19a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org/*
29a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org *  Copyright (c) 2013 The WebRTC project authors. All Rights Reserved.
39a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org *
49a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org *  Use of this source code is governed by a BSD-style license
59a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org *  that can be found in the LICENSE file in the root of the source
69a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org *  tree. An additional intellectual property rights grant can be found
79a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org *  in the file PATENTS.  All contributing project authors may
89a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org *  be found in the AUTHORS file in the root of the source tree.
99a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org */
109a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
119a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org// Test to verify correct operation for externally created decoders.
129a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
139a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org#include <string>
149a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org#include <list>
159a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
169a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org#include "gmock/gmock.h"
179a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org#include "gtest/gtest.h"
18e5abc854f3dc47de16067c2a41476c39b7626722henrik.lundin@webrtc.org#include "webrtc/modules/audio_coding/neteq/interface/neteq.h"
19e5abc854f3dc47de16067c2a41476c39b7626722henrik.lundin@webrtc.org#include "webrtc/modules/audio_coding/neteq/mock/mock_external_decoder_pcm16b.h"
20e5abc854f3dc47de16067c2a41476c39b7626722henrik.lundin@webrtc.org#include "webrtc/modules/audio_coding/neteq/tools/input_audio_file.h"
21e5abc854f3dc47de16067c2a41476c39b7626722henrik.lundin@webrtc.org#include "webrtc/modules/audio_coding/neteq/tools/rtp_generator.h"
229a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org#include "webrtc/system_wrappers/interface/scoped_ptr.h"
239a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org#include "webrtc/test/testsupport/fileutils.h"
247537dde7698d151f5c50b5f160e4ed28347b0c90henrike@webrtc.org#include "webrtc/test/testsupport/gtest_disable.h"
259a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
269a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.orgnamespace webrtc {
279a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
289a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.orgusing ::testing::_;
299a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
309a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org// This test encodes a few packets of PCM16b 32 kHz data and inserts it into two
319a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org// different NetEq instances. The first instance uses the internal version of
329a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org// the decoder object, while the second one uses an externally created decoder
339a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org// object (ExternalPcm16B wrapped in MockExternalPcm16B, both defined above).
349a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org// The test verifies that the output from both instances match.
359a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.orgclass NetEqExternalDecoderTest : public ::testing::Test {
369a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org protected:
379a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  static const int kTimeStepMs = 10;
389a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  static const int kMaxBlockSize = 480;  // 10 ms @ 48 kHz.
399a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  static const uint8_t kPayloadType = 95;
409a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  static const int kSampleRateHz = 32000;
419a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
429a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  NetEqExternalDecoderTest()
439a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      : sample_rate_hz_(kSampleRateHz),
449a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        samples_per_ms_(sample_rate_hz_ / 1000),
459a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        frame_size_ms_(10),
469a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        frame_size_samples_(frame_size_ms_ * samples_per_ms_),
479a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        output_size_samples_(frame_size_ms_ * samples_per_ms_),
489a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        external_decoder_(new MockExternalPcm16B(kDecoderPCM16Bswb32kHz)),
499a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        rtp_generator_(samples_per_ms_),
509a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        payload_size_bytes_(0),
519a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        last_send_time_(0),
529a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        last_arrival_time_(0) {
534087215f83d5a77b86fde9ebf8598dfe7ecd70a1henrik.lundin@webrtc.org    NetEq::Config config;
544087215f83d5a77b86fde9ebf8598dfe7ecd70a1henrik.lundin@webrtc.org    config.sample_rate_hz = sample_rate_hz_;
554087215f83d5a77b86fde9ebf8598dfe7ecd70a1henrik.lundin@webrtc.org    neteq_external_ = NetEq::Create(config);
564087215f83d5a77b86fde9ebf8598dfe7ecd70a1henrik.lundin@webrtc.org    neteq_ = NetEq::Create(config);
579a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    input_ = new int16_t[frame_size_samples_];
589a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    encoded_ = new uint8_t[2 * frame_size_samples_];
599a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  }
609a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
619a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  ~NetEqExternalDecoderTest() {
629a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    delete neteq_external_;
639a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    delete neteq_;
649a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    // We will now delete the decoder ourselves, so expecting Die to be called.
659a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    EXPECT_CALL(*external_decoder_, Die()).Times(1);
669a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    delete external_decoder_;
679a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    delete [] input_;
689a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    delete [] encoded_;
699a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  }
709a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
719a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  virtual void SetUp() {
729a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    const std::string file_name =
739a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        webrtc::test::ResourcePath("audio_coding/testfile32kHz", "pcm");
749a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    input_file_.reset(new test::InputAudioFile(file_name));
759a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    assert(sample_rate_hz_ == 32000);
769a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    NetEqDecoder decoder = kDecoderPCM16Bswb32kHz;
779a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    EXPECT_CALL(*external_decoder_, Init());
789a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    // NetEq is not allowed to delete the external decoder (hence Times(0)).
799a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    EXPECT_CALL(*external_decoder_, Die()).Times(0);
809a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    ASSERT_EQ(NetEq::kOK,
819a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org              neteq_external_->RegisterExternalDecoder(external_decoder_,
829a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                                                       decoder,
839a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                                                       kPayloadType));
849a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    ASSERT_EQ(NetEq::kOK,
859a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org              neteq_->RegisterPayloadType(decoder, kPayloadType));
869a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  }
879a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
889a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  virtual void TearDown() {}
899a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
909a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  int GetNewPackets() {
919a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    if (!input_file_->Read(frame_size_samples_, input_)) {
929a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      return -1;
939a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    }
949a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    payload_size_bytes_ = WebRtcPcm16b_Encode(input_, frame_size_samples_,
959a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                                             encoded_);
969a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    if (frame_size_samples_ * 2 != payload_size_bytes_) {
979a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      return -1;
989a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    }
999a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    int next_send_time = rtp_generator_.GetRtpHeader(kPayloadType,
1009a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                                                     frame_size_samples_,
1019a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                                                     &rtp_header_);
1029a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    return next_send_time;
1039a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  }
1049a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
1059a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  void VerifyOutput(size_t num_samples) {
1069a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    for (size_t i = 0; i < num_samples; ++i) {
1079a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      ASSERT_EQ(output_[i], output_external_[i]) <<
1089a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org          "Diff in sample " << i << ".";
1099a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    }
1109a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  }
1119a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
1129a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  virtual int GetArrivalTime(int send_time) {
1139a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    int arrival_time = last_arrival_time_ + (send_time - last_send_time_);
1149a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    last_send_time_ = send_time;
1159a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    last_arrival_time_ = arrival_time;
1169a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    return arrival_time;
1179a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  }
1189a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
1199a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  virtual bool Lost() { return false; }
1209a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
1219a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  void RunTest(int num_loops) {
1229a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    // Get next input packets (mono and multi-channel).
1239a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    int next_send_time;
1249a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    int next_arrival_time;
1259a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    do {
1269a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      next_send_time = GetNewPackets();
1279a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      ASSERT_NE(-1, next_send_time);
1289a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      next_arrival_time = GetArrivalTime(next_send_time);
1299a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    } while (Lost());  // If lost, immediately read the next packet.
1309a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
1319a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    EXPECT_CALL(*external_decoder_, Decode(_, payload_size_bytes_, _, _))
1329a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        .Times(num_loops);
1339a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
1349a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    int time_now = 0;
1359a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    for (int k = 0; k < num_loops; ++k) {
1369a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      while (time_now >= next_arrival_time) {
1379a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        // Insert packet in regular instance.
1389a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        ASSERT_EQ(NetEq::kOK,
1399a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                  neteq_->InsertPacket(rtp_header_, encoded_,
1409a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                                       payload_size_bytes_,
1419a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                                       next_arrival_time));
1429a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        // Insert packet in external decoder instance.
1439a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        EXPECT_CALL(*external_decoder_,
1449a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                    IncomingPacket(_, payload_size_bytes_,
1459a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                                   rtp_header_.header.sequenceNumber,
1469a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                                   rtp_header_.header.timestamp,
1479a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                                   next_arrival_time));
1489a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        ASSERT_EQ(NetEq::kOK,
1499a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                  neteq_external_->InsertPacket(rtp_header_, encoded_,
1509a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                                                payload_size_bytes_,
1519a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                                                next_arrival_time));
1529a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        // Get next input packet.
1539a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        do {
1549a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org          next_send_time = GetNewPackets();
1559a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org          ASSERT_NE(-1, next_send_time);
1569a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org          next_arrival_time = GetArrivalTime(next_send_time);
1579a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org        } while (Lost());  // If lost, immediately read the next packet.
1589a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      }
1599a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      NetEqOutputType output_type;
1609a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      // Get audio from regular instance.
1619a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      int samples_per_channel;
1629a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      int num_channels;
1639a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      EXPECT_EQ(NetEq::kOK,
1649a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                neteq_->GetAudio(kMaxBlockSize, output_,
1659a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                                 &samples_per_channel, &num_channels,
1669a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                                 &output_type));
1679a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      EXPECT_EQ(1, num_channels);
1689a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      EXPECT_EQ(output_size_samples_, samples_per_channel);
1699a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      // Get audio from external decoder instance.
1709a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      ASSERT_EQ(NetEq::kOK,
1719a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                neteq_external_->GetAudio(kMaxBlockSize, output_external_,
1729a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                                          &samples_per_channel, &num_channels,
1739a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org                                          &output_type));
1749a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      EXPECT_EQ(1, num_channels);
1759a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      EXPECT_EQ(output_size_samples_, samples_per_channel);
1769a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      std::ostringstream ss;
1779a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      ss << "Lap number " << k << ".";
1789a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      SCOPED_TRACE(ss.str());  // Print out the parameter values on failure.
1799a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      // Compare mono and multi-channel.
1809a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      ASSERT_NO_FATAL_FAILURE(VerifyOutput(output_size_samples_));
1819a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
1829a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org      time_now += kTimeStepMs;
1839a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org    }
1849a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  }
1859a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
1869a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  const int sample_rate_hz_;
1879a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  const int samples_per_ms_;
1889a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  const int frame_size_ms_;
1899a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  const int frame_size_samples_;
1909a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  const int output_size_samples_;
1919a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  NetEq* neteq_external_;
1929a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  NetEq* neteq_;
1939a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  MockExternalPcm16B* external_decoder_;
1949a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  test::RtpGenerator rtp_generator_;
1959a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  int16_t* input_;
1969a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  uint8_t* encoded_;
1979a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  int16_t output_[kMaxBlockSize];
1989a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  int16_t output_external_[kMaxBlockSize];
1999a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  WebRtcRTPHeader rtp_header_;
2009a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  int payload_size_bytes_;
2019a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  int last_send_time_;
2029a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  int last_arrival_time_;
2039a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  scoped_ptr<test::InputAudioFile> input_file_;
2049a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org};
2059a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
20654c9b21d0c8e401c9351c1f03296fadc659825e6henrik.lundin@webrtc.orgTEST_F(NetEqExternalDecoderTest, RunTest) {
2079a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org  RunTest(100);  // Run 100 laps @ 10 ms each in the test loop.
2089a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org}
2099a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org
2109a400812ca0006d12e538d465ab6728a8ecd07aahenrik.lundin@webrtc.org}  // namespace webrtc
211