| Index: media/filters/audio_renderer_base_unittest.cc
|
| diff --git a/media/filters/audio_renderer_base_unittest.cc b/media/filters/audio_renderer_base_unittest.cc
|
| index 76b1915c5fd4233e0fd50c26197c6e2535b0f76b..5682d37508e103384d7d542a0b3dda9a9f2392d3 100644
|
| --- a/media/filters/audio_renderer_base_unittest.cc
|
| +++ b/media/filters/audio_renderer_base_unittest.cc
|
| @@ -42,6 +42,8 @@ class MockAudioRendererBase : public AudioRendererBase {
|
| private:
|
| FRIEND_TEST(AudioRendererBaseTest, OneCompleteReadCycle);
|
| FRIEND_TEST(AudioRendererBaseTest, Underflow);
|
| + FRIEND_TEST(AudioRendererBaseTest, Underflow_EndOfStream);
|
| + friend class AudioRendererBaseTest;
|
|
|
| DISALLOW_COPY_AND_ASSIGN(MockAudioRendererBase);
|
| };
|
| @@ -88,18 +90,49 @@ class AudioRendererBaseTest : public ::testing::Test {
|
| base::Unretained(this));
|
| }
|
|
|
| + scoped_refptr<DataBuffer> CreateBuffer(int data_size, uint8 value) {
|
| + scoped_refptr<DataBuffer> buffer(new DataBuffer(data_size));
|
| + buffer->SetDataSize(data_size);
|
| + memset(buffer->GetWritableData(), value, buffer->GetDataSize());
|
| + return buffer;
|
| + }
|
| +
|
| void WriteUntilNoPendingReads(int data_size, uint8 value,
|
| uint32* bytes_buffered) {
|
| while (pending_reads_ > 0) {
|
| - scoped_refptr<DataBuffer> buffer(new DataBuffer(data_size));
|
| - buffer->SetDataSize(data_size);
|
| - memset(buffer->GetWritableData(), value, buffer->GetDataSize());
|
| --pending_reads_;
|
| *bytes_buffered += data_size;
|
| - decoder_->ConsumeAudioSamplesForTest(buffer);
|
| + decoder_->ConsumeAudioSamplesForTest(CreateBuffer(data_size, value));
|
| + }
|
| + }
|
| +
|
| + void ConsumeBufferedData(uint32 data_size, uint8 expected_value,
|
| + uint32* bytes_buffered) {
|
| + DCHECK(bytes_buffered);
|
| + DCHECK_GT(*bytes_buffered, 0u);
|
| +
|
| + base::TimeDelta playback_delay(base::TimeDelta::FromSeconds(1));
|
| + scoped_array<uint8> buffer(new uint8[data_size]);
|
| + while (*bytes_buffered > 0) {
|
| + EXPECT_EQ(data_size, renderer_->FillBuffer(buffer.get(), data_size,
|
| + playback_delay, false));
|
| + EXPECT_EQ(expected_value, buffer[0]);
|
| + *bytes_buffered -= data_size;
|
| }
|
| }
|
|
|
| + void ExpectUnderflow(uint32 data_size, int checkpoint_value) {
|
| + scoped_array<uint8> buffer(new uint8[data_size]);
|
| + base::TimeDelta playback_delay(base::TimeDelta::FromSeconds(1));
|
| +
|
| + EXPECT_CALL(*this, OnUnderflow());
|
| + EXPECT_CALL(*renderer_, CheckPoint(checkpoint_value));
|
| + EXPECT_EQ(0u, renderer_->FillBuffer(buffer.get(), data_size, playback_delay,
|
| + false));
|
| + renderer_->CheckPoint(checkpoint_value);
|
| + }
|
| +
|
| +
|
| protected:
|
| static const size_t kMaxQueueSize;
|
|
|
| @@ -283,41 +316,25 @@ TEST_F(AudioRendererBaseTest, Underflow) {
|
| EXPECT_EQ(1.0f, renderer_->GetPlaybackRate());
|
|
|
| // Consume all of the data passed into the renderer.
|
| - uint8 buffer[kDataSize];
|
| - while (bytes_buffered > 0) {
|
| - EXPECT_EQ(kDataSize,
|
| - renderer_->FillBuffer(buffer, kDataSize, playback_delay, false));
|
| - EXPECT_EQ(1, buffer[0]);
|
| - bytes_buffered -= kDataSize;
|
| - }
|
| + ConsumeBufferedData(kDataSize, 1, &bytes_buffered);
|
|
|
| // Make sure there are read requests pending.
|
| EXPECT_GT(pending_reads_, 0u);
|
|
|
| // Verify the next FillBuffer() call triggers calls the underflow callback
|
| // since the queue is empty.
|
| - EXPECT_CALL(*this, OnUnderflow());
|
| - EXPECT_CALL(*renderer_, CheckPoint(1));
|
| - EXPECT_EQ(0u, renderer_->FillBuffer(buffer, kDataSize, playback_delay,
|
| - false));
|
| - renderer_->CheckPoint(1);
|
| + ExpectUnderflow(kDataSize, 1);
|
|
|
| // Verify that zeroed out buffers are being returned during the underflow.
|
| - for (int i = 0; i < 5; ++i) {
|
| - EXPECT_EQ(kDataSize,
|
| - renderer_->FillBuffer(buffer, kDataSize, playback_delay, false));
|
| - EXPECT_EQ(0, buffer[0]);
|
| - }
|
| + uint32 zeros_to_read = 5 * kDataSize;
|
| + ConsumeBufferedData(kDataSize, 0, &zeros_to_read);
|
|
|
| renderer_->ResumeAfterUnderflow(false);
|
|
|
| // Verify we are still getting zeroed out buffers since no new data has been
|
| // pushed to the renderer.
|
| - for (int i = 0; i < 5; ++i) {
|
| - EXPECT_EQ(kDataSize,
|
| - renderer_->FillBuffer(buffer, kDataSize, playback_delay, false));
|
| - EXPECT_EQ(0, buffer[0]);
|
| - }
|
| + zeros_to_read = 5 * kDataSize;
|
| + ConsumeBufferedData(kDataSize, 0, &zeros_to_read);
|
|
|
| // Satisfy all pending read requests.
|
| WriteUntilNoPendingReads(kDataSize, 2, &bytes_buffered);
|
| @@ -325,12 +342,73 @@ TEST_F(AudioRendererBaseTest, Underflow) {
|
| EXPECT_GE(bytes_buffered, bytes_for_preroll);
|
|
|
| // Verify that we are now getting the new data.
|
| - while (bytes_buffered > 0) {
|
| - EXPECT_EQ(kDataSize,
|
| - renderer_->FillBuffer(buffer, kDataSize, playback_delay, false));
|
| - EXPECT_EQ(2, buffer[0]);
|
| - bytes_buffered -= kDataSize;
|
| + ConsumeBufferedData(kDataSize, 2, &bytes_buffered);
|
| +}
|
| +
|
| +
|
| +TEST_F(AudioRendererBaseTest, Underflow_EndOfStream) {
|
| + InSequence s;
|
| +
|
| + base::TimeDelta playback_delay(base::TimeDelta::FromSeconds(1));
|
| +
|
| + // Then our subclass will be asked to initialize.
|
| + EXPECT_CALL(*renderer_, OnInitialize(_, _, _))
|
| + .WillOnce(Return(true));
|
| +
|
| + // Initialize, we shouldn't have any reads.
|
| + renderer_->Initialize(decoder_, NewExpectedClosure(), NewUnderflowClosure());
|
| + EXPECT_EQ(0u, pending_reads_);
|
| +
|
| + // Now seek to trigger prerolling, verifying the callback hasn't been
|
| + // executed yet.
|
| + EXPECT_CALL(*renderer_, CheckPoint(0));
|
| + renderer_->Seek(base::TimeDelta(), NewExpectedStatusCB(PIPELINE_OK));
|
| + EXPECT_EQ(kMaxQueueSize, pending_reads_);
|
| + renderer_->CheckPoint(0);
|
| +
|
| + // Now satisfy the read requests. Our callback should be executed after
|
| + // exiting this loop.
|
| + const uint32 kDataSize = 1024;
|
| + uint32 bytes_buffered = 0;
|
| +
|
| + WriteUntilNoPendingReads(kDataSize, 1, &bytes_buffered);
|
| +
|
| + // Then set the renderer to play state.
|
| + renderer_->Play(NewExpectedClosure());
|
| + renderer_->SetPlaybackRate(1.0f);
|
| + EXPECT_EQ(1.0f, renderer_->GetPlaybackRate());
|
| +
|
| + // Consume all of the data passed into the renderer.
|
| + ConsumeBufferedData(kDataSize, 1, &bytes_buffered);
|
| +
|
| + // Make sure there are read requests pending.
|
| + EXPECT_GT(pending_reads_, 0u);
|
| +
|
| + // Verify the next FillBuffer() call triggers calls the underflow callback
|
| + // since the queue is empty.
|
| + ExpectUnderflow(kDataSize, 1);
|
| +
|
| + DCHECK_GE(pending_reads_, 2u);
|
| +
|
| + // Write a buffer.
|
| + bytes_buffered += kDataSize;
|
| + --pending_reads_;
|
| + decoder_->ConsumeAudioSamplesForTest(CreateBuffer(kDataSize, 3));
|
| +
|
| + // Verify we are getting zeroed out buffers since we haven't pushed enough
|
| + // data to satisfy preroll.
|
| + uint32 zeros_to_read = 5 * kDataSize;
|
| + ConsumeBufferedData(kDataSize, 0, &zeros_to_read);
|
| +
|
| + // Send end of stream buffers for all pending reads.
|
| + while (pending_reads_ > 0) {
|
| + scoped_refptr<DataBuffer> buffer(new DataBuffer(0));
|
| + --pending_reads_;
|
| + decoder_->ConsumeAudioSamplesForTest(buffer);
|
| }
|
| +
|
| + // Verify that we are now getting the new data.
|
| + ConsumeBufferedData(kDataSize, 3, &bytes_buffered);
|
| }
|
|
|
| } // namespace media
|
|
|