• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2024 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 "bt_connection_manager.h"
17 
18 #include "common_event_manager.h"
19 #include "common_event_support.h"
20 #include "external_deps_proxy.h"
21 #include "infc_service.h"
22 #include "loghelper.h"
23 #include "nfc_service.h"
24 
25 namespace OHOS {
26 namespace NFC {
27 namespace TAG {
28 const uint64_t BT_ENABLE_TIMEOUT = 3000; // ms
29 const uint64_t BT_PAIR_TIMEOUT = 10000; // ms
30 const uint64_t BT_CONNECT_TIMEOUT = 5000; // ms
31 const uint8_t PROFILE_MAX_SIZE = 21;
32 
33 enum BtConnAction {
34     ACTION_INIT = 1,
35     ACTION_DISCONNECT,
36     ACTION_CONNECT
37 };
38 
39 enum BtConnState {
40     STATE_WAITING_FOR_BT_ENABLE = 1,
41     STATE_INIT,
42     STATE_INIT_COMPLETE,
43     STATE_PAIRING,
44     STATE_PAIR_COMPLETE,
45     STATE_CONNECTING,
46     STATE_DISCONNECTING,
47     STATE_COMPLETE
48 };
49 
50 enum BtConnResult {
51     CONN_RES_WAITING = 1,
52     CONN_RES_CONNECTED,
53     CONN_RES_DISCONNECTED
54 };
55 
56 static Bluetooth::A2dpSource *g_a2dp;
57 static Bluetooth::HandsFreeAudioGateway *g_hfp;
58 static Bluetooth::HidHost *g_hid;
59 
60 Bluetooth::BluetoothRemoteDevice g_device;
61 std::shared_ptr<BtData> g_btData {};
62 
63 bool g_isStateObserverRegistered = false;
64 bool g_isDevObserverRegistered = false;
65 bool g_isA2dpSupported = false;
66 bool g_isHfpSupported = false;
67 
68 uint8_t g_a2dpConnState = 0;
69 uint8_t g_hfpConnState = 0;
70 uint8_t g_hidConnState = 0;
71 
72 uint8_t g_state = 0;
73 uint8_t g_action = 0;
74 
BtConnectionManager()75 BtConnectionManager::BtConnectionManager()
76 {
77 }
78 
GetInstance()79 BtConnectionManager& BtConnectionManager::GetInstance()
80 {
81     static BtConnectionManager instance;
82     return instance;
83 }
84 
Initialize(std::weak_ptr<NfcService> nfcService)85 void BtConnectionManager::Initialize(std::weak_ptr<NfcService> nfcService)
86 {
87     DebugLog("Init: isInitialized = %{public}d", isInitialized_);
88     if (isInitialized_) {
89         return;
90     }
91     nfcService_ = nfcService;
92     isInitialized_ = true;
93 }
94 
SendMsgToEvtHandler(NfcCommonEvent evt,int64_t delay)95 void BtConnectionManager::SendMsgToEvtHandler(NfcCommonEvent evt, int64_t delay)
96 {
97     if (nfcService_.expired()) {
98         ErrorLog("nfcService expired");
99         return;
100     }
101     if (nfcService_.lock()->eventHandler_ == nullptr) {
102         ErrorLog("event handler is null");
103         return;
104     }
105     DebugLog("SendMsgToEvtHandler: event:%{public}d, delay:%{public}ld", evt, delay);
106     nfcService_.lock()->eventHandler_->SendEvent(static_cast<uint32_t>(evt), delay);
107 }
108 
SendConnMsgToEvtHandler(NfcCommonEvent evt,const Bluetooth::BluetoothRemoteDevice & device,int32_t state,BtProfileType type)109 void BtConnectionManager::SendConnMsgToEvtHandler(NfcCommonEvent evt, const Bluetooth::BluetoothRemoteDevice &device,
110                                                   int32_t state, BtProfileType type)
111 {
112     if (nfcService_.expired()) {
113         ErrorLog("nfcService expired");
114         return;
115     }
116     if (nfcService_.lock()->eventHandler_ == nullptr) {
117         ErrorLog("event handler is null");
118         return;
119     }
120     std::shared_ptr<BtConnectionInfo> info = std::make_shared<BtConnectionInfo>();
121     info->macAddr_ = device.GetDeviceAddr();
122     info->state_ = state;
123     info->type_ = static_cast<uint8_t>(type);
124     DebugLog("SendConnMsgToEvtHandler: event:%{public}d", evt);
125     nfcService_.lock()->eventHandler_->SendEvent(static_cast<uint32_t>(evt), info, 0);
126 }
127 
RemoveMsgFromEvtHandler(NfcCommonEvent evt)128 void BtConnectionManager::RemoveMsgFromEvtHandler(NfcCommonEvent evt)
129 {
130     if (nfcService_.expired()) {
131         ErrorLog("nfcService expired");
132         return;
133     }
134     if (nfcService_.lock()->eventHandler_ == nullptr) {
135         ErrorLog("event handler is null");
136         return;
137     }
138     DebugLog("RemoveMsgFromEvtHandler: event:%{public}d", evt);
139     nfcService_.lock()->eventHandler_->RemoveEvent(static_cast<uint32_t>(evt), static_cast<int64_t>(0));
140 }
141 
RegisterBtObserver()142 void BtConnectionManager::RegisterBtObserver()
143 {
144     DebugLog("RegisterBtStateObserver");
145     if (btObserver_ == nullptr) {
146         btObserver_ = BtConnectionManager::BtStateObserver::GetInstance();
147     }
148     Bluetooth::BluetoothHost::GetDefaultHost().RegisterObserver(btObserver_);
149     g_isStateObserverRegistered = true;
150 }
151 
UnregisterBtObserverAndProfile()152 void BtConnectionManager::UnregisterBtObserverAndProfile()
153 {
154     DebugLog("UnregisterBtObserverAndProfile");
155     if (btObserver_ != nullptr && g_isStateObserverRegistered) {
156         Bluetooth::BluetoothHost::GetDefaultHost().DeregisterObserver(btObserver_);
157         btObserver_ = nullptr;
158         g_isStateObserverRegistered = false;
159         DebugLog("UnregisterBtObserverAndProfile: bt state observer deregistered");
160     }
161     if (btRemoteDevObserver_ != nullptr && g_isDevObserverRegistered) {
162         Bluetooth::BluetoothHost::GetDefaultHost().DeregisterRemoteDeviceObserver(btRemoteDevObserver_);
163         btRemoteDevObserver_ = nullptr;
164         g_isDevObserverRegistered = false;
165         DebugLog("UnregisterBtObserverAndProfile: bt remote device observer deregistered");
166     }
167     if (g_a2dp != nullptr) {
168         if (btA2dpObserver_) {
169             g_a2dp->DeregisterObserver(btA2dpObserver_);
170             btA2dpObserver_ = nullptr;
171             DebugLog("UnregisterBtObserverAndProfile: bt a2dp observer deregistered");
172         }
173         g_a2dp = nullptr;
174     }
175     if (g_hfp != nullptr) {
176         if (btHfpObserver_) {
177             g_hfp->DeregisterObserver(btHfpObserver_);
178             btHfpObserver_ = nullptr;
179             DebugLog("UnregisterBtObserverAndProfile: bt state observer deregistered");
180         }
181         g_hfp = nullptr;
182     }
183     if (g_hid != nullptr) {
184         if (btHidObserver_) {
185             g_hid->DeregisterObserver(btHidObserver_);
186             btHidObserver_ = nullptr;
187             DebugLog("UnregisterBtObserverAndProfile: bt state observer deregistered");
188         }
189         g_hid = nullptr;
190     }
191 }
192 
193 // lock outside
OnFinish()194 void BtConnectionManager::OnFinish()
195 {
196     DebugLog("OnFinish");
197     RemoveMsgFromEvtHandler(NfcCommonEvent::MSG_BT_ENABLE_TIMEOUT);
198     RemoveMsgFromEvtHandler(NfcCommonEvent::MSG_BT_PAIR_TIMEOUT);
199     RemoveMsgFromEvtHandler(NfcCommonEvent::MSG_BT_CONNECT_TIMEOUT);
200     UnregisterBtObserverAndProfile();
201     g_isStateObserverRegistered = false;
202     g_isDevObserverRegistered = false;
203     g_isA2dpSupported = false;
204     g_isHfpSupported = false;
205     g_a2dpConnState = 0;
206     g_hfpConnState = 0;
207     g_hidConnState = 0;
208     g_state = 0;
209     g_action = 0;
210     g_btData = nullptr;
211 }
212 
HandleBtEnableFailed()213 void BtConnectionManager::HandleBtEnableFailed()
214 {
215     std::unique_lock<std::shared_mutex> guard(mutex_);
216     ErrorLog("Bt Enable Failed");
217     OnFinish();
218 }
219 
HandleBtPairFailed()220 void BtConnectionManager::HandleBtPairFailed()
221 {
222     std::unique_lock<std::shared_mutex> guard(mutex_);
223     ErrorLog("Bt Pair Failed");
224     OnFinish();
225 }
226 
HandleBtConnectFailed()227 void BtConnectionManager::HandleBtConnectFailed()
228 {
229     std::unique_lock<std::shared_mutex> guard(mutex_);
230     ErrorLog("Bt Connect Failed");
231     OnFinish();
232 }
233 
IsBtEnabled()234 bool BtConnectionManager::IsBtEnabled()
235 {
236     bool isEnabled = Bluetooth::BluetoothHost::GetDefaultHost().IsBrEnabled();
237     InfoLog("IsBtEnabled: %{public}d", isEnabled);
238     return isEnabled;
239 }
240 
HandleEnableBt()241 bool BtConnectionManager::HandleEnableBt()
242 {
243     DebugLog("HandleEnableBt");
244     SendMsgToEvtHandler(NfcCommonEvent::MSG_BT_ENABLE_TIMEOUT, BT_ENABLE_TIMEOUT);
245     if (Bluetooth::BluetoothHost::GetDefaultHost().EnableBle() != Bluetooth::RET_NO_ERROR) { // EnableBt() is deprecated
246         ErrorLog("HandleEnableBt: failed");
247         return false;
248     }
249     return true;
250 }
251 
HandleBtPair()252 bool BtConnectionManager::HandleBtPair()
253 {
254     DebugLog("HandleBtPair");
255     bool isDiscovering = false;
256     Bluetooth::BluetoothHost::GetDefaultHost().IsBtDiscovering(isDiscovering, g_btData->transport_);
257     if (isDiscovering) {
258         InfoLog("Cancel discovery");
259         Bluetooth::BluetoothHost::GetDefaultHost().CancelBtDiscovery();
260     }
261     // oob pair mode currently not supported by bluetooth
262     if (btRemoteDevObserver_ == nullptr) {
263         btRemoteDevObserver_ = std::make_shared<BtRemoteDevObserver>();
264     }
265     Bluetooth::BluetoothHost::GetDefaultHost().RegisterRemoteDeviceObserver(btRemoteDevObserver_);
266     g_isDevObserverRegistered = true;
267 
268     InfoLog("Handle bt pair start");
269     g_device.StartCrediblePair();
270     SendMsgToEvtHandler(NfcCommonEvent::MSG_BT_PAIR_TIMEOUT, BT_PAIR_TIMEOUT);
271     return true;
272 }
273 
IsA2dpSupported()274 bool BtConnectionManager::IsA2dpSupported()
275 {
276     if (g_btData == nullptr) {
277         ErrorLog("IsA2dpSupported: g_btData error");
278         return false;
279     }
280     for (Bluetooth::UUID uuid : g_btData->uuids_) {
281         if ((uuid.ToString().compare(Bluetooth::BLUETOOTH_UUID_A2DP_SINK) == 0) ||
282             (uuid.ToString().compare(Bluetooth::BLUETOOTH_UUID_AVRCP_CT) == 0)) {
283             return true;
284         }
285     }
286     return g_btData->btClass_.IsProfileSupported(Bluetooth::PROFILE_ID_A2DP_SRC);
287 }
288 
IsHfpSupported()289 bool BtConnectionManager::IsHfpSupported()
290 {
291     if (g_btData == nullptr) {
292         ErrorLog("IsHfpSupported: g_btData error");
293         return false;
294     }
295     for (Bluetooth::UUID uuid : g_btData->uuids_) {
296         if ((uuid.ToString().compare(Bluetooth::BLUETOOTH_UUID_HFP_AG) == 0) ||
297             (uuid.ToString().compare(Bluetooth::BLUETOOTH_UUID_HFP_HF) == 0)) {
298             return true;
299         }
300     }
301     return g_btData->btClass_.IsProfileSupported(Bluetooth::PROFILE_ID_HFP_AG);
302 }
303 
304 // false to OnFinish()
HandleBtInit()305 bool BtConnectionManager::HandleBtInit()
306 {
307     if (g_btData == nullptr) {
308         ErrorLog("HandleBtInit: g_btData error");
309         return false;
310     }
311     if (g_device.GetDeviceAddr().compare(g_btData->macAddress_) != 0) {
312         g_device = Bluetooth::BluetoothRemoteDevice(g_btData->macAddress_, g_btData->transport_);
313     }
314     if (g_btData->transport_ == Bluetooth::GATT_TRANSPORT_TYPE_LE) {
315         InfoLog("Init: hid getprofile");
316         if (g_hid == nullptr) {
317             g_hid = Bluetooth::HidHost::GetProfile();
318         }
319     } else {
320         if (g_a2dp == nullptr) {
321             g_a2dp = Bluetooth::A2dpSource::GetProfile();
322         }
323         if (g_hfp == nullptr) {
324             g_hfp = Bluetooth::HandsFreeAudioGateway::GetProfile();
325         }
326         g_isA2dpSupported = IsA2dpSupported();
327         g_isHfpSupported = IsHfpSupported();
328         InfoLog("Init:a2dp: %{public}d, hfp: %{public}d", g_isA2dpSupported, g_isHfpSupported);
329         if (!g_isA2dpSupported && !g_isHfpSupported) {
330             // if both not supported, maybe the info is empty in ndef
331             // try both
332             g_isA2dpSupported = true;
333             g_isHfpSupported = true;
334             InfoLog("Init:a2dp and hid not supported");
335         }
336     }
337     return true;
338 }
339 
340 // false to OnFinish()
DecideInitNextAction()341 bool BtConnectionManager::DecideInitNextAction()
342 {
343     if (g_btData == nullptr) {
344         ErrorLog("HandleBtInit: g_btData error");
345         return false;
346     }
347     int32_t state = 0;
348     if (g_btData->transport_ == Bluetooth::GATT_TRANSPORT_TYPE_LE) {
349         if (!g_hid) {
350             ErrorLog("DecideInitNextAction: hid not supported");
351             return false;
352         }
353         g_hid->GetDeviceState(g_device, state);
354         InfoLog("DecideInitNextAction: hid device state: %{public}d", state);
355         if (state == static_cast<int32_t>(Bluetooth::BTConnectState::CONNECTED)) {
356             g_action = ACTION_DISCONNECT;
357         } else {
358             g_action = ACTION_CONNECT;
359         }
360     } else {
361         if (g_a2dp && g_isA2dpSupported) {
362             g_a2dp->GetDeviceState(g_device, state);
363         }
364 
365         InfoLog("DecideInitNextAction: a2dp device state: %{public}d", state);
366         if (state == static_cast<int32_t>(Bluetooth::BTConnectState::CONNECTED)) {
367             g_action = ACTION_DISCONNECT;
368         } else {
369             // unconnected a2dp and all hfp go to connect action
370             g_action = ACTION_CONNECT;
371         }
372     }
373     return true;
374 }
375 
GetProfileList()376 bool BtConnectionManager::GetProfileList()
377 {
378     std::vector<uint32_t> profileList = Bluetooth::BluetoothHost::GetDefaultHost().GetProfileList();
379     if (profileList.size() == 0 && profileList.size() > PROFILE_MAX_SIZE) {
380         ErrorLog("profile list size error");
381         return false;
382     }
383     for (uint32_t i = 0; i < profileList.size(); i++) {
384         if (g_btData->transport_ == Bluetooth::GATT_TRANSPORT_TYPE_LE &&
385             profileList[i] == Bluetooth::PROFILE_ID_HID_HOST) {
386             InfoLog("PROFILE_ID_HID_HOST");
387             return true;
388         } else {
389             if (profileList[i] == Bluetooth::PROFILE_ID_A2DP_SRC ||
390                 profileList[i] == Bluetooth::PROFILE_ID_HFP_AG) {
391                 InfoLog("PROFILE_ID_A2DP_SRC OR PROFILE_ID_HFP_AG");
392                 return true;
393             }
394         }
395     }
396     return false;
397 }
398 
NextActionInit()399 void BtConnectionManager::NextActionInit()
400 {
401     InfoLog("NextActionInit: g_state: %{public}d", g_state);
402     if (g_state == STATE_WAITING_FOR_BT_ENABLE) {
403         return;
404     }
405     if (g_state == STATE_INIT) {
406         if (!GetProfileList()) {
407             ErrorLog("NextActionInit: GetProfileList error");
408             return OnFinish();
409         }
410         if (!HandleBtInit()) {
411             ErrorLog("NextActionInit: HandleBtInit error");
412             return OnFinish();
413         }
414         if (!DecideInitNextAction()) {
415             ErrorLog("NextActionInit: DecideInitNextAction error");
416             return OnFinish();
417         }
418         g_state = STATE_INIT_COMPLETE;
419     }
420     NextAction();
421 }
422 
RegisterProfileObserver(BtProfileType type)423 void BtConnectionManager::RegisterProfileObserver(BtProfileType type)
424 {
425     InfoLog("RegisterProfileObserver type: %{public}d", type);
426     switch (type) {
427         case A2DP_SRC: {
428             if (!g_a2dp || !g_isA2dpSupported) {
429                 ErrorLog("RegisterProfileObserver: a2dp error");
430                 break;
431             }
432             if (!btA2dpObserver_) {
433                 btA2dpObserver_ = std::make_shared<BtA2dpObserver>();
434                 g_a2dp->RegisterObserver(btA2dpObserver_);
435             }
436             break;
437         }
438         case HFP_AG: {
439             if (!g_hfp || !g_isHfpSupported) {
440                 ErrorLog("RegisterProfileObserver: hfp error");
441                 break;
442             }
443             if (!btHfpObserver_) {
444                 btHfpObserver_ = std::make_shared<BtHfpObserver>();
445                 g_hfp->RegisterObserver(btHfpObserver_);
446             }
447             break;
448         }
449         case HID_HOST: {
450             if (!g_hid) {
451                 ErrorLog("RegisterProfileObserver: hid error");
452                 break;
453             }
454             if (!btHidObserver_) {
455                 btHidObserver_ = std::make_shared<BtHidObserver>();
456                 g_hid->RegisterObserver(btHidObserver_);
457             }
458             break;
459         }
460         default:
461             break;
462     }
463 }
464 
465 // true for need wait, false for go to NextStep
HandleBtConnect()466 bool BtConnectionManager::HandleBtConnect()
467 {
468     DebugLog("HandleBtConnect");
469     int32_t state = 0;
470     if (g_hfp) {
471         g_hfp->GetDeviceState(g_device, state);
472         InfoLog("HandleBtConnect: hfp state = %{public}d", state);
473         if (state != static_cast<int32_t>(Bluetooth::BTConnectState::CONNECTED)) {
474             if (g_isHfpSupported) {
475                 g_hfpConnState = BtConnResult::CONN_RES_WAITING;
476                 RegisterProfileObserver(HFP_AG);
477                 InfoLog("HandleBtConnect: hfp connect start");
478                 g_hfp->Connect(g_device);
479             } else {
480                 g_hfpConnState = BtConnResult::CONN_RES_DISCONNECTED;
481                 InfoLog("HandleBtConnect: hfp disconnected");
482             }
483         } else {
484             g_hfpConnState = BtConnResult::CONN_RES_CONNECTED;
485             InfoLog("HandleBtConnect: hfp connected");
486         }
487     }
488     if (g_a2dp) {
489         g_a2dp->GetDeviceState(g_device, state);
490         InfoLog("HandleBtConnect: a2dp state = %{public}d", state);
491         if (state != static_cast<int32_t>(Bluetooth::BTConnectState::CONNECTED)) {
492             if (g_isA2dpSupported) {
493                 g_a2dpConnState = BtConnResult::CONN_RES_WAITING;
494                 RegisterProfileObserver(A2DP_SRC);
495                 InfoLog("HandleBtConnect: a2dp connect start");
496                 g_a2dp->Connect(g_device);
497             } else {
498                 g_a2dpConnState = BtConnResult::CONN_RES_DISCONNECTED;
499                 InfoLog("HandleBtConnect: a2dp disconnected");
500             }
501         } else {
502             g_a2dpConnState = BtConnResult::CONN_RES_CONNECTED;
503             InfoLog("HandleBtConnect: a2dp connected");
504         }
505     }
506     if (g_a2dpConnState == BtConnResult::CONN_RES_WAITING ||
507         g_hfpConnState == BtConnResult::CONN_RES_WAITING) {
508         InfoLog("HandleBtConnect: waiting for connect result");
509         SendMsgToEvtHandler(NfcCommonEvent::MSG_BT_CONNECT_TIMEOUT, BT_CONNECT_TIMEOUT);
510         return true;
511     }
512     return false;
513 }
514 
515 // true for need wait, false for go to OnFinish()
HandleBtConnectWaiting()516 bool BtConnectionManager::HandleBtConnectWaiting()
517 {
518     if (g_a2dpConnState == BtConnResult::CONN_RES_WAITING ||
519         g_hfpConnState == BtConnResult::CONN_RES_WAITING) {
520         InfoLog("HandleBtConnectWaiting: waiting for connect result");
521         return true;
522     }
523     if (g_a2dpConnState == BtConnResult::CONN_RES_CONNECTED ||
524         g_hfpConnState == BtConnResult::CONN_RES_CONNECTED) {
525         InfoLog("HandleBtConnectWaiting: connect success");
526         g_device.SetDeviceAlias(g_btData->name_);
527         return false;
528     } else {
529         // connect failed
530         return false;
531     }
532 }
533 
NextActionConnect()534 void BtConnectionManager::NextActionConnect()
535 {
536     int pairState = 0;
537     g_device.GetPairState(pairState);
538     InfoLog("NextActionConnect: state: %{public}d, pairState: %{public}d", g_state, pairState);
539     switch (g_state) {
540         case STATE_INIT_COMPLETE: {
541             if (pairState != Bluetooth::PAIR_PAIRED) {
542                 g_state = STATE_PAIRING;
543                 PublishPairBtNtf();
544                 break;
545             }
546             // fall-through
547             // when already paired
548         }
549         case STATE_PAIR_COMPLETE: {
550             g_state = STATE_CONNECTING;
551             if (g_btData->transport_ != Bluetooth::GATT_TRANSPORT_TYPE_LE) {
552                 if (HandleBtConnect()) {
553                     InfoLog("connecting, need wait");
554                     break;
555                 }
556             }
557             // fall-through
558             // when transport not LE or connect success
559         }
560         case STATE_CONNECTING: {
561             if (g_btData->transport_ != Bluetooth::GATT_TRANSPORT_TYPE_LE) {
562                 if (!HandleBtConnectWaiting()) {
563                     OnFinish();
564                 }
565             }
566             break;
567         }
568         default:
569             break;
570     }
571 }
572 
573 // true for need wait, false for go to NextStep
HandleBtDisconnect()574 bool BtConnectionManager::HandleBtDisconnect()
575 {
576     int32_t devState = 0;
577     if (g_btData->transport_ == Bluetooth::GATT_TRANSPORT_TYPE_LE) {
578         if (!g_hid) {
579             return false;
580         }
581         g_hid->GetDeviceState(g_device, devState);
582         if (devState != static_cast<int32_t>(Bluetooth::BTConnectState::DISCONNECTED)) {
583             g_hidConnState = BtConnResult::CONN_RES_WAITING;
584             RegisterProfileObserver(HID_HOST);
585             InfoLog("HandleBtDisconnect: hid disconnect start");
586             g_hid->Disconnect(g_device);
587             return true;
588         } else {
589             g_hidConnState = BtConnResult::CONN_RES_DISCONNECTED;
590             InfoLog("HandleBtDisconnect: hfp disconnect");
591         }
592     } else {
593         if (g_hfp && g_isHfpSupported) {
594             g_hfp->GetDeviceState(g_device, devState);
595             if (devState != static_cast<int32_t>(Bluetooth::BTConnectState::DISCONNECTED)) {
596                 g_hfpConnState = BtConnResult::CONN_RES_WAITING;
597                 RegisterProfileObserver(HFP_AG);
598                 InfoLog("HandleBtDisconnect: hfp disconnect start");
599             } else {
600                 g_hfpConnState = BtConnResult::CONN_RES_DISCONNECTED;
601                 InfoLog("HandleBtDisconnect: hfp disconnected");
602             }
603         }
604         if (g_a2dp && g_isA2dpSupported) {
605             g_a2dp->GetDeviceState(g_device, devState);
606             if (devState != static_cast<int32_t>(Bluetooth::BTConnectState::DISCONNECTED)) {
607                 g_a2dpConnState = BtConnResult::CONN_RES_WAITING;
608                 RegisterProfileObserver(A2DP_SRC);
609                 InfoLog("HandleBtDisconnect: a2dp disconnect start");
610             } else {
611                 g_a2dpConnState = BtConnResult::CONN_RES_DISCONNECTED;
612                 InfoLog("HandleBtDisconnect: a2dp disconnected");
613             }
614         }
615         if (g_a2dpConnState == BtConnResult::CONN_RES_WAITING ||
616             g_hfpConnState == BtConnResult::CONN_RES_WAITING) {
617             Bluetooth::BluetoothHost::GetDefaultHost().DisconnectAllowedProfiles(g_btData->macAddress_);
618             InfoLog("HandleBtDisconnect: waiting for disconnect result");
619             return true;
620         }
621     }
622     return false;
623 }
624 
625 // true for need wait, false for go to OnFinish()
HandleBtDisconnectWaiting()626 bool BtConnectionManager::HandleBtDisconnectWaiting()
627 {
628     if (g_btData->transport_ == Bluetooth::GATT_TRANSPORT_TYPE_LE) {
629         if (g_hidConnState == BtConnResult::CONN_RES_DISCONNECTED) {
630             InfoLog("HandleBtDisconnectWaiting:hid disconnected");
631             return false;
632         }
633     } else {
634         if (g_a2dpConnState == BtConnResult::CONN_RES_WAITING ||
635             g_hfpConnState == BtConnResult::CONN_RES_WAITING) {
636             InfoLog("HandleBtDisconnectWaiting: waiting for disconnect result");
637             return true;
638         }
639         if (g_a2dpConnState == BtConnResult::CONN_RES_DISCONNECTED &&
640             g_hfpConnState == BtConnResult::CONN_RES_DISCONNECTED) {
641             InfoLog("HandleBtDisconnectWaiting: disconnect success");
642             return false;
643         }
644     }
645     return false;
646 }
647 
NextActionDisconnect()648 void BtConnectionManager::NextActionDisconnect()
649 {
650     int pairState = 0;
651     g_device.GetPairState(pairState);
652     InfoLog("NextActionConnect: state: %{public}d, pairState: %{public}d", g_state, pairState);
653     switch (g_state) {
654         case STATE_INIT_COMPLETE: {
655             g_state = STATE_DISCONNECTING;
656             if (HandleBtDisconnect()) {
657                 InfoLog("NextActionConnect: disconnecting need wait");
658                 break;
659             }
660             // fall-through
661             // when already disconnected
662         }
663         case STATE_DISCONNECTING: {
664             if (!HandleBtDisconnectWaiting()) {
665                 OnFinish();
666             }
667             break;
668         }
669         default:
670             break;
671     }
672 }
673 
NextAction()674 void BtConnectionManager::NextAction()
675 {
676     InfoLog("NextAction: state: %{public}d action: %{public}d", g_state, g_action);
677     switch (g_action) {
678         case ACTION_INIT:
679             NextActionInit();
680             break;
681         case ACTION_CONNECT:
682             NextActionConnect();
683             break;
684         case ACTION_DISCONNECT:
685             NextActionDisconnect();
686             break;
687         default:
688             break;
689     }
690 }
691 
TryPairBt(std::shared_ptr<BtData> data)692 void BtConnectionManager::TryPairBt(std::shared_ptr<BtData> data)
693 {
694     std::unique_lock<std::shared_mutex> guard(mutex_);
695     if (!data || !data->isValid_) {
696         ErrorLog("TryPairBt: data error");
697         return;
698     }
699     RemoveMsgFromEvtHandler(NfcCommonEvent::MSG_BT_ENABLE_TIMEOUT);
700     RemoveMsgFromEvtHandler(NfcCommonEvent::MSG_BT_CONNECT_TIMEOUT);
701     g_btData = data;
702     g_action = ACTION_INIT;
703     RegisterBtObserver();
704     if (IsBtEnabled()) {
705         g_state = STATE_INIT;
706         NextAction();
707     } else {
708         g_state = STATE_WAITING_FOR_BT_ENABLE;
709         if (!HandleEnableBt()) {
710             ErrorLog("TryPairBt enable bt failed");
711             OnFinish();
712         }
713     }
714 }
715 
PublishPairBtNtf()716 void BtConnectionManager::PublishPairBtNtf()
717 {
718     RemoveMsgFromEvtHandler(NfcCommonEvent::MSG_BT_PAIR_TIMEOUT);
719     if (g_btData == nullptr) {
720         ErrorLog("PublishPairBtNtf: g_btData nullptr");
721         return;
722     }
723     InfoLog("PublishPairBtNtf: Publish notification name: %{private}s", g_btData->name_.c_str());
724     ExternalDepsProxy::GetInstance().PublishNfcNotification(NFC_BT_NOTIFICATION_ID, g_btData->name_, 0);
725 }
726 
OnBtNtfClicked()727 void BtConnectionManager::OnBtNtfClicked()
728 {
729     InfoLog("OnBtNtfClicked");
730     std::unique_lock<std::shared_mutex> guard(mutex_);
731     if (g_btData == nullptr) {
732         ErrorLog("OnBtNtfClicked: g_btData error");
733         return;
734     }
735     g_action = ACTION_CONNECT;
736     if (IsBtEnabled()) {
737         g_state = STATE_PAIRING;
738         HandleBtPair();
739         NextAction();
740     } else {
741         g_state = STATE_WAITING_FOR_BT_ENABLE;
742         if (!HandleEnableBt()) {
743             ErrorLog("OnBtNtfClicked enable bt failed");
744             OnFinish();
745         }
746     }
747 }
748 
OnBtEnabled()749 void BtConnectionManager::OnBtEnabled()
750 {
751     DebugLog("OnBtEnabled");
752     RemoveMsgFromEvtHandler(NfcCommonEvent::MSG_BT_ENABLE_TIMEOUT);
753     if (g_state == STATE_WAITING_FOR_BT_ENABLE) {
754         g_state = STATE_INIT;
755         NextAction();
756     }
757 }
758 
OnStateChanged(const int transport,const int status)759 void BtConnectionManager::BtStateObserver::OnStateChanged(const int transport, const int status)
760 {
761     InfoLog("OnStateChanged transport: %{public}d, status: %{public}d", transport, status);
762     if (transport == static_cast<int>(Bluetooth::BTTransport::ADAPTER_BREDR) &&
763         status == static_cast<int>(Bluetooth::STATE_TURN_ON)) {
764         BtConnectionManager::GetInstance().OnBtEnabled();
765     }
766 }
767 
OnPairStatusChanged(std::shared_ptr<BtConnectionInfo> info)768 void BtConnectionManager::OnPairStatusChanged(std::shared_ptr<BtConnectionInfo> info)
769 {
770     std::unique_lock<std::shared_mutex> guard(mutex_);
771     if (info == nullptr) {
772         ErrorLog("OnPairStatusChanged: info is null");
773         return;
774     }
775     if (g_btData == nullptr) {
776         ErrorLog("OnPairStatusChanged: g_btData error");
777         return;
778     }
779     if (info->macAddr_.compare(g_btData->macAddress_) != 0) {
780         ErrorLog("OnPairStatusChanged not same device");
781         return;
782     }
783     if (g_state == STATE_PAIRING) {
784         if (info->state_ == Bluetooth::PAIR_PAIRED) {
785             RemoveMsgFromEvtHandler(NfcCommonEvent::MSG_BT_PAIR_TIMEOUT);
786             g_state = STATE_PAIR_COMPLETE;
787             NextAction();
788         } else if (info->state_ == Bluetooth::PAIR_NONE) {
789             // timeout msg removed in OnFinish()
790             OnFinish();
791         }
792     }
793 }
794 
OnPairStatusChanged(const Bluetooth::BluetoothRemoteDevice & device,int status,int cause)795 void BtConnectionManager::BtRemoteDevObserver::OnPairStatusChanged(const Bluetooth::BluetoothRemoteDevice &device,
796                                                                    int status, int cause)
797 {
798     (void)cause; // Unused parameter
799     InfoLog("OnPairStatusChanged status: %{public}d", status);
800     BtConnectionManager::GetInstance().SendConnMsgToEvtHandler(NfcCommonEvent::MSG_BT_PAIR_STATUS_CHANGED,
801         device, status, BtConnectionManager::BtProfileType::A2DP_SRC);
802 }
803 
OnConnectionStateChanged(std::shared_ptr<BtConnectionInfo> info)804 void BtConnectionManager::OnConnectionStateChanged(std::shared_ptr<BtConnectionInfo> info)
805 {
806     std::unique_lock<std::shared_mutex> guard(mutex_);
807     if (info == nullptr) {
808         ErrorLog("OnConnectionStateChanged: info is null");
809         return;
810     }
811     if (g_btData == nullptr) {
812         ErrorLog("OnConnectionStateChanged: g_btData error");
813         return;
814     }
815     if (info->macAddr_.compare(g_btData->macAddress_) != 0) {
816         ErrorLog("OnConnectionStateChanged not same device");
817         return;
818     }
819     if (info->state_ == static_cast<int32_t>(Bluetooth::BTConnectState::CONNECTED)) {
820         {
821             if (info->type_ == static_cast<uint8_t>(HFP_AG)) {
822                 g_hfpConnState = CONN_RES_CONNECTED;
823             } else if (info->type_ == static_cast<uint8_t>(A2DP_SRC)) {
824                 g_a2dpConnState = CONN_RES_CONNECTED;
825             } else if (info->type_ == static_cast<uint8_t>(HID_HOST)) {
826                 g_hidConnState = CONN_RES_CONNECTED;
827             }
828         }
829         NextAction();
830     } else if (info->state_ == static_cast<int32_t>(Bluetooth::BTConnectState::DISCONNECTED)) {
831         {
832             if (g_action == ACTION_CONNECT) {
833                 // need retry
834                 return;
835             }
836             if (info->type_ == static_cast<uint8_t>(HFP_AG)) {
837                 g_hfpConnState = CONN_RES_DISCONNECTED;
838             } else if (info->type_ == static_cast<uint8_t>(A2DP_SRC)) {
839                 g_a2dpConnState = CONN_RES_DISCONNECTED;
840             } else if (info->type_ == static_cast<uint8_t>(HID_HOST)) {
841                 g_hidConnState = CONN_RES_DISCONNECTED;
842             }
843         }
844         NextAction();
845     }
846 }
847 
OnConnectionStateChanged(const Bluetooth::BluetoothRemoteDevice & device,int32_t state,int32_t cause)848 void BtConnectionManager::BtA2dpObserver::OnConnectionStateChanged(const Bluetooth::BluetoothRemoteDevice &device,
849                                                                    int32_t state, int32_t cause)
850 {
851     (void)cause; // Unused param
852     InfoLog("BtA2dpObserver::OnConnectionStateChanged state: %{public}d", state);
853     BtConnectionManager::GetInstance().SendConnMsgToEvtHandler(NfcCommonEvent::MSG_BT_CONNECT_STATUS_CHANGED,
854         device, state, BtConnectionManager::BtProfileType::A2DP_SRC);
855 }
856 
OnConnectionStateChanged(const Bluetooth::BluetoothRemoteDevice & device,int32_t state,int32_t cause)857 void BtConnectionManager::BtHfpObserver::OnConnectionStateChanged(const Bluetooth::BluetoothRemoteDevice &device,
858                                                                   int32_t state, int32_t cause)
859 {
860     (void)cause; // Unused param
861     InfoLog("BtHfpObserver::OnConnectionStateChanged state: %{public}d", state);
862     BtConnectionManager::GetInstance().SendConnMsgToEvtHandler(NfcCommonEvent::MSG_BT_CONNECT_STATUS_CHANGED,
863         device, state, BtConnectionManager::BtProfileType::HFP_AG);
864 }
865 
OnConnectionStateChanged(const Bluetooth::BluetoothRemoteDevice & device,int state,int cause)866 void BtConnectionManager::BtHidObserver::OnConnectionStateChanged(const Bluetooth::BluetoothRemoteDevice &device,
867                                                                   int state, int cause)
868 {
869     (void)cause; // Unused param
870     InfoLog("BtHidObserver::OnConnectionStateChanged state: %{public}d", state);
871     BtConnectionManager::GetInstance().SendConnMsgToEvtHandler(NfcCommonEvent::MSG_BT_CONNECT_STATUS_CHANGED,
872         device, state, BtConnectionManager::BtProfileType::HID_HOST);
873 }
874 } // namespace TAG
875 } // namespace NFC
876 } // namespace OHOS
877