OLD | NEW |
(Empty) | |
| 1 // Copyright (c) 2012 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 "base/memory/scoped_ptr.h" |
| 6 #include "base/synchronization/waitable_event.h" |
| 7 #include "base/win/scoped_com_initializer.h" |
| 8 #include "media/audio/win/core_audio_util_win.h" |
| 9 #include "testing/gmock/include/gmock/gmock.h" |
| 10 #include "testing/gtest/include/gtest/gtest.h" |
| 11 |
| 12 using base::win::ScopedCOMInitializer; |
| 13 |
| 14 namespace media { |
| 15 |
| 16 class CoreAudioUtilWinTest : public ::testing::Test { |
| 17 protected: |
| 18 // The test runs on a COM thread in the multithreaded apartment (MTA). |
| 19 // If we don't initialize the COM library on a thread before using COM, |
| 20 // all function calls will return CO_E_NOTINITIALIZED. |
| 21 CoreAudioUtilWinTest() |
| 22 : com_init_(ScopedCOMInitializer::kMTA) { |
| 23 DCHECK(com_init_.succeeded()); |
| 24 } |
| 25 virtual ~CoreAudioUtilWinTest() {} |
| 26 |
| 27 bool CanRunAudioTest() { |
| 28 bool core_audio = CoreAudioUtil::IsSupported(); |
| 29 if (!core_audio) |
| 30 return false; |
| 31 int capture_devices = CoreAudioUtil::NumberOfActiveDevices(eCapture); |
| 32 int render_devices = CoreAudioUtil::NumberOfActiveDevices(eRender); |
| 33 return ((capture_devices > 0) && (render_devices > 0)); |
| 34 } |
| 35 |
| 36 ScopedCOMInitializer com_init_; |
| 37 }; |
| 38 |
| 39 TEST_F(CoreAudioUtilWinTest, NumberOfActiveDevices) { |
| 40 if (!CanRunAudioTest()) |
| 41 return; |
| 42 |
| 43 int render_devices = CoreAudioUtil::NumberOfActiveDevices(eRender); |
| 44 EXPECT_GT(render_devices, 0); |
| 45 int capture_devices = CoreAudioUtil::NumberOfActiveDevices(eCapture); |
| 46 EXPECT_GT(capture_devices, 0); |
| 47 int total_devices = CoreAudioUtil::NumberOfActiveDevices(eAll); |
| 48 EXPECT_EQ(total_devices, render_devices + capture_devices); |
| 49 } |
| 50 |
| 51 TEST_F(CoreAudioUtilWinTest, CreateDeviceEnumerator) { |
| 52 if (!CanRunAudioTest()) |
| 53 return; |
| 54 |
| 55 ScopedComPtr<IMMDeviceEnumerator> enumerator = |
| 56 CoreAudioUtil::CreateDeviceEnumerator(); |
| 57 EXPECT_TRUE(enumerator); |
| 58 } |
| 59 |
| 60 TEST_F(CoreAudioUtilWinTest, CreateDefaultDevice) { |
| 61 if (!CanRunAudioTest()) |
| 62 return; |
| 63 |
| 64 struct { |
| 65 EDataFlow flow; |
| 66 ERole role; |
| 67 } data[] = { |
| 68 {eRender, eConsole}, |
| 69 {eRender, eCommunications}, |
| 70 {eRender, eMultimedia}, |
| 71 {eCapture, eConsole}, |
| 72 {eCapture, eCommunications}, |
| 73 {eCapture, eMultimedia} |
| 74 }; |
| 75 |
| 76 // Create default devices for all flow/role combinations above. |
| 77 ScopedComPtr<IMMDevice> audio_device; |
| 78 for (int i = 0; i < arraysize(data); ++i) { |
| 79 audio_device = |
| 80 CoreAudioUtil::CreateDefaultDevice(data[i].flow, data[i].role); |
| 81 EXPECT_TRUE(audio_device); |
| 82 EXPECT_EQ(data[i].flow, CoreAudioUtil::GetDataFlow(audio_device)); |
| 83 } |
| 84 |
| 85 // Only eRender and eCapture are allowed as flow parameter. |
| 86 audio_device = CoreAudioUtil::CreateDefaultDevice(eAll, eConsole); |
| 87 EXPECT_FALSE(audio_device); |
| 88 } |
| 89 |
| 90 TEST_F(CoreAudioUtilWinTest, CreateDevice) { |
| 91 if (!CanRunAudioTest()) |
| 92 return; |
| 93 |
| 94 // Get name and ID of default device used for playback. |
| 95 ScopedComPtr<IMMDevice> default_render_device = |
| 96 CoreAudioUtil::CreateDefaultDevice(eRender, eConsole); |
| 97 AudioDeviceName default_render_name; |
| 98 EXPECT_TRUE(SUCCEEDED(CoreAudioUtil::GetDeviceName(default_render_device, |
| 99 &default_render_name))); |
| 100 |
| 101 // Use the uniqe ID as input to CreateDevice() and create a corresponding |
| 102 // IMMDevice. |
| 103 ScopedComPtr<IMMDevice> audio_device = |
| 104 CoreAudioUtil::CreateDevice(default_render_name.unique_id); |
| 105 EXPECT_TRUE(audio_device); |
| 106 |
| 107 // Verify that the two IMMDevice interfaces represents the same endpoint |
| 108 // by comparing their unique IDs. |
| 109 AudioDeviceName device_name; |
| 110 EXPECT_TRUE(SUCCEEDED(CoreAudioUtil::GetDeviceName(audio_device, |
| 111 &device_name))); |
| 112 EXPECT_EQ(default_render_name.unique_id, device_name.unique_id); |
| 113 } |
| 114 |
| 115 TEST_F(CoreAudioUtilWinTest, GetDefaultDeviceName) { |
| 116 if (!CanRunAudioTest()) |
| 117 return; |
| 118 |
| 119 struct { |
| 120 EDataFlow flow; |
| 121 ERole role; |
| 122 } data[] = { |
| 123 {eRender, eConsole}, |
| 124 {eRender, eCommunications}, |
| 125 {eCapture, eConsole}, |
| 126 {eCapture, eCommunications} |
| 127 }; |
| 128 |
| 129 // Get name and ID of default devices for all flow/role combinations above. |
| 130 ScopedComPtr<IMMDevice> audio_device; |
| 131 AudioDeviceName device_name; |
| 132 for (int i = 0; i < arraysize(data); ++i) { |
| 133 audio_device = |
| 134 CoreAudioUtil::CreateDefaultDevice(data[i].flow, data[i].role); |
| 135 EXPECT_TRUE(SUCCEEDED(CoreAudioUtil::GetDeviceName(audio_device, |
| 136 &device_name))); |
| 137 EXPECT_FALSE(device_name.device_name.empty()); |
| 138 EXPECT_FALSE(device_name.unique_id.empty()); |
| 139 } |
| 140 } |
| 141 |
| 142 TEST_F(CoreAudioUtilWinTest, GetFriendlyName) { |
| 143 if (!CanRunAudioTest()) |
| 144 return; |
| 145 |
| 146 // Get name and ID of default device used for recording. |
| 147 ScopedComPtr<IMMDevice> audio_device = |
| 148 CoreAudioUtil::CreateDefaultDevice(eCapture, eConsole); |
| 149 AudioDeviceName device_name; |
| 150 HRESULT hr = CoreAudioUtil::GetDeviceName(audio_device, &device_name); |
| 151 EXPECT_TRUE(SUCCEEDED(hr)); |
| 152 |
| 153 // Use unique ID as input to GetFriendlyName() and compare the result |
| 154 // with the already obtained friendly name for the default capture device. |
| 155 std::string friendly_name = CoreAudioUtil::GetFriendlyName( |
| 156 device_name.unique_id); |
| 157 EXPECT_EQ(friendly_name, device_name.device_name); |
| 158 |
| 159 // Same test as above but for playback. |
| 160 audio_device = CoreAudioUtil::CreateDefaultDevice(eRender, eConsole); |
| 161 hr = CoreAudioUtil::GetDeviceName(audio_device, &device_name); |
| 162 EXPECT_TRUE(SUCCEEDED(hr)); |
| 163 friendly_name = CoreAudioUtil::GetFriendlyName(device_name.unique_id); |
| 164 EXPECT_EQ(friendly_name, device_name.device_name); |
| 165 } |
| 166 |
| 167 TEST_F(CoreAudioUtilWinTest, DeviceIsDefault) { |
| 168 if (!CanRunAudioTest()) |
| 169 return; |
| 170 |
| 171 // Verify that the default render device is correctly identified as a |
| 172 // default device. |
| 173 ScopedComPtr<IMMDevice> audio_device = |
| 174 CoreAudioUtil::CreateDefaultDevice(eRender, eConsole); |
| 175 AudioDeviceName name; |
| 176 EXPECT_TRUE(SUCCEEDED(CoreAudioUtil::GetDeviceName(audio_device, &name))); |
| 177 const std::string id = name.unique_id; |
| 178 EXPECT_TRUE(CoreAudioUtil::DeviceIsDefault(eRender, eConsole, id)); |
| 179 EXPECT_FALSE(CoreAudioUtil::DeviceIsDefault(eCapture, eConsole, id)); |
| 180 } |
| 181 |
| 182 TEST_F(CoreAudioUtilWinTest, CreateClient) { |
| 183 if (!CanRunAudioTest()) |
| 184 return; |
| 185 |
| 186 EDataFlow data[] = {eRender, eCapture}; |
| 187 ScopedComPtr<IMMDevice> device; |
| 188 |
| 189 for (int i = 0; i < arraysize(data); ++i) { |
| 190 device = CoreAudioUtil::CreateDefaultDevice(data[i], eConsole); |
| 191 EXPECT_TRUE(device); |
| 192 EXPECT_EQ(data[i], CoreAudioUtil::GetDataFlow(device)); |
| 193 } |
| 194 } |
| 195 |
| 196 } // namespace media |
OLD | NEW |