audio_renderer_mixer_unittest.cc revision 7d4cd473f85ac64c3747c96c277f9e506a0d2246
1b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato// Copyright (c) 2012 The Chromium Authors. All rights reserved.
2b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato// Use of this source code is governed by a BSD-style license that can be
3b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato// found in the LICENSE file.
4b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
5b9cc48a43ed984587c939d02fba5316bf5c0df6eYing Wang// MSVC++ requires this to be set before any other includes to get M_PI.
6b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato#define _USE_MATH_DEFINES
7b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato#include <cmath>
8b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
9b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato#include "base/bind.h"
10b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato#include "base/bind_helpers.h"
11b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato#include "base/memory/scoped_ptr.h"
12b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato#include "base/memory/scoped_vector.h"
13b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato#include "base/synchronization/waitable_event.h"
14b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato#include "base/threading/platform_thread.h"
15b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato#include "media/base/audio_renderer_mixer.h"
16b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato#include "media/base/audio_renderer_mixer_input.h"
17b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato#include "media/base/fake_audio_render_callback.h"
18b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato#include "media/base/mock_audio_renderer_sink.h"
19b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato#include "testing/gmock/include/gmock/gmock.h"
20b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato#include "testing/gtest/include/gtest/gtest.h"
21b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
22b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onoratonamespace media {
23b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
24b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato// Parameters which control the many input case tests.
25b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onoratostatic const int kMixerInputs = 8;
26b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onoratostatic const int kMixerCycles = 3;
27b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
28b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato// Parameters used for testing.
29b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onoratostatic const int kBitsPerChannel = 32;
30b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onoratostatic const ChannelLayout kChannelLayout = CHANNEL_LAYOUT_STEREO;
31b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onoratostatic const int kHighLatencyBufferSize = 8192;
32b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onoratostatic const int kLowLatencyBufferSize = 256;
33b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onoratostatic const int kSampleRate = 48000;
34b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
35b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato// Number of full sine wave cycles for each Render() call.
36b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onoratostatic const int kSineCycles = 4;
37b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
38b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato// Tuple of <input sampling rate, output sampling rate, epsilon>.
39b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onoratotypedef std::tr1::tuple<int, int, double> AudioRendererMixerTestData;
40b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onoratoclass AudioRendererMixerTest
41b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    : public testing::TestWithParam<AudioRendererMixerTestData> {
42b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato public:
43b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  AudioRendererMixerTest()
44b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      : epsilon_(std::tr1::get<2>(GetParam())),
45b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato        half_fill_(false) {
46b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    // Create input and output parameters based on test parameters.
47b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    input_parameters_ = AudioParameters(
48b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato        AudioParameters::AUDIO_PCM_LINEAR, kChannelLayout,
49b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato        std::tr1::get<0>(GetParam()), kBitsPerChannel, kHighLatencyBufferSize);
50b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    output_parameters_ = AudioParameters(
51b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato        AudioParameters::AUDIO_PCM_LOW_LATENCY, kChannelLayout,
52b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato        std::tr1::get<1>(GetParam()), 16, kLowLatencyBufferSize);
53b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
54b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    sink_ = new MockAudioRendererSink();
55b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    EXPECT_CALL(*sink_.get(), Start());
56b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    EXPECT_CALL(*sink_.get(), Stop());
57b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
58b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    mixer_.reset(new AudioRendererMixer(
59b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato        input_parameters_, output_parameters_, sink_));
60b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    mixer_callback_ = sink_->callback();
61b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
62b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    audio_bus_ = AudioBus::Create(output_parameters_);
63b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    expected_audio_bus_ = AudioBus::Create(output_parameters_);
64b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
65b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    // Allocate one callback for generating expected results.
66b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    double step = kSineCycles / static_cast<double>(
67b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato        output_parameters_.frames_per_buffer());
68b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    expected_callback_.reset(new FakeAudioRenderCallback(step));
69b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  }
70b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
71b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  AudioRendererMixer* GetMixer(const AudioParameters& params) {
72b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    return mixer_.get();
73b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  }
74b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
75b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  MOCK_METHOD1(RemoveMixer, void(const AudioParameters&));
76b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
77b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  void InitializeInputs(int count) {
78b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    mixer_inputs_.reserve(count);
79b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    fake_callbacks_.reserve(count);
80b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
81b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    // Setup FakeAudioRenderCallback step to compensate for resampling.
82b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    double scale_factor = input_parameters_.sample_rate() /
83b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato        static_cast<double>(output_parameters_.sample_rate());
84b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    double step = kSineCycles / (scale_factor *
85b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato        static_cast<double>(output_parameters_.frames_per_buffer()));
86b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
87b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    for (int i = 0; i < count; ++i) {
88b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      fake_callbacks_.push_back(new FakeAudioRenderCallback(step));
89b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      mixer_inputs_.push_back(new AudioRendererMixerInput(
90b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato          base::Bind(&AudioRendererMixerTest::GetMixer,
91b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato                     base::Unretained(this)),
92b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato          base::Bind(&AudioRendererMixerTest::RemoveMixer,
93b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato                     base::Unretained(this))));
94b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      mixer_inputs_[i]->Initialize(input_parameters_, fake_callbacks_[i]);
95b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      mixer_inputs_[i]->SetVolume(1.0f);
96b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    }
97b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    EXPECT_CALL(*this, RemoveMixer(testing::_)).Times(count);
98b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  }
99b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
100b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  bool ValidateAudioData(int index, int frames, float scale, double epsilon) {
101b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    for (int i = 0; i < audio_bus_->channels(); ++i) {
102b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      for (int j = index; j < frames; j++) {
103b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato        double error = fabs(audio_bus_->channel(i)[j] -
104b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato            expected_audio_bus_->channel(i)[j] * scale);
105b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato        if (error > epsilon) {
106b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato          EXPECT_NEAR(expected_audio_bus_->channel(i)[j] * scale,
107b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato                      audio_bus_->channel(i)[j], epsilon)
108b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato              << " i=" << i << ", j=" << j;
109b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato          return false;
110b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato        }
111b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      }
112b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    }
113b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    return true;
114b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  }
115b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
116b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  bool ValidateAudioData(int index, int frames, float scale) {
117b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    return ValidateAudioData(index, frames, scale, epsilon_);
118b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  }
119b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
120b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  bool RenderAndValidateAudioData(float scale) {
121b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    if (half_fill_) {
122b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      for (size_t i = 0; i < fake_callbacks_.size(); ++i)
123b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato        fake_callbacks_[i]->set_half_fill(true);
124b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      expected_callback_->set_half_fill(true);
125b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      // Initialize the AudioBus completely or we'll run into Valgrind problems
126b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      // during the verification step below.
127b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      expected_audio_bus_->Zero();
128b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    }
129b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
130b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    // Render actual audio data.
131b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    int frames = mixer_callback_->Render(audio_bus_.get(), 0);
132b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    if (frames != audio_bus_->frames())
133b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      return false;
134b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
135b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    // Render expected audio data (without scaling).
136b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    expected_callback_->Render(expected_audio_bus_.get(), 0);
137b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
138b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    if (half_fill_) {
139b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      // In this case, just verify that every frame was initialized, this will
140b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      // only fail under tooling such as valgrind.
141b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      return ValidateAudioData(
142b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato          0, frames, 0, std::numeric_limits<double>::max());
143b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    } else {
144b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      return ValidateAudioData(0, frames, scale);
145b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    }
146b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  }
147b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
148b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  // Fill |audio_bus_| fully with |value|.
149b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  void FillAudioData(float value) {
150b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    for (int i = 0; i < audio_bus_->channels(); ++i) {
151b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      std::fill(audio_bus_->channel(i),
152b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato                audio_bus_->channel(i) + audio_bus_->frames(), value);
153b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    }
154b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  }
155b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
156b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  // Verify silence when mixer inputs are in pre-Start() and post-Start().
157b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  void StartTest(int inputs) {
158b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    InitializeInputs(inputs);
159b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
160b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    // Verify silence before any inputs have been started.  Fill the buffer
161b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    // before hand with non-zero data to ensure we get zeros back.
162b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    FillAudioData(1.0f);
163b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    EXPECT_TRUE(RenderAndValidateAudioData(0.0f));
164b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
165b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    // Start() all even numbered mixer inputs and ensure we still get silence.
166b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    for (size_t i = 0; i < mixer_inputs_.size(); i += 2)
167b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      mixer_inputs_[i]->Start();
168b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    FillAudioData(1.0f);
169b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    EXPECT_TRUE(RenderAndValidateAudioData(0.0f));
170b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
171b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    // Start() all mixer inputs and ensure we still get silence.
172b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    for (size_t i = 1; i < mixer_inputs_.size(); i += 2)
173b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      mixer_inputs_[i]->Start();
174b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    FillAudioData(1.0f);
175b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    EXPECT_TRUE(RenderAndValidateAudioData(0.0f));
176b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
177b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    for (size_t i = 0; i < mixer_inputs_.size(); ++i)
178b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      mixer_inputs_[i]->Stop();
179b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  }
180b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
181b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  // Verify output when mixer inputs are in post-Play() state.
182b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  void PlayTest(int inputs) {
183b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    InitializeInputs(inputs);
184b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
185b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    // Play() all mixer inputs and ensure we get the right values.
186b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    for (size_t i = 0; i < mixer_inputs_.size(); ++i) {
187b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      mixer_inputs_[i]->Start();
188b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      mixer_inputs_[i]->Play();
189b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    }
190b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
191b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    for (int i = 0; i < kMixerCycles; ++i)
192b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      ASSERT_TRUE(RenderAndValidateAudioData(mixer_inputs_.size()));
193b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
194b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    for (size_t i = 0; i < mixer_inputs_.size(); ++i)
195b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      mixer_inputs_[i]->Stop();
196b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  }
197b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
198b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  // Verify volume adjusted output when mixer inputs are in post-Play() state.
199b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato  void PlayVolumeAdjustedTest(int inputs) {
200b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    InitializeInputs(inputs);
201b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
202b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    for (size_t i = 0; i < mixer_inputs_.size(); ++i) {
203b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      mixer_inputs_[i]->Start();
204b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      mixer_inputs_[i]->Play();
205b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    }
206b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
207b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    // Set a different volume for each mixer input and verify the results.
208b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    float total_scale = 0;
209b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    for (size_t i = 0; i < mixer_inputs_.size(); ++i) {
210b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      float volume = static_cast<float>(i) / mixer_inputs_.size();
211b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      total_scale += volume;
212b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      EXPECT_TRUE(mixer_inputs_[i]->SetVolume(volume));
213b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    }
214b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato    for (int i = 0; i < kMixerCycles; ++i)
215b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato      ASSERT_TRUE(RenderAndValidateAudioData(total_scale));
216b72c5c2e5482cf10117b2b25f642f7616b2326c3Joe Onorato
217    for (size_t i = 0; i < mixer_inputs_.size(); ++i)
218      mixer_inputs_[i]->Stop();
219  }
220
221  // Verify output when mixer inputs can only partially fulfill a Render().
222  void PlayPartialRenderTest(int inputs) {
223    InitializeInputs(inputs);
224
225    for (size_t i = 0; i < mixer_inputs_.size(); ++i) {
226      mixer_inputs_[i]->Start();
227      mixer_inputs_[i]->Play();
228    }
229
230    // Verify a properly filled buffer when half filled (remainder zeroed).
231    half_fill_ = true;
232    ASSERT_TRUE(RenderAndValidateAudioData(mixer_inputs_.size()));
233
234    for (size_t i = 0; i < mixer_inputs_.size(); ++i)
235      mixer_inputs_[i]->Stop();
236  }
237
238  // Verify output when mixer inputs are in Pause() state.
239  void PauseTest(int inputs) {
240    InitializeInputs(inputs);
241
242    for (size_t i = 0; i < mixer_inputs_.size(); ++i) {
243      mixer_inputs_[i]->Start();
244      mixer_inputs_[i]->Play();
245    }
246
247    // Pause() all even numbered mixer inputs and ensure we get the right value.
248    for (size_t i = 0; i < mixer_inputs_.size(); i += 2)
249      mixer_inputs_[i]->Pause();
250    for (int i = 0; i < kMixerCycles; ++i)
251      ASSERT_TRUE(RenderAndValidateAudioData(mixer_inputs_.size() / 2));
252
253    for (size_t i = 0; i < mixer_inputs_.size(); ++i)
254      mixer_inputs_[i]->Stop();
255  }
256
257  // Verify output when mixer inputs are in post-Stop() state.
258  void StopTest(int inputs) {
259    InitializeInputs(inputs);
260
261    // Start() and Stop() all inputs.
262    for (size_t i = 0; i < mixer_inputs_.size(); ++i) {
263      mixer_inputs_[i]->Start();
264      mixer_inputs_[i]->Stop();
265    }
266
267    // Verify we get silence back; fill |audio_bus_| before hand to be sure.
268    FillAudioData(1.0f);
269    EXPECT_TRUE(RenderAndValidateAudioData(0.0f));
270  }
271
272 protected:
273  virtual ~AudioRendererMixerTest() {}
274
275  scoped_refptr<MockAudioRendererSink> sink_;
276  scoped_ptr<AudioRendererMixer> mixer_;
277  AudioRendererSink::RenderCallback* mixer_callback_;
278  AudioParameters input_parameters_;
279  AudioParameters output_parameters_;
280  scoped_ptr<AudioBus> audio_bus_;
281  scoped_ptr<AudioBus> expected_audio_bus_;
282  std::vector< scoped_refptr<AudioRendererMixerInput> > mixer_inputs_;
283  ScopedVector<FakeAudioRenderCallback> fake_callbacks_;
284  scoped_ptr<FakeAudioRenderCallback> expected_callback_;
285  double epsilon_;
286  bool half_fill_;
287
288  DISALLOW_COPY_AND_ASSIGN(AudioRendererMixerTest);
289};
290
291class AudioRendererMixerBehavioralTest : public AudioRendererMixerTest {};
292
293ACTION_P(SignalEvent, event) {
294  event->Signal();
295}
296
297// Verify a mixer with no inputs returns silence for all requested frames.
298TEST_P(AudioRendererMixerTest, NoInputs) {
299  FillAudioData(1.0f);
300  EXPECT_TRUE(RenderAndValidateAudioData(0.0f));
301}
302
303// Test mixer output with one input in the pre-Start() and post-Start() state.
304TEST_P(AudioRendererMixerTest, OneInputStart) {
305  StartTest(1);
306}
307
308// Test mixer output with many inputs in the pre-Start() and post-Start() state.
309TEST_P(AudioRendererMixerTest, ManyInputStart) {
310  StartTest(kMixerInputs);
311}
312
313// Test mixer output with one input in the post-Play() state.
314TEST_P(AudioRendererMixerTest, OneInputPlay) {
315  PlayTest(1);
316}
317
318// Test mixer output with many inputs in the post-Play() state.
319TEST_P(AudioRendererMixerTest, ManyInputPlay) {
320  PlayTest(kMixerInputs);
321}
322
323// Test volume adjusted mixer output with one input in the post-Play() state.
324TEST_P(AudioRendererMixerTest, OneInputPlayVolumeAdjusted) {
325  PlayVolumeAdjustedTest(1);
326}
327
328// Test volume adjusted mixer output with many inputs in the post-Play() state.
329TEST_P(AudioRendererMixerTest, ManyInputPlayVolumeAdjusted) {
330  PlayVolumeAdjustedTest(kMixerInputs);
331}
332
333// Test mixer output with one input and partial Render() in post-Play() state.
334TEST_P(AudioRendererMixerTest, OneInputPlayPartialRender) {
335  PlayPartialRenderTest(1);
336}
337
338// Test mixer output with many inputs and partial Render() in post-Play() state.
339TEST_P(AudioRendererMixerTest, ManyInputPlayPartialRender) {
340  PlayPartialRenderTest(kMixerInputs);
341}
342
343// Test mixer output with one input in the post-Pause() state.
344TEST_P(AudioRendererMixerTest, OneInputPause) {
345  PauseTest(1);
346}
347
348// Test mixer output with many inputs in the post-Pause() state.
349TEST_P(AudioRendererMixerTest, ManyInputPause) {
350  PauseTest(kMixerInputs);
351}
352
353// Test mixer output with one input in the post-Stop() state.
354TEST_P(AudioRendererMixerTest, OneInputStop) {
355  StopTest(1);
356}
357
358// Test mixer output with many inputs in the post-Stop() state.
359TEST_P(AudioRendererMixerTest, ManyInputStop) {
360  StopTest(kMixerInputs);
361}
362
363// Test mixer with many inputs in mixed post-Stop() and post-Play() states.
364TEST_P(AudioRendererMixerTest, ManyInputMixedStopPlay) {
365  InitializeInputs(kMixerInputs);
366
367  // Start() all inputs.
368  for (size_t i = 0; i < mixer_inputs_.size(); ++i)
369    mixer_inputs_[i]->Start();
370
371  // Stop() all even numbered mixer inputs and Play() all odd numbered inputs
372  // and ensure we get the right value.
373  for (size_t i = 1; i < mixer_inputs_.size(); i += 2) {
374    mixer_inputs_[i - 1]->Stop();
375    mixer_inputs_[i]->Play();
376  }
377  ASSERT_TRUE(RenderAndValidateAudioData(std::max(
378      mixer_inputs_.size() / 2, static_cast<size_t>(1))));
379
380  for (size_t i = 1; i < mixer_inputs_.size(); i += 2)
381    mixer_inputs_[i]->Stop();
382}
383
384TEST_P(AudioRendererMixerBehavioralTest, OnRenderError) {
385  InitializeInputs(kMixerInputs);
386  for (size_t i = 0; i < mixer_inputs_.size(); ++i) {
387    mixer_inputs_[i]->Start();
388    mixer_inputs_[i]->Play();
389    EXPECT_CALL(*fake_callbacks_[i], OnRenderError()).Times(1);
390  }
391
392  mixer_callback_->OnRenderError();
393  for (size_t i = 0; i < mixer_inputs_.size(); ++i)
394    mixer_inputs_[i]->Stop();
395}
396
397// Ensure constructing an AudioRendererMixerInput, but not initializing it does
398// not call RemoveMixer().
399TEST_P(AudioRendererMixerBehavioralTest, NoInitialize) {
400  EXPECT_CALL(*this, RemoveMixer(testing::_)).Times(0);
401  scoped_refptr<AudioRendererMixerInput> audio_renderer_mixer =
402      new AudioRendererMixerInput(
403          base::Bind(&AudioRendererMixerTest::GetMixer,
404                     base::Unretained(this)),
405          base::Bind(&AudioRendererMixerTest::RemoveMixer,
406                     base::Unretained(this)));
407}
408
409// Ensure the physical stream is paused after a certain amount of time with no
410// inputs playing.  The test will hang if the behavior is incorrect.
411TEST_P(AudioRendererMixerBehavioralTest, MixerPausesStream) {
412  const base::TimeDelta kPauseTime = base::TimeDelta::FromMilliseconds(500);
413  // This value can't be too low or valgrind, tsan will timeout on the bots.
414  const base::TimeDelta kTestTimeout = 10 * kPauseTime;
415  mixer_->set_pause_delay_for_testing(kPauseTime);
416
417  base::WaitableEvent pause_event(true, false);
418  EXPECT_CALL(*sink_.get(), Pause()).Times(2)
419      .WillRepeatedly(SignalEvent(&pause_event));
420  InitializeInputs(1);
421
422  // Ensure never playing the input results in a sink pause.
423  const base::TimeDelta kSleepTime = base::TimeDelta::FromMilliseconds(100);
424  base::TimeTicks start_time = base::TimeTicks::Now();
425  while (!pause_event.IsSignaled()) {
426    mixer_callback_->Render(audio_bus_.get(), 0);
427    base::PlatformThread::Sleep(kSleepTime);
428    ASSERT_TRUE(base::TimeTicks::Now() - start_time < kTestTimeout);
429  }
430  pause_event.Reset();
431
432  // Playing the input for the first time should cause a sink play.
433  mixer_inputs_[0]->Start();
434  EXPECT_CALL(*sink_.get(), Play());
435  mixer_inputs_[0]->Play();
436  mixer_inputs_[0]->Pause();
437
438  // Ensure once the input is paused the sink eventually pauses.
439  start_time = base::TimeTicks::Now();
440  while (!pause_event.IsSignaled()) {
441    mixer_callback_->Render(audio_bus_.get(), 0);
442    base::PlatformThread::Sleep(kSleepTime);
443    ASSERT_TRUE(base::TimeTicks::Now() - start_time < kTestTimeout);
444  }
445
446  mixer_inputs_[0]->Stop();
447}
448
449INSTANTIATE_TEST_CASE_P(
450    AudioRendererMixerTest, AudioRendererMixerTest, testing::Values(
451        // No resampling.
452        std::tr1::make_tuple(44100, 44100, 0.00000048),
453
454        // Upsampling.
455        std::tr1::make_tuple(44100, 48000, 0.033),
456
457        // Downsampling.
458        std::tr1::make_tuple(48000, 41000, 0.042)));
459
460// Test cases for behavior which is independent of parameters.  Values() doesn't
461// support single item lists and we don't want these test cases to run for every
462// parameter set.
463INSTANTIATE_TEST_CASE_P(
464    AudioRendererMixerBehavioralTest, AudioRendererMixerBehavioralTest,
465    testing::ValuesIn(std::vector<AudioRendererMixerTestData>(
466        1, std::tr1::make_tuple(44100, 44100, 0))));
467
468}  // namespace media
469