Merge pull request #21228 from alalek:issue_21198

pull/21235/head
Alexander Alekhin 3 years ago
commit c4ab0c09ea
  1. 8
      modules/imgproc/src/opencl/resize.cl
  2. 3
      modules/imgproc/src/resize.cpp
  3. 14
      modules/imgproc/test/ocl/test_warp.cpp

@ -51,8 +51,6 @@
#endif
#endif
#define INTER_RESIZE_COEF_SCALE (1 << INTER_RESIZE_COEF_BITS)
#define CAST_BITS (INTER_RESIZE_COEF_BITS << 1)
#define INC(x,l) min(x+1,l-1)
#define noconvert
@ -188,7 +186,9 @@ __kernel void resizeLN(__global const uchar * srcptr, int src_step, int src_offs
int y_ = INC(y, src_rows);
int x_ = INC(x, src_cols);
#if depth <= 4
#if depth <= 1 // 8U/8S only, 16U+ cause integer overflows
#define INTER_RESIZE_COEF_SCALE (1 << INTER_RESIZE_COEF_BITS)
#define CAST_BITS (INTER_RESIZE_COEF_BITS << 1)
u = u * INTER_RESIZE_COEF_SCALE;
v = v * INTER_RESIZE_COEF_SCALE;
@ -214,7 +214,7 @@ __kernel void resizeLN(__global const uchar * srcptr, int src_step, int src_offs
WT data2 = convertToWT(loadpix(srcptr + mad24(y_, src_step, mad24(x, TSIZE, src_offset))));
WT data3 = convertToWT(loadpix(srcptr + mad24(y_, src_step, mad24(x_, TSIZE, src_offset))));
T uval = u1 * v1 * data0 + u * v1 * data1 + u1 * v *data2 + u * v *data3;
T uval = convertToDT((u1 * v1) * data0 + (u * v1) * data1 + (u1 * v) * data2 + (u * v) * data3);
#endif
storepix(uval, dstptr + mad24(dy, dst_step, mad24(dx, TSIZE, dst_offset)));
}

@ -3376,7 +3376,8 @@ static bool ocl_resize( InputArray _src, OutputArray _dst, Size dsize,
}
else
{
int wdepth = std::max(depth, CV_32S), wtype = CV_MAKETYPE(wdepth, cn);
int wdepth = depth <= CV_8S ? CV_32S : std::max(depth, CV_32F);
int wtype = CV_MAKETYPE(wdepth, cn);
k.create("resizeLN", ocl::imgproc::resize_oclsrc,
format("-D INTER_LINEAR -D depth=%d -D T=%s -D T1=%s "
"-D WT=%s -D convertToWT=%s -D convertToDT=%s -D cn=%d "

@ -327,6 +327,20 @@ OCL_TEST_P(Resize, Mat)
}
}
OCL_TEST(Resize, overflow_21198)
{
Mat src(Size(600, 600), CV_16UC3, Scalar::all(32768));
UMat src_u;
src.copyTo(src_u);
Mat dst;
cv::resize(src, dst, Size(1024, 1024), 0, 0, INTER_LINEAR);
UMat dst_u;
cv::resize(src_u, dst_u, Size(1024, 1024), 0, 0, INTER_LINEAR);
EXPECT_LE(cv::norm(dst_u, dst, NORM_INF), 1.0f);
}
/////////////////////////////////////////////////////////////////////////////////////////////////
// remap

Loading…
Cancel
Save