11b362b15af34006e6a11974088a46d42b903418eJohann/* 21b362b15af34006e6a11974088a46d42b903418eJohann * Copyright (c) 2010 The WebM project authors. All Rights Reserved. 31b362b15af34006e6a11974088a46d42b903418eJohann * 41b362b15af34006e6a11974088a46d42b903418eJohann * Use of this source code is governed by a BSD-style license 51b362b15af34006e6a11974088a46d42b903418eJohann * that can be found in the LICENSE file in the root of the source 61b362b15af34006e6a11974088a46d42b903418eJohann * tree. An additional intellectual property rights grant can be found 71b362b15af34006e6a11974088a46d42b903418eJohann * in the file PATENTS. All contributing project authors may 81b362b15af34006e6a11974088a46d42b903418eJohann * be found in the AUTHORS file in the root of the source tree. 91b362b15af34006e6a11974088a46d42b903418eJohann */ 101b362b15af34006e6a11974088a46d42b903418eJohann 111b362b15af34006e6a11974088a46d42b903418eJohann 121b362b15af34006e6a11974088a46d42b903418eJohann#include "extend.h" 131b362b15af34006e6a11974088a46d42b903418eJohann#include "vpx_mem/vpx_mem.h" 141b362b15af34006e6a11974088a46d42b903418eJohann 151b362b15af34006e6a11974088a46d42b903418eJohann 161b362b15af34006e6a11974088a46d42b903418eJohannstatic void copy_and_extend_plane 171b362b15af34006e6a11974088a46d42b903418eJohann( 181b362b15af34006e6a11974088a46d42b903418eJohann unsigned char *s, /* source */ 191b362b15af34006e6a11974088a46d42b903418eJohann int sp, /* source pitch */ 201b362b15af34006e6a11974088a46d42b903418eJohann unsigned char *d, /* destination */ 211b362b15af34006e6a11974088a46d42b903418eJohann int dp, /* destination pitch */ 221b362b15af34006e6a11974088a46d42b903418eJohann int h, /* height */ 231b362b15af34006e6a11974088a46d42b903418eJohann int w, /* width */ 241b362b15af34006e6a11974088a46d42b903418eJohann int et, /* extend top border */ 251b362b15af34006e6a11974088a46d42b903418eJohann int el, /* extend left border */ 261b362b15af34006e6a11974088a46d42b903418eJohann int eb, /* extend bottom border */ 271b362b15af34006e6a11974088a46d42b903418eJohann int er /* extend right border */ 281b362b15af34006e6a11974088a46d42b903418eJohann) 291b362b15af34006e6a11974088a46d42b903418eJohann{ 301b362b15af34006e6a11974088a46d42b903418eJohann int i; 311b362b15af34006e6a11974088a46d42b903418eJohann unsigned char *src_ptr1, *src_ptr2; 321b362b15af34006e6a11974088a46d42b903418eJohann unsigned char *dest_ptr1, *dest_ptr2; 331b362b15af34006e6a11974088a46d42b903418eJohann int linesize; 341b362b15af34006e6a11974088a46d42b903418eJohann 351b362b15af34006e6a11974088a46d42b903418eJohann /* copy the left and right most columns out */ 361b362b15af34006e6a11974088a46d42b903418eJohann src_ptr1 = s; 371b362b15af34006e6a11974088a46d42b903418eJohann src_ptr2 = s + w - 1; 381b362b15af34006e6a11974088a46d42b903418eJohann dest_ptr1 = d - el; 391b362b15af34006e6a11974088a46d42b903418eJohann dest_ptr2 = d + w; 401b362b15af34006e6a11974088a46d42b903418eJohann 411b362b15af34006e6a11974088a46d42b903418eJohann for (i = 0; i < h; i++) 421b362b15af34006e6a11974088a46d42b903418eJohann { 43da49e34c1fb5e99681f4ad99c21d9cfd83eddb96Vignesh Venkatasubramanian memset(dest_ptr1, src_ptr1[0], el); 44da49e34c1fb5e99681f4ad99c21d9cfd83eddb96Vignesh Venkatasubramanian memcpy(dest_ptr1 + el, src_ptr1, w); 45da49e34c1fb5e99681f4ad99c21d9cfd83eddb96Vignesh Venkatasubramanian memset(dest_ptr2, src_ptr2[0], er); 461b362b15af34006e6a11974088a46d42b903418eJohann src_ptr1 += sp; 471b362b15af34006e6a11974088a46d42b903418eJohann src_ptr2 += sp; 481b362b15af34006e6a11974088a46d42b903418eJohann dest_ptr1 += dp; 491b362b15af34006e6a11974088a46d42b903418eJohann dest_ptr2 += dp; 501b362b15af34006e6a11974088a46d42b903418eJohann } 511b362b15af34006e6a11974088a46d42b903418eJohann 521b362b15af34006e6a11974088a46d42b903418eJohann /* Now copy the top and bottom lines into each line of the respective 531b362b15af34006e6a11974088a46d42b903418eJohann * borders 541b362b15af34006e6a11974088a46d42b903418eJohann */ 551b362b15af34006e6a11974088a46d42b903418eJohann src_ptr1 = d - el; 561b362b15af34006e6a11974088a46d42b903418eJohann src_ptr2 = d + dp * (h - 1) - el; 571b362b15af34006e6a11974088a46d42b903418eJohann dest_ptr1 = d + dp * (-et) - el; 581b362b15af34006e6a11974088a46d42b903418eJohann dest_ptr2 = d + dp * (h) - el; 591b362b15af34006e6a11974088a46d42b903418eJohann linesize = el + er + w; 601b362b15af34006e6a11974088a46d42b903418eJohann 611b362b15af34006e6a11974088a46d42b903418eJohann for (i = 0; i < et; i++) 621b362b15af34006e6a11974088a46d42b903418eJohann { 63da49e34c1fb5e99681f4ad99c21d9cfd83eddb96Vignesh Venkatasubramanian memcpy(dest_ptr1, src_ptr1, linesize); 641b362b15af34006e6a11974088a46d42b903418eJohann dest_ptr1 += dp; 651b362b15af34006e6a11974088a46d42b903418eJohann } 661b362b15af34006e6a11974088a46d42b903418eJohann 671b362b15af34006e6a11974088a46d42b903418eJohann for (i = 0; i < eb; i++) 681b362b15af34006e6a11974088a46d42b903418eJohann { 69da49e34c1fb5e99681f4ad99c21d9cfd83eddb96Vignesh Venkatasubramanian memcpy(dest_ptr2, src_ptr2, linesize); 701b362b15af34006e6a11974088a46d42b903418eJohann dest_ptr2 += dp; 711b362b15af34006e6a11974088a46d42b903418eJohann } 721b362b15af34006e6a11974088a46d42b903418eJohann} 731b362b15af34006e6a11974088a46d42b903418eJohann 741b362b15af34006e6a11974088a46d42b903418eJohann 751b362b15af34006e6a11974088a46d42b903418eJohannvoid vp8_copy_and_extend_frame(YV12_BUFFER_CONFIG *src, 761b362b15af34006e6a11974088a46d42b903418eJohann YV12_BUFFER_CONFIG *dst) 771b362b15af34006e6a11974088a46d42b903418eJohann{ 781b362b15af34006e6a11974088a46d42b903418eJohann int et = dst->border; 791b362b15af34006e6a11974088a46d42b903418eJohann int el = dst->border; 801b362b15af34006e6a11974088a46d42b903418eJohann int eb = dst->border + dst->y_height - src->y_height; 811b362b15af34006e6a11974088a46d42b903418eJohann int er = dst->border + dst->y_width - src->y_width; 821b362b15af34006e6a11974088a46d42b903418eJohann 831b362b15af34006e6a11974088a46d42b903418eJohann copy_and_extend_plane(src->y_buffer, src->y_stride, 841b362b15af34006e6a11974088a46d42b903418eJohann dst->y_buffer, dst->y_stride, 851b362b15af34006e6a11974088a46d42b903418eJohann src->y_height, src->y_width, 861b362b15af34006e6a11974088a46d42b903418eJohann et, el, eb, er); 871b362b15af34006e6a11974088a46d42b903418eJohann 881b362b15af34006e6a11974088a46d42b903418eJohann et = dst->border >> 1; 891b362b15af34006e6a11974088a46d42b903418eJohann el = dst->border >> 1; 901b362b15af34006e6a11974088a46d42b903418eJohann eb = (dst->border >> 1) + dst->uv_height - src->uv_height; 911b362b15af34006e6a11974088a46d42b903418eJohann er = (dst->border >> 1) + dst->uv_width - src->uv_width; 921b362b15af34006e6a11974088a46d42b903418eJohann 931b362b15af34006e6a11974088a46d42b903418eJohann copy_and_extend_plane(src->u_buffer, src->uv_stride, 941b362b15af34006e6a11974088a46d42b903418eJohann dst->u_buffer, dst->uv_stride, 951b362b15af34006e6a11974088a46d42b903418eJohann src->uv_height, src->uv_width, 961b362b15af34006e6a11974088a46d42b903418eJohann et, el, eb, er); 971b362b15af34006e6a11974088a46d42b903418eJohann 981b362b15af34006e6a11974088a46d42b903418eJohann copy_and_extend_plane(src->v_buffer, src->uv_stride, 991b362b15af34006e6a11974088a46d42b903418eJohann dst->v_buffer, dst->uv_stride, 1001b362b15af34006e6a11974088a46d42b903418eJohann src->uv_height, src->uv_width, 1011b362b15af34006e6a11974088a46d42b903418eJohann et, el, eb, er); 1021b362b15af34006e6a11974088a46d42b903418eJohann} 1031b362b15af34006e6a11974088a46d42b903418eJohann 1041b362b15af34006e6a11974088a46d42b903418eJohann 1051b362b15af34006e6a11974088a46d42b903418eJohannvoid vp8_copy_and_extend_frame_with_rect(YV12_BUFFER_CONFIG *src, 1061b362b15af34006e6a11974088a46d42b903418eJohann YV12_BUFFER_CONFIG *dst, 1071b362b15af34006e6a11974088a46d42b903418eJohann int srcy, int srcx, 1081b362b15af34006e6a11974088a46d42b903418eJohann int srch, int srcw) 1091b362b15af34006e6a11974088a46d42b903418eJohann{ 1101b362b15af34006e6a11974088a46d42b903418eJohann int et = dst->border; 1111b362b15af34006e6a11974088a46d42b903418eJohann int el = dst->border; 1121b362b15af34006e6a11974088a46d42b903418eJohann int eb = dst->border + dst->y_height - src->y_height; 1131b362b15af34006e6a11974088a46d42b903418eJohann int er = dst->border + dst->y_width - src->y_width; 1141b362b15af34006e6a11974088a46d42b903418eJohann int src_y_offset = srcy * src->y_stride + srcx; 1151b362b15af34006e6a11974088a46d42b903418eJohann int dst_y_offset = srcy * dst->y_stride + srcx; 1161b362b15af34006e6a11974088a46d42b903418eJohann int src_uv_offset = ((srcy * src->uv_stride) >> 1) + (srcx >> 1); 1171b362b15af34006e6a11974088a46d42b903418eJohann int dst_uv_offset = ((srcy * dst->uv_stride) >> 1) + (srcx >> 1); 1181b362b15af34006e6a11974088a46d42b903418eJohann 1191b362b15af34006e6a11974088a46d42b903418eJohann /* If the side is not touching the bounder then don't extend. */ 1201b362b15af34006e6a11974088a46d42b903418eJohann if (srcy) 1211b362b15af34006e6a11974088a46d42b903418eJohann et = 0; 1221b362b15af34006e6a11974088a46d42b903418eJohann if (srcx) 1231b362b15af34006e6a11974088a46d42b903418eJohann el = 0; 1241b362b15af34006e6a11974088a46d42b903418eJohann if (srcy + srch != src->y_height) 1251b362b15af34006e6a11974088a46d42b903418eJohann eb = 0; 1261b362b15af34006e6a11974088a46d42b903418eJohann if (srcx + srcw != src->y_width) 1271b362b15af34006e6a11974088a46d42b903418eJohann er = 0; 1281b362b15af34006e6a11974088a46d42b903418eJohann 1291b362b15af34006e6a11974088a46d42b903418eJohann copy_and_extend_plane(src->y_buffer + src_y_offset, 1301b362b15af34006e6a11974088a46d42b903418eJohann src->y_stride, 1311b362b15af34006e6a11974088a46d42b903418eJohann dst->y_buffer + dst_y_offset, 1321b362b15af34006e6a11974088a46d42b903418eJohann dst->y_stride, 1331b362b15af34006e6a11974088a46d42b903418eJohann srch, srcw, 1341b362b15af34006e6a11974088a46d42b903418eJohann et, el, eb, er); 1351b362b15af34006e6a11974088a46d42b903418eJohann 1361b362b15af34006e6a11974088a46d42b903418eJohann et = (et + 1) >> 1; 1371b362b15af34006e6a11974088a46d42b903418eJohann el = (el + 1) >> 1; 1381b362b15af34006e6a11974088a46d42b903418eJohann eb = (eb + 1) >> 1; 1391b362b15af34006e6a11974088a46d42b903418eJohann er = (er + 1) >> 1; 1401b362b15af34006e6a11974088a46d42b903418eJohann srch = (srch + 1) >> 1; 1411b362b15af34006e6a11974088a46d42b903418eJohann srcw = (srcw + 1) >> 1; 1421b362b15af34006e6a11974088a46d42b903418eJohann 1431b362b15af34006e6a11974088a46d42b903418eJohann copy_and_extend_plane(src->u_buffer + src_uv_offset, 1441b362b15af34006e6a11974088a46d42b903418eJohann src->uv_stride, 1451b362b15af34006e6a11974088a46d42b903418eJohann dst->u_buffer + dst_uv_offset, 1461b362b15af34006e6a11974088a46d42b903418eJohann dst->uv_stride, 1471b362b15af34006e6a11974088a46d42b903418eJohann srch, srcw, 1481b362b15af34006e6a11974088a46d42b903418eJohann et, el, eb, er); 1491b362b15af34006e6a11974088a46d42b903418eJohann 1501b362b15af34006e6a11974088a46d42b903418eJohann copy_and_extend_plane(src->v_buffer + src_uv_offset, 1511b362b15af34006e6a11974088a46d42b903418eJohann src->uv_stride, 1521b362b15af34006e6a11974088a46d42b903418eJohann dst->v_buffer + dst_uv_offset, 1531b362b15af34006e6a11974088a46d42b903418eJohann dst->uv_stride, 1541b362b15af34006e6a11974088a46d42b903418eJohann srch, srcw, 1551b362b15af34006e6a11974088a46d42b903418eJohann et, el, eb, er); 1561b362b15af34006e6a11974088a46d42b903418eJohann} 1571b362b15af34006e6a11974088a46d42b903418eJohann 1581b362b15af34006e6a11974088a46d42b903418eJohann 1591b362b15af34006e6a11974088a46d42b903418eJohann/* note the extension is only for the last row, for intra prediction purpose */ 1601b362b15af34006e6a11974088a46d42b903418eJohannvoid vp8_extend_mb_row(YV12_BUFFER_CONFIG *ybf, 1611b362b15af34006e6a11974088a46d42b903418eJohann unsigned char *YPtr, 1621b362b15af34006e6a11974088a46d42b903418eJohann unsigned char *UPtr, 1631b362b15af34006e6a11974088a46d42b903418eJohann unsigned char *VPtr) 1641b362b15af34006e6a11974088a46d42b903418eJohann{ 1651b362b15af34006e6a11974088a46d42b903418eJohann int i; 1661b362b15af34006e6a11974088a46d42b903418eJohann 1671b362b15af34006e6a11974088a46d42b903418eJohann YPtr += ybf->y_stride * 14; 1681b362b15af34006e6a11974088a46d42b903418eJohann UPtr += ybf->uv_stride * 6; 1691b362b15af34006e6a11974088a46d42b903418eJohann VPtr += ybf->uv_stride * 6; 1701b362b15af34006e6a11974088a46d42b903418eJohann 1711b362b15af34006e6a11974088a46d42b903418eJohann for (i = 0; i < 4; i++) 1721b362b15af34006e6a11974088a46d42b903418eJohann { 1731b362b15af34006e6a11974088a46d42b903418eJohann YPtr[i] = YPtr[-1]; 1741b362b15af34006e6a11974088a46d42b903418eJohann UPtr[i] = UPtr[-1]; 1751b362b15af34006e6a11974088a46d42b903418eJohann VPtr[i] = VPtr[-1]; 1761b362b15af34006e6a11974088a46d42b903418eJohann } 1771b362b15af34006e6a11974088a46d42b903418eJohann 1781b362b15af34006e6a11974088a46d42b903418eJohann YPtr += ybf->y_stride; 1791b362b15af34006e6a11974088a46d42b903418eJohann UPtr += ybf->uv_stride; 1801b362b15af34006e6a11974088a46d42b903418eJohann VPtr += ybf->uv_stride; 1811b362b15af34006e6a11974088a46d42b903418eJohann 1821b362b15af34006e6a11974088a46d42b903418eJohann for (i = 0; i < 4; i++) 1831b362b15af34006e6a11974088a46d42b903418eJohann { 1841b362b15af34006e6a11974088a46d42b903418eJohann YPtr[i] = YPtr[-1]; 1851b362b15af34006e6a11974088a46d42b903418eJohann UPtr[i] = UPtr[-1]; 1861b362b15af34006e6a11974088a46d42b903418eJohann VPtr[i] = VPtr[-1]; 1871b362b15af34006e6a11974088a46d42b903418eJohann } 1881b362b15af34006e6a11974088a46d42b903418eJohann} 189