1 /*
2 * Copyright (C) 2021 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_observer_list.h"
27 #include "iservice_registry.h"
28 #include "raw_address.h"
29 #include "system_ability_definition.h"
30 #include "bluetooth_avrcp_tg.h"
31
32 namespace OHOS {
33 namespace Bluetooth {
34 struct AvrcpTarget::impl {
35 public:
36 class ObserverImpl : public BluetoothAvrcpTgObserverStub {
37 public:
ObserverImpl(AvrcpTarget::impl * impl)38 explicit ObserverImpl(AvrcpTarget::impl *impl) : impl_(impl)
39 {}
40 ~ObserverImpl() override = default;
41
OnConnectionStateChanged(const BluetoothRawAddress & addr,int32_t state)42 void OnConnectionStateChanged(const BluetoothRawAddress &addr, int32_t state) override
43 {
44 HILOGD("%{public}s start.", __func__);
45 BluetoothRemoteDevice device(addr.GetAddress(), BTTransport::ADAPTER_BREDR);
46 impl_->OnConnectionStateChanged(device, static_cast<int>(state));
47
48 return;
49 }
50
51 private:
52 AvrcpTarget::impl *impl_;
53 };
54
55 class AvrcpTgDeathRecipient final : public IRemoteObject::DeathRecipient {
56 public:
AvrcpTgDeathRecipient(AvrcpTarget::impl & avrcpTgServer)57 AvrcpTgDeathRecipient(AvrcpTarget::impl &avrcpTgServer) : avrcpTgServer_(avrcpTgServer) {};
58 ~AvrcpTgDeathRecipient() final = default;
59 BLUETOOTH_DISALLOW_COPY_AND_ASSIGN(AvrcpTgDeathRecipient);
60
OnRemoteDied(const wptr<IRemoteObject> & remote)61 void OnRemoteDied(const wptr<IRemoteObject> &remote) final
62 {
63 HILOGI("AvrcpTarget::impl::AvrcpTgDeathRecipient::OnRemoteDied starts");
64 avrcpTgServer_.proxy_->AsObject()->RemoveDeathRecipient(avrcpTgServer_.deathRecipient_);
65 avrcpTgServer_.proxy_ = nullptr;
66 }
67
68 private:
69 AvrcpTarget::impl &avrcpTgServer_;
70 };
71
implOHOS::Bluetooth::AvrcpTarget::impl72 impl()
73 {
74 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
75
76 sptr<ISystemAbilityManager> samgr = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
77 sptr<IRemoteObject> hostRemote = samgr->GetSystemAbility(BLUETOOTH_HOST_SYS_ABILITY_ID);
78 if (!hostRemote) {
79 HILOGI("AvrcpTarget::impl:impl() failed: no hostRemote");
80 return;
81 }
82
83 sptr<IBluetoothHost> hostProxy = iface_cast<IBluetoothHost>(hostRemote);
84 sptr<IRemoteObject> remote = hostProxy->GetProfile(PROFILE_AVRCP_TG);
85 if (!remote) {
86 HILOGI("AvrcpTarget::impl:impl() failed: no remote");
87 return;
88 }
89 HILOGI("AvrcpTarget::impl:impl() remote obtained");
90 proxy_ = iface_cast<IBluetoothAvrcpTg>(remote);
91
92 deathRecipient_ = new AvrcpTgDeathRecipient(*this);
93 if (!proxy_) {
94 HILOGI("AvrcpTg::impl:impl() proxy_ is null when used!");
95 } else {
96 proxy_->AsObject()->AddDeathRecipient(deathRecipient_);
97 }
98
99 observer_ = new (std::nothrow) ObserverImpl(this);
100 proxy_->RegisterObserver(observer_);
101 }
102
~implOHOS::Bluetooth::AvrcpTarget::impl103 ~impl()
104 {
105 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
106 proxy_->UnregisterObserver(observer_);
107 }
108
IsEnabledOHOS::Bluetooth::AvrcpTarget::impl109 bool IsEnabled(void)
110 {
111 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
112
113 return (proxy_ != nullptr && !BluetoothHost::GetDefaultHost().IsBtDiscovering());
114 }
115
OnConnectionStateChangedOHOS::Bluetooth::AvrcpTarget::impl116 void OnConnectionStateChanged(const BluetoothRemoteDevice &device, int state)
117 {
118 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
119 std::lock_guard<std::mutex> lock(observerMutex_);
120 observers_.ForEach([device, state](std::shared_ptr<IObserver> observer) {
121 observer->OnConnectionStateChanged(device, state);
122 });
123 }
124
125 std::mutex observerMutex_;
126 sptr<IBluetoothAvrcpTg> proxy_;
127 BluetoothObserverList<AvrcpTarget::IObserver> observers_;
128 sptr<ObserverImpl> observer_;
129 sptr<AvrcpTgDeathRecipient> deathRecipient_;
130 };
131
GetProfile(void)132 AvrcpTarget *AvrcpTarget::GetProfile(void)
133 {
134 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
135
136 static AvrcpTarget instance;
137
138 return &instance;
139 }
140
141 /******************************************************************
142 * REGISTER / UNREGISTER OBSERVER *
143 ******************************************************************/
144
RegisterObserver(AvrcpTarget::IObserver * observer)145 void AvrcpTarget::RegisterObserver(AvrcpTarget::IObserver *observer)
146 {
147 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
148
149 std::lock_guard<std::mutex> lock(pimpl->observerMutex_);
150 if (pimpl->IsEnabled()) {
151 std::shared_ptr<IObserver> observerPtr(observer, [](IObserver *) {});
152 pimpl->observers_.Register(observerPtr);
153 }
154 }
155
UnregisterObserver(AvrcpTarget::IObserver * observer)156 void AvrcpTarget::UnregisterObserver(AvrcpTarget::IObserver *observer)
157 {
158 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
159
160 std::lock_guard<std::mutex> lock(pimpl->observerMutex_);
161
162 std::shared_ptr<IObserver> observerPtr(observer, [](IObserver *) {});
163 if (pimpl->IsEnabled()) {
164 pimpl->observers_.Deregister(observerPtr);
165 }
166 }
167
168 /******************************************************************
169 * CONNECTION *
170 ******************************************************************/
171
SetActiveDevice(const BluetoothRemoteDevice & device)172 void AvrcpTarget::SetActiveDevice(const BluetoothRemoteDevice &device)
173 {
174 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
175
176 if (pimpl->IsEnabled()) {
177 BluetoothRawAddress rawAddr(device.GetDeviceAddr());
178 pimpl->proxy_->SetActiveDevice(rawAddr);
179 }
180 }
181
GetConnectedDevices(void)182 std::vector<BluetoothRemoteDevice> AvrcpTarget::GetConnectedDevices(void)
183 {
184 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
185
186 std::vector<BluetoothRemoteDevice> devices;
187
188 if (pimpl->IsEnabled()) {
189 std::vector<sptr<BluetoothRawAddress>> rawAddrs;
190 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 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
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<sptr<BluetoothRawAddress>> rawAddrs;
213 rawAddrs = pimpl->proxy_->GetDevicesByStates(convertStates);
214
215 for (auto rawAddr : rawAddrs) {
216 BluetoothRemoteDevice device(rawAddr->GetAddress(), BTTransport::ADAPTER_BREDR);
217 devices.push_back(device);
218 }
219 }
220
221 return devices;
222 }
223
GetDeviceState(const BluetoothRemoteDevice & device)224 int AvrcpTarget::GetDeviceState(const BluetoothRemoteDevice &device)
225 {
226 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
227
228 int32_t result = static_cast<int32_t>(BTConnectState::DISCONNECTED);
229
230 if (pimpl->IsEnabled()) {
231 BluetoothRawAddress rawAddr(device.GetDeviceAddr());
232 result = pimpl->proxy_->GetDeviceState(rawAddr);
233 }
234
235 return static_cast<int>(result);
236 }
237
Connect(const BluetoothRemoteDevice & device)238 bool AvrcpTarget::Connect(const BluetoothRemoteDevice &device)
239 {
240 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
241
242 int result = RET_BAD_STATUS;
243
244 if (pimpl->IsEnabled()) {
245 BluetoothRawAddress rawAddr(device.GetDeviceAddr());
246 result = pimpl->proxy_->Connect(rawAddr);
247 }
248
249 return result == RET_NO_ERROR ? true : false;
250 }
251
Disconnect(const BluetoothRemoteDevice & device)252 bool AvrcpTarget::Disconnect(const BluetoothRemoteDevice &device)
253 {
254 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
255
256 int result = RET_BAD_STATUS;
257
258 if (pimpl->IsEnabled()) {
259 BluetoothRawAddress rawAddr(device.GetDeviceAddr());
260 result = pimpl->proxy_->Disconnect(rawAddr);
261 }
262
263 return result == RET_NO_ERROR ? true : false;
264 }
265
266 /******************************************************************
267 * NOTIFICATION *
268 ******************************************************************/
269
NotifyPlaybackStatusChanged(uint8_t playStatus,uint32_t playbackPos)270 void AvrcpTarget::NotifyPlaybackStatusChanged(uint8_t playStatus, uint32_t playbackPos)
271 {
272 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
273
274 if (pimpl->IsEnabled()) {
275 pimpl->proxy_->NotifyPlaybackStatusChanged(
276 static_cast<int32_t>(playStatus), static_cast<int32_t>(playbackPos));
277 }
278 }
279
NotifyTrackChanged(uint64_t uid,uint32_t playbackPos)280 void AvrcpTarget::NotifyTrackChanged(uint64_t uid, uint32_t playbackPos)
281 {
282 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
283
284 if (pimpl->IsEnabled()) {
285 pimpl->proxy_->NotifyTrackChanged(static_cast<int64_t>(uid), static_cast<int32_t>(playbackPos));
286 }
287 }
288
NotifyTrackReachedEnd(uint32_t playbackPos)289 void AvrcpTarget::NotifyTrackReachedEnd(uint32_t playbackPos)
290 {
291 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
292
293 if (pimpl->IsEnabled()) {
294 pimpl->proxy_->NotifyTrackReachedEnd(static_cast<int32_t>(playbackPos));
295 }
296 }
297
NotifyTrackReachedStart(uint32_t playbackPos)298 void AvrcpTarget::NotifyTrackReachedStart(uint32_t playbackPos)
299 {
300 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
301
302 if (pimpl->IsEnabled()) {
303 pimpl->proxy_->NotifyTrackReachedStart(static_cast<int32_t>(playbackPos));
304 }
305 }
306
NotifyPlaybackPosChanged(uint32_t playbackPos)307 void AvrcpTarget::NotifyPlaybackPosChanged(uint32_t playbackPos)
308 {
309 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
310
311 if (pimpl->IsEnabled()) {
312 pimpl->proxy_->NotifyPlaybackPosChanged(static_cast<int32_t>(playbackPos));
313 }
314 }
315
NotifyPlayerAppSettingChanged(const std::vector<uint8_t> & attributes,const std::vector<uint8_t> & values)316 void AvrcpTarget::NotifyPlayerAppSettingChanged(
317 const std::vector<uint8_t> &attributes, const std::vector<uint8_t> &values)
318 {
319 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
320
321 std::vector<int32_t> attrs;
322 std::vector<int32_t> vals;
323
324 for (auto attribute : attributes) {
325 attrs.push_back(attribute);
326 }
327 for (auto value : values) {
328 vals.push_back(value);
329 }
330
331 if (pimpl->IsEnabled()) {
332 pimpl->proxy_->NotifyPlayerAppSettingChanged(attrs, vals);
333 }
334 }
335
NotifyNowPlayingContentChanged(void)336 void AvrcpTarget::NotifyNowPlayingContentChanged(void)
337 {
338 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
339
340 if (pimpl->IsEnabled()) {
341 pimpl->proxy_->NotifyNowPlayingContentChanged();
342 }
343 }
344
NotifyAvailablePlayersChanged(void)345 void AvrcpTarget::NotifyAvailablePlayersChanged(void)
346 {
347 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
348
349 if (pimpl->IsEnabled()) {
350 pimpl->proxy_->NotifyAvailablePlayersChanged();
351 }
352 }
353
NotifyAddressedPlayerChanged(uint16_t playerId,uint16_t uidCounter)354 void AvrcpTarget::NotifyAddressedPlayerChanged(uint16_t playerId, uint16_t uidCounter)
355 {
356 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
357
358 if (pimpl->IsEnabled()) {
359 pimpl->proxy_->NotifyAddressedPlayerChanged(
360 static_cast<int32_t>(playerId), static_cast<int32_t>(uidCounter));
361 }
362 }
363
NotifyUidChanged(uint16_t uidCounter)364 void AvrcpTarget::NotifyUidChanged(uint16_t uidCounter)
365 {
366 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
367
368 if (pimpl->IsEnabled()) {
369 pimpl->proxy_->NotifyUidChanged(static_cast<int32_t>(uidCounter));
370 }
371 }
372
NotifyVolumeChanged(uint8_t volume)373 void AvrcpTarget::NotifyVolumeChanged(uint8_t volume)
374 {
375 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
376
377 if (pimpl->IsEnabled()) {
378 pimpl->proxy_->NotifyVolumeChanged(static_cast<int32_t>(volume));
379 }
380 }
381
AvrcpTarget(void)382 AvrcpTarget::AvrcpTarget(void)
383 {
384 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
385
386 pimpl = std::make_unique<impl>();
387 }
388
~AvrcpTarget(void)389 AvrcpTarget::~AvrcpTarget(void)
390 {
391 HILOGD("[%{public}s]: %{public}s(): Enter!", __FILE__, __FUNCTION__);
392
393 pimpl->proxy_->AsObject()->RemoveDeathRecipient(pimpl->deathRecipient_);
394 pimpl = nullptr;
395 }
396 } // namespace ohos
397 } // namespace bluetooth
398