• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 <hdf_log.h>
17 #include "audio_internal.h"
18 #include "i_bluetooth_a2dp_src.h"
19 #include "i_bluetooth_host.h"
20 #include "bluetooth_a2dp_src_observer.h"
21 #include "bluetooth_def.h"
22 #include "iservice_registry.h"
23 #include "system_ability_definition.h"
24 #include "audio_bluetooth_manager.h"
25 
26 #ifdef A2DP_HDI_SERVICE
27 #include "bluetooth_audio_device.h"
28 #endif
29 
30 #define HDF_LOG_TAG BTAudioBluetoothManager
31 
32 namespace OHOS {
33 namespace Bluetooth {
34 using namespace OHOS::bluetooth;
35 
36 #ifdef A2DP_HDI_SERVICE
37 using namespace OHOS::bluetooth::audio;
38 static const char *g_bluetoothAudioDeviceSoPath = HDF_LIBRARY_FULL_PATH("libbluetooth_audio_session");
39 static void *g_ptrAudioDeviceHandle = NULL;
40 SetUpFunc setUpFunc;
41 TearDownFunc tearDownFunc;
42 GetStateFunc getStateFunc;
43 StartPlayingFunc startPlayingFunc;
44 SuspendPlayingFunc suspendPlayingFunc;
45 StopPlayingFunc stopPlayingFunc;
46 WriteFrameFunc writeFrameFunc;
47 #endif
48 
49 sptr<IBluetoothA2dpSrc> g_proxy_ = nullptr;
50 static sptr<BluetoothA2dpSrcObserver> g_btA2dpSrcObserverCallbacks = nullptr;
51 int g_playState = A2DP_NOT_PLAYING;
52 
AudioOnConnectionStateChanged(const RawAddress & device,int state)53 static void AudioOnConnectionStateChanged(const RawAddress &device, int state)
54 {
55     HDF_LOGI("%{public}s, state:%{public}d", __func__, state);
56     (void) state;
57 }
58 
AudioOnPlayingStatusChanged(const RawAddress & device,int playingState,int error)59 static void AudioOnPlayingStatusChanged(const RawAddress &device, int playingState, int error)
60 {
61     HDF_LOGI("%{public}s, playingState:%{public}d", __func__, playingState);
62     g_playState = playingState;
63     (void) error;
64 }
65 
AudioOnConfigurationChanged(const RawAddress & device,const BluetoothA2dpCodecInfo & info,int error)66 static void AudioOnConfigurationChanged(const RawAddress &device, const BluetoothA2dpCodecInfo &info, int error)
67 {
68     (void) device;
69     (void) info;
70     (void) error;
71 }
72 
AudioOnMediaStackChanged(const RawAddress & device,int action)73 static void AudioOnMediaStackChanged(const RawAddress &device, int action)
74 {
75     (void) device;
76     (void) action;
77 }
78 
79 
80 static BtA2dpAudioCallback g_hdiCallbacks = {
81     .OnConnectionStateChanged = AudioOnConnectionStateChanged,
82     .OnPlayingStatusChanged = AudioOnPlayingStatusChanged,
83     .OnConfigurationChanged =  AudioOnConfigurationChanged,
84     .OnMediaStackChanged = AudioOnMediaStackChanged,
85 };
86 
GetPlayingState()87 int GetPlayingState()
88 {
89     HDF_LOGI("%{public}s: state:%{public}d", __func__, g_playState);
90     return g_playState;
91 }
92 
GetProxy()93 void GetProxy()
94 {
95     HDF_LOGI("%{public}s start", __func__);
96     sptr<ISystemAbilityManager> samgr = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
97     if (!samgr) {
98         HDF_LOGE("%{public}s: error: no samgr", __func__);
99         return;
100     }
101 
102     sptr<IRemoteObject> hostRemote = samgr->GetSystemAbility(BLUETOOTH_HOST_SYS_ABILITY_ID);
103     if (!hostRemote) {
104         HDF_LOGE("%{public}s: failed: no hostRemote", __func__);
105         return;
106     }
107 
108     sptr<IBluetoothHost> hostProxy = iface_cast<IBluetoothHost>(hostRemote);
109     if (!hostProxy) {
110         HDF_LOGE("%{public}s: error: host no proxy", __func__);
111         return;
112     }
113 
114     sptr<IRemoteObject> remote = hostProxy->GetProfile("A2dpSrcServer");
115     if (!remote) {
116         HDF_LOGE("%{public}s: error: no remote", __func__);
117         return;
118     }
119 
120     g_proxy_ = iface_cast<IBluetoothA2dpSrc>(remote);
121     if (!g_proxy_) {
122         HDF_LOGE("%{public}s: error: no proxy", __func__);
123         return;
124     }
125 }
126 
RegisterObserver()127 void RegisterObserver()
128 {
129     HDF_LOGI("%{public}s", __func__);
130     g_btA2dpSrcObserverCallbacks = new (std::nothrow) BluetoothA2dpSrcObserver(&g_hdiCallbacks);
131     if (!g_btA2dpSrcObserverCallbacks) {
132         HDF_LOGE("%{public}s: g_btA2dpSrcObserverCallbacks is null", __func__);
133         return;
134     }
135     if (!g_proxy_) {
136         HDF_LOGE("%{public}s: g_proxy_ is null", __func__);
137         return;
138     }
139     g_proxy_->RegisterObserver(g_btA2dpSrcObserverCallbacks);
140 }
141 
DeRegisterObserver()142 void DeRegisterObserver()
143 {
144     HDF_LOGI("%{public}s", __func__);
145     if (!g_proxy_) {
146         HDF_LOGE("%{public}s: g_proxy_ is null", __func__);
147         return;
148     }
149     g_proxy_->DeregisterObserver(g_btA2dpSrcObserverCallbacks);
150 }
151 
152 #ifdef A2DP_HDI_SERVICE
InitAudioDeviceSoHandle(const char * path)153 static bool InitAudioDeviceSoHandle(const char* path)
154 {
155     if (path == NULL) {
156         HDF_LOGE("%{public}s: path is NULL", __func__);
157         return false;
158     }
159     char pathBuf[PATH_MAX] = {'\0'};
160     if (realpath(path, pathBuf) == NULL) {
161         return false;
162     }
163     if (g_ptrAudioDeviceHandle == NULL) {
164         g_ptrAudioDeviceHandle = dlopen(pathBuf, RTLD_LAZY);
165         if (g_ptrAudioDeviceHandle == NULL) {
166             HDF_LOGE("%{public}s: open lib so fail, reason:%{public}s ", __func__, dlerror());
167             return false;
168         }
169 
170         setUpFunc = (SetUpFunc)dlsym(g_ptrAudioDeviceHandle, "SetUp");
171         tearDownFunc = (TearDownFunc)dlsym(g_ptrAudioDeviceHandle, "TearDown");
172         getStateFunc = (GetStateFunc)dlsym(g_ptrAudioDeviceHandle, "GetState");
173         startPlayingFunc = (StartPlayingFunc)dlsym(g_ptrAudioDeviceHandle, "StartPlaying");
174         suspendPlayingFunc = (SuspendPlayingFunc)dlsym(g_ptrAudioDeviceHandle, "SuspendPlaying");
175         stopPlayingFunc = (StopPlayingFunc)dlsym(g_ptrAudioDeviceHandle, "StopPlaying");
176         writeFrameFunc = (WriteFrameFunc)dlsym(g_ptrAudioDeviceHandle, "WriteFrame");
177         if (setUpFunc == NULL || tearDownFunc == NULL || getStateFunc == NULL || startPlayingFunc == NULL ||
178             suspendPlayingFunc == NULL || stopPlayingFunc == NULL || writeFrameFunc == NULL) {
179                 HDF_LOGE("%{public}s: lib so func not found", __func__);
180                 return false;
181         }
182     }
183     return true;
184 }
185 
SetUp()186 bool SetUp()
187 {
188     bool ret = false;
189     ret = InitAudioDeviceSoHandle(g_bluetoothAudioDeviceSoPath);
190     if (ret == true) {
191         ret = setUpFunc();
192     }
193     if (ret == false) {
194         HDF_LOGE("%{public}s failed!", __func__);
195     }
196     return ret;
197 }
198 
TearDown()199 void TearDown()
200 {
201     tearDownFunc();
202 }
203 #endif
204 
205 
WriteFrame(const uint8_t * data,uint32_t size)206 int WriteFrame(const uint8_t *data, uint32_t size)
207 {
208     HDF_LOGI("%{public}s", __func__);
209 #ifdef A2DP_HDI_SERVICE
210     BTAudioStreamState state = getStateFunc();
211     if (state != BTAudioStreamState::STARTED) {
212         HDF_LOGE("%{public}s: state=%{public}hhu", __func__, state);
213         if (!startPlayingFunc()) {
214             HDF_LOGE("%{public}s: fail to startPlaying", __func__);
215             return HDF_FAILURE;
216         }
217     }
218     return writeFrameFunc(data, size);
219 #else
220     if (!g_proxy_) {
221         HDF_LOGE("%{public}s: g_proxy_ is null", __func__);
222         return RET_BAD_STATUS;
223     }
224     if (g_playState == A2DP_NOT_PLAYING) {
225         HDF_LOGE("%{public}s: playState is not Streaming", __func__);
226         return RET_BAD_STATUS;
227     }
228     return g_proxy_->WriteFrame(data, size);
229 #endif
230 }
231 
StartPlaying()232 int StartPlaying()
233 {
234     HDF_LOGI("%{public}s", __func__);
235 #ifdef A2DP_HDI_SERVICE
236     return HDF_SUCCESS;
237 #else
238     if (!g_proxy_) {
239         HDF_LOGE("%{public}s: g_proxy_ is null", __func__);
240         return RET_BAD_STATUS;
241     }
242     return g_proxy_->StartPlaying(g_proxy_->GetActiveSinkDevice());
243 #endif
244 }
245 
SuspendPlaying()246 int SuspendPlaying()
247 {
248     HDF_LOGI("%{public}s", __func__);
249 #ifdef A2DP_HDI_SERVICE
250     int retval = 0;
251     BTAudioStreamState state = getStateFunc();
252     HDF_LOGE("%{public}s: state=%{public}hhu", __func__, state);
253     if (state == BTAudioStreamState::STARTED) {
254         retval = (suspendPlayingFunc() ? HDF_SUCCESS : HDF_FAILURE);
255     } else {
256         HDF_LOGE("%{public}s: state=%{public}hhu is bad state", __func__, state);
257     }
258     return retval;
259 #else
260     if (!g_proxy_) {
261         HDF_LOGE("%{public}s: g_proxy_ is null", __func__);
262         return RET_BAD_STATUS;
263     }
264     return g_proxy_->SuspendPlaying(g_proxy_->GetActiveSinkDevice());
265 #endif
266 }
267 
StopPlaying()268 int StopPlaying()
269 {
270     HDF_LOGI("%{public}s", __func__);
271 #ifdef A2DP_HDI_SERVICE
272     BTAudioStreamState state = getStateFunc();
273     HDF_LOGE("%{public}s: state=%{public}hhu", __func__, state);
274     if (state != BTAudioStreamState::INVALID) {
275         stopPlayingFunc();
276     }
277     return HDF_SUCCESS;
278 #else
279     if (!g_proxy_) {
280         HDF_LOGE("%{public}s: g_proxy_ is null", __func__);
281         return RET_BAD_STATUS;
282     }
283     return g_proxy_->StopPlaying(g_proxy_->GetActiveSinkDevice());
284 #endif
285 }
286 }
287 }