From 579113950cb718e93cf4e9197738e56bfd725543 Mon Sep 17 00:00:00 2001 From: "fbarchard@google.com" Date: Tue, 20 Nov 2012 22:22:33 +0000 Subject: [PATCH] check for interpolation of 0 and do a memcpy to avoid touching the row + 1 which may be one past the end of the buffer. BUG=153 TEST=valgrind Review URL: https://webrtc-codereview.appspot.com/930026 git-svn-id: http://libyuv.googlecode.com/svn/trunk@500 16f28f9a-4ce2-e073-06de-1de4eb20be90 --- README.chromium | 2 +- include/libyuv/version.h | 2 +- source/scale.cc | 16 ++++++++++------ source/scale_argb.cc | 20 +++++++++++++++----- 4 files changed, 27 insertions(+), 13 deletions(-) diff --git a/README.chromium b/README.chromium index a52ace54c..a99b02fa3 100644 --- a/README.chromium +++ b/README.chromium @@ -1,6 +1,6 @@ Name: libyuv URL: http://code.google.com/p/libyuv/ -Version: 499 +Version: 500 License: BSD License File: LICENSE diff --git a/include/libyuv/version.h b/include/libyuv/version.h index fa5e98d49..fb8f06735 100644 --- a/include/libyuv/version.h +++ b/include/libyuv/version.h @@ -11,6 +11,6 @@ #ifndef INCLUDE_LIBYUV_VERSION_H_ // NOLINT #define INCLUDE_LIBYUV_VERSION_H_ -#define LIBYUV_VERSION 499 +#define LIBYUV_VERSION 500 #endif // INCLUDE_LIBYUV_VERSION_H_ NOLINT diff --git a/source/scale.cc b/source/scale.cc index d8315bf81..d4ff9dbc5 100644 --- a/source/scale.cc +++ b/source/scale.cc @@ -2559,10 +2559,17 @@ static void ScaleFilterRows_C(uint8* dst_ptr, const uint8* src_ptr, ptrdiff_t src_stride, int dst_width, int source_y_fraction) { assert(dst_width > 0); + // Specialized case for 100% first row. Helps avoid reading beyond last row. + if (source_y_fraction == 0) { + memcpy(dst_ptr, src_ptr, dst_width); + dst_ptr[dst_width] = dst_ptr[dst_width - 1]; + return; + } int y1_fraction = source_y_fraction; int y0_fraction = 256 - y1_fraction; const uint8* src_ptr1 = src_ptr + src_stride; + for (int x = 0; x < dst_width - 1; x += 2) { dst_ptr[0] = (src_ptr[0] * y0_fraction + src_ptr1[0] * y1_fraction) >> 8; dst_ptr[1] = (src_ptr[1] * y0_fraction + src_ptr1[1] * y1_fraction) >> 8; @@ -3115,10 +3122,10 @@ void ScalePlaneBilinear(int src_width, int src_height, int x = (dx >= 65536) ? ((dx >> 1) - 32768) : (dx >> 1); int y = (dy >= 65536) ? ((dy >> 1) - 32768) : (dy >> 1); int maxy = (src_height > 1) ? ((src_height - 1) << 16) - 1 : 0; - if (y > maxy) { - y = maxy; - } for (int j = 0; j < dst_height; ++j) { + if (y > maxy) { + y = maxy; + } int yi = y >> 16; int yf = (y >> 8) & 255; const uint8* src = src_ptr + yi * src_stride; @@ -3127,9 +3134,6 @@ void ScalePlaneBilinear(int src_width, int src_height, ScaleFilterCols_C(dst_ptr, row, dst_width, x, dx); dst_ptr += dst_stride; y += dy; - if (y > maxy) { - y = maxy; - } } } } diff --git a/source/scale_argb.cc b/source/scale_argb.cc index 4b2259c4f..635269ad2 100644 --- a/source/scale_argb.cc +++ b/source/scale_argb.cc @@ -838,13 +838,21 @@ static void ScaleARGBFilterCols_C(uint8* dst_argb, const uint8* src_argb, } } -static const int kMaxInputWidth = 2560; - // C version 2x2 -> 2x1 void ScaleARGBFilterRows_C(uint8* dst_argb, const uint8* src_argb, ptrdiff_t src_stride, int dst_width, int source_y_fraction) { assert(dst_width > 0); + // Specialized case for 100% first row. Helps avoid reading beyond last row. + if (source_y_fraction == 0) { + memcpy(dst_argb, src_argb, dst_width * 4); + dst_argb += dst_width * 4; + dst_argb[0] = dst_argb[-4]; + dst_argb[1] = dst_argb[-3]; + dst_argb[2] = dst_argb[-2]; + dst_argb[3] = dst_argb[-1]; + return; + } int y1_fraction = source_y_fraction; int y0_fraction = 256 - y1_fraction; const uint8* src_ptr1 = src_argb + src_stride; @@ -953,6 +961,8 @@ static void ScaleARGBDownEven(int src_width, int src_height, * interpolation. */ +// Maximum width handled by 2 pass Bilinear. +static const int kMaxInputWidth = 2560; static void ScaleARGBBilinear(int src_width, int src_height, int dst_width, int dst_height, int src_stride, int dst_stride, @@ -989,6 +999,9 @@ static void ScaleARGBBilinear(int src_width, int src_height, int y = (dy >= 65536) ? ((dy >> 1) - 32768) : (dy >> 1); int maxy = (src_height > 1) ? ((src_height - 1) << 16) - 1 : 0; for (int j = 0; j < dst_height; ++j) { + if (y > maxy) { + y = maxy; + } int yi = y >> 16; int yf = (y >> 8) & 255; const uint8* src = src_argb + yi * src_stride; @@ -996,9 +1009,6 @@ static void ScaleARGBBilinear(int src_width, int src_height, ScaleARGBFilterCols_C(dst_argb, row, dst_width, x, dx); dst_argb += dst_stride; y += dy; - if (y > maxy) { - y = maxy; - } } }