• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2021-2022 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include <list>
17 #include <memory>
18 #include <mutex>
19 
20 #include "bluetooth_def.h"
21 #include "bluetooth_avrcp_tg_proxy.h"
22 #include "bluetooth_avrcp_tg_observer_stub.h"
23 #include "bluetooth_host.h"
24 #include "bluetooth_host_proxy.h"
25 #include "bluetooth_log.h"
26 #include "bluetooth_utils.h"
27 #include "bluetooth_observer_list.h"
28 #include "iservice_registry.h"
29 #include "raw_address.h"
30 #include "system_ability_definition.h"
31 #include "bluetooth_avrcp_tg.h"
32 
33 namespace OHOS {
34 namespace Bluetooth {
35 struct AvrcpTarget::impl {
36 public:
37     class ObserverImpl : public BluetoothAvrcpTgObserverStub {
38     public:
ObserverImpl(AvrcpTarget::impl * impl)39         explicit ObserverImpl(AvrcpTarget::impl *impl) : impl_(impl)
40         {}
41         ~ObserverImpl() override = default;
42 
OnConnectionStateChanged(const BluetoothRawAddress & addr,int32_t state)43         void OnConnectionStateChanged(const BluetoothRawAddress &addr, int32_t state) override
44         {
45             HILOGI("enter, address: %{public}s, state: %{public}d", GetEncryptAddr(addr.GetAddress()).c_str(), state);
46             BluetoothRemoteDevice device(addr.GetAddress(), BTTransport::ADAPTER_BREDR);
47             impl_->OnConnectionStateChanged(device, static_cast<int>(state));
48 
49             return;
50         }
51 
52     private:
53         AvrcpTarget::impl *impl_;
54     };
55 
56     class AvrcpTgDeathRecipient final : public IRemoteObject::DeathRecipient {
57     public:
AvrcpTgDeathRecipient(AvrcpTarget::impl & avrcpTgServer)58         AvrcpTgDeathRecipient(AvrcpTarget::impl &avrcpTgServer) : avrcpTgServer_(avrcpTgServer) {};
59         ~AvrcpTgDeathRecipient() final = default;
60         BLUETOOTH_DISALLOW_COPY_AND_ASSIGN(AvrcpTgDeathRecipient);
61 
OnRemoteDied(const wptr<IRemoteObject> & remote)62         void OnRemoteDied(const wptr<IRemoteObject> &remote) final
63         {
64             HILOGI("starts");
65             avrcpTgServer_.proxy_->AsObject()->RemoveDeathRecipient(avrcpTgServer_.deathRecipient_);
66             avrcpTgServer_.proxy_ = nullptr;
67         }
68 
69     private:
70         AvrcpTarget::impl &avrcpTgServer_;
71     };
72 
implOHOS::Bluetooth::AvrcpTarget::impl73     impl()
74     {
75         HILOGI("enter");
76 
77         sptr<ISystemAbilityManager> samgr = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
78         sptr<IRemoteObject> hostRemote = samgr->GetSystemAbility(BLUETOOTH_HOST_SYS_ABILITY_ID);
79         if (!hostRemote) {
80             HILOGI("failed: no hostRemote");
81             return;
82         }
83 
84         sptr<IBluetoothHost> hostProxy = iface_cast<IBluetoothHost>(hostRemote);
85         sptr<IRemoteObject> remote = hostProxy->GetProfile(PROFILE_AVRCP_TG);
86         if (!remote) {
87             HILOGI("failed: no remote");
88             return;
89         }
90         HILOGI("remote obtained");
91         proxy_ = iface_cast<IBluetoothAvrcpTg>(remote);
92 
93         deathRecipient_ = new AvrcpTgDeathRecipient(*this);
94         if (!proxy_) {
95             HILOGI("proxy_ is null when used!");
96         } else {
97             proxy_->AsObject()->AddDeathRecipient(deathRecipient_);
98         }
99 
100         observer_ = new (std::nothrow) ObserverImpl(this);
101         proxy_->RegisterObserver(observer_);
102     }
103 
~implOHOS::Bluetooth::AvrcpTarget::impl104     ~impl()
105     {
106         HILOGI("enter");
107         proxy_->UnregisterObserver(observer_);
108     }
109 
IsEnabledOHOS::Bluetooth::AvrcpTarget::impl110     bool IsEnabled(void)
111     {
112         HILOGI("enter");
113 
114         return (proxy_ != nullptr && !BluetoothHost::GetDefaultHost().IsBtDiscovering());
115     }
116 
OnConnectionStateChangedOHOS::Bluetooth::AvrcpTarget::impl117     void OnConnectionStateChanged(const BluetoothRemoteDevice &device, int state)
118     {
119         HILOGI("enter, device: %{public}s, state: %{public}d", GET_ENCRYPT_ADDR(device), state);
120         std::lock_guard<std::mutex> lock(observerMutex_);
121         observers_.ForEach([device, state](std::shared_ptr<IObserver> observer) {
122             observer->OnConnectionStateChanged(device, state);
123         });
124     }
125 
126     std::mutex observerMutex_;
127     sptr<IBluetoothAvrcpTg> proxy_;
128     BluetoothObserverList<AvrcpTarget::IObserver> observers_;
129     sptr<ObserverImpl> observer_;
130     sptr<AvrcpTgDeathRecipient> deathRecipient_;
131 };
132 
GetProfile(void)133 AvrcpTarget *AvrcpTarget::GetProfile(void)
134 {
135     HILOGI("enter");
136 
137     static AvrcpTarget instance;
138 
139     return &instance;
140 }
141 
142 /******************************************************************
143  * REGISTER / UNREGISTER OBSERVER                                 *
144  ******************************************************************/
145 
RegisterObserver(AvrcpTarget::IObserver * observer)146 void AvrcpTarget::RegisterObserver(AvrcpTarget::IObserver *observer)
147 {
148     HILOGI("enter");
149 
150     std::lock_guard<std::mutex> lock(pimpl->observerMutex_);
151     if (pimpl->IsEnabled()) {
152         std::shared_ptr<IObserver> observerPtr(observer, [](IObserver *) {});
153         pimpl->observers_.Register(observerPtr);
154     }
155 }
156 
UnregisterObserver(AvrcpTarget::IObserver * observer)157 void AvrcpTarget::UnregisterObserver(AvrcpTarget::IObserver *observer)
158 {
159     HILOGI("enter");
160 
161     std::lock_guard<std::mutex> lock(pimpl->observerMutex_);
162 
163     std::shared_ptr<IObserver> observerPtr(observer, [](IObserver *) {});
164     if (pimpl->IsEnabled()) {
165         pimpl->observers_.Deregister(observerPtr);
166     }
167 }
168 
169 /******************************************************************
170  * CONNECTION                                                     *
171  ******************************************************************/
172 
SetActiveDevice(const BluetoothRemoteDevice & device)173 void AvrcpTarget::SetActiveDevice(const BluetoothRemoteDevice &device)
174 {
175     HILOGI("enter, device: %{public}s", GET_ENCRYPT_ADDR(device));
176 
177     if (pimpl->IsEnabled()) {
178         BluetoothRawAddress rawAddr(device.GetDeviceAddr());
179         pimpl->proxy_->SetActiveDevice(rawAddr);
180     }
181 }
182 
GetConnectedDevices(void)183 std::vector<BluetoothRemoteDevice> AvrcpTarget::GetConnectedDevices(void)
184 {
185     HILOGI("enter");
186 
187     std::vector<BluetoothRemoteDevice> devices;
188 
189     if (pimpl->IsEnabled()) {
190         std::vector<BluetoothRawAddress> rawAddrs = pimpl->proxy_->GetConnectedDevices();
191 
192         for (auto rawAddr : rawAddrs) {
193             BluetoothRemoteDevice device(rawAddr.GetAddress(), BTTransport::ADAPTER_BREDR);
194             devices.push_back(device);
195         }
196     }
197 
198     return devices;
199 }
200 
GetDevicesByStates(std::vector<int> states)201 std::vector<BluetoothRemoteDevice> AvrcpTarget::GetDevicesByStates(std::vector<int> states)
202 {
203     HILOGI("enter");
204 
205     std::vector<BluetoothRemoteDevice> devices;
206 
207     if (pimpl->IsEnabled()) {
208         std::vector<int32_t> convertStates;
209         for (auto state : states) {
210             convertStates.push_back(static_cast<int32_t>(state));
211         }
212         std::vector<BluetoothRawAddress> rawAddrs = pimpl->proxy_->GetDevicesByStates(convertStates);
213 
214         for (auto rawAddr : rawAddrs) {
215             BluetoothRemoteDevice device(rawAddr.GetAddress(), BTTransport::ADAPTER_BREDR);
216             devices.push_back(device);
217         }
218     }
219 
220     return devices;
221 }
222 
GetDeviceState(const BluetoothRemoteDevice & device)223 int AvrcpTarget::GetDeviceState(const BluetoothRemoteDevice &device)
224 {
225     HILOGI("enter, device: %{public}s", GET_ENCRYPT_ADDR(device));
226 
227     int32_t result = static_cast<int32_t>(BTConnectState::DISCONNECTED);
228 
229     if (pimpl->IsEnabled()) {
230         BluetoothRawAddress rawAddr(device.GetDeviceAddr());
231         result = pimpl->proxy_->GetDeviceState(rawAddr);
232     }
233 
234     return static_cast<int>(result);
235 }
236 
Connect(const BluetoothRemoteDevice & device)237 bool AvrcpTarget::Connect(const BluetoothRemoteDevice &device)
238 {
239     HILOGI("enter, device: %{public}s", GET_ENCRYPT_ADDR(device));
240 
241     int result = RET_BAD_STATUS;
242 
243     if (pimpl->IsEnabled()) {
244         BluetoothRawAddress rawAddr(device.GetDeviceAddr());
245         result = pimpl->proxy_->Connect(rawAddr);
246     }
247 
248     return result == RET_NO_ERROR ? true : false;
249 }
250 
Disconnect(const BluetoothRemoteDevice & device)251 bool AvrcpTarget::Disconnect(const BluetoothRemoteDevice &device)
252 {
253     HILOGI("enter, device: %{public}s", GET_ENCRYPT_ADDR(device));
254 
255     int result = RET_BAD_STATUS;
256 
257     if (pimpl->IsEnabled()) {
258         BluetoothRawAddress rawAddr(device.GetDeviceAddr());
259         result = pimpl->proxy_->Disconnect(rawAddr);
260     }
261 
262     return result == RET_NO_ERROR ? true : false;
263 }
264 
265 /******************************************************************
266  * NOTIFICATION                                                   *
267  ******************************************************************/
268 
NotifyPlaybackStatusChanged(uint8_t playStatus,uint32_t playbackPos)269 void AvrcpTarget::NotifyPlaybackStatusChanged(uint8_t playStatus, uint32_t playbackPos)
270 {
271     HILOGI("enter, playStatus: %{public}d, playbackPos: %{public}d", playStatus, playbackPos);
272 
273     if (pimpl->IsEnabled()) {
274         pimpl->proxy_->NotifyPlaybackStatusChanged(
275             static_cast<int32_t>(playStatus), static_cast<int32_t>(playbackPos));
276     }
277 }
278 
NotifyTrackChanged(uint64_t uid,uint32_t playbackPos)279 void AvrcpTarget::NotifyTrackChanged(uint64_t uid, uint32_t playbackPos)
280 {
281     HILOGI("enter, playbackPos: %{public}d", playbackPos);
282 
283     if (pimpl->IsEnabled()) {
284         pimpl->proxy_->NotifyTrackChanged(static_cast<int64_t>(uid), static_cast<int32_t>(playbackPos));
285     }
286 }
287 
NotifyTrackReachedEnd(uint32_t playbackPos)288 void AvrcpTarget::NotifyTrackReachedEnd(uint32_t playbackPos)
289 {
290     HILOGI("enter, playbackPos: %{public}d", playbackPos);
291 
292     if (pimpl->IsEnabled()) {
293         pimpl->proxy_->NotifyTrackReachedEnd(static_cast<int32_t>(playbackPos));
294     }
295 }
296 
NotifyTrackReachedStart(uint32_t playbackPos)297 void AvrcpTarget::NotifyTrackReachedStart(uint32_t playbackPos)
298 {
299     HILOGI("enter, playbackPos: %{public}d", playbackPos);
300 
301     if (pimpl->IsEnabled()) {
302         pimpl->proxy_->NotifyTrackReachedStart(static_cast<int32_t>(playbackPos));
303     }
304 }
305 
NotifyPlaybackPosChanged(uint32_t playbackPos)306 void AvrcpTarget::NotifyPlaybackPosChanged(uint32_t playbackPos)
307 {
308     HILOGI("enter, playbackPos: %{public}d", playbackPos);
309 
310     if (pimpl->IsEnabled()) {
311         pimpl->proxy_->NotifyPlaybackPosChanged(static_cast<int32_t>(playbackPos));
312     }
313 }
314 
NotifyPlayerAppSettingChanged(const std::vector<uint8_t> & attributes,const std::vector<uint8_t> & values)315 void AvrcpTarget::NotifyPlayerAppSettingChanged(
316     const std::vector<uint8_t> &attributes, const std::vector<uint8_t> &values)
317 {
318     HILOGI("enter");
319 
320     std::vector<int32_t> attrs;
321     std::vector<int32_t> vals;
322 
323     for (auto attribute : attributes) {
324         attrs.push_back(attribute);
325     }
326     for (auto value : values) {
327         vals.push_back(value);
328     }
329 
330     if (pimpl->IsEnabled()) {
331         pimpl->proxy_->NotifyPlayerAppSettingChanged(attrs, vals);
332     }
333 }
334 
NotifyNowPlayingContentChanged(void)335 void AvrcpTarget::NotifyNowPlayingContentChanged(void)
336 {
337     HILOGI("enter");
338 
339     if (pimpl->IsEnabled()) {
340         pimpl->proxy_->NotifyNowPlayingContentChanged();
341     }
342 }
343 
NotifyAvailablePlayersChanged(void)344 void AvrcpTarget::NotifyAvailablePlayersChanged(void)
345 {
346     HILOGI("enter");
347 
348     if (pimpl->IsEnabled()) {
349         pimpl->proxy_->NotifyAvailablePlayersChanged();
350     }
351 }
352 
NotifyAddressedPlayerChanged(uint16_t playerId,uint16_t uidCounter)353 void AvrcpTarget::NotifyAddressedPlayerChanged(uint16_t playerId, uint16_t uidCounter)
354 {
355     HILOGI("enter, playerId: %{public}d, uidCounter: %{public}d", playerId, uidCounter);
356 
357     if (pimpl->IsEnabled()) {
358         pimpl->proxy_->NotifyAddressedPlayerChanged(
359             static_cast<int32_t>(playerId), static_cast<int32_t>(uidCounter));
360     }
361 }
362 
NotifyUidChanged(uint16_t uidCounter)363 void AvrcpTarget::NotifyUidChanged(uint16_t uidCounter)
364 {
365     HILOGI("enter, uidCounter: %{public}d", uidCounter);
366 
367     if (pimpl->IsEnabled()) {
368         pimpl->proxy_->NotifyUidChanged(static_cast<int32_t>(uidCounter));
369     }
370 }
371 
NotifyVolumeChanged(uint8_t volume)372 void AvrcpTarget::NotifyVolumeChanged(uint8_t volume)
373 {
374     HILOGI("enter, volume: %{public}d", volume);
375 
376     if (pimpl->IsEnabled()) {
377         pimpl->proxy_->NotifyVolumeChanged(static_cast<int32_t>(volume));
378     }
379 }
380 
AvrcpTarget(void)381 AvrcpTarget::AvrcpTarget(void)
382 {
383     HILOGI("enter");
384 
385     pimpl = std::make_unique<impl>();
386 }
387 
~AvrcpTarget(void)388 AvrcpTarget::~AvrcpTarget(void)
389 {
390     HILOGI("enter");
391 
392     pimpl->proxy_->AsObject()->RemoveDeathRecipient(pimpl->deathRecipient_);
393     pimpl = nullptr;
394 }
395 } // namespace Bluetooth
396 } // namespace OHOS
397