1 /*
2  * Copyright (c) 2021-2023 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 #ifndef LOG_TAG
16 #define LOG_TAG "AudioBluetoothManager"
17 #endif
18 
19 #include "audio_bluetooth_manager.h"
20 #include "bluetooth_def.h"
21 #include "audio_errors.h"
22 #include "audio_common_log.h"
23 #include "bluetooth_audio_manager.h"
24 #include "bluetooth_device_manager.h"
25 #include "bluetooth_device_utils.h"
26 #include "bluetooth_hfp_ag.h"
27 
28 namespace OHOS {
29 namespace Bluetooth {
30 using namespace AudioStandard;
31 
32 A2dpSource *AudioA2dpManager::a2dpInstance_ = nullptr;
33 std::shared_ptr<AudioA2dpListener> AudioA2dpManager::a2dpListener_ = std::make_shared<AudioA2dpListener>();
34 int AudioA2dpManager::connectionState_ = static_cast<int>(BTConnectState::DISCONNECTED);
35 BluetoothRemoteDevice AudioA2dpManager::activeA2dpDevice_;
36 std::mutex g_a2dpInstanceLock;
37 HandsFreeAudioGateway *AudioHfpManager::hfpInstance_ = nullptr;
38 std::shared_ptr<AudioHfpListener> AudioHfpManager::hfpListener_ = std::make_shared<AudioHfpListener>();
39 AudioScene AudioHfpManager::scene_ = AUDIO_SCENE_DEFAULT;
40 AudioScene AudioHfpManager::sceneFromPolicy_ = AUDIO_SCENE_DEFAULT;
41 OHOS::Bluetooth::ScoCategory AudioHfpManager::scoCategory = OHOS::Bluetooth::ScoCategory::SCO_DEFAULT;
42 OHOS::Bluetooth::RecognitionStatus AudioHfpManager::recognitionStatus =
43     OHOS::Bluetooth::RecognitionStatus::RECOGNITION_DISCONNECTED;
44 BluetoothRemoteDevice AudioHfpManager::activeHfpDevice_;
45 std::vector<std::shared_ptr<AudioA2dpPlayingStateChangedListener>> AudioA2dpManager::a2dpPlayingStateChangedListeners_;
46 std::mutex g_activehfpDeviceLock;
47 std::mutex g_audioSceneLock;
48 std::mutex g_hfpInstanceLock;
49 std::mutex g_a2dpPlayingStateChangedLock;
50 
GetAudioStreamInfo(A2dpCodecInfo codecInfo,AudioStreamInfo & audioStreamInfo)51 static bool GetAudioStreamInfo(A2dpCodecInfo codecInfo, AudioStreamInfo &audioStreamInfo)
52 {
53     AUDIO_DEBUG_LOG("codec info rate[%{public}d]  format[%{public}d]  channel[%{public}d]",
54         codecInfo.sampleRate, codecInfo.bitsPerSample, codecInfo.channelMode);
55     switch (codecInfo.sampleRate) {
56         case A2DP_SBC_SAMPLE_RATE_48000_USER:
57         case A2DP_L2HCV2_SAMPLE_RATE_48000_USER:
58             audioStreamInfo.samplingRate = SAMPLE_RATE_48000;
59             break;
60         case A2DP_SBC_SAMPLE_RATE_44100_USER:
61             audioStreamInfo.samplingRate = SAMPLE_RATE_44100;
62             break;
63         case A2DP_SBC_SAMPLE_RATE_32000_USER:
64             audioStreamInfo.samplingRate = SAMPLE_RATE_32000;
65             break;
66         case A2DP_SBC_SAMPLE_RATE_16000_USER:
67             audioStreamInfo.samplingRate = SAMPLE_RATE_16000;
68             break;
69         case A2DP_L2HCV2_SAMPLE_RATE_96000_USER:
70             audioStreamInfo.samplingRate = SAMPLE_RATE_96000;
71             break;
72         default:
73             return false;
74     }
75     switch (codecInfo.bitsPerSample) {
76         case A2DP_SAMPLE_BITS_16_USER:
77             audioStreamInfo.format = SAMPLE_S16LE;
78             break;
79         case A2DP_SAMPLE_BITS_24_USER:
80             audioStreamInfo.format = SAMPLE_S24LE;
81             break;
82         case A2DP_SAMPLE_BITS_32_USER:
83             audioStreamInfo.format = SAMPLE_S32LE;
84             break;
85         default:
86             return false;
87     }
88     switch (codecInfo.channelMode) {
89         case A2DP_SBC_CHANNEL_MODE_STEREO_USER:
90             audioStreamInfo.channels = STEREO;
91             break;
92         case A2DP_SBC_CHANNEL_MODE_MONO_USER:
93             audioStreamInfo.channels = MONO;
94             break;
95         default:
96             return false;
97     }
98     audioStreamInfo.encoding = ENCODING_PCM;
99     return true;
100 }
101 
102 // LCOV_EXCL_START
RegisterBluetoothA2dpListener()103 void AudioA2dpManager::RegisterBluetoothA2dpListener()
104 {
105     AUDIO_INFO_LOG("AudioA2dpManager::RegisterBluetoothA2dpListener");
106     std::lock_guard<std::mutex> a2dpLock(g_a2dpInstanceLock);
107     a2dpInstance_ = A2dpSource::GetProfile();
108     CHECK_AND_RETURN_LOG(a2dpInstance_ != nullptr, "Failed to obtain A2DP profile instance");
109     a2dpInstance_->RegisterObserver(a2dpListener_);
110 }
111 
UnregisterBluetoothA2dpListener()112 void AudioA2dpManager::UnregisterBluetoothA2dpListener()
113 {
114     AUDIO_INFO_LOG("AudioA2dpManager::UnregisterBluetoothA2dpListener");
115     std::lock_guard<std::mutex> a2dpLock(g_a2dpInstanceLock);
116     CHECK_AND_RETURN_LOG(a2dpInstance_ != nullptr, "A2DP profile instance unavailable");
117     a2dpInstance_->DeregisterObserver(a2dpListener_);
118     a2dpInstance_ = nullptr;
119 }
120 
DisconnectBluetoothA2dpSink()121 void AudioA2dpManager::DisconnectBluetoothA2dpSink()
122 {
123     int connectionState = static_cast<int>(BTConnectState::DISCONNECTED);
124     auto a2dpList = MediaBluetoothDeviceManager::GetAllA2dpBluetoothDevice();
125     for (const auto &device : a2dpList) {
126         a2dpListener_->OnConnectionStateChanged(device, connectionState,
127             static_cast<uint32_t>(ConnChangeCause::CONNECT_CHANGE_COMMON_CAUSE));
128     }
129 
130     auto virtualDevices = MediaBluetoothDeviceManager::GetA2dpVirtualDeviceList();
131     for (const auto &virtualDevice : virtualDevices) {
132         a2dpListener_->OnVirtualDeviceChanged(static_cast<int32_t>(Bluetooth::BT_VIRTUAL_DEVICE_REMOVE),
133             virtualDevice.GetDeviceAddr());
134     }
135 
136     MediaBluetoothDeviceManager::ClearAllA2dpBluetoothDevice();
137 }
138 
SetActiveA2dpDevice(const std::string & macAddress)139 int32_t AudioA2dpManager::SetActiveA2dpDevice(const std::string& macAddress)
140 {
141     std::lock_guard<std::mutex> a2dpLock(g_a2dpInstanceLock);
142     AUDIO_WARNING_LOG("incoming device:%{public}s, current device:%{public}s",
143         GetEncryptAddr(macAddress).c_str(), GetEncryptAddr(activeA2dpDevice_.GetDeviceAddr()).c_str());
144     a2dpInstance_ = A2dpSource::GetProfile();
145     CHECK_AND_RETURN_RET_LOG(a2dpInstance_ != nullptr, ERROR, "Failed to obtain A2DP profile instance");
146     BluetoothRemoteDevice device;
147     if (macAddress != "") {
148         int32_t tmp = MediaBluetoothDeviceManager::GetConnectedA2dpBluetoothDevice(macAddress, device);
149         CHECK_AND_RETURN_RET_LOG(tmp == SUCCESS, ERROR, "the configuring A2DP device doesn't exist.");
150     } else {
151         AUDIO_INFO_LOG("Deactive A2DP device");
152     }
153     int32_t ret = a2dpInstance_->SetActiveSinkDevice(device);
154     CHECK_AND_RETURN_RET_LOG(ret == 0, ERROR, "SetActiveA2dpDevice failed. result: %{public}d", ret);
155     activeA2dpDevice_ = device;
156     return SUCCESS;
157 }
158 
GetActiveA2dpDevice()159 std::string AudioA2dpManager::GetActiveA2dpDevice()
160 {
161     std::lock_guard<std::mutex> a2dpLock(g_a2dpInstanceLock);
162     a2dpInstance_ = A2dpSource::GetProfile();
163     CHECK_AND_RETURN_RET_LOG(a2dpInstance_ != nullptr, "", "Failed to obtain A2DP profile instance");
164     BluetoothRemoteDevice device = a2dpInstance_->GetActiveSinkDevice();
165     return device.GetDeviceAddr();
166 }
167 
SetDeviceAbsVolume(const std::string & macAddress,int32_t volume)168 int32_t AudioA2dpManager::SetDeviceAbsVolume(const std::string& macAddress, int32_t volume)
169 {
170     BluetoothRemoteDevice device;
171     int32_t ret = MediaBluetoothDeviceManager::GetConnectedA2dpBluetoothDevice(macAddress, device);
172     CHECK_AND_RETURN_RET_LOG(ret == SUCCESS, ERROR, "SetDeviceAbsVolume: the configuring A2DP device doesn't exist.");
173     return AvrcpTarget::GetProfile()->SetDeviceAbsoluteVolume(device, volume);
174 }
175 
GetA2dpDeviceStreamInfo(const std::string & macAddress,AudioStreamInfo & streamInfo)176 int32_t AudioA2dpManager::GetA2dpDeviceStreamInfo(const std::string& macAddress,
177     AudioStreamInfo &streamInfo)
178 {
179     std::lock_guard<std::mutex> a2dpLock(g_a2dpInstanceLock);
180     a2dpInstance_ = A2dpSource::GetProfile();
181     CHECK_AND_RETURN_RET_LOG(a2dpInstance_ != nullptr, ERROR, "Failed to obtain A2DP profile instance");
182     BluetoothRemoteDevice device;
183     int32_t ret = MediaBluetoothDeviceManager::GetConnectedA2dpBluetoothDevice(macAddress, device);
184     CHECK_AND_RETURN_RET_LOG(ret == SUCCESS, ERROR,
185         "GetA2dpDeviceStreamInfo: the configuring A2DP device doesn't exist.");
186     A2dpCodecStatus codecStatus = a2dpInstance_->GetCodecStatus(device);
187     bool result = GetAudioStreamInfo(codecStatus.codecInfo, streamInfo);
188     CHECK_AND_RETURN_RET_LOG(result, ERROR, "GetA2dpDeviceStreamInfo: Unsupported a2dp codec info");
189     return SUCCESS;
190 }
191 
HasA2dpDeviceConnected()192 bool AudioA2dpManager::HasA2dpDeviceConnected()
193 {
194     a2dpInstance_ = A2dpSource::GetProfile();
195     CHECK_AND_RETURN_RET(a2dpInstance_, false);
196     std::vector<int32_t> states {static_cast<int32_t>(BTConnectState::CONNECTED)};
197     std::vector<BluetoothRemoteDevice> devices;
198     a2dpInstance_->GetDevicesByStates(states, devices);
199 
200     return !devices.empty();
201 }
202 
A2dpOffloadSessionRequest(const std::vector<A2dpStreamInfo> & info)203 int32_t AudioA2dpManager::A2dpOffloadSessionRequest(const std::vector<A2dpStreamInfo> &info)
204 {
205     CHECK_AND_RETURN_RET_LOG(activeA2dpDevice_.GetDeviceAddr() != "00:00:00:00:00:00", A2DP_NOT_OFFLOAD,
206         "Invalid mac address, not request, return A2DP_NOT_OFFLOAD.");
207     int32_t ret = a2dpInstance_->A2dpOffloadSessionRequest(activeA2dpDevice_, info);
208     AUDIO_DEBUG_LOG("Request %{public}zu stream and return a2dp offload state %{public}d", info.size(), ret);
209     return ret;
210 }
211 
OffloadStartPlaying(const std::vector<int32_t> & sessionsID)212 int32_t AudioA2dpManager::OffloadStartPlaying(const std::vector<int32_t> &sessionsID)
213 {
214     CHECK_AND_RETURN_RET_LOG(activeA2dpDevice_.GetDeviceAddr() != "00:00:00:00:00:00", ERROR,
215         "Invalid mac address, not start, return error.");
216     AUDIO_DEBUG_LOG("Start playing %{public}zu stream", sessionsID.size());
217     return a2dpInstance_->OffloadStartPlaying(activeA2dpDevice_, sessionsID);
218 }
219 
OffloadStopPlaying(const std::vector<int32_t> & sessionsID)220 int32_t AudioA2dpManager::OffloadStopPlaying(const std::vector<int32_t> &sessionsID)
221 {
222     if (activeA2dpDevice_.GetDeviceAddr() == "00:00:00:00:00:00") {
223         AUDIO_DEBUG_LOG("Invalid mac address, not stop, return error.");
224         return ERROR;
225     }
226     AUDIO_DEBUG_LOG("Stop playing %{public}zu stream", sessionsID.size());
227     return a2dpInstance_->OffloadStopPlaying(activeA2dpDevice_, sessionsID);
228 }
229 
GetRenderPosition(uint32_t & delayValue,uint64_t & sendDataSize,uint32_t & timeStamp)230 int32_t AudioA2dpManager::GetRenderPosition(uint32_t &delayValue, uint64_t &sendDataSize, uint32_t &timeStamp)
231 {
232     if (activeA2dpDevice_.GetDeviceAddr() == "00:00:00:00:00:00") {
233         AUDIO_DEBUG_LOG("Invalid mac address, return error.");
234         return ERROR;
235     }
236     return ERROR;
237     // a2dpInstance_->GetRenderPosition(activeA2dpDevice_, delayValue, sendDataSize, timeStamp);
238 }
239 
RegisterA2dpPlayingStateChangedListener(std::shared_ptr<AudioA2dpPlayingStateChangedListener> listener)240 int32_t AudioA2dpManager::RegisterA2dpPlayingStateChangedListener(
241     std::shared_ptr<AudioA2dpPlayingStateChangedListener> listener)
242 {
243     std::lock_guard<std::mutex> lock(g_a2dpPlayingStateChangedLock);
244     a2dpPlayingStateChangedListeners_.push_back(listener);
245     return SUCCESS;
246 }
247 
OnA2dpPlayingStateChanged(const std::string & deviceAddress,int32_t playingState)248 void AudioA2dpManager::OnA2dpPlayingStateChanged(const std::string &deviceAddress, int32_t playingState)
249 {
250     std::lock_guard<std::mutex> lock(g_a2dpPlayingStateChangedLock);
251     for (auto listener : a2dpPlayingStateChangedListeners_) {
252         listener->OnA2dpPlayingStateChanged(deviceAddress, playingState);
253     }
254 }
255 
CheckA2dpDeviceReconnect()256 void AudioA2dpManager::CheckA2dpDeviceReconnect()
257 {
258     if (a2dpInstance_ == nullptr) {
259         a2dpInstance_ = A2dpSource::GetProfile();
260     }
261     CHECK_AND_RETURN_LOG(a2dpInstance_ != nullptr, "A2DP profile instance unavailable");
262     std::vector<int32_t> states {static_cast<int32_t>(BTConnectState::CONNECTED)};
263     std::vector<BluetoothRemoteDevice> devices;
264     a2dpInstance_->GetDevicesByStates(states, devices);
265 
266     for (auto &device : devices) {
267         a2dpListener_->OnConnectionStateChanged(device, static_cast<int32_t>(BTConnectState::CONNECTED),
268             static_cast<uint32_t>(ConnChangeCause::CONNECT_CHANGE_COMMON_CAUSE));
269 
270         int32_t wearState = 0; // 0 unwear state
271         if (IsBTWearDetectionEnable(device)) {
272             wearState = BluetoothAudioManager::GetInstance().IsDeviceWearing(device);
273             if (wearState == 1) MediaBluetoothDeviceManager::SetMediaStack(device, WEAR_ACTION); // 1 wear state
274         }
275         AUDIO_WARNING_LOG("reconnect a2dp device:%{public}s, wear state:%{public}d",
276             GetEncryptAddr(device.GetDeviceAddr()).c_str(), wearState);
277     }
278 
279     std::vector<std::string> virtualDevices;
280     a2dpInstance_->GetVirtualDeviceList(virtualDevices);
281     for (auto &macAddress : virtualDevices) {
282         AUDIO_WARNING_LOG("reconnect virtual a2dp device:%{public}s", GetEncryptAddr(macAddress).c_str());
283         a2dpListener_->OnVirtualDeviceChanged(static_cast<int32_t>(Bluetooth::BT_VIRTUAL_DEVICE_ADD), macAddress);
284     }
285 }
286 
Connect(const std::string & macAddress)287 int32_t AudioA2dpManager::Connect(const std::string &macAddress)
288 {
289     CHECK_AND_RETURN_RET_LOG(a2dpInstance_ != nullptr, ERROR, "A2DP profile instance unavailable");
290     BluetoothRemoteDevice virtualDevice = BluetoothRemoteDevice(macAddress);
291     if (MediaBluetoothDeviceManager::IsA2dpBluetoothDeviceConnecting(macAddress)) {
292         AUDIO_WARNING_LOG("A2dp device %{public}s is connecting, ignore connect request",
293             GetEncryptAddr(macAddress).c_str());
294         virtualDevice.SetVirtualAutoConnectType(CONN_REASON_MANUAL_VIRTUAL_CONNECT_PREEMPT_FLAG, 0);
295         return SUCCESS;
296     }
297     std::vector<std::string> virtualDevices;
298     a2dpInstance_->GetVirtualDeviceList(virtualDevices);
299     if (std::find(virtualDevices.begin(), virtualDevices.end(), macAddress) == virtualDevices.end()) {
300         AUDIO_WARNING_LOG("A2dp device %{public}s is not virtual device, ignore connect request",
301             GetEncryptAddr(macAddress).c_str());
302         return SUCCESS;
303     }
304     int32_t ret = a2dpInstance_->Connect(virtualDevice);
305     CHECK_AND_RETURN_RET_LOG(ret == 0, ERROR, "A2dp Connect Failed");
306     virtualDevice.SetVirtualAutoConnectType(CONN_REASON_MANUAL_VIRTUAL_CONNECT_PREEMPT_FLAG, 0);
307     return SUCCESS;
308 }
309 
OnConnectionStateChanged(const BluetoothRemoteDevice & device,int state,int cause)310 void AudioA2dpListener::OnConnectionStateChanged(const BluetoothRemoteDevice &device, int state, int cause)
311 {
312     AUDIO_WARNING_LOG("state: %{public}d, macAddress: %{public}s", state,
313         GetEncryptAddr(device.GetDeviceAddr()).c_str());
314     // Record connection state and device for hdi start time to check
315     AudioA2dpManager::SetConnectionState(state);
316     if (state == static_cast<int>(BTConnectState::CONNECTING)) {
317         MediaBluetoothDeviceManager::SetMediaStack(device, BluetoothDeviceAction::CONNECTING_ACTION);
318     }
319     if (state == static_cast<int>(BTConnectState::CONNECTED)) {
320         MediaBluetoothDeviceManager::SetMediaStack(device, BluetoothDeviceAction::CONNECT_ACTION);
321     }
322     if (state == static_cast<int>(BTConnectState::DISCONNECTED)) {
323         MediaBluetoothDeviceManager::SetMediaStack(device, BluetoothDeviceAction::DISCONNECT_ACTION);
324     }
325 }
326 
OnConfigurationChanged(const BluetoothRemoteDevice & device,const A2dpCodecInfo & codecInfo,int error)327 void AudioA2dpListener::OnConfigurationChanged(const BluetoothRemoteDevice &device, const A2dpCodecInfo &codecInfo,
328     int error)
329 {
330     AUDIO_INFO_LOG("OnConfigurationChanged: sampleRate: %{public}d, channels: %{public}d, format: %{public}d",
331         codecInfo.sampleRate, codecInfo.channelMode, codecInfo.bitsPerSample);
332     AudioStreamInfo streamInfo = {};
333     bool result = GetAudioStreamInfo(codecInfo, streamInfo);
334     CHECK_AND_RETURN_LOG(result, "OnConfigurationChanged: Unsupported a2dp codec info");
335     MediaBluetoothDeviceManager::UpdateA2dpDeviceConfiguration(device, streamInfo);
336 }
337 
OnPlayingStatusChanged(const BluetoothRemoteDevice & device,int playingState,int error)338 void AudioA2dpListener::OnPlayingStatusChanged(const BluetoothRemoteDevice &device, int playingState, int error)
339 {
340     AUDIO_INFO_LOG("OnPlayingStatusChanged, state: %{public}d, error: %{public}d", playingState, error);
341     if (error == SUCCESS) {
342         AudioA2dpManager::OnA2dpPlayingStateChanged(device.GetDeviceAddr(), playingState);
343     }
344 }
345 
OnMediaStackChanged(const BluetoothRemoteDevice & device,int action)346 void AudioA2dpListener::OnMediaStackChanged(const BluetoothRemoteDevice &device, int action)
347 {
348     AUDIO_INFO_LOG("OnMediaStackChanged, action: %{public}d", action);
349     MediaBluetoothDeviceManager::SetMediaStack(device, action);
350 }
351 
OnVirtualDeviceChanged(int32_t action,std::string address)352 void AudioA2dpListener::OnVirtualDeviceChanged(int32_t action, std::string address)
353 {
354     AUDIO_WARNING_LOG("action: %{public}d, macAddress: %{public}s", action,
355         GetEncryptAddr(address).c_str());
356     if (action == static_cast<int32_t>(Bluetooth::BT_VIRTUAL_DEVICE_ADD)) {
357         MediaBluetoothDeviceManager::SetMediaStack(BluetoothRemoteDevice(address),
358             BluetoothDeviceAction::VIRTUAL_DEVICE_ADD_ACTION);
359     }
360     if (action == static_cast<int32_t>(Bluetooth::BT_VIRTUAL_DEVICE_REMOVE)) {
361         MediaBluetoothDeviceManager::SetMediaStack(BluetoothRemoteDevice(address),
362             BluetoothDeviceAction::VIRTUAL_DEVICE_REMOVE_ACTION);
363     }
364 }
365 
RegisterBluetoothScoListener()366 void AudioHfpManager::RegisterBluetoothScoListener()
367 {
368     AUDIO_INFO_LOG("AudioHfpManager::RegisterBluetoothScoListener");
369     std::lock_guard<std::mutex> hfpLock(g_hfpInstanceLock);
370     hfpInstance_ = HandsFreeAudioGateway::GetProfile();
371     CHECK_AND_RETURN_LOG(hfpInstance_ != nullptr, "Failed to obtain HFP AG profile instance");
372 
373     hfpInstance_->RegisterObserver(hfpListener_);
374 }
375 
UnregisterBluetoothScoListener()376 void AudioHfpManager::UnregisterBluetoothScoListener()
377 {
378     AUDIO_INFO_LOG("AudioHfpManager::UnregisterBluetoothScoListene");
379     std::lock_guard<std::mutex> hfpLock(g_hfpInstanceLock);
380     CHECK_AND_RETURN_LOG(hfpInstance_ != nullptr, "HFP AG profile instance unavailable");
381 
382     hfpInstance_->DeregisterObserver(hfpListener_);
383     hfpInstance_ = nullptr;
384 }
385 
CheckHfpDeviceReconnect()386 void AudioHfpManager::CheckHfpDeviceReconnect()
387 {
388     if (hfpInstance_ == nullptr) {
389         hfpInstance_ = HandsFreeAudioGateway::GetProfile();
390     }
391     CHECK_AND_RETURN_LOG(hfpInstance_ != nullptr, "HFP profile instance unavailable");
392     std::vector<int32_t> states {static_cast<int32_t>(BTConnectState::CONNECTED)};
393     std::vector<BluetoothRemoteDevice> devices = hfpInstance_->GetDevicesByStates(states);
394     for (auto &device : devices) {
395         hfpListener_->OnConnectionStateChanged(device, static_cast<int32_t>(BTConnectState::CONNECTED),
396             static_cast<uint32_t>(ConnChangeCause::CONNECT_CHANGE_COMMON_CAUSE));
397 
398         int32_t wearState = 0; // 0 unwear state
399         if (IsBTWearDetectionEnable(device)) {
400             wearState = BluetoothAudioManager::GetInstance().IsDeviceWearing(device);
401             if (wearState == 1) HfpBluetoothDeviceManager::SetHfpStack(device, WEAR_ACTION); // 1 wear state
402         }
403         AUDIO_INFO_LOG("reconnect hfp device:%{public}s, wear state:%{public}d",
404             GetEncryptAddr(device.GetDeviceAddr()).c_str(), wearState);
405     }
406 
407     std::vector<std::string> virtualDevices;
408     hfpInstance_->GetVirtualDeviceList(virtualDevices);
409     for (auto &macAddress : virtualDevices) {
410         AUDIO_PRERELEASE_LOGI("reconnect virtual hfp device:%{public}s", GetEncryptAddr(macAddress).c_str());
411         hfpListener_->OnVirtualDeviceChanged(static_cast<int32_t>(Bluetooth::BT_VIRTUAL_DEVICE_ADD), macAddress);
412     }
413 }
414 
HandleScoWithRecongnition(bool handleFlag,BluetoothRemoteDevice & device)415 int32_t AudioHfpManager::HandleScoWithRecongnition(bool handleFlag, BluetoothRemoteDevice &device)
416 {
417     CHECK_AND_RETURN_RET_LOG(hfpInstance_ != nullptr, ERROR, "HFP AG profile instance unavailable");
418     bool ret = true;
419     if (handleFlag) {
420         int8_t scoCategory = GetScoCategoryFromScene(scene_);
421         if (scoCategory == ScoCategory::SCO_DEFAULT &&
422             AudioHfpManager::scoCategory != ScoCategory::SCO_RECOGNITION) {
423             AUDIO_INFO_LOG("Recongnition sco connect");
424             AudioHfpManager::recognitionStatus = RecognitionStatus::RECOGNITION_CONNECTING;
425             ret = hfpInstance_->OpenVoiceRecognition(device);
426             if (ret) {
427                 AudioHfpManager::scoCategory = ScoCategory::SCO_RECOGNITION;
428                 AudioHfpManager::recognitionStatus = RecognitionStatus::RECOGNITION_CONNECTED;
429             }
430         } else {
431             AUDIO_WARNING_LOG("Sco Connected OR Connecting, No Need to Create");
432         }
433     } else {
434         if (AudioHfpManager::scoCategory == ScoCategory::SCO_RECOGNITION) {
435             AUDIO_INFO_LOG("Recongnition sco close");
436             AudioHfpManager::recognitionStatus = RecognitionStatus::RECOGNITION_DISCONNECTING;
437             ret = hfpInstance_->CloseVoiceRecognition(device);
438             if (ret) {
439                 AudioHfpManager::scoCategory = ScoCategory::SCO_DEFAULT;
440                 AudioHfpManager::recognitionStatus = RecognitionStatus::RECOGNITION_DISCONNECTED;
441             }
442         }
443     }
444     CHECK_AND_RETURN_RET_LOG(ret == true, ERROR, "HandleScoWithRecongnition failed, result: %{public}d", ret);
445     return SUCCESS;
446 }
447 
ClearRecongnitionStatus()448 void AudioHfpManager::ClearRecongnitionStatus()
449 {
450     if (AudioHfpManager::scoCategory == ScoCategory::SCO_RECOGNITION) {
451         AudioHfpManager::scoCategory = ScoCategory::SCO_DEFAULT;
452         AudioHfpManager::recognitionStatus = RecognitionStatus::RECOGNITION_DISCONNECTED;
453     }
454 }
455 
GetScoCategory()456 ScoCategory AudioHfpManager::GetScoCategory()
457 {
458     return scoCategory;
459 }
460 
GetRecognitionStatus()461 RecognitionStatus AudioHfpManager::GetRecognitionStatus()
462 {
463     return recognitionStatus;
464 }
465 
SetActiveHfpDevice(const std::string & macAddress)466 int32_t AudioHfpManager::SetActiveHfpDevice(const std::string &macAddress)
467 {
468     BluetoothRemoteDevice device;
469     if (HfpBluetoothDeviceManager::GetConnectedHfpBluetoothDevice(macAddress, device) != SUCCESS) {
470         AUDIO_ERR_LOG("SetActiveHfpDevice failed for the HFP device %{public}s does not exist.",
471             GetEncryptAddr(macAddress).c_str());
472         return ERROR;
473     }
474     std::lock_guard<std::mutex> hfpDeviceLock(g_activehfpDeviceLock);
475     AUDIO_INFO_LOG("incoming device:%{public}s, current device:%{public}s",
476         GetEncryptAddr(macAddress).c_str(), GetEncryptAddr(activeHfpDevice_.GetDeviceAddr()).c_str());
477     if (macAddress != activeHfpDevice_.GetDeviceAddr()) {
478         AUDIO_WARNING_LOG("Active hfp device is changed, need to DisconnectSco for current activeHfpDevice.");
479         int32_t ret = DisconnectSco();
480         CHECK_AND_RETURN_RET_LOG(ret == 0, ERROR, "DisconnectSco failed, result: %{public}d", ret);
481     }
482     std::lock_guard<std::mutex> hfpLock(g_hfpInstanceLock);
483     CHECK_AND_RETURN_RET_LOG(hfpInstance_ != nullptr, ERROR, "HFP AG profile instance unavailable");
484     bool res = hfpInstance_->SetActiveDevice(device);
485     CHECK_AND_RETURN_RET_LOG(res == true, ERROR, "SetActiveHfpDevice failed, result: %{public}d", res);
486     activeHfpDevice_ = device;
487     return SUCCESS;
488 }
489 
GetActiveHfpDevice()490 std::string AudioHfpManager::GetActiveHfpDevice()
491 {
492     std::lock_guard<std::mutex> hfpLock(g_hfpInstanceLock);
493     CHECK_AND_RETURN_RET_LOG(hfpInstance_ != nullptr, "", "HFP AG profile instance unavailable");
494     BluetoothRemoteDevice device = hfpInstance_->GetActiveDevice();
495     return device.GetDeviceAddr();
496 }
497 
ConnectScoWithAudioScene(AudioScene scene)498 int32_t AudioHfpManager::ConnectScoWithAudioScene(AudioScene scene)
499 {
500     if (scoCategory == ScoCategory::SCO_RECOGNITION) {
501         AUDIO_WARNING_LOG("Recognition Sco Connected");
502         return SUCCESS;
503     }
504     std::lock_guard<std::mutex> sceneLock(g_audioSceneLock);
505     int8_t lastScoCategory = GetScoCategoryFromScene(scene_);
506     int8_t newScoCategory = GetScoCategoryFromScene(scene);
507     AUDIO_INFO_LOG("new sco category is %{public}d, last sco category is %{public}d", newScoCategory, lastScoCategory);
508 
509     if (lastScoCategory == newScoCategory) {
510         AUDIO_INFO_LOG("sco category %{public}d not change", newScoCategory);
511         return SUCCESS;
512     }
513     std::lock_guard<std::mutex> hfpLock(g_hfpInstanceLock);
514     CHECK_AND_RETURN_RET_LOG(hfpInstance_ != nullptr, ERROR, "HFP AG profile instance unavailable");
515     bool isInbardingEnabled = false;
516     hfpInstance_->IsInbandRingingEnabled(isInbardingEnabled);
517     if ((scene == AUDIO_SCENE_RINGING || scene == AUDIO_SCENE_VOICE_RINGING) && !isInbardingEnabled) {
518         AUDIO_WARNING_LOG("The inbarding switch is off, ignore the ring scene.");
519         return SUCCESS;
520     }
521     int32_t ret;
522     if (lastScoCategory != ScoCategory::SCO_DEFAULT) {
523         AUDIO_INFO_LOG("Entered to disConnectSco for last audioScene category.");
524         ret = hfpInstance_->DisconnectSco(static_cast<uint8_t>(lastScoCategory));
525         CHECK_AND_RETURN_RET_LOG(ret == 0, ERROR,
526             "ConnectScoWithAudioScene failed as the last SCO failed to be disconnected, result: %{public}d", ret);
527     }
528     if (newScoCategory != ScoCategory::SCO_DEFAULT) {
529         AUDIO_INFO_LOG("Entered to connectSco for new audioScene category.");
530         ret = hfpInstance_->ConnectSco(static_cast<uint8_t>(newScoCategory));
531         CHECK_AND_RETURN_RET_LOG(ret == 0, ERROR, "ConnectScoWithAudioScene failed, result: %{public}d", ret);
532     }
533     scene_ = scene;
534     return SUCCESS;
535 }
536 
DisconnectSco()537 int32_t AudioHfpManager::DisconnectSco()
538 {
539     std::lock_guard<std::mutex> sceneLock(g_audioSceneLock);
540     int8_t currentScoCategory = GetScoCategoryFromScene(scene_);
541     if (currentScoCategory == ScoCategory::SCO_DEFAULT) {
542         AUDIO_WARNING_LOG("Current sco category is DEFAULT, not need to disconnect sco.");
543         return SUCCESS;
544     }
545     AUDIO_INFO_LOG("current sco category %{public}d", currentScoCategory);
546 
547     std::lock_guard<std::mutex> hfpLock(g_hfpInstanceLock);
548     CHECK_AND_RETURN_RET_LOG(hfpInstance_ != nullptr, ERROR, "HFP AG profile instance unavailable");
549     int32_t ret = hfpInstance_->DisconnectSco(static_cast<uint8_t>(currentScoCategory));
550     CHECK_AND_RETURN_RET_LOG(ret == 0, ERROR, "DisconnectSco failed, result: %{public}d", ret);
551     scene_ = AUDIO_SCENE_DEFAULT;
552     return SUCCESS;
553 }
554 
GetScoCategoryFromScene(AudioScene scene)555 int8_t AudioHfpManager::GetScoCategoryFromScene(AudioScene scene)
556 {
557     switch (scene) {
558         case AUDIO_SCENE_VOICE_RINGING:
559         case AUDIO_SCENE_PHONE_CALL:
560             return ScoCategory::SCO_CALLULAR;
561         case AUDIO_SCENE_RINGING:
562         case AUDIO_SCENE_PHONE_CHAT:
563             return ScoCategory::SCO_VIRTUAL;
564         default:
565             return ScoCategory::SCO_DEFAULT;
566     }
567 }
568 
DisconnectBluetoothHfpSink()569 void AudioHfpManager::DisconnectBluetoothHfpSink()
570 {
571     int connectionState = static_cast<int>(BTConnectState::DISCONNECTED);
572     auto hfpList = HfpBluetoothDeviceManager::GetAllHfpBluetoothDevice();
573     for (const auto &device : hfpList) {
574         hfpListener_->OnConnectionStateChanged(device, connectionState,
575             static_cast<uint32_t>(ConnChangeCause::CONNECT_CHANGE_COMMON_CAUSE));
576     }
577 
578     auto virtualDevices = HfpBluetoothDeviceManager::GetHfpVirtualDeviceList();
579     for (const auto &virtualDevice : virtualDevices) {
580         hfpListener_->OnVirtualDeviceChanged(static_cast<int32_t>(Bluetooth::BT_VIRTUAL_DEVICE_REMOVE),
581             virtualDevice.GetDeviceAddr());
582     }
583     HfpBluetoothDeviceManager::ClearAllHfpBluetoothDevice();
584 }
585 
UpdateCurrentActiveHfpDevice(const BluetoothRemoteDevice & device)586 void AudioHfpManager::UpdateCurrentActiveHfpDevice(const BluetoothRemoteDevice &device)
587 {
588     std::lock_guard<std::mutex> hfpDeviceLock(g_activehfpDeviceLock);
589     activeHfpDevice_ = device;
590 }
591 
GetCurrentActiveHfpDevice()592 std::string AudioHfpManager::GetCurrentActiveHfpDevice()
593 {
594     std::lock_guard<std::mutex> hfpDeviceLock(g_activehfpDeviceLock);
595     return activeHfpDevice_.GetDeviceAddr();
596 }
597 
UpdateAudioScene(AudioScene scene)598 void AudioHfpManager::UpdateAudioScene(AudioScene scene)
599 {
600     std::lock_guard<std::mutex> sceneLock(g_audioSceneLock);
601     scene_ = scene;
602 }
603 
GetCurrentAudioScene()604 AudioStandard::AudioScene AudioHfpManager::GetCurrentAudioScene()
605 {
606     std::lock_guard<std::mutex> sceneLock(g_audioSceneLock);
607     return scene_;
608 }
609 
SetAudioSceneFromPolicy(AudioScene scene)610 void AudioHfpManager::SetAudioSceneFromPolicy(AudioScene scene)
611 {
612     sceneFromPolicy_ = scene;
613 }
614 
GetPolicyAudioScene()615 AudioStandard::AudioScene AudioHfpManager::GetPolicyAudioScene()
616 {
617     return sceneFromPolicy_;
618 }
619 
Connect(const std::string & macAddress)620 int32_t AudioHfpManager::Connect(const std::string &macAddress)
621 {
622     CHECK_AND_RETURN_RET_LOG(hfpInstance_ != nullptr, ERROR, "HFP AG profile instance unavailable");
623     BluetoothRemoteDevice virtualDevice = BluetoothRemoteDevice(macAddress);
624     if (HfpBluetoothDeviceManager::IsHfpBluetoothDeviceConnecting(macAddress)) {
625         AUDIO_WARNING_LOG("Hfp device %{public}s is connecting, ignore connect request",
626             GetEncryptAddr(macAddress).c_str());
627         virtualDevice.SetVirtualAutoConnectType(CONN_REASON_MANUAL_VIRTUAL_CONNECT_PREEMPT_FLAG, 0);
628         return SUCCESS;
629     }
630     std::vector<std::string> virtualDevices;
631     hfpInstance_->GetVirtualDeviceList(virtualDevices);
632     if (std::find(virtualDevices.begin(), virtualDevices.end(), macAddress) == virtualDevices.end()) {
633         AUDIO_WARNING_LOG("Hfp device %{public}s is not virtual device, ignore connect request",
634             GetEncryptAddr(macAddress).c_str());
635         return SUCCESS;
636     }
637     int32_t ret = hfpInstance_->Connect(virtualDevice);
638     CHECK_AND_RETURN_RET_LOG(ret == 0, ERROR, "Hfp Connect Failed");
639     virtualDevice.SetVirtualAutoConnectType(CONN_REASON_MANUAL_VIRTUAL_CONNECT_PREEMPT_FLAG, 0);
640     return SUCCESS;
641 }
642 
OnScoStateChanged(const BluetoothRemoteDevice & device,int state,int reason)643 void AudioHfpListener::OnScoStateChanged(const BluetoothRemoteDevice &device, int state, int reason)
644 {
645     AUDIO_WARNING_LOG("state:[%{public}d] reason:[%{public}d] device:[%{public}s]",
646         state, reason, GetEncryptAddr(device.GetDeviceAddr()).c_str());
647     // SCO_DISCONNECTED = 3, SCO_CONNECTING = 4, SCO_DISCONNECTING = 5, SCO_CONNECTED = 6
648     HfpScoConnectState scoState = static_cast<HfpScoConnectState>(state);
649     if (scoState == HfpScoConnectState::SCO_CONNECTED || scoState == HfpScoConnectState::SCO_DISCONNECTED) {
650         if (device.GetDeviceAddr() == AudioHfpManager::GetCurrentActiveHfpDevice() &&
651             scoState == HfpScoConnectState::SCO_DISCONNECTED) {
652             BluetoothRemoteDevice defaultDevice;
653             AudioHfpManager::UpdateCurrentActiveHfpDevice(defaultDevice);
654             AUDIO_WARNING_LOG("Sco disconnect, need set audio scene as default.");
655             AudioHfpManager::UpdateAudioScene(AUDIO_SCENE_DEFAULT);
656         } else if (scoState == HfpScoConnectState::SCO_CONNECTED && reason == HFP_AG_SCO_REMOTE_USER_SET_UP) {
657             AudioScene audioScene = AudioHfpManager::GetPolicyAudioScene();
658             if (audioScene != AudioHfpManager::GetCurrentAudioScene()) {
659                 AUDIO_WARNING_LOG("Sco connect by peripheral device, update scene_ %{public}d", audioScene);
660                 AudioHfpManager::UpdateAudioScene(audioScene);
661             }
662             AudioHfpManager::UpdateCurrentActiveHfpDevice(device);
663         }
664         bool isConnected = (scoState == HfpScoConnectState::SCO_CONNECTED) ? true : false;
665 
666         // VGS feature
667         bool isVgsSupported = false;
668         if (isConnected) {
669             HandsFreeAudioGateway *hfpInstance = HandsFreeAudioGateway::GetProfile();
670             CHECK_AND_RETURN_LOG(hfpInstance != nullptr, "Failed to obtain HFP AG profile instance");
671             hfpInstance->IsVgsSupported(device, isVgsSupported);
672         }
673         AUDIO_INFO_LOG("AudioHfpListener::OnScoStateChanged: isVgsSupported: [%{public}d]", isVgsSupported);
674         HfpBluetoothDeviceManager::OnScoStateChanged(device, isVgsSupported, reason);
675     }
676 }
677 
OnConnectionStateChanged(const BluetoothRemoteDevice & device,int state,int cause)678 void AudioHfpListener::OnConnectionStateChanged(const BluetoothRemoteDevice &device, int state, int cause)
679 {
680     AUDIO_WARNING_LOG("state: %{public}d device: %{public}s", state,
681         GetEncryptAddr(device.GetDeviceAddr()).c_str());
682     if (state == static_cast<int>(BTConnectState::CONNECTING)) {
683         HfpBluetoothDeviceManager::SetHfpStack(device, BluetoothDeviceAction::CONNECTING_ACTION);
684     }
685     if (state == static_cast<int>(BTConnectState::CONNECTED)) {
686         HfpBluetoothDeviceManager::SetHfpStack(device, BluetoothDeviceAction::CONNECT_ACTION);
687     }
688     if (state == static_cast<int>(BTConnectState::DISCONNECTED)) {
689         if (device.GetDeviceAddr() == AudioHfpManager::GetCurrentActiveHfpDevice()) {
690             BluetoothRemoteDevice defaultDevice;
691             AudioHfpManager::UpdateCurrentActiveHfpDevice(defaultDevice);
692             AUDIO_WARNING_LOG("Current active hfp device diconnect, need set audio scene as default.");
693             AudioHfpManager::UpdateAudioScene(AUDIO_SCENE_DEFAULT);
694         }
695         HfpBluetoothDeviceManager::SetHfpStack(device, BluetoothDeviceAction::DISCONNECT_ACTION);
696     }
697 }
698 
OnHfpStackChanged(const BluetoothRemoteDevice & device,int action)699 void AudioHfpListener::OnHfpStackChanged(const BluetoothRemoteDevice &device, int action)
700 {
701     AUDIO_WARNING_LOG("action: %{public}d device: %{public}s", action, GetEncryptAddr(device.GetDeviceAddr()).c_str());
702     HfpBluetoothDeviceManager::SetHfpStack(device, action);
703 }
704 
OnVirtualDeviceChanged(int32_t action,std::string macAddress)705 void AudioHfpListener::OnVirtualDeviceChanged(int32_t action, std::string macAddress)
706 {
707     AUDIO_WARNING_LOG("action: %{public}d device: %{public}s", action, GetEncryptAddr(macAddress).c_str());
708     if (action == static_cast<int32_t>(Bluetooth::BT_VIRTUAL_DEVICE_ADD)) {
709         HfpBluetoothDeviceManager::SetHfpStack(BluetoothRemoteDevice(macAddress),
710             BluetoothDeviceAction::VIRTUAL_DEVICE_ADD_ACTION);
711     }
712     if (action == static_cast<int32_t>(Bluetooth::BT_VIRTUAL_DEVICE_REMOVE)) {
713         HfpBluetoothDeviceManager::SetHfpStack(BluetoothRemoteDevice(macAddress),
714             BluetoothDeviceAction::VIRTUAL_DEVICE_REMOVE_ACTION);
715     }
716 }
717 // LCOV_EXCL_STOP
718 } // namespace Bluetooth
719 } // namespace OHOS
720