/*M/////////////////////////////////////////////////////////////////////////////////////// // // IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING. // // By downloading, copying, installing or using the software you agree to this license. // If you do not agree to this license, do not download, install, // copy or use the software. // // // Intel License Agreement // For Open Source Computer Vision Library // // Copyright (C) 2000, Intel Corporation, all rights reserved. // Third party copyrights are property of their respective owners. // // Redistribution and use in source and binary forms, with or without modification, // are permitted provided that the following conditions are met: // // * Redistribution's of source code must retain the above copyright notice, // this list of conditions and the following disclaimer. // // * Redistribution's in binary form must reproduce the above copyright notice, // this list of conditions and the following disclaimer in the documentation // and/or other materials provided with the distribution. // // * The name of Intel Corporation may not be used to endorse or promote products // derived from this software without specific prior written permission. // // This software is provided by the copyright holders and contributors "as is" and // any express or implied warranties, including, but not limited to, the implied // warranties of merchantability and fitness for a particular purpose are disclaimed. // In no event shall the Intel Corporation or contributors be liable for any direct, // indirect, incidental, special, exemplary, or consequential damages // (including, but not limited to, procurement of substitute goods or services; // loss of use, data, or profits; or business interruption) however caused // and on any theory of liability, whether in contract, strict liability, // or tort (including negligence or otherwise) arising in any way out of // the use of this software, even if advised of the possibility of such damage. // //M*/ #include "test_precomp.hpp" #ifdef HAVE_CUDA namespace { //////////////////////////////////////////////////////////////////////////////// // Merge PARAM_TEST_CASE(Merge, cv::gpu::DeviceInfo, cv::Size, MatDepth, Channels, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; int depth; int channels; bool useRoi; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); channels = GET_PARAM(3); useRoi = GET_PARAM(4); cv::gpu::setDevice(devInfo.deviceID()); } }; TEST_P(Merge, Accuracy) { std::vector src; src.reserve(channels); for (int i = 0; i < channels; ++i) src.push_back(cv::Mat(size, depth, cv::Scalar::all(i))); std::vector d_src; for (int i = 0; i < channels; ++i) d_src.push_back(loadMat(src[i], useRoi)); if (depth == CV_64F && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::merge(d_src, dst); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst; cv::gpu::merge(d_src, dst); cv::Mat dst_gold; cv::merge(src, dst_gold); EXPECT_MAT_NEAR(dst_gold, dst, 0.0); } } INSTANTIATE_TEST_CASE_P(GPU_Core, Merge, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, ALL_DEPTH, testing::Values(1, 2, 3, 4), WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Split PARAM_TEST_CASE(Split, cv::gpu::DeviceInfo, cv::Size, MatDepth, Channels, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; int depth; int channels; bool useRoi; int type; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); channels = GET_PARAM(3); useRoi = GET_PARAM(4); cv::gpu::setDevice(devInfo.deviceID()); type = CV_MAKE_TYPE(depth, channels); } }; TEST_P(Split, Accuracy) { cv::Mat src = randomMat(size, type); if (depth == CV_64F && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { std::vector dst; cv::gpu::split(loadMat(src), dst); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { std::vector dst; cv::gpu::split(loadMat(src, useRoi), dst); std::vector dst_gold; cv::split(src, dst_gold); ASSERT_EQ(dst_gold.size(), dst.size()); for (size_t i = 0; i < dst_gold.size(); ++i) { EXPECT_MAT_NEAR(dst_gold[i], dst[i], 0.0); } } } INSTANTIATE_TEST_CASE_P(GPU_Core, Split, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, ALL_DEPTH, testing::Values(1, 2, 3, 4), WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Add_Array PARAM_TEST_CASE(Add_Array, cv::gpu::DeviceInfo, cv::Size, std::pair, Channels, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; std::pair depth; int channels; bool useRoi; int stype; int dtype; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); channels = GET_PARAM(3); useRoi = GET_PARAM(4); cv::gpu::setDevice(devInfo.deviceID()); stype = CV_MAKE_TYPE(depth.first, channels); dtype = CV_MAKE_TYPE(depth.second, channels); } }; TEST_P(Add_Array, Accuracy) { cv::Mat mat1 = randomMat(size, stype); cv::Mat mat2 = randomMat(size, stype); cv::Mat mask = randomMat(size, CV_8UC1, 0.0, 2.0); if ((depth.first == CV_64F || depth.second == CV_64F) && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::add(loadMat(mat1), loadMat(mat2), dst, cv::gpu::GpuMat(), depth.second); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, dtype, useRoi); dst.setTo(cv::Scalar::all(0)); cv::gpu::add(loadMat(mat1, useRoi), loadMat(mat2, useRoi), dst, channels == 1 ? loadMat(mask, useRoi) : cv::gpu::GpuMat(), depth.second); cv::Mat dst_gold(size, dtype, cv::Scalar::all(0)); cv::add(mat1, mat2, dst_gold, channels == 1 ? mask : cv::noArray(), depth.second); EXPECT_MAT_NEAR(dst_gold, dst, depth.first >= CV_32F || depth.second >= CV_32F ? 1e-4 : 0.0); } } INSTANTIATE_TEST_CASE_P(GPU_Core, Add_Array, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, DEPTH_PAIRS, ALL_CHANNELS, WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Add_Scalar PARAM_TEST_CASE(Add_Scalar, cv::gpu::DeviceInfo, cv::Size, std::pair, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; std::pair depth; bool useRoi; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); useRoi = GET_PARAM(3); cv::gpu::setDevice(devInfo.deviceID()); } }; TEST_P(Add_Scalar, WithOutMask) { cv::Mat mat = randomMat(size, depth.first); cv::Scalar val = randomScalar(0, 255); if ((depth.first == CV_64F || depth.second == CV_64F) && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::add(loadMat(mat), val, dst, cv::gpu::GpuMat(), depth.second); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, depth.second, useRoi); dst.setTo(cv::Scalar::all(0)); cv::gpu::add(loadMat(mat, useRoi), val, dst, cv::gpu::GpuMat(), depth.second); cv::Mat dst_gold(size, depth.second, cv::Scalar::all(0)); cv::add(mat, val, dst_gold, cv::noArray(), depth.second); EXPECT_MAT_NEAR(dst_gold, dst, depth.first >= CV_32F || depth.second >= CV_32F ? 1e-4 : 0.0); } } TEST_P(Add_Scalar, WithMask) { cv::Mat mat = randomMat(size, depth.first); cv::Scalar val = randomScalar(0, 255); cv::Mat mask = randomMat(size, CV_8UC1, 0.0, 2.0); if ((depth.first == CV_64F || depth.second == CV_64F) && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::add(loadMat(mat), val, dst, cv::gpu::GpuMat(), depth.second); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, depth.second, useRoi); dst.setTo(cv::Scalar::all(0)); cv::gpu::add(loadMat(mat, useRoi), val, dst, loadMat(mask, useRoi), depth.second); cv::Mat dst_gold(size, depth.second, cv::Scalar::all(0)); cv::add(mat, val, dst_gold, mask, depth.second); EXPECT_MAT_NEAR(dst_gold, dst, depth.first >= CV_32F || depth.second >= CV_32F ? 1e-4 : 0.0); } } INSTANTIATE_TEST_CASE_P(GPU_Core, Add_Scalar, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, DEPTH_PAIRS, WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Subtract_Array PARAM_TEST_CASE(Subtract_Array, cv::gpu::DeviceInfo, cv::Size, std::pair, Channels, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; std::pair depth; int channels; bool useRoi; int stype; int dtype; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); channels = GET_PARAM(3); useRoi = GET_PARAM(4); cv::gpu::setDevice(devInfo.deviceID()); stype = CV_MAKE_TYPE(depth.first, channels); dtype = CV_MAKE_TYPE(depth.second, channels); } }; TEST_P(Subtract_Array, Accuracy) { cv::Mat mat1 = randomMat(size, stype); cv::Mat mat2 = randomMat(size, stype); cv::Mat mask = randomMat(size, CV_8UC1, 0.0, 2.0); if ((depth.first == CV_64F || depth.second == CV_64F) && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::subtract(loadMat(mat1), loadMat(mat2), dst, cv::gpu::GpuMat(), depth.second); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, dtype, useRoi); dst.setTo(cv::Scalar::all(0)); cv::gpu::subtract(loadMat(mat1, useRoi), loadMat(mat2, useRoi), dst, channels == 1 ? loadMat(mask, useRoi) : cv::gpu::GpuMat(), depth.second); cv::Mat dst_gold(size, dtype, cv::Scalar::all(0)); cv::subtract(mat1, mat2, dst_gold, channels == 1 ? mask : cv::noArray(), depth.second); EXPECT_MAT_NEAR(dst_gold, dst, depth.first >= CV_32F || depth.second >= CV_32F ? 1e-4 : 0.0); } } INSTANTIATE_TEST_CASE_P(GPU_Core, Subtract_Array, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, DEPTH_PAIRS, ALL_CHANNELS, WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Subtract_Scalar PARAM_TEST_CASE(Subtract_Scalar, cv::gpu::DeviceInfo, cv::Size, std::pair, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; std::pair depth; bool useRoi; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); useRoi = GET_PARAM(3); cv::gpu::setDevice(devInfo.deviceID()); } }; TEST_P(Subtract_Scalar, WithOutMask) { cv::Mat mat = randomMat(size, depth.first); cv::Scalar val = randomScalar(0, 255); if ((depth.first == CV_64F || depth.second == CV_64F) && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::subtract(loadMat(mat), val, dst, cv::gpu::GpuMat(), depth.second); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, depth.second, useRoi); dst.setTo(cv::Scalar::all(0)); cv::gpu::subtract(loadMat(mat, useRoi), val, dst, cv::gpu::GpuMat(), depth.second); cv::Mat dst_gold(size, depth.second, cv::Scalar::all(0)); cv::subtract(mat, val, dst_gold, cv::noArray(), depth.second); EXPECT_MAT_NEAR(dst_gold, dst, depth.first >= CV_32F || depth.second >= CV_32F ? 1e-4 : 0.0); } } TEST_P(Subtract_Scalar, WithMask) { cv::Mat mat = randomMat(size, depth.first); cv::Scalar val = randomScalar(0, 255); cv::Mat mask = randomMat(size, CV_8UC1, 0.0, 2.0); if ((depth.first == CV_64F || depth.second == CV_64F) && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::subtract(loadMat(mat), val, dst, cv::gpu::GpuMat(), depth.second); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, depth.second, useRoi); dst.setTo(cv::Scalar::all(0)); cv::gpu::subtract(loadMat(mat, useRoi), val, dst, loadMat(mask, useRoi), depth.second); cv::Mat dst_gold(size, depth.second, cv::Scalar::all(0)); cv::subtract(mat, val, dst_gold, mask, depth.second); EXPECT_MAT_NEAR(dst_gold, dst, depth.first >= CV_32F || depth.second >= CV_32F ? 1e-4 : 0.0); } } INSTANTIATE_TEST_CASE_P(GPU_Core, Subtract_Scalar, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, DEPTH_PAIRS, WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Multiply_Array PARAM_TEST_CASE(Multiply_Array, cv::gpu::DeviceInfo, cv::Size, std::pair, Channels, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; std::pair depth; int channels; bool useRoi; int stype; int dtype; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); channels = GET_PARAM(3); useRoi = GET_PARAM(4); cv::gpu::setDevice(devInfo.deviceID()); stype = CV_MAKE_TYPE(depth.first, channels); dtype = CV_MAKE_TYPE(depth.second, channels); } }; TEST_P(Multiply_Array, WithOutScale) { cv::Mat mat1 = randomMat(size, stype); cv::Mat mat2 = randomMat(size, stype); if ((depth.first == CV_64F || depth.second == CV_64F) && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::multiply(loadMat(mat1), loadMat(mat2), dst, 1, depth.second); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, dtype, useRoi); cv::gpu::multiply(loadMat(mat1, useRoi), loadMat(mat2, useRoi), dst, 1, depth.second); cv::Mat dst_gold; cv::multiply(mat1, mat2, dst_gold, 1, depth.second); EXPECT_MAT_NEAR(dst_gold, dst, depth.first >= CV_32F || depth.second >= CV_32F ? 1e-4 : 0.0); } } TEST_P(Multiply_Array, WithScale) { cv::Mat mat1 = randomMat(size, stype); cv::Mat mat2 = randomMat(size, stype); double scale = randomDouble(0.0, 255.0); if ((depth.first == CV_64F || depth.second == CV_64F) && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::multiply(loadMat(mat1), loadMat(mat2), dst, scale, depth.second); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, dtype, useRoi); cv::gpu::multiply(loadMat(mat1, useRoi), loadMat(mat2, useRoi), dst, scale, depth.second); cv::Mat dst_gold; cv::multiply(mat1, mat2, dst_gold, scale, depth.second); EXPECT_MAT_NEAR(dst_gold, dst, 1.0); } } INSTANTIATE_TEST_CASE_P(GPU_Core, Multiply_Array, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, DEPTH_PAIRS, ALL_CHANNELS, WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Multiply_Array_Special PARAM_TEST_CASE(Multiply_Array_Special, cv::gpu::DeviceInfo, cv::Size, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; bool useRoi; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); useRoi = GET_PARAM(2); cv::gpu::setDevice(devInfo.deviceID()); } }; TEST_P(Multiply_Array_Special, Case_8UC4x_32FC1) { cv::Mat mat1 = randomMat(size, CV_8UC4); cv::Mat mat2 = randomMat(size, CV_32FC1); cv::gpu::GpuMat dst = createMat(size, CV_8UC4, useRoi); cv::gpu::multiply(loadMat(mat1, useRoi), loadMat(mat2, useRoi), dst); cv::Mat h_dst(dst); for (int y = 0; y < h_dst.rows; ++y) { const cv::Vec4b* mat1_row = mat1.ptr(y); const float* mat2_row = mat2.ptr(y); const cv::Vec4b* dst_row = h_dst.ptr(y); for (int x = 0; x < h_dst.cols; ++x) { cv::Vec4b val1 = mat1_row[x]; float val2 = mat2_row[x]; cv::Vec4b actual = dst_row[x]; cv::Vec4b gold; gold[0] = cv::saturate_cast(val1[0] * val2); gold[1] = cv::saturate_cast(val1[1] * val2); gold[2] = cv::saturate_cast(val1[2] * val2); gold[3] = cv::saturate_cast(val1[3] * val2); ASSERT_LE(std::abs(gold[0] - actual[0]), 1.0); ASSERT_LE(std::abs(gold[1] - actual[1]), 1.0); ASSERT_LE(std::abs(gold[1] - actual[1]), 1.0); ASSERT_LE(std::abs(gold[1] - actual[1]), 1.0); } } } TEST_P(Multiply_Array_Special, Case_16SC4x_32FC1) { cv::Mat mat1 = randomMat(size, CV_16SC4); cv::Mat mat2 = randomMat(size, CV_32FC1); cv::gpu::GpuMat dst = createMat(size, CV_16SC4, useRoi); cv::gpu::multiply(loadMat(mat1, useRoi), loadMat(mat2, useRoi), dst); cv::Mat h_dst(dst); for (int y = 0; y < h_dst.rows; ++y) { const cv::Vec4s* mat1_row = mat1.ptr(y); const float* mat2_row = mat2.ptr(y); const cv::Vec4s* dst_row = h_dst.ptr(y); for (int x = 0; x < h_dst.cols; ++x) { cv::Vec4s val1 = mat1_row[x]; float val2 = mat2_row[x]; cv::Vec4s actual = dst_row[x]; cv::Vec4s gold; gold[0] = cv::saturate_cast(val1[0] * val2); gold[1] = cv::saturate_cast(val1[1] * val2); gold[2] = cv::saturate_cast(val1[2] * val2); gold[3] = cv::saturate_cast(val1[3] * val2); ASSERT_LE(std::abs(gold[0] - actual[0]), 1.0); ASSERT_LE(std::abs(gold[1] - actual[1]), 1.0); ASSERT_LE(std::abs(gold[1] - actual[1]), 1.0); ASSERT_LE(std::abs(gold[1] - actual[1]), 1.0); } } } INSTANTIATE_TEST_CASE_P(GPU_Core, Multiply_Array_Special, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Multiply_Scalar PARAM_TEST_CASE(Multiply_Scalar, cv::gpu::DeviceInfo, cv::Size, std::pair, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; std::pair depth; bool useRoi; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); useRoi = GET_PARAM(3); cv::gpu::setDevice(devInfo.deviceID()); } }; TEST_P(Multiply_Scalar, WithOutScale) { cv::Mat mat = randomMat(size, depth.first); cv::Scalar val = randomScalar(0, 255); if ((depth.first == CV_64F || depth.second == CV_64F) && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::multiply(loadMat(mat), val, dst, 1, depth.second); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, depth.second, useRoi); cv::gpu::multiply(loadMat(mat, useRoi), val, dst, 1, depth.second); cv::Mat dst_gold; cv::multiply(mat, val, dst_gold, 1, depth.second); EXPECT_MAT_NEAR(dst_gold, dst, depth.first >= CV_32F || depth.second >= CV_32F ? 1e-2 : 0.0); } } TEST_P(Multiply_Scalar, WithScale) { cv::Mat mat = randomMat(size, depth.first); cv::Scalar val = randomScalar(0, 255); double scale = randomDouble(0.0, 255.0); if ((depth.first == CV_64F || depth.second == CV_64F) && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::multiply(loadMat(mat), val, dst, scale, depth.second); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, depth.second, useRoi); cv::gpu::multiply(loadMat(mat, useRoi), val, dst, scale, depth.second); cv::Mat dst_gold; cv::multiply(mat, val, dst_gold, scale, depth.second); EXPECT_MAT_NEAR(dst_gold, dst, depth.first >= CV_32F || depth.second >= CV_32F ? 1e-4 : 0.0); } } INSTANTIATE_TEST_CASE_P(GPU_Core, Multiply_Scalar, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, DEPTH_PAIRS, WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Divide_Array PARAM_TEST_CASE(Divide_Array, cv::gpu::DeviceInfo, cv::Size, std::pair, Channels, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; std::pair depth; int channels; bool useRoi; int stype; int dtype; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); channels = GET_PARAM(3); useRoi = GET_PARAM(4); cv::gpu::setDevice(devInfo.deviceID()); stype = CV_MAKE_TYPE(depth.first, channels); dtype = CV_MAKE_TYPE(depth.second, channels); } }; TEST_P(Divide_Array, WithOutScale) { cv::Mat mat1 = randomMat(size, stype); cv::Mat mat2 = randomMat(size, stype, 1.0, 255.0); if ((depth.first == CV_64F || depth.second == CV_64F) && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::divide(loadMat(mat1), loadMat(mat2), dst, 1, depth.second); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, dtype, useRoi); cv::gpu::divide(loadMat(mat1, useRoi), loadMat(mat2, useRoi), dst, 1, depth.second); cv::Mat dst_gold; cv::divide(mat1, mat2, dst_gold, 1, depth.second); EXPECT_MAT_NEAR(dst_gold, dst, depth.first >= CV_32F || depth.second >= CV_32F ? 1e-4 : 1.0); } } TEST_P(Divide_Array, WithScale) { cv::Mat mat1 = randomMat(size, stype); cv::Mat mat2 = randomMat(size, stype, 1.0, 255.0); double scale = randomDouble(0.0, 255.0); if ((depth.first == CV_64F || depth.second == CV_64F) && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::divide(loadMat(mat1), loadMat(mat2), dst, scale, depth.second); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, dtype, useRoi); cv::gpu::divide(loadMat(mat1, useRoi), loadMat(mat2, useRoi), dst, scale, depth.second); cv::Mat dst_gold; cv::divide(mat1, mat2, dst_gold, scale, depth.second); EXPECT_MAT_NEAR(dst_gold, dst, depth.first >= CV_32F || depth.second >= CV_32F ? 1e-2 : 1.0); } } INSTANTIATE_TEST_CASE_P(GPU_Core, Divide_Array, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, DEPTH_PAIRS, ALL_CHANNELS, WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Divide_Array_Special PARAM_TEST_CASE(Divide_Array_Special, cv::gpu::DeviceInfo, cv::Size, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; bool useRoi; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); useRoi = GET_PARAM(2); cv::gpu::setDevice(devInfo.deviceID()); } }; TEST_P(Divide_Array_Special, Case_8UC4x_32FC1) { cv::Mat mat1 = randomMat(size, CV_8UC4); cv::Mat mat2 = randomMat(size, CV_32FC1, 1.0, 255.0); cv::gpu::GpuMat dst = createMat(size, CV_8UC4, useRoi); cv::gpu::divide(loadMat(mat1, useRoi), loadMat(mat2, useRoi), dst); cv::Mat h_dst(dst); for (int y = 0; y < h_dst.rows; ++y) { const cv::Vec4b* mat1_row = mat1.ptr(y); const float* mat2_row = mat2.ptr(y); const cv::Vec4b* dst_row = h_dst.ptr(y); for (int x = 0; x < h_dst.cols; ++x) { cv::Vec4b val1 = mat1_row[x]; float val2 = mat2_row[x]; cv::Vec4b actual = dst_row[x]; cv::Vec4b gold; gold[0] = cv::saturate_cast(val1[0] / val2); gold[1] = cv::saturate_cast(val1[1] / val2); gold[2] = cv::saturate_cast(val1[2] / val2); gold[3] = cv::saturate_cast(val1[3] / val2); ASSERT_LE(std::abs(gold[0] - actual[0]), 1.0); ASSERT_LE(std::abs(gold[1] - actual[1]), 1.0); ASSERT_LE(std::abs(gold[1] - actual[1]), 1.0); ASSERT_LE(std::abs(gold[1] - actual[1]), 1.0); } } } TEST_P(Divide_Array_Special, Case_16SC4x_32FC1) { cv::Mat mat1 = randomMat(size, CV_16SC4); cv::Mat mat2 = randomMat(size, CV_32FC1, 1.0, 255.0); cv::gpu::GpuMat dst = createMat(size, CV_16SC4, useRoi); cv::gpu::divide(loadMat(mat1, useRoi), loadMat(mat2, useRoi), dst); cv::Mat h_dst(dst); for (int y = 0; y < h_dst.rows; ++y) { const cv::Vec4s* mat1_row = mat1.ptr(y); const float* mat2_row = mat2.ptr(y); const cv::Vec4s* dst_row = h_dst.ptr(y); for (int x = 0; x < h_dst.cols; ++x) { cv::Vec4s val1 = mat1_row[x]; float val2 = mat2_row[x]; cv::Vec4s actual = dst_row[x]; cv::Vec4s gold; gold[0] = cv::saturate_cast(val1[0] / val2); gold[1] = cv::saturate_cast(val1[1] / val2); gold[2] = cv::saturate_cast(val1[2] / val2); gold[3] = cv::saturate_cast(val1[3] / val2); ASSERT_LE(std::abs(gold[0] - actual[0]), 1.0); ASSERT_LE(std::abs(gold[1] - actual[1]), 1.0); ASSERT_LE(std::abs(gold[1] - actual[1]), 1.0); ASSERT_LE(std::abs(gold[1] - actual[1]), 1.0); } } } INSTANTIATE_TEST_CASE_P(GPU_Core, Divide_Array_Special, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Divide_Scalar PARAM_TEST_CASE(Divide_Scalar, cv::gpu::DeviceInfo, cv::Size, std::pair, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; std::pair depth; bool useRoi; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); useRoi = GET_PARAM(3); cv::gpu::setDevice(devInfo.deviceID()); } }; TEST_P(Divide_Scalar, WithOutScale) { cv::Mat mat = randomMat(size, depth.first); cv::Scalar val = randomScalar(1.0, 255.0); if ((depth.first == CV_64F || depth.second == CV_64F) && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::divide(loadMat(mat), val, dst, 1, depth.second); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, depth.second, useRoi); cv::gpu::divide(loadMat(mat, useRoi), val, dst, 1, depth.second); cv::Mat dst_gold; cv::divide(mat, val, dst_gold, 1, depth.second); EXPECT_MAT_NEAR(dst_gold, dst, depth.first >= CV_32F || depth.second >= CV_32F ? 1e-4 : 0.0); } } TEST_P(Divide_Scalar, WithScale) { cv::Mat mat = randomMat(size, depth.first); cv::Scalar val = randomScalar(1.0, 255.0); double scale = randomDouble(0.0, 255.0); if ((depth.first == CV_64F || depth.second == CV_64F) && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::divide(loadMat(mat), val, dst, scale, depth.second); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, depth.second, useRoi); cv::gpu::divide(loadMat(mat, useRoi), val, dst, scale, depth.second); cv::Mat dst_gold; cv::divide(mat, val, dst_gold, scale, depth.second); EXPECT_MAT_NEAR(dst_gold, dst, depth.first >= CV_32F || depth.second >= CV_32F ? 1e-4 : 0.0); } } INSTANTIATE_TEST_CASE_P(GPU_Core, Divide_Scalar, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, DEPTH_PAIRS, WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Divide_Scalar_Inv PARAM_TEST_CASE(Divide_Scalar_Inv, cv::gpu::DeviceInfo, cv::Size, std::pair, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; std::pair depth; bool useRoi; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); useRoi = GET_PARAM(3); cv::gpu::setDevice(devInfo.deviceID()); } }; TEST_P(Divide_Scalar_Inv, Accuracy) { double scale = randomDouble(0.0, 255.0); cv::Mat mat = randomMat(size, depth.first, 1.0, 255.0); if ((depth.first == CV_64F || depth.second == CV_64F) && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::divide(scale, loadMat(mat), dst, depth.second); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, depth.second, useRoi); cv::gpu::divide(scale, loadMat(mat, useRoi), dst, depth.second); cv::Mat dst_gold; cv::divide(scale, mat, dst_gold, depth.second); EXPECT_MAT_NEAR(dst_gold, dst, depth.first >= CV_32F || depth.second >= CV_32F ? 1e-4 : 0.0); } } INSTANTIATE_TEST_CASE_P(GPU_Core, Divide_Scalar_Inv, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, DEPTH_PAIRS, WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // AbsDiff PARAM_TEST_CASE(AbsDiff, cv::gpu::DeviceInfo, cv::Size, MatDepth, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; int depth; bool useRoi; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); useRoi = GET_PARAM(3); cv::gpu::setDevice(devInfo.deviceID()); } }; TEST_P(AbsDiff, Array) { cv::Mat src1 = randomMat(size, depth); cv::Mat src2 = randomMat(size, depth); if (depth == CV_64F && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::absdiff(loadMat(src1), loadMat(src2), dst); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, depth, useRoi); cv::gpu::absdiff(loadMat(src1, useRoi), loadMat(src2, useRoi), dst); cv::Mat dst_gold; cv::absdiff(src1, src2, dst_gold); EXPECT_MAT_NEAR(dst_gold, dst, 0.0); } } TEST_P(AbsDiff, Scalar) { cv::Mat src = randomMat(size, depth); cv::Scalar val = randomScalar(0.0, 255.0); if (depth == CV_64F && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::absdiff(loadMat(src), val, dst); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, depth, useRoi); cv::gpu::absdiff(loadMat(src, useRoi), val, dst); cv::Mat dst_gold; cv::absdiff(src, val, dst_gold); EXPECT_MAT_NEAR(dst_gold, dst, depth <= CV_32F ? 1.0 : 1e-5); } } INSTANTIATE_TEST_CASE_P(GPU_Core, AbsDiff, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, ALL_DEPTH, WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Abs PARAM_TEST_CASE(Abs, cv::gpu::DeviceInfo, cv::Size, MatDepth, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; int depth; bool useRoi; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); useRoi = GET_PARAM(3); cv::gpu::setDevice(devInfo.deviceID()); } }; TEST_P(Abs, Accuracy) { cv::Mat src = randomMat(size, depth); cv::gpu::GpuMat dst = createMat(size, depth, useRoi); cv::gpu::abs(loadMat(src, useRoi), dst); cv::Mat dst_gold = cv::abs(src); EXPECT_MAT_NEAR(dst_gold, dst, 0.0); } INSTANTIATE_TEST_CASE_P(GPU_Core, Abs, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, testing::Values(MatDepth(CV_16S), MatDepth(CV_32F)), WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Sqr PARAM_TEST_CASE(Sqr, cv::gpu::DeviceInfo, cv::Size, MatDepth, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; int depth; bool useRoi; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); useRoi = GET_PARAM(3); cv::gpu::setDevice(devInfo.deviceID()); } }; TEST_P(Sqr, Accuracy) { cv::Mat src = randomMat(size, depth, 0, depth == CV_8U ? 16 : 255); cv::gpu::GpuMat dst = createMat(size, depth, useRoi); cv::gpu::sqr(loadMat(src, useRoi), dst); cv::Mat dst_gold; cv::multiply(src, src, dst_gold); EXPECT_MAT_NEAR(dst_gold, dst, 0.0); } INSTANTIATE_TEST_CASE_P(GPU_Core, Sqr, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, testing::Values(MatDepth(CV_8U), MatDepth(CV_16U), MatDepth(CV_16S), MatDepth(CV_32F)), WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Sqrt template void sqrtImpl(const cv::Mat& src, cv::Mat& dst) { dst.create(src.size(), src.type()); for (int y = 0; y < src.rows; ++y) { for (int x = 0; x < src.cols; ++x) dst.at(y, x) = static_cast(std::sqrt(static_cast(src.at(y, x)))); } } void sqrtGold(const cv::Mat& src, cv::Mat& dst) { typedef void (*func_t)(const cv::Mat& src, cv::Mat& dst); const func_t funcs[] = { sqrtImpl, sqrtImpl, sqrtImpl, sqrtImpl, sqrtImpl, sqrtImpl }; funcs[src.depth()](src, dst); } PARAM_TEST_CASE(Sqrt, cv::gpu::DeviceInfo, cv::Size, MatDepth, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; int depth; bool useRoi; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); useRoi = GET_PARAM(3); cv::gpu::setDevice(devInfo.deviceID()); } }; TEST_P(Sqrt, Accuracy) { cv::Mat src = randomMat(size, depth); cv::gpu::GpuMat dst = createMat(size, depth, useRoi); cv::gpu::sqrt(loadMat(src, useRoi), dst); cv::Mat dst_gold; sqrtGold(src, dst_gold); EXPECT_MAT_NEAR(dst_gold, dst, depth < CV_32F ? 1.0 : 1e-5); } INSTANTIATE_TEST_CASE_P(GPU_Core, Sqrt, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, testing::Values(MatDepth(CV_8U), MatDepth(CV_16U), MatDepth(CV_16S), MatDepth(CV_32F)), WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Log template void logImpl(const cv::Mat& src, cv::Mat& dst) { dst.create(src.size(), src.type()); for (int y = 0; y < src.rows; ++y) { for (int x = 0; x < src.cols; ++x) dst.at(y, x) = static_cast(std::log(static_cast(src.at(y, x)))); } } void logGold(const cv::Mat& src, cv::Mat& dst) { typedef void (*func_t)(const cv::Mat& src, cv::Mat& dst); const func_t funcs[] = { logImpl, logImpl, logImpl, logImpl, logImpl, logImpl }; funcs[src.depth()](src, dst); } PARAM_TEST_CASE(Log, cv::gpu::DeviceInfo, cv::Size, MatDepth, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; int depth; bool useRoi; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); useRoi = GET_PARAM(3); cv::gpu::setDevice(devInfo.deviceID()); } }; TEST_P(Log, Accuracy) { cv::Mat src = randomMat(size, depth, 1.0, 255.0); cv::gpu::GpuMat dst = createMat(size, depth, useRoi); cv::gpu::log(loadMat(src, useRoi), dst); cv::Mat dst_gold; logGold(src, dst_gold); EXPECT_MAT_NEAR(dst_gold, dst, depth < CV_32F ? 1.0 : 1e-6); } INSTANTIATE_TEST_CASE_P(GPU_Core, Log, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, testing::Values(MatDepth(CV_8U), MatDepth(CV_16U), MatDepth(CV_16S), MatDepth(CV_32F)), WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Exp template void expImpl(const cv::Mat& src, cv::Mat& dst) { dst.create(src.size(), src.type()); for (int y = 0; y < src.rows; ++y) { for (int x = 0; x < src.cols; ++x) dst.at(y, x) = cv::saturate_cast(static_cast(std::exp(static_cast(src.at(y, x))))); } } void expImpl_float(const cv::Mat& src, cv::Mat& dst) { dst.create(src.size(), src.type()); for (int y = 0; y < src.rows; ++y) { for (int x = 0; x < src.cols; ++x) dst.at(y, x) = std::exp(static_cast(src.at(y, x))); } } void expGold(const cv::Mat& src, cv::Mat& dst) { typedef void (*func_t)(const cv::Mat& src, cv::Mat& dst); const func_t funcs[] = { expImpl, expImpl, expImpl, expImpl, expImpl, expImpl_float }; funcs[src.depth()](src, dst); } PARAM_TEST_CASE(Exp, cv::gpu::DeviceInfo, cv::Size, MatDepth, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; int depth; bool useRoi; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); useRoi = GET_PARAM(3); cv::gpu::setDevice(devInfo.deviceID()); } }; TEST_P(Exp, Accuracy) { cv::Mat src = randomMat(size, depth, 0.0, 10.0); cv::gpu::GpuMat dst = createMat(size, depth, useRoi); cv::gpu::exp(loadMat(src, useRoi), dst); cv::Mat dst_gold; expGold(src, dst_gold); EXPECT_MAT_NEAR(dst_gold, dst, depth < CV_32F ? 1.0 : 1e-2); } INSTANTIATE_TEST_CASE_P(GPU_Core, Exp, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, testing::Values(MatDepth(CV_8U), MatDepth(CV_16U), MatDepth(CV_16S), MatDepth(CV_32F)), WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Compare_Array CV_ENUM(CmpCode, cv::CMP_EQ, cv::CMP_GT, cv::CMP_GE, cv::CMP_LT, cv::CMP_LE, cv::CMP_NE) #define ALL_CMP_CODES testing::Values(CmpCode(cv::CMP_EQ), CmpCode(cv::CMP_NE), CmpCode(cv::CMP_GT), CmpCode(cv::CMP_GE), CmpCode(cv::CMP_LT), CmpCode(cv::CMP_LE)) PARAM_TEST_CASE(Compare_Array, cv::gpu::DeviceInfo, cv::Size, MatDepth, CmpCode, UseRoi) { cv::gpu::DeviceInfo devInfo; cv::Size size; int depth; int cmp_code; bool useRoi; virtual void SetUp() { devInfo = GET_PARAM(0); size = GET_PARAM(1); depth = GET_PARAM(2); cmp_code = GET_PARAM(3); useRoi = GET_PARAM(4); cv::gpu::setDevice(devInfo.deviceID()); } }; TEST_P(Compare_Array, Accuracy) { cv::Mat src1 = randomMat(size, depth); cv::Mat src2 = randomMat(size, depth); if (depth == CV_64F && !supportFeature(devInfo, cv::gpu::NATIVE_DOUBLE)) { try { cv::gpu::GpuMat dst; cv::gpu::compare(loadMat(src1), loadMat(src2), dst, cmp_code); } catch (const cv::Exception& e) { ASSERT_EQ(CV_StsUnsupportedFormat, e.code); } } else { cv::gpu::GpuMat dst = createMat(size, CV_8UC1, useRoi); cv::gpu::compare(loadMat(src1, useRoi), loadMat(src2, useRoi), dst, cmp_code); cv::Mat dst_gold; cv::compare(src1, src2, dst_gold, cmp_code); EXPECT_MAT_NEAR(dst_gold, dst, 0.0); } } INSTANTIATE_TEST_CASE_P(GPU_Core, Compare_Array, testing::Combine( ALL_DEVICES, DIFFERENT_SIZES, ALL_DEPTH, ALL_CMP_CODES, WHOLE_SUBMAT)); //////////////////////////////////////////////////////////////////////////////// // Compare_Scalar namespace { template