• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *  Copyright (c) 2012 The WebRTC project authors. All Rights Reserved.
3  *
4  *  Use of this source code is governed by a BSD-style license
5  *  that can be found in the LICENSE file in the root of the source
6  *  tree. An additional intellectual property rights grant can be found
7  *  in the file PATENTS.  All contributing project authors may
8  *  be found in the AUTHORS file in the root of the source tree.
9  */
10 
11 #include "modules/audio_processing/utility/delay_estimator.h"
12 
13 #include "modules/audio_processing/utility/delay_estimator_internal.h"
14 #include "modules/audio_processing/utility/delay_estimator_wrapper.h"
15 #include "test/gtest.h"
16 
17 namespace webrtc {
18 
19 namespace {
20 
21 enum { kSpectrumSize = 65 };
22 // Delay history sizes.
23 enum { kMaxDelay = 100 };
24 enum { kLookahead = 10 };
25 enum { kHistorySize = kMaxDelay + kLookahead };
26 // Length of binary spectrum sequence.
27 enum { kSequenceLength = 400 };
28 
29 const int kDifferentHistorySize = 3;
30 const int kDifferentLookahead = 1;
31 
32 const int kEnable[] = {0, 1};
33 const size_t kSizeEnable = sizeof(kEnable) / sizeof(*kEnable);
34 
35 class DelayEstimatorTest : public ::testing::Test {
36  protected:
37   DelayEstimatorTest();
38   void SetUp() override;
39   void TearDown() override;
40 
41   void Init();
42   void InitBinary();
43   void VerifyDelay(BinaryDelayEstimator* binary_handle, int offset, int delay);
44   void RunBinarySpectra(BinaryDelayEstimator* binary1,
45                         BinaryDelayEstimator* binary2,
46                         int near_offset,
47                         int lookahead_offset,
48                         int far_offset);
49   void RunBinarySpectraTest(int near_offset,
50                             int lookahead_offset,
51                             int ref_robust_validation,
52                             int robust_validation);
53 
54   void* handle_;
55   DelayEstimator* self_;
56   void* farend_handle_;
57   DelayEstimatorFarend* farend_self_;
58   BinaryDelayEstimator* binary_;
59   BinaryDelayEstimatorFarend* binary_farend_;
60   int spectrum_size_;
61   // Dummy input spectra.
62   float far_f_[kSpectrumSize];
63   float near_f_[kSpectrumSize];
64   uint16_t far_u16_[kSpectrumSize];
65   uint16_t near_u16_[kSpectrumSize];
66   uint32_t binary_spectrum_[kSequenceLength + kHistorySize];
67 };
68 
DelayEstimatorTest()69 DelayEstimatorTest::DelayEstimatorTest()
70     : handle_(NULL),
71       self_(NULL),
72       farend_handle_(NULL),
73       farend_self_(NULL),
74       binary_(NULL),
75       binary_farend_(NULL),
76       spectrum_size_(kSpectrumSize) {
77   // Dummy input data are set with more or less arbitrary non-zero values.
78   memset(far_f_, 1, sizeof(far_f_));
79   memset(near_f_, 2, sizeof(near_f_));
80   memset(far_u16_, 1, sizeof(far_u16_));
81   memset(near_u16_, 2, sizeof(near_u16_));
82   // Construct a sequence of binary spectra used to verify delay estimate. The
83   // |kSequenceLength| has to be long enough for the delay estimation to leave
84   // the initialized state.
85   binary_spectrum_[0] = 1;
86   for (int i = 1; i < (kSequenceLength + kHistorySize); i++) {
87     binary_spectrum_[i] = 3 * binary_spectrum_[i - 1];
88   }
89 }
90 
SetUp()91 void DelayEstimatorTest::SetUp() {
92   farend_handle_ =
93       WebRtc_CreateDelayEstimatorFarend(kSpectrumSize, kHistorySize);
94   ASSERT_TRUE(farend_handle_ != NULL);
95   farend_self_ = reinterpret_cast<DelayEstimatorFarend*>(farend_handle_);
96   handle_ = WebRtc_CreateDelayEstimator(farend_handle_, kLookahead);
97   ASSERT_TRUE(handle_ != NULL);
98   self_ = reinterpret_cast<DelayEstimator*>(handle_);
99   binary_farend_ = WebRtc_CreateBinaryDelayEstimatorFarend(kHistorySize);
100   ASSERT_TRUE(binary_farend_ != NULL);
101   binary_ = WebRtc_CreateBinaryDelayEstimator(binary_farend_, kLookahead);
102   ASSERT_TRUE(binary_ != NULL);
103 }
104 
TearDown()105 void DelayEstimatorTest::TearDown() {
106   WebRtc_FreeDelayEstimator(handle_);
107   handle_ = NULL;
108   self_ = NULL;
109   WebRtc_FreeDelayEstimatorFarend(farend_handle_);
110   farend_handle_ = NULL;
111   farend_self_ = NULL;
112   WebRtc_FreeBinaryDelayEstimator(binary_);
113   binary_ = NULL;
114   WebRtc_FreeBinaryDelayEstimatorFarend(binary_farend_);
115   binary_farend_ = NULL;
116 }
117 
Init()118 void DelayEstimatorTest::Init() {
119   // Initialize Delay Estimator
120   EXPECT_EQ(0, WebRtc_InitDelayEstimatorFarend(farend_handle_));
121   EXPECT_EQ(0, WebRtc_InitDelayEstimator(handle_));
122   // Verify initialization.
123   EXPECT_EQ(0, farend_self_->far_spectrum_initialized);
124   EXPECT_EQ(0, self_->near_spectrum_initialized);
125   EXPECT_EQ(-2, WebRtc_last_delay(handle_));  // Delay in initial state.
126   EXPECT_FLOAT_EQ(0, WebRtc_last_delay_quality(handle_));  // Zero quality.
127 }
128 
InitBinary()129 void DelayEstimatorTest::InitBinary() {
130   // Initialize Binary Delay Estimator (far-end part).
131   WebRtc_InitBinaryDelayEstimatorFarend(binary_farend_);
132   // Initialize Binary Delay Estimator
133   WebRtc_InitBinaryDelayEstimator(binary_);
134   // Verify initialization. This does not guarantee a complete check, since
135   // |last_delay| may be equal to -2 before initialization if done on the fly.
136   EXPECT_EQ(-2, binary_->last_delay);
137 }
138 
VerifyDelay(BinaryDelayEstimator * binary_handle,int offset,int delay)139 void DelayEstimatorTest::VerifyDelay(BinaryDelayEstimator* binary_handle,
140                                      int offset,
141                                      int delay) {
142   // Verify that we WebRtc_binary_last_delay() returns correct delay.
143   EXPECT_EQ(delay, WebRtc_binary_last_delay(binary_handle));
144 
145   if (delay != -2) {
146     // Verify correct delay estimate. In the non-causal case the true delay
147     // is equivalent with the |offset|.
148     EXPECT_EQ(offset, delay);
149   }
150 }
151 
RunBinarySpectra(BinaryDelayEstimator * binary1,BinaryDelayEstimator * binary2,int near_offset,int lookahead_offset,int far_offset)152 void DelayEstimatorTest::RunBinarySpectra(BinaryDelayEstimator* binary1,
153                                           BinaryDelayEstimator* binary2,
154                                           int near_offset,
155                                           int lookahead_offset,
156                                           int far_offset) {
157   int different_validations =
158       binary1->robust_validation_enabled ^ binary2->robust_validation_enabled;
159   WebRtc_InitBinaryDelayEstimatorFarend(binary_farend_);
160   WebRtc_InitBinaryDelayEstimator(binary1);
161   WebRtc_InitBinaryDelayEstimator(binary2);
162   // Verify initialization. This does not guarantee a complete check, since
163   // |last_delay| may be equal to -2 before initialization if done on the fly.
164   EXPECT_EQ(-2, binary1->last_delay);
165   EXPECT_EQ(-2, binary2->last_delay);
166   for (int i = kLookahead; i < (kSequenceLength + kLookahead); i++) {
167     WebRtc_AddBinaryFarSpectrum(binary_farend_,
168                                 binary_spectrum_[i + far_offset]);
169     int delay_1 = WebRtc_ProcessBinarySpectrum(binary1, binary_spectrum_[i]);
170     int delay_2 = WebRtc_ProcessBinarySpectrum(
171         binary2, binary_spectrum_[i - near_offset]);
172 
173     VerifyDelay(binary1, far_offset + kLookahead, delay_1);
174     VerifyDelay(binary2,
175                 far_offset + kLookahead + lookahead_offset + near_offset,
176                 delay_2);
177     // Expect the two delay estimates to be offset by |lookahead_offset| +
178     // |near_offset| when we have left the initial state.
179     if ((delay_1 != -2) && (delay_2 != -2)) {
180       EXPECT_EQ(delay_1, delay_2 - lookahead_offset - near_offset);
181     }
182     // For the case of identical signals |delay_1| and |delay_2| should match
183     // all the time, unless one of them has robust validation turned on.  In
184     // that case the robust validation leaves the initial state faster.
185     if ((near_offset == 0) && (lookahead_offset == 0)) {
186       if (!different_validations) {
187         EXPECT_EQ(delay_1, delay_2);
188       } else {
189         if (binary1->robust_validation_enabled) {
190           EXPECT_GE(delay_1, delay_2);
191         } else {
192           EXPECT_GE(delay_2, delay_1);
193         }
194       }
195     }
196   }
197   // Verify that we have left the initialized state.
198   EXPECT_NE(-2, WebRtc_binary_last_delay(binary1));
199   EXPECT_LT(0, WebRtc_binary_last_delay_quality(binary1));
200   EXPECT_NE(-2, WebRtc_binary_last_delay(binary2));
201   EXPECT_LT(0, WebRtc_binary_last_delay_quality(binary2));
202 }
203 
RunBinarySpectraTest(int near_offset,int lookahead_offset,int ref_robust_validation,int robust_validation)204 void DelayEstimatorTest::RunBinarySpectraTest(int near_offset,
205                                               int lookahead_offset,
206                                               int ref_robust_validation,
207                                               int robust_validation) {
208   BinaryDelayEstimator* binary2 = WebRtc_CreateBinaryDelayEstimator(
209       binary_farend_, kLookahead + lookahead_offset);
210   // Verify the delay for both causal and non-causal systems. For causal systems
211   // the delay is equivalent with a positive |offset| of the far-end sequence.
212   // For non-causal systems the delay is equivalent with a negative |offset| of
213   // the far-end sequence.
214   binary_->robust_validation_enabled = ref_robust_validation;
215   binary2->robust_validation_enabled = robust_validation;
216   for (int offset = -kLookahead;
217        offset < kMaxDelay - lookahead_offset - near_offset; offset++) {
218     RunBinarySpectra(binary_, binary2, near_offset, lookahead_offset, offset);
219   }
220   WebRtc_FreeBinaryDelayEstimator(binary2);
221   binary2 = NULL;
222   binary_->robust_validation_enabled = 0;  // Reset reference.
223 }
224 
TEST_F(DelayEstimatorTest,CorrectErrorReturnsOfWrapper)225 TEST_F(DelayEstimatorTest, CorrectErrorReturnsOfWrapper) {
226   // In this test we verify correct error returns on invalid API calls.
227 
228   // WebRtc_CreateDelayEstimatorFarend() and WebRtc_CreateDelayEstimator()
229   // should return a NULL pointer on invalid input values.
230   // Make sure we have a non-NULL value at start, so we can detect NULL after
231   // create failure.
232   void* handle = farend_handle_;
233   handle = WebRtc_CreateDelayEstimatorFarend(33, kHistorySize);
234   EXPECT_TRUE(handle == NULL);
235   handle = WebRtc_CreateDelayEstimatorFarend(kSpectrumSize, 1);
236   EXPECT_TRUE(handle == NULL);
237 
238   handle = handle_;
239   handle = WebRtc_CreateDelayEstimator(NULL, kLookahead);
240   EXPECT_TRUE(handle == NULL);
241   handle = WebRtc_CreateDelayEstimator(farend_handle_, -1);
242   EXPECT_TRUE(handle == NULL);
243 
244   // WebRtc_InitDelayEstimatorFarend() and WebRtc_InitDelayEstimator() should
245   // return -1 if we have a NULL pointer as |handle|.
246   EXPECT_EQ(-1, WebRtc_InitDelayEstimatorFarend(NULL));
247   EXPECT_EQ(-1, WebRtc_InitDelayEstimator(NULL));
248 
249   // WebRtc_AddFarSpectrumFloat() should return -1 if we have:
250   // 1) NULL pointer as |handle|.
251   // 2) NULL pointer as far-end spectrum.
252   // 3) Incorrect spectrum size.
253   EXPECT_EQ(-1, WebRtc_AddFarSpectrumFloat(NULL, far_f_, spectrum_size_));
254   // Use |farend_handle_| which is properly created at SetUp().
255   EXPECT_EQ(-1,
256             WebRtc_AddFarSpectrumFloat(farend_handle_, NULL, spectrum_size_));
257   EXPECT_EQ(-1, WebRtc_AddFarSpectrumFloat(farend_handle_, far_f_,
258                                            spectrum_size_ + 1));
259 
260   // WebRtc_AddFarSpectrumFix() should return -1 if we have:
261   // 1) NULL pointer as |handle|.
262   // 2) NULL pointer as far-end spectrum.
263   // 3) Incorrect spectrum size.
264   // 4) Too high precision in far-end spectrum (Q-domain > 15).
265   EXPECT_EQ(-1, WebRtc_AddFarSpectrumFix(NULL, far_u16_, spectrum_size_, 0));
266   EXPECT_EQ(-1,
267             WebRtc_AddFarSpectrumFix(farend_handle_, NULL, spectrum_size_, 0));
268   EXPECT_EQ(-1, WebRtc_AddFarSpectrumFix(farend_handle_, far_u16_,
269                                          spectrum_size_ + 1, 0));
270   EXPECT_EQ(-1, WebRtc_AddFarSpectrumFix(farend_handle_, far_u16_,
271                                          spectrum_size_, 16));
272 
273   // WebRtc_set_history_size() should return -1 if:
274   // 1) |handle| is a NULL.
275   // 2) |history_size| <= 1.
276   EXPECT_EQ(-1, WebRtc_set_history_size(NULL, 1));
277   EXPECT_EQ(-1, WebRtc_set_history_size(handle_, 1));
278   // WebRtc_history_size() should return -1 if:
279   // 1) NULL pointer input.
280   EXPECT_EQ(-1, WebRtc_history_size(NULL));
281   // 2) there is a mismatch between history size.
282   void* tmp_handle = WebRtc_CreateDelayEstimator(farend_handle_, kHistorySize);
283   EXPECT_EQ(0, WebRtc_InitDelayEstimator(tmp_handle));
284   EXPECT_EQ(kDifferentHistorySize,
285             WebRtc_set_history_size(tmp_handle, kDifferentHistorySize));
286   EXPECT_EQ(kDifferentHistorySize, WebRtc_history_size(tmp_handle));
287   EXPECT_EQ(kHistorySize, WebRtc_set_history_size(handle_, kHistorySize));
288   EXPECT_EQ(-1, WebRtc_history_size(tmp_handle));
289 
290   // WebRtc_set_lookahead() should return -1 if we try a value outside the
291   /// buffer.
292   EXPECT_EQ(-1, WebRtc_set_lookahead(handle_, kLookahead + 1));
293   EXPECT_EQ(-1, WebRtc_set_lookahead(handle_, -1));
294 
295   // WebRtc_set_allowed_offset() should return -1 if we have:
296   // 1) NULL pointer as |handle|.
297   // 2) |allowed_offset| < 0.
298   EXPECT_EQ(-1, WebRtc_set_allowed_offset(NULL, 0));
299   EXPECT_EQ(-1, WebRtc_set_allowed_offset(handle_, -1));
300 
301   EXPECT_EQ(-1, WebRtc_get_allowed_offset(NULL));
302 
303   // WebRtc_enable_robust_validation() should return -1 if we have:
304   // 1) NULL pointer as |handle|.
305   // 2) Incorrect |enable| value (not 0 or 1).
306   EXPECT_EQ(-1, WebRtc_enable_robust_validation(NULL, kEnable[0]));
307   EXPECT_EQ(-1, WebRtc_enable_robust_validation(handle_, -1));
308   EXPECT_EQ(-1, WebRtc_enable_robust_validation(handle_, 2));
309 
310   // WebRtc_is_robust_validation_enabled() should return -1 if we have NULL
311   // pointer as |handle|.
312   EXPECT_EQ(-1, WebRtc_is_robust_validation_enabled(NULL));
313 
314   // WebRtc_DelayEstimatorProcessFloat() should return -1 if we have:
315   // 1) NULL pointer as |handle|.
316   // 2) NULL pointer as near-end spectrum.
317   // 3) Incorrect spectrum size.
318   // 4) Non matching history sizes if multiple delay estimators using the same
319   //    far-end reference.
320   EXPECT_EQ(-1,
321             WebRtc_DelayEstimatorProcessFloat(NULL, near_f_, spectrum_size_));
322   // Use |handle_| which is properly created at SetUp().
323   EXPECT_EQ(-1,
324             WebRtc_DelayEstimatorProcessFloat(handle_, NULL, spectrum_size_));
325   EXPECT_EQ(-1, WebRtc_DelayEstimatorProcessFloat(handle_, near_f_,
326                                                   spectrum_size_ + 1));
327   // |tmp_handle| is already in a non-matching state.
328   EXPECT_EQ(-1, WebRtc_DelayEstimatorProcessFloat(tmp_handle, near_f_,
329                                                   spectrum_size_));
330 
331   // WebRtc_DelayEstimatorProcessFix() should return -1 if we have:
332   // 1) NULL pointer as |handle|.
333   // 2) NULL pointer as near-end spectrum.
334   // 3) Incorrect spectrum size.
335   // 4) Too high precision in near-end spectrum (Q-domain > 15).
336   // 5) Non matching history sizes if multiple delay estimators using the same
337   //    far-end reference.
338   EXPECT_EQ(
339       -1, WebRtc_DelayEstimatorProcessFix(NULL, near_u16_, spectrum_size_, 0));
340   EXPECT_EQ(-1,
341             WebRtc_DelayEstimatorProcessFix(handle_, NULL, spectrum_size_, 0));
342   EXPECT_EQ(-1, WebRtc_DelayEstimatorProcessFix(handle_, near_u16_,
343                                                 spectrum_size_ + 1, 0));
344   EXPECT_EQ(-1, WebRtc_DelayEstimatorProcessFix(handle_, near_u16_,
345                                                 spectrum_size_, 16));
346   // |tmp_handle| is already in a non-matching state.
347   EXPECT_EQ(-1, WebRtc_DelayEstimatorProcessFix(tmp_handle, near_u16_,
348                                                 spectrum_size_, 0));
349   WebRtc_FreeDelayEstimator(tmp_handle);
350 
351   // WebRtc_last_delay() should return -1 if we have a NULL pointer as |handle|.
352   EXPECT_EQ(-1, WebRtc_last_delay(NULL));
353 
354   // Free any local memory if needed.
355   WebRtc_FreeDelayEstimator(handle);
356 }
357 
TEST_F(DelayEstimatorTest,VerifyAllowedOffset)358 TEST_F(DelayEstimatorTest, VerifyAllowedOffset) {
359   // Is set to zero by default.
360   EXPECT_EQ(0, WebRtc_get_allowed_offset(handle_));
361   for (int i = 1; i >= 0; i--) {
362     EXPECT_EQ(0, WebRtc_set_allowed_offset(handle_, i));
363     EXPECT_EQ(i, WebRtc_get_allowed_offset(handle_));
364     Init();
365     // Unaffected over a reset.
366     EXPECT_EQ(i, WebRtc_get_allowed_offset(handle_));
367   }
368 }
369 
TEST_F(DelayEstimatorTest,VerifyEnableRobustValidation)370 TEST_F(DelayEstimatorTest, VerifyEnableRobustValidation) {
371   // Disabled by default.
372   EXPECT_EQ(0, WebRtc_is_robust_validation_enabled(handle_));
373   for (size_t i = 0; i < kSizeEnable; ++i) {
374     EXPECT_EQ(0, WebRtc_enable_robust_validation(handle_, kEnable[i]));
375     EXPECT_EQ(kEnable[i], WebRtc_is_robust_validation_enabled(handle_));
376     Init();
377     // Unaffected over a reset.
378     EXPECT_EQ(kEnable[i], WebRtc_is_robust_validation_enabled(handle_));
379   }
380 }
381 
TEST_F(DelayEstimatorTest,InitializedSpectrumAfterProcess)382 TEST_F(DelayEstimatorTest, InitializedSpectrumAfterProcess) {
383   // In this test we verify that the mean spectra are initialized after first
384   // time we call WebRtc_AddFarSpectrum() and Process() respectively. The test
385   // also verifies the state is not left for zero spectra.
386   const float kZerosFloat[kSpectrumSize] = {0.0};
387   const uint16_t kZerosU16[kSpectrumSize] = {0};
388 
389   // For floating point operations, process one frame and verify initialization
390   // flag.
391   Init();
392   EXPECT_EQ(0, WebRtc_AddFarSpectrumFloat(farend_handle_, kZerosFloat,
393                                           spectrum_size_));
394   EXPECT_EQ(0, farend_self_->far_spectrum_initialized);
395   EXPECT_EQ(0,
396             WebRtc_AddFarSpectrumFloat(farend_handle_, far_f_, spectrum_size_));
397   EXPECT_EQ(1, farend_self_->far_spectrum_initialized);
398   EXPECT_EQ(-2, WebRtc_DelayEstimatorProcessFloat(handle_, kZerosFloat,
399                                                   spectrum_size_));
400   EXPECT_EQ(0, self_->near_spectrum_initialized);
401   EXPECT_EQ(
402       -2, WebRtc_DelayEstimatorProcessFloat(handle_, near_f_, spectrum_size_));
403   EXPECT_EQ(1, self_->near_spectrum_initialized);
404 
405   // For fixed point operations, process one frame and verify initialization
406   // flag.
407   Init();
408   EXPECT_EQ(0, WebRtc_AddFarSpectrumFix(farend_handle_, kZerosU16,
409                                         spectrum_size_, 0));
410   EXPECT_EQ(0, farend_self_->far_spectrum_initialized);
411   EXPECT_EQ(
412       0, WebRtc_AddFarSpectrumFix(farend_handle_, far_u16_, spectrum_size_, 0));
413   EXPECT_EQ(1, farend_self_->far_spectrum_initialized);
414   EXPECT_EQ(-2, WebRtc_DelayEstimatorProcessFix(handle_, kZerosU16,
415                                                 spectrum_size_, 0));
416   EXPECT_EQ(0, self_->near_spectrum_initialized);
417   EXPECT_EQ(-2, WebRtc_DelayEstimatorProcessFix(handle_, near_u16_,
418                                                 spectrum_size_, 0));
419   EXPECT_EQ(1, self_->near_spectrum_initialized);
420 }
421 
TEST_F(DelayEstimatorTest,CorrectLastDelay)422 TEST_F(DelayEstimatorTest, CorrectLastDelay) {
423   // In this test we verify that we get the correct last delay upon valid call.
424   // We simply process the same data until we leave the initialized state
425   // (|last_delay| = -2). Then we compare the Process() output with the
426   // last_delay() call.
427 
428   // TODO(bjornv): Update quality values for robust validation.
429   int last_delay = 0;
430   // Floating point operations.
431   Init();
432   for (int i = 0; i < 200; i++) {
433     EXPECT_EQ(
434         0, WebRtc_AddFarSpectrumFloat(farend_handle_, far_f_, spectrum_size_));
435     last_delay =
436         WebRtc_DelayEstimatorProcessFloat(handle_, near_f_, spectrum_size_);
437     if (last_delay != -2) {
438       EXPECT_EQ(last_delay, WebRtc_last_delay(handle_));
439       if (!WebRtc_is_robust_validation_enabled(handle_)) {
440         EXPECT_FLOAT_EQ(7203.f / kMaxBitCountsQ9,
441                         WebRtc_last_delay_quality(handle_));
442       }
443       break;
444     }
445   }
446   // Verify that we have left the initialized state.
447   EXPECT_NE(-2, WebRtc_last_delay(handle_));
448   EXPECT_LT(0, WebRtc_last_delay_quality(handle_));
449 
450   // Fixed point operations.
451   Init();
452   for (int i = 0; i < 200; i++) {
453     EXPECT_EQ(0, WebRtc_AddFarSpectrumFix(farend_handle_, far_u16_,
454                                           spectrum_size_, 0));
455     last_delay =
456         WebRtc_DelayEstimatorProcessFix(handle_, near_u16_, spectrum_size_, 0);
457     if (last_delay != -2) {
458       EXPECT_EQ(last_delay, WebRtc_last_delay(handle_));
459       if (!WebRtc_is_robust_validation_enabled(handle_)) {
460         EXPECT_FLOAT_EQ(7203.f / kMaxBitCountsQ9,
461                         WebRtc_last_delay_quality(handle_));
462       }
463       break;
464     }
465   }
466   // Verify that we have left the initialized state.
467   EXPECT_NE(-2, WebRtc_last_delay(handle_));
468   EXPECT_LT(0, WebRtc_last_delay_quality(handle_));
469 }
470 
TEST_F(DelayEstimatorTest,CorrectErrorReturnsOfBinaryEstimatorFarend)471 TEST_F(DelayEstimatorTest, CorrectErrorReturnsOfBinaryEstimatorFarend) {
472   // In this test we verify correct output on invalid API calls to the Binary
473   // Delay Estimator (far-end part).
474 
475   BinaryDelayEstimatorFarend* binary = binary_farend_;
476   // WebRtc_CreateBinaryDelayEstimatorFarend() should return -1 if the input
477   // history size is less than 2. This is to make sure the buffer shifting
478   // applies properly.
479   // Make sure we have a non-NULL value at start, so we can detect NULL after
480   // create failure.
481   binary = WebRtc_CreateBinaryDelayEstimatorFarend(1);
482   EXPECT_TRUE(binary == NULL);
483 }
484 
TEST_F(DelayEstimatorTest,CorrectErrorReturnsOfBinaryEstimator)485 TEST_F(DelayEstimatorTest, CorrectErrorReturnsOfBinaryEstimator) {
486   // In this test we verify correct output on invalid API calls to the Binary
487   // Delay Estimator.
488 
489   BinaryDelayEstimator* binary_handle = binary_;
490   // WebRtc_CreateBinaryDelayEstimator() should return -1 if we have a NULL
491   // pointer as |binary_farend| or invalid input values. Upon failure, the
492   // |binary_handle| should be NULL.
493   // Make sure we have a non-NULL value at start, so we can detect NULL after
494   // create failure.
495   binary_handle = WebRtc_CreateBinaryDelayEstimator(NULL, kLookahead);
496   EXPECT_TRUE(binary_handle == NULL);
497   binary_handle = WebRtc_CreateBinaryDelayEstimator(binary_farend_, -1);
498   EXPECT_TRUE(binary_handle == NULL);
499 }
500 
TEST_F(DelayEstimatorTest,MeanEstimatorFix)501 TEST_F(DelayEstimatorTest, MeanEstimatorFix) {
502   // In this test we verify that we update the mean value in correct direction
503   // only. With "direction" we mean increase or decrease.
504 
505   int32_t mean_value = 4000;
506   int32_t mean_value_before = mean_value;
507   int32_t new_mean_value = mean_value * 2;
508 
509   // Increasing |mean_value|.
510   WebRtc_MeanEstimatorFix(new_mean_value, 10, &mean_value);
511   EXPECT_LT(mean_value_before, mean_value);
512   EXPECT_GT(new_mean_value, mean_value);
513 
514   // Decreasing |mean_value|.
515   new_mean_value = mean_value / 2;
516   mean_value_before = mean_value;
517   WebRtc_MeanEstimatorFix(new_mean_value, 10, &mean_value);
518   EXPECT_GT(mean_value_before, mean_value);
519   EXPECT_LT(new_mean_value, mean_value);
520 }
521 
TEST_F(DelayEstimatorTest,ExactDelayEstimateMultipleNearSameSpectrum)522 TEST_F(DelayEstimatorTest, ExactDelayEstimateMultipleNearSameSpectrum) {
523   // In this test we verify that we get the correct delay estimates if we shift
524   // the signal accordingly. We create two Binary Delay Estimators and feed them
525   // with the same signals, so they should output the same results.
526   // We verify both causal and non-causal delays.
527   // For these noise free signals, the robust validation should not have an
528   // impact, hence we turn robust validation on/off for both reference and
529   // delayed near end.
530 
531   for (size_t i = 0; i < kSizeEnable; ++i) {
532     for (size_t j = 0; j < kSizeEnable; ++j) {
533       RunBinarySpectraTest(0, 0, kEnable[i], kEnable[j]);
534     }
535   }
536 }
537 
TEST_F(DelayEstimatorTest,ExactDelayEstimateMultipleNearDifferentSpectrum)538 TEST_F(DelayEstimatorTest, ExactDelayEstimateMultipleNearDifferentSpectrum) {
539   // In this test we use the same setup as above, but we now feed the two Binary
540   // Delay Estimators with different signals, so they should output different
541   // results.
542   // For these noise free signals, the robust validation should not have an
543   // impact, hence we turn robust validation on/off for both reference and
544   // delayed near end.
545 
546   const int kNearOffset = 1;
547   for (size_t i = 0; i < kSizeEnable; ++i) {
548     for (size_t j = 0; j < kSizeEnable; ++j) {
549       RunBinarySpectraTest(kNearOffset, 0, kEnable[i], kEnable[j]);
550     }
551   }
552 }
553 
TEST_F(DelayEstimatorTest,ExactDelayEstimateMultipleNearDifferentLookahead)554 TEST_F(DelayEstimatorTest, ExactDelayEstimateMultipleNearDifferentLookahead) {
555   // In this test we use the same setup as above, feeding the two Binary
556   // Delay Estimators with the same signals. The difference is that we create
557   // them with different lookahead.
558   // For these noise free signals, the robust validation should not have an
559   // impact, hence we turn robust validation on/off for both reference and
560   // delayed near end.
561 
562   const int kLookaheadOffset = 1;
563   for (size_t i = 0; i < kSizeEnable; ++i) {
564     for (size_t j = 0; j < kSizeEnable; ++j) {
565       RunBinarySpectraTest(0, kLookaheadOffset, kEnable[i], kEnable[j]);
566     }
567   }
568 }
569 
TEST_F(DelayEstimatorTest,AllowedOffsetNoImpactWhenRobustValidationDisabled)570 TEST_F(DelayEstimatorTest, AllowedOffsetNoImpactWhenRobustValidationDisabled) {
571   // The same setup as in ExactDelayEstimateMultipleNearSameSpectrum with the
572   // difference that |allowed_offset| is set for the reference binary delay
573   // estimator.
574 
575   binary_->allowed_offset = 10;
576   RunBinarySpectraTest(0, 0, 0, 0);
577   binary_->allowed_offset = 0;  // Reset reference.
578 }
579 
TEST_F(DelayEstimatorTest,VerifyLookaheadAtCreate)580 TEST_F(DelayEstimatorTest, VerifyLookaheadAtCreate) {
581   void* farend_handle =
582       WebRtc_CreateDelayEstimatorFarend(kSpectrumSize, kMaxDelay);
583   ASSERT_TRUE(farend_handle != NULL);
584   void* handle = WebRtc_CreateDelayEstimator(farend_handle, kLookahead);
585   ASSERT_TRUE(handle != NULL);
586   EXPECT_EQ(kLookahead, WebRtc_lookahead(handle));
587   WebRtc_FreeDelayEstimator(handle);
588   WebRtc_FreeDelayEstimatorFarend(farend_handle);
589 }
590 
TEST_F(DelayEstimatorTest,VerifyLookaheadIsSetAndKeptAfterInit)591 TEST_F(DelayEstimatorTest, VerifyLookaheadIsSetAndKeptAfterInit) {
592   EXPECT_EQ(kLookahead, WebRtc_lookahead(handle_));
593   EXPECT_EQ(kDifferentLookahead,
594             WebRtc_set_lookahead(handle_, kDifferentLookahead));
595   EXPECT_EQ(kDifferentLookahead, WebRtc_lookahead(handle_));
596   EXPECT_EQ(0, WebRtc_InitDelayEstimatorFarend(farend_handle_));
597   EXPECT_EQ(kDifferentLookahead, WebRtc_lookahead(handle_));
598   EXPECT_EQ(0, WebRtc_InitDelayEstimator(handle_));
599   EXPECT_EQ(kDifferentLookahead, WebRtc_lookahead(handle_));
600 }
601 
TEST_F(DelayEstimatorTest,VerifyHistorySizeAtCreate)602 TEST_F(DelayEstimatorTest, VerifyHistorySizeAtCreate) {
603   EXPECT_EQ(kHistorySize, WebRtc_history_size(handle_));
604 }
605 
TEST_F(DelayEstimatorTest,VerifyHistorySizeIsSetAndKeptAfterInit)606 TEST_F(DelayEstimatorTest, VerifyHistorySizeIsSetAndKeptAfterInit) {
607   EXPECT_EQ(kHistorySize, WebRtc_history_size(handle_));
608   EXPECT_EQ(kDifferentHistorySize,
609             WebRtc_set_history_size(handle_, kDifferentHistorySize));
610   EXPECT_EQ(kDifferentHistorySize, WebRtc_history_size(handle_));
611   EXPECT_EQ(0, WebRtc_InitDelayEstimator(handle_));
612   EXPECT_EQ(kDifferentHistorySize, WebRtc_history_size(handle_));
613   EXPECT_EQ(0, WebRtc_InitDelayEstimatorFarend(farend_handle_));
614   EXPECT_EQ(kDifferentHistorySize, WebRtc_history_size(handle_));
615 }
616 
617 // TODO(bjornv): Add tests for SoftReset...(...).
618 
619 }  // namespace
620 
621 }  // namespace webrtc
622