• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //
2 //  Copyright 2015 Google, Inc.
3 //
4 //  Licensed under the Apache License, Version 2.0 (the "License");
5 //  you may not use this file except in compliance with the License.
6 //  You may obtain a copy of the License at:
7 //
8 //  http://www.apache.org/licenses/LICENSE-2.0
9 //
10 //  Unless required by applicable law or agreed to in writing, software
11 //  distributed under the License is distributed on an "AS IS" BASIS,
12 //  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 //  See the License for the specific language governing permissions and
14 //  limitations under the License.
15 //
16 
17 #include "service/hal/bluetooth_avrcp_interface.h"
18 
19 #include <base/logging.h>
20 #include <base/observer_list.h>
21 
22 #include <mutex>
23 #include <shared_mutex>
24 
25 #include "abstract_observer_list.h"
26 #include "service/hal/bluetooth_interface.h"
27 #include "service/logging_helpers.h"
28 #include "types/raw_address.h"
29 
30 using std::lock_guard;
31 using std::mutex;
32 using std::shared_lock;
33 using std::unique_lock;
34 #if defined(OS_GENERIC) && defined(_LIBCPP_VERSION) && (_LIBCPP_VERSION < 3500)
35 using shared_mutex_impl = std::shared_mutex;
36 #else
37 using shared_mutex_impl = std::shared_timed_mutex;
38 #endif
39 
40 namespace bluetooth {
41 namespace hal {
42 
43 namespace {
44 
45 // The global BluetoothAvrcpInterface instance.
46 BluetoothAvrcpInterface* g_interface = nullptr;
47 
48 // Mutex used by callbacks to access |g_interface|. If we initialize or clean it
49 // use unique_lock. If only accessing |g_interface| use shared lock.
50 // TODO(jpawlowski): this should be just shared_mutex, as we currently don't use
51 // timed methods. Change to shared_mutex when we upgrade to C++14
52 shared_mutex_impl g_instance_lock;
53 
54 // Helper for obtaining the observer lists. This is forward declared here
55 // and defined below since it depends on BluetoothInterfaceImpl.
56 btbase::AbstractObserverList<BluetoothAvrcpInterface::TargetObserver>*
57 GetTargetObservers();
58 
59 btbase::AbstractObserverList<BluetoothAvrcpInterface::ControlObserver>*
60 GetControlObservers();
61 
62 #define VERIFY_INTERFACE_OR_RETURN()                                   \
63   do {                                                                 \
64     if (!g_interface) {                                                \
65       LOG(WARNING) << "Callback received while |g_interface| is NULL"; \
66       return;                                                          \
67     }                                                                  \
68   } while (0)
69 
RemoteFeaturesCallback(const RawAddress & bd_addr,btrc_remote_features_t features)70 void RemoteFeaturesCallback(const RawAddress& bd_addr,
71                             btrc_remote_features_t features) {
72   shared_lock<shared_mutex_impl> lock(g_instance_lock);
73   VLOG(2) << __func__;
74   VERIFY_INTERFACE_OR_RETURN();
75   for (auto& observer : *GetTargetObservers()) {
76     observer.RemoteFeaturesCallback(bd_addr, features);
77   }
78 }
79 
GetPlayStatusCallback(const RawAddress & bd_addr)80 void GetPlayStatusCallback(const RawAddress& bd_addr) {
81   shared_lock<shared_mutex_impl> lock(g_instance_lock);
82   VLOG(2) << __func__;
83   VERIFY_INTERFACE_OR_RETURN();
84   for (auto& observer : *GetTargetObservers()) {
85     observer.GetPlayStatusCallback(bd_addr);
86   }
87 }
88 
ListPlayerAppAttrCallback(const RawAddress & bd_addr)89 void ListPlayerAppAttrCallback(const RawAddress& bd_addr) {
90   shared_lock<shared_mutex_impl> lock(g_instance_lock);
91   VLOG(2) << __func__;
92   VERIFY_INTERFACE_OR_RETURN();
93   for (auto& observer : *GetTargetObservers()) {
94     observer.ListPlayerAppAttrCallback(bd_addr);
95   }
96 }
97 
ListPlayerAppValuesCallback(btrc_player_attr_t attr_id,const RawAddress & bd_addr)98 void ListPlayerAppValuesCallback(btrc_player_attr_t attr_id,
99                                  const RawAddress& bd_addr) {
100   shared_lock<shared_mutex_impl> lock(g_instance_lock);
101   VLOG(2) << __func__;
102   VERIFY_INTERFACE_OR_RETURN();
103   for (auto& observer : *GetTargetObservers()) {
104     observer.ListPlayerAppValuesCallback(attr_id, bd_addr);
105   }
106 }
107 
GetPlayerAppValueCallback(uint8_t num_attr,btrc_player_attr_t * p_attrs,const RawAddress & bd_addr)108 void GetPlayerAppValueCallback(uint8_t num_attr, btrc_player_attr_t* p_attrs,
109                                const RawAddress& bd_addr) {
110   shared_lock<shared_mutex_impl> lock(g_instance_lock);
111   VLOG(2) << __func__;
112   VERIFY_INTERFACE_OR_RETURN();
113   for (auto& observer : *GetTargetObservers()) {
114     observer.GetPlayerAppValueCallback(num_attr, p_attrs, bd_addr);
115   }
116 }
117 
GetPlayerAppAttrsTextCallback(uint8_t num_attr,btrc_player_attr_t * p_attrs,const RawAddress & bd_addr)118 void GetPlayerAppAttrsTextCallback(uint8_t num_attr,
119                                    btrc_player_attr_t* p_attrs,
120                                    const RawAddress& bd_addr) {
121   shared_lock<shared_mutex_impl> lock(g_instance_lock);
122   VLOG(2) << __func__;
123   VERIFY_INTERFACE_OR_RETURN();
124   for (auto& observer : *GetTargetObservers()) {
125     observer.GetPlayerAppAttrsTextCallback(num_attr, p_attrs, bd_addr);
126   }
127 }
128 
GetPlayerAppValuesTextCallback(uint8_t attr_id,uint8_t num_val,uint8_t * p_vals,const RawAddress & bd_addr)129 void GetPlayerAppValuesTextCallback(uint8_t attr_id, uint8_t num_val,
130                                     uint8_t* p_vals,
131                                     const RawAddress& bd_addr) {
132   shared_lock<shared_mutex_impl> lock(g_instance_lock);
133   VLOG(2) << __func__;
134   VERIFY_INTERFACE_OR_RETURN();
135   for (auto& observer : *GetTargetObservers()) {
136     observer.GetPlayerAppValuesTextCallback(attr_id, num_val, p_vals, bd_addr);
137   }
138 }
139 
SetPlayerAppValueCallback(btrc_player_settings_t * p_vals,const RawAddress & bd_addr)140 void SetPlayerAppValueCallback(btrc_player_settings_t* p_vals,
141                                const RawAddress& bd_addr) {
142   shared_lock<shared_mutex_impl> lock(g_instance_lock);
143   VLOG(2) << __func__;
144   VERIFY_INTERFACE_OR_RETURN();
145   for (auto& observer : *GetTargetObservers()) {
146     observer.SetPlayerAppValueCallback(p_vals, bd_addr);
147   }
148 }
149 
GetElementAttrCallback(uint8_t num_attr,btrc_media_attr_t * p_attrs,const RawAddress & bd_addr)150 void GetElementAttrCallback(uint8_t num_attr, btrc_media_attr_t* p_attrs,
151                             const RawAddress& bd_addr) {
152   shared_lock<shared_mutex_impl> lock(g_instance_lock);
153   VLOG(2) << __func__;
154   VERIFY_INTERFACE_OR_RETURN();
155   for (auto& observer : *GetTargetObservers()) {
156     observer.GetElementAttrCallback(num_attr, p_attrs, bd_addr);
157   }
158 }
159 
RegisterNotificationCallback(btrc_event_id_t event_id,uint32_t param,const RawAddress & bd_addr)160 void RegisterNotificationCallback(btrc_event_id_t event_id, uint32_t param,
161                                   const RawAddress& bd_addr) {
162   shared_lock<shared_mutex_impl> lock(g_instance_lock);
163   VLOG(2) << __func__;
164   VERIFY_INTERFACE_OR_RETURN();
165   for (auto& observer : *GetTargetObservers()) {
166     observer.RegisterNotificationCallback(event_id, param, bd_addr);
167   }
168 }
169 
VolumeChangeCallback(uint8_t volume,uint8_t ctype,const RawAddress & bd_addr)170 void VolumeChangeCallback(uint8_t volume, uint8_t ctype,
171                           const RawAddress& bd_addr) {
172   shared_lock<shared_mutex_impl> lock(g_instance_lock);
173   VLOG(2) << __func__;
174   VERIFY_INTERFACE_OR_RETURN();
175   for (auto& observer : *GetTargetObservers()) {
176     observer.VolumeChangeCallback(volume, ctype, bd_addr);
177   }
178 }
179 
PassthroughCmdCallback(int id,int key_state,const RawAddress & bd_addr)180 void PassthroughCmdCallback(int id, int key_state, const RawAddress& bd_addr) {
181   shared_lock<shared_mutex_impl> lock(g_instance_lock);
182   VLOG(2) << __func__;
183   VERIFY_INTERFACE_OR_RETURN();
184   for (auto& observer : *GetTargetObservers()) {
185     observer.PassthroughCmdCallback(id, key_state, bd_addr);
186   }
187 }
188 
SetAddressedPlayerCallback(uint16_t player_id,const RawAddress & bd_addr)189 void SetAddressedPlayerCallback(uint16_t player_id, const RawAddress& bd_addr) {
190   shared_lock<shared_mutex_impl> lock(g_instance_lock);
191   VLOG(2) << __func__;
192   VERIFY_INTERFACE_OR_RETURN();
193   for (auto& observer : *GetTargetObservers()) {
194     observer.SetAddressedPlayerCallback(player_id, bd_addr);
195   }
196 }
197 
SetBrowsedPlayerCallback(uint16_t player_id,const RawAddress & bd_addr)198 void SetBrowsedPlayerCallback(uint16_t player_id, const RawAddress& bd_addr) {
199   shared_lock<shared_mutex_impl> lock(g_instance_lock);
200   VLOG(2) << __func__;
201   VERIFY_INTERFACE_OR_RETURN();
202   for (auto& observer : *GetTargetObservers()) {
203     observer.SetBrowsedPlayerCallback(player_id, bd_addr);
204   }
205 }
206 
GetFolderItemsCallback(uint8_t scope,uint32_t start_item,uint32_t end_item,uint8_t num_attr,uint32_t * p_attr_ids,const RawAddress & bd_addr)207 void GetFolderItemsCallback(uint8_t scope, uint32_t start_item,
208                             uint32_t end_item, uint8_t num_attr,
209                             uint32_t* p_attr_ids, const RawAddress& bd_addr) {
210   shared_lock<shared_mutex_impl> lock(g_instance_lock);
211   VLOG(2) << __func__;
212   VERIFY_INTERFACE_OR_RETURN();
213   for (auto& observer : *GetTargetObservers()) {
214     observer.GetFolderItemsCallback(scope, start_item, end_item, num_attr,
215                                     p_attr_ids, bd_addr);
216   }
217 }
218 
ChangePathCallback(uint8_t direction,uint8_t * folder_uid,const RawAddress & bd_addr)219 void ChangePathCallback(uint8_t direction, uint8_t* folder_uid,
220                         const RawAddress& bd_addr) {
221   shared_lock<shared_mutex_impl> lock(g_instance_lock);
222   VLOG(2) << __func__;
223   VERIFY_INTERFACE_OR_RETURN();
224   for (auto& observer : *GetTargetObservers()) {
225     observer.ChangePathCallback(direction, folder_uid, bd_addr);
226   }
227 }
228 
GetItemAttrCallback(uint8_t scope,uint8_t * uid,uint16_t uid_counter,uint8_t num_attr,btrc_media_attr_t * p_attrs,const RawAddress & bd_addr)229 void GetItemAttrCallback(uint8_t scope, uint8_t* uid, uint16_t uid_counter,
230                          uint8_t num_attr, btrc_media_attr_t* p_attrs,
231                          const RawAddress& bd_addr) {
232   shared_lock<shared_mutex_impl> lock(g_instance_lock);
233   VLOG(2) << __func__;
234   VERIFY_INTERFACE_OR_RETURN();
235   for (auto& observer : *GetTargetObservers()) {
236     observer.GetItemAttrCallback(scope, uid, uid_counter, num_attr, p_attrs,
237                                  bd_addr);
238   }
239 }
240 
PlayItemCallback(uint8_t scope,uint16_t uid_counter,uint8_t * uid,const RawAddress & bd_addr)241 void PlayItemCallback(uint8_t scope, uint16_t uid_counter, uint8_t* uid,
242                       const RawAddress& bd_addr) {
243   shared_lock<shared_mutex_impl> lock(g_instance_lock);
244   VLOG(2) << __func__;
245   VERIFY_INTERFACE_OR_RETURN();
246   for (auto& observer : *GetTargetObservers()) {
247     observer.PlayItemCallback(scope, uid_counter, uid, bd_addr);
248   }
249 }
250 
GetTotalNumOfItemsCallback(uint8_t scope,const RawAddress & bd_addr)251 void GetTotalNumOfItemsCallback(uint8_t scope, const RawAddress& bd_addr) {
252   shared_lock<shared_mutex_impl> lock(g_instance_lock);
253   VLOG(2) << __func__;
254   VERIFY_INTERFACE_OR_RETURN();
255   for (auto& observer : *GetTargetObservers()) {
256     observer.GetTotalNumOfItemsCallback(scope, bd_addr);
257   }
258 }
259 
SearchCallback(uint16_t charset_id,uint16_t str_len,uint8_t * p_str,const RawAddress & bd_addr)260 void SearchCallback(uint16_t charset_id, uint16_t str_len, uint8_t* p_str,
261                     const RawAddress& bd_addr) {
262   shared_lock<shared_mutex_impl> lock(g_instance_lock);
263   VLOG(2) << __func__;
264   VERIFY_INTERFACE_OR_RETURN();
265   for (auto& observer : *GetTargetObservers()) {
266     observer.SearchCallback(str_len, p_str, bd_addr);
267   }
268 }
269 
AddToNowPlayingCallback(uint8_t scope,uint8_t * uid,uint16_t uid_counter,const RawAddress & bd_addr)270 void AddToNowPlayingCallback(uint8_t scope, uint8_t* uid, uint16_t uid_counter,
271                              const RawAddress& bd_addr) {
272   shared_lock<shared_mutex_impl> lock(g_instance_lock);
273   VLOG(2) << __func__;
274   VERIFY_INTERFACE_OR_RETURN();
275   for (auto& observer : *GetTargetObservers()) {
276     observer.AddToNowPlayingCallback(scope, uid, uid_counter, bd_addr);
277   }
278 }
279 
PassthroughRspCallback(const RawAddress & bd_addr,int id,int key_state)280 void PassthroughRspCallback(const RawAddress& bd_addr, int id, int key_state) {
281   shared_lock<shared_mutex_impl> lock(g_instance_lock);
282   VLOG(2) << __func__;
283   VERIFY_INTERFACE_OR_RETURN();
284   for (auto& observer : *GetControlObservers()) {
285     observer.PassthroughRspCallback(bd_addr, id, key_state);
286   }
287 }
288 
GroupnavigationRspCallback(int id,int key_state)289 void GroupnavigationRspCallback(int id, int key_state) {
290   shared_lock<shared_mutex_impl> lock(g_instance_lock);
291   VLOG(2) << __func__;
292   VERIFY_INTERFACE_OR_RETURN();
293   for (auto& observer : *GetControlObservers()) {
294     observer.GroupnavigationRspCallback(id, key_state);
295   }
296 }
297 
ConnectionStateCallback(bool rc_connect,bool bt_connect,const RawAddress & bd_addr)298 void ConnectionStateCallback(bool rc_connect, bool bt_connect,
299                              const RawAddress& bd_addr) {
300   shared_lock<shared_mutex_impl> lock(g_instance_lock);
301   VLOG(2) << __func__;
302   VERIFY_INTERFACE_OR_RETURN();
303   for (auto& observer : *GetControlObservers()) {
304     observer.ConnectionStateCallback(rc_connect, bt_connect, bd_addr);
305   }
306 }
307 
CtrlGetrcfeaturesCallback(const RawAddress & bd_addr,int features)308 void CtrlGetrcfeaturesCallback(const RawAddress& bd_addr, int features) {
309   shared_lock<shared_mutex_impl> lock(g_instance_lock);
310   VLOG(2) << __func__;
311   VERIFY_INTERFACE_OR_RETURN();
312   for (auto& observer : *GetControlObservers()) {
313     observer.CtrlGetrcfeaturesCallback(bd_addr, features);
314   }
315 }
316 
CtrlSetplayerapplicationsettingRspCallback(const RawAddress & bd_addr,uint8_t accepted)317 void CtrlSetplayerapplicationsettingRspCallback(const RawAddress& bd_addr,
318                                                 uint8_t accepted) {
319   shared_lock<shared_mutex_impl> lock(g_instance_lock);
320   VLOG(2) << __func__;
321   VERIFY_INTERFACE_OR_RETURN();
322 
323   for (auto& observer : *GetControlObservers()) {
324     observer.CtrlSetplayerapplicationsettingRspCallback(bd_addr, accepted);
325   }
326 }
327 
CtrlPlayerapplicationsettingCallback(const RawAddress & bd_addr,uint8_t num_attr,btrc_player_app_attr_t * app_attrs,uint8_t num_ext_attr,btrc_player_app_ext_attr_t * ext_attrs)328 void CtrlPlayerapplicationsettingCallback(
329     const RawAddress& bd_addr, uint8_t num_attr,
330     btrc_player_app_attr_t* app_attrs, uint8_t num_ext_attr,
331     btrc_player_app_ext_attr_t* ext_attrs) {
332   shared_lock<shared_mutex_impl> lock(g_instance_lock);
333   VLOG(2) << __func__;
334   VERIFY_INTERFACE_OR_RETURN();
335   for (auto& observer : *GetControlObservers()) {
336     observer.CtrlPlayerapplicationsettingCallback(bd_addr, num_attr, app_attrs,
337                                                   num_ext_attr, ext_attrs);
338   }
339 }
340 
CtrlPlayerapplicationsettingChangedCallback(const RawAddress & bd_addr,const btrc_player_settings_t & vals)341 void CtrlPlayerapplicationsettingChangedCallback(
342     const RawAddress& bd_addr, const btrc_player_settings_t& vals) {
343   shared_lock<shared_mutex_impl> lock(g_instance_lock);
344   VLOG(2) << __func__;
345   VERIFY_INTERFACE_OR_RETURN();
346   for (auto& observer : *GetControlObservers()) {
347     observer.CtrlPlayerapplicationsettingChangedCallback(bd_addr, vals);
348   }
349 }
350 
CtrlSetabsvolCmdCallback(const RawAddress & bd_addr,uint8_t abs_vol,uint8_t label)351 void CtrlSetabsvolCmdCallback(const RawAddress& bd_addr, uint8_t abs_vol,
352                               uint8_t label) {
353   shared_lock<shared_mutex_impl> lock(g_instance_lock);
354   VLOG(2) << __func__;
355   VERIFY_INTERFACE_OR_RETURN();
356   for (auto& observer : *GetControlObservers()) {
357     observer.CtrlSetabsvolCmdCallback(bd_addr, abs_vol, label);
358   }
359 }
360 
CtrlRegisternotificationAbsVolCallback(const RawAddress & bd_addr,uint8_t label)361 void CtrlRegisternotificationAbsVolCallback(const RawAddress& bd_addr,
362                                             uint8_t label) {
363   shared_lock<shared_mutex_impl> lock(g_instance_lock);
364   VLOG(2) << __func__;
365   VERIFY_INTERFACE_OR_RETURN();
366   for (auto& observer : *GetControlObservers()) {
367     observer.CtrlRegisternotificationAbsVolCallback(bd_addr, label);
368   }
369 }
370 
CtrlTrackChangedCallback(const RawAddress & bd_addr,uint8_t num_attr,btrc_element_attr_val_t * p_attrs)371 void CtrlTrackChangedCallback(const RawAddress& bd_addr, uint8_t num_attr,
372                               btrc_element_attr_val_t* p_attrs) {
373   shared_lock<shared_mutex_impl> lock(g_instance_lock);
374   VLOG(2) << __func__;
375   VERIFY_INTERFACE_OR_RETURN();
376   for (auto& observer : *GetControlObservers()) {
377     observer.CtrlTrackChangedCallback(bd_addr, num_attr, p_attrs);
378   }
379 }
380 
CtrlPlayPositionChangedCallback(const RawAddress & bd_addr,uint32_t song_len,uint32_t song_pos)381 void CtrlPlayPositionChangedCallback(const RawAddress& bd_addr,
382                                      uint32_t song_len, uint32_t song_pos) {
383   shared_lock<shared_mutex_impl> lock(g_instance_lock);
384   VLOG(2) << __func__;
385   VERIFY_INTERFACE_OR_RETURN();
386   for (auto& observer : *GetControlObservers()) {
387     observer.CtrlPlayPositionChangedCallback(bd_addr, song_len, song_pos);
388   }
389 }
390 
CtrlPlayStatusChangedCallback(const RawAddress & bd_addr,btrc_play_status_t play_status)391 void CtrlPlayStatusChangedCallback(const RawAddress& bd_addr,
392                                    btrc_play_status_t play_status) {
393   shared_lock<shared_mutex_impl> lock(g_instance_lock);
394   VLOG(2) << __func__;
395   VERIFY_INTERFACE_OR_RETURN();
396   for (auto& observer : *GetControlObservers()) {
397     observer.CtrlPlayStatusChangedCallback(bd_addr, play_status);
398   }
399 }
400 
CtrlGetFolderItemsCallback(const RawAddress & bd_addr,btrc_status_t status,const btrc_folder_items_t * folder_items,uint8_t count)401 void CtrlGetFolderItemsCallback(const RawAddress& bd_addr, btrc_status_t status,
402                                 const btrc_folder_items_t* folder_items,
403                                 uint8_t count) {
404   shared_lock<shared_mutex_impl> lock(g_instance_lock);
405   VLOG(2) << __func__;
406   VERIFY_INTERFACE_OR_RETURN();
407   for (auto& observer : *GetControlObservers()) {
408     observer.CtrlGetFolderItemsCallback(bd_addr, status, folder_items, count);
409   }
410 }
411 
CtrlChangePathCallback(const RawAddress & bd_addr,uint32_t count)412 void CtrlChangePathCallback(const RawAddress& bd_addr, uint32_t count) {
413   shared_lock<shared_mutex_impl> lock(g_instance_lock);
414   VLOG(2) << __func__;
415   VERIFY_INTERFACE_OR_RETURN();
416   for (auto& observer : *GetControlObservers()) {
417     observer.CtrlChangePathCallback(bd_addr, count);
418   }
419 }
420 
CtrlSetBrowsedPlayerCallback(const RawAddress & bd_addr,uint8_t num_items,uint8_t depth)421 void CtrlSetBrowsedPlayerCallback(const RawAddress& bd_addr, uint8_t num_items,
422                                   uint8_t depth) {
423   shared_lock<shared_mutex_impl> lock(g_instance_lock);
424   VLOG(2) << __func__;
425   VERIFY_INTERFACE_OR_RETURN();
426   for (auto& observer : *GetControlObservers()) {
427     observer.CtrlSetBrowsedPlayerCallback(bd_addr, num_items, depth);
428   }
429 }
430 
CtrlSetAddressedPlayerCallback(const RawAddress & bd_addr,uint8_t status)431 void CtrlSetAddressedPlayerCallback(const RawAddress& bd_addr, uint8_t status) {
432   shared_lock<shared_mutex_impl> lock(g_instance_lock);
433   VLOG(2) << __func__;
434   VERIFY_INTERFACE_OR_RETURN();
435   for (auto& observer : *GetControlObservers()) {
436     observer.CtrlSetAddressedPlayerCallback(bd_addr, status);
437   }
438 }
439 
440 btrc_callbacks_t target_callbacks = {
441     .size = sizeof(btrc_callbacks_t),
442     .remote_features_cb = RemoteFeaturesCallback,
443     .get_play_status_cb = GetPlayStatusCallback,
444     .list_player_app_attr_cb = ListPlayerAppAttrCallback,
445     .list_player_app_values_cb = ListPlayerAppValuesCallback,
446     .get_player_app_value_cb = GetPlayerAppValueCallback,
447     .get_player_app_attrs_text_cb = GetPlayerAppAttrsTextCallback,
448     .get_player_app_values_text_cb = GetPlayerAppValuesTextCallback,
449     .set_player_app_value_cb = SetPlayerAppValueCallback,
450     .get_element_attr_cb = GetElementAttrCallback,
451     .register_notification_cb = RegisterNotificationCallback,
452     .volume_change_cb = VolumeChangeCallback,
453     .passthrough_cmd_cb = PassthroughCmdCallback,
454     .set_addressed_player_cb = SetAddressedPlayerCallback,
455     .set_browsed_player_cb = SetBrowsedPlayerCallback,
456     .get_folder_items_cb = GetFolderItemsCallback,
457     .change_path_cb = ChangePathCallback,
458     .get_item_attr_cb = GetItemAttrCallback,
459     .play_item_cb = PlayItemCallback,
460     .get_total_num_of_items_cb = GetTotalNumOfItemsCallback,
461     .search_cb = SearchCallback,
462     .add_to_now_playing_cb = AddToNowPlayingCallback,
463 };
464 
465 btrc_ctrl_callbacks_t control_callbacks = {
466     .size = sizeof(btrc_ctrl_callbacks_t),
467     .passthrough_rsp_cb = PassthroughRspCallback,
468     .groupnavigation_rsp_cb = GroupnavigationRspCallback,
469     .connection_state_cb = ConnectionStateCallback,
470     .getrcfeatures_cb = CtrlGetrcfeaturesCallback,
471     .setplayerappsetting_rsp_cb = CtrlSetplayerapplicationsettingRspCallback,
472     .playerapplicationsetting_cb = CtrlPlayerapplicationsettingCallback,
473     .playerapplicationsetting_changed_cb =
474         CtrlPlayerapplicationsettingChangedCallback,
475     .setabsvol_cmd_cb = CtrlSetabsvolCmdCallback,
476     .registernotification_absvol_cb = CtrlRegisternotificationAbsVolCallback,
477     .track_changed_cb = CtrlTrackChangedCallback,
478     .play_position_changed_cb = CtrlPlayPositionChangedCallback,
479     .play_status_changed_cb = CtrlPlayStatusChangedCallback,
480     .get_folder_items_cb = CtrlGetFolderItemsCallback,
481     .change_folder_path_cb = CtrlChangePathCallback,
482     .set_browsed_player_cb = CtrlSetBrowsedPlayerCallback,
483     .set_addressed_player_cb = CtrlSetAddressedPlayerCallback,
484 };
485 
486 }  // namespace
487 
488 // BluetoothAvrcpInterface implementation for production.
489 class BluetoothAvrcpInterfaceImpl : public BluetoothAvrcpInterface {
490  public:
BluetoothAvrcpInterfaceImpl()491   BluetoothAvrcpInterfaceImpl() : control_iface_(nullptr) {}
492 
493   BluetoothAvrcpInterfaceImpl(const BluetoothAvrcpInterfaceImpl&) = delete;
494   BluetoothAvrcpInterfaceImpl& operator=(const BluetoothAvrcpInterfaceImpl&) =
495       delete;
496 
~BluetoothAvrcpInterfaceImpl()497   ~BluetoothAvrcpInterfaceImpl() override {
498     if (control_iface_) control_iface_->cleanup();
499   }
500 
AvrcpControlEnable()501   bool AvrcpControlEnable() override {
502     if (control_enabled_) {
503       return true;
504     }
505 
506     if (control_iface_->init(&control_callbacks) != BT_STATUS_SUCCESS) {
507       LOG(ERROR) << "Failed to initialize HAL AVRCP control interface";
508       return false;
509     }
510 
511     control_enabled_ = true;
512     return true;
513   }
514 
AvrcpControlDisable()515   void AvrcpControlDisable() override {
516     if (!control_enabled_) {
517       return;
518     }
519 
520     control_iface_->cleanup();
521     control_enabled_ = false;
522   }
523 
AvrcpTargetEnable()524   bool AvrcpTargetEnable() override {
525     if (target_enabled_) {
526       return true;
527     }
528 
529     if (target_iface_->init(&target_callbacks) != BT_STATUS_SUCCESS) {
530       LOG(ERROR) << "Failed to initialize HAL AVRCP target interface";
531       return false;
532     }
533 
534     target_enabled_ = true;
535     return true;
536   }
537 
AvrcpTargetDisable()538   void AvrcpTargetDisable() override {
539     if (!target_enabled_) {
540       return;
541     }
542 
543     target_iface_->cleanup();
544     target_enabled_ = false;
545   }
546 
AddTargetObserver(TargetObserver * observer)547   void AddTargetObserver(TargetObserver* observer) override {
548     target_observers_.AddObserver(observer);
549   }
550 
RemoveTargetObserver(TargetObserver * observer)551   void RemoveTargetObserver(TargetObserver* observer) override {
552     target_observers_.RemoveObserver(observer);
553   }
554 
AddControlObserver(ControlObserver * observer)555   void AddControlObserver(ControlObserver* observer) override {
556     control_observers_.AddObserver(observer);
557   }
558 
RemoveControlObserver(ControlObserver * observer)559   void RemoveControlObserver(ControlObserver* observer) override {
560     control_observers_.RemoveObserver(observer);
561   }
562 
GetTargetHALInterface() const563   const btrc_interface_t* GetTargetHALInterface() const override {
564     return target_iface_;
565   }
566 
GetControlHALInterface() const567   const btrc_ctrl_interface_t* GetControlHALInterface() const override {
568     return control_iface_;
569   }
570 
571   // Initialize the interface.
Initialize()572   bool Initialize() {
573     const bt_interface_t* bt_iface =
574         BluetoothInterface::Get()->GetHALInterface();
575     CHECK(bt_iface);
576 
577     auto* target_iface = reinterpret_cast<const btrc_interface_t*>(
578         bt_iface->get_profile_interface(BT_PROFILE_AV_RC_ID));
579     if (!target_iface) {
580       LOG(ERROR) << "Failed to obtain HAL AVRCP target interface handle";
581       return false;
582     }
583 
584     auto* control_iface = reinterpret_cast<const btrc_ctrl_interface_t*>(
585         bt_iface->get_profile_interface(BT_PROFILE_AV_RC_CTRL_ID));
586     if (!control_iface) {
587       LOG(ERROR) << "Failed to obtain HAL AVRCP control interface handle";
588       return false;
589     }
590 
591     control_iface_ = control_iface;
592     target_iface_ = target_iface;
593 
594     // Only initialize the control interface.
595     return AvrcpControlEnable();
596   }
597 
target_observers()598   btbase::AbstractObserverList<TargetObserver>* target_observers() {
599     return &target_observers_;
600   }
601 
control_observers()602   btbase::AbstractObserverList<ControlObserver>* control_observers() {
603     return &control_observers_;
604   }
605 
606  private:
607   // List of observers that are interested in notifications from us.
608   // We're not using a base::ObserverListThreadSafe, which it posts observer
609   // events automatically on the origin threads, as we want to avoid that
610   // overhead and simply forward the events to the upper layer.
611   btbase::AbstractObserverList<TargetObserver> target_observers_;
612   btbase::AbstractObserverList<ControlObserver> control_observers_;
613 
614   // The HAL handle obtained from the shared library. We hold a weak reference
615   // to this since the actual data resides in the shared Bluetooth library.
616   const btrc_interface_t* target_iface_ = nullptr;
617   const btrc_ctrl_interface_t* control_iface_ = nullptr;
618 
619   bool control_enabled_ = false;
620   bool target_enabled_ = false;
621 };
622 
623 namespace {
624 
625 btbase::AbstractObserverList<BluetoothAvrcpInterface::TargetObserver>*
GetTargetObservers()626 GetTargetObservers() {
627   CHECK(g_interface);
628   return static_cast<BluetoothAvrcpInterfaceImpl*>(g_interface)
629       ->target_observers();
630 }
631 
632 btbase::AbstractObserverList<BluetoothAvrcpInterface::ControlObserver>*
GetControlObservers()633 GetControlObservers() {
634   CHECK(g_interface);
635   return static_cast<BluetoothAvrcpInterfaceImpl*>(g_interface)
636       ->control_observers();
637 }
638 
639 }  // namespace
640 
RemoteFeaturesCallback(const RawAddress & bd_addr,btrc_remote_features_t features)641 void BluetoothAvrcpInterface::TargetObserver::RemoteFeaturesCallback(
642     const RawAddress& bd_addr, btrc_remote_features_t features) {
643   // Do nothing.
644 }
645 
GetPlayStatusCallback(const RawAddress & bd_addr)646 void BluetoothAvrcpInterface::TargetObserver::GetPlayStatusCallback(
647     const RawAddress& bd_addr) {
648   // Do nothing.
649 }
650 
ListPlayerAppAttrCallback(const RawAddress & bd_addr)651 void BluetoothAvrcpInterface::TargetObserver::ListPlayerAppAttrCallback(
652     const RawAddress& bd_addr) {
653   // Do nothing.
654 }
655 
ListPlayerAppValuesCallback(btrc_player_attr_t attr_id,const RawAddress & bd_addr)656 void BluetoothAvrcpInterface::TargetObserver::ListPlayerAppValuesCallback(
657     btrc_player_attr_t attr_id, const RawAddress& bd_addr) {
658   // Do nothing.
659 }
660 
GetPlayerAppValueCallback(uint8_t num_attr,btrc_player_attr_t * p_attrs,const RawAddress & bd_addr)661 void BluetoothAvrcpInterface::TargetObserver::GetPlayerAppValueCallback(
662     uint8_t num_attr, btrc_player_attr_t* p_attrs, const RawAddress& bd_addr) {
663   // Do nothing.
664 }
665 
GetPlayerAppAttrsTextCallback(uint8_t num_attr,btrc_player_attr_t * p_attrs,const RawAddress & bd_addr)666 void BluetoothAvrcpInterface::TargetObserver::GetPlayerAppAttrsTextCallback(
667     uint8_t num_attr, btrc_player_attr_t* p_attrs, const RawAddress& bd_addr) {
668   // Do nothing.
669 }
670 
GetPlayerAppValuesTextCallback(uint8_t attr_id,uint8_t num_val,uint8_t * p_vals,const RawAddress & bd_addr)671 void BluetoothAvrcpInterface::TargetObserver::GetPlayerAppValuesTextCallback(
672     uint8_t attr_id, uint8_t num_val, uint8_t* p_vals,
673     const RawAddress& bd_addr) {
674   // Do nothing.
675 }
676 
SetPlayerAppValueCallback(btrc_player_settings_t * p_vals,const RawAddress & bd_addr)677 void BluetoothAvrcpInterface::TargetObserver::SetPlayerAppValueCallback(
678     btrc_player_settings_t* p_vals, const RawAddress& bd_addr) {
679   // Do nothing.
680 }
681 
GetElementAttrCallback(uint8_t num_attr,btrc_media_attr_t * p_attrs,const RawAddress & bd_addr)682 void BluetoothAvrcpInterface::TargetObserver::GetElementAttrCallback(
683     uint8_t num_attr, btrc_media_attr_t* p_attrs, const RawAddress& bd_addr) {
684   // Do nothing.
685 }
686 
RegisterNotificationCallback(btrc_event_id_t event_id,uint32_t param,const RawAddress & bd_addr)687 void BluetoothAvrcpInterface::TargetObserver::RegisterNotificationCallback(
688     btrc_event_id_t event_id, uint32_t param, const RawAddress& bd_addr) {
689   // Do nothing.
690 }
691 
VolumeChangeCallback(uint8_t volume,uint8_t ctype,const RawAddress & bd_addr)692 void BluetoothAvrcpInterface::TargetObserver::VolumeChangeCallback(
693     uint8_t volume, uint8_t ctype, const RawAddress& bd_addr) {
694   // Do nothing.
695 }
696 
PassthroughCmdCallback(int id,int key_state,const RawAddress & bd_addr)697 void BluetoothAvrcpInterface::TargetObserver::PassthroughCmdCallback(
698     int id, int key_state, const RawAddress& bd_addr) {
699   // Do nothing.
700 }
701 
SetAddressedPlayerCallback(uint16_t player_id,const RawAddress & bd_addr)702 void BluetoothAvrcpInterface::TargetObserver::SetAddressedPlayerCallback(
703     uint16_t player_id, const RawAddress& bd_addr) {
704   // Do nothing.
705 }
706 
SetBrowsedPlayerCallback(uint16_t player_id,const RawAddress & bd_addr)707 void BluetoothAvrcpInterface::TargetObserver::SetBrowsedPlayerCallback(
708     uint16_t player_id, const RawAddress& bd_addr) {
709   // Do nothing.
710 }
711 
GetFolderItemsCallback(uint8_t scope,uint32_t start_item,uint32_t end_item,uint8_t num_attr,uint32_t * p_attr_ids,const RawAddress & bd_addr)712 void BluetoothAvrcpInterface::TargetObserver::GetFolderItemsCallback(
713     uint8_t scope, uint32_t start_item, uint32_t end_item, uint8_t num_attr,
714     uint32_t* p_attr_ids, const RawAddress& bd_addr) {
715   // Do nothing.
716 }
717 
ChangePathCallback(uint8_t direction,uint8_t * folder_uid,const RawAddress & bd_addr)718 void BluetoothAvrcpInterface::TargetObserver::ChangePathCallback(
719     uint8_t direction, uint8_t* folder_uid, const RawAddress& bd_addr) {
720   // Do nothing.
721 }
722 
GetItemAttrCallback(uint8_t scope,uint8_t * uid,uint16_t uid_counter,uint8_t num_attr,btrc_media_attr_t * p_attrs,const RawAddress & bd_addr)723 void BluetoothAvrcpInterface::TargetObserver::GetItemAttrCallback(
724     uint8_t scope, uint8_t* uid, uint16_t uid_counter, uint8_t num_attr,
725     btrc_media_attr_t* p_attrs, const RawAddress& bd_addr) {
726   // Do nothing.
727 }
728 
PlayItemCallback(uint8_t scope,uint16_t uid_counter,uint8_t * uid,const RawAddress & bd_addr)729 void BluetoothAvrcpInterface::TargetObserver::PlayItemCallback(
730     uint8_t scope, uint16_t uid_counter, uint8_t* uid,
731     const RawAddress& bd_addr) {
732   // Do nothing.
733 }
734 
GetTotalNumOfItemsCallback(uint8_t scope,const RawAddress & bd_addr)735 void BluetoothAvrcpInterface::TargetObserver::GetTotalNumOfItemsCallback(
736     uint8_t scope, const RawAddress& bd_addr) {
737   // Do nothing.
738 }
739 
SearchCallback(uint16_t str_len,uint8_t * p_str,const RawAddress & bd_addr)740 void BluetoothAvrcpInterface::TargetObserver::SearchCallback(
741     uint16_t str_len, uint8_t* p_str, const RawAddress& bd_addr) {
742   // Do nothing.
743 }
744 
AddToNowPlayingCallback(uint8_t scope,uint8_t * uid,uint16_t uid_counter,const RawAddress & bd_addr)745 void BluetoothAvrcpInterface::TargetObserver::AddToNowPlayingCallback(
746     uint8_t scope, uint8_t* uid, uint16_t uid_counter,
747     const RawAddress& bd_addr) {
748   // Do nothing.
749 }
750 
PassthroughRspCallback(const RawAddress &,int,int)751 void BluetoothAvrcpInterface::ControlObserver::PassthroughRspCallback(
752     const RawAddress& /* bd_addr */, int /* id */, int /* key_state */) {
753   // Do nothing.
754 }
755 
GroupnavigationRspCallback(int,int)756 void BluetoothAvrcpInterface::ControlObserver::GroupnavigationRspCallback(
757     int /* id */, int /* key_state */) {
758   // Do nothing.
759 }
760 
ConnectionStateCallback(bool,bool,const RawAddress &)761 void BluetoothAvrcpInterface::ControlObserver::ConnectionStateCallback(
762     bool /* rc_connect */, bool /* bt_connect */,
763     const RawAddress& /* bd_addr */) {
764   // Do nothing.
765 }
766 
CtrlGetrcfeaturesCallback(const RawAddress &,int)767 void BluetoothAvrcpInterface::ControlObserver::CtrlGetrcfeaturesCallback(
768     const RawAddress& /* bd_addr */, int /* features */) {
769   // Do nothing.
770 }
771 
772 void BluetoothAvrcpInterface::ControlObserver::
CtrlSetplayerapplicationsettingRspCallback(const RawAddress &,uint8_t)773     CtrlSetplayerapplicationsettingRspCallback(const RawAddress& /* bd_addr */,
774                                                uint8_t /* accepted */) {
775   // Do nothing.
776 }
777 
778 void BluetoothAvrcpInterface::ControlObserver::
CtrlPlayerapplicationsettingCallback(const RawAddress &,uint8_t,btrc_player_app_attr_t *,uint8_t,btrc_player_app_ext_attr_t *)779     CtrlPlayerapplicationsettingCallback(
780         const RawAddress& /* bd_addr */, uint8_t /* num_attr */,
781         btrc_player_app_attr_t* /* app_attrs */, uint8_t /* num_ext_attr */,
782         btrc_player_app_ext_attr_t* /* ext_attrs */) {
783   // Do nothing.
784 }
785 
786 void BluetoothAvrcpInterface::ControlObserver::
CtrlPlayerapplicationsettingChangedCallback(const RawAddress &,const btrc_player_settings_t &)787     CtrlPlayerapplicationsettingChangedCallback(
788         const RawAddress& /* bd_addr*/,
789         const btrc_player_settings_t& /* vals */) {
790   // Do nothing.
791 }
792 
CtrlSetabsvolCmdCallback(const RawAddress &,uint8_t,uint8_t)793 void BluetoothAvrcpInterface::ControlObserver::CtrlSetabsvolCmdCallback(
794     const RawAddress& /* bd_addr */, uint8_t /* abs_vol */,
795     uint8_t /* label */) {
796   // Do nothing.
797 }
798 
799 void BluetoothAvrcpInterface::ControlObserver::
CtrlRegisternotificationAbsVolCallback(const RawAddress &,uint8_t)800     CtrlRegisternotificationAbsVolCallback(const RawAddress& /* bd_addr */,
801                                            uint8_t /* label */) {
802   // Do nothing.
803 }
804 
CtrlTrackChangedCallback(const RawAddress &,uint8_t,btrc_element_attr_val_t *)805 void BluetoothAvrcpInterface::ControlObserver::CtrlTrackChangedCallback(
806     const RawAddress& /*bd_addr */, uint8_t /* num_attr */,
807     btrc_element_attr_val_t* /* p_attrs */) {
808   // Do nothing.
809 }
810 
CtrlPlayPositionChangedCallback(const RawAddress &,uint32_t,uint32_t)811 void BluetoothAvrcpInterface::ControlObserver::CtrlPlayPositionChangedCallback(
812     const RawAddress& /* bd_addr */, uint32_t /* song_len */,
813     uint32_t /* song_pos */) {
814   // Do nothing.
815 }
816 
CtrlPlayStatusChangedCallback(const RawAddress &,btrc_play_status_t)817 void BluetoothAvrcpInterface::ControlObserver::CtrlPlayStatusChangedCallback(
818     const RawAddress& /* bd_addr */, btrc_play_status_t /* play_status */) {
819   // Do nothing.
820 }
821 
CtrlGetFolderItemsCallback(const RawAddress &,btrc_status_t,const btrc_folder_items_t *,uint8_t)822 void BluetoothAvrcpInterface::ControlObserver::CtrlGetFolderItemsCallback(
823     const RawAddress& /* bd_addr */, btrc_status_t /* status */,
824     const btrc_folder_items_t* /*folder_items */, uint8_t /* count */) {
825   // Do nothing.
826 }
827 
CtrlChangePathCallback(const RawAddress &,uint32_t)828 void BluetoothAvrcpInterface::ControlObserver::CtrlChangePathCallback(
829     const RawAddress& /* bd_addr */, uint32_t /* count */) {
830   // Do nothing.
831 }
832 
CtrlSetBrowsedPlayerCallback(const RawAddress &,uint8_t,uint8_t)833 void BluetoothAvrcpInterface::ControlObserver::CtrlSetBrowsedPlayerCallback(
834     const RawAddress& /* bd_addr */, uint8_t /* num_items */,
835     uint8_t /* depth */) {
836   // Do nothing.
837 }
838 
CtrlSetAddressedPlayerCallback(const RawAddress &,uint8_t)839 void BluetoothAvrcpInterface::ControlObserver::CtrlSetAddressedPlayerCallback(
840     const RawAddress& /* bd_addr */, uint8_t /* status */) {
841   // Do nothing.
842 }
843 
844 // static
Initialize()845 bool BluetoothAvrcpInterface::Initialize() {
846   unique_lock<shared_mutex_impl> lock(g_instance_lock);
847   CHECK(!g_interface);
848 
849   std::unique_ptr<BluetoothAvrcpInterfaceImpl> impl(
850       new BluetoothAvrcpInterfaceImpl());
851   if (!impl->Initialize()) {
852     LOG(ERROR) << "Failed to initialize BluetoothAvrcpInterface";
853     return false;
854   }
855 
856   g_interface = impl.release();
857 
858   return true;
859 }
860 
861 // static
CleanUp()862 void BluetoothAvrcpInterface::CleanUp() {
863   unique_lock<shared_mutex_impl> lock(g_instance_lock);
864   CHECK(g_interface);
865 
866   delete g_interface;
867   g_interface = nullptr;
868 }
869 
870 // static
IsInitialized()871 bool BluetoothAvrcpInterface::IsInitialized() {
872   shared_lock<shared_mutex_impl> lock(g_instance_lock);
873 
874   return g_interface != nullptr;
875 }
876 
877 // static
Get()878 BluetoothAvrcpInterface* BluetoothAvrcpInterface::Get() {
879   shared_lock<shared_mutex_impl> lock(g_instance_lock);
880   CHECK(g_interface);
881   return g_interface;
882 }
883 
884 // static
InitializeForTesting(BluetoothAvrcpInterface * test_instance)885 void BluetoothAvrcpInterface::InitializeForTesting(
886     BluetoothAvrcpInterface* test_instance) {
887   unique_lock<shared_mutex_impl> lock(g_instance_lock);
888   CHECK(test_instance);
889   CHECK(!g_interface);
890 
891   g_interface = test_instance;
892 }
893 
894 }  // namespace hal
895 }  // namespace bluetooth
896