Merge pull request #1263 from abidrahmank:pyCLAHE_24
[profile/ivi/opencv.git] / modules / ts / include / opencv2 / ts / ts.hpp
1 #ifndef __OPENCV_GTESTCV_HPP__
2 #define __OPENCV_GTESTCV_HPP__
3
4 #include <stdarg.h> // for va_list
5
6 #ifdef HAVE_WINRT
7     #pragma warning(disable:4447) // Disable warning 'main' signature found without threading model
8 #endif
9
10 #ifdef _MSC_VER
11 #pragma warning( disable: 4127 )
12 #endif
13
14 #define GTEST_DONT_DEFINE_FAIL      0
15 #define GTEST_DONT_DEFINE_SUCCEED   0
16 #define GTEST_DONT_DEFINE_ASSERT_EQ 0
17 #define GTEST_DONT_DEFINE_ASSERT_NE 0
18 #define GTEST_DONT_DEFINE_ASSERT_LE 0
19 #define GTEST_DONT_DEFINE_ASSERT_LT 0
20 #define GTEST_DONT_DEFINE_ASSERT_GE 0
21 #define GTEST_DONT_DEFINE_ASSERT_GT 0
22 #define GTEST_DONT_DEFINE_TEST      0
23
24 #include "opencv2/ts/ts_gtest.h"
25
26 #ifndef GTEST_USES_SIMPLE_RE
27 #  define GTEST_USES_SIMPLE_RE 0
28 #endif
29 #ifndef GTEST_USES_POSIX_RE
30 #  define GTEST_USES_POSIX_RE 0
31 #endif
32
33 #include "opencv2/core/core.hpp"
34
35 namespace cvtest
36 {
37
38 using std::vector;
39 using std::string;
40 using cv::RNG;
41 using cv::Mat;
42 using cv::Scalar;
43 using cv::Size;
44 using cv::Point;
45 using cv::Rect;
46
47 class CV_EXPORTS TS;
48
49 CV_EXPORTS int64 readSeed(const char* str);
50
51 CV_EXPORTS void randUni( RNG& rng, Mat& a, const Scalar& param1, const Scalar& param2 );
52
53 inline unsigned randInt( RNG& rng )
54 {
55     return (unsigned)rng;
56 }
57
58 inline  double randReal( RNG& rng )
59 {
60     return (double)rng;
61 }
62
63
64 CV_EXPORTS const char* getTypeName( int type );
65 CV_EXPORTS int typeByName( const char* type_name );
66
67 CV_EXPORTS string vec2str(const string& sep, const int* v, size_t nelems);
68
69 inline int clipInt( int val, int min_val, int max_val )
70 {
71     if( val < min_val )
72         val = min_val;
73     if( val > max_val )
74         val = max_val;
75     return val;
76 }
77
78 CV_EXPORTS double getMinVal(int depth);
79 CV_EXPORTS double getMaxVal(int depth);
80
81 CV_EXPORTS Size randomSize(RNG& rng, double maxSizeLog);
82 CV_EXPORTS void randomSize(RNG& rng, int minDims, int maxDims, double maxSizeLog, vector<int>& sz);
83 CV_EXPORTS int randomType(RNG& rng, int typeMask, int minChannels, int maxChannels);
84 CV_EXPORTS Mat randomMat(RNG& rng, Size size, int type, double minVal, double maxVal, bool useRoi);
85 CV_EXPORTS Mat randomMat(RNG& rng, const vector<int>& size, int type, double minVal, double maxVal, bool useRoi);
86 CV_EXPORTS void add(const Mat& a, double alpha, const Mat& b, double beta,
87                       Scalar gamma, Mat& c, int ctype, bool calcAbs=false);
88 CV_EXPORTS void multiply(const Mat& a, const Mat& b, Mat& c, double alpha=1);
89 CV_EXPORTS void divide(const Mat& a, const Mat& b, Mat& c, double alpha=1);
90
91 CV_EXPORTS void convert(const Mat& src, Mat& dst, int dtype, double alpha=1, double beta=0);
92 CV_EXPORTS void copy(const Mat& src, Mat& dst, const Mat& mask=Mat(), bool invertMask=false);
93 CV_EXPORTS void set(Mat& dst, const Scalar& gamma, const Mat& mask=Mat());
94
95 // working with multi-channel arrays
96 CV_EXPORTS void extract( const Mat& a, Mat& plane, int coi );
97 CV_EXPORTS void insert( const Mat& plane, Mat& a, int coi );
98
99 // checks that the array does not have NaNs and/or Infs and all the elements are
100 // within [min_val,max_val). idx is the index of the first "bad" element.
101 CV_EXPORTS int check( const Mat& data, double min_val, double max_val, vector<int>* idx );
102
103 // modifies values that are close to zero
104 CV_EXPORTS void  patchZeros( Mat& mat, double level );
105
106 CV_EXPORTS void transpose(const Mat& src, Mat& dst);
107 CV_EXPORTS void erode(const Mat& src, Mat& dst, const Mat& _kernel, Point anchor=Point(-1,-1),
108                       int borderType=IPL_BORDER_CONSTANT, const Scalar& borderValue=Scalar());
109 CV_EXPORTS void dilate(const Mat& src, Mat& dst, const Mat& _kernel, Point anchor=Point(-1,-1),
110                        int borderType=IPL_BORDER_CONSTANT, const Scalar& borderValue=Scalar());
111 CV_EXPORTS void filter2D(const Mat& src, Mat& dst, int ddepth, const Mat& kernel,
112                          Point anchor, double delta, int borderType,
113                          const Scalar& borderValue=Scalar());
114 CV_EXPORTS void copyMakeBorder(const Mat& src, Mat& dst, int top, int bottom, int left, int right,
115                                int borderType, const Scalar& borderValue=Scalar());
116 CV_EXPORTS Mat calcSobelKernel2D( int dx, int dy, int apertureSize, int origin=0 );
117 CV_EXPORTS Mat calcLaplaceKernel2D( int aperture_size );
118
119 CV_EXPORTS void initUndistortMap( const Mat& a, const Mat& k, Size sz, Mat& mapx, Mat& mapy );
120
121 CV_EXPORTS void minMaxLoc(const Mat& src, double* minval, double* maxval,
122                           vector<int>* minloc, vector<int>* maxloc, const Mat& mask=Mat());
123 CV_EXPORTS double norm(const Mat& src, int normType, const Mat& mask=Mat());
124 CV_EXPORTS double norm(const Mat& src1, const Mat& src2, int normType, const Mat& mask=Mat());
125 CV_EXPORTS Scalar mean(const Mat& src, const Mat& mask=Mat());
126
127 CV_EXPORTS bool cmpUlps(const Mat& data, const Mat& refdata, int expMaxDiff, double* realMaxDiff, vector<int>* idx);
128
129 // compares two arrays. max_diff is the maximum actual difference,
130 // success_err_level is maximum allowed difference, idx is the index of the first
131 // element for which difference is >success_err_level
132 // (or index of element with the maximum difference)
133 CV_EXPORTS int cmpEps( const Mat& data, const Mat& refdata, double* max_diff,
134                        double success_err_level, vector<int>* idx,
135                        bool element_wise_relative_error );
136
137 // a wrapper for the previous function. in case of error prints the message to log file.
138 CV_EXPORTS int cmpEps2( TS* ts, const Mat& data, const Mat& refdata, double success_err_level,
139                         bool element_wise_relative_error, const char* desc );
140
141 CV_EXPORTS int cmpEps2_64f( TS* ts, const double* val, const double* refval, int len,
142                         double eps, const char* param_name );
143
144 CV_EXPORTS void logicOp(const Mat& src1, const Mat& src2, Mat& dst, char c);
145 CV_EXPORTS void logicOp(const Mat& src, const Scalar& s, Mat& dst, char c);
146 CV_EXPORTS void min(const Mat& src1, const Mat& src2, Mat& dst);
147 CV_EXPORTS void min(const Mat& src, double s, Mat& dst);
148 CV_EXPORTS void max(const Mat& src1, const Mat& src2, Mat& dst);
149 CV_EXPORTS void max(const Mat& src, double s, Mat& dst);
150
151 CV_EXPORTS void compare(const Mat& src1, const Mat& src2, Mat& dst, int cmpop);
152 CV_EXPORTS void compare(const Mat& src, double s, Mat& dst, int cmpop);
153 CV_EXPORTS void gemm(const Mat& src1, const Mat& src2, double alpha,
154                      const Mat& src3, double beta, Mat& dst, int flags);
155     CV_EXPORTS void transform( const Mat& src, Mat& dst, const Mat& transmat, const Mat& shift );
156 CV_EXPORTS double crossCorr(const Mat& src1, const Mat& src2);
157
158 struct CV_EXPORTS MatInfo
159 {
160     MatInfo(const Mat& _m) : m(&_m) {}
161     const Mat* m;
162 };
163
164 CV_EXPORTS std::ostream& operator << (std::ostream& out, const MatInfo& m);
165
166 struct CV_EXPORTS MatComparator
167 {
168 public:
169     MatComparator(double maxdiff, int context);
170
171     ::testing::AssertionResult operator()(const char* expr1, const char* expr2,
172                                           const Mat& m1, const Mat& m2);
173
174     double maxdiff;
175     double realmaxdiff;
176     vector<int> loc0;
177     int context;
178 };
179
180
181
182 class BaseTest;
183 class TS;
184
185 class CV_EXPORTS BaseTest
186 {
187 public:
188     // constructor(s) and destructor
189     BaseTest();
190     virtual ~BaseTest();
191
192     // the main procedure of the test
193     virtual void run( int start_from );
194
195     // the wrapper for run that cares of exceptions
196     virtual void safe_run( int start_from=0 );
197
198     const string& get_name() const { return name; }
199
200     // returns true if and only if the different test cases do not depend on each other
201     // (so that test system could get right to a problematic test case)
202     virtual bool can_do_fast_forward();
203
204     // deallocates all the memory.
205     // called by init() (before initialization) and by the destructor
206     virtual void clear();
207
208 protected:
209     int test_case_count; // the total number of test cases
210
211     // read test params
212     virtual int read_params( CvFileStorage* fs );
213
214     // returns the number of tests or -1 if it is unknown a-priori
215     virtual int get_test_case_count();
216
217     // prepares data for the next test case. rng seed is updated by the function
218     virtual int prepare_test_case( int test_case_idx );
219
220     // checks if the test output is valid and accurate
221     virtual int validate_test_results( int test_case_idx );
222
223     // calls the tested function. the method is called from run_test_case()
224     virtual void run_func(); // runs tested func(s)
225
226     // updates progress bar
227     virtual int update_progress( int progress, int test_case_idx, int count, double dt );
228
229     // finds test parameter
230     const CvFileNode* find_param( CvFileStorage* fs, const char* param_name );
231
232     // name of the test (it is possible to locate a test by its name)
233     string name;
234
235     // pointer to the system that includes the test
236     TS* ts;
237 };
238
239
240 /*****************************************************************************************\
241 *                               Information about a failed test                           *
242 \*****************************************************************************************/
243
244 struct TestInfo
245 {
246     TestInfo();
247
248     // pointer to the test
249     BaseTest* test;
250
251     // failure code (CV_FAIL*)
252     int code;
253
254     // seed value right before the data for the failed test case is prepared.
255     uint64 rng_seed;
256
257     // seed value right before running the test
258     uint64 rng_seed0;
259
260     // index of test case, can be then passed to BaseTest::proceed_to_test_case()
261     int test_case_idx;
262 };
263
264 /*****************************************************************************************\
265 *                                 Base Class for test system                              *
266 \*****************************************************************************************/
267
268 // common parameters:
269 struct CV_EXPORTS TSParams
270 {
271     TSParams();
272
273     // RNG seed, passed to and updated by every test executed.
274     uint64 rng_seed;
275
276     // whether to use IPP, MKL etc. or not
277     bool use_optimized;
278
279     // extensivity of the tests, scale factor for test_case_count
280     double test_case_count_scale;
281 };
282
283
284 class CV_EXPORTS TS
285 {
286 public:
287     // constructor(s) and destructor
288     TS();
289     virtual ~TS();
290
291     enum
292     {
293         NUL=0,
294         SUMMARY_IDX=0,
295         SUMMARY=1 << SUMMARY_IDX,
296         LOG_IDX=1,
297         LOG=1 << LOG_IDX,
298         CSV_IDX=2,
299         CSV=1 << CSV_IDX,
300         CONSOLE_IDX=3,
301         CONSOLE=1 << CONSOLE_IDX,
302         MAX_IDX=4
303     };
304
305     static TS* ptr();
306
307     // initialize test system before running the first test
308     virtual void init( const string& modulename );
309
310     // low-level printing functions that are used by individual tests and by the system itself
311     virtual void printf( int streams, const char* fmt, ... );
312     virtual void vprintf( int streams, const char* fmt, va_list arglist );
313
314     // updates the context: current test, test case, rng state
315     virtual void update_context( BaseTest* test, int test_case_idx, bool update_ts_context );
316
317     const TestInfo* get_current_test_info() { return &current_test_info; }
318
319     // sets information about a failed test
320     virtual void set_failed_test_info( int fail_code );
321
322     virtual void set_gtest_status();
323
324     // test error codes
325     enum
326     {
327         // everything is Ok
328         OK=0,
329
330         // generic error: stub value to be used
331         // temporarily if the error's cause is unknown
332         FAIL_GENERIC=-1,
333
334         // the test is missing some essential data to proceed further
335         FAIL_MISSING_TEST_DATA=-2,
336
337         // the tested function raised an error via cxcore error handler
338         FAIL_ERROR_IN_CALLED_FUNC=-3,
339
340         // an exception has been raised;
341         // for memory and arithmetic exception
342         // there are two specialized codes (see below...)
343         FAIL_EXCEPTION=-4,
344
345         // a memory exception
346         // (access violation, access to missed page, stack overflow etc.)
347         FAIL_MEMORY_EXCEPTION=-5,
348
349         // arithmetic exception (overflow, division by zero etc.)
350         FAIL_ARITHM_EXCEPTION=-6,
351
352         // the tested function corrupted memory (no exception have been raised)
353         FAIL_MEMORY_CORRUPTION_BEGIN=-7,
354         FAIL_MEMORY_CORRUPTION_END=-8,
355
356         // the tested function (or test ifself) do not deallocate some memory
357         FAIL_MEMORY_LEAK=-9,
358
359         // the tested function returned invalid object, e.g. matrix, containing NaNs,
360         // structure with NULL or out-of-range fields (while it should not)
361         FAIL_INVALID_OUTPUT=-10,
362
363         // the tested function returned valid object, but it does not match to
364         // the original (or produced by the test) object
365         FAIL_MISMATCH=-11,
366
367         // the tested function returned valid object (a single number or numerical array),
368         // but it differs too much from the original (or produced by the test) object
369         FAIL_BAD_ACCURACY=-12,
370
371         // the tested function hung. Sometimes, can be determined by unexpectedly long
372         // processing time (in this case there should be possibility to interrupt such a function
373         FAIL_HANG=-13,
374
375         // unexpected responce on passing bad arguments to the tested function
376         // (the function crashed, proceed succesfully (while it should not), or returned
377         // error code that is different from what is expected)
378         FAIL_BAD_ARG_CHECK=-14,
379
380         // the test data (in whole or for the particular test case) is invalid
381         FAIL_INVALID_TEST_DATA=-15,
382
383         // the test has been skipped because it is not in the selected subset of the tests to run,
384         // because it has been run already within the same run with the same parameters, or because
385         // of some other reason and this is not considered as an error.
386         // Normally TS::run() (or overrided method in the derived class) takes care of what
387         // needs to be run, so this code should not occur.
388         SKIPPED=1
389     };
390
391     // get file storage
392     CvFileStorage* get_file_storage();
393
394     // get RNG to generate random input data for a test
395     RNG& get_rng() { return rng; }
396
397     // returns the current error code
398     int get_err_code() { return current_test_info.code; }
399
400     // returns the test extensivity scale
401     double get_test_case_count_scale() { return params.test_case_count_scale; }
402
403     const string& get_data_path() const { return data_path; }
404
405     // returns textual description of failure code
406     static string str_from_code( int code );
407
408 protected:
409
410     // these are allocated within a test to try keep them valid in case of stack corruption
411     RNG rng;
412
413     // information about the current test
414     TestInfo current_test_info;
415
416     // the path to data files used by tests
417     string data_path;
418
419     TSParams params;
420     std::string output_buf[MAX_IDX];
421 };
422
423
424 /*****************************************************************************************\
425 *            Subclass of BaseTest for testing functions that process dense arrays           *
426 \*****************************************************************************************/
427
428 class CV_EXPORTS ArrayTest : public BaseTest
429 {
430 public:
431     // constructor(s) and destructor
432     ArrayTest();
433     virtual ~ArrayTest();
434
435     virtual void clear();
436
437 protected:
438
439     virtual int read_params( CvFileStorage* fs );
440     virtual int prepare_test_case( int test_case_idx );
441     virtual int validate_test_results( int test_case_idx );
442
443     virtual void prepare_to_validation( int test_case_idx );
444     virtual void get_test_array_types_and_sizes( int test_case_idx, vector<vector<Size> >& sizes, vector<vector<int> >& types );
445     virtual void fill_array( int test_case_idx, int i, int j, Mat& arr );
446     virtual void get_minmax_bounds( int i, int j, int type, Scalar& low, Scalar& high );
447     virtual double get_success_error_level( int test_case_idx, int i, int j );
448
449     bool cvmat_allowed;
450     bool iplimage_allowed;
451     bool optional_mask;
452     bool element_wise_relative_error;
453
454     int min_log_array_size;
455     int max_log_array_size;
456
457     enum { INPUT, INPUT_OUTPUT, OUTPUT, REF_INPUT_OUTPUT, REF_OUTPUT, TEMP, MASK, MAX_ARR };
458
459     vector<vector<void*> > test_array;
460     vector<vector<Mat> > test_mat;
461     float buf[4];
462 };
463
464
465 class CV_EXPORTS BadArgTest : public BaseTest
466 {
467 public:
468     // constructor(s) and destructor
469     BadArgTest();
470     virtual ~BadArgTest();
471
472 protected:
473     virtual int run_test_case( int expected_code, const string& descr );
474     virtual void run_func(void) = 0;
475     int test_case_idx;
476     int progress;
477     double t, freq;
478
479     template<class F>
480     int run_test_case( int expected_code, const string& _descr, F f)
481     {
482         double new_t = (double)cv::getTickCount(), dt;
483         if( test_case_idx < 0 )
484         {
485             test_case_idx = 0;
486             progress = 0;
487             dt = 0;
488         }
489         else
490         {
491             dt = (new_t - t)/(freq*1000);
492             t = new_t;
493         }
494         progress = update_progress(progress, test_case_idx, 0, dt);
495
496         int errcount = 0;
497         bool thrown = false;
498         const char* descr = _descr.c_str() ? _descr.c_str() : "";
499
500         try
501         {
502             f();
503         }
504         catch(const cv::Exception& e)
505         {
506             thrown = true;
507             if( e.code != expected_code )
508             {
509                 ts->printf(TS::LOG, "%s (test case #%d): the error code %d is different from the expected %d\n",
510                     descr, test_case_idx, e.code, expected_code);
511                 errcount = 1;
512             }
513         }
514         catch(...)
515         {
516             thrown = true;
517             ts->printf(TS::LOG, "%s  (test case #%d): unknown exception was thrown (the function has likely crashed)\n",
518                        descr, test_case_idx);
519             errcount = 1;
520         }
521         if(!thrown)
522         {
523             ts->printf(TS::LOG, "%s  (test case #%d): no expected exception was thrown\n",
524                        descr, test_case_idx);
525             errcount = 1;
526         }
527         test_case_idx++;
528
529         return errcount;
530     }
531 };
532
533 struct CV_EXPORTS DefaultRngAuto
534 {
535     const uint64 old_state;
536
537     DefaultRngAuto() : old_state(cv::theRNG().state) { cv::theRNG().state = (uint64)-1; }
538     ~DefaultRngAuto() { cv::theRNG().state = old_state; }
539
540     DefaultRngAuto& operator=(const DefaultRngAuto&);
541 };
542
543 }
544
545 namespace cvtest
546 {
547
548 // test images generation functions
549 CV_EXPORTS void fillGradient(Mat& img, int delta = 5);
550 CV_EXPORTS void smoothBorder(Mat& img, const Scalar& color, int delta = 3);
551
552 CV_EXPORTS void printVersionInfo(bool useStdOut = true);
553 } //namespace cvtest
554
555 // fills c with zeros
556 CV_EXPORTS void cvTsZero( CvMat* c, const CvMat* mask=0 );
557
558 // copies a to b (whole matrix or only the selected region)
559 CV_EXPORTS void cvTsCopy( const CvMat* a, CvMat* b, const CvMat* mask=0 );
560
561 // converts one array to another
562 CV_EXPORTS void  cvTsConvert( const CvMat* src, CvMat* dst );
563
564 CV_EXPORTS void cvTsGEMM( const CvMat* a, const CvMat* b, double alpha,
565                          const CvMat* c, double beta, CvMat* d, int flags );
566
567 #define CV_TEST_MAIN(resourcesubdir) \
568 int main(int argc, char **argv) \
569 { \
570     cvtest::TS::ptr()->init(resourcesubdir); \
571     ::testing::InitGoogleTest(&argc, argv); \
572     cvtest::printVersionInfo();\
573     return RUN_ALL_TESTS(); \
574 }
575
576 // This usually only makes sense in perf tests with several implementations,
577 // some of which are not available.
578 #define CV_TEST_FAIL_NO_IMPL() do { \
579     ::testing::Test::RecordProperty("custom_status", "noimpl"); \
580     FAIL() << "No equivalent implementation."; \
581 } while (0)
582
583 #endif
584
585 #include "ts_perf.hpp"