1 // Copyright 2016 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 #include <stdio.h>
7 #include <syslog.h>
8 
9 #include <map>
10 #include <vector>
11 
12 extern "C" {
13 #include "cras_observer.c"
14 #include "cras_observer.h"
15 #include "cras_types.h"
16 }
17 
18 namespace {
19 
20 static size_t cras_alert_destroy_called;
21 static size_t cras_alert_create_called;
22 static std::vector<struct cras_alert*> cras_alert_create_return_values;
23 typedef std::map<struct cras_alert*, void*> alert_callback_map;
24 static alert_callback_map cras_alert_create_prepare_map;
25 static alert_callback_map cras_alert_add_callback_map;
26 typedef std::map<struct cras_alert*, unsigned int> alert_flags_map;
27 static alert_flags_map cras_alert_create_flags_map;
28 static struct cras_alert* cras_alert_pending_alert_value;
29 static void* cras_alert_pending_data_value = NULL;
30 static size_t cras_alert_pending_data_size_value;
31 static size_t cras_iodev_list_update_device_list_called;
32 static std::vector<void*> cb_context;
33 static size_t cb_output_volume_changed_called;
34 static std::vector<int32_t> cb_output_volume_changed_volume;
35 static size_t cb_output_mute_changed_called;
36 static std::vector<int> cb_output_mute_changed_muted;
37 static std::vector<int> cb_output_mute_changed_user_muted;
38 static std::vector<int> cb_output_mute_changed_mute_locked;
39 static size_t cb_capture_gain_changed_called;
40 static std::vector<int32_t> cb_capture_gain_changed_gain;
41 static size_t cb_capture_mute_changed_called;
42 static std::vector<int> cb_capture_mute_changed_muted;
43 static std::vector<int> cb_capture_mute_changed_mute_locked;
44 static size_t cb_nodes_changed_called;
45 static size_t cb_active_node_changed_called;
46 static std::vector<enum CRAS_STREAM_DIRECTION> cb_active_node_changed_dir;
47 static std::vector<cras_node_id_t> cb_active_node_changed_node_id;
48 static size_t cb_output_node_volume_changed_called;
49 static std::vector<cras_node_id_t> cb_output_node_volume_changed_node_id;
50 static std::vector<int32_t> cb_output_node_volume_changed_volume;
51 static size_t cb_node_left_right_swapped_changed_called;
52 static std::vector<cras_node_id_t> cb_node_left_right_swapped_changed_node_id;
53 static std::vector<int> cb_node_left_right_swapped_changed_swapped;
54 static size_t cb_input_node_gain_changed_called;
55 static std::vector<cras_node_id_t> cb_input_node_gain_changed_node_id;
56 static std::vector<int32_t> cb_input_node_gain_changed_gain;
57 static size_t cb_num_active_streams_changed_called;
58 static std::vector<enum CRAS_STREAM_DIRECTION>
59     cb_num_active_streams_changed_dir;
60 static std::vector<uint32_t> cb_num_active_streams_changed_num;
61 static size_t cb_num_input_streams_with_permission_called;
62 static std::vector<std::vector<uint32_t>>
63     cb_num_input_streams_with_permission_array;
64 
ResetStubData()65 static void ResetStubData() {
66   cras_alert_destroy_called = 0;
67   cras_alert_create_called = 0;
68   cras_alert_create_return_values.clear();
69   cras_alert_create_prepare_map.clear();
70   cras_alert_create_flags_map.clear();
71   cras_alert_add_callback_map.clear();
72   cras_alert_pending_alert_value = NULL;
73   cras_alert_pending_data_size_value = 0;
74   if (cras_alert_pending_data_value) {
75     free(cras_alert_pending_data_value);
76     cras_alert_pending_data_value = NULL;
77   }
78   cras_iodev_list_update_device_list_called = 0;
79   cb_context.clear();
80   cb_output_volume_changed_called = 0;
81   cb_output_volume_changed_volume.clear();
82   cb_output_mute_changed_called = 0;
83   cb_output_mute_changed_muted.clear();
84   cb_output_mute_changed_user_muted.clear();
85   cb_output_mute_changed_mute_locked.clear();
86   cb_capture_gain_changed_called = 0;
87   cb_capture_gain_changed_gain.clear();
88   cb_capture_mute_changed_called = 0;
89   cb_capture_mute_changed_muted.clear();
90   cb_capture_mute_changed_mute_locked.clear();
91   cb_nodes_changed_called = 0;
92   cb_active_node_changed_called = 0;
93   cb_active_node_changed_dir.clear();
94   cb_active_node_changed_node_id.clear();
95   cb_output_node_volume_changed_called = 0;
96   cb_output_node_volume_changed_node_id.clear();
97   cb_output_node_volume_changed_volume.clear();
98   cb_node_left_right_swapped_changed_called = 0;
99   cb_node_left_right_swapped_changed_node_id.clear();
100   cb_node_left_right_swapped_changed_swapped.clear();
101   cb_input_node_gain_changed_called = 0;
102   cb_input_node_gain_changed_node_id.clear();
103   cb_input_node_gain_changed_gain.clear();
104   cb_num_active_streams_changed_called = 0;
105   cb_num_active_streams_changed_dir.clear();
106   cb_num_active_streams_changed_num.clear();
107   cb_num_input_streams_with_permission_called = 0;
108   cb_num_input_streams_with_permission_array.clear();
109 }
110 
111 /* System output volume changed. */
cb_output_volume_changed(void * context,int32_t volume)112 void cb_output_volume_changed(void* context, int32_t volume) {
113   cb_output_volume_changed_called++;
114   cb_context.push_back(context);
115   cb_output_volume_changed_volume.push_back(volume);
116 }
117 /* System output mute changed. */
cb_output_mute_changed(void * context,int muted,int user_muted,int mute_locked)118 void cb_output_mute_changed(void* context,
119                             int muted,
120                             int user_muted,
121                             int mute_locked) {
122   cb_output_mute_changed_called++;
123   cb_context.push_back(context);
124   cb_output_mute_changed_muted.push_back(muted);
125   cb_output_mute_changed_user_muted.push_back(user_muted);
126   cb_output_mute_changed_mute_locked.push_back(mute_locked);
127 }
128 /* System input/capture gain changed. */
cb_capture_gain_changed(void * context,int32_t gain)129 void cb_capture_gain_changed(void* context, int32_t gain) {
130   cb_capture_gain_changed_called++;
131   cb_context.push_back(context);
132   cb_capture_gain_changed_gain.push_back(gain);
133 }
134 
135 /* System input/capture mute changed. */
cb_capture_mute_changed(void * context,int muted,int mute_locked)136 void cb_capture_mute_changed(void* context, int muted, int mute_locked) {
137   cb_capture_mute_changed_called++;
138   cb_context.push_back(context);
139   cb_capture_mute_changed_muted.push_back(muted);
140   cb_capture_mute_changed_mute_locked.push_back(mute_locked);
141 }
142 
143 /* Device or node topology changed. */
cb_nodes_changed(void * context)144 void cb_nodes_changed(void* context) {
145   cb_nodes_changed_called++;
146   cb_context.push_back(context);
147 }
148 
149 /* Active node changed. A notification is sent for every change.
150  * When there is no active node, node_id is 0. */
cb_active_node_changed(void * context,enum CRAS_STREAM_DIRECTION dir,cras_node_id_t node_id)151 void cb_active_node_changed(void* context,
152                             enum CRAS_STREAM_DIRECTION dir,
153                             cras_node_id_t node_id) {
154   cb_active_node_changed_called++;
155   cb_context.push_back(context);
156   cb_active_node_changed_dir.push_back(dir);
157   cb_active_node_changed_node_id.push_back(node_id);
158 }
159 
160 /* Output node volume changed. */
cb_output_node_volume_changed(void * context,cras_node_id_t node_id,int32_t volume)161 void cb_output_node_volume_changed(void* context,
162                                    cras_node_id_t node_id,
163                                    int32_t volume) {
164   cb_output_node_volume_changed_called++;
165   cb_context.push_back(context);
166   cb_output_node_volume_changed_node_id.push_back(node_id);
167   cb_output_node_volume_changed_volume.push_back(volume);
168 }
169 
170 /* Node left/right swapped state change. */
cb_node_left_right_swapped_changed(void * context,cras_node_id_t node_id,int swapped)171 void cb_node_left_right_swapped_changed(void* context,
172                                         cras_node_id_t node_id,
173                                         int swapped) {
174   cb_node_left_right_swapped_changed_called++;
175   cb_context.push_back(context);
176   cb_node_left_right_swapped_changed_node_id.push_back(node_id);
177   cb_node_left_right_swapped_changed_swapped.push_back(swapped);
178 }
179 
180 /* Input gain changed. */
cb_input_node_gain_changed(void * context,cras_node_id_t node_id,int32_t gain)181 void cb_input_node_gain_changed(void* context,
182                                 cras_node_id_t node_id,
183                                 int32_t gain) {
184   cb_input_node_gain_changed_called++;
185   cb_context.push_back(context);
186   cb_input_node_gain_changed_node_id.push_back(node_id);
187   cb_input_node_gain_changed_gain.push_back(gain);
188 }
189 
190 /* Number of active streams changed. */
cb_num_active_streams_changed(void * context,enum CRAS_STREAM_DIRECTION dir,uint32_t num_active_streams)191 void cb_num_active_streams_changed(void* context,
192                                    enum CRAS_STREAM_DIRECTION dir,
193                                    uint32_t num_active_streams) {
194   cb_num_active_streams_changed_called++;
195   cb_context.push_back(context);
196   cb_num_active_streams_changed_dir.push_back(dir);
197   cb_num_active_streams_changed_num.push_back(num_active_streams);
198 }
199 
cb_num_input_streams_with_permission_changed(void * context,uint32_t num_input_streams[CRAS_NUM_CLIENT_TYPE])200 void cb_num_input_streams_with_permission_changed(
201     void* context,
202     uint32_t num_input_streams[CRAS_NUM_CLIENT_TYPE]) {
203   cb_num_input_streams_with_permission_called++;
204   cb_context.push_back(context);
205   cb_num_input_streams_with_permission_array.push_back(std::vector<uint32_t>(
206       num_input_streams, num_input_streams + CRAS_NUM_CLIENT_TYPE));
207 }
208 
209 class ObserverTest : public testing::Test {
210  protected:
SetUp()211   virtual void SetUp() {
212     int rc;
213 
214     ResetStubData();
215     rc = cras_observer_server_init();
216     ASSERT_EQ(0, rc);
217     EXPECT_EQ(17, cras_alert_create_called);
218     EXPECT_EQ(reinterpret_cast<void*>(output_volume_alert),
219               cras_alert_add_callback_map[g_observer->alerts.output_volume]);
220     EXPECT_EQ(reinterpret_cast<void*>(output_mute_alert),
221               cras_alert_add_callback_map[g_observer->alerts.output_mute]);
222     EXPECT_EQ(reinterpret_cast<void*>(capture_gain_alert),
223               cras_alert_add_callback_map[g_observer->alerts.capture_gain]);
224     EXPECT_EQ(reinterpret_cast<void*>(capture_mute_alert),
225               cras_alert_add_callback_map[g_observer->alerts.capture_mute]);
226     EXPECT_EQ(reinterpret_cast<void*>(nodes_alert),
227               cras_alert_add_callback_map[g_observer->alerts.nodes]);
228     EXPECT_EQ(reinterpret_cast<void*>(nodes_prepare),
229               cras_alert_create_prepare_map[g_observer->alerts.nodes]);
230     EXPECT_EQ(reinterpret_cast<void*>(active_node_alert),
231               cras_alert_add_callback_map[g_observer->alerts.active_node]);
232     EXPECT_EQ(CRAS_ALERT_FLAG_KEEP_ALL_DATA,
233               cras_alert_create_flags_map[g_observer->alerts.active_node]);
234     EXPECT_EQ(
235         reinterpret_cast<void*>(output_node_volume_alert),
236         cras_alert_add_callback_map[g_observer->alerts.output_node_volume]);
237     EXPECT_EQ(reinterpret_cast<void*>(node_left_right_swapped_alert),
238               cras_alert_add_callback_map[g_observer->alerts
239                                               .node_left_right_swapped]);
240     EXPECT_EQ(reinterpret_cast<void*>(input_node_gain_alert),
241               cras_alert_add_callback_map[g_observer->alerts.input_node_gain]);
242     EXPECT_EQ(reinterpret_cast<void*>(num_active_streams_alert),
243               cras_alert_add_callback_map
244                   [g_observer->alerts.num_active_streams[CRAS_STREAM_OUTPUT]]);
245     EXPECT_EQ(reinterpret_cast<void*>(num_active_streams_alert),
246               cras_alert_add_callback_map
247                   [g_observer->alerts.num_active_streams[CRAS_STREAM_INPUT]]);
248     EXPECT_EQ(reinterpret_cast<void*>(num_active_streams_alert),
249               cras_alert_add_callback_map[g_observer->alerts.num_active_streams
250                                               [CRAS_STREAM_POST_MIX_PRE_DSP]]);
251     EXPECT_EQ(reinterpret_cast<void*>(suspend_changed_alert),
252               cras_alert_add_callback_map[g_observer->alerts.suspend_changed]);
253     EXPECT_EQ(
254         reinterpret_cast<void*>(hotword_triggered_alert),
255         cras_alert_add_callback_map[g_observer->alerts.hotword_triggered]);
256     EXPECT_EQ(reinterpret_cast<void*>(non_empty_audio_state_changed_alert),
257               cras_alert_add_callback_map[g_observer->alerts
258                                               .non_empty_audio_state_changed]);
259     EXPECT_EQ(
260         reinterpret_cast<void*>(bt_battery_changed_alert),
261         cras_alert_add_callback_map[g_observer->alerts.bt_battery_changed]);
262 
263     cras_observer_get_ops(NULL, &ops1_);
264     EXPECT_NE(0, cras_observer_ops_are_empty(&ops1_));
265 
266     cras_observer_get_ops(NULL, &ops2_);
267     EXPECT_NE(0, cras_observer_ops_are_empty(&ops2_));
268 
269     context1_ = reinterpret_cast<void*>(1);
270     context2_ = reinterpret_cast<void*>(2);
271   }
272 
TearDown()273   virtual void TearDown() {
274     cras_observer_server_free();
275     EXPECT_EQ(17, cras_alert_destroy_called);
276     ResetStubData();
277   }
278 
DoObserverAlert(cras_alert_cb alert,void * data)279   void DoObserverAlert(cras_alert_cb alert, void* data) {
280     client1_ = cras_observer_add(&ops1_, context1_);
281     client2_ = cras_observer_add(&ops2_, context2_);
282     ASSERT_NE(client1_, reinterpret_cast<struct cras_observer_client*>(NULL));
283     ASSERT_NE(client2_, reinterpret_cast<struct cras_observer_client*>(NULL));
284 
285     ASSERT_NE(alert, reinterpret_cast<cras_alert_cb>(NULL));
286     alert(NULL, data);
287 
288     EXPECT_EQ(cb_context[0], context1_);
289     EXPECT_EQ(cb_context[1], context2_);
290   }
291 
DoObserverRemoveClear(cras_alert_cb alert,void * data)292   void DoObserverRemoveClear(cras_alert_cb alert, void* data) {
293     ASSERT_NE(alert, reinterpret_cast<cras_alert_cb>(NULL));
294     ASSERT_NE(client1_, reinterpret_cast<struct cras_observer_client*>(NULL));
295     ASSERT_NE(client2_, reinterpret_cast<struct cras_observer_client*>(NULL));
296 
297     // Test observer removal.
298     cras_observer_remove(client1_);
299     cb_context.clear();
300     alert(NULL, data);
301     EXPECT_EQ(cb_context[0], context2_);
302     EXPECT_EQ(cb_context.size(), 1);
303 
304     // Clear out ops1_.
305     cras_observer_get_ops(NULL, &ops1_);
306     EXPECT_NE(0, cras_observer_ops_are_empty(&ops1_));
307 
308     // Get the current value of ops2_ into ops1_.
309     cras_observer_get_ops(client2_, &ops1_);
310     EXPECT_EQ(0, memcmp((void*)&ops1_, (void*)&ops2_, sizeof(ops1_)));
311 
312     // Clear out opts for client2.
313     cras_observer_get_ops(NULL, &ops2_);
314     EXPECT_NE(0, cras_observer_ops_are_empty(&ops2_));
315     cras_observer_set_ops(client2_, &ops2_);
316 
317     cras_observer_remove(client2_);
318     cb_context.clear();
319     alert(NULL, data);
320     // No callbacks executed.
321     EXPECT_EQ(cb_context.size(), 0);
322   }
323 
324   struct cras_observer_client* client1_;
325   struct cras_observer_client* client2_;
326   struct cras_observer_ops ops1_;
327   struct cras_observer_ops ops2_;
328   void* context1_;
329   void* context2_;
330 };
331 
TEST_F(ObserverTest,NotifyOutputVolume)332 TEST_F(ObserverTest, NotifyOutputVolume) {
333   struct cras_observer_alert_data_volume* data;
334   const int32_t volume = 100;
335 
336   cras_observer_notify_output_volume(volume);
337   EXPECT_EQ(cras_alert_pending_alert_value, g_observer->alerts.output_volume);
338   ASSERT_EQ(cras_alert_pending_data_size_value, sizeof(*data));
339   ASSERT_NE(cras_alert_pending_data_value, reinterpret_cast<void*>(NULL));
340   data = reinterpret_cast<struct cras_observer_alert_data_volume*>(
341       cras_alert_pending_data_value);
342   EXPECT_EQ(data->volume, volume);
343 
344   ops1_.output_volume_changed = cb_output_volume_changed;
345   ops2_.output_volume_changed = cb_output_volume_changed;
346   DoObserverAlert(output_volume_alert, data);
347   ASSERT_EQ(2, cb_output_volume_changed_called);
348   EXPECT_EQ(cb_output_volume_changed_volume[0], volume);
349   EXPECT_EQ(cb_output_volume_changed_volume[1], volume);
350 
351   DoObserverRemoveClear(output_volume_alert, data);
352 };
353 
TEST_F(ObserverTest,NotifyOutputMute)354 TEST_F(ObserverTest, NotifyOutputMute) {
355   struct cras_observer_alert_data_mute* data;
356   const int muted = 1;
357   const int user_muted = 0;
358   const int mute_locked = 0;
359 
360   cras_observer_notify_output_mute(muted, user_muted, mute_locked);
361   EXPECT_EQ(cras_alert_pending_alert_value, g_observer->alerts.output_mute);
362   ASSERT_EQ(cras_alert_pending_data_size_value, sizeof(*data));
363   ASSERT_NE(cras_alert_pending_data_value, reinterpret_cast<void*>(NULL));
364   data = reinterpret_cast<struct cras_observer_alert_data_mute*>(
365       cras_alert_pending_data_value);
366   EXPECT_EQ(data->muted, muted);
367   EXPECT_EQ(data->user_muted, user_muted);
368   EXPECT_EQ(data->mute_locked, mute_locked);
369 
370   ops1_.output_mute_changed = cb_output_mute_changed;
371   ops2_.output_mute_changed = cb_output_mute_changed;
372   DoObserverAlert(output_mute_alert, data);
373   ASSERT_EQ(2, cb_output_mute_changed_called);
374   EXPECT_EQ(cb_output_mute_changed_muted[0], muted);
375   EXPECT_EQ(cb_output_mute_changed_muted[1], muted);
376   EXPECT_EQ(cb_output_mute_changed_user_muted[0], user_muted);
377   EXPECT_EQ(cb_output_mute_changed_user_muted[1], user_muted);
378   EXPECT_EQ(cb_output_mute_changed_mute_locked[0], mute_locked);
379   EXPECT_EQ(cb_output_mute_changed_mute_locked[1], mute_locked);
380 
381   DoObserverRemoveClear(output_mute_alert, data);
382 };
383 
TEST_F(ObserverTest,NotifyCaptureGain)384 TEST_F(ObserverTest, NotifyCaptureGain) {
385   struct cras_observer_alert_data_volume* data;
386   const int32_t gain = -20;
387 
388   cras_observer_notify_capture_gain(gain);
389   EXPECT_EQ(cras_alert_pending_alert_value, g_observer->alerts.capture_gain);
390   ASSERT_EQ(cras_alert_pending_data_size_value, sizeof(*data));
391   ASSERT_NE(cras_alert_pending_data_value, reinterpret_cast<void*>(NULL));
392   data = reinterpret_cast<struct cras_observer_alert_data_volume*>(
393       cras_alert_pending_data_value);
394   EXPECT_EQ(data->volume, gain);
395 
396   ops1_.capture_gain_changed = cb_capture_gain_changed;
397   ops2_.capture_gain_changed = cb_capture_gain_changed;
398   DoObserverAlert(capture_gain_alert, data);
399   ASSERT_EQ(2, cb_capture_gain_changed_called);
400   EXPECT_EQ(cb_capture_gain_changed_gain[0], gain);
401   EXPECT_EQ(cb_capture_gain_changed_gain[1], gain);
402 
403   DoObserverRemoveClear(capture_gain_alert, data);
404 };
405 
TEST_F(ObserverTest,NotifyCaptureMute)406 TEST_F(ObserverTest, NotifyCaptureMute) {
407   struct cras_observer_alert_data_mute* data;
408   const int muted = 1;
409   const int mute_locked = 0;
410 
411   cras_observer_notify_capture_mute(muted, mute_locked);
412   EXPECT_EQ(cras_alert_pending_alert_value, g_observer->alerts.capture_mute);
413   ASSERT_EQ(cras_alert_pending_data_size_value, sizeof(*data));
414   ASSERT_NE(cras_alert_pending_data_value, reinterpret_cast<void*>(NULL));
415   data = reinterpret_cast<struct cras_observer_alert_data_mute*>(
416       cras_alert_pending_data_value);
417   EXPECT_EQ(data->muted, muted);
418   EXPECT_EQ(data->mute_locked, mute_locked);
419 
420   ops1_.capture_mute_changed = cb_capture_mute_changed;
421   ops2_.capture_mute_changed = cb_capture_mute_changed;
422   DoObserverAlert(capture_mute_alert, data);
423   ASSERT_EQ(2, cb_capture_mute_changed_called);
424   EXPECT_EQ(cb_capture_mute_changed_muted[0], muted);
425   EXPECT_EQ(cb_capture_mute_changed_muted[1], muted);
426   EXPECT_EQ(cb_capture_mute_changed_mute_locked[0], mute_locked);
427   EXPECT_EQ(cb_capture_mute_changed_mute_locked[1], mute_locked);
428 
429   DoObserverRemoveClear(capture_mute_alert, data);
430 };
431 
TEST_F(ObserverTest,NotifyNodes)432 TEST_F(ObserverTest, NotifyNodes) {
433   cras_observer_notify_nodes();
434   EXPECT_EQ(cras_alert_pending_alert_value, g_observer->alerts.nodes);
435 
436   ops1_.nodes_changed = cb_nodes_changed;
437   ops2_.nodes_changed = cb_nodes_changed;
438   DoObserverAlert(nodes_alert, NULL);
439   ASSERT_EQ(2, cb_nodes_changed_called);
440 
441   DoObserverRemoveClear(nodes_alert, NULL);
442 };
443 
TEST_F(ObserverTest,NotifyActiveNode)444 TEST_F(ObserverTest, NotifyActiveNode) {
445   struct cras_observer_alert_data_active_node* data;
446   const enum CRAS_STREAM_DIRECTION dir = CRAS_STREAM_INPUT;
447   const cras_node_id_t node_id = 0x0001000100020002;
448 
449   cras_observer_notify_active_node(dir, node_id);
450   EXPECT_EQ(cras_alert_pending_alert_value, g_observer->alerts.active_node);
451   ASSERT_EQ(cras_alert_pending_data_size_value, sizeof(*data));
452   ASSERT_NE(cras_alert_pending_data_value, reinterpret_cast<void*>(NULL));
453   data = reinterpret_cast<struct cras_observer_alert_data_active_node*>(
454       cras_alert_pending_data_value);
455   EXPECT_EQ(data->node_id, node_id);
456   EXPECT_EQ(data->direction, dir);
457 
458   ops1_.active_node_changed = cb_active_node_changed;
459   ops2_.active_node_changed = cb_active_node_changed;
460   DoObserverAlert(active_node_alert, data);
461   ASSERT_EQ(2, cb_active_node_changed_called);
462   EXPECT_EQ(cb_active_node_changed_dir[0], dir);
463   EXPECT_EQ(cb_active_node_changed_dir[1], dir);
464   EXPECT_EQ(cb_active_node_changed_node_id[0], node_id);
465   EXPECT_EQ(cb_active_node_changed_node_id[1], node_id);
466 
467   DoObserverRemoveClear(active_node_alert, data);
468 };
469 
TEST_F(ObserverTest,NotifyOutputNodeVolume)470 TEST_F(ObserverTest, NotifyOutputNodeVolume) {
471   struct cras_observer_alert_data_node_volume* data;
472   const cras_node_id_t node_id = 0x0001000100020002;
473   const int32_t volume = 100;
474 
475   cras_observer_notify_output_node_volume(node_id, volume);
476   EXPECT_EQ(cras_alert_pending_alert_value,
477             g_observer->alerts.output_node_volume);
478   ASSERT_EQ(cras_alert_pending_data_size_value, sizeof(*data));
479   ASSERT_NE(cras_alert_pending_data_value, reinterpret_cast<void*>(NULL));
480   data = reinterpret_cast<struct cras_observer_alert_data_node_volume*>(
481       cras_alert_pending_data_value);
482   EXPECT_EQ(data->node_id, node_id);
483   EXPECT_EQ(data->volume, volume);
484 
485   ops1_.output_node_volume_changed = cb_output_node_volume_changed;
486   ops2_.output_node_volume_changed = cb_output_node_volume_changed;
487   DoObserverAlert(output_node_volume_alert, data);
488   ASSERT_EQ(2, cb_output_node_volume_changed_called);
489   EXPECT_EQ(cb_output_node_volume_changed_volume[0], volume);
490   EXPECT_EQ(cb_output_node_volume_changed_volume[1], volume);
491   EXPECT_EQ(cb_output_node_volume_changed_node_id[0], node_id);
492   EXPECT_EQ(cb_output_node_volume_changed_node_id[1], node_id);
493 
494   DoObserverRemoveClear(output_node_volume_alert, data);
495 };
496 
TEST_F(ObserverTest,NotifyNodeLeftRightSwapped)497 TEST_F(ObserverTest, NotifyNodeLeftRightSwapped) {
498   struct cras_observer_alert_data_node_lr_swapped* data;
499   const cras_node_id_t node_id = 0x0001000100020002;
500   const int swapped = 1;
501 
502   cras_observer_notify_node_left_right_swapped(node_id, swapped);
503   EXPECT_EQ(cras_alert_pending_alert_value,
504             g_observer->alerts.node_left_right_swapped);
505   ASSERT_EQ(cras_alert_pending_data_size_value, sizeof(*data));
506   ASSERT_NE(cras_alert_pending_data_value, reinterpret_cast<void*>(NULL));
507   data = reinterpret_cast<struct cras_observer_alert_data_node_lr_swapped*>(
508       cras_alert_pending_data_value);
509   EXPECT_EQ(data->node_id, node_id);
510   EXPECT_EQ(data->swapped, swapped);
511 
512   ops1_.node_left_right_swapped_changed = cb_node_left_right_swapped_changed;
513   ops2_.node_left_right_swapped_changed = cb_node_left_right_swapped_changed;
514   DoObserverAlert(node_left_right_swapped_alert, data);
515   ASSERT_EQ(2, cb_node_left_right_swapped_changed_called);
516   EXPECT_EQ(cb_node_left_right_swapped_changed_swapped[0], swapped);
517   EXPECT_EQ(cb_node_left_right_swapped_changed_swapped[1], swapped);
518   EXPECT_EQ(cb_node_left_right_swapped_changed_node_id[0], node_id);
519   EXPECT_EQ(cb_node_left_right_swapped_changed_node_id[1], node_id);
520 
521   DoObserverRemoveClear(node_left_right_swapped_alert, data);
522 };
523 
TEST_F(ObserverTest,NotifyInputNodeGain)524 TEST_F(ObserverTest, NotifyInputNodeGain) {
525   struct cras_observer_alert_data_node_volume* data;
526   const cras_node_id_t node_id = 0x0001000100020002;
527   const int32_t gain = -20;
528 
529   cras_observer_notify_input_node_gain(node_id, gain);
530   EXPECT_EQ(cras_alert_pending_alert_value, g_observer->alerts.input_node_gain);
531   ASSERT_EQ(cras_alert_pending_data_size_value, sizeof(*data));
532   ASSERT_NE(cras_alert_pending_data_value, reinterpret_cast<void*>(NULL));
533   data = reinterpret_cast<struct cras_observer_alert_data_node_volume*>(
534       cras_alert_pending_data_value);
535   EXPECT_EQ(data->node_id, node_id);
536   EXPECT_EQ(data->volume, gain);
537 
538   ops1_.input_node_gain_changed = cb_input_node_gain_changed;
539   ops2_.input_node_gain_changed = cb_input_node_gain_changed;
540   DoObserverAlert(input_node_gain_alert, data);
541   ASSERT_EQ(2, cb_input_node_gain_changed_called);
542   EXPECT_EQ(cb_input_node_gain_changed_gain[0], gain);
543   EXPECT_EQ(cb_input_node_gain_changed_gain[1], gain);
544   EXPECT_EQ(cb_input_node_gain_changed_node_id[0], node_id);
545   EXPECT_EQ(cb_input_node_gain_changed_node_id[1], node_id);
546 
547   DoObserverRemoveClear(input_node_gain_alert, data);
548 };
549 
TEST_F(ObserverTest,NotifySuspendChanged)550 TEST_F(ObserverTest, NotifySuspendChanged) {
551   struct cras_observer_alert_data_suspend* data;
552 
553   cras_observer_notify_suspend_changed(1);
554   EXPECT_EQ(cras_alert_pending_alert_value, g_observer->alerts.suspend_changed);
555   ASSERT_EQ(cras_alert_pending_data_size_value, sizeof(*data));
556   ASSERT_NE(cras_alert_pending_data_value, reinterpret_cast<void*>(NULL));
557   data = reinterpret_cast<struct cras_observer_alert_data_suspend*>(
558       cras_alert_pending_data_value);
559   EXPECT_EQ(data->suspended, 1);
560 
561   cras_observer_notify_suspend_changed(0);
562   EXPECT_EQ(cras_alert_pending_alert_value, g_observer->alerts.suspend_changed);
563   ASSERT_EQ(cras_alert_pending_data_size_value, sizeof(*data));
564   ASSERT_NE(cras_alert_pending_data_value, reinterpret_cast<void*>(NULL));
565   data = reinterpret_cast<struct cras_observer_alert_data_suspend*>(
566       cras_alert_pending_data_value);
567   EXPECT_EQ(data->suspended, 0);
568 }
569 
TEST_F(ObserverTest,NotifyNumActiveStreams)570 TEST_F(ObserverTest, NotifyNumActiveStreams) {
571   struct cras_observer_alert_data_streams* data;
572   const enum CRAS_STREAM_DIRECTION dir = CRAS_STREAM_INPUT;
573   const uint32_t active_streams = 10;
574 
575   cras_observer_notify_num_active_streams(dir, active_streams);
576   EXPECT_EQ(cras_alert_pending_alert_value,
577             g_observer->alerts.num_active_streams[CRAS_STREAM_INPUT]);
578   ASSERT_EQ(cras_alert_pending_data_size_value, sizeof(*data));
579   ASSERT_NE(cras_alert_pending_data_value, reinterpret_cast<void*>(NULL));
580   data = reinterpret_cast<struct cras_observer_alert_data_streams*>(
581       cras_alert_pending_data_value);
582   EXPECT_EQ(data->num_active_streams, active_streams);
583   EXPECT_EQ(data->direction, dir);
584 
585   ops1_.num_active_streams_changed = cb_num_active_streams_changed;
586   ops2_.num_active_streams_changed = cb_num_active_streams_changed;
587   DoObserverAlert(num_active_streams_alert, data);
588   ASSERT_EQ(2, cb_num_active_streams_changed_called);
589   EXPECT_EQ(cb_num_active_streams_changed_dir[0], dir);
590   EXPECT_EQ(cb_num_active_streams_changed_dir[1], dir);
591   EXPECT_EQ(cb_num_active_streams_changed_num[0], active_streams);
592   EXPECT_EQ(cb_num_active_streams_changed_num[1], active_streams);
593 
594   DoObserverRemoveClear(num_active_streams_alert, data);
595 };
596 
TEST_F(ObserverTest,NotifyNumInputStreamsWithPermission)597 TEST_F(ObserverTest, NotifyNumInputStreamsWithPermission) {
598   struct cras_observer_alert_data_input_streams* data;
599   uint32_t num_input_streams[CRAS_NUM_CLIENT_TYPE] = {};
600   for (unsigned type = 0; type < CRAS_NUM_CLIENT_TYPE; ++type) {
601     num_input_streams[type] = (uint32_t)type;
602   }
603 
604   cras_observer_notify_input_streams_with_permission(num_input_streams);
605   ASSERT_EQ(cras_alert_pending_data_size_value, sizeof(*data));
606   ASSERT_NE(cras_alert_pending_data_value, reinterpret_cast<void*>(NULL));
607   data = reinterpret_cast<struct cras_observer_alert_data_input_streams*>(
608       cras_alert_pending_data_value);
609   for (unsigned type = 0; type < CRAS_NUM_CLIENT_TYPE; ++type) {
610     EXPECT_EQ(data->num_input_streams[type], num_input_streams[type]);
611   }
612 
613   ops1_.num_input_streams_with_permission_changed =
614       cb_num_input_streams_with_permission_changed;
615   ops2_.num_input_streams_with_permission_changed =
616       cb_num_input_streams_with_permission_changed;
617   DoObserverAlert(num_input_streams_with_permission_alert, data);
618   ASSERT_EQ(2, cb_num_input_streams_with_permission_called);
619   for (auto cb_num_input_streams : cb_num_input_streams_with_permission_array) {
620     ASSERT_EQ(cb_num_input_streams.size(), (size_t)CRAS_NUM_CLIENT_TYPE);
621     for (unsigned type = 0; type < CRAS_NUM_CLIENT_TYPE; ++type) {
622       EXPECT_EQ(cb_num_input_streams[type], num_input_streams[type]);
623     }
624   }
625   DoObserverRemoveClear(num_input_streams_with_permission_alert, data);
626 }
627 
TEST_F(ObserverTest,NotifyHotwordTriggered)628 TEST_F(ObserverTest, NotifyHotwordTriggered) {
629   struct cras_observer_alert_data_hotword_triggered* data;
630 
631   cras_observer_notify_hotword_triggered(100, 200);
632   EXPECT_EQ(cras_alert_pending_alert_value,
633             g_observer->alerts.hotword_triggered);
634   ASSERT_EQ(cras_alert_pending_data_size_value, sizeof(*data));
635   ASSERT_NE(cras_alert_pending_data_value, reinterpret_cast<void*>(NULL));
636   data = reinterpret_cast<struct cras_observer_alert_data_hotword_triggered*>(
637       cras_alert_pending_data_value);
638   EXPECT_EQ(data->tv_sec, 100);
639   EXPECT_EQ(data->tv_nsec, 200);
640 }
641 
TEST_F(ObserverTest,NonEmpyAudioStateChanged)642 TEST_F(ObserverTest, NonEmpyAudioStateChanged) {
643   struct cras_observer_non_empty_audio_state* data;
644 
645   cras_observer_notify_non_empty_audio_state_changed(1);
646   EXPECT_EQ(cras_alert_pending_alert_value,
647             g_observer->alerts.non_empty_audio_state_changed);
648   ASSERT_EQ(cras_alert_pending_data_size_value, sizeof(*data));
649   ASSERT_NE(cras_alert_pending_data_value, reinterpret_cast<void*>(NULL));
650   data = reinterpret_cast<struct cras_observer_non_empty_audio_state*>(
651       cras_alert_pending_data_value);
652   EXPECT_EQ(data->non_empty, 1);
653 }
654 
TEST_F(ObserverTest,BluetoothBatteryChanged)655 TEST_F(ObserverTest, BluetoothBatteryChanged) {
656   struct cras_observer_alert_data_bt_battery_changed* data;
657   const char* address = "test";
658 
659   cras_observer_notify_bt_battery_changed(address, 30);
660   EXPECT_EQ(cras_alert_pending_alert_value,
661             g_observer->alerts.bt_battery_changed);
662   ASSERT_EQ(cras_alert_pending_data_size_value, sizeof(*data));
663   ASSERT_NE(cras_alert_pending_data_value, reinterpret_cast<void*>(NULL));
664   data = reinterpret_cast<struct cras_observer_alert_data_bt_battery_changed*>(
665       cras_alert_pending_data_value);
666   EXPECT_EQ(data->address, address);
667   EXPECT_EQ(data->level, 30);
668 }
669 
670 // Stubs
671 extern "C" {
672 
cras_alert_destroy(struct cras_alert * alert)673 void cras_alert_destroy(struct cras_alert* alert) {
674   cras_alert_destroy_called++;
675 }
676 
cras_alert_create(cras_alert_prepare prepare,unsigned int flags)677 struct cras_alert* cras_alert_create(cras_alert_prepare prepare,
678                                      unsigned int flags) {
679   struct cras_alert* alert = NULL;
680 
681   cras_alert_create_called++;
682   alert = reinterpret_cast<struct cras_alert*>(cras_alert_create_called);
683   cras_alert_create_return_values.push_back(alert);
684   cras_alert_create_flags_map[alert] = flags;
685   cras_alert_create_prepare_map[alert] = reinterpret_cast<void*>(prepare);
686   return alert;
687 }
688 
cras_alert_add_callback(struct cras_alert * alert,cras_alert_cb cb,void * arg)689 int cras_alert_add_callback(struct cras_alert* alert,
690                             cras_alert_cb cb,
691                             void* arg) {
692   cras_alert_add_callback_map[alert] = reinterpret_cast<void*>(cb);
693   return 0;
694 }
695 
cras_alert_pending(struct cras_alert * alert)696 void cras_alert_pending(struct cras_alert* alert) {
697   cras_alert_pending_alert_value = alert;
698 }
699 
cras_alert_pending_data(struct cras_alert * alert,void * data,size_t data_size)700 void cras_alert_pending_data(struct cras_alert* alert,
701                              void* data,
702                              size_t data_size) {
703   cras_alert_pending_alert_value = alert;
704   cras_alert_pending_data_size_value = data_size;
705   if (cras_alert_pending_data_value)
706     free(cras_alert_pending_data_value);
707   if (data) {
708     cras_alert_pending_data_value = malloc(data_size);
709     memcpy(cras_alert_pending_data_value, data, data_size);
710   } else
711     cras_alert_pending_data_value = NULL;
712 }
713 
cras_iodev_list_update_device_list()714 void cras_iodev_list_update_device_list() {
715   cras_iodev_list_update_device_list_called++;
716 }
717 
718 }  // extern "C"
719 
720 }  // namespace
721 
main(int argc,char ** argv)722 int main(int argc, char** argv) {
723   ::testing::InitGoogleTest(&argc, argv);
724   openlog(NULL, LOG_PERROR, LOG_USER);
725   return RUN_ALL_TESTS();
726 }
727