Chromium Code Reviews
|
| OLD | NEW |
|---|---|
| (Empty) | |
| 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | |
| 2 // Use of this source code is governed by a BSD-style license that can be | |
| 3 // found in the LICENSE file. | |
| 4 | |
| 5 #include <windows.h> | |
| 6 #include <mmsystem.h> | |
| 7 | |
| 8 #include "base/basictypes.h" | |
| 9 #include "base/environment.h" | |
| 10 #include "base/memory/scoped_ptr.h" | |
| 11 #include "base/message_loop.h" | |
| 12 #include "base/test/test_timeouts.h" | |
| 13 #include "base/time.h" | |
| 14 #include "base/win/scoped_com_initializer.h" | |
| 15 #include "media/audio/audio_io.h" | |
| 16 #include "media/audio/audio_manager.h" | |
| 17 #include "media/audio/win/audio_low_latency_output_win.h" | |
| 18 #include "media/base/seekable_buffer.h" | |
| 19 #include "media/base/test_data_util.h" | |
| 20 #include "testing/gmock_mutant.h" | |
| 21 #include "testing/gmock/include/gmock/gmock.h" | |
| 22 #include "testing/gtest/include/gtest/gtest.h" | |
| 23 | |
| 24 using ::testing::_; | |
| 25 using ::testing::AnyNumber; | |
| 26 using ::testing::Between; | |
| 27 using ::testing::CreateFunctor; | |
| 28 using ::testing::DoAll; | |
| 29 using ::testing::Gt; | |
| 30 using ::testing::InvokeWithoutArgs; | |
| 31 using ::testing::NotNull; | |
| 32 using ::testing::Return; | |
| 33 using base::win::ScopedCOMInitializer; | |
| 34 | |
| 35 namespace media { | |
| 36 | |
| 37 static const char kSpeechFile_16b_s_48k[] = "speech_16b_stereo_48kHz.raw"; | |
| 38 static const char kSpeechFile_16b_s_44k[] = "speech_16b_stereo_44kHz.raw"; | |
| 39 static const size_t kFileDurationMs = 20000; | |
| 40 | |
| 41 static const size_t kMaxDeltaSamples = 1000; | |
| 42 static const char* kDeltaTimeMsFileName = "delta_times_ms.txt"; | |
| 43 | |
| 44 MATCHER_P(HasValidDelay, value, "") { | |
| 45 // It is difficult to come up with a perfect test condition for the delay | |
| 46 // estimation. For now, verify that the produced output delay is always | |
| 47 // larger than the selected buffer size. | |
| 48 return arg.hardware_delay_bytes > value.hardware_delay_bytes; | |
| 49 } | |
| 50 | |
| 51 class MockAudioSourceCallback : public AudioOutputStream::AudioSourceCallback { | |
| 52 public: | |
| 53 MOCK_METHOD4(OnMoreData, uint32(AudioOutputStream* stream, | |
| 54 uint8* dest, | |
| 55 uint32 max_size, | |
| 56 AudioBuffersState buffers_state)); | |
| 57 MOCK_METHOD2(OnError, void(AudioOutputStream* stream, int code)); | |
| 58 }; | |
| 59 | |
| 60 // This audio source implementation should be used for manual tests only since | |
| 61 // it takes about 20 seconds to play out a file. | |
| 62 class ReadFromFileAudioSource : public AudioOutputStream::AudioSourceCallback { | |
| 63 public: | |
| 64 explicit ReadFromFileAudioSource(const std::string& name) | |
| 65 : pos_(0), | |
| 66 previous_call_time_(base::Time::Now()), | |
| 67 text_file_(fopen(kDeltaTimeMsFileName, "wt")), | |
|
Paweł Hajdan Jr.
2011/11/04 11:32:11
nit: Why not use base/file_util? Up to you, but I
tommi (sloooow) - chröme
2011/11/07 11:47:03
+1
henrika (OOO until Aug 14)
2011/11/07 14:09:45
Now uses base/file_util and base/path_service.
| |
| 68 elements_to_write_(0) { | |
| 69 // Reads a test file from media/test/data directory and stores it in | |
| 70 // a scoped_array. | |
| 71 ReadTestDataFile(name, &file_, &file_size_); | |
| 72 file_size_ = file_size_; | |
| 73 | |
| 74 // Creates an array that will store delta times between callbacks. | |
| 75 // The content of this array will be written to a text file at | |
| 76 // destruction and can then be used for off-line analysis of the exact | |
| 77 // timing of callbacks. | |
| 78 delta_times_.reset(new int[kMaxDeltaSamples]); | |
| 79 } | |
| 80 | |
| 81 virtual ~ReadFromFileAudioSource() { | |
| 82 // Write the array which contains delta times to a text file. | |
| 83 size_t elements_written = 0; | |
| 84 while (elements_written < elements_to_write_) { | |
| 85 fprintf(text_file_, "%d\n", delta_times_[elements_written]); | |
| 86 elements_written++; | |
|
tommi (sloooow) - chröme
2011/11/07 11:47:03
nit: ++elements_written
henrika (OOO until Aug 14)
2011/11/07 14:09:45
Big difference ;-)
Done.
| |
| 87 } | |
| 88 fclose(text_file_); | |
| 89 } | |
| 90 | |
| 91 // AudioOutputStream::AudioSourceCallback implementation. | |
| 92 virtual uint32 OnMoreData(AudioOutputStream* stream, | |
| 93 uint8* dest, | |
| 94 uint32 max_size, | |
| 95 AudioBuffersState buffers_state) { | |
| 96 // Store time difference between two successive callbacks in an array. | |
| 97 // These values will be written to a file in the destructor. | |
| 98 int diff = (base::Time::Now() - previous_call_time_).InMilliseconds(); | |
| 99 previous_call_time_ = base::Time::Now(); | |
| 100 if (elements_to_write_ < kMaxDeltaSamples) { | |
| 101 delta_times_[elements_to_write_] = diff; | |
| 102 elements_to_write_++; | |
|
tommi (sloooow) - chröme
2011/11/07 11:47:03
nit: and here
henrika (OOO until Aug 14)
2011/11/07 14:09:45
Done.
| |
| 103 } | |
| 104 | |
| 105 // Use samples read from a data file and fill up the audio buffer | |
| 106 // provided to us in the callback. | |
| 107 if (pos_ + static_cast<int>(max_size) > file_size_) | |
| 108 max_size = file_size_ - pos_; | |
| 109 if (max_size) { | |
| 110 memcpy(dest, &file_[pos_], max_size); | |
| 111 pos_ += max_size; | |
| 112 } | |
| 113 return max_size; | |
| 114 } | |
| 115 | |
| 116 virtual void OnError(AudioOutputStream* stream, int code) {} | |
| 117 | |
| 118 int file_size() { return file_size_; } | |
| 119 | |
| 120 private: | |
| 121 scoped_array<uint8> file_; | |
| 122 scoped_array<int> delta_times_; | |
| 123 int file_size_; | |
| 124 int pos_; | |
| 125 base::Time previous_call_time_; | |
| 126 FILE* text_file_; | |
| 127 size_t elements_to_write_; | |
| 128 }; | |
| 129 | |
| 130 // Convenience method which ensures that we are not running on the build | |
| 131 // bots and that at least one valid output device can be found. | |
| 132 static bool CanRunAudioTests() { | |
| 133 scoped_ptr<base::Environment> env(base::Environment::Create()); | |
| 134 if (env->HasVar("CHROME_HEADLESS")) | |
| 135 return false; | |
| 136 AudioManager* audio_man = AudioManager::GetAudioManager(); | |
| 137 if (NULL == audio_man) | |
| 138 return false; | |
| 139 // TODO(henrika): note that we use Wave today to query the number of | |
| 140 // existing output devices. | |
| 141 return audio_man->HasAudioOutputDevices(); | |
| 142 } | |
| 143 | |
| 144 // Convenience method which creates a default AudioOutputStream object but | |
| 145 // also allows the user to modify the default settings. | |
| 146 class AudioOutputStreamWrapper { | |
| 147 public: | |
| 148 AudioOutputStreamWrapper() | |
| 149 : com_init_(ScopedCOMInitializer::kMTA), | |
| 150 audio_man_(AudioManager::GetAudioManager()), | |
| 151 format_(AudioParameters::AUDIO_PCM_LOW_LATENCY), | |
| 152 channel_layout_(CHANNEL_LAYOUT_STEREO), | |
| 153 bits_per_sample_(16) { | |
| 154 // Use native/mixing sample rate and 10ms frame size as default. | |
| 155 sample_rate_ = static_cast<int>( | |
| 156 WASAPIAudioOutputStream::HardwareSampleRate(eConsole)); | |
| 157 samples_per_packet_ = sample_rate_ / 100; | |
| 158 DCHECK(sample_rate_); | |
| 159 } | |
| 160 | |
| 161 ~AudioOutputStreamWrapper() {} | |
| 162 | |
| 163 // Creates AudioOutputStream object using default parameters. | |
| 164 AudioOutputStream* Create() { | |
| 165 return CreateOutputStream(); | |
| 166 } | |
| 167 | |
| 168 // Creates AudioOutputStream object using non-default parameters where the | |
| 169 // frame size is modified. | |
| 170 AudioOutputStream* Create(int samples_per_packet) { | |
| 171 samples_per_packet_ = samples_per_packet; | |
| 172 return CreateOutputStream(); | |
| 173 } | |
| 174 | |
| 175 // Creates AudioOutputStream object using non-default parameters where the | |
| 176 // channel layout is modified. | |
| 177 AudioOutputStream* Create(ChannelLayout channel_layout) { | |
| 178 channel_layout_ = channel_layout; | |
| 179 return CreateOutputStream(); | |
| 180 } | |
| 181 | |
| 182 AudioParameters::Format format() const { return format_; } | |
| 183 int channels() const { return ChannelLayoutToChannelCount(channel_layout_); } | |
| 184 int bits_per_sample() const { return bits_per_sample_; } | |
| 185 int sample_rate() const { return sample_rate_; } | |
| 186 int samples_per_packet() const { return samples_per_packet_; } | |
| 187 | |
| 188 private: | |
| 189 AudioOutputStream* CreateOutputStream() { | |
| 190 AudioOutputStream* aos = audio_man_->MakeAudioOutputStream( | |
| 191 AudioParameters(format_, channel_layout_, sample_rate_, | |
| 192 bits_per_sample_, samples_per_packet_)); | |
| 193 EXPECT_TRUE(aos); | |
| 194 return aos; | |
| 195 } | |
| 196 | |
| 197 ScopedCOMInitializer com_init_; | |
| 198 AudioManager* audio_man_; | |
| 199 AudioParameters::Format format_; | |
| 200 ChannelLayout channel_layout_; | |
| 201 int bits_per_sample_; | |
| 202 int sample_rate_; | |
| 203 int samples_per_packet_; | |
| 204 }; | |
| 205 | |
| 206 // Convenience method which creates a default AudioOutputStream object. | |
| 207 static AudioOutputStream* CreateDefaultAudioOutputStream() { | |
| 208 AudioOutputStreamWrapper aosw; | |
| 209 AudioOutputStream* aos = aosw.Create(); | |
| 210 return aos; | |
| 211 } | |
| 212 | |
| 213 static void QuitMessageLoop(base::MessageLoopProxy* proxy) { | |
| 214 proxy->PostTask(FROM_HERE, new MessageLoop::QuitTask()); | |
| 215 } | |
| 216 | |
| 217 // Verify that we can retrieve the current hardware/mixing sample rate | |
| 218 // for all supported device roles. The ERole enumeration defines constants | |
| 219 // that indicate the role that the system/user has assigned to an audio | |
| 220 // endpoint device. | |
| 221 // TODO(henrika): modify this test when we support full device enumeration. | |
| 222 TEST(WinAudioOutputTest, WASAPIAudioOutputStreamTestHardwareSampleRate) { | |
| 223 if (!CanRunAudioTests()) | |
| 224 return; | |
| 225 | |
| 226 ScopedCOMInitializer com_init(ScopedCOMInitializer::kMTA); | |
| 227 | |
| 228 // Default device intended for games, system notification sounds, | |
| 229 // and voice commands. | |
| 230 int fs = static_cast<int>( | |
| 231 WASAPIAudioOutputStream::HardwareSampleRate(eConsole)); | |
| 232 EXPECT_GE(fs, 0); | |
| 233 | |
| 234 // Default communication device intended for e.g. VoIP communication. | |
| 235 fs = static_cast<int>( | |
| 236 WASAPIAudioOutputStream::HardwareSampleRate(eCommunications)); | |
| 237 EXPECT_GE(fs, 0); | |
| 238 | |
| 239 // Multimedia device for music, movies and live music recording. | |
| 240 fs = static_cast<int>( | |
| 241 WASAPIAudioOutputStream::HardwareSampleRate(eMultimedia)); | |
| 242 EXPECT_GE(fs, 0); | |
| 243 } | |
| 244 | |
| 245 // Test Create(), Close() calling sequence. | |
| 246 TEST(WinAudioOutputTest, WASAPIAudioOutputStreamTestCreateAndClose) { | |
| 247 if (!CanRunAudioTests()) | |
| 248 return; | |
| 249 AudioOutputStream* aos = CreateDefaultAudioOutputStream(); | |
| 250 aos->Close(); | |
| 251 } | |
| 252 | |
| 253 // Test Open(), Close() calling sequence. | |
| 254 TEST(WinAudioOutputTest, WASAPIAudioOutputStreamTestOpenAndClose) { | |
| 255 if (!CanRunAudioTests()) | |
| 256 return; | |
| 257 AudioOutputStream* aos = CreateDefaultAudioOutputStream(); | |
| 258 EXPECT_TRUE(aos->Open()); | |
| 259 aos->Close(); | |
| 260 } | |
| 261 | |
| 262 // Test Open(), Start(), Close() calling sequence. | |
| 263 TEST(WinAudioOutputTest, WASAPIAudioOutputStreamTestOpenStartAndClose) { | |
| 264 if (!CanRunAudioTests()) | |
| 265 return; | |
| 266 AudioOutputStream* aos = CreateDefaultAudioOutputStream(); | |
| 267 EXPECT_TRUE(aos->Open()); | |
| 268 MockAudioSourceCallback source; | |
| 269 EXPECT_CALL(source, OnError(aos, _)) | |
| 270 .Times(0); | |
| 271 aos->Start(&source); | |
| 272 aos->Close(); | |
| 273 } | |
| 274 | |
| 275 // Test Open(), Start(), Stop(), Close() calling sequence. | |
| 276 TEST(WinAudioOutputTest, WASAPIAudioOutputStreamTestOpenStartStopAndClose) { | |
| 277 if (!CanRunAudioTests()) | |
| 278 return; | |
| 279 AudioOutputStream* aos = CreateDefaultAudioOutputStream(); | |
| 280 EXPECT_TRUE(aos->Open()); | |
| 281 MockAudioSourceCallback source; | |
| 282 EXPECT_CALL(source, OnError(aos, _)) | |
| 283 .Times(0); | |
| 284 aos->Start(&source); | |
| 285 aos->Stop(); | |
| 286 aos->Close(); | |
| 287 } | |
| 288 | |
| 289 // Test SetVolume(), GetVolume() | |
| 290 TEST(WinAudioOutputTest, WASAPIAudioOutputStreamTestVolume) { | |
| 291 if (!CanRunAudioTests()) | |
| 292 return; | |
| 293 AudioOutputStream* aos = CreateDefaultAudioOutputStream(); | |
| 294 | |
| 295 // Initial volume should be full volume (1.0). | |
| 296 double volume = 0.0; | |
| 297 aos->GetVolume(&volume); | |
| 298 EXPECT_TRUE(volume == 1.0); | |
|
tommi (sloooow) - chröme
2011/11/07 11:47:03
EXPECT_EQ (below too)
henrika (OOO until Aug 14)
2011/11/07 14:09:45
Done.
| |
| 299 | |
| 300 // Verify some valid volume settings. | |
| 301 aos->SetVolume(0.0); | |
| 302 aos->GetVolume(&volume); | |
| 303 EXPECT_TRUE(volume == 0.0); | |
| 304 | |
| 305 aos->SetVolume(0.5); | |
| 306 aos->GetVolume(&volume); | |
| 307 EXPECT_TRUE(volume == 0.5); | |
| 308 | |
| 309 aos->SetVolume(1.0); | |
| 310 aos->GetVolume(&volume); | |
| 311 EXPECT_TRUE(volume == 1.0); | |
| 312 | |
| 313 // Ensure that invalid volume setting have no effect. | |
| 314 aos->SetVolume(1.5); | |
| 315 aos->GetVolume(&volume); | |
| 316 EXPECT_TRUE(volume == 1.0); | |
| 317 | |
| 318 aos->SetVolume(-0.5); | |
| 319 aos->GetVolume(&volume); | |
| 320 EXPECT_TRUE(volume == 1.0); | |
| 321 | |
| 322 aos->Close(); | |
| 323 } | |
| 324 | |
| 325 // Test some additional calling sequences. | |
| 326 TEST(WinAudioOutputTest, WASAPIAudioOutputStreamTestMiscCallingSequences) { | |
| 327 if (!CanRunAudioTests()) | |
| 328 return; | |
| 329 AudioOutputStream* aos = CreateDefaultAudioOutputStream(); | |
| 330 WASAPIAudioOutputStream* waos = static_cast<WASAPIAudioOutputStream*>(aos); | |
| 331 | |
| 332 // Open(), Open() should fail the second time. | |
| 333 EXPECT_TRUE(aos->Open()); | |
| 334 EXPECT_FALSE(aos->Open()); | |
|
tommi (sloooow) - chröme
2011/11/07 11:47:03
It is a bit confusing that Open fails the second t
henrika (OOO until Aug 14)
2011/11/07 14:09:45
Good point. Modified. Second call to Open() now re
| |
| 335 | |
| 336 MockAudioSourceCallback source; | |
| 337 | |
| 338 // Start(), Start() is a valid calling sequence (second call does nothing). | |
| 339 aos->Start(&source); | |
| 340 EXPECT_TRUE(waos->started()); | |
| 341 aos->Start(&source); | |
| 342 EXPECT_TRUE(waos->started()); | |
| 343 | |
| 344 // Stop(), Stop() is a valid calling sequence (second call does nothing). | |
| 345 aos->Stop(); | |
| 346 EXPECT_FALSE(waos->started()); | |
| 347 aos->Stop(); | |
| 348 EXPECT_FALSE(waos->started()); | |
| 349 | |
| 350 aos->Close(); | |
| 351 } | |
| 352 | |
| 353 // Use default packet size (10ms) and verify that rendering starts. | |
| 354 TEST(WinAudioOutputTest, WASAPIAudioOutputStreamTestPacketSizeInMilliseconds) { | |
| 355 if (!CanRunAudioTests()) | |
| 356 return; | |
| 357 | |
| 358 MessageLoopForUI loop; | |
| 359 scoped_refptr<base::MessageLoopProxy> proxy(loop.message_loop_proxy()); | |
| 360 | |
| 361 MockAudioSourceCallback source; | |
| 362 | |
| 363 // Create default WASAPI output stream which plays out in stereo using | |
| 364 // the shared mixing rate. The default buffer size is 10ms. | |
| 365 AudioOutputStreamWrapper aosw; | |
| 366 AudioOutputStream* aos = aosw.Create(); | |
| 367 EXPECT_TRUE(aos->Open()); | |
| 368 | |
| 369 // Derive the expected size in bytes of each packet. | |
| 370 uint32 bytes_per_packet = aosw.channels() * aosw.samples_per_packet() * | |
| 371 (aosw.bits_per_sample() / 8); | |
| 372 | |
| 373 // Set up expected minimum delay estimation. | |
| 374 AudioBuffersState state(0, bytes_per_packet); | |
| 375 | |
| 376 // Wait for the first callback and verify its parameters. | |
| 377 EXPECT_CALL(source, OnMoreData(aos, NotNull(), bytes_per_packet, | |
| 378 HasValidDelay(state))) | |
| 379 .WillOnce( | |
| 380 DoAll( | |
| 381 InvokeWithoutArgs( | |
| 382 CreateFunctor(&QuitMessageLoop, proxy.get())), | |
| 383 Return(bytes_per_packet))); | |
| 384 | |
| 385 aos->Start(&source); | |
| 386 loop.PostDelayedTask(FROM_HERE, new MessageLoop::QuitTask(), | |
| 387 TestTimeouts::action_timeout_ms()); | |
| 388 loop.Run(); | |
| 389 aos->Stop(); | |
| 390 aos->Close(); | |
| 391 } | |
| 392 | |
| 393 // Use a fixed packets size (independent of sample rate) and verify | |
| 394 // that rendering starts. | |
| 395 TEST(WinAudioOutputTest, WASAPIAudioOutputStreamTestPacketSizeInSamples) { | |
| 396 if (!CanRunAudioTests()) | |
| 397 return; | |
| 398 | |
| 399 MessageLoopForUI loop; | |
| 400 scoped_refptr<base::MessageLoopProxy> proxy(loop.message_loop_proxy()); | |
| 401 | |
| 402 MockAudioSourceCallback source; | |
| 403 | |
| 404 // Create default WASAPI output stream which plays out in stereo using | |
| 405 // the shared mixing rate. The buffer size is set to 1024 samples. | |
| 406 AudioOutputStreamWrapper aosw; | |
| 407 AudioOutputStream* aos = aosw.Create(1024); | |
| 408 EXPECT_TRUE(aos->Open()); | |
| 409 | |
| 410 // Derive the expected size in bytes of each packet. | |
| 411 uint32 bytes_per_packet = aosw.channels() * aosw.samples_per_packet() * | |
| 412 (aosw.bits_per_sample() / 8); | |
| 413 | |
| 414 // Set up expected minimum delay estimation. | |
| 415 AudioBuffersState state(0, bytes_per_packet); | |
| 416 | |
| 417 // Wait for the first callback and verify its parameters. | |
| 418 EXPECT_CALL(source, OnMoreData(aos, NotNull(), bytes_per_packet, | |
| 419 HasValidDelay(state))) | |
| 420 .WillOnce( | |
| 421 DoAll( | |
| 422 InvokeWithoutArgs( | |
| 423 CreateFunctor(&QuitMessageLoop, proxy.get())), | |
| 424 Return(bytes_per_packet))); | |
| 425 | |
| 426 aos->Start(&source); | |
| 427 loop.PostDelayedTask(FROM_HERE, new MessageLoop::QuitTask(), | |
| 428 TestTimeouts::action_timeout_ms()); | |
| 429 loop.Run(); | |
| 430 aos->Stop(); | |
| 431 aos->Close(); | |
| 432 } | |
| 433 | |
| 434 TEST(WinAudioOutputTest, WASAPIAudioOutputStreamTestMono) { | |
| 435 if (!CanRunAudioTests()) | |
| 436 return; | |
| 437 | |
| 438 MessageLoopForUI loop; | |
| 439 scoped_refptr<base::MessageLoopProxy> proxy(loop.message_loop_proxy()); | |
| 440 | |
| 441 MockAudioSourceCallback source; | |
| 442 | |
| 443 // Create default WASAPI output stream which plays out in *mono* using | |
| 444 // the shared mixing rate. The default buffer size is 10ms. | |
| 445 AudioOutputStreamWrapper aosw; | |
| 446 AudioOutputStream* aos = aosw.Create(CHANNEL_LAYOUT_MONO); | |
| 447 EXPECT_TRUE(aos->Open()); | |
| 448 | |
| 449 // Derive the expected size in bytes of each packet. | |
| 450 uint32 bytes_per_packet = aosw.channels() * aosw.samples_per_packet() * | |
| 451 (aosw.bits_per_sample() / 8); | |
| 452 | |
| 453 // Set up expected minimum delay estimation. | |
| 454 AudioBuffersState state(0, bytes_per_packet); | |
| 455 | |
| 456 EXPECT_CALL(source, OnMoreData(aos, NotNull(), bytes_per_packet, | |
| 457 HasValidDelay(state))) | |
| 458 .WillOnce( | |
| 459 DoAll( | |
| 460 InvokeWithoutArgs( | |
| 461 CreateFunctor(&QuitMessageLoop, proxy.get())), | |
| 462 Return(bytes_per_packet))); | |
| 463 | |
| 464 aos->Start(&source); | |
| 465 loop.PostDelayedTask(FROM_HERE, new MessageLoop::QuitTask(), | |
| 466 TestTimeouts::action_timeout_ms()); | |
| 467 loop.Run(); | |
| 468 aos->Stop(); | |
| 469 aos->Close(); | |
| 470 } | |
| 471 | |
| 472 // This test is intended for manual tests and should only be enabled | |
| 473 // when it is required to store the captured data on a local file. | |
| 474 // By default, GTest will print out YOU HAVE 1 DISABLED TEST. | |
| 475 // To include disabled tests in test execution, just invoke the test program | |
| 476 // with --gtest_also_run_disabled_tests or set the GTEST_ALSO_RUN_DISABLED_TESTS | |
| 477 // environment variable to a value greater than 0. | |
| 478 // The test files are approximately 20 seconds long. | |
| 479 TEST(WinAudioOutputTest, DISABLED_WASAPIAudioOutputStreamReadFromFile) { | |
|
tommi (sloooow) - chröme
2011/11/07 11:47:03
Is it necessary to have the test disabled since it
henrika (OOO until Aug 14)
2011/11/07 14:09:45
Please advice. I figured that it was not OK to add
tommi (sloooow) - chröme
2011/11/07 17:37:17
Nope, you're right, 20 seconds is too long. But d
| |
| 480 if (!CanRunAudioTests()) | |
| 481 return; | |
| 482 | |
| 483 AudioOutputStreamWrapper aosw; | |
| 484 AudioOutputStream* aos = aosw.Create(); | |
| 485 EXPECT_TRUE(aos->Open()); | |
| 486 | |
| 487 std::string file_name; | |
| 488 if (aosw.sample_rate() == 48000) { | |
| 489 file_name = kSpeechFile_16b_s_48k; | |
| 490 } else if (aosw.sample_rate() == 44100) { | |
| 491 file_name = kSpeechFile_16b_s_44k; | |
| 492 } else if (aosw.sample_rate() == 96000) { | |
| 493 // Use 48kHz file at 96kHz as well. Will sound as Donald Duck. | |
| 494 file_name = kSpeechFile_16b_s_48k; | |
| 495 } else { | |
| 496 fprintf(stderr, "This test supports 44.1, 48kHz and 96kHz only.\n"); | |
|
Paweł Hajdan Jr.
2011/11/04 11:32:11
Don't you want the test to fail then?
FAIL() << "
henrika (OOO until Aug 14)
2011/11/07 14:09:45
Fixed. Thanks.
| |
| 497 return; | |
| 498 } | |
| 499 ReadFromFileAudioSource file_source(file_name); | |
| 500 int file_duration_ms = kFileDurationMs; | |
| 501 | |
| 502 fprintf(stderr, " File name : %s\n", file_name.c_str()); | |
|
Paweł Hajdan Jr.
2011/11/04 11:32:11
nit: I think you should generally use LOG in favor
tommi (sloooow) - chröme
2011/11/07 11:47:03
+1
henrika (OOO until Aug 14)
2011/11/07 14:09:45
Done.
| |
| 503 fprintf(stderr, " Sample rate: %d\n", aosw.sample_rate()); | |
| 504 fprintf(stderr, " File size : %d\n", file_source.file_size()); | |
| 505 fprintf(stderr, " >> Listen to the file while playing...\n"); | |
| 506 | |
| 507 aos->Start(&file_source); | |
| 508 base::PlatformThread::Sleep(file_duration_ms); | |
| 509 aos->Stop(); | |
| 510 | |
| 511 fprintf(stderr, " >> File playout has stopped.\n"); | |
| 512 aos->Close(); | |
| 513 } | |
| 514 | |
| 515 } // namespace media | |
| OLD | NEW |