sync_buffer_unittest.cc (6603B)
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_coding/neteq/sync_buffer.h" 12 13 #include <cstddef> 14 #include <cstdint> 15 16 #include "api/audio/audio_frame.h" 17 #include "modules/audio_coding/neteq/audio_multi_vector.h" 18 #include "rtc_base/numerics/safe_conversions.h" 19 #include "test/gtest.h" 20 21 namespace webrtc { 22 23 TEST(SyncBuffer, CreateAndDestroy) { 24 // Create a SyncBuffer with two channels and 10 samples each. 25 static const size_t kLen = 10; 26 static const size_t kChannels = 2; 27 SyncBuffer sync_buffer(kChannels, kLen); 28 EXPECT_EQ(kChannels, sync_buffer.Channels()); 29 EXPECT_EQ(kLen, sync_buffer.Size()); 30 // When the buffer is empty, the next index to play out is at the end. 31 EXPECT_EQ(kLen, sync_buffer.next_index()); 32 // Verify that all elements are zero. 33 for (size_t channel = 0; channel < kChannels; ++channel) { 34 for (size_t i = 0; i < kLen; ++i) { 35 EXPECT_EQ(0, sync_buffer[channel][i]); 36 } 37 } 38 } 39 40 TEST(SyncBuffer, SetNextIndex) { 41 // Create a SyncBuffer with two channels and 100 samples each. 42 static const size_t kLen = 100; 43 static const size_t kChannels = 2; 44 SyncBuffer sync_buffer(kChannels, kLen); 45 sync_buffer.set_next_index(0); 46 EXPECT_EQ(0u, sync_buffer.next_index()); 47 sync_buffer.set_next_index(kLen / 2); 48 EXPECT_EQ(kLen / 2, sync_buffer.next_index()); 49 sync_buffer.set_next_index(kLen); 50 EXPECT_EQ(kLen, sync_buffer.next_index()); 51 // Try to set larger than the buffer size; should cap at buffer size. 52 sync_buffer.set_next_index(kLen + 1); 53 EXPECT_EQ(kLen, sync_buffer.next_index()); 54 } 55 56 TEST(SyncBuffer, PushBackAndFlush) { 57 // Create a SyncBuffer with two channels and 100 samples each. 58 static const size_t kLen = 100; 59 static const size_t kChannels = 2; 60 SyncBuffer sync_buffer(kChannels, kLen); 61 static const size_t kNewLen = 10; 62 AudioMultiVector new_data(kChannels, kNewLen); 63 // Populate `new_data`. 64 for (size_t channel = 0; channel < kChannels; ++channel) { 65 for (size_t i = 0; i < kNewLen; ++i) { 66 new_data[channel][i] = checked_cast<int16_t>(i); 67 } 68 } 69 // Push back `new_data` into `sync_buffer`. This operation should pop out 70 // data from the front of `sync_buffer`, so that the size of the buffer 71 // remains the same. The `next_index_` should also move with the same length. 72 sync_buffer.PushBack(new_data); 73 ASSERT_EQ(kLen, sync_buffer.Size()); 74 // Verify that `next_index_` moved accordingly. 75 EXPECT_EQ(kLen - kNewLen, sync_buffer.next_index()); 76 // Verify the new contents. 77 for (size_t channel = 0; channel < kChannels; ++channel) { 78 for (size_t i = 0; i < kNewLen; ++i) { 79 EXPECT_EQ(new_data[channel][i], 80 sync_buffer[channel][sync_buffer.next_index() + i]); 81 } 82 } 83 84 // Now flush the buffer, and verify that it is all zeros, and that next_index 85 // points to the end. 86 sync_buffer.Flush(); 87 ASSERT_EQ(kLen, sync_buffer.Size()); 88 EXPECT_EQ(kLen, sync_buffer.next_index()); 89 for (size_t channel = 0; channel < kChannels; ++channel) { 90 for (size_t i = 0; i < kLen; ++i) { 91 EXPECT_EQ(0, sync_buffer[channel][i]); 92 } 93 } 94 } 95 96 TEST(SyncBuffer, PushFrontZeros) { 97 // Create a SyncBuffer with two channels and 100 samples each. 98 static const size_t kLen = 100; 99 static const size_t kChannels = 2; 100 SyncBuffer sync_buffer(kChannels, kLen); 101 static const size_t kNewLen = 10; 102 AudioMultiVector new_data(kChannels, kNewLen); 103 // Populate `new_data`. 104 for (size_t channel = 0; channel < kChannels; ++channel) { 105 for (size_t i = 0; i < kNewLen; ++i) { 106 new_data[channel][i] = checked_cast<int16_t>(1000 + i); 107 } 108 } 109 sync_buffer.PushBack(new_data); 110 EXPECT_EQ(kLen, sync_buffer.Size()); 111 112 // Push `kNewLen` - 1 zeros into each channel in the front of the SyncBuffer. 113 sync_buffer.PushFrontZeros(kNewLen - 1); 114 EXPECT_EQ(kLen, sync_buffer.Size()); // Size should remain the same. 115 // Verify that `next_index_` moved accordingly. Should be at the end - 1. 116 EXPECT_EQ(kLen - 1, sync_buffer.next_index()); 117 // Verify the zeros. 118 for (size_t channel = 0; channel < kChannels; ++channel) { 119 for (size_t i = 0; i < kNewLen - 1; ++i) { 120 EXPECT_EQ(0, sync_buffer[channel][i]); 121 } 122 } 123 // Verify that the correct data is at the end of the SyncBuffer. 124 for (size_t channel = 0; channel < kChannels; ++channel) { 125 EXPECT_EQ(1000, sync_buffer[channel][sync_buffer.next_index()]); 126 } 127 } 128 129 TEST(SyncBuffer, GetNextAudioInterleaved) { 130 // Create a SyncBuffer with two channels and 100 samples each. 131 static const size_t kLen = 100; 132 static const size_t kChannels = 2; 133 SyncBuffer sync_buffer(kChannels, kLen); 134 static const size_t kNewLen = 10; 135 AudioMultiVector new_data(kChannels, kNewLen); 136 // Populate `new_data`. 137 for (size_t channel = 0; channel < kChannels; ++channel) { 138 for (size_t i = 0; i < kNewLen; ++i) { 139 new_data[channel][i] = checked_cast<int16_t>(i); 140 } 141 } 142 // Push back `new_data` into `sync_buffer`. This operation should pop out 143 // data from the front of `sync_buffer`, so that the size of the buffer 144 // remains the same. The `next_index_` should also move with the same length. 145 sync_buffer.PushBack(new_data); 146 147 // Read to interleaved output. Read in two batches, where each read operation 148 // should automatically update the `net_index_` in the SyncBuffer. 149 // `samples` is the number of samples read from each channel. 150 // That is, the number of samples written to `output` is `samples` * 151 // `kChannels`. 152 const size_t samples = kNewLen / 2; 153 AudioFrame output1; 154 EXPECT_TRUE(sync_buffer.GetNextAudioInterleaved( 155 output1.mutable_data(samples, kChannels))); 156 157 AudioFrame output2; 158 EXPECT_TRUE(sync_buffer.GetNextAudioInterleaved( 159 output2.mutable_data(samples, kChannels))); 160 161 // Verify the data. 162 const int16_t* output_ptr = output1.data(); 163 for (size_t i = 0; i < samples; ++i) { 164 for (size_t channel = 0; channel < kChannels; ++channel) { 165 EXPECT_EQ(new_data[channel][i], *output_ptr); 166 ++output_ptr; 167 } 168 } 169 output_ptr = output2.data(); 170 for (size_t i = kNewLen / 2; i < kNewLen; ++i) { 171 for (size_t channel = 0; channel < kChannels; ++channel) { 172 EXPECT_EQ(new_data[channel][i], *output_ptr); 173 ++output_ptr; 174 } 175 } 176 } 177 178 } // namespace webrtc