Hello.
It seems the ipp 2018.3.210 contains a bug in the ippiWarpPerspectiveLinear_8u_C1R function.
The following sequence of code generates exception (Unhandled exception at 0x776DE9A3 (ntdll.dll) in blabla.exe: 0xC0000374: A heap has been corrupted (parameters: 0x77714270).) after last function call (all params are correct and the resulting image is also ok):
int specSize, buffSize; ippCheck(ippiWarpQuadGetSize( IppiSize(src.size()), srcQuad, IppiSize(dst.size()), dstQuad, ippWarpPerspective, ipp8u, ippLinear, ippBorderTransp, &specSize, &buffSize)); IppBuff<IppiWarpSpec> spec(specSize); ippCheck(ippiWarpQuadLinearInit( IppiSize(src.size()), srcQuad, IppiSize(dst.size()), dstQuad, ippWarpPerspective, ipp8u, 1, ippBorderTransp, 0, 0, spec.ptr())); IppBuff<Ipp8u> buffer(buffSize); ippCheck(ippiWarpPerspectiveLinear_8u_C1R( src.ptr(), (int)src.step, dst.ptr(), (int)dst.step, IppiPoint(), IppiSize(dst.size()), spec.ptr(), buffer.ptr()));
Link Copied
Hello,
thank for the report, will investigate and report about results.
Pavel
update:
I use 32 bit static libraries.
I've checked versions 2017.1.143 and 2017.4.210 - all the same.
ippiWarpAffineLinear_8u_C1R works fine.
OS Windows 7 (x64), Visual Studio 2015.
P.S. IppBuff<> is my wrapper around ippMalloc / ippFree; ippCheck() just checks the function return values.
Hi Alexander,
Could you please provide the simple reproducer with actual parameters values? Or at least image sizes.
Best regards,
Tatyana
source image size: 438 x 270
destination image size: 768 x 160
source quadrangle is convex and about 270 x 100 inside source image
destination quadrangle is the whole destination image.
Alexander,
I've checked your reproducer and found that you missed ippiWarpGetBufferSize usage for defining the size of buffer for ippiWarpPerspectiveLinear_8u_C1R.
Please see an example here: https://software.intel.com/en-us/ipp-dev-reference-warpquadnearestinit-sample
And the documentation for ippiWarpPerspectiveLinear https://software.intel.com/en-us/ipp-dev-reference-warpperspectivelinear
Also please find the fixed version of your example:
#include <ipp.h> #include <vector> #include <iostream> #include <Windows.h> class HeapChecker { private: void check() const {_heapchk();} public: explicit HeapChecker() {check();} ~HeapChecker() {check();} }; int main() { const int srcW = 438, srcH = 270, dstW = 768, dstH = 160; std::vector<Ipp8u> src(srcW * srcH); std::vector<Ipp8u> dst(dstW * dstH); double srcQuad[4][2] = {{82., 140.}, {355., 134.}, {352., 221.}, {82., 218.}}; double dstQuad[4][2] = {{0., 0.}, {767., 0.}, {767., 159.}, {0., 159.}}; IppStatus sts = ippStsNoErr; int specSize, buffSize; sts = ippiWarpQuadGetSize( IppiSize{srcW, srcH}, srcQuad, IppiSize{dstW, dstH}, dstQuad, ippWarpPerspective, ipp8u, ippLinear, ippBorderTransp, &specSize, &buffSize); IppiWarpSpec *spec = (IppiWarpSpec*)ippsMalloc_8u(specSize); sts = ippiWarpQuadLinearInit( IppiSize{srcW, srcH}, srcQuad, IppiSize{dstW, dstH}, dstQuad, ippWarpPerspective, ipp8u, 1, ippBorderTransp, 0, 0, spec); sts = ippiWarpGetBufferSize(spec, IppiSize{ dstW, dstH }, &buffSize); Ipp8u *buffer = ippsMalloc_8u(buffSize); { HeapChecker heap_checker; sts = ippiWarpPerspectiveLinear_8u_C1R( src.data(), srcW, dst.data(), dstW, IppiPoint(), IppiSize{dstW, dstH}, spec, buffer); } std::cout << "I'm happy if you see this"; ippFree(spec); ippFree(buffer); }
Best regards,
Tatyana
Thank very much you for your assistance.
Yes, it was my fault.
P.S. In my defence I'd like to say that the functions call logic seems to me rather weird: why do we need to submit &buffSize at the ippiWarpQuadGetSize function call if the real buffer size is calculated by another function - ippiWarpGetBufferSize ?
Alexander,
ippiWarpQuadGetSize calculates buffer size for Init functions. In case of Linear interpolation additional buffer is not required. But in case of Cubic one you can see the last parameter - Init Buffer (https://software.intel.com/en-us/ipp-dev-reference-warpperspectivecubicinit).
So it was introduced 1 API to cover all possible cases of interpolations.
Best regards,
Tatyana
For more complete information about compiler optimizations, see our Optimization Notice.