Chromium Code Reviews| OLD | NEW |
|---|---|
| (Empty) | |
| 1 // Copyright (c) 2016 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 <stdint.h> | |
| 6 #include <string> | |
| 7 | |
| 8 #include "base/bind.h" | |
| 9 #include "base/command_line.h" | |
| 10 #include "content/browser/media/audio_output_impl.h" | |
| 11 #include "content/browser/media/audio_output_stream_impl.h" | |
| 12 #include "content/browser/media/capture/audio_mirroring_manager.h" | |
| 13 #include "content/browser/media/media_internals.h" | |
| 14 #include "content/browser/renderer_host/media/media_stream_manager.h" | |
| 15 #include "content/public/test/test_browser_thread_bundle.h" | |
| 16 #include "media/audio/audio_manager.h" | |
| 17 #include "media/base/media_switches.h" | |
| 18 #include "media/mojo/interfaces/audio_output.mojom.h" | |
| 19 #include "testing/gmock/include/gmock/gmock.h" | |
| 20 #include "testing/gtest/include/gtest/gtest.h" | |
| 21 | |
| 22 using ::testing::_; | |
| 23 using ::testing::Return; | |
| 24 | |
| 25 namespace content { | |
| 26 | |
| 27 namespace { | |
| 28 | |
| 29 const int kRenderFrameId1 = 5; | |
| 30 const int kRenderFrameId2 = 3; | |
| 31 const int kStreamId1 = 9; | |
| 32 const int kStreamId2 = 20; | |
| 33 | |
| 34 const int kStreamIds[] = {800, 2, 30, 22}; | |
| 35 const unsigned int kStreamIdsSize = 4; | |
| 36 const int kRenderProcessId = 1; | |
| 37 | |
| 38 std::string ReturnMockSalt() { | |
| 39 return std::string(); | |
| 40 } | |
| 41 | |
| 42 ResourceContext::SaltCallback GetMockSaltCallback() { | |
| 43 return base::Bind(&ReturnMockSalt); | |
| 44 } | |
| 45 } | |
| 46 | |
| 47 class MockAudioOutputStreamImpl : public AudioOutputStreamImpl { | |
| 48 public: | |
| 49 explicit MockAudioOutputStreamImpl( | |
| 50 media::mojom::AudioOutputStreamRequest request, | |
| 51 int stream_id, | |
| 52 int renderer_frame_id, | |
| 53 AudioRendererHost* audio_renderer_host) | |
| 54 : AudioOutputStreamImpl(std::move(request), | |
| 55 stream_id, | |
| 56 renderer_frame_id, | |
| 57 audio_renderer_host) {} | |
| 58 MOCK_METHOD0(Close, void()); | |
| 59 }; | |
| 60 | |
| 61 class MockAudioRendererHost : public AudioRendererHost { | |
| 62 public: | |
| 63 MockAudioRendererHost(int render_process_id, | |
| 64 media::AudioManager* audio_manager, | |
| 65 AudioMirroringManager* mirroring_manager, | |
| 66 MediaInternals* media_internals, | |
| 67 MediaStreamManager* media_stream_manager, | |
| 68 const ResourceContext::SaltCallback& salt_callback) | |
| 69 : AudioRendererHost(render_process_id, | |
| 70 audio_manager, | |
| 71 mirroring_manager, | |
| 72 media_internals, | |
| 73 media_stream_manager, | |
| 74 salt_callback) {} | |
| 75 | |
| 76 MOCK_METHOD1(CloseStream, void(int stream_id)); | |
| 77 MOCK_METHOD4( | |
| 78 CreateStream, | |
| 79 void(int stream_id, | |
| 80 int render_frame_id, | |
| 81 const media::AudioParameters& params, | |
| 82 const media::mojom::AudioOutput::CreateStreamCallback& callback)); | |
| 83 | |
| 84 MOCK_METHOD2( | |
| 85 DoCompleteCreation, | |
| 86 void(int stream_id, | |
| 87 const media::mojom::AudioOutput::CreateStreamCallback& callback)); | |
| 88 MOCK_METHOD2(set_audio_output_impl, | |
| 89 void(int render_frame_id, AudioOutputImpl* audio_output_impl)); | |
| 90 | |
| 91 protected: | |
| 92 FRIEND_TEST_ALL_PREFIXES(AudioOutputImplTest, CreateServiceOnIOThread); | |
| 93 FRIEND_TEST_ALL_PREFIXES(AudioOutputImplTest, CreateStream); | |
| 94 friend class AudioOutputImplTest; | |
| 95 virtual ~MockAudioRendererHost() {} | |
| 96 | |
| 97 private: | |
| 98 DISALLOW_COPY_AND_ASSIGN(MockAudioRendererHost); | |
| 99 }; | |
| 100 | |
| 101 class AudioOutputImplTest : public ::testing::Test { | |
| 102 public: | |
| 103 AudioOutputImplTest() { | |
| 104 audio_manager_ = media::AudioManager::CreateForTesting( | |
| 105 base::ThreadTaskRunnerHandle::Get()); | |
| 106 | |
| 107 base::CommandLine::ForCurrentProcess()->AppendSwitch( | |
| 108 switches::kUseFakeDeviceForMediaStream); | |
| 109 media_stream_manager_.reset(new MediaStreamManager(audio_manager_.get())); | |
| 110 | |
| 111 // Enable caching to make enumerations run in a single thread | |
| 112 media_stream_manager_->audio_output_device_enumerator()->SetCachePolicy( | |
| 113 AudioOutputDeviceEnumerator::CACHE_POLICY_MANUAL_INVALIDATION); | |
| 114 | |
| 115 audio_renderer_host_ = new MockAudioRendererHost( | |
| 116 kRenderProcessId, audio_manager_.get(), &mirroring_manager_, | |
| 117 MediaInternals::GetInstance(), media_stream_manager_.get(), | |
| 118 GetMockSaltCallback()); | |
| 119 } | |
| 120 void CreateCallback(int stream_id, | |
| 121 media::mojom::AudioOutputStreamPtr stream, | |
| 122 mojo::ScopedSharedBufferHandle shared_buffer, | |
| 123 mojo::ScopedHandle socket_descriptor) {} | |
| 124 | |
| 125 ~AudioOutputImplTest() override {} | |
| 126 | |
| 127 private: | |
| 128 std::unique_ptr<MediaStreamManager> media_stream_manager_; | |
| 129 TestBrowserThreadBundle thread_bundle_; | |
| 130 media::ScopedAudioManagerPtr audio_manager_; | |
| 131 AudioMirroringManager mirroring_manager_; | |
| 132 | |
| 133 protected: | |
| 134 MockAudioRendererHost* audio_renderer_host_; | |
| 135 std::unique_ptr<base::MessageLoop> message_loop_; | |
| 136 | |
| 137 DISALLOW_COPY_AND_ASSIGN(AudioOutputImplTest); | |
| 138 }; | |
| 139 | |
| 140 TEST_F(AudioOutputImplTest, CreateStream) { | |
| 141 auto callback = | |
| 142 base::Bind(&AudioOutputImplTest::CreateCallback, base::Unretained(this)); | |
| 143 | |
| 144 media::AudioParameters params( | |
| 145 media::AudioParameters::AUDIO_FAKE, media::CHANNEL_LAYOUT_STEREO, | |
| 146 media::AudioParameters::kAudioCDSampleRate, 16, | |
| 147 media::AudioParameters::kAudioCDSampleRate / 10); | |
| 148 | |
| 149 EXPECT_CALL(*audio_renderer_host_, | |
| 150 CreateStream(kStreamId1, kRenderFrameId1, _, _)) | |
| 151 .Times(1); | |
| 152 | |
| 153 AudioOutputImpl audio_output_impl1(audio_renderer_host_, kRenderFrameId1, | |
| 154 media::mojom::AudioOutputRequest()); | |
| 155 audio_output_impl1.CreateStream(kStreamId1, params, callback); | |
| 156 | |
| 157 EXPECT_CALL(*audio_renderer_host_, | |
| 158 CreateStream(kStreamId2, kRenderFrameId2, _, _)) | |
| 159 .Times(1); | |
| 160 | |
| 161 AudioOutputImpl audio_output_impl2(audio_renderer_host_, kRenderFrameId2, | |
| 162 media::mojom::AudioOutputRequest()); | |
| 163 audio_output_impl2.CreateStream(kStreamId2, params, callback); | |
| 164 } | |
| 165 | |
| 166 TEST_F(AudioOutputImplTest, StreamFactory) { | |
| 167 AudioOutputImpl audio_output_impl(audio_renderer_host_, kRenderFrameId1, | |
| 168 media::mojom::AudioOutputRequest()); | |
| 169 EXPECT_EQ(0u, audio_output_impl.stream_impls_.size()); | |
| 170 unsigned int i = 0; | |
|
tommi (sloooow) - chröme
2016/05/20 13:26:12
we don't use "unsigned int"
| |
| 171 for (i = 0; i < kStreamIdsSize; i++) { | |
|
tommi (sloooow) - chröme
2016/05/20 13:26:12
also 'i' should be declared for the scope it's use
| |
| 172 auto stream = audio_output_impl.StreamFactory( | |
| 173 kStreamIds[i], kRenderFrameId1, audio_renderer_host_); | |
| 174 EXPECT_TRUE(stream.is_bound()); | |
| 175 EXPECT_NE(audio_output_impl.stream_impls_.end(), | |
| 176 audio_output_impl.stream_impls_.find(kStreamIds[i])); | |
| 177 EXPECT_EQ(kStreamIds[i], | |
| 178 audio_output_impl.stream_impls_[kStreamIds[i]]->get_stream_id()); | |
| 179 | |
| 180 EXPECT_EQ(i + 1, audio_output_impl.stream_impls_.size()); | |
| 181 } | |
| 182 } | |
| 183 | |
| 184 TEST_F(AudioOutputImplTest, RemoveStream) { | |
| 185 AudioOutputImpl audio_output_impl(audio_renderer_host_, kRenderFrameId1, | |
| 186 media::mojom::AudioOutputRequest()); | |
| 187 | |
| 188 EXPECT_EQ(0u, audio_output_impl.stream_impls_.size()); | |
| 189 // Remove a stream from an empty audio_output_impl should not be possible. | |
| 190 EXPECT_FALSE(audio_output_impl.RemoveStream(kStreamId1)); | |
| 191 EXPECT_EQ(0u, audio_output_impl.stream_impls_.size()); | |
| 192 unsigned int i = 0; | |
| 193 // Fill stream_impls_ with streams. | |
| 194 for (i = 0; i < kStreamIdsSize; i++) { | |
| 195 auto stream = audio_output_impl.StreamFactory( | |
| 196 kStreamIds[i], kRenderFrameId1, audio_renderer_host_); | |
| 197 EXPECT_NE(audio_output_impl.stream_impls_.end(), | |
| 198 audio_output_impl.stream_impls_.find(kStreamIds[i])); | |
| 199 EXPECT_EQ(kStreamIds[i], | |
| 200 audio_output_impl.stream_impls_[kStreamIds[i]]->get_stream_id()); | |
| 201 EXPECT_EQ(i + 1, audio_output_impl.stream_impls_.size()); | |
| 202 } | |
| 203 // Remove streams. | |
| 204 for (i = 0; i < kStreamIdsSize; i++) { | |
| 205 EXPECT_TRUE(audio_output_impl.RemoveStream(kStreamIds[i])); | |
| 206 EXPECT_EQ(audio_output_impl.stream_impls_.end(), | |
| 207 audio_output_impl.stream_impls_.find(kStreamIds[i])); | |
| 208 EXPECT_EQ(kStreamIdsSize - i - 1, audio_output_impl.stream_impls_.size()); | |
| 209 } | |
| 210 } | |
| 211 | |
| 212 } // namespace content | |
| OLD | NEW |