1 // Copyright 2015 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.
8 #include "base/logging.h"
9 #include "base/memory/ref_counted.h"
10 #include "base/message_loop/message_loop.h"
11 #include "chromeos/dbus/bluetooth_media_client.h"
12 #include "chromeos/dbus/bluetooth_media_endpoint_service_provider.h"
13 #include "chromeos/dbus/bluetooth_media_transport_client.h"
14 #include "chromeos/dbus/dbus_thread_manager.h"
15 #include "chromeos/dbus/fake_bluetooth_media_client.h"
16 #include "chromeos/dbus/fake_bluetooth_media_endpoint_service_provider.h"
17 #include "chromeos/dbus/fake_bluetooth_media_transport_client.h"
18 #include "dbus/object_path.h"
19 #include "device/bluetooth/bluetooth_adapter.h"
20 #include "device/bluetooth/bluetooth_adapter_factory.h"
21 #include "device/bluetooth/bluetooth_audio_sink.h"
22 #include "device/bluetooth/bluetooth_audio_sink_chromeos.h"
23 #include "testing/gtest/include/gtest/gtest.h"
25 using dbus::ObjectPath
;
26 using device::BluetoothAdapter
;
27 using device::BluetoothAdapterFactory
;
28 using device::BluetoothAudioSink
;
32 class TestAudioSinkObserver
: public BluetoothAudioSink::Observer
{
34 explicit TestAudioSinkObserver(scoped_refptr
<BluetoothAudioSink
> audio_sink
)
35 : state_changed_count_(0),
36 volume_changed_count_(0),
38 state_(audio_sink
->GetState()),
39 audio_sink_(audio_sink
) {
40 audio_sink_
->AddObserver(this);
43 ~TestAudioSinkObserver() override
{ audio_sink_
->RemoveObserver(this); }
45 void BluetoothAudioSinkStateChanged(
46 BluetoothAudioSink
* audio_sink
,
47 BluetoothAudioSink::State state
) override
{
48 if (state
== BluetoothAudioSink::STATE_IDLE
)
51 ++state_changed_count_
;
54 void BluetoothAudioSinkVolumeChanged(BluetoothAudioSink
* audio_sink
,
55 uint16_t volume
) override
{
56 ++volume_changed_count_
;
59 void BluetoothAudioSinkDataAvailable(BluetoothAudioSink
* audio_sink
,
61 size_t size
) override
{
64 data_
.insert(data_
.begin(), data
, data
+ size
);
67 int state_changed_count_
;
68 int volume_changed_count_
;
69 int data_available_count_
;
71 std::vector
<char> data_
;
72 BluetoothAudioSink::State state_
;
75 scoped_refptr
<BluetoothAudioSink
> audio_sink_
;
78 class BluetoothAudioSinkChromeOSTest
: public testing::Test
{
80 void SetUp() override
{
81 DBusThreadManager::Initialize();
84 error_callback_count_
= 0;
86 fake_media_
= static_cast<FakeBluetoothMediaClient
*>(
87 DBusThreadManager::Get()->GetBluetoothMediaClient());
88 fake_transport_
= static_cast<FakeBluetoothMediaTransportClient
*>(
89 DBusThreadManager::Get()->GetBluetoothMediaTransportClient());
91 // Initiates Delegate::TransportProperties with default values.
93 ObjectPath(FakeBluetoothMediaTransportClient::kTransportDevicePath
);
94 properties_
.uuid
= BluetoothMediaClient::kBluetoothAudioSinkUUID
;
95 properties_
.codec
= FakeBluetoothMediaTransportClient::kTransportCodec
;
96 properties_
.configuration
=
97 FakeBluetoothMediaTransportClient::kTransportConfiguration
;
98 properties_
.state
= BluetoothMediaTransportClient::kStateIdle
;
99 properties_
.delay
.reset(
100 new uint16_t(FakeBluetoothMediaTransportClient::kTransportDelay
));
101 properties_
.volume
.reset(
102 new uint16_t(FakeBluetoothMediaTransportClient::kTransportVolume
));
107 void TearDown() override
{
109 error_callback_count_
= 0;
112 fake_media_
->SetVisible(true);
114 // The adapter should outlive audio sink.
115 audio_sink_
= nullptr;
117 DBusThreadManager::Shutdown();
120 // Gets the existing Bluetooth adapter.
122 BluetoothAdapterFactory::GetAdapter(
123 base::Bind(&BluetoothAudioSinkChromeOSTest::GetAdapterCallback
,
124 base::Unretained(this)));
127 // Called whenever BluetoothAdapter is retrieved successfully.
128 void GetAdapterCallback(scoped_refptr
<BluetoothAdapter
> adapter
) {
131 ASSERT_NE(adapter_
.get(), nullptr);
132 ASSERT_TRUE(adapter_
->IsInitialized());
133 adapter_
->SetPowered(
135 base::Bind(&BluetoothAudioSinkChromeOSTest::Callback
,
136 base::Unretained(this)),
137 base::Bind(&BluetoothAudioSinkChromeOSTest::ErrorCallback
,
138 base::Unretained(this)));
139 ASSERT_TRUE(adapter_
->IsPresent());
140 ASSERT_TRUE(adapter_
->IsPowered());
141 EXPECT_EQ(callback_count_
, 1);
142 EXPECT_EQ(error_callback_count_
, 0);
144 // Resets callback_count_.
148 // Registers BluetoothAudioSinkChromeOS with default codec and capabilities.
149 // If the audio sink is retrieved successfully, the state changes to
150 // STATE_DISCONNECTED.
151 void GetAudioSink() {
152 // Sets up valid codec and capabilities.
153 BluetoothAudioSink::Options options
;
154 ASSERT_EQ(options
.codec
, 0x00);
155 ASSERT_EQ(options
.capabilities
,
156 std::vector
<uint8_t>({0x3f, 0xff, 0x12, 0x35}));
158 // Registers |audio_sink_| with valid codec and capabilities
159 adapter_
->RegisterAudioSink(
161 base::Bind(&BluetoothAudioSinkChromeOSTest::RegisterCallback
,
162 base::Unretained(this)),
163 base::Bind(&BluetoothAudioSinkChromeOSTest::RegisterErrorCallback
,
164 base::Unretained(this)));
166 observer_
.reset(new TestAudioSinkObserver(audio_sink_
));
167 EXPECT_EQ(callback_count_
, 1);
168 EXPECT_EQ(error_callback_count_
, 0);
169 EXPECT_EQ(observer_
->state_changed_count_
, 0);
170 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
173 void GetFakeMediaEndpoint() {
174 BluetoothAudioSinkChromeOS
* audio_sink_chromeos
=
175 static_cast<BluetoothAudioSinkChromeOS
*>(audio_sink_
.get());
176 ASSERT_NE(audio_sink_chromeos
, nullptr);
178 media_endpoint_
= static_cast<FakeBluetoothMediaEndpointServiceProvider
*>(
179 audio_sink_chromeos
->GetEndpointServiceProvider());
182 // Called whenever RegisterAudioSink is completed successfully.
183 void RegisterCallback(
184 scoped_refptr
<BluetoothAudioSink
> audio_sink
) {
186 audio_sink_
= audio_sink
;
188 GetFakeMediaEndpoint();
189 ASSERT_NE(media_endpoint_
, nullptr);
190 fake_media_
->SetEndpointRegistered(media_endpoint_
, true);
192 ASSERT_NE(audio_sink_
.get(), nullptr);
193 ASSERT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
196 // Called whenever RegisterAudioSink failed.
197 void RegisterErrorCallback(BluetoothAudioSink::ErrorCode error_code
) {
198 ++error_callback_count_
;
199 EXPECT_EQ(error_code
, BluetoothAudioSink::ERROR_NOT_REGISTERED
);
202 // Called whenever there capabilities are returned from SelectConfiguration.
203 void SelectConfigurationCallback(const std::vector
<uint8_t>& capabilities
) {
206 // |capabilities| should be the same as the capabilities for registering an
207 // audio sink in GetAudioSink().
208 EXPECT_EQ(capabilities
, std::vector
<uint8_t>({0x3f, 0xff, 0x12, 0x35}));
211 void UnregisterErrorCallback(BluetoothAudioSink::ErrorCode error_code
) {
212 ++error_callback_count_
;
213 EXPECT_EQ(error_code
, BluetoothAudioSink::ERROR_NOT_UNREGISTERED
);
216 // Generic callbacks.
221 void ErrorCallback() {
222 ++error_callback_count_
;
227 int error_callback_count_
;
229 base::MessageLoopForIO message_loop_
;
231 FakeBluetoothMediaClient
* fake_media_
;
232 FakeBluetoothMediaTransportClient
* fake_transport_
;
233 FakeBluetoothMediaEndpointServiceProvider
* media_endpoint_
;
234 scoped_ptr
<TestAudioSinkObserver
> observer_
;
235 scoped_refptr
<BluetoothAdapter
> adapter_
;
236 scoped_refptr
<BluetoothAudioSink
> audio_sink_
;
238 // The default property set used while calling SetConfiguration on a media
240 BluetoothMediaEndpointServiceProvider::Delegate::TransportProperties
244 TEST_F(BluetoothAudioSinkChromeOSTest
, RegisterSucceeded
) {
248 TEST_F(BluetoothAudioSinkChromeOSTest
, RegisterFailedWithInvalidOptions
) {
249 // Sets options with an invalid codec and valid capabilities.
250 BluetoothAudioSink::Options options
;
251 options
.codec
= 0xff;
252 options
.capabilities
= std::vector
<uint8_t>({0x3f, 0xff, 0x12, 0x35});
254 adapter_
->RegisterAudioSink(
256 base::Bind(&BluetoothAudioSinkChromeOSTest::RegisterCallback
,
257 base::Unretained(this)),
258 base::Bind(&BluetoothAudioSinkChromeOSTest::RegisterErrorCallback
,
259 base::Unretained(this)));
261 EXPECT_EQ(callback_count_
, 0);
262 EXPECT_EQ(error_callback_count_
, 1);
264 // Sets options with a valid codec and invalid capabilities.
265 options
.codec
= 0x00;
266 options
.capabilities
.clear();
267 adapter_
->RegisterAudioSink(
269 base::Bind(&BluetoothAudioSinkChromeOSTest::RegisterCallback
,
270 base::Unretained(this)),
271 base::Bind(&BluetoothAudioSinkChromeOSTest::RegisterErrorCallback
,
272 base::Unretained(this)));
274 EXPECT_EQ(callback_count_
, 0);
275 EXPECT_EQ(error_callback_count_
, 2);
278 TEST_F(BluetoothAudioSinkChromeOSTest
, SelectConfiguration
) {
281 // Simulates calling SelectConfiguration on the media endpoint object owned by
282 // |audio_sink_| with some fake capabilities.
283 media_endpoint_
->SelectConfiguration(
284 std::vector
<uint8_t>({0x21, 0x15, 0x33, 0x2C}),
285 base::Bind(&BluetoothAudioSinkChromeOSTest::SelectConfigurationCallback
,
286 base::Unretained(this)));
288 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
289 EXPECT_EQ(callback_count_
, 2);
290 EXPECT_EQ(error_callback_count_
, 0);
291 EXPECT_EQ(observer_
->state_changed_count_
, 0);
292 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
295 TEST_F(BluetoothAudioSinkChromeOSTest
, SetConfiguration
) {
298 media_endpoint_
->SelectConfiguration(
299 std::vector
<uint8_t>({0x21, 0x15, 0x33, 0x2C}),
300 base::Bind(&BluetoothAudioSinkChromeOSTest::SelectConfigurationCallback
,
301 base::Unretained(this)));
303 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
304 EXPECT_EQ(callback_count_
, 2);
305 EXPECT_EQ(error_callback_count_
, 0);
306 EXPECT_EQ(observer_
->state_changed_count_
, 0);
307 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
309 // Simulates calling SetConfiguration on the media endpoint object owned by
310 // |audio_sink_| with a fake transport path and a
311 // Delegate::TransportProperties structure.
312 media_endpoint_
->SetConfiguration(
313 fake_transport_
->GetTransportPath(media_endpoint_
->object_path()),
316 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_IDLE
);
317 EXPECT_EQ(callback_count_
, 2);
318 EXPECT_EQ(error_callback_count_
, 0);
319 EXPECT_EQ(observer_
->state_changed_count_
, 1);
320 EXPECT_EQ(observer_
->volume_changed_count_
, 1);
323 TEST_F(BluetoothAudioSinkChromeOSTest
, SetConfigurationWithUnexpectedState
) {
326 media_endpoint_
->SelectConfiguration(
327 std::vector
<uint8_t>({0x21, 0x15, 0x33, 0x2C}),
328 base::Bind(&BluetoothAudioSinkChromeOSTest::SelectConfigurationCallback
,
329 base::Unretained(this)));
331 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
332 EXPECT_EQ(callback_count_
, 2);
333 EXPECT_EQ(error_callback_count_
, 0);
334 EXPECT_EQ(observer_
->state_changed_count_
, 0);
335 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
337 // Set state of Delegate::TransportProperties with an unexpected value.
338 properties_
.state
= "pending";
340 media_endpoint_
->SetConfiguration(
341 fake_transport_
->GetTransportPath(media_endpoint_
->object_path()),
344 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
345 EXPECT_EQ(callback_count_
, 2);
346 EXPECT_EQ(error_callback_count_
, 0);
347 EXPECT_EQ(observer_
->state_changed_count_
, 0);
348 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
351 // Checks if the observer is notified on media-removed event when the state of
352 // |audio_sink_| is STATE_DISCONNECTED. Once the media object is removed, the
353 // audio sink is no longer valid.
354 TEST_F(BluetoothAudioSinkChromeOSTest
, MediaRemovedDuringDisconnectedState
) {
357 // Gets the media object and makes it invisible to see if the state of the
358 // audio sink changes accordingly.
359 fake_media_
->SetVisible(false);
361 GetFakeMediaEndpoint();
363 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_INVALID
);
364 EXPECT_EQ(media_endpoint_
, nullptr);
365 EXPECT_EQ(observer_
->state_changed_count_
, 1);
366 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
369 // Checks if the observer is notified on media-removed event when the state of
370 // |audio_sink_| is STATE_IDLE. Once the media object is removed, the audio sink
371 // is no longer valid.
372 TEST_F(BluetoothAudioSinkChromeOSTest
, MediaRemovedDuringIdleState
) {
375 media_endpoint_
->SelectConfiguration(
376 std::vector
<uint8_t>({0x21, 0x15, 0x33, 0x2C}),
377 base::Bind(&BluetoothAudioSinkChromeOSTest::SelectConfigurationCallback
,
378 base::Unretained(this)));
380 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
381 EXPECT_EQ(callback_count_
, 2);
382 EXPECT_EQ(error_callback_count_
, 0);
383 EXPECT_EQ(observer_
->state_changed_count_
, 0);
384 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
386 media_endpoint_
->SetConfiguration(
387 fake_transport_
->GetTransportPath(media_endpoint_
->object_path()),
390 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_IDLE
);
391 EXPECT_EQ(callback_count_
, 2);
392 EXPECT_EQ(error_callback_count_
, 0);
393 EXPECT_EQ(observer_
->state_changed_count_
, 1);
394 EXPECT_EQ(observer_
->volume_changed_count_
, 1);
396 // Gets the media object and makes it invisible to see if the state of the
397 // audio sink changes accordingly.
398 fake_media_
->SetVisible(false);
400 GetFakeMediaEndpoint();
402 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_INVALID
);
403 EXPECT_EQ(media_endpoint_
, nullptr);
405 // The state becomes disconnted and then invalid, since the removal of
406 // transport object should happend before media becomes invisible.
407 // State: STATE_IDLE -> STATE_DISCONNECTED -> STATE_INVALID
408 EXPECT_EQ(observer_
->state_changed_count_
, 3);
409 EXPECT_EQ(observer_
->volume_changed_count_
, 2);
412 TEST_F(BluetoothAudioSinkChromeOSTest
, MediaRemovedDuringActiveState
) {
415 media_endpoint_
->SelectConfiguration(
416 std::vector
<uint8_t>({0x21, 0x15, 0x33, 0x2C}),
417 base::Bind(&BluetoothAudioSinkChromeOSTest::SelectConfigurationCallback
,
418 base::Unretained(this)));
420 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
421 EXPECT_EQ(callback_count_
, 2);
422 EXPECT_EQ(error_callback_count_
, 0);
423 EXPECT_EQ(observer_
->state_changed_count_
, 0);
424 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
426 media_endpoint_
->SetConfiguration(
427 fake_transport_
->GetTransportPath(media_endpoint_
->object_path()),
430 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_IDLE
);
431 EXPECT_EQ(callback_count_
, 2);
432 EXPECT_EQ(error_callback_count_
, 0);
433 EXPECT_EQ(observer_
->state_changed_count_
, 1);
434 EXPECT_EQ(observer_
->volume_changed_count_
, 1);
436 fake_transport_
->SetState(media_endpoint_
->object_path(), "pending");
438 message_loop_
.RunUntilIdle();
440 // Acquire is called when the state of |audio_sink_| becomes STATE_PENDING,
441 // and Acquire will trigger state change. Therefore, the state will be
442 // STATE_ACTIVE right after STATE_PENDING.
443 // State: STATE_IDLE -> STATE_PENDING -> STATE_ACTIVE
444 EXPECT_EQ(observer_
->state_changed_count_
, 3);
446 // Gets the media object and makes it invisible to see if the state of the
447 // audio sink changes accordingly.
448 fake_media_
->SetVisible(false);
450 GetFakeMediaEndpoint();
452 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_INVALID
);
453 EXPECT_EQ(media_endpoint_
, nullptr);
455 // The state becomes disconnted and then invalid, since the removal of
456 // transport object should happend before media becomes invisible.
457 // State: STATE_ACTIVE -> STATE_DISCONNECTED -> STATE_INVALID
458 EXPECT_EQ(observer_
->state_changed_count_
, 5);
459 EXPECT_EQ(observer_
->volume_changed_count_
, 2);
462 // Checks if the observer is notified on transport-removed event when the state
463 // of |audio_sink_| is STATE_IDEL. Once the media transport object is removed,
464 // the audio sink is disconnected.
465 TEST_F(BluetoothAudioSinkChromeOSTest
, TransportRemovedDuringIdleState
) {
468 media_endpoint_
->SelectConfiguration(
469 std::vector
<uint8_t>({0x21, 0x15, 0x33, 0x2C}),
470 base::Bind(&BluetoothAudioSinkChromeOSTest::SelectConfigurationCallback
,
471 base::Unretained(this)));
473 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
474 EXPECT_EQ(callback_count_
, 2);
475 EXPECT_EQ(error_callback_count_
, 0);
476 EXPECT_EQ(observer_
->state_changed_count_
, 0);
477 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
479 media_endpoint_
->SetConfiguration(
480 fake_transport_
->GetTransportPath(media_endpoint_
->object_path()),
483 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_IDLE
);
484 EXPECT_EQ(callback_count_
, 2);
485 EXPECT_EQ(error_callback_count_
, 0);
486 EXPECT_EQ(observer_
->state_changed_count_
, 1);
487 EXPECT_EQ(observer_
->volume_changed_count_
, 1);
489 // Makes the transport object invalid to see if the state of the audio sink
490 // changes accordingly.
491 fake_transport_
->SetValid(media_endpoint_
, false);
493 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
494 EXPECT_NE(media_endpoint_
, nullptr);
495 EXPECT_EQ(observer_
->state_changed_count_
, 2);
496 EXPECT_EQ(observer_
->volume_changed_count_
, 2);
499 TEST_F(BluetoothAudioSinkChromeOSTest
, TransportRemovedDuringActiveState
) {
502 media_endpoint_
->SelectConfiguration(
503 std::vector
<uint8_t>({0x21, 0x15, 0x33, 0x2C}),
504 base::Bind(&BluetoothAudioSinkChromeOSTest::SelectConfigurationCallback
,
505 base::Unretained(this)));
507 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
508 EXPECT_EQ(callback_count_
, 2);
509 EXPECT_EQ(error_callback_count_
, 0);
510 EXPECT_EQ(observer_
->state_changed_count_
, 0);
511 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
513 media_endpoint_
->SetConfiguration(
514 fake_transport_
->GetTransportPath(media_endpoint_
->object_path()),
517 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_IDLE
);
518 EXPECT_EQ(callback_count_
, 2);
519 EXPECT_EQ(error_callback_count_
, 0);
520 EXPECT_EQ(observer_
->state_changed_count_
, 1);
521 EXPECT_EQ(observer_
->volume_changed_count_
, 1);
523 fake_transport_
->SetState(media_endpoint_
->object_path(), "pending");
525 message_loop_
.RunUntilIdle();
527 // Acquire is called when the state of |audio_sink_| becomes STATE_PENDING,
528 // and Acquire will trigger state change. Therefore, the state will be
529 // STATE_ACTIVE right after STATE_PENDING.
530 // State: STATE_IDLE -> STATE_PENDING -> STATE_ACTIVE
531 EXPECT_EQ(observer_
->state_changed_count_
, 3);
533 // Makes the transport object invalid to see if the state of the audio sink
534 // changes accordingly.
535 fake_transport_
->SetValid(media_endpoint_
, false);
537 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
538 EXPECT_NE(media_endpoint_
, nullptr);
539 EXPECT_EQ(observer_
->state_changed_count_
, 4);
540 EXPECT_EQ(observer_
->volume_changed_count_
, 2);
543 TEST_F(BluetoothAudioSinkChromeOSTest
,
544 AdapterPoweredChangedDuringDisconnectedState
) {
547 adapter_
->SetPowered(
549 base::Bind(&BluetoothAudioSinkChromeOSTest::Callback
,
550 base::Unretained(this)),
551 base::Bind(&BluetoothAudioSinkChromeOSTest::ErrorCallback
,
552 base::Unretained(this)));
554 EXPECT_TRUE(adapter_
->IsPresent());
555 EXPECT_FALSE(adapter_
->IsPowered());
556 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
557 EXPECT_EQ(callback_count_
, 2);
558 EXPECT_EQ(error_callback_count_
, 0);
559 EXPECT_EQ(observer_
->state_changed_count_
, 0);
560 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
562 adapter_
->SetPowered(
564 base::Bind(&BluetoothAudioSinkChromeOSTest::Callback
,
565 base::Unretained(this)),
566 base::Bind(&BluetoothAudioSinkChromeOSTest::ErrorCallback
,
567 base::Unretained(this)));
569 EXPECT_TRUE(adapter_
->IsPresent());
570 EXPECT_TRUE(adapter_
->IsPowered());
571 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
572 EXPECT_EQ(callback_count_
, 3);
573 EXPECT_EQ(error_callback_count_
, 0);
574 EXPECT_EQ(observer_
->state_changed_count_
, 0);
575 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
578 TEST_F(BluetoothAudioSinkChromeOSTest
, AdapterPoweredChangedDuringIdleState
) {
581 media_endpoint_
->SelectConfiguration(
582 std::vector
<uint8_t>({0x21, 0x15, 0x33, 0x2C}),
583 base::Bind(&BluetoothAudioSinkChromeOSTest::SelectConfigurationCallback
,
584 base::Unretained(this)));
586 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
587 EXPECT_EQ(callback_count_
, 2);
588 EXPECT_EQ(error_callback_count_
, 0);
589 EXPECT_EQ(observer_
->state_changed_count_
, 0);
590 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
592 media_endpoint_
->SetConfiguration(
593 fake_transport_
->GetTransportPath(media_endpoint_
->object_path()),
596 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_IDLE
);
597 EXPECT_EQ(callback_count_
, 2);
598 EXPECT_EQ(error_callback_count_
, 0);
599 EXPECT_EQ(observer_
->state_changed_count_
, 1);
600 EXPECT_EQ(observer_
->volume_changed_count_
, 1);
602 adapter_
->SetPowered(
604 base::Bind(&BluetoothAudioSinkChromeOSTest::Callback
,
605 base::Unretained(this)),
606 base::Bind(&BluetoothAudioSinkChromeOSTest::ErrorCallback
,
607 base::Unretained(this)));
608 GetFakeMediaEndpoint();
610 EXPECT_TRUE(adapter_
->IsPresent());
611 EXPECT_FALSE(adapter_
->IsPowered());
612 EXPECT_NE(media_endpoint_
, nullptr);
613 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
614 EXPECT_EQ(callback_count_
, 3);
615 EXPECT_EQ(error_callback_count_
, 0);
616 EXPECT_EQ(observer_
->state_changed_count_
, 2);
617 EXPECT_EQ(observer_
->volume_changed_count_
, 2);
620 TEST_F(BluetoothAudioSinkChromeOSTest
,
621 UnregisterAudioSinkDuringDisconnectedState
) {
624 audio_sink_
->Unregister(
625 base::Bind(&BluetoothAudioSinkChromeOSTest::Callback
,
626 base::Unretained(this)),
627 base::Bind(&BluetoothAudioSinkChromeOSTest::UnregisterErrorCallback
,
628 base::Unretained(this)));
630 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_INVALID
);
631 EXPECT_EQ(callback_count_
, 2);
632 EXPECT_EQ(error_callback_count_
, 0);
633 EXPECT_EQ(observer_
->state_changed_count_
, 1);
634 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
637 TEST_F(BluetoothAudioSinkChromeOSTest
, UnregisterAudioSinkDuringIdleState
) {
640 media_endpoint_
->SelectConfiguration(
641 std::vector
<uint8_t>({0x21, 0x15, 0x33, 0x2C}),
642 base::Bind(&BluetoothAudioSinkChromeOSTest::SelectConfigurationCallback
,
643 base::Unretained(this)));
645 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
646 EXPECT_EQ(callback_count_
, 2);
647 EXPECT_EQ(error_callback_count_
, 0);
648 EXPECT_EQ(observer_
->state_changed_count_
, 0);
649 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
651 media_endpoint_
->SetConfiguration(
652 fake_transport_
->GetTransportPath(media_endpoint_
->object_path()),
655 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_IDLE
);
656 EXPECT_EQ(callback_count_
, 2);
657 EXPECT_EQ(error_callback_count_
, 0);
658 EXPECT_EQ(observer_
->state_changed_count_
, 1);
659 EXPECT_EQ(observer_
->volume_changed_count_
, 1);
661 audio_sink_
->Unregister(
662 base::Bind(&BluetoothAudioSinkChromeOSTest::Callback
,
663 base::Unretained(this)),
664 base::Bind(&BluetoothAudioSinkChromeOSTest::UnregisterErrorCallback
,
665 base::Unretained(this)));
667 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_INVALID
);
668 EXPECT_EQ(callback_count_
, 3);
669 EXPECT_EQ(error_callback_count_
, 0);
671 // The state becomes disconnted and then invalid, since the removal of
672 // transport object should happend before the unregistration of endpoint.
673 // State: STATE_IDLE -> STATE_DISCONNECTED -> STATE_INVALID
674 EXPECT_EQ(observer_
->state_changed_count_
, 3);
675 EXPECT_EQ(observer_
->volume_changed_count_
, 2);
678 TEST_F(BluetoothAudioSinkChromeOSTest
, UnregisterAudioSinkDuringActiveState
) {
681 media_endpoint_
->SelectConfiguration(
682 std::vector
<uint8_t>({0x21, 0x15, 0x33, 0x2C}),
683 base::Bind(&BluetoothAudioSinkChromeOSTest::SelectConfigurationCallback
,
684 base::Unretained(this)));
686 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
687 EXPECT_EQ(callback_count_
, 2);
688 EXPECT_EQ(error_callback_count_
, 0);
689 EXPECT_EQ(observer_
->state_changed_count_
, 0);
690 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
692 media_endpoint_
->SetConfiguration(
693 fake_transport_
->GetTransportPath(media_endpoint_
->object_path()),
696 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_IDLE
);
697 EXPECT_EQ(callback_count_
, 2);
698 EXPECT_EQ(error_callback_count_
, 0);
699 EXPECT_EQ(observer_
->state_changed_count_
, 1);
700 EXPECT_EQ(observer_
->volume_changed_count_
, 1);
702 fake_transport_
->SetState(media_endpoint_
->object_path(), "pending");
704 message_loop_
.RunUntilIdle();
706 // Acquire is called when the state of |audio_sink_| becomes STATE_PENDING,
707 // and Acquire will trigger state change. Therefore, the state will be
708 // STATE_ACTIVE right after STATE_PENDING.
709 // State: STATE_IDLE -> STATE_PENDING -> STATE_ACTIVE
710 EXPECT_EQ(observer_
->state_changed_count_
, 3);
712 audio_sink_
->Unregister(
713 base::Bind(&BluetoothAudioSinkChromeOSTest::Callback
,
714 base::Unretained(this)),
715 base::Bind(&BluetoothAudioSinkChromeOSTest::UnregisterErrorCallback
,
716 base::Unretained(this)));
718 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_INVALID
);
719 EXPECT_EQ(callback_count_
, 3);
720 EXPECT_EQ(error_callback_count_
, 0);
721 EXPECT_EQ(observer_
->state_changed_count_
, 5);
722 EXPECT_EQ(observer_
->volume_changed_count_
, 2);
725 TEST_F(BluetoothAudioSinkChromeOSTest
, StateChanged
) {
728 media_endpoint_
->SelectConfiguration(
729 std::vector
<uint8_t>({0x21, 0x15, 0x33, 0x2C}),
730 base::Bind(&BluetoothAudioSinkChromeOSTest::SelectConfigurationCallback
,
731 base::Unretained(this)));
733 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
734 EXPECT_EQ(callback_count_
, 2);
735 EXPECT_EQ(error_callback_count_
, 0);
736 EXPECT_EQ(observer_
->state_changed_count_
, 0);
737 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
739 media_endpoint_
->SetConfiguration(
740 fake_transport_
->GetTransportPath(media_endpoint_
->object_path()),
743 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_IDLE
);
744 EXPECT_EQ(callback_count_
, 2);
745 EXPECT_EQ(error_callback_count_
, 0);
746 EXPECT_EQ(observer_
->state_changed_count_
, 1);
747 EXPECT_EQ(observer_
->volume_changed_count_
, 1);
749 // Changes the current state of transport to pending.
750 fake_transport_
->SetState(media_endpoint_
->object_path(), "pending");
752 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_PENDING
);
753 EXPECT_EQ(observer_
->state_changed_count_
, 3);
754 EXPECT_EQ(observer_
->volume_changed_count_
, 1);
757 TEST_F(BluetoothAudioSinkChromeOSTest
, VolumeChanged
) {
760 media_endpoint_
->SelectConfiguration(
761 std::vector
<uint8_t>({0x21, 0x15, 0x33, 0x2C}),
762 base::Bind(&BluetoothAudioSinkChromeOSTest::SelectConfigurationCallback
,
763 base::Unretained(this)));
765 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
766 EXPECT_EQ(callback_count_
, 2);
767 EXPECT_EQ(error_callback_count_
, 0);
768 EXPECT_EQ(observer_
->state_changed_count_
, 0);
769 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
771 media_endpoint_
->SetConfiguration(
772 fake_transport_
->GetTransportPath(media_endpoint_
->object_path()),
775 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_IDLE
);
776 EXPECT_EQ(callback_count_
, 2);
777 EXPECT_EQ(error_callback_count_
, 0);
778 EXPECT_EQ(observer_
->state_changed_count_
, 1);
779 EXPECT_EQ(observer_
->volume_changed_count_
, 1);
781 // |kTransportVolume| is the initial volume of the transport, and this
782 // value is propagated to the audio sink via SetConfiguration.
783 EXPECT_EQ(audio_sink_
->GetVolume(),
784 FakeBluetoothMediaTransportClient::kTransportVolume
);
786 // Changes volume to a valid level.
787 fake_transport_
->SetVolume(media_endpoint_
->object_path(), 100);
789 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_IDLE
);
790 EXPECT_EQ(observer_
->state_changed_count_
, 1);
791 EXPECT_EQ(observer_
->volume_changed_count_
, 2);
792 EXPECT_EQ(audio_sink_
->GetVolume(), 100);
794 // Changes volume to an invalid level.
795 fake_transport_
->SetVolume(media_endpoint_
->object_path(), 200);
797 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_IDLE
);
798 EXPECT_EQ(observer_
->state_changed_count_
, 1);
799 EXPECT_EQ(observer_
->volume_changed_count_
, 3);
800 EXPECT_EQ(audio_sink_
->GetVolume(), BluetoothAudioSink::kInvalidVolume
);
803 TEST_F(BluetoothAudioSinkChromeOSTest
, AcquireFD
) {
806 media_endpoint_
->SelectConfiguration(
807 std::vector
<uint8_t>({0x21, 0x15, 0x33, 0x2C}),
808 base::Bind(&BluetoothAudioSinkChromeOSTest::SelectConfigurationCallback
,
809 base::Unretained(this)));
811 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
812 EXPECT_EQ(callback_count_
, 2);
813 EXPECT_EQ(error_callback_count_
, 0);
814 EXPECT_EQ(observer_
->state_changed_count_
, 0);
815 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
817 media_endpoint_
->SetConfiguration(
818 fake_transport_
->GetTransportPath(media_endpoint_
->object_path()),
821 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_IDLE
);
822 EXPECT_EQ(callback_count_
, 2);
823 EXPECT_EQ(error_callback_count_
, 0);
824 EXPECT_EQ(observer_
->state_changed_count_
, 1);
825 EXPECT_EQ(observer_
->volume_changed_count_
, 1);
827 fake_transport_
->SetState(media_endpoint_
->object_path(), "pending");
829 std::vector
<char> data_one(16, 0x12);
830 fake_transport_
->WriteData(media_endpoint_
->object_path(), data_one
);
832 message_loop_
.RunUntilIdle();
834 // Acquire is called when the state of |audio_sink_| becomes STATE_PENDING,
835 // and Acquire will trigger state change. Therefore, the state will be
836 // STATE_ACTIVE right after STATE_PENDING.
837 // State: STATE_IDLE -> STATE_PENDING -> STATE_ACTIVE
838 EXPECT_EQ(observer_
->state_changed_count_
, 3);
839 EXPECT_EQ(observer_
->total_read_
, data_one
.size());
840 EXPECT_EQ(observer_
->data_
, data_one
);
843 // Tests the case where the remote device pauses and resume audio streaming.
844 TEST_F(BluetoothAudioSinkChromeOSTest
, PauseAndResume
) {
847 media_endpoint_
->SelectConfiguration(
848 std::vector
<uint8_t>({0x21, 0x15, 0x33, 0x2C}),
849 base::Bind(&BluetoothAudioSinkChromeOSTest::SelectConfigurationCallback
,
850 base::Unretained(this)));
852 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
853 EXPECT_EQ(callback_count_
, 2);
854 EXPECT_EQ(error_callback_count_
, 0);
855 EXPECT_EQ(observer_
->state_changed_count_
, 0);
856 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
858 media_endpoint_
->SetConfiguration(
859 fake_transport_
->GetTransportPath(media_endpoint_
->object_path()),
862 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_IDLE
);
863 EXPECT_EQ(callback_count_
, 2);
864 EXPECT_EQ(error_callback_count_
, 0);
865 EXPECT_EQ(observer_
->state_changed_count_
, 1);
866 EXPECT_EQ(observer_
->volume_changed_count_
, 1);
868 fake_transport_
->SetState(media_endpoint_
->object_path(), "pending");
870 std::vector
<char> data_one(16, 0x12);
871 fake_transport_
->WriteData(media_endpoint_
->object_path(), data_one
);
873 message_loop_
.RunUntilIdle();
875 EXPECT_EQ(observer_
->data_
, data_one
);
876 EXPECT_EQ(observer_
->state_changed_count_
, 3);
877 EXPECT_EQ(observer_
->total_read_
, data_one
.size());
879 // Simulates the situation where the remote device pauses and resume audio
881 fake_transport_
->SetState(media_endpoint_
->object_path(), "idle");
883 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_IDLE
);
884 EXPECT_EQ(observer_
->state_changed_count_
, 4);
886 fake_transport_
->SetState(media_endpoint_
->object_path(), "pending");
888 std::vector
<char> data_two(8, 0x10);
889 fake_transport_
->WriteData(media_endpoint_
->object_path(), data_two
);
891 message_loop_
.RunUntilIdle();
893 EXPECT_EQ(observer_
->data_
, data_two
);
894 EXPECT_EQ(observer_
->state_changed_count_
, 6);
895 EXPECT_EQ(observer_
->total_read_
, data_two
.size());
898 TEST_F(BluetoothAudioSinkChromeOSTest
, ContinuouslyStreaming
) {
901 media_endpoint_
->SelectConfiguration(
902 std::vector
<uint8_t>({0x21, 0x15, 0x33, 0x2C}),
903 base::Bind(&BluetoothAudioSinkChromeOSTest::SelectConfigurationCallback
,
904 base::Unretained(this)));
906 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_DISCONNECTED
);
907 EXPECT_EQ(callback_count_
, 2);
908 EXPECT_EQ(error_callback_count_
, 0);
909 EXPECT_EQ(observer_
->state_changed_count_
, 0);
910 EXPECT_EQ(observer_
->volume_changed_count_
, 0);
912 media_endpoint_
->SetConfiguration(
913 fake_transport_
->GetTransportPath(media_endpoint_
->object_path()),
916 EXPECT_EQ(audio_sink_
->GetState(), BluetoothAudioSink::STATE_IDLE
);
917 EXPECT_EQ(callback_count_
, 2);
918 EXPECT_EQ(error_callback_count_
, 0);
919 EXPECT_EQ(observer_
->state_changed_count_
, 1);
920 EXPECT_EQ(observer_
->volume_changed_count_
, 1);
922 fake_transport_
->SetState(media_endpoint_
->object_path(), "pending");
924 std::vector
<char> data_one(16, 0x12);
925 fake_transport_
->WriteData(media_endpoint_
->object_path(), data_one
);
927 message_loop_
.RunUntilIdle();
929 EXPECT_EQ(observer_
->data_
, data_one
);
930 EXPECT_EQ(observer_
->state_changed_count_
, 3);
931 EXPECT_EQ(observer_
->total_read_
, data_one
.size());
933 std::vector
<char> data_two(8, 0x10);
934 fake_transport_
->WriteData(media_endpoint_
->object_path(), data_two
);
936 message_loop_
.RunUntilIdle();
938 EXPECT_EQ(observer_
->data_
, data_two
);
939 EXPECT_EQ(observer_
->state_changed_count_
, 3);
940 EXPECT_EQ(observer_
->total_read_
, data_one
.size() + data_two
.size());
943 } // namespace chromeos