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