Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 /* | 1 /* |
| 2 * Copyright (c) 2011 The WebRTC project authors. All Rights Reserved. | 2 * Copyright (c) 2011 The WebRTC project authors. All Rights Reserved. |
| 3 * | 3 * |
| 4 * Use of this source code is governed by a BSD-style license | 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 | 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 | 6 * tree. An additional intellectual property rights grant can be found |
| 7 * in the file PATENTS. All contributing project authors may | 7 * in the file PATENTS. All contributing project authors may |
| 8 * be found in the AUTHORS file in the root of the source tree. | 8 * be found in the AUTHORS file in the root of the source tree. |
| 9 */ | 9 */ |
| 10 | 10 |
| 11 #include "webrtc/modules/audio_coding/neteq/include/neteq.h" | 11 #include "webrtc/modules/audio_coding/neteq/include/neteq.h" |
| 12 | 12 |
| 13 #include <math.h> | 13 #include <math.h> |
| 14 #include <stdlib.h> | 14 #include <stdlib.h> |
| 15 #include <string.h> // memset | 15 #include <string.h> // memset |
| 16 | 16 |
| 17 #include <algorithm> | 17 #include <algorithm> |
| 18 #include <memory> | 18 #include <memory> |
| 19 #include <set> | 19 #include <set> |
| 20 #include <string> | 20 #include <string> |
| 21 #include <vector> | 21 #include <vector> |
| 22 | 22 |
| 23 #include "gflags/gflags.h" | 23 #include "gflags/gflags.h" |
| 24 #include "testing/gtest/include/gtest/gtest.h" | 24 #include "testing/gtest/include/gtest/gtest.h" |
| 25 #include "webrtc/base/sha1digest.h" | |
| 26 #include "webrtc/base/stringencode.h" | |
| 25 #include "webrtc/modules/audio_coding/neteq/tools/audio_loop.h" | 27 #include "webrtc/modules/audio_coding/neteq/tools/audio_loop.h" |
| 26 #include "webrtc/modules/audio_coding/neteq/tools/rtp_file_source.h" | 28 #include "webrtc/modules/audio_coding/neteq/tools/rtp_file_source.h" |
| 27 #include "webrtc/modules/audio_coding/codecs/pcm16b/pcm16b.h" | 29 #include "webrtc/modules/audio_coding/codecs/pcm16b/pcm16b.h" |
| 28 #include "webrtc/modules/include/module_common_types.h" | 30 #include "webrtc/modules/include/module_common_types.h" |
| 29 #include "webrtc/test/testsupport/fileutils.h" | 31 #include "webrtc/test/testsupport/fileutils.h" |
| 30 #include "webrtc/typedefs.h" | 32 #include "webrtc/typedefs.h" |
| 31 | 33 |
| 32 #ifdef WEBRTC_NETEQ_UNITTEST_BITEXACT | 34 #ifdef WEBRTC_NETEQ_UNITTEST_BITEXACT |
| 33 #ifdef WEBRTC_ANDROID_PLATFORM_BUILD | 35 #ifdef WEBRTC_ANDROID_PLATFORM_BUILD |
| 34 #include "external/webrtc/webrtc/modules/audio_coding/neteq/neteq_unittest.pb.h" | 36 #include "external/webrtc/webrtc/modules/audio_coding/neteq/neteq_unittest.pb.h" |
| 35 #else | 37 #else |
| 36 #include "webrtc/audio_coding/neteq/neteq_unittest.pb.h" | 38 #include "webrtc/audio_coding/neteq/neteq_unittest.pb.h" |
| 37 #endif | 39 #endif |
| 38 #endif | 40 #endif |
| 39 | 41 |
| 40 DEFINE_bool(gen_ref, false, "Generate reference files."); | 42 DEFINE_bool(gen_ref, false, "Generate reference files."); |
| 41 | 43 |
| 42 namespace { | 44 namespace { |
| 43 | 45 |
| 46 const std::string& PlatformChecksum(const std::string& checksum_general, | |
| 47 const std::string& checksum_android, | |
| 48 const std::string& checksum_win_32, | |
| 49 const std::string& checksum_win_64) { | |
| 50 #ifdef WEBRTC_ANDROID | |
| 51 if (!checksum_android.empty()) | |
|
hlundin-webrtc
2016/04/29 12:26:28
I think I would rather have the strings always pop
minyue-webrtc
2016/04/29 13:11:27
Sounds good to me. I was thinking that 1) the refe
| |
| 52 return checksum_android; | |
| 53 #endif // WEBRTC_ANDROID | |
| 54 | |
| 55 #ifdef WEBRTC_WIN | |
| 56 #ifdef WEBRTC_ARCH_64_BITS | |
| 57 if (!checksum_win_64.empty()) | |
| 58 return checksum_win_64; | |
| 59 #else | |
| 60 if (!checksum_win_32.empty()) | |
| 61 return checksum_win_32; | |
| 62 #endif // WEBRTC_ARCH_64_BITS | |
| 63 #endif // WEBRTC_WIN | |
| 64 | |
| 65 return checksum_general; | |
| 66 } | |
| 67 | |
| 44 bool IsAllZero(const int16_t* buf, size_t buf_length) { | 68 bool IsAllZero(const int16_t* buf, size_t buf_length) { |
| 45 bool all_zero = true; | 69 bool all_zero = true; |
| 46 for (size_t n = 0; n < buf_length && all_zero; ++n) | 70 for (size_t n = 0; n < buf_length && all_zero; ++n) |
| 47 all_zero = buf[n] == 0; | 71 all_zero = buf[n] == 0; |
| 48 return all_zero; | 72 return all_zero; |
| 49 } | 73 } |
| 50 | 74 |
| 51 bool IsAllNonZero(const int16_t* buf, size_t buf_length) { | 75 bool IsAllNonZero(const int16_t* buf, size_t buf_length) { |
| 52 bool all_non_zero = true; | 76 bool all_non_zero = true; |
| 53 for (size_t n = 0; n < buf_length && all_non_zero; ++n) | 77 for (size_t n = 0; n < buf_length && all_non_zero; ++n) |
| (...skipping 24 matching lines...) Expand all Loading... | |
| 78 | 102 |
| 79 void Convert(const webrtc::RtcpStatistics& stats_raw, | 103 void Convert(const webrtc::RtcpStatistics& stats_raw, |
| 80 webrtc::neteq_unittest::RtcpStatistics* stats) { | 104 webrtc::neteq_unittest::RtcpStatistics* stats) { |
| 81 stats->set_fraction_lost(stats_raw.fraction_lost); | 105 stats->set_fraction_lost(stats_raw.fraction_lost); |
| 82 stats->set_cumulative_lost(stats_raw.cumulative_lost); | 106 stats->set_cumulative_lost(stats_raw.cumulative_lost); |
| 83 stats->set_extended_max_sequence_number( | 107 stats->set_extended_max_sequence_number( |
| 84 stats_raw.extended_max_sequence_number); | 108 stats_raw.extended_max_sequence_number); |
| 85 stats->set_jitter(stats_raw.jitter); | 109 stats->set_jitter(stats_raw.jitter); |
| 86 } | 110 } |
| 87 | 111 |
| 88 void WriteMessage(FILE* file, const std::string& message) { | 112 void WriteMessage(FILE* file, rtc::MessageDigest* digest, |
|
minyue-webrtc
2016/04/29 13:11:27
I also like to rename this guy
hlundin-webrtc
2016/04/29 13:19:09
Acknowledged.
| |
| 113 const std::string& message) { | |
| 89 int32_t size = message.length(); | 114 int32_t size = message.length(); |
| 90 ASSERT_EQ(1u, fwrite(&size, sizeof(size), 1, file)); | 115 if (file) |
| 116 ASSERT_EQ(1u, fwrite(&size, sizeof(size), 1, file)); | |
| 117 digest->Update(&size, sizeof(size)); | |
| 118 | |
| 91 if (size <= 0) | 119 if (size <= 0) |
|
hlundin-webrtc
2016/04/29 12:26:28
Can you omit this early return? I mean, the length
minyue-webrtc
2016/04/29 13:11:27
Yes. When I read this part, I did not like it myse
| |
| 92 return; | 120 return; |
| 93 ASSERT_EQ(static_cast<size_t>(size), | 121 if (file) |
| 94 fwrite(message.data(), sizeof(char), size, file)); | 122 ASSERT_EQ(static_cast<size_t>(size), |
| 123 fwrite(message.data(), sizeof(char), size, file)); | |
| 124 digest->Update(message.data(), sizeof(char) * size); | |
| 95 } | 125 } |
| 96 | 126 |
| 97 void ReadMessage(FILE* file, std::string* message) { | |
| 98 int32_t size; | |
| 99 ASSERT_EQ(1u, fread(&size, sizeof(size), 1, file)); | |
| 100 if (size <= 0) | |
| 101 return; | |
| 102 std::unique_ptr<char[]> buffer(new char[size]); | |
| 103 ASSERT_EQ(static_cast<size_t>(size), | |
| 104 fread(buffer.get(), sizeof(char), size, file)); | |
| 105 message->assign(buffer.get(), size); | |
| 106 } | |
| 107 #endif // WEBRTC_NETEQ_UNITTEST_BITEXACT | 127 #endif // WEBRTC_NETEQ_UNITTEST_BITEXACT |
| 108 | 128 |
| 109 } // namespace | 129 } // namespace |
| 110 | 130 |
| 111 namespace webrtc { | 131 namespace webrtc { |
| 112 | 132 |
| 113 class RefFiles { | 133 class ResultSink { |
| 114 public: | 134 public: |
| 115 RefFiles(const std::string& input_file, const std::string& output_file); | 135 explicit ResultSink(const std::string& output_file); |
| 116 ~RefFiles(); | 136 ~ResultSink(); |
| 117 template<class T> void ProcessReference(const T& test_results); | 137 |
| 118 template<typename T, size_t n> void ProcessReference( | 138 template<typename T, size_t n> void AddResult( |
| 119 const T (&test_results)[n], | 139 const T (&test_results)[n], |
| 120 size_t length); | 140 size_t length); |
| 121 template<typename T, size_t n> void WriteToFile( | |
| 122 const T (&test_results)[n], | |
| 123 size_t length); | |
| 124 template<typename T, size_t n> void ReadFromFileAndCompare( | |
| 125 const T (&test_results)[n], | |
| 126 size_t length); | |
| 127 void WriteToFile(const NetEqNetworkStatistics& stats); | |
| 128 void ReadFromFileAndCompare(const NetEqNetworkStatistics& stats); | |
| 129 void WriteToFile(const RtcpStatistics& stats); | |
| 130 void ReadFromFileAndCompare(const RtcpStatistics& stats); | |
| 131 | 141 |
| 132 FILE* input_fp_; | 142 void AddResult(const NetEqNetworkStatistics& stats); |
| 143 void AddResult(const RtcpStatistics& stats); | |
| 144 | |
| 145 void VerifyChecksum(const std::string& ref_check_sum); | |
| 146 | |
| 147 private: | |
| 133 FILE* output_fp_; | 148 FILE* output_fp_; |
| 149 std::unique_ptr<rtc::MessageDigest> digest_; | |
| 134 }; | 150 }; |
| 135 | 151 |
| 136 RefFiles::RefFiles(const std::string &input_file, | 152 ResultSink::ResultSink(const std::string &output_file) |
| 137 const std::string &output_file) | 153 : output_fp_(NULL), |
|
hlundin-webrtc
2016/04/29 12:26:28
nullptr
minyue-webrtc
2016/04/29 13:11:27
Done.
| |
| 138 : input_fp_(NULL), | 154 digest_(new rtc::Sha1Digest()) { |
| 139 output_fp_(NULL) { | |
| 140 if (!input_file.empty()) { | |
| 141 input_fp_ = fopen(input_file.c_str(), "rb"); | |
| 142 EXPECT_TRUE(input_fp_ != NULL); | |
| 143 } | |
| 144 if (!output_file.empty()) { | 155 if (!output_file.empty()) { |
| 145 output_fp_ = fopen(output_file.c_str(), "wb"); | 156 output_fp_ = fopen(output_file.c_str(), "wb"); |
| 146 EXPECT_TRUE(output_fp_ != NULL); | 157 EXPECT_TRUE(output_fp_ != NULL); |
| 147 } | 158 } |
| 148 } | 159 } |
| 149 | 160 |
| 150 RefFiles::~RefFiles() { | 161 ResultSink::~ResultSink() { |
| 151 if (input_fp_) { | 162 if (output_fp_) |
| 152 EXPECT_EQ(EOF, fgetc(input_fp_)); // Make sure that we reached the end. | 163 fclose(output_fp_); |
| 153 fclose(input_fp_); | |
| 154 } | |
| 155 if (output_fp_) fclose(output_fp_); | |
| 156 } | |
| 157 | |
| 158 template<class T> | |
| 159 void RefFiles::ProcessReference(const T& test_results) { | |
| 160 WriteToFile(test_results); | |
| 161 ReadFromFileAndCompare(test_results); | |
| 162 } | 164 } |
| 163 | 165 |
| 164 template<typename T, size_t n> | 166 template<typename T, size_t n> |
| 165 void RefFiles::ProcessReference(const T (&test_results)[n], size_t length) { | 167 void ResultSink::AddResult(const T (&test_results)[n], size_t length) { |
| 166 WriteToFile(test_results, length); | |
| 167 ReadFromFileAndCompare(test_results, length); | |
| 168 } | |
| 169 | |
| 170 template<typename T, size_t n> | |
| 171 void RefFiles::WriteToFile(const T (&test_results)[n], size_t length) { | |
| 172 if (output_fp_) { | 168 if (output_fp_) { |
| 173 ASSERT_EQ(length, fwrite(&test_results, sizeof(T), length, output_fp_)); | 169 ASSERT_EQ(length, fwrite(&test_results, sizeof(T), length, output_fp_)); |
| 174 } | 170 } |
| 171 digest_->Update(&test_results, sizeof(T) * length); | |
| 175 } | 172 } |
| 176 | 173 |
| 177 template<typename T, size_t n> | 174 void ResultSink::AddResult(const NetEqNetworkStatistics& stats_raw) { |
| 178 void RefFiles::ReadFromFileAndCompare(const T (&test_results)[n], | |
| 179 size_t length) { | |
| 180 if (input_fp_) { | |
| 181 // Read from ref file. | |
| 182 T* ref = new T[length]; | |
| 183 ASSERT_EQ(length, fread(ref, sizeof(T), length, input_fp_)); | |
| 184 // Compare | |
| 185 ASSERT_EQ(0, memcmp(&test_results, ref, sizeof(T) * length)); | |
| 186 delete [] ref; | |
| 187 } | |
| 188 } | |
| 189 | |
| 190 void RefFiles::WriteToFile(const NetEqNetworkStatistics& stats_raw) { | |
| 191 #ifdef WEBRTC_NETEQ_UNITTEST_BITEXACT | 175 #ifdef WEBRTC_NETEQ_UNITTEST_BITEXACT |
| 192 if (!output_fp_) | |
| 193 return; | |
| 194 neteq_unittest::NetEqNetworkStatistics stats; | 176 neteq_unittest::NetEqNetworkStatistics stats; |
| 195 Convert(stats_raw, &stats); | 177 Convert(stats_raw, &stats); |
| 196 | 178 |
| 197 std::string stats_string; | 179 std::string stats_string; |
| 198 ASSERT_TRUE(stats.SerializeToString(&stats_string)); | 180 ASSERT_TRUE(stats.SerializeToString(&stats_string)); |
| 199 WriteMessage(output_fp_, stats_string); | 181 WriteMessage(output_fp_, digest_.get(), stats_string); |
| 200 #else | 182 #else |
| 201 FAIL() << "Writing to reference file requires Proto Buffer."; | 183 FAIL() << "Writing to reference file requires Proto Buffer."; |
| 202 #endif // WEBRTC_NETEQ_UNITTEST_BITEXACT | 184 #endif // WEBRTC_NETEQ_UNITTEST_BITEXACT |
| 203 } | 185 } |
| 204 | 186 |
| 205 void RefFiles::ReadFromFileAndCompare( | 187 void ResultSink::AddResult(const RtcpStatistics& stats_raw) { |
| 206 const NetEqNetworkStatistics& stats) { | |
| 207 #ifdef WEBRTC_NETEQ_UNITTEST_BITEXACT | 188 #ifdef WEBRTC_NETEQ_UNITTEST_BITEXACT |
| 208 if (!input_fp_) | |
| 209 return; | |
| 210 | |
| 211 std::string stats_string; | |
| 212 ReadMessage(input_fp_, &stats_string); | |
| 213 neteq_unittest::NetEqNetworkStatistics ref_stats; | |
| 214 ASSERT_TRUE(ref_stats.ParseFromString(stats_string)); | |
| 215 | |
| 216 // Compare | |
| 217 ASSERT_EQ(stats.current_buffer_size_ms, ref_stats.current_buffer_size_ms()); | |
| 218 ASSERT_EQ(stats.preferred_buffer_size_ms, | |
| 219 ref_stats.preferred_buffer_size_ms()); | |
| 220 ASSERT_EQ(stats.jitter_peaks_found, ref_stats.jitter_peaks_found()); | |
| 221 ASSERT_EQ(stats.packet_loss_rate, ref_stats.packet_loss_rate()); | |
| 222 ASSERT_EQ(stats.packet_discard_rate, ref_stats.packet_discard_rate()); | |
| 223 ASSERT_EQ(stats.expand_rate, ref_stats.expand_rate()); | |
| 224 ASSERT_EQ(stats.preemptive_rate, ref_stats.preemptive_rate()); | |
| 225 ASSERT_EQ(stats.accelerate_rate, ref_stats.accelerate_rate()); | |
| 226 ASSERT_EQ(stats.clockdrift_ppm, ref_stats.clockdrift_ppm()); | |
| 227 ASSERT_EQ(stats.added_zero_samples, ref_stats.added_zero_samples()); | |
| 228 ASSERT_EQ(stats.secondary_decoded_rate, ref_stats.secondary_decoded_rate()); | |
| 229 ASSERT_LE(stats.speech_expand_rate, ref_stats.expand_rate()); | |
| 230 #else | |
| 231 FAIL() << "Reading from reference file requires Proto Buffer."; | |
| 232 #endif // WEBRTC_NETEQ_UNITTEST_BITEXACT | |
| 233 } | |
| 234 | |
| 235 void RefFiles::WriteToFile(const RtcpStatistics& stats_raw) { | |
| 236 #ifdef WEBRTC_NETEQ_UNITTEST_BITEXACT | |
| 237 if (!output_fp_) | |
| 238 return; | |
| 239 neteq_unittest::RtcpStatistics stats; | 189 neteq_unittest::RtcpStatistics stats; |
| 240 Convert(stats_raw, &stats); | 190 Convert(stats_raw, &stats); |
| 241 | 191 |
| 242 std::string stats_string; | 192 std::string stats_string; |
| 243 ASSERT_TRUE(stats.SerializeToString(&stats_string)); | 193 ASSERT_TRUE(stats.SerializeToString(&stats_string)); |
| 244 WriteMessage(output_fp_, stats_string); | 194 WriteMessage(output_fp_, digest_.get(), stats_string); |
| 245 #else | 195 #else |
| 246 FAIL() << "Writing to reference file requires Proto Buffer."; | 196 FAIL() << "Writing to reference file requires Proto Buffer."; |
| 247 #endif // WEBRTC_NETEQ_UNITTEST_BITEXACT | 197 #endif // WEBRTC_NETEQ_UNITTEST_BITEXACT |
| 248 } | 198 } |
| 249 | 199 |
| 250 void RefFiles::ReadFromFileAndCompare(const RtcpStatistics& stats) { | 200 void ResultSink::VerifyChecksum(const std::string& checksum) { |
| 251 #ifdef WEBRTC_NETEQ_UNITTEST_BITEXACT | 201 std::vector<char> buffer; |
| 252 if (!input_fp_) | 202 buffer.resize(digest_->Size()); |
| 253 return; | 203 digest_->Finish(&buffer[0], buffer.size()); |
| 254 std::string stats_string; | 204 const std::string result = rtc::hex_encode(&buffer[0], digest_->Size()); |
| 255 ReadMessage(input_fp_, &stats_string); | 205 EXPECT_EQ(checksum, result); |
| 256 neteq_unittest::RtcpStatistics ref_stats; | |
| 257 ASSERT_TRUE(ref_stats.ParseFromString(stats_string)); | |
| 258 | |
| 259 // Compare | |
| 260 ASSERT_EQ(stats.fraction_lost, ref_stats.fraction_lost()); | |
| 261 ASSERT_EQ(stats.cumulative_lost, ref_stats.cumulative_lost()); | |
| 262 ASSERT_EQ(stats.extended_max_sequence_number, | |
| 263 ref_stats.extended_max_sequence_number()); | |
| 264 ASSERT_EQ(stats.jitter, ref_stats.jitter()); | |
| 265 #else | |
| 266 FAIL() << "Reading from reference file requires Proto Buffer."; | |
| 267 #endif // WEBRTC_NETEQ_UNITTEST_BITEXACT | |
| 268 } | 206 } |
| 269 | 207 |
| 270 class NetEqDecodingTest : public ::testing::Test { | 208 class NetEqDecodingTest : public ::testing::Test { |
| 271 protected: | 209 protected: |
| 272 // NetEQ must be polled for data once every 10 ms. Thus, neither of the | 210 // NetEQ must be polled for data once every 10 ms. Thus, neither of the |
| 273 // constants below can be changed. | 211 // constants below can be changed. |
| 274 static const int kTimeStepMs = 10; | 212 static const int kTimeStepMs = 10; |
| 275 static const size_t kBlockSize8kHz = kTimeStepMs * 8; | 213 static const size_t kBlockSize8kHz = kTimeStepMs * 8; |
| 276 static const size_t kBlockSize16kHz = kTimeStepMs * 16; | 214 static const size_t kBlockSize16kHz = kTimeStepMs * 16; |
| 277 static const size_t kBlockSize32kHz = kTimeStepMs * 32; | 215 static const size_t kBlockSize32kHz = kTimeStepMs * 32; |
| 278 static const size_t kBlockSize48kHz = kTimeStepMs * 48; | 216 static const size_t kBlockSize48kHz = kTimeStepMs * 48; |
| 279 static const int kInitSampleRateHz = 8000; | 217 static const int kInitSampleRateHz = 8000; |
| 280 | 218 |
| 281 NetEqDecodingTest(); | 219 NetEqDecodingTest(); |
| 282 virtual void SetUp(); | 220 virtual void SetUp(); |
| 283 virtual void TearDown(); | 221 virtual void TearDown(); |
| 284 void SelectDecoders(NetEqDecoder* used_codec); | 222 void SelectDecoders(NetEqDecoder* used_codec); |
| 285 void LoadDecoders(); | 223 void LoadDecoders(); |
| 286 void OpenInputFile(const std::string &rtp_file); | 224 void OpenInputFile(const std::string &rtp_file); |
| 287 void Process(); | 225 void Process(); |
| 288 | 226 |
| 289 void DecodeAndCompare(const std::string& rtp_file, | 227 void DecodeAndCompare(const std::string& rtp_file, |
| 290 const std::string& ref_file, | 228 const std::string& output_checksum, |
| 291 const std::string& stat_ref_file, | 229 const std::string& network_stats_checksum, |
| 292 const std::string& rtcp_ref_file); | 230 const std::string& rtcp_stats_checksum, |
| 231 bool gen_ref); | |
| 293 | 232 |
| 294 static void PopulateRtpInfo(int frame_index, | 233 static void PopulateRtpInfo(int frame_index, |
| 295 int timestamp, | 234 int timestamp, |
| 296 WebRtcRTPHeader* rtp_info); | 235 WebRtcRTPHeader* rtp_info); |
| 297 static void PopulateCng(int frame_index, | 236 static void PopulateCng(int frame_index, |
| 298 int timestamp, | 237 int timestamp, |
| 299 WebRtcRTPHeader* rtp_info, | 238 WebRtcRTPHeader* rtp_info, |
| 300 uint8_t* payload, | 239 uint8_t* payload, |
| 301 size_t* payload_len); | 240 size_t* payload_len); |
| 302 | 241 |
| (...skipping 124 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 427 (out_frame_.samples_per_channel_ == kBlockSize16kHz) || | 366 (out_frame_.samples_per_channel_ == kBlockSize16kHz) || |
| 428 (out_frame_.samples_per_channel_ == kBlockSize32kHz) || | 367 (out_frame_.samples_per_channel_ == kBlockSize32kHz) || |
| 429 (out_frame_.samples_per_channel_ == kBlockSize48kHz)); | 368 (out_frame_.samples_per_channel_ == kBlockSize48kHz)); |
| 430 output_sample_rate_ = out_frame_.sample_rate_hz_; | 369 output_sample_rate_ = out_frame_.sample_rate_hz_; |
| 431 EXPECT_EQ(output_sample_rate_, neteq_->last_output_sample_rate_hz()); | 370 EXPECT_EQ(output_sample_rate_, neteq_->last_output_sample_rate_hz()); |
| 432 | 371 |
| 433 // Increase time. | 372 // Increase time. |
| 434 sim_clock_ += kTimeStepMs; | 373 sim_clock_ += kTimeStepMs; |
| 435 } | 374 } |
| 436 | 375 |
| 437 void NetEqDecodingTest::DecodeAndCompare(const std::string& rtp_file, | 376 void NetEqDecodingTest::DecodeAndCompare( |
| 438 const std::string& ref_file, | 377 const std::string& rtp_file, |
| 439 const std::string& stat_ref_file, | 378 const std::string& output_checksum, |
| 440 const std::string& rtcp_ref_file) { | 379 const std::string& network_stats_checksum, |
| 380 const std::string& rtcp_stats_checksum, | |
| 381 bool gen_ref) { | |
| 441 OpenInputFile(rtp_file); | 382 OpenInputFile(rtp_file); |
| 442 | 383 |
| 443 std::string ref_out_file = ""; | 384 std::string ref_out_file = |
| 444 if (ref_file.empty()) { | 385 gen_ref ? webrtc::test::OutputPath() + "neteq_universal_ref.pcm" : ""; |
| 445 ref_out_file = webrtc::test::OutputPath() + "neteq_universal_ref.pcm"; | 386 ResultSink ref_files(ref_out_file); |
|
minyue-webrtc
2016/04/29 13:11:27
I'd rename ref_files as well.
hlundin-webrtc
2016/04/29 13:19:09
Acknowledged.
| |
| 446 } | |
| 447 RefFiles ref_files(ref_file, ref_out_file); | |
| 448 | 387 |
| 449 std::string stat_out_file = ""; | 388 std::string stat_out_file = |
| 450 if (stat_ref_file.empty()) { | 389 gen_ref ? webrtc::test::OutputPath() + "neteq_network_stats.dat" : ""; |
| 451 stat_out_file = webrtc::test::OutputPath() + "neteq_network_stats.dat"; | 390 ResultSink network_stat_files(stat_out_file); |
| 452 } | |
| 453 RefFiles network_stat_files(stat_ref_file, stat_out_file); | |
| 454 | 391 |
| 455 std::string rtcp_out_file = ""; | 392 std::string rtcp_out_file = |
| 456 if (rtcp_ref_file.empty()) { | 393 gen_ref ? webrtc::test::OutputPath() + "neteq_rtcp_stats.dat" : ""; |
| 457 rtcp_out_file = webrtc::test::OutputPath() + "neteq_rtcp_stats.dat"; | 394 ResultSink rtcp_stat_files(rtcp_out_file); |
| 458 } | |
| 459 RefFiles rtcp_stat_files(rtcp_ref_file, rtcp_out_file); | |
| 460 | 395 |
| 461 packet_.reset(rtp_source_->NextPacket()); | 396 packet_.reset(rtp_source_->NextPacket()); |
| 462 int i = 0; | 397 int i = 0; |
| 463 while (packet_) { | 398 while (packet_) { |
| 464 std::ostringstream ss; | 399 std::ostringstream ss; |
| 465 ss << "Lap number " << i++ << " in DecodeAndCompare while loop"; | 400 ss << "Lap number " << i++ << " in DecodeAndCompare while loop"; |
| 466 SCOPED_TRACE(ss.str()); // Print out the parameter values on failure. | 401 SCOPED_TRACE(ss.str()); // Print out the parameter values on failure. |
| 467 ASSERT_NO_FATAL_FAILURE(Process()); | 402 ASSERT_NO_FATAL_FAILURE(Process()); |
| 468 ASSERT_NO_FATAL_FAILURE(ref_files.ProcessReference( | 403 ASSERT_NO_FATAL_FAILURE(ref_files.AddResult( |
| 469 out_frame_.data_, out_frame_.samples_per_channel_)); | 404 out_frame_.data_, out_frame_.samples_per_channel_)); |
| 470 | 405 |
| 471 // Query the network statistics API once per second | 406 // Query the network statistics API once per second |
| 472 if (sim_clock_ % 1000 == 0) { | 407 if (sim_clock_ % 1000 == 0) { |
| 473 // Process NetworkStatistics. | 408 // Process NetworkStatistics. |
| 474 NetEqNetworkStatistics network_stats; | 409 NetEqNetworkStatistics network_stats; |
| 475 ASSERT_EQ(0, neteq_->NetworkStatistics(&network_stats)); | 410 ASSERT_EQ(0, neteq_->NetworkStatistics(&network_stats)); |
| 476 ASSERT_NO_FATAL_FAILURE( | 411 ASSERT_NO_FATAL_FAILURE( |
| 477 network_stat_files.ProcessReference(network_stats)); | 412 network_stat_files.AddResult(network_stats)); |
| 478 // Compare with CurrentDelay, which should be identical. | 413 // Compare with CurrentDelay, which should be identical. |
| 479 EXPECT_EQ(network_stats.current_buffer_size_ms, neteq_->CurrentDelayMs()); | 414 EXPECT_EQ(network_stats.current_buffer_size_ms, neteq_->CurrentDelayMs()); |
| 480 | 415 |
| 481 // Process RTCPstat. | 416 // Process RTCPstat. |
| 482 RtcpStatistics rtcp_stats; | 417 RtcpStatistics rtcp_stats; |
| 483 neteq_->GetRtcpStatistics(&rtcp_stats); | 418 neteq_->GetRtcpStatistics(&rtcp_stats); |
| 484 ASSERT_NO_FATAL_FAILURE(rtcp_stat_files.ProcessReference(rtcp_stats)); | 419 ASSERT_NO_FATAL_FAILURE(rtcp_stat_files.AddResult(rtcp_stats)); |
| 485 } | 420 } |
| 486 } | 421 } |
| 422 | |
| 423 ref_files.VerifyChecksum(output_checksum); | |
|
hlundin-webrtc
2016/04/29 12:26:28
I think you should add SCOPED_TRACE("ref_files") o
minyue-webrtc
2016/04/29 13:11:27
Done.
| |
| 424 network_stat_files.VerifyChecksum(network_stats_checksum); | |
| 425 rtcp_stat_files.VerifyChecksum(rtcp_stats_checksum); | |
| 487 } | 426 } |
| 488 | 427 |
| 489 void NetEqDecodingTest::PopulateRtpInfo(int frame_index, | 428 void NetEqDecodingTest::PopulateRtpInfo(int frame_index, |
| 490 int timestamp, | 429 int timestamp, |
| 491 WebRtcRTPHeader* rtp_info) { | 430 WebRtcRTPHeader* rtp_info) { |
| 492 rtp_info->header.sequenceNumber = frame_index; | 431 rtp_info->header.sequenceNumber = frame_index; |
| 493 rtp_info->header.timestamp = timestamp; | 432 rtp_info->header.timestamp = timestamp; |
| 494 rtp_info->header.ssrc = 0x1234; // Just an arbitrary SSRC. | 433 rtp_info->header.ssrc = 0x1234; // Just an arbitrary SSRC. |
| 495 rtp_info->header.payloadType = 94; // PCM16b WB codec. | 434 rtp_info->header.payloadType = 94; // PCM16b WB codec. |
| 496 rtp_info->header.markerBit = 0; | 435 rtp_info->header.markerBit = 0; |
| (...skipping 18 matching lines...) Expand all Loading... | |
| 515 (defined(WEBRTC_CODEC_ISAC) || defined(WEBRTC_CODEC_ISACFX)) && \ | 454 (defined(WEBRTC_CODEC_ISAC) || defined(WEBRTC_CODEC_ISACFX)) && \ |
| 516 defined(WEBRTC_CODEC_ILBC) && defined(WEBRTC_CODEC_G722) && \ | 455 defined(WEBRTC_CODEC_ILBC) && defined(WEBRTC_CODEC_G722) && \ |
| 517 !defined(WEBRTC_ARCH_ARM64) && !defined(UNDEFINED_SANITIZER) | 456 !defined(WEBRTC_ARCH_ARM64) && !defined(UNDEFINED_SANITIZER) |
| 518 #define MAYBE_TestBitExactness TestBitExactness | 457 #define MAYBE_TestBitExactness TestBitExactness |
| 519 #else | 458 #else |
| 520 #define MAYBE_TestBitExactness DISABLED_TestBitExactness | 459 #define MAYBE_TestBitExactness DISABLED_TestBitExactness |
| 521 #endif | 460 #endif |
| 522 TEST_F(NetEqDecodingTest, MAYBE_TestBitExactness) { | 461 TEST_F(NetEqDecodingTest, MAYBE_TestBitExactness) { |
| 523 const std::string input_rtp_file = | 462 const std::string input_rtp_file = |
| 524 webrtc::test::ResourcePath("audio_coding/neteq_universal_new", "rtp"); | 463 webrtc::test::ResourcePath("audio_coding/neteq_universal_new", "rtp"); |
| 525 // Note that neteq4_universal_ref.pcm and neteq4_universal_ref_win_32.pcm | |
| 526 // are identical. The latter could have been removed, but if clients still | |
| 527 // have a copy of the file, the test will fail. | |
| 528 const std::string input_ref_file = | |
| 529 webrtc::test::ResourcePath("audio_coding/neteq4_universal_ref", "pcm"); | |
| 530 #if defined(_MSC_VER) && (_MSC_VER >= 1700) | |
| 531 // For Visual Studio 2012 and later, we will have to use the generic reference | |
| 532 // file, rather than the windows-specific one. | |
| 533 const std::string network_stat_ref_file = webrtc::test::ProjectRootPath() + | |
| 534 "resources/audio_coding/neteq4_network_stats.dat"; | |
| 535 #else | |
| 536 const std::string network_stat_ref_file = | |
| 537 webrtc::test::ResourcePath("audio_coding/neteq4_network_stats", "dat"); | |
| 538 #endif | |
| 539 const std::string rtcp_stat_ref_file = | |
| 540 webrtc::test::ResourcePath("audio_coding/neteq4_rtcp_stats", "dat"); | |
| 541 | 464 |
| 542 if (FLAGS_gen_ref) { | 465 const std::string output_checksum = PlatformChecksum( |
| 543 DecodeAndCompare(input_rtp_file, "", "", ""); | 466 "f587883b7c371ee8d87dbf1b0f07525af7d959b8", |
| 544 } else { | 467 "a349bd71dba548029b05d1d2a6dc7caafab9a856", |
| 545 DecodeAndCompare(input_rtp_file, | 468 "", |
|
hlundin-webrtc
2016/04/29 12:26:28
Follow my suggestion in PlatformChecksum, and expl
minyue-webrtc
2016/04/29 13:11:27
Done.
| |
| 546 input_ref_file, | 469 "08266b198e7686b3cd9330813e0d2cd72fc8fdc2"); |
| 547 network_stat_ref_file, | 470 |
| 548 rtcp_stat_ref_file); | 471 const std::string network_stats_checksum = PlatformChecksum( |
| 549 } | 472 "2cf380a05ee07080bd72471e8ec7777a39644ec9", |
| 473 "2853ab577fe571adfc7b18f77bbe58f1253d2019", | |
| 474 "", | |
| 475 ""); | |
| 476 | |
| 477 const std::string rtcp_stats_checksum = PlatformChecksum( | |
| 478 "b8880bf9fed2487efbddcb8d94b9937a29ae521d", | |
| 479 "f3f7b3d3e71d7e635240b5373b57df6a7e4ce9d4", | |
| 480 "", | |
| 481 ""); | |
| 482 | |
| 483 DecodeAndCompare(input_rtp_file, | |
| 484 output_checksum, | |
| 485 network_stats_checksum, | |
| 486 rtcp_stats_checksum, | |
| 487 FLAGS_gen_ref); | |
| 550 } | 488 } |
| 551 | 489 |
| 552 // Disabled for UBSan: https://bugs.chromium.org/p/webrtc/issues/detail?id=5820 | 490 // Disabled for UBSan: https://bugs.chromium.org/p/webrtc/issues/detail?id=5820 |
| 553 #if !defined(WEBRTC_IOS) && !defined(WEBRTC_ANDROID) && \ | 491 #if !defined(WEBRTC_IOS) && !defined(WEBRTC_ANDROID) && \ |
| 554 defined(WEBRTC_NETEQ_UNITTEST_BITEXACT) && \ | 492 defined(WEBRTC_NETEQ_UNITTEST_BITEXACT) && \ |
| 555 defined(WEBRTC_CODEC_OPUS) && !defined(UNDEFINED_SANITIZER) | 493 defined(WEBRTC_CODEC_OPUS) && !defined(UNDEFINED_SANITIZER) |
| 556 #define MAYBE_TestOpusBitExactness TestOpusBitExactness | 494 #define MAYBE_TestOpusBitExactness TestOpusBitExactness |
| 557 #else | 495 #else |
| 558 #define MAYBE_TestOpusBitExactness DISABLED_TestOpusBitExactness | 496 #define MAYBE_TestOpusBitExactness DISABLED_TestOpusBitExactness |
| 559 #endif | 497 #endif |
| 560 TEST_F(NetEqDecodingTest, MAYBE_TestOpusBitExactness) { | 498 TEST_F(NetEqDecodingTest, MAYBE_TestOpusBitExactness) { |
| 561 const std::string input_rtp_file = | 499 const std::string input_rtp_file = |
| 562 webrtc::test::ResourcePath("audio_coding/neteq_opus", "rtp"); | 500 webrtc::test::ResourcePath("audio_coding/neteq_opus", "rtp"); |
| 563 const std::string input_ref_file = | |
| 564 // The pcm files were generated by using Opus v1.1.2 to decode the RTC | |
| 565 // file generated by Opus v1.1 | |
| 566 webrtc::test::ResourcePath("audio_coding/neteq4_opus_ref", "pcm"); | |
| 567 const std::string network_stat_ref_file = | |
| 568 // The network stats file was generated when using Opus v1.1.2 to decode | |
| 569 // the RTC file generated by Opus v1.1 | |
| 570 webrtc::test::ResourcePath("audio_coding/neteq4_opus_network_stats", | |
| 571 "dat"); | |
| 572 const std::string rtcp_stat_ref_file = | |
| 573 webrtc::test::ResourcePath("audio_coding/neteq4_opus_rtcp_stats", "dat"); | |
| 574 | 501 |
| 575 if (FLAGS_gen_ref) { | 502 const std::string output_checksum = PlatformChecksum( |
| 576 DecodeAndCompare(input_rtp_file, "", "", ""); | 503 "c23004d91ffbe5e7a1f24620fc89b58c0426040f", |
| 577 } else { | 504 "", "", ""); |
| 578 DecodeAndCompare(input_rtp_file, | 505 |
| 579 input_ref_file, | 506 const std::string network_stats_checksum = PlatformChecksum( |
| 580 network_stat_ref_file, | 507 "dc2d9f584efb0111ebcd71a2c86f1fb09cd8c2bb", |
| 581 rtcp_stat_ref_file); | 508 "", "", ""); |
| 582 } | 509 |
| 510 const std::string rtcp_stats_checksum = PlatformChecksum( | |
| 511 "e37c797e3de6a64dda88c9ade7a013d022a2e1e0", | |
| 512 "", "", ""); | |
| 513 | |
| 514 DecodeAndCompare(input_rtp_file, | |
| 515 output_checksum, | |
| 516 network_stats_checksum, | |
| 517 rtcp_stats_checksum, | |
| 518 FLAGS_gen_ref); | |
| 583 } | 519 } |
| 584 | 520 |
| 585 // Use fax mode to avoid time-scaling. This is to simplify the testing of | 521 // Use fax mode to avoid time-scaling. This is to simplify the testing of |
| 586 // packet waiting times in the packet buffer. | 522 // packet waiting times in the packet buffer. |
| 587 class NetEqDecodingTestFaxMode : public NetEqDecodingTest { | 523 class NetEqDecodingTestFaxMode : public NetEqDecodingTest { |
| 588 protected: | 524 protected: |
| 589 NetEqDecodingTestFaxMode() : NetEqDecodingTest() { | 525 NetEqDecodingTestFaxMode() : NetEqDecodingTest() { |
| 590 config_.playout_mode = kPlayoutFax; | 526 config_.playout_mode = kPlayoutFax; |
| 591 } | 527 } |
| 592 }; | 528 }; |
| (...skipping 978 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1571 timestamp += kSamples; | 1507 timestamp += kSamples; |
| 1572 | 1508 |
| 1573 // Pull audio once. | 1509 // Pull audio once. |
| 1574 ASSERT_EQ(0, neteq_->GetAudio(&out_frame_)); | 1510 ASSERT_EQ(0, neteq_->GetAudio(&out_frame_)); |
| 1575 ASSERT_EQ(kBlockSize16kHz, out_frame_.samples_per_channel_); | 1511 ASSERT_EQ(kBlockSize16kHz, out_frame_.samples_per_channel_); |
| 1576 } | 1512 } |
| 1577 // Verify speech output. | 1513 // Verify speech output. |
| 1578 EXPECT_EQ(AudioFrame::kNormalSpeech, out_frame_.speech_type_); | 1514 EXPECT_EQ(AudioFrame::kNormalSpeech, out_frame_.speech_type_); |
| 1579 } | 1515 } |
| 1580 } // namespace webrtc | 1516 } // namespace webrtc |
| OLD | NEW |