1 // Copyright (c) 2014 The Chromium OS 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 <gtest/gtest.h>
6
7 extern "C" {
8 #include "cras_bt_constants.h"
9 #include "cras_bt_device.h"
10 #include "cras_bt_io.h"
11 #include "cras_bt_log.h"
12 #include "cras_iodev.h"
13 #include "cras_main_message.h"
14
15 #define FAKE_OBJ_PATH "/obj/path"
16 }
17
18 static struct cras_iodev* cras_bt_io_create_profile_ret;
19 static struct cras_iodev* cras_bt_io_append_btio_val;
20 static struct cras_ionode* cras_bt_io_get_profile_ret;
21 static unsigned int cras_bt_io_create_called;
22 static unsigned int cras_bt_io_append_called;
23 static unsigned int cras_bt_io_remove_called;
24 static unsigned int cras_bt_io_destroy_called;
25 static enum cras_bt_device_profile cras_bt_io_create_profile_val;
26 static enum cras_bt_device_profile cras_bt_io_append_profile_val;
27 static unsigned int cras_bt_io_try_remove_ret;
28
29 static cras_main_message* cras_main_message_send_msg;
30 static cras_message_callback cras_main_message_add_handler_callback;
31 static void* cras_main_message_add_handler_callback_data;
32 static int cras_tm_create_timer_called;
33 static int cras_a2dp_start_called;
34 static int cras_a2dp_suspend_connected_device_called;
35 static int cras_hfp_ag_remove_conflict_called;
36 static int cras_hfp_ag_start_called;
37 static int cras_hfp_ag_suspend_connected_device_called;
38 static void (*cras_tm_create_timer_cb)(struct cras_timer* t, void* data);
39 static void* cras_tm_create_timer_cb_data;
40 static int dbus_message_new_method_call_called;
41 static const char* dbus_message_new_method_call_method;
42 static struct cras_bt_device* cras_a2dp_connected_device_ret;
43 static struct cras_bt_device* cras_a2dp_suspend_connected_device_dev;
44
45 struct MockDBusMessage {
46 int type;
47 void* value;
48 MockDBusMessage* next;
49 MockDBusMessage* recurse;
50 };
51
ResetStubData()52 void ResetStubData() {
53 cras_bt_io_get_profile_ret = NULL;
54 cras_bt_io_create_called = 0;
55 cras_bt_io_append_called = 0;
56 cras_bt_io_remove_called = 0;
57 cras_bt_io_destroy_called = 0;
58 cras_bt_io_try_remove_ret = 0;
59 cras_main_message_send_msg = NULL;
60 cras_tm_create_timer_called = 0;
61 cras_a2dp_start_called = 0;
62 cras_a2dp_suspend_connected_device_called = 0;
63 cras_hfp_ag_remove_conflict_called = 0;
64 cras_hfp_ag_start_called = 0;
65 cras_hfp_ag_suspend_connected_device_called = 0;
66 dbus_message_new_method_call_method = NULL;
67 dbus_message_new_method_call_called = 0;
68 cras_a2dp_connected_device_ret = NULL;
69 }
70
FreeMockDBusMessage(MockDBusMessage * head)71 static void FreeMockDBusMessage(MockDBusMessage* head) {
72 if (head->next != NULL)
73 FreeMockDBusMessage(head->next);
74 if (head->recurse != NULL)
75 FreeMockDBusMessage(head->recurse);
76 if (head->type == DBUS_TYPE_STRING)
77 free((char*)head->value);
78 delete head;
79 }
80
NewMockDBusConnectedMessage()81 static struct MockDBusMessage* NewMockDBusConnectedMessage() {
82 MockDBusMessage* msg = new MockDBusMessage{DBUS_TYPE_ARRAY, NULL};
83 MockDBusMessage* dict =
84 new MockDBusMessage{DBUS_TYPE_STRING, (void*)strdup("Connected")};
85 MockDBusMessage* variant = new MockDBusMessage{DBUS_TYPE_BOOLEAN, (void*)1};
86
87 msg->recurse = dict;
88 dict->next = new MockDBusMessage{DBUS_TYPE_INVALID, NULL};
89 dict->next->recurse = variant;
90 return msg;
91 }
92
93 namespace {
94
95 class BtDeviceTestSuite : public testing::Test {
96 protected:
SetUp()97 virtual void SetUp() {
98 ResetStubData();
99 bt_iodev1.direction = CRAS_STREAM_OUTPUT;
100 bt_iodev1.update_active_node = update_active_node;
101 bt_iodev2.direction = CRAS_STREAM_INPUT;
102 bt_iodev2.update_active_node = update_active_node;
103 d1_.direction = CRAS_STREAM_OUTPUT;
104 d1_.update_active_node = update_active_node;
105 d2_.direction = CRAS_STREAM_OUTPUT;
106 d2_.update_active_node = update_active_node;
107 d3_.direction = CRAS_STREAM_INPUT;
108 d3_.update_active_node = update_active_node;
109 btlog = cras_bt_event_log_init();
110 }
111
TearDown()112 virtual void TearDown() {
113 if (cras_main_message_send_msg)
114 free(cras_main_message_send_msg);
115 cras_bt_event_log_deinit(btlog);
116 }
117
update_active_node(struct cras_iodev * iodev,unsigned node_idx,unsigned dev_enabled)118 static void update_active_node(struct cras_iodev* iodev,
119 unsigned node_idx,
120 unsigned dev_enabled) {}
121
122 struct cras_iodev bt_iodev1;
123 struct cras_iodev bt_iodev2;
124 struct cras_iodev d3_;
125 struct cras_iodev d2_;
126 struct cras_iodev d1_;
127 };
128
TEST(BtDeviceSuite,CreateBtDevice)129 TEST(BtDeviceSuite, CreateBtDevice) {
130 struct cras_bt_device* device;
131
132 device = cras_bt_device_create(NULL, FAKE_OBJ_PATH);
133 EXPECT_NE((void*)NULL, device);
134
135 device = cras_bt_device_get(FAKE_OBJ_PATH);
136 EXPECT_NE((void*)NULL, device);
137
138 cras_bt_device_remove(device);
139 device = cras_bt_device_get(FAKE_OBJ_PATH);
140 EXPECT_EQ((void*)NULL, device);
141 }
142
TEST_F(BtDeviceTestSuite,AppendRmIodev)143 TEST_F(BtDeviceTestSuite, AppendRmIodev) {
144 struct cras_bt_device* device;
145 device = cras_bt_device_create(NULL, FAKE_OBJ_PATH);
146 bt_iodev1.nodes = reinterpret_cast<struct cras_ionode*>(0x123);
147 cras_bt_io_create_profile_ret = &bt_iodev1;
148 cras_bt_device_append_iodev(device, &d1_, CRAS_BT_DEVICE_PROFILE_A2DP_SOURCE);
149 EXPECT_EQ(1, cras_bt_io_create_called);
150 EXPECT_EQ(0, cras_bt_io_append_called);
151 EXPECT_EQ(CRAS_BT_DEVICE_PROFILE_A2DP_SOURCE, cras_bt_io_create_profile_val);
152 cras_bt_device_set_active_profile(device, CRAS_BT_DEVICE_PROFILE_A2DP_SOURCE);
153
154 cras_bt_device_append_iodev(device, &d2_,
155 CRAS_BT_DEVICE_PROFILE_HFP_AUDIOGATEWAY);
156 EXPECT_EQ(1, cras_bt_io_create_called);
157 EXPECT_EQ(1, cras_bt_io_append_called);
158 EXPECT_EQ(CRAS_BT_DEVICE_PROFILE_HFP_AUDIOGATEWAY,
159 cras_bt_io_append_profile_val);
160 EXPECT_EQ(&bt_iodev1, cras_bt_io_append_btio_val);
161
162 /* Test HFP disconnected and switch to A2DP. */
163 cras_bt_io_get_profile_ret = bt_iodev1.nodes;
164 cras_bt_io_try_remove_ret = CRAS_BT_DEVICE_PROFILE_A2DP_SOURCE;
165 cras_bt_device_set_active_profile(device,
166 CRAS_BT_DEVICE_PROFILE_HFP_AUDIOGATEWAY);
167 cras_bt_device_rm_iodev(device, &d2_);
168 EXPECT_EQ(1, cras_bt_io_remove_called);
169
170 /* Test A2DP disconnection will cause bt_io destroy. */
171 cras_bt_io_try_remove_ret = 0;
172 cras_bt_device_rm_iodev(device, &d1_);
173 EXPECT_EQ(1, cras_bt_io_remove_called);
174 EXPECT_EQ(1, cras_bt_io_destroy_called);
175 EXPECT_EQ(0, cras_bt_device_get_active_profile(device));
176 cras_bt_device_remove(device);
177 }
178
TEST_F(BtDeviceTestSuite,SwitchProfile)179 TEST_F(BtDeviceTestSuite, SwitchProfile) {
180 struct cras_bt_device* device;
181
182 ResetStubData();
183 device = cras_bt_device_create(NULL, FAKE_OBJ_PATH);
184 cras_bt_io_create_profile_ret = &bt_iodev1;
185 cras_bt_device_append_iodev(device, &d1_, CRAS_BT_DEVICE_PROFILE_A2DP_SOURCE);
186 cras_bt_io_create_profile_ret = &bt_iodev2;
187 cras_bt_device_append_iodev(device, &d3_,
188 CRAS_BT_DEVICE_PROFILE_HFP_AUDIOGATEWAY);
189
190 cras_bt_device_start_monitor();
191 cras_bt_device_switch_profile_enable_dev(device, &bt_iodev1);
192
193 /* Two bt iodevs were all active. */
194 cras_main_message_add_handler_callback(
195 cras_main_message_send_msg, cras_main_message_add_handler_callback_data);
196
197 /* One bt iodev was active, the other was not. */
198 cras_bt_device_switch_profile_enable_dev(device, &bt_iodev2);
199 cras_main_message_add_handler_callback(
200 cras_main_message_send_msg, cras_main_message_add_handler_callback_data);
201
202 /* Output bt iodev wasn't active, close the active input iodev. */
203 cras_bt_device_switch_profile(device, &bt_iodev2);
204 cras_main_message_add_handler_callback(
205 cras_main_message_send_msg, cras_main_message_add_handler_callback_data);
206 cras_bt_device_remove(device);
207 }
208
TEST_F(BtDeviceTestSuite,SetDeviceConnectedA2dpOnly)209 TEST_F(BtDeviceTestSuite, SetDeviceConnectedA2dpOnly) {
210 struct cras_bt_device* device;
211 struct MockDBusMessage *msg_root, *cur;
212 ResetStubData();
213
214 device = cras_bt_device_create(NULL, FAKE_OBJ_PATH);
215 EXPECT_NE((void*)NULL, device);
216
217 cras_bt_device_add_supported_profiles(device, A2DP_SINK_UUID);
218
219 cur = msg_root = NewMockDBusConnectedMessage();
220 cras_bt_device_update_properties(device, (DBusMessageIter*)&cur, NULL);
221 EXPECT_EQ(1, cras_tm_create_timer_called);
222 EXPECT_NE((void*)NULL, cras_tm_create_timer_cb);
223
224 /* Schedule another timer, if A2DP not yet configured. */
225 cras_tm_create_timer_cb(NULL, cras_tm_create_timer_cb_data);
226 EXPECT_EQ(2, cras_tm_create_timer_called);
227 EXPECT_EQ(1, dbus_message_new_method_call_called);
228 EXPECT_STREQ("ConnectProfile", dbus_message_new_method_call_method);
229
230 cras_bt_device_a2dp_configured(device);
231 cras_tm_create_timer_cb(NULL, cras_tm_create_timer_cb_data);
232 EXPECT_EQ(2, cras_tm_create_timer_called);
233 EXPECT_EQ(1, cras_hfp_ag_remove_conflict_called);
234 EXPECT_EQ(1, cras_a2dp_start_called);
235
236 cras_bt_device_remove(device);
237 FreeMockDBusMessage(msg_root);
238 }
239
TEST_F(BtDeviceTestSuite,SetDeviceConnectedHfpHspOnly)240 TEST_F(BtDeviceTestSuite, SetDeviceConnectedHfpHspOnly) {
241 struct cras_bt_device* device;
242 struct MockDBusMessage *msg_root, *cur;
243
244 ResetStubData();
245
246 device = cras_bt_device_create(NULL, FAKE_OBJ_PATH);
247 EXPECT_NE((void*)NULL, device);
248
249 cras_bt_device_add_supported_profiles(device, HSP_HS_UUID);
250 cras_bt_device_add_supported_profiles(device, HFP_HF_UUID);
251
252 cur = msg_root = NewMockDBusConnectedMessage();
253 cras_bt_device_update_properties(device, (DBusMessageIter*)&cur, NULL);
254 EXPECT_EQ(1, cras_tm_create_timer_called);
255 EXPECT_NE((void*)NULL, cras_tm_create_timer_cb);
256
257 /* Schedule another timer, if HFP AG not yet intialized. */
258 cras_tm_create_timer_cb(NULL, cras_tm_create_timer_cb_data);
259 EXPECT_EQ(2, cras_tm_create_timer_called);
260 EXPECT_EQ(1, dbus_message_new_method_call_called);
261 EXPECT_STREQ("ConnectProfile", dbus_message_new_method_call_method);
262
263 cras_bt_device_audio_gateway_initialized(device);
264
265 cras_tm_create_timer_cb(NULL, cras_tm_create_timer_cb_data);
266 EXPECT_EQ(2, cras_tm_create_timer_called);
267 EXPECT_EQ(1, cras_hfp_ag_remove_conflict_called);
268 EXPECT_EQ(1, cras_hfp_ag_start_called);
269
270 cras_bt_device_remove(device);
271 FreeMockDBusMessage(msg_root);
272 }
273
TEST_F(BtDeviceTestSuite,SetDeviceConnectedA2dpHfpHsp)274 TEST_F(BtDeviceTestSuite, SetDeviceConnectedA2dpHfpHsp) {
275 struct cras_bt_device* device;
276 struct MockDBusMessage *msg_root, *cur;
277
278 ResetStubData();
279
280 device = cras_bt_device_create(NULL, FAKE_OBJ_PATH);
281 EXPECT_NE((void*)NULL, device);
282
283 cras_bt_device_add_supported_profiles(device, A2DP_SINK_UUID);
284 cras_bt_device_add_supported_profiles(device, HSP_HS_UUID);
285 cras_bt_device_add_supported_profiles(device, HFP_HF_UUID);
286
287 cur = msg_root = NewMockDBusConnectedMessage();
288 cras_bt_device_update_properties(device, (DBusMessageIter*)&cur, NULL);
289 EXPECT_EQ(1, cras_tm_create_timer_called);
290 EXPECT_NE((void*)NULL, cras_tm_create_timer_cb);
291
292 /* Schedule another timer, if not HFP nor A2DP is ready. */
293 cras_tm_create_timer_cb(NULL, cras_tm_create_timer_cb_data);
294 EXPECT_EQ(2, cras_tm_create_timer_called);
295
296 cras_bt_device_audio_gateway_initialized(device);
297
298 /* Schedule another timer, because A2DP is not ready. */
299 cras_tm_create_timer_cb(NULL, cras_tm_create_timer_cb_data);
300 EXPECT_EQ(3, cras_tm_create_timer_called);
301 EXPECT_EQ(0, cras_hfp_ag_start_called);
302 EXPECT_EQ(1, dbus_message_new_method_call_called);
303 EXPECT_STREQ("ConnectProfile", dbus_message_new_method_call_method);
304
305 cras_bt_device_a2dp_configured(device);
306
307 cras_tm_create_timer_cb(NULL, cras_tm_create_timer_cb_data);
308 EXPECT_EQ(3, cras_tm_create_timer_called);
309 EXPECT_EQ(1, cras_hfp_ag_remove_conflict_called);
310 EXPECT_EQ(1, cras_a2dp_start_called);
311 EXPECT_EQ(1, cras_hfp_ag_start_called);
312
313 cras_bt_device_remove(device);
314 FreeMockDBusMessage(msg_root);
315 }
316
TEST_F(BtDeviceTestSuite,DevConnectedConflictCheck)317 TEST_F(BtDeviceTestSuite, DevConnectedConflictCheck) {
318 struct cras_bt_device* device;
319 struct MockDBusMessage *msg_root, *cur;
320
321 ResetStubData();
322
323 device = cras_bt_device_create(NULL, FAKE_OBJ_PATH);
324 EXPECT_NE((void*)NULL, device);
325
326 cras_bt_device_add_supported_profiles(device, A2DP_SINK_UUID);
327 cras_bt_device_add_supported_profiles(device, HSP_HS_UUID);
328 cras_bt_device_add_supported_profiles(device, HFP_HF_UUID);
329
330 cur = msg_root = NewMockDBusConnectedMessage();
331 cras_bt_device_update_properties(device, (DBusMessageIter*)&cur, NULL);
332 cras_bt_device_audio_gateway_initialized(device);
333 cras_bt_device_a2dp_configured(device);
334 EXPECT_EQ(1, cras_tm_create_timer_called);
335
336 /* Fake that a different device already connected with A2DP */
337 cras_a2dp_connected_device_ret =
338 reinterpret_cast<struct cras_bt_device*>(0x99);
339 cras_tm_create_timer_cb(NULL, cras_tm_create_timer_cb_data);
340 EXPECT_EQ(1, cras_tm_create_timer_called);
341
342 /* Expect check conflict in HFP AG and A2DP. */
343 EXPECT_EQ(1, cras_hfp_ag_remove_conflict_called);
344 EXPECT_EQ(1, cras_a2dp_suspend_connected_device_called);
345 EXPECT_EQ(cras_a2dp_suspend_connected_device_dev,
346 cras_a2dp_connected_device_ret);
347
348 EXPECT_EQ(1, cras_a2dp_start_called);
349 EXPECT_EQ(1, cras_hfp_ag_start_called);
350
351 cras_bt_device_remove(device);
352 FreeMockDBusMessage(msg_root);
353 }
354
TEST_F(BtDeviceTestSuite,A2dpDropped)355 TEST_F(BtDeviceTestSuite, A2dpDropped) {
356 struct cras_bt_device* device;
357 struct MockDBusMessage *msg_root, *cur;
358
359 ResetStubData();
360
361 device = cras_bt_device_create(NULL, FAKE_OBJ_PATH);
362 EXPECT_NE((void*)NULL, device);
363
364 cras_bt_device_add_supported_profiles(device, A2DP_SINK_UUID);
365 cras_bt_device_add_supported_profiles(device, HSP_HS_UUID);
366 cras_bt_device_add_supported_profiles(device, HFP_HF_UUID);
367
368 cur = msg_root = NewMockDBusConnectedMessage();
369 cras_bt_device_update_properties(device, (DBusMessageIter*)&cur, NULL);
370 EXPECT_EQ(1, cras_tm_create_timer_called);
371 EXPECT_NE((void*)NULL, cras_tm_create_timer_cb);
372
373 /* Schedule another timer, if HFP AG not yet intialized. */
374 cras_tm_create_timer_cb(NULL, cras_tm_create_timer_cb_data);
375 EXPECT_EQ(2, cras_tm_create_timer_called);
376 EXPECT_EQ(1, dbus_message_new_method_call_called);
377 EXPECT_STREQ("ConnectProfile", dbus_message_new_method_call_method);
378
379 cras_bt_device_a2dp_configured(device);
380
381 cras_tm_create_timer_cb(NULL, cras_tm_create_timer_cb_data);
382 EXPECT_EQ(3, cras_tm_create_timer_called);
383
384 cras_bt_device_notify_profile_dropped(device,
385 CRAS_BT_DEVICE_PROFILE_A2DP_SINK);
386 EXPECT_EQ(4, cras_tm_create_timer_called);
387
388 /* Expect suspend timer is scheduled. */
389 cras_tm_create_timer_cb(NULL, cras_tm_create_timer_cb_data);
390 EXPECT_EQ(1, cras_a2dp_suspend_connected_device_called);
391 EXPECT_EQ(1, cras_hfp_ag_suspend_connected_device_called);
392 EXPECT_EQ(2, dbus_message_new_method_call_called);
393 EXPECT_STREQ("Disconnect", dbus_message_new_method_call_method);
394
395 cras_bt_device_remove(device);
396 FreeMockDBusMessage(msg_root);
397 }
398
TEST_F(BtDeviceTestSuite,ConnectionWatchTimeout)399 TEST_F(BtDeviceTestSuite, ConnectionWatchTimeout) {
400 struct cras_bt_device* device;
401 struct MockDBusMessage *msg_root, *cur;
402
403 ResetStubData();
404
405 device = cras_bt_device_create(NULL, FAKE_OBJ_PATH);
406 EXPECT_NE((void*)NULL, device);
407
408 cras_bt_device_add_supported_profiles(device, A2DP_SINK_UUID);
409 cras_bt_device_add_supported_profiles(device, HSP_HS_UUID);
410 cras_bt_device_add_supported_profiles(device, HFP_HF_UUID);
411
412 cur = msg_root = NewMockDBusConnectedMessage();
413 cras_bt_device_update_properties(device, (DBusMessageIter*)&cur, NULL);
414 EXPECT_EQ(1, cras_tm_create_timer_called);
415 EXPECT_NE((void*)NULL, cras_tm_create_timer_cb);
416
417 /* Schedule another timer, if HFP AG not yet intialized. */
418 cras_tm_create_timer_cb(NULL, cras_tm_create_timer_cb_data);
419 EXPECT_EQ(2, cras_tm_create_timer_called);
420 EXPECT_EQ(1, dbus_message_new_method_call_called);
421 EXPECT_STREQ("ConnectProfile", dbus_message_new_method_call_method);
422
423 cras_bt_device_a2dp_configured(device);
424
425 for (int i = 0; i < 29; i++) {
426 cras_tm_create_timer_cb(NULL, cras_tm_create_timer_cb_data);
427 EXPECT_EQ(i + 3, cras_tm_create_timer_called);
428 EXPECT_EQ(0, cras_a2dp_start_called);
429 EXPECT_EQ(0, cras_hfp_ag_start_called);
430 EXPECT_EQ(0, cras_hfp_ag_remove_conflict_called);
431 }
432
433 dbus_message_new_method_call_called = 0;
434
435 /* Expect suspend timer is scheduled. */
436 cras_tm_create_timer_cb(NULL, cras_tm_create_timer_cb_data);
437 EXPECT_EQ(1, cras_a2dp_suspend_connected_device_called);
438 EXPECT_EQ(1, cras_hfp_ag_suspend_connected_device_called);
439 EXPECT_EQ(1, dbus_message_new_method_call_called);
440 EXPECT_STREQ("Disconnect", dbus_message_new_method_call_method);
441
442 cras_bt_device_remove(device);
443 FreeMockDBusMessage(msg_root);
444 }
445
446 /* Stubs */
447 extern "C" {
448
449 struct cras_bt_event_log* btlog;
450
451 /* From bt_io */
cras_bt_io_create(struct cras_bt_device * device,struct cras_iodev * dev,enum cras_bt_device_profile profile)452 struct cras_iodev* cras_bt_io_create(struct cras_bt_device* device,
453 struct cras_iodev* dev,
454 enum cras_bt_device_profile profile) {
455 cras_bt_io_create_called++;
456 cras_bt_io_create_profile_val = profile;
457 return cras_bt_io_create_profile_ret;
458 }
cras_bt_io_destroy(struct cras_iodev * bt_iodev)459 void cras_bt_io_destroy(struct cras_iodev* bt_iodev) {
460 cras_bt_io_destroy_called++;
461 }
cras_bt_io_get_profile(struct cras_iodev * bt_iodev,enum cras_bt_device_profile profile)462 struct cras_ionode* cras_bt_io_get_profile(
463 struct cras_iodev* bt_iodev,
464 enum cras_bt_device_profile profile) {
465 return cras_bt_io_get_profile_ret;
466 }
cras_bt_io_append(struct cras_iodev * bt_iodev,struct cras_iodev * dev,enum cras_bt_device_profile profile)467 int cras_bt_io_append(struct cras_iodev* bt_iodev,
468 struct cras_iodev* dev,
469 enum cras_bt_device_profile profile) {
470 cras_bt_io_append_called++;
471 cras_bt_io_append_profile_val = profile;
472 cras_bt_io_append_btio_val = bt_iodev;
473 return 0;
474 }
cras_bt_io_on_profile(struct cras_iodev * bt_iodev,enum cras_bt_device_profile profile)475 int cras_bt_io_on_profile(struct cras_iodev* bt_iodev,
476 enum cras_bt_device_profile profile) {
477 return 0;
478 }
cras_bt_io_try_remove(struct cras_iodev * bt_iodev,struct cras_iodev * dev)479 unsigned int cras_bt_io_try_remove(struct cras_iodev* bt_iodev,
480 struct cras_iodev* dev) {
481 return cras_bt_io_try_remove_ret;
482 }
cras_bt_io_remove(struct cras_iodev * bt_iodev,struct cras_iodev * dev)483 int cras_bt_io_remove(struct cras_iodev* bt_iodev, struct cras_iodev* dev) {
484 cras_bt_io_remove_called++;
485 return 0;
486 }
487
488 /* From bt_adapter */
cras_bt_adapter_get(const char * object_path)489 struct cras_bt_adapter* cras_bt_adapter_get(const char* object_path) {
490 return NULL;
491 }
cras_bt_adapter_address(const struct cras_bt_adapter * adapter)492 const char* cras_bt_adapter_address(const struct cras_bt_adapter* adapter) {
493 return NULL;
494 }
495
cras_bt_adapter_on_usb(struct cras_bt_adapter * adapter)496 int cras_bt_adapter_on_usb(struct cras_bt_adapter* adapter) {
497 return 1;
498 }
499
500 /* From bt_profile */
cras_bt_profile_on_device_disconnected(struct cras_bt_device * device)501 void cras_bt_profile_on_device_disconnected(struct cras_bt_device* device) {}
502
503 /* From hfp_ag_profile */
cras_hfp_ag_get_slc(struct cras_bt_device * device)504 struct hfp_slc_handle* cras_hfp_ag_get_slc(struct cras_bt_device* device) {
505 return NULL;
506 }
507
cras_hfp_ag_suspend_connected_device(struct cras_bt_device * device)508 void cras_hfp_ag_suspend_connected_device(struct cras_bt_device* device) {
509 cras_hfp_ag_suspend_connected_device_called++;
510 }
511
cras_a2dp_suspend_connected_device(struct cras_bt_device * device)512 void cras_a2dp_suspend_connected_device(struct cras_bt_device* device) {
513 cras_a2dp_suspend_connected_device_called++;
514 cras_a2dp_suspend_connected_device_dev = device;
515 }
516
cras_a2dp_start(struct cras_bt_device * device)517 void cras_a2dp_start(struct cras_bt_device* device) {
518 cras_a2dp_start_called++;
519 }
520
cras_a2dp_connected_device()521 struct cras_bt_device* cras_a2dp_connected_device() {
522 return cras_a2dp_connected_device_ret;
523 }
524
cras_hfp_ag_remove_conflict(struct cras_bt_device * device)525 int cras_hfp_ag_remove_conflict(struct cras_bt_device* device) {
526 cras_hfp_ag_remove_conflict_called++;
527 return 0;
528 }
529
cras_hfp_ag_start(struct cras_bt_device * device)530 int cras_hfp_ag_start(struct cras_bt_device* device) {
531 cras_hfp_ag_start_called++;
532 return 0;
533 }
534
cras_hfp_ag_suspend()535 void cras_hfp_ag_suspend() {}
536
537 /* From hfp_slc */
hfp_event_speaker_gain(struct hfp_slc_handle * handle,int gain)538 int hfp_event_speaker_gain(struct hfp_slc_handle* handle, int gain) {
539 return 0;
540 }
541
542 /* From iodev_list */
543
cras_iodev_open(struct cras_iodev * dev,unsigned int cb_level,const struct cras_audio_format * fmt)544 int cras_iodev_open(struct cras_iodev* dev,
545 unsigned int cb_level,
546 const struct cras_audio_format* fmt) {
547 return 0;
548 }
549
cras_iodev_close(struct cras_iodev * dev)550 int cras_iodev_close(struct cras_iodev* dev) {
551 return 0;
552 }
553
cras_iodev_list_dev_is_enabled(const struct cras_iodev * dev)554 int cras_iodev_list_dev_is_enabled(const struct cras_iodev* dev) {
555 return 0;
556 }
557
cras_iodev_list_suspend_dev(struct cras_iodev * dev)558 void cras_iodev_list_suspend_dev(struct cras_iodev* dev) {}
559
cras_iodev_list_resume_dev(struct cras_iodev * dev)560 void cras_iodev_list_resume_dev(struct cras_iodev* dev) {}
561
cras_iodev_list_notify_node_volume(struct cras_ionode * node)562 void cras_iodev_list_notify_node_volume(struct cras_ionode* node) {}
563
cras_main_message_send(struct cras_main_message * msg)564 int cras_main_message_send(struct cras_main_message* msg) {
565 // cras_main_message is a local variable from caller, we should allocate
566 // memory from heap and copy its data
567 if (cras_main_message_send_msg)
568 free(cras_main_message_send_msg);
569 cras_main_message_send_msg =
570 (struct cras_main_message*)calloc(1, msg->length);
571 memcpy((void*)cras_main_message_send_msg, (void*)msg, msg->length);
572 return 0;
573 }
574
cras_main_message_add_handler(enum CRAS_MAIN_MESSAGE_TYPE type,cras_message_callback callback,void * callback_data)575 int cras_main_message_add_handler(enum CRAS_MAIN_MESSAGE_TYPE type,
576 cras_message_callback callback,
577 void* callback_data) {
578 cras_main_message_add_handler_callback = callback;
579 cras_main_message_add_handler_callback_data = callback_data;
580 return 0;
581 }
582
583 /* From cras_system_state */
cras_system_state_get_tm()584 struct cras_tm* cras_system_state_get_tm() {
585 return NULL;
586 }
587
588 /* From cras_tm */
cras_tm_create_timer(struct cras_tm * tm,unsigned int ms,void (* cb)(struct cras_timer * t,void * data),void * cb_data)589 struct cras_timer* cras_tm_create_timer(struct cras_tm* tm,
590 unsigned int ms,
591 void (*cb)(struct cras_timer* t,
592 void* data),
593 void* cb_data) {
594 cras_tm_create_timer_called++;
595 cras_tm_create_timer_cb = cb;
596 cras_tm_create_timer_cb_data = cb_data;
597 return NULL;
598 }
599
cras_tm_cancel_timer(struct cras_tm * tm,struct cras_timer * t)600 void cras_tm_cancel_timer(struct cras_tm* tm, struct cras_timer* t) {}
601
dbus_message_new_method_call(const char * destination,const char * path,const char * iface,const char * method)602 DBusMessage* dbus_message_new_method_call(const char* destination,
603 const char* path,
604 const char* iface,
605 const char* method) {
606 dbus_message_new_method_call_called++;
607 dbus_message_new_method_call_method = method;
608 return reinterpret_cast<DBusMessage*>(0x456);
609 }
610
dbus_message_unref(DBusMessage * message)611 void dbus_message_unref(DBusMessage* message) {}
612
dbus_message_append_args(DBusMessage * message,int first_arg_type,...)613 dbus_bool_t dbus_message_append_args(DBusMessage* message,
614 int first_arg_type,
615 ...) {
616 return true;
617 }
618
dbus_connection_send_with_reply(DBusConnection * connection,DBusMessage * message,DBusPendingCall ** pending_return,int timeout_milliseconds)619 dbus_bool_t dbus_connection_send_with_reply(DBusConnection* connection,
620 DBusMessage* message,
621 DBusPendingCall** pending_return,
622 int timeout_milliseconds) {
623 return true;
624 }
625
dbus_pending_call_set_notify(DBusPendingCall * pending,DBusPendingCallNotifyFunction function,void * user_data,DBusFreeFunction free_user_data)626 dbus_bool_t dbus_pending_call_set_notify(DBusPendingCall* pending,
627 DBusPendingCallNotifyFunction function,
628 void* user_data,
629 DBusFreeFunction free_user_data) {
630 return true;
631 }
632
dbus_message_iter_recurse(DBusMessageIter * iter,DBusMessageIter * sub)633 void dbus_message_iter_recurse(DBusMessageIter* iter, DBusMessageIter* sub) {
634 MockDBusMessage* msg = *(MockDBusMessage**)iter;
635 MockDBusMessage** cur = (MockDBusMessage**)sub;
636 *cur = msg->recurse;
637 }
638
dbus_message_iter_next(DBusMessageIter * iter)639 dbus_bool_t dbus_message_iter_next(DBusMessageIter* iter) {
640 MockDBusMessage** cur = (MockDBusMessage**)iter;
641 MockDBusMessage* msg = *cur;
642 *cur = msg->next;
643 return true;
644 }
645
dbus_message_iter_get_arg_type(DBusMessageIter * iter)646 int dbus_message_iter_get_arg_type(DBusMessageIter* iter) {
647 MockDBusMessage* msg;
648
649 if (iter == NULL)
650 return DBUS_TYPE_INVALID;
651
652 msg = *(MockDBusMessage**)iter;
653 if (msg == NULL)
654 return DBUS_TYPE_INVALID;
655
656 return msg->type;
657 }
658
dbus_message_iter_get_basic(DBusMessageIter * iter,void * value)659 void dbus_message_iter_get_basic(DBusMessageIter* iter, void* value) {
660 MockDBusMessage* msg = *(MockDBusMessage**)iter;
661 switch (msg->type) {
662 case DBUS_TYPE_BOOLEAN:
663 memcpy(value, &msg->value, sizeof(int));
664 break;
665 case DBUS_TYPE_STRING:
666 memcpy(value, &msg->value, sizeof(char*));
667 break;
668 }
669 }
670
671 } // extern "C"
672 } // namespace
673
main(int argc,char ** argv)674 int main(int argc, char** argv) {
675 ::testing::InitGoogleTest(&argc, argv);
676 return RUN_ALL_TESTS();
677 }
678