sad_test.cc 23 KB
Newer Older
Johann's avatar
Johann committed
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
/*
 *  Copyright (c) 2012 The WebM project authors. All Rights Reserved.
 *
 *  Use of this source code is governed by a BSD-style license
 *  that can be found in the LICENSE file in the root of the source
 *  tree. An additional intellectual property rights grant can be found
 *  in the file PATENTS.  All contributing project authors may
 *  be found in the AUTHORS file in the root of the source tree.
 */


#include <string.h>
#include <limits.h>
#include <stdio.h>

#include "./vpx_config.h"
17
#if CONFIG_VP8_ENCODER
18
#include "./vp8_rtcd.h"
19
20
21
22
#endif
#if CONFIG_VP9_ENCODER
#include "./vp9_rtcd.h"
#endif
23
#include "vpx_mem/vpx_mem.h"
Johann's avatar
Johann committed
24
25

#include "test/acm_random.h"
26
#include "test/clear_system_state.h"
27
#include "test/register_state_check.h"
Johann's avatar
Johann committed
28
29
30
31
#include "test/util.h"
#include "third_party/googletest/src/include/gtest/gtest.h"


32
#if CONFIG_VP8_ENCODER
33
34
35
36
37
38
typedef unsigned int (*SadMxNFunc)(const unsigned char *source_ptr,
                                   int source_stride,
                                   const unsigned char *reference_ptr,
                                   int reference_stride,
                                   unsigned int max_sad);
typedef std::tr1::tuple<int, int, SadMxNFunc> SadMxNParam;
39
40
#endif
#if CONFIG_VP9_ENCODER
41
42
43
44
45
typedef unsigned int (*SadMxNVp9Func)(const unsigned char *source_ptr,
                                      int source_stride,
                                      const unsigned char *reference_ptr,
                                      int reference_stride);
typedef std::tr1::tuple<int, int, SadMxNVp9Func> SadMxNVp9Param;
46
#endif
Johann's avatar
Johann committed
47

48
49
50
51
52
53
typedef void (*SadMxNx4Func)(const uint8_t *src_ptr,
                             int src_stride,
                             const unsigned char *const ref_ptr[],
                             int ref_stride,
                             unsigned int *sad_array);
typedef std::tr1::tuple<int, int, SadMxNx4Func> SadMxNx4Param;
54

Johann's avatar
Johann committed
55
56
57
using libvpx_test::ACMRandom;

namespace {
58
class SADTestBase : public ::testing::Test {
59
 public:
60
61
  SADTestBase(int width, int height) : width_(width), height_(height) {}

62
63
  static void SetUpTestCase() {
    source_data_ = reinterpret_cast<uint8_t*>(
64
        vpx_memalign(kDataAlignment, kDataBlockSize));
65
66
67
68
69
70
71
72
73
74
75
    reference_data_ = reinterpret_cast<uint8_t*>(
        vpx_memalign(kDataAlignment, kDataBufferSize));
  }

  static void TearDownTestCase() {
    vpx_free(source_data_);
    source_data_ = NULL;
    vpx_free(reference_data_);
    reference_data_ = NULL;
  }

76
77
78
79
  virtual void TearDown() {
    libvpx_test::ClearSystemState();
  }

80
 protected:
81
  // Handle blocks up to 4 blocks 64x64 with stride up to 128
82
  static const int kDataAlignment = 16;
83
84
  static const int kDataBlockSize = 64 * 128;
  static const int kDataBufferSize = 4 * kDataBlockSize;
85

Johann's avatar
Johann committed
86
  virtual void SetUp() {
87
    source_stride_ = (width_ + 31) & ~31;
Johann's avatar
Johann committed
88
89
90
91
    reference_stride_ = width_ * 2;
    rnd_.Reset(ACMRandom::DeterministicSeed());
  }

92
93
  virtual uint8_t* GetReference(int block_idx) {
    return reference_data_ + block_idx * kDataBlockSize;
Johann's avatar
Johann committed
94
95
96
97
  }

  // Sum of Absolute Differences. Given two blocks, calculate the absolute
  // difference between two pixels in the same relative location; accumulate.
98
  unsigned int ReferenceSAD(unsigned int max_sad, int block_idx) {
Johann's avatar
Johann committed
99
    unsigned int sad = 0;
100
    const uint8_t* const reference = GetReference(block_idx);
Johann's avatar
Johann committed
101
102
103
104

    for (int h = 0; h < height_; ++h) {
      for (int w = 0; w < width_; ++w) {
        sad += abs(source_data_[h * source_stride_ + w]
105
               - reference[h * reference_stride_ + w]);
Johann's avatar
Johann committed
106
      }
107
108
109
      if (sad > max_sad) {
        break;
      }
Johann's avatar
Johann committed
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
    }
    return sad;
  }

  void FillConstant(uint8_t *data, int stride, uint8_t fill_constant) {
    for (int h = 0; h < height_; ++h) {
      for (int w = 0; w < width_; ++w) {
        data[h * stride + w] = fill_constant;
      }
    }
  }

  void FillRandom(uint8_t *data, int stride) {
    for (int h = 0; h < height_; ++h) {
      for (int w = 0; w < width_; ++w) {
        data[h * stride + w] = rnd_.Rand8();
      }
    }
  }

130
131
132
133
134
135
136
137
138
  int width_, height_;
  static uint8_t* source_data_;
  int source_stride_;
  static uint8_t* reference_data_;
  int reference_stride_;

  ACMRandom rnd_;
};

139
140
class SADx4Test
    : public SADTestBase,
141
      public ::testing::WithParamInterface<SadMxNx4Param> {
142
143
144
145
146
147
148
149
 public:
  SADx4Test() : SADTestBase(GET_PARAM(0), GET_PARAM(1)) {}

 protected:
  void SADs(unsigned int *results) {
    const uint8_t* refs[] = {GetReference(0), GetReference(1),
                             GetReference(2), GetReference(3)};

150
151
152
    ASM_REGISTER_STATE_CHECK(GET_PARAM(2)(source_data_, source_stride_,
                                          refs, reference_stride_,
                                          results));
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
  }

  void CheckSADs() {
    unsigned int reference_sad, exp_sad[4];

    SADs(exp_sad);
    for (int block = 0; block < 4; ++block) {
      reference_sad = ReferenceSAD(UINT_MAX, block);

      EXPECT_EQ(reference_sad, exp_sad[block]) << "block " << block;
    }
  }
};

#if CONFIG_VP8_ENCODER
class SADTest
    : public SADTestBase,
170
      public ::testing::WithParamInterface<SadMxNParam> {
171
172
173
174
 public:
  SADTest() : SADTestBase(GET_PARAM(0), GET_PARAM(1)) {}

 protected:
175
  unsigned int SAD(unsigned int max_sad, int block_idx) {
176
177
178
    unsigned int ret;
    const uint8_t* const reference = GetReference(block_idx);

179
180
181
    ASM_REGISTER_STATE_CHECK(ret = GET_PARAM(2)(source_data_, source_stride_,
                                                reference, reference_stride_,
                                                max_sad));
182
183
184
    return ret;
  }

185
186
187
  void CheckSAD(unsigned int max_sad) {
    const unsigned int reference_sad = ReferenceSAD(max_sad, 0);
    const unsigned int exp_sad = SAD(max_sad, 0);
Johann's avatar
Johann committed
188
189
190
191
192
193
194
195

    if (reference_sad <= max_sad) {
      ASSERT_EQ(exp_sad, reference_sad);
    } else {
      // Alternative implementations are not required to check max_sad
      ASSERT_GE(exp_sad, reference_sad);
    }
  }
196
};
197
#endif  // CONFIG_VP8_ENCODER
Johann's avatar
Johann committed
198

199
200
201
#if CONFIG_VP9_ENCODER
class SADVP9Test
    : public SADTestBase,
202
      public ::testing::WithParamInterface<SadMxNVp9Param> {
203
 public:
204
  SADVP9Test() : SADTestBase(GET_PARAM(0), GET_PARAM(1)) {}
Johann's avatar
Johann committed
205

206
 protected:
207
208
209
  unsigned int SAD(int block_idx) {
    unsigned int ret;
    const uint8_t* const reference = GetReference(block_idx);
210

211
212
    ASM_REGISTER_STATE_CHECK(ret = GET_PARAM(2)(source_data_, source_stride_,
                                                reference, reference_stride_));
213
    return ret;
214
215
  }

216
217
218
  void CheckSAD() {
    const unsigned int reference_sad = ReferenceSAD(UINT_MAX, 0);
    const unsigned int exp_sad = SAD(0);
219

220
    ASSERT_EQ(reference_sad, exp_sad);
221
  }
Johann's avatar
Johann committed
222
};
223
#endif  // CONFIG_VP9_ENCODER
Johann's avatar
Johann committed
224

225
226
uint8_t* SADTestBase::source_data_ = NULL;
uint8_t* SADTestBase::reference_data_ = NULL;
227

228
#if CONFIG_VP8_ENCODER
Johann's avatar
Johann committed
229
230
231
TEST_P(SADTest, MaxRef) {
  FillConstant(source_data_, source_stride_, 0);
  FillConstant(reference_data_, reference_stride_, 255);
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
  CheckSAD(UINT_MAX);
}

TEST_P(SADTest, MaxSrc) {
  FillConstant(source_data_, source_stride_, 255);
  FillConstant(reference_data_, reference_stride_, 0);
  CheckSAD(UINT_MAX);
}

TEST_P(SADTest, ShortRef) {
  int tmp_stride = reference_stride_;
  reference_stride_ >>= 1;
  FillRandom(source_data_, source_stride_);
  FillRandom(reference_data_, reference_stride_);
  CheckSAD(UINT_MAX);
  reference_stride_ = tmp_stride;
}

TEST_P(SADTest, UnalignedRef) {
  // The reference frame, but not the source frame, may be unaligned for
  // certain types of searches.
  const int tmp_stride = reference_stride_;
  reference_stride_ -= 1;
  FillRandom(source_data_, source_stride_);
  FillRandom(reference_data_, reference_stride_);
  CheckSAD(UINT_MAX);
  reference_stride_ = tmp_stride;
}

TEST_P(SADTest, ShortSrc) {
  const int tmp_stride = source_stride_;
  source_stride_ >>= 1;
  FillRandom(source_data_, source_stride_);
  FillRandom(reference_data_, reference_stride_);
  CheckSAD(UINT_MAX);
  source_stride_ = tmp_stride;
}

TEST_P(SADTest, MaxSAD) {
  // Verify that, when max_sad is set, the implementation does not return a
  // value lower than the reference.
  FillConstant(source_data_, source_stride_, 255);
  FillConstant(reference_data_, reference_stride_, 0);
  CheckSAD(128);
}
#endif  // CONFIG_VP8_ENCODER

#if CONFIG_VP9_ENCODER
TEST_P(SADVP9Test, MaxRef) {
  FillConstant(source_data_, source_stride_, 0);
  FillConstant(reference_data_, reference_stride_, 255);
  CheckSAD();
}

TEST_P(SADVP9Test, MaxSrc) {
  FillConstant(source_data_, source_stride_, 255);
  FillConstant(reference_data_, reference_stride_, 0);
  CheckSAD();
Johann's avatar
Johann committed
290
291
}

292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
TEST_P(SADVP9Test, ShortRef) {
  const int tmp_stride = reference_stride_;
  reference_stride_ >>= 1;
  FillRandom(source_data_, source_stride_);
  FillRandom(reference_data_, reference_stride_);
  CheckSAD();
  reference_stride_ = tmp_stride;
}

TEST_P(SADVP9Test, UnalignedRef) {
  // The reference frame, but not the source frame, may be unaligned for
  // certain types of searches.
  const int tmp_stride = reference_stride_;
  reference_stride_ -= 1;
  FillRandom(source_data_, source_stride_);
  FillRandom(reference_data_, reference_stride_);
  CheckSAD();
  reference_stride_ = tmp_stride;
}

TEST_P(SADVP9Test, ShortSrc) {
  const int tmp_stride = source_stride_;
  source_stride_ >>= 1;
  FillRandom(source_data_, source_stride_);
  FillRandom(reference_data_, reference_stride_);
  CheckSAD();
  source_stride_ = tmp_stride;
}
#endif  // CONFIG_VP9_ENCODER

322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
TEST_P(SADx4Test, MaxRef) {
  FillConstant(source_data_, source_stride_, 0);
  FillConstant(GetReference(0), reference_stride_, 255);
  FillConstant(GetReference(1), reference_stride_, 255);
  FillConstant(GetReference(2), reference_stride_, 255);
  FillConstant(GetReference(3), reference_stride_, 255);
  CheckSADs();
}

TEST_P(SADx4Test, MaxSrc) {
  FillConstant(source_data_, source_stride_, 255);
  FillConstant(GetReference(0), reference_stride_, 0);
  FillConstant(GetReference(1), reference_stride_, 0);
  FillConstant(GetReference(2), reference_stride_, 0);
  FillConstant(GetReference(3), reference_stride_, 0);
  CheckSADs();
}

TEST_P(SADx4Test, ShortRef) {
  int tmp_stride = reference_stride_;
  reference_stride_ >>= 1;
  FillRandom(source_data_, source_stride_);
  FillRandom(GetReference(0), reference_stride_);
  FillRandom(GetReference(1), reference_stride_);
  FillRandom(GetReference(2), reference_stride_);
  FillRandom(GetReference(3), reference_stride_);
  CheckSADs();
  reference_stride_ = tmp_stride;
}

TEST_P(SADx4Test, UnalignedRef) {
  // The reference frame, but not the source frame, may be unaligned for
  // certain types of searches.
  int tmp_stride = reference_stride_;
  reference_stride_ -= 1;
  FillRandom(source_data_, source_stride_);
  FillRandom(GetReference(0), reference_stride_);
  FillRandom(GetReference(1), reference_stride_);
  FillRandom(GetReference(2), reference_stride_);
  FillRandom(GetReference(3), reference_stride_);
  CheckSADs();
  reference_stride_ = tmp_stride;
}

TEST_P(SADx4Test, ShortSrc) {
  int tmp_stride = source_stride_;
  source_stride_ >>= 1;
  FillRandom(source_data_, source_stride_);
  FillRandom(GetReference(0), reference_stride_);
  FillRandom(GetReference(1), reference_stride_);
  FillRandom(GetReference(2), reference_stride_);
  FillRandom(GetReference(3), reference_stride_);
  CheckSADs();
  source_stride_ = tmp_stride;
}

James Zern's avatar
James Zern committed
378
379
using std::tr1::make_tuple;

380
381
//------------------------------------------------------------------------------
// C functions
382
#if CONFIG_VP8_ENCODER
383
384
385
386
387
388
const SadMxNFunc sad_16x16_c = vp8_sad16x16_c;
const SadMxNFunc sad_8x16_c = vp8_sad8x16_c;
const SadMxNFunc sad_16x8_c = vp8_sad16x8_c;
const SadMxNFunc sad_8x8_c = vp8_sad8x8_c;
const SadMxNFunc sad_4x4_c = vp8_sad4x4_c;
const SadMxNParam c_tests[] = {
James Zern's avatar
James Zern committed
389
390
391
392
393
  make_tuple(16, 16, sad_16x16_c),
  make_tuple(8, 16, sad_8x16_c),
  make_tuple(16, 8, sad_16x8_c),
  make_tuple(8, 8, sad_8x8_c),
  make_tuple(4, 4, sad_4x4_c),
394
395
396
397
};
INSTANTIATE_TEST_CASE_P(C, SADTest, ::testing::ValuesIn(c_tests));
#endif  // CONFIG_VP8_ENCODER

398
#if CONFIG_VP9_ENCODER
399
400
401
402
403
404
405
406
407
408
const SadMxNVp9Func sad_64x64_c_vp9 = vp9_sad64x64_c;
const SadMxNVp9Func sad_32x32_c_vp9 = vp9_sad32x32_c;
const SadMxNVp9Func sad_16x16_c_vp9 = vp9_sad16x16_c;
const SadMxNVp9Func sad_8x16_c_vp9 = vp9_sad8x16_c;
const SadMxNVp9Func sad_16x8_c_vp9 = vp9_sad16x8_c;
const SadMxNVp9Func sad_8x8_c_vp9 = vp9_sad8x8_c;
const SadMxNVp9Func sad_8x4_c_vp9 = vp9_sad8x4_c;
const SadMxNVp9Func sad_4x8_c_vp9 = vp9_sad4x8_c;
const SadMxNVp9Func sad_4x4_c_vp9 = vp9_sad4x4_c;
const SadMxNVp9Param c_vp9_tests[] = {
James Zern's avatar
James Zern committed
409
410
411
412
413
414
  make_tuple(64, 64, sad_64x64_c_vp9),
  make_tuple(32, 32, sad_32x32_c_vp9),
  make_tuple(16, 16, sad_16x16_c_vp9),
  make_tuple(8, 16, sad_8x16_c_vp9),
  make_tuple(16, 8, sad_16x8_c_vp9),
  make_tuple(8, 8, sad_8x8_c_vp9),
415
416
  make_tuple(8, 4, sad_8x4_c_vp9),
  make_tuple(4, 8, sad_4x8_c_vp9),
James Zern's avatar
James Zern committed
417
418
  make_tuple(4, 4, sad_4x4_c_vp9),
};
419
INSTANTIATE_TEST_CASE_P(C, SADVP9Test, ::testing::ValuesIn(c_vp9_tests));
Johann's avatar
Johann committed
420

421
422
423
424
425
426
427
428
429
430
431
432
433
const SadMxNx4Func sad_64x64x4d_c = vp9_sad64x64x4d_c;
const SadMxNx4Func sad_64x32x4d_c = vp9_sad64x32x4d_c;
const SadMxNx4Func sad_32x64x4d_c = vp9_sad32x64x4d_c;
const SadMxNx4Func sad_32x32x4d_c = vp9_sad32x32x4d_c;
const SadMxNx4Func sad_32x16x4d_c = vp9_sad32x16x4d_c;
const SadMxNx4Func sad_16x32x4d_c = vp9_sad16x32x4d_c;
const SadMxNx4Func sad_16x16x4d_c = vp9_sad16x16x4d_c;
const SadMxNx4Func sad_16x8x4d_c = vp9_sad16x8x4d_c;
const SadMxNx4Func sad_8x16x4d_c = vp9_sad8x16x4d_c;
const SadMxNx4Func sad_8x8x4d_c = vp9_sad8x8x4d_c;
const SadMxNx4Func sad_8x4x4d_c = vp9_sad8x4x4d_c;
const SadMxNx4Func sad_4x8x4d_c = vp9_sad4x8x4d_c;
const SadMxNx4Func sad_4x4x4d_c = vp9_sad4x4x4d_c;
434
435
INSTANTIATE_TEST_CASE_P(C, SADx4Test, ::testing::Values(
                        make_tuple(64, 64, sad_64x64x4d_c),
436
437
                        make_tuple(64, 32, sad_64x32x4d_c),
                        make_tuple(32, 64, sad_32x64x4d_c),
438
                        make_tuple(32, 32, sad_32x32x4d_c),
439
440
                        make_tuple(32, 16, sad_32x16x4d_c),
                        make_tuple(16, 32, sad_16x32x4d_c),
441
                        make_tuple(16, 16, sad_16x16x4d_c),
442
443
                        make_tuple(16, 8, sad_16x8x4d_c),
                        make_tuple(8, 16, sad_8x16x4d_c),
444
                        make_tuple(8, 8, sad_8x8x4d_c),
445
446
                        make_tuple(8, 4, sad_8x4x4d_c),
                        make_tuple(4, 8, sad_4x8x4d_c),
447
                        make_tuple(4, 4, sad_4x4x4d_c)));
448
#endif  // CONFIG_VP9_ENCODER
449

450
451
//------------------------------------------------------------------------------
// ARM functions
Johann's avatar
Johann committed
452
#if HAVE_MEDIA
453
#if CONFIG_VP8_ENCODER
454
const SadMxNFunc sad_16x16_armv6 = vp8_sad16x16_armv6;
Johann's avatar
Johann committed
455
INSTANTIATE_TEST_CASE_P(MEDIA, SADTest, ::testing::Values(
James Zern's avatar
James Zern committed
456
                        make_tuple(16, 16, sad_16x16_armv6)));
457
458
#endif  // CONFIG_VP8_ENCODER
#endif  // HAVE_MEDIA
459

Johann's avatar
Johann committed
460
#if HAVE_NEON
461
#if CONFIG_VP8_ENCODER
462
463
464
465
466
const SadMxNFunc sad_16x16_neon = vp8_sad16x16_neon;
const SadMxNFunc sad_8x16_neon = vp8_sad8x16_neon;
const SadMxNFunc sad_16x8_neon = vp8_sad16x8_neon;
const SadMxNFunc sad_8x8_neon = vp8_sad8x8_neon;
const SadMxNFunc sad_4x4_neon = vp8_sad4x4_neon;
Johann's avatar
Johann committed
467
INSTANTIATE_TEST_CASE_P(NEON, SADTest, ::testing::Values(
James Zern's avatar
James Zern committed
468
469
470
471
472
                        make_tuple(16, 16, sad_16x16_neon),
                        make_tuple(8, 16, sad_8x16_neon),
                        make_tuple(16, 8, sad_16x8_neon),
                        make_tuple(8, 8, sad_8x8_neon),
                        make_tuple(4, 4, sad_4x4_neon)));
473
#endif  // CONFIG_VP8_ENCODER
474
#if CONFIG_VP9_ENCODER
475
476
477
const SadMxNVp9Func sad_64x64_neon_vp9 = vp9_sad64x64_neon;
const SadMxNVp9Func sad_32x32_neon_vp9 = vp9_sad32x32_neon;
const SadMxNVp9Func sad_16x16_neon_vp9 = vp9_sad16x16_neon;
Scott LaVarnway's avatar
Scott LaVarnway committed
478
const SadMxNVp9Func sad_8x8_neon_vp9 = vp9_sad8x8_neon;
479
const SadMxNVp9Param neon_vp9_tests[] = {
480
481
482
  make_tuple(64, 64, sad_64x64_neon_vp9),
  make_tuple(32, 32, sad_32x32_neon_vp9),
  make_tuple(16, 16, sad_16x16_neon_vp9),
Scott LaVarnway's avatar
Scott LaVarnway committed
483
  make_tuple(8, 8, sad_8x8_neon_vp9),
484
485
486
};
INSTANTIATE_TEST_CASE_P(NEON, SADVP9Test, ::testing::ValuesIn(neon_vp9_tests));
#endif  // CONFIG_VP9_ENCODER
487
#endif  // HAVE_NEON
Johann's avatar
Johann committed
488

489
490
//------------------------------------------------------------------------------
// x86 functions
Johann's avatar
Johann committed
491
#if HAVE_MMX
492
#if CONFIG_VP8_ENCODER
493
494
495
496
497
498
const SadMxNFunc sad_16x16_mmx = vp8_sad16x16_mmx;
const SadMxNFunc sad_8x16_mmx = vp8_sad8x16_mmx;
const SadMxNFunc sad_16x8_mmx = vp8_sad16x8_mmx;
const SadMxNFunc sad_8x8_mmx = vp8_sad8x8_mmx;
const SadMxNFunc sad_4x4_mmx = vp8_sad4x4_mmx;
const SadMxNParam mmx_tests[] = {
James Zern's avatar
James Zern committed
499
500
501
502
503
  make_tuple(16, 16, sad_16x16_mmx),
  make_tuple(8, 16, sad_8x16_mmx),
  make_tuple(16, 8, sad_16x8_mmx),
  make_tuple(8, 8, sad_8x8_mmx),
  make_tuple(4, 4, sad_4x4_mmx),
504
505
506
507
};
INSTANTIATE_TEST_CASE_P(MMX, SADTest, ::testing::ValuesIn(mmx_tests));
#endif  // CONFIG_VP8_ENCODER

508
#if CONFIG_VP9_ENCODER
509
510
511
512
513
514
const SadMxNVp9Func sad_16x16_mmx_vp9 = vp9_sad16x16_mmx;
const SadMxNVp9Func sad_8x16_mmx_vp9 = vp9_sad8x16_mmx;
const SadMxNVp9Func sad_16x8_mmx_vp9 = vp9_sad16x8_mmx;
const SadMxNVp9Func sad_8x8_mmx_vp9 = vp9_sad8x8_mmx;
const SadMxNVp9Func sad_4x4_mmx_vp9 = vp9_sad4x4_mmx;
const SadMxNVp9Param mmx_vp9_tests[] = {
James Zern's avatar
James Zern committed
515
516
517
518
519
520
  make_tuple(16, 16, sad_16x16_mmx_vp9),
  make_tuple(8, 16, sad_8x16_mmx_vp9),
  make_tuple(16, 8, sad_16x8_mmx_vp9),
  make_tuple(8, 8, sad_8x8_mmx_vp9),
  make_tuple(4, 4, sad_4x4_mmx_vp9),
};
521
522
523
INSTANTIATE_TEST_CASE_P(MMX, SADVP9Test, ::testing::ValuesIn(mmx_vp9_tests));
#endif  // CONFIG_VP9_ENCODER
#endif  // HAVE_MMX
524
525
526

#if HAVE_SSE
#if CONFIG_VP9_ENCODER
Jim Bankoski's avatar
Jim Bankoski committed
527
#if CONFIG_USE_X86INC
528
529
const SadMxNVp9Func sad_4x4_sse_vp9 = vp9_sad4x4_sse;
const SadMxNVp9Func sad_4x8_sse_vp9 = vp9_sad4x8_sse;
530
INSTANTIATE_TEST_CASE_P(SSE, SADVP9Test, ::testing::Values(
531
532
                        make_tuple(4, 4, sad_4x4_sse_vp9),
                        make_tuple(4, 8, sad_4x8_sse_vp9)));
533

534
535
const SadMxNx4Func sad_4x8x4d_sse = vp9_sad4x8x4d_sse;
const SadMxNx4Func sad_4x4x4d_sse = vp9_sad4x4x4d_sse;
536
INSTANTIATE_TEST_CASE_P(SSE, SADx4Test, ::testing::Values(
537
                        make_tuple(4, 8, sad_4x8x4d_sse),
538
                        make_tuple(4, 4, sad_4x4x4d_sse)));
539
540
541
#endif  // CONFIG_USE_X86INC
#endif  // CONFIG_VP9_ENCODER
#endif  // HAVE_SSE
542

Johann's avatar
Johann committed
543
#if HAVE_SSE2
544
#if CONFIG_VP8_ENCODER
545
546
547
548
549
550
const SadMxNFunc sad_16x16_wmt = vp8_sad16x16_wmt;
const SadMxNFunc sad_8x16_wmt = vp8_sad8x16_wmt;
const SadMxNFunc sad_16x8_wmt = vp8_sad16x8_wmt;
const SadMxNFunc sad_8x8_wmt = vp8_sad8x8_wmt;
const SadMxNFunc sad_4x4_wmt = vp8_sad4x4_wmt;
const SadMxNParam sse2_tests[] = {
James Zern's avatar
James Zern committed
551
552
553
554
555
  make_tuple(16, 16, sad_16x16_wmt),
  make_tuple(8, 16, sad_8x16_wmt),
  make_tuple(16, 8, sad_16x8_wmt),
  make_tuple(8, 8, sad_8x8_wmt),
  make_tuple(4, 4, sad_4x4_wmt),
556
557
558
559
};
INSTANTIATE_TEST_CASE_P(SSE2, SADTest, ::testing::ValuesIn(sse2_tests));
#endif  // CONFIG_VP8_ENCODER

560
#if CONFIG_VP9_ENCODER
Jim Bankoski's avatar
Jim Bankoski committed
561
#if CONFIG_USE_X86INC
562
563
564
565
566
567
568
569
570
571
572
573
const SadMxNVp9Func sad_64x64_sse2_vp9 = vp9_sad64x64_sse2;
const SadMxNVp9Func sad_64x32_sse2_vp9 = vp9_sad64x32_sse2;
const SadMxNVp9Func sad_32x64_sse2_vp9 = vp9_sad32x64_sse2;
const SadMxNVp9Func sad_32x32_sse2_vp9 = vp9_sad32x32_sse2;
const SadMxNVp9Func sad_32x16_sse2_vp9 = vp9_sad32x16_sse2;
const SadMxNVp9Func sad_16x32_sse2_vp9 = vp9_sad16x32_sse2;
const SadMxNVp9Func sad_16x16_sse2_vp9 = vp9_sad16x16_sse2;
const SadMxNVp9Func sad_16x8_sse2_vp9 = vp9_sad16x8_sse2;
const SadMxNVp9Func sad_8x16_sse2_vp9 = vp9_sad8x16_sse2;
const SadMxNVp9Func sad_8x8_sse2_vp9 = vp9_sad8x8_sse2;
const SadMxNVp9Func sad_8x4_sse2_vp9 = vp9_sad8x4_sse2;
const SadMxNVp9Param sse2_vp9_tests[] = {
James Zern's avatar
James Zern committed
574
  make_tuple(64, 64, sad_64x64_sse2_vp9),
575
576
  make_tuple(64, 32, sad_64x32_sse2_vp9),
  make_tuple(32, 64, sad_32x64_sse2_vp9),
James Zern's avatar
James Zern committed
577
  make_tuple(32, 32, sad_32x32_sse2_vp9),
578
579
  make_tuple(32, 16, sad_32x16_sse2_vp9),
  make_tuple(16, 32, sad_16x32_sse2_vp9),
James Zern's avatar
James Zern committed
580
581
  make_tuple(16, 16, sad_16x16_sse2_vp9),
  make_tuple(16, 8, sad_16x8_sse2_vp9),
582
  make_tuple(8, 16, sad_8x16_sse2_vp9),
James Zern's avatar
James Zern committed
583
  make_tuple(8, 8, sad_8x8_sse2_vp9),
584
  make_tuple(8, 4, sad_8x4_sse2_vp9),
James Zern's avatar
James Zern committed
585
};
586
INSTANTIATE_TEST_CASE_P(SSE2, SADVP9Test, ::testing::ValuesIn(sse2_vp9_tests));
587

588
589
590
591
592
593
594
595
596
597
598
const SadMxNx4Func sad_64x64x4d_sse2 = vp9_sad64x64x4d_sse2;
const SadMxNx4Func sad_64x32x4d_sse2 = vp9_sad64x32x4d_sse2;
const SadMxNx4Func sad_32x64x4d_sse2 = vp9_sad32x64x4d_sse2;
const SadMxNx4Func sad_32x32x4d_sse2 = vp9_sad32x32x4d_sse2;
const SadMxNx4Func sad_32x16x4d_sse2 = vp9_sad32x16x4d_sse2;
const SadMxNx4Func sad_16x32x4d_sse2 = vp9_sad16x32x4d_sse2;
const SadMxNx4Func sad_16x16x4d_sse2 = vp9_sad16x16x4d_sse2;
const SadMxNx4Func sad_16x8x4d_sse2 = vp9_sad16x8x4d_sse2;
const SadMxNx4Func sad_8x16x4d_sse2 = vp9_sad8x16x4d_sse2;
const SadMxNx4Func sad_8x8x4d_sse2 = vp9_sad8x8x4d_sse2;
const SadMxNx4Func sad_8x4x4d_sse2 = vp9_sad8x4x4d_sse2;
599
600
INSTANTIATE_TEST_CASE_P(SSE2, SADx4Test, ::testing::Values(
                        make_tuple(64, 64, sad_64x64x4d_sse2),
601
602
                        make_tuple(64, 32, sad_64x32x4d_sse2),
                        make_tuple(32, 64, sad_32x64x4d_sse2),
603
                        make_tuple(32, 32, sad_32x32x4d_sse2),
604
605
                        make_tuple(32, 16, sad_32x16x4d_sse2),
                        make_tuple(16, 32, sad_16x32x4d_sse2),
606
607
608
                        make_tuple(16, 16, sad_16x16x4d_sse2),
                        make_tuple(16, 8, sad_16x8x4d_sse2),
                        make_tuple(8, 16, sad_8x16x4d_sse2),
609
610
                        make_tuple(8, 8, sad_8x8x4d_sse2),
                        make_tuple(8, 4, sad_8x4x4d_sse2)));
611
612
613
#endif  // CONFIG_USE_X86INC
#endif  // CONFIG_VP9_ENCODER
#endif  // HAVE_SSE2
614
615
616

#if HAVE_SSE3
#if CONFIG_VP8_ENCODER
617
618
619
620
621
const SadMxNx4Func sad_16x16x4d_sse3 = vp8_sad16x16x4d_sse3;
const SadMxNx4Func sad_16x8x4d_sse3 = vp8_sad16x8x4d_sse3;
const SadMxNx4Func sad_8x16x4d_sse3 = vp8_sad8x16x4d_sse3;
const SadMxNx4Func sad_8x8x4d_sse3 = vp8_sad8x8x4d_sse3;
const SadMxNx4Func sad_4x4x4d_sse3 = vp8_sad4x4x4d_sse3;
622
623
624
625
626
627
INSTANTIATE_TEST_CASE_P(SSE3, SADx4Test, ::testing::Values(
                        make_tuple(16, 16, sad_16x16x4d_sse3),
                        make_tuple(16, 8, sad_16x8x4d_sse3),
                        make_tuple(8, 16, sad_8x16x4d_sse3),
                        make_tuple(8, 8, sad_8x8x4d_sse3),
                        make_tuple(4, 4, sad_4x4x4d_sse3)));
628
629
#endif  // CONFIG_VP8_ENCODER
#endif  // HAVE_SSE3
630

Johann's avatar
Johann committed
631
#if HAVE_SSSE3
Jim Bankoski's avatar
Jim Bankoski committed
632
#if CONFIG_USE_X86INC
Yaowu Xu's avatar
Yaowu Xu committed
633
#if CONFIG_VP8_ENCODER
634
const SadMxNFunc sad_16x16_sse3 = vp8_sad16x16_sse3;
Johann's avatar
Johann committed
635
INSTANTIATE_TEST_CASE_P(SSE3, SADTest, ::testing::Values(
James Zern's avatar
James Zern committed
636
                        make_tuple(16, 16, sad_16x16_sse3)));
637
638
639
#endif  // CONFIG_VP8_ENCODER
#endif  // CONFIG_USE_X86INC
#endif  // HAVE_SSSE3
Johann's avatar
Johann committed
640

641
642
643
644
645
646
647
648
649
650
651
652
#if HAVE_AVX2
#if CONFIG_VP9_ENCODER
// TODO(jzern): these prototypes can be removed after the avx2 versions are
// reenabled in vp9_rtcd_defs.pl.
extern "C" {
void vp9_sad32x32x4d_avx2(const uint8_t *src_ptr, int src_stride,
                          const uint8_t *const ref_ptr[], int ref_stride,
                          unsigned int *sad_array);
void vp9_sad64x64x4d_avx2(const uint8_t *src_ptr, int src_stride,
                          const uint8_t *const ref_ptr[], int ref_stride,
                          unsigned int *sad_array);
}
653
654
const SadMxNx4Func sad_64x64x4d_avx2 = vp9_sad64x64x4d_avx2;
const SadMxNx4Func sad_32x32x4d_avx2 = vp9_sad32x32x4d_avx2;
655
656
657
658
659
660
INSTANTIATE_TEST_CASE_P(DISABLED_AVX2, SADx4Test, ::testing::Values(
                        make_tuple(32, 32, sad_32x32x4d_avx2),
                        make_tuple(64, 64, sad_64x64x4d_avx2)));
#endif  // CONFIG_VP9_ENCODER
#endif  // HAVE_AVX2

Johann's avatar
Johann committed
661
}  // namespace