1 /*
2  * Copyright (c) 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 
16 #include "softbus_conn_ble_manager.h"
17 
18 #include <ctype.h>
19 #include <securec.h>
20 
21 #include "bus_center_event.h"
22 #include "bus_center_manager.h"
23 #include "conn_event.h"
24 #include "conn_log.h"
25 #include "softbus_adapter_ble_conflict.h"
26 #include "softbus_adapter_bt_common.h"
27 #include "softbus_adapter_crypto.h"
28 #include "softbus_adapter_mem.h"
29 #include "softbus_adapter_timer.h"
30 #include "softbus_conn_ble_trans.h"
31 #include "softbus_conn_common.h"
32 #include "softbus_datahead_transform.h"
33 #include "softbus_utils.h"
34 
35 #define CONFLICT_REUSE_CONNECTING 0
36 #define SHORT_UDID_HASH_LEN       8
37 
38 enum BleMgrState {
39     BLE_MGR_STATE_AVAILABLE,
40     BLE_MGR_STATE_CONNECTING,
41     BLE_MGR_STATE_MAX,
42 };
43 
44 enum BleMgrLooperMsg {
45     BLE_MGR_MSG_NEXT_CMD,
46     BLE_MGR_MSG_CONNECT_REQUEST,
47     BLE_MGR_MSG_CONNECT_SUCCESS,
48     BLE_MGR_MSG_CONNECT_TIMEOUT,
49     BLE_MGR_MSG_CONNECT_FAIL,
50     BLE_MGR_MSG_SERVER_ACCEPTED,
51     BLE_MGR_MSG_DATA_RECEIVED,
52     BLE_MGR_MSG_CONNECTION_CLOSED,
53     BLE_MGR_MSG_CONNECTION_RESUME,
54     BLE_MGR_MSG_DISCONNECT_REQUEST,
55     BLE_MGR_MSG_PREVENT_TIMEOUT,
56     BLE_MGR_MSG_RESET,
57     BLE_MRG_MSG_KEEP_ALIVE_TIMEOUT,
58 };
59 
60 typedef struct {
61     SoftBusList *connections;
62     ConnBleState *state;
63     ListNode waitings;
64     ConnBleDevice *connecting;
65     // prevent device connect request
66     SoftBusList *prevents;
67 } BleManager;
68 
69 typedef struct {
70     uint32_t connectionId;
71     int32_t status;
72 } BleStatusContext;
73 
74 typedef struct {
75     ListNode node;
76     char udid[UDID_BUF_LEN];
77     int32_t timeout;
78 } BlePrevent;
79 
80 enum BleConnectionCompareType {
81     BLE_CONNECTION_COMPARE_TYPE_CONNECTION_ID,
82     BLE_CONNECTION_COMPARE_TYPE_ADDRESS,
83     BLE_CONNECTION_COMPARE_TYPE_UNDERLAY_HANDLE,
84     BLE_CONNECTION_COMPARE_TYPE_UDID_IGNORE_ADDRESS,
85     BLE_CONNECTION_COMPARE_TYPE_UDID_CLIENT_SIDE,
86 };
87 
88 typedef struct {
89     enum BleConnectionCompareType type;
90     union {
91         struct {
92             uint32_t connectionId;
93         } connectionIdOption;
94         struct {
95             const char *addr;
96             ConnSideType side;
97             ProtocolType protocol;
98         } addressOption;
99         struct {
100             int32_t underlayerHandle;
101             ConnSideType side;
102             ProtocolType protocol;
103         } underlayerHandleOption;
104         struct {
105             const char *addr;
106             const char *udid;
107             ProtocolType protocol;
108         } udidAddressOption;
109         struct {
110             const char *udid;
111             BleProtocolType protocol;
112         } udidClientOption;
113     };
114 } BleConnectionCompareOption;
115 
116 typedef bool (*BleConnectionCompareFunc)(ConnBleConnection *connection, const BleConnectionCompareOption *option);
117 static void TransitionToState(enum BleMgrState target);
118 static int32_t PendingDevice(ConnBleDevice *device, const char *anomizeAddress, const char *anomizeUdid);
119 static void BleClientConnectFailed(uint32_t connectionId, int32_t error);
120 static void ReceivedControlData(ConnBleConnection *connection, const uint8_t *data, uint32_t dataLen);
121 static bool IsSameDevice(const char *leftIdentifier, const char *rightIdentifier);
122 static void BleManagerMsgHandler(SoftBusMessage *msg);
123 static int BleCompareManagerLooperEventFunc(const SoftBusMessage *msg, void *args);
124 static int32_t BleUpdateConnection(uint32_t connectionId, UpdateOption *option);
125 static void DelayRegisterLnnOnlineListener(void);
126 
127 static BleManager g_bleManager = { 0 };
128 static SoftBusHandlerWrapper g_bleManagerSyncHandler = {
129     .handler = {
130         .name = (char *)"BleManagerAsyncHandler",
131         .HandleMessage = BleManagerMsgHandler,
132         // assign when initiation
133         .looper = NULL,
134     },
135     .eventCompareFunc = BleCompareManagerLooperEventFunc,
136 };
137 static ConnectCallback g_connectCallback = { 0 };
138 
BleNameAvailableState(void)139 static char *BleNameAvailableState(void)
140 {
141     return "avaible state";
142 }
143 
BleNameConnectingState(void)144 static char *BleNameConnectingState(void)
145 {
146     return "connectting state";
147 }
148 
BleEnterAvailableState(void)149 static void BleEnterAvailableState(void)
150 {
151     CONN_LOGI(CONN_BLE, "ble manager enter avaible state");
152     ConnPostMsgToLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_NEXT_CMD, 0, 0, NULL, 0);
153 }
154 
BleEnterConnectingState(void)155 static void BleEnterConnectingState(void)
156 {
157     CONN_LOGI(CONN_BLE, "ble manager enter connecting state");
158 }
159 
BleExitAvailableState(void)160 static void BleExitAvailableState(void)
161 {
162     CONN_LOGI(CONN_BLE, "ble manager exit avaible state");
163 }
164 
BleExitConnectingState(void)165 static void BleExitConnectingState(void)
166 {
167     CONN_LOGI(CONN_BLE, "ble manager exit connecting state");
168 }
169 
DfxRecordBleConnectFail(uint32_t reqId,uint32_t pId,ConnBleDevice * device,const ConnectStatistics * statistics,int32_t reason)170 static void DfxRecordBleConnectFail(
171     uint32_t reqId, uint32_t pId, ConnBleDevice *device, const ConnectStatistics *statistics, int32_t reason)
172 {
173     if (statistics == NULL) {
174         CONN_LOGW(CONN_BLE, "statistics is null");
175         return;
176     }
177 
178     SoftBusConnType connType =
179         device->protocol == BLE_GATT ? SOFTBUS_HISYSEVT_CONN_TYPE_BLE : SOFTBUS_HISYSEVT_CONN_TYPE_COC;
180 
181     CONN_LOGD(CONN_BLE, "record ble conn fail, connectTraceId=%{public}u, reason=%{public}d",
182         statistics->connectTraceId, reason);
183     uint64_t costTime = SoftBusGetSysTimeMs() - statistics->startTime;
184     SoftbusRecordConnResult(pId, connType, SOFTBUS_EVT_CONN_FAIL, costTime, reason);
185     ConnEventExtra extra = {
186         .requestId = reqId,
187         .linkType = CONNECT_BLE,
188         .connProtocol = device->protocol,
189         .costTime = costTime,
190         .peerBleMac = device->addr,
191         .errcode = reason,
192         .result = EVENT_STAGE_RESULT_FAILED
193     };
194     CONN_EVENT(EVENT_SCENE_CONNECT, EVENT_STAGE_CONNECT_END, extra);
195     ConnAlarmExtra extraAlarm = {
196         .linkType = CONNECT_BLE,
197         .errcode = reason,
198     };
199     CONN_ALARM(CONNECTION_FAIL_ALARM, MANAGE_ALARM_TYPE, extraAlarm);
200 }
201 
DfxRecordBleConnectSuccess(uint32_t pId,ConnBleConnection * connection,ConnectStatistics * statistics)202 static void DfxRecordBleConnectSuccess(uint32_t pId, ConnBleConnection *connection, ConnectStatistics *statistics)
203 {
204     if (statistics == NULL) {
205         CONN_LOGW(CONN_BLE, "statistics is null");
206         return;
207     }
208 
209     CONN_LOGD(CONN_BLE, "record ble conn succ, connectTraceId=%{public}u", statistics->connectTraceId);
210     SoftBusConnType connType =
211         connection->protocol == BLE_GATT ? SOFTBUS_HISYSEVT_CONN_TYPE_BLE : SOFTBUS_HISYSEVT_CONN_TYPE_COC;
212 
213     uint64_t costTime = SoftBusGetSysTimeMs() - statistics->startTime;
214     SoftbusRecordConnResult(pId, connType, SOFTBUS_EVT_CONN_SUCC, costTime, SOFTBUS_HISYSEVT_CONN_OK);
215     ConnEventExtra extra = {
216         .connectionId = (int32_t)connection->connectionId,
217         .linkType = CONNECT_BLE,
218         .connProtocol = connection->protocol,
219         .costTime = (int32_t)costTime,
220         .isReuse = statistics->reuse ? 1 : 0,
221         .peerBleMac = connection->addr,
222         .requestId = (int32_t)statistics->reqId,
223         .result = EVENT_STAGE_RESULT_OK
224     };
225     CONN_EVENT(EVENT_SCENE_CONNECT, EVENT_STAGE_CONNECT_END, extra);
226 }
227 
NewRequest(ConnBleRequest ** outRequest,const ConnBleConnectRequestContext * ctx)228 static int32_t NewRequest(ConnBleRequest **outRequest, const ConnBleConnectRequestContext *ctx)
229 {
230     ConnBleRequest *request = SoftBusCalloc(sizeof(ConnBleRequest));
231     if (request == NULL) {
232         CONN_LOGE(CONN_BLE, "request calloc faild");
233         return SOFTBUS_MALLOC_ERR;
234     }
235     ListInit(&request->node);
236     request->requestId = ctx->requestId;
237     request->challengeCode = ctx->challengeCode;
238     request->result = ctx->result;
239     request->protocol = ctx->protocol;
240     request->statistics.startTime = ctx->statistics.startTime;
241 
242     *outRequest = request;
243     return SOFTBUS_OK;
244 }
245 
NewDevice(ConnBleDevice ** outDevice,const ConnBleConnectRequestContext * ctx)246 static int32_t NewDevice(ConnBleDevice **outDevice, const ConnBleConnectRequestContext *ctx)
247 {
248     ConnBleDevice *device = SoftBusCalloc(sizeof(ConnBleDevice));
249     if (device == NULL) {
250         CONN_LOGE(CONN_BLE, "device calloc faild");
251         return SOFTBUS_MALLOC_ERR;
252     }
253     ListInit(&device->node);
254     if (strcpy_s(device->addr, BT_MAC_LEN, ctx->addr) != EOK ||
255         strcpy_s(device->udid, UDID_BUF_LEN, ctx->udid) != EOK) {
256         SoftBusFree(device);
257         return SOFTBUS_MEM_ERR;
258     }
259     device->fastestConnectEnable = ctx->fastestConnectEnable;
260     device->state = BLE_DEVICE_STATE_INIT;
261     device->protocol = ctx->protocol;
262     device->psm = ctx->psm;
263     device->retryCount = 0;
264     uint64_t feature = 0;
265     if (LnnGetConnSubFeatureByUdidHashStr(ctx->udid, &feature) != SOFTBUS_OK) {
266         CONN_LOGD(CONN_BLE, "get connSubFeature failed");
267     }
268     device->isSupportNetworkIdExchange = (feature & (1 << CONN_FEATURE_SUPPORT_NETWORKID_EXCAHNGE)) != 0;
269     ListInit(&device->requests);
270     *outDevice = device;
271     return SOFTBUS_OK;
272 }
273 
FreeDevice(ConnBleDevice * device)274 static void FreeDevice(ConnBleDevice *device)
275 {
276     ConnBleRequest *it = NULL;
277     ConnBleRequest *next = NULL;
278     LIST_FOR_EACH_ENTRY_SAFE(it, next, &device->requests, ConnBleRequest, node) {
279         ListDelete(&it->node);
280         SoftBusFree(it);
281     }
282     ListDelete(&device->node);
283     SoftBusFree(device);
284 }
285 
ConvertCtxToDevice(ConnBleDevice ** outDevice,const ConnBleConnectRequestContext * ctx)286 static int32_t ConvertCtxToDevice(ConnBleDevice **outDevice, const ConnBleConnectRequestContext *ctx)
287 {
288     ConnBleRequest *request = NULL;
289     int32_t status = NewRequest(&request, ctx);
290     if (status != SOFTBUS_OK) {
291         CONN_LOGE(CONN_BLE, "newrequest is failed, err=%{public}d", status);
292         return status;
293     }
294     ConnBleDevice *device = NULL;
295     status = NewDevice(&device, ctx);
296     if (status != SOFTBUS_OK) {
297         SoftBusFree(request);
298         return status;
299     }
300     ListAdd(&device->requests, &request->node);
301     *outDevice = device;
302     return SOFTBUS_OK;
303 }
304 
BleConvert2ConnectionInfo(ConnBleConnection * connection,ConnectionInfo * info)305 static int32_t BleConvert2ConnectionInfo(ConnBleConnection *connection, ConnectionInfo *info)
306 {
307     info->isAvailable = connection->state == BLE_CONNECTION_STATE_EXCHANGED_BASIC_INFO ? 1 : 0;
308     info->isServer = connection->side == CONN_SIDE_SERVER ? 1 : 0;
309     info->type = CONNECT_BLE;
310     if (strcpy_s(info->bleInfo.bleMac, BT_MAC_LEN, connection->addr) != EOK) {
311         return SOFTBUS_STRCPY_ERR;
312     }
313     info->bleInfo.protocol = connection->protocol;
314     info->bleInfo.psm = 0;
315     int32_t status = SOFTBUS_OK;
316     bool isSupportNetWorkIdExchange =
317         (connection->featureBitSet & (1 << BLE_FEATURE_SUPPORT_SUPPORT_NETWORKID_BASICINFO_EXCAHNGE)) != 0;
318     if (connection->protocol == BLE_COC || isSupportNetWorkIdExchange) {
319         info->bleInfo.psm = connection->psm;
320         ConnBleInnerComplementDeviceId(connection);
321         if (strlen(connection->udid) == 0) {
322             CONN_LOGW(CONN_BLE, "generate udid hash failed: device is not lnn online, connId=%{public}d",
323                 connection->connectionId);
324             // it will be complement later on lnn online listener
325             return SOFTBUS_OK;
326         }
327     }
328     status = SoftBusGenerateStrHash(
329         (unsigned char *)connection->udid, strlen(connection->udid), (unsigned char *)info->bleInfo.deviceIdHash);
330     if (status != SOFTBUS_OK) {
331         CONN_LOGE(CONN_BLE,
332             "convert ble connection info failed: generate udid hash failed, connId=%{public}u, err=%{public}d",
333             connection->connectionId, status);
334         return status;
335     }
336     return SOFTBUS_OK;
337 }
338 
BleNotifyDeviceConnectResult(const ConnBleDevice * device,ConnBleConnection * connection,int32_t reason,bool isReuse)339 static void BleNotifyDeviceConnectResult(const ConnBleDevice *device, ConnBleConnection *connection, int32_t reason,
340     bool isReuse)
341 {
342     char anomizeAddress[BT_MAC_LEN] = { 0 };
343     ConvertAnonymizeMacAddress(anomizeAddress, BT_MAC_LEN, device->addr, BT_MAC_LEN);
344 
345     ConnBleRequest *it = NULL;
346     if (connection == NULL) {
347         LIST_FOR_EACH_ENTRY(it, &device->requests, ConnBleRequest, node) {
348             CONN_LOGI(CONN_BLE,
349                 "ble notify connect requestfailed, requestId=%{public}u, addr=%{public}s, protocol=%{public}d, "
350                 "reason=%{public}d",
351                 it->requestId, anomizeAddress, device->protocol, reason);
352             DfxRecordBleConnectFail(it->requestId, DEFAULT_PID, (ConnBleDevice *)device, &it->statistics, reason);
353             it->result.OnConnectFailed(it->requestId, reason);
354         }
355         return;
356     }
357     UpdateOption option = {
358         .type = CONNECT_BLE,
359         .bleOption = {
360             .priority = CONN_BLE_PRIORITY_BALANCED,
361         }
362     };
363     BleUpdateConnection(connection->connectionId, &option);
364 
365     ConnectionInfo info = { 0 };
366     int32_t status = BleConvert2ConnectionInfo(connection, &info);
367     if (status != SOFTBUS_OK) {
368         CONN_LOGE(
369             CONN_BLE, "convert ble connection info failed, It cann't backoff now, just ahead. err=%{public}d", status);
370     }
371     LIST_FOR_EACH_ENTRY(it, &device->requests, ConnBleRequest, node) {
372         ConnBleUpdateConnectionRc(connection, it->challengeCode, 1);
373         CONN_LOGI(CONN_BLE,
374             "ble notify connect request success, "
375             "requestId=%{public}u, addr=%{public}s, connId=%{public}u, protocol=%{public}d, challenge=%{public}u",
376             it->requestId, anomizeAddress, connection->connectionId, device->protocol, it->challengeCode);
377         it->statistics.reqId = it->requestId;
378         it->statistics.reuse = isReuse;
379         DfxRecordBleConnectSuccess(DEFAULT_PID, connection, &it->statistics);
380         info.bleInfo.challengeCode = it->challengeCode;
381         it->result.OnConnectSuccessed(it->requestId, connection->connectionId, &info);
382     }
383 }
384 
BleReuseConnection(ConnBleDevice * device,ConnBleConnection * connection)385 static bool BleReuseConnection(ConnBleDevice *device, ConnBleConnection *connection)
386 {
387     CONN_CHECK_AND_RETURN_RET_LOGE(SoftBusMutexLock(&connection->lock) == SOFTBUS_OK, false, CONN_BLE,
388         "ATTENTION UNEXPECTED ERROR! ble reuse connection failed: try to lock failed, connId=%{public}u",
389         connection->connectionId);
390     enum ConnBleConnectionState state = connection->state;
391     (void)SoftBusMutexUnlock(&connection->lock);
392     if (state != BLE_CONNECTION_STATE_EXCHANGED_BASIC_INFO) {
393         return false;
394     }
395     BleNotifyDeviceConnectResult(device, connection, 0, true);
396     return true;
397 }
398 
BleCheckPreventing(const char * udid)399 static bool BleCheckPreventing(const char *udid)
400 {
401     CONN_CHECK_AND_RETURN_RET_LOGE(SoftBusMutexLock(&g_bleManager.prevents->lock) == SOFTBUS_OK, false, CONN_BLE,
402         "ATTENTION UNEXPECTED ERROR! ble check preventing failed: try to lock failed");
403     bool preventing = false;
404     BlePrevent *it = NULL;
405     LIST_FOR_EACH_ENTRY(it, &g_bleManager.prevents->list, BlePrevent, node) {
406         if (IsSameDevice(udid, (char *)it->udid)) {
407             preventing = true;
408             break;
409         }
410     }
411     (void)SoftBusMutexUnlock(&g_bleManager.prevents->lock);
412     return preventing;
413 }
414 
415 typedef int32_t (*DeviceAction)(ConnBleDevice *device, const char *anomizeAddress, const char *anomizeUdid);
AttempReuseConnect(ConnBleDevice * device,DeviceAction actionIfAbsent)416 static void AttempReuseConnect(ConnBleDevice *device, DeviceAction actionIfAbsent)
417 {
418     char anomizeAddress[BT_MAC_LEN] = { 0 };
419     ConvertAnonymizeMacAddress(anomizeAddress, BT_MAC_LEN, device->addr, BT_MAC_LEN);
420     char anomizeUdid[UDID_BUF_LEN] = { 0 };
421     ConvertAnonymizeSensitiveString(anomizeUdid, UDID_BUF_LEN, device->udid);
422 
423     // ignore protocol type
424     ConnBleConnection *udidConnection = ConnBleGetConnectionByUdid(device->addr, device->udid, BLE_PROTOCOL_ANY);
425     ConnBleConnection *clientConnection = ConnBleGetConnectionByAddr(device->addr, CONN_SIDE_CLIENT, BLE_PROTOCOL_ANY);
426     ConnBleConnection *serverConnection = ConnBleGetConnectionByAddr(device->addr, CONN_SIDE_SERVER, BLE_PROTOCOL_ANY);
427     if (udidConnection == NULL && clientConnection == NULL && serverConnection == NULL) {
428         if (BleCheckPreventing(device->udid)) {
429             CONN_LOGI(CONN_BLE,
430                 "ble manager reject connect request as udid is in prevent list, addr=%{public}s, udid=%{public}s",
431                 anomizeAddress, anomizeUdid);
432             BleNotifyDeviceConnectResult(device, NULL, SOFTBUS_CONN_BLE_CONNECT_PREVENTED_ERR, false);
433             FreeDevice(device);
434             return;
435         }
436         device->state = BLE_DEVICE_STATE_WAIT_SCHEDULE;
437         int32_t status = actionIfAbsent(device, anomizeAddress, anomizeUdid);
438         if (status != SOFTBUS_OK) {
439             BleNotifyDeviceConnectResult(device, NULL, status, false);
440             FreeDevice(device);
441         }
442         return;
443     }
444     do {
445         if (udidConnection != NULL && BleReuseConnection(device, udidConnection)) {
446             CONN_LOGW(CONN_BLE, "reuse ble connection by udid");
447             FreeDevice(device);
448             break;
449         }
450         if (clientConnection != NULL && BleReuseConnection(device, clientConnection)) {
451             CONN_LOGW(CONN_BLE, "reuse ble client connection by address");
452             FreeDevice(device);
453             break;
454         }
455         if (serverConnection != NULL && BleReuseConnection(device, serverConnection)) {
456             CONN_LOGW(CONN_BLE, "reuse ble server connection by address");
457             FreeDevice(device);
458             break;
459         }
460         device->state = BLE_DEVICE_STATE_WAIT_EVENT;
461         PendingDevice(device, anomizeAddress, anomizeUdid);
462     } while (false);
463 
464     if (udidConnection != NULL) {
465         ConnBleReturnConnection(&udidConnection);
466     }
467     if (clientConnection != NULL) {
468         ConnBleReturnConnection(&clientConnection);
469     }
470     if (serverConnection != NULL) {
471         ConnBleReturnConnection(&serverConnection);
472     }
473 }
474 
BleConnectDeviceDirectly(ConnBleDevice * device,const char * anomizeAddress,const char * anomizeUdid)475 static int32_t BleConnectDeviceDirectly(ConnBleDevice *device, const char *anomizeAddress, const char *anomizeUdid)
476 {
477     CONN_LOGI(CONN_BLE, "ble manager start schedule connect request, addr=%{public}s, udid=%{public}s", anomizeAddress,
478         anomizeUdid);
479     DelayRegisterLnnOnlineListener();
480     device->state = BLE_DEVICE_STATE_SCHEDULING;
481     int32_t status = SOFTBUS_OK;
482     ConnBleConnection *connection = ConnBleCreateConnection(
483         device->addr, device->protocol, CONN_SIDE_CLIENT, INVALID_UNDERLAY_HANDLE, device->fastestConnectEnable);
484     if (connection == NULL) {
485         return SOFTBUS_CONN_BLE_INTERNAL_ERR;
486     }
487     connection->featureBitSet =
488         (device->isSupportNetworkIdExchange ? (1 << BLE_FEATURE_SUPPORT_SUPPORT_NETWORKID_BASICINFO_EXCAHNGE) : 0);
489     connection->psm = device->psm;
490     char *address = NULL;
491     do {
492         address = (char *)SoftBusCalloc(BT_MAC_LEN);
493         if (address == NULL || strcpy_s(address, BT_MAC_LEN, device->addr) != EOK) {
494             CONN_LOGE(CONN_BLE,
495                 "copy ble address for connect timeout event failed, requestAddress=%{public}s, udid=%{public}s",
496                 anomizeAddress, anomizeUdid);
497             status = SOFTBUS_MEM_ERR;
498             break;
499         }
500 
501         status = ConnBleSaveConnection(connection);
502         if (status != SOFTBUS_OK) {
503             break;
504         }
505         status = ConnBleConnect(connection);
506         if (status != SOFTBUS_OK) {
507             break;
508         }
509         g_bleManager.connecting = device;
510         status = ConnPostMsgToLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_CONNECT_TIMEOUT,
511             connection->connectionId, 0, address, BLE_CONNECT_TIMEOUT_MILLIS);
512         if (status != SOFTBUS_OK) {
513             CONN_LOGE(CONN_BLE, "post msg failed, requestAddress=%{public}s, udid=%{public}s, error=%{public}d",
514                 anomizeAddress, anomizeUdid, status);
515             break;
516         }
517         TransitionToState(BLE_MGR_STATE_CONNECTING);
518     } while (false);
519 
520     ConnEventExtra extra = {
521         .connectionId = (int32_t)connection->connectionId,
522         .peerBleMac = device->addr,
523         .peerUdid = device->udid,
524         .linkType = CONNECT_BLE,
525         .errcode = status,
526         .result = status == SOFTBUS_OK ? EVENT_STAGE_RESULT_OK : EVENT_STAGE_RESULT_FAILED
527     };
528     CONN_EVENT(EVENT_SCENE_CONNECT, EVENT_STAGE_CONNECT_DEVICE_DIRECTLY, extra);
529     if (status != SOFTBUS_OK) {
530         ConnBleRemoveConnection(connection);
531         SoftBusFree(address);
532     }
533     ConnBleReturnConnection(&connection);
534     return status;
535 }
536 
PendingDevice(ConnBleDevice * device,const char * anomizeAddress,const char * anomizeUdid)537 static int32_t PendingDevice(ConnBleDevice *device, const char *anomizeAddress, const char *anomizeUdid)
538 {
539     CONN_LOGI(CONN_BLE, "ble manager pend connect request, addr=%{public}s, udid=%{public}s, deviceState=%{public}d",
540         anomizeAddress, anomizeUdid, device->state);
541     ConnBleDevice *connecting = g_bleManager.connecting;
542     char connectingAnomizeAddress[BT_MAC_LEN] = { 0 };
543     if (connecting != NULL) {
544         ConvertAnonymizeMacAddress(connectingAnomizeAddress, BT_MAC_LEN, connecting->addr, BT_MAC_LEN);
545     }
546 
547     ConnBleDevice *target = NULL;
548     if (connecting != NULL && StrCmpIgnoreCase(connecting->addr, device->addr) == 0) {
549         target = connecting;
550     } else {
551         ConnBleDevice *it = NULL;
552         LIST_FOR_EACH_ENTRY(it, &g_bleManager.waitings, ConnBleDevice, node) {
553             if (StrCmpIgnoreCase(it->addr, device->addr) == 0) {
554                 target = it;
555                 break;
556             }
557         }
558     }
559     CONN_LOGD(CONN_BLE, "pengding current ble connect request, request addr=%{public}s, connecting addr=%{public}s",
560         anomizeAddress, connectingAnomizeAddress);
561     if (target == NULL) {
562         ListTailInsert(&g_bleManager.waitings, &device->node);
563         return SOFTBUS_OK;
564     }
565 
566     ConnBleDevice *requestIt = NULL;
567     ConnBleDevice *requestNext = NULL;
568     LIST_FOR_EACH_ENTRY_SAFE(requestIt, requestNext, &device->requests, ConnBleDevice, node) {
569         ListDelete(&requestIt->node);
570         ListAdd(&target->requests, &requestIt->node);
571     }
572     target->fastestConnectEnable = (device->fastestConnectEnable || target->fastestConnectEnable);
573     if (strlen(target->udid) == 0 && strlen(device->udid) != 0) {
574         if (strcpy_s(target->udid, UDID_BUF_LEN, device->udid) != EOK) {
575             CONN_LOGE(CONN_BLE,
576                 "copy ble connect request udid to previous request failed, it is not a big deal, just "
577                 "ahead, addr=%{public}s",
578                 anomizeAddress);
579         }
580     }
581     target->state = device->state;
582     FreeDevice(device);
583     return SOFTBUS_OK;
584 }
585 
BleConnectRequestOnAvailableState(const ConnBleConnectRequestContext * ctx)586 static void BleConnectRequestOnAvailableState(const ConnBleConnectRequestContext *ctx)
587 {
588     ConnBleDevice *device = NULL;
589     int32_t status = ConvertCtxToDevice(&device, ctx);
590     if (status != SOFTBUS_OK) {
591         CONN_LOGE(
592             CONN_BLE, "convert ble connect request failed, reqId=%{public}u, err=%{public}d", ctx->requestId, status);
593         DfxRecordBleConnectFail(ctx->requestId, DEFAULT_PID, device, &ctx->statistics, status);
594         ctx->result.OnConnectFailed(ctx->requestId, status);
595         return;
596     }
597     char anomizeAddress[BT_MAC_LEN] = { 0 };
598     ConvertAnonymizeMacAddress(anomizeAddress, BT_MAC_LEN, device->addr, BT_MAC_LEN);
599     char anomizeUdid[UDID_BUF_LEN] = { 0 };
600     ConvertAnonymizeSensitiveString(anomizeUdid, UDID_BUF_LEN, device->udid);
601     device->state = BLE_DEVICE_STATE_WAIT_SCHEDULE;
602     PendingDevice(device, anomizeAddress, anomizeUdid);
603     ConnPostMsgToLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_NEXT_CMD, 0, 0, NULL, 0);
604 }
605 
BleConnectRequestOnConnectingState(const ConnBleConnectRequestContext * ctx)606 static void BleConnectRequestOnConnectingState(const ConnBleConnectRequestContext *ctx)
607 {
608     ConnBleDevice *device = NULL;
609     int32_t status = ConvertCtxToDevice(&device, ctx);
610     if (status != SOFTBUS_OK) {
611         CONN_LOGE(
612             CONN_BLE, "convert ble connect request failed, reqId=%{public}u, err=%{public}d", ctx->requestId, status);
613         DfxRecordBleConnectFail(ctx->requestId, DEFAULT_PID, device, &ctx->statistics, status);
614         ctx->result.OnConnectFailed(ctx->requestId, status);
615         return;
616     }
617     AttempReuseConnect(device, PendingDevice);
618 }
619 
620 // handlePendingRequest
BleHandlePendingRequestOnAvailableState(void)621 static void BleHandlePendingRequestOnAvailableState(void)
622 {
623     ConnBleDevice *target = NULL;
624     ConnBleDevice *it = NULL;
625     LIST_FOR_EACH_ENTRY(it, &g_bleManager.waitings, ConnBleDevice, node) {
626         if (it->state == BLE_DEVICE_STATE_WAIT_SCHEDULE) {
627             target = it;
628             break;
629         }
630     }
631     if (target == NULL) {
632         return;
633     }
634     ListDelete(&target->node);
635     AttempReuseConnect(target, BleConnectDeviceDirectly);
636 }
637 
638 // onConnectTimeout
BleClientConnectTimeoutOnConnectingState(uint32_t connectionId,const char * address)639 static void BleClientConnectTimeoutOnConnectingState(uint32_t connectionId, const char *address)
640 {
641     char anomizeAddress[BT_MAC_LEN] = { 0 };
642     ConvertAnonymizeMacAddress(anomizeAddress, BT_MAC_LEN, address, BT_MAC_LEN);
643 
644     ConnBleConnection *connection = ConnBleGetConnectionById(connectionId);
645     if (connection != NULL) {
646         CONN_LOGE(CONN_BLE, "ble connect timeout, interrupt connect progress, addr=%{public}s, connId=%{public}u",
647             anomizeAddress, connection->connectionId);
648         ConnBleDisconnectNow(connection, BLE_DISCONNECT_REASON_CONNECT_TIMEOUT);
649         ConnBleRemoveConnection(connection);
650         ConnBleReturnConnection(&connection);
651     } else {
652         CONN_LOGE(CONN_BLE,
653             "ble connect timeout, connection object not exist, skip interrupt connect progress. "
654             "addr=%{public}s, connId=%{public}u", anomizeAddress, connectionId);
655     }
656     ConnBleDevice *connectingDevice = g_bleManager.connecting;
657     if (connectingDevice == NULL || StrCmpIgnoreCase(connectingDevice->addr, address) != 0) {
658         CONN_LOGE(CONN_BLE,
659             "ble connect timeout, connecting device is null or address mismatch with this event. "
660             "addr=%{public}s, connId=%{public}u", anomizeAddress, connectionId);
661         return;
662     }
663     BleNotifyDeviceConnectResult(connectingDevice, NULL, SOFTBUS_CONN_BLE_CONNECT_TIMEOUT_ERR, false);
664     FreeDevice(connectingDevice);
665     g_bleManager.connecting = NULL;
666     TransitionToState(BLE_MGR_STATE_AVAILABLE);
667 }
668 // clientConnected
BleClientConnected(uint32_t connectionId)669 static void BleClientConnected(uint32_t connectionId)
670 {
671     ConnBleConnection *connection = ConnBleGetConnectionById(connectionId);
672     if (connection == NULL) {
673         CONN_LOGE(CONN_BLE, "can not get ble connection, is it removed? connectionId=%{public}u", connectionId);
674         return;
675     }
676     char anomizeAddress[BT_MAC_LEN] = { 0 };
677     ConvertAnonymizeMacAddress(anomizeAddress, BT_MAC_LEN, connection->addr, BT_MAC_LEN);
678     ConnBleDevice *connectingDevice = g_bleManager.connecting;
679     if (connectingDevice == NULL || StrCmpIgnoreCase(connectingDevice->addr, connection->addr) != 0) {
680         CONN_LOGE(CONN_BLE,
681             "there is no connecting device, is it connected after timeout? connId=%{public}u, addr=%{public}s",
682             connectionId, anomizeAddress);
683         ConnBleUpdateConnectionRc(connection, 0, -1);
684         ConnBleReturnConnection(&connection);
685         return;
686     }
687     ConnRemoveMsgFromLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_CONNECT_TIMEOUT, connectionId, 0, NULL);
688     CONN_LOGI(
689         CONN_BLE, "ble client connect success, clientId=%{public}d, addr=%{public}s", connectionId, anomizeAddress);
690     connection->underlayerFastConnectFailedScanFailure = false;
691     BleNotifyDeviceConnectResult(connectingDevice, connection, 0, false);
692     FreeDevice(connectingDevice);
693     g_bleManager.connecting = NULL;
694     TransitionToState(BLE_MGR_STATE_AVAILABLE);
695     ConnBleReturnConnection(&connection);
696 }
697 
BleTryReuseServerOrRetryConnect(ConnBleConnection * connection,ConnBleDevice * connectingDevice,const char * anomizeAddress)698 static int32_t BleTryReuseServerOrRetryConnect(ConnBleConnection *connection, ConnBleDevice *connectingDevice,
699     const char *anomizeAddress)
700 {
701     ConnBleConnection *serverConnection =
702         ConnBleGetConnectionByAddr(connection->addr, CONN_SIDE_SERVER, connectingDevice->protocol);
703     if (serverConnection != NULL && BleReuseConnection(connectingDevice, serverConnection)) {
704         CONN_LOGI(CONN_BLE, "ble client connect failed, but there is a server connection connected, reuse it, "
705                 "connId=%{public}u, addr=%{public}s", serverConnection->connectionId, anomizeAddress);
706         ConnBleReturnConnection(&serverConnection);
707         FreeDevice(connectingDevice);
708         return SOFTBUS_OK;
709     }
710 
711     connectingDevice->retryCount += 1;
712     if (!connection->underlayerFastConnectFailedScanFailure
713         || connectingDevice->retryCount >= BLE_GATT_CONNECT_MAX_RETRY_COUNT) {
714         return SOFTBUS_CONN_BLE_FAST_CONNECT_FAILED_NOT_RETRY;
715     }
716     connectingDevice->state = BLE_DEVICE_STATE_WAIT_SCHEDULE;
717     ListNodeInsert(&g_bleManager.waitings, &connectingDevice->node);
718     CONN_LOGI(CONN_BLE, "ble client try to connect once, connId=%{public}u", connection->connectionId);
719     return SOFTBUS_OK;
720 }
721 
722 // clientConnectFailed
BleClientConnectFailed(uint32_t connectionId,int32_t error)723 static void BleClientConnectFailed(uint32_t connectionId, int32_t error)
724 {
725     ConnBleConnection *connection = ConnBleGetConnectionById(connectionId);
726     if (connection == NULL) {
727         CONN_LOGE(CONN_BLE, "can not get ble connection, is it removed? connId=%{public}u, err=%{public}d",
728             connectionId, error);
729         return;
730     }
731 
732     char anomizeAddress[BT_MAC_LEN] = { 0 };
733     ConvertAnonymizeMacAddress(anomizeAddress, BT_MAC_LEN, connection->addr, BT_MAC_LEN);
734     CONN_LOGI(CONN_BLE, "ble client connect failed, connId=%{public}u, addr=%{public}s, err=%{public}d", connectionId,
735         anomizeAddress, error);
736     ConnBleDisconnectNow(connection, BLE_DISCONNECT_REASON_INTERNAL_ERROR);
737 
738     ConnBleDevice *connectingDevice = g_bleManager.connecting;
739     if (connectingDevice == NULL || StrCmpIgnoreCase(connectingDevice->addr, connection->addr) != 0) {
740         CONN_LOGE(CONN_BLE, "there is no connecting device, is it connected after timeout? "
741             " connId=%{public}u, addr=%{public}s, err=%{public}d", connectionId, anomizeAddress, error);
742         ConnBleRemoveConnection(connection);
743         ConnBleReturnConnection(&connection);
744         return;
745     }
746     ConnRemoveMsgFromLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_CONNECT_TIMEOUT, connectionId, 0, NULL);
747 
748     if (BleTryReuseServerOrRetryConnect(connection, connectingDevice, anomizeAddress) != SOFTBUS_OK) {
749         BleNotifyDeviceConnectResult(connectingDevice, NULL, error, false);
750         FreeDevice(connectingDevice);
751     }
752     g_bleManager.connecting = NULL;
753     ConnBleRemoveConnection(connection);
754     ConnBleReturnConnection(&connection);
755     TransitionToState(BLE_MGR_STATE_AVAILABLE);
756 }
757 
IsSameHashId(const char * leftHash,const char * rightHash)758 static bool IsSameHashId(const char *leftHash, const char *rightHash)
759 {
760     size_t leftLen = strlen(leftHash);
761     size_t rightLen = strlen(rightHash);
762     size_t min = leftLen < rightLen ? leftLen : rightLen;
763     for (size_t i = 0; i < min; i++) {
764         if (toupper(leftHash[i]) != toupper(rightHash[i])) {
765             return false;
766         }
767     }
768     return true;
769 }
770 
IsSameDevice(const char * leftIdentifier,const char * rightIdentifier)771 static bool IsSameDevice(const char *leftIdentifier, const char *rightIdentifier)
772 {
773     if (leftIdentifier == NULL || rightIdentifier == NULL) {
774         return false;
775     }
776 
777     size_t leftLen = strlen(leftIdentifier);
778     size_t rightLen = strlen(rightIdentifier);
779     if (leftLen == 0 || rightLen == 0) {
780         return false;
781     }
782     if (leftLen == rightLen) {
783         return StrCmpIgnoreCase(leftIdentifier, rightIdentifier) == 0;
784     }
785     unsigned char leftHash[UDID_HASH_LEN] = { 0 };
786     unsigned char rightHash[UDID_HASH_LEN] = { 0 };
787     if (SoftBusGenerateStrHash((const unsigned char *)leftIdentifier, leftLen, leftHash) != SOFTBUS_OK ||
788         SoftBusGenerateStrHash((const unsigned char *)rightIdentifier, rightLen, rightHash) != SOFTBUS_OK) {
789         CONN_LOGE(CONN_BLE, "generate hash failed");
790         return false;
791     }
792     // only compare first 8 bytes of hash
793     char leftHashStr[HEXIFY_LEN(SHORT_UDID_HASH_LEN)] = { 0 };
794     char rightHashStr[HEXIFY_LEN(SHORT_UDID_HASH_LEN)] = { 0 };
795     if (ConvertBytesToHexString(leftHashStr, HEXIFY_LEN(SHORT_UDID_HASH_LEN), leftHash, SHORT_UDID_HASH_LEN) !=
796         SOFTBUS_OK ||
797         ConvertBytesToHexString(rightHashStr, HEXIFY_LEN(SHORT_UDID_HASH_LEN), rightHash, SHORT_UDID_HASH_LEN) !=
798         SOFTBUS_OK) {
799         CONN_LOGE(CONN_BLE, "convert bytes to array failed");
800         return false;
801     }
802     if (leftLen == UDID_BUF_LEN - 1) {
803         return IsSameHashId(leftHashStr, rightIdentifier);
804     } else if (rightLen == UDID_BUF_LEN - 1) {
805         return IsSameHashId(leftIdentifier, rightHashStr);
806     } else {
807         return IsSameHashId(leftHashStr, rightHashStr);
808     }
809 }
810 
811 // BleServerAccepted
BleServerAccepted(uint32_t connectionId)812 static void BleServerAccepted(uint32_t connectionId)
813 {
814     ConnBleConnection *connection = ConnBleGetConnectionById(connectionId);
815     if (connection == NULL) {
816         CONN_LOGE(CONN_BLE, "can not get ble connection, is it removed? connectionId=%{public}u", connectionId);
817         return;
818     }
819 
820     char anomizeAddress[BT_MAC_LEN] = { 0 };
821     ConvertAnonymizeMacAddress(anomizeAddress, BT_MAC_LEN, connection->addr, BT_MAC_LEN);
822 
823     ConnectionInfo info = { 0 };
824     int32_t status = BleConvert2ConnectionInfo(connection, &info);
825     if (status != SOFTBUS_OK) {
826         CONN_LOGE(
827             CONN_BLE, "convert connection info failed. It can not backoff now, just ahead. err=%{public}d", status);
828     }
829     char udidHashStr[HEXIFY_LEN(SHORT_UDID_HASH_LEN)] = { 0 };
830     status = ConvertBytesToHexString(
831         udidHashStr, HEXIFY_LEN(SHORT_UDID_HASH_LEN), (unsigned char *)info.bleInfo.deviceIdHash, SHORT_UDID_HASH_LEN);
832     if (status != SOFTBUS_OK) {
833         CONN_LOGE(CONN_BLE, "convert peerUdidHash to string failed, connectionId=%{public}u, err=%{public}d.",
834             connectionId, status);
835     }
836     char anomizeUdid[UDID_BUF_LEN] = { 0 };
837     ConvertAnonymizeSensitiveString(anomizeUdid, UDID_BUF_LEN, udidHashStr);
838     CONN_LOGI(CONN_BLE,
839         "ble server accept a new connection, connId=%{public}u, peerAddr=%{public}s, peerUdid=%{public}s",
840         connectionId, anomizeAddress, anomizeUdid);
841     g_connectCallback.OnConnected(connectionId, &info);
842     ConnEventExtra extra = {
843         .connectionId = (int32_t)connectionId,
844         .peerBleMac = connection->addr,
845         .peerUdid = connection->udid,
846         .linkType = CONNECT_BLE,
847         .result = EVENT_STAGE_RESULT_OK
848     };
849     CONN_EVENT(EVENT_SCENE_CONNECT, EVENT_STAGE_CONNECT_SERVER_ACCEPTED, extra);
850 
851     ConnBleDevice *connectingDevice = g_bleManager.connecting;
852     if (connectingDevice != NULL && StrCmpIgnoreCase(connectingDevice->addr, connection->addr) == 0) {
853         CONN_LOGW(CONN_BLE,
854             "both ends request establish connection at the same time, it will reused after connect failed, "
855             "connId=%{public}u, peerAddr=%{public}s",
856             connectionId, anomizeAddress);
857     }
858 
859     ConnBleDevice *it = NULL;
860     ConnBleDevice *next = NULL;
861     LIST_FOR_EACH_ENTRY_SAFE(it, next, &g_bleManager.waitings, ConnBleDevice, node) {
862         if ((StrCmpIgnoreCase(it->addr, connection->addr) == 0 || IsSameDevice(it->udid, connection->udid))) {
863             if (BleReuseConnection(it, connection)) {
864                 ListDelete(&it->node);
865                 FreeDevice(it);
866             }
867         }
868     }
869     ConnBleReturnConnection(&connection);
870 }
871 
872 // connectionClosed
BleConnectionClosed(uint32_t connectionId,int32_t error)873 static void BleConnectionClosed(uint32_t connectionId, int32_t error)
874 {
875     ConnBleConnection *connection = ConnBleGetConnectionById(connectionId);
876     CONN_CHECK_AND_RETURN_LOGW(connection != NULL, CONN_BLE, "connection not exist, connId=%{public}u", connectionId);
877 
878     ConnBleDevice *it = NULL;
879     LIST_FOR_EACH_ENTRY(it, &g_bleManager.waitings, ConnBleDevice, node) {
880         if (StrCmpIgnoreCase(it->addr, connection->addr) == 0 || IsSameDevice(it->udid, connection->udid)) {
881             it->state = BLE_DEVICE_STATE_WAIT_SCHEDULE;
882         }
883     }
884     ConnectionInfo info = { 0 };
885     int32_t status = BleConvert2ConnectionInfo(connection, &info);
886     if (status != SOFTBUS_OK) {
887         CONN_LOGE(
888             CONN_BLE, "convert ble connection info failed. It cann't backoff now, just ahead. err=%{public}d", status);
889     }
890     char udidHashStr[HEXIFY_LEN(UDID_HASH_LEN)] = { 0 };
891     status = ConvertBytesToHexString(
892         udidHashStr, HEXIFY_LEN(UDID_HASH_LEN), (unsigned char *)info.bleInfo.deviceIdHash, UDID_HASH_LEN);
893     if (status != SOFTBUS_OK) {
894         CONN_LOGE(
895             CONN_BLE, "convert udid hash to string failed, It cann't backoff now, just ahead. err=%{public}d", status);
896     }
897     if (connection->protocol == BLE_GATT) {
898         SoftbusBleConflictNotifyDisconnect(connection->addr, udidHashStr);
899     }
900     ConnBleRemoveConnection(connection);
901     ConnBleReturnConnection(&connection);
902     ConnPostMsgToLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_NEXT_CMD, 0, 0, NULL, 0);
903     g_connectCallback.OnDisconnected(connectionId, &info);
904 }
905 
906 // connectionResume
BleConnectionResume(uint32_t connectionId)907 static void BleConnectionResume(uint32_t connectionId)
908 {
909     ConnBleConnection *connection = ConnBleGetConnectionById(connectionId);
910     CONN_CHECK_AND_RETURN_LOGW(connection != NULL, CONN_BLE,
911         "ble connection resume handle failed: connection not exist, connId=%{public}u", connectionId);
912 
913     ConnBleDevice *it = NULL;
914     ConnBleDevice *next = NULL;
915     LIST_FOR_EACH_ENTRY_SAFE(it, next, &g_bleManager.waitings, ConnBleDevice, node) {
916         if (it->protocol == connection->protocol &&
917             (StrCmpIgnoreCase(it->addr, connection->addr) == 0 || IsSameDevice(it->udid, connection->udid))) {
918             if (BleReuseConnection(it, connection)) {
919                 ListDelete(&it->node);
920                 FreeDevice(it);
921             }
922         }
923     }
924 
925     ConnBleReturnConnection(&connection);
926 }
927 
928 // disconnectRequest
BleDisconnectRequest(uint32_t connectionId)929 static void BleDisconnectRequest(uint32_t connectionId)
930 {
931     ConnBleConnection *connection = ConnBleGetConnectionById(connectionId);
932     CONN_CHECK_AND_RETURN_LOGW(connection != NULL, CONN_BLE,
933         "connection is not exist, connId=%{public}u", connectionId);
934     ConnBleUpdateConnectionRc(connection, 0, -1);
935     ConnBleReturnConnection(&connection);
936 }
937 
938 // dataReceived
BleDataReceived(ConnBleDataReceivedContext * ctx)939 static void BleDataReceived(ConnBleDataReceivedContext *ctx)
940 {
941     ConnBleConnection *connection = ConnBleGetConnectionById(ctx->connectionId);
942     if (connection == NULL) {
943         CONN_LOGE(CONN_BLE, "connection not exist, is it removed? connId=%{public}u", ctx->connectionId);
944         SoftBusFree(ctx->data);
945         return;
946     }
947 
948     do {
949         if (!ctx->isConnCharacteristic) {
950             CONN_LOGI(CONN_BLE, "ble dispatch receive data, none conn data, connId=%{public}u, dataLength=%{public}u",
951                 connection->connectionId, ctx->dataLen);
952             g_connectCallback.OnDataReceived(ctx->connectionId, MODULE_BLE_NET, 0, (char *)ctx->data, ctx->dataLen);
953             break;
954         }
955 
956         if (ctx->dataLen < sizeof(ConnPktHead)) {
957             CONN_LOGE(CONN_BLE, "dataLength(=%{public}u) is less than header size, connId=%{public}u",
958                 ctx->dataLen, ctx->connectionId);
959             break;
960         }
961 
962         ConnPktHead *head = (ConnPktHead *)ctx->data;
963         UnpackConnPktHead(head);
964         CONN_LOGI(CONN_BLE, "ble dispatch receive data, connId=%{public}u, Len=%{public}u, Flg=%{public}d, "
965             "Module=%{public}d, Seq=%{public}" PRId64 "", connection->connectionId, ctx->dataLen, head->flag,
966             head->module, head->seq);
967         uint32_t pktHeadLen = ConnGetHeadSize();
968         if (head->module == MODULE_CONNECTION) {
969             ReceivedControlData(connection, ctx->data + pktHeadLen, ctx->dataLen - pktHeadLen);
970         } else if (head->module == MODULE_OLD_NEARBY) {
971             SoftbusBleConflictNotifyDateReceive(
972                 connection->underlayerHandle, ctx->data + pktHeadLen, ctx->dataLen - pktHeadLen);
973         } else {
974             g_connectCallback.OnDataReceived(
975                 ctx->connectionId, (ConnModule)head->module, head->seq, (char *)ctx->data, ctx->dataLen);
976         }
977     } while (false);
978 
979     SoftBusFree(ctx->data);
980     ctx->data = NULL;
981     ConnBleReturnConnection(&connection);
982 }
983 
ReceivedControlData(ConnBleConnection * connection,const uint8_t * data,uint32_t dataLen)984 static void ReceivedControlData(ConnBleConnection *connection, const uint8_t *data, uint32_t dataLen)
985 {
986     cJSON *json = cJSON_ParseWithLength((const char *)data, dataLen);
987     if (json == NULL) {
988         CONN_LOGE(CONN_BLE, "parse json failed. connId=%{public}u", connection->connectionId);
989         return;
990     }
991 
992     int32_t method = 0;
993     if (!GetJsonObjectNumberItem(json, CTRL_MSG_KEY_METHOD, &method)) {
994         CONN_LOGE(CONN_BLE, "parse method failed. connId=%{public}u", connection->connectionId);
995         cJSON_Delete(json);
996         return;
997     }
998     CONN_LOGD(
999         CONN_BLE, "ble receive control data, connId=%{public}u, method=%{public}d",
1000         connection->connectionId, method);
1001     int32_t status = SOFTBUS_OK;
1002     switch (method) {
1003         case METHOD_NOTIFY_REQUEST:
1004             status = ConnBleOnReferenceRequest(connection, json);
1005             break;
1006         default:
1007             CONN_LOGE(CONN_BLE, "received control message, UNSUPPORT method. connId=%{public}u, method=%{public}d",
1008                 connection->connectionId, method);
1009             break;
1010     }
1011     if (status != SOFTBUS_OK) {
1012         CONN_LOGE(CONN_BLE, "unexpected error. connId=%{public}u, method=%{public}d, err=%{public}d",
1013             connection->connectionId, method, status);
1014     }
1015     cJSON_Delete(json);
1016 }
1017 
BleReuseConnectionCommon(const char * udid,const char * anomizeAddress,ProtocolType protocol)1018 static int32_t BleReuseConnectionCommon(const char *udid, const char *anomizeAddress, ProtocolType protocol)
1019 {
1020     ConnBleConnection *connection = ConnBleGetClientConnectionByUdid(udid, protocol);
1021     if (connection == NULL) {
1022         return SOFTBUS_CONN_BLE_CONNECTION_NOT_EXIST_ERR;
1023     }
1024     if (SoftBusMutexLock(&connection->lock) != SOFTBUS_OK) {
1025         CONN_LOGE(
1026             CONN_BLE, "try to lock failed, connId=%{public}u, addr=%{public}s",
1027             connection->connectionId, anomizeAddress);
1028         ConnBleReturnConnection(&connection);
1029         return SOFTBUS_LOCK_ERR;
1030     }
1031     enum ConnBleConnectionState state = connection->state;
1032     int32_t underlayerHandle = connection->underlayerHandle;
1033     (void)SoftBusMutexUnlock(&connection->lock);
1034     int32_t status = SOFTBUS_CONN_BLE_CONNECTION_NOT_READY_ERR;
1035     if (state == BLE_CONNECTION_STATE_EXCHANGED_BASIC_INFO) {
1036         status = ConnBleUpdateConnectionRc(connection, 0, 1); /* no need challenge, set default value 0 */
1037     }
1038     CONN_LOGI(CONN_BLE, "reuse connection, connId=%{public}u, state=%{public}d, addr=%{public}s, status=%{public}d",
1039         connection->connectionId, state, anomizeAddress, status);
1040     ConnBleReturnConnection(&connection);
1041     if (status == SOFTBUS_OK) {
1042         return underlayerHandle;
1043     }
1044     return status;
1045 }
1046 
BleReuseConnectionRequestOnAvailableState(const ConnBleReuseConnectionContext * ctx)1047 static int32_t BleReuseConnectionRequestOnAvailableState(const ConnBleReuseConnectionContext *ctx)
1048 {
1049     char anomizeAddress[BT_MAC_LEN] = { 0 };
1050     ConvertAnonymizeMacAddress(anomizeAddress, BT_MAC_LEN, ctx->addr, BT_MAC_LEN);
1051     return BleReuseConnectionCommon(ctx->udid, anomizeAddress, ctx->protocol);
1052 }
1053 
ConflictOnConnectSuccessed(uint32_t requestId,uint32_t connectionId,const ConnectionInfo * info)1054 static void ConflictOnConnectSuccessed(uint32_t requestId, uint32_t connectionId, const ConnectionInfo *info)
1055 {
1056     (void)connectionId;
1057     (void)info;
1058     ConnBleConnection *connection = ConnBleGetConnectionById(connectionId);
1059     CONN_CHECK_AND_RETURN_LOGW(connection != NULL, CONN_BLE, "conn not exist, connId=%{public}u", connectionId);
1060     int32_t underlayHandle = connection->underlayerHandle;
1061     ConnBleReturnConnection(&connection);
1062     SoftbusBleConflictNotifyConnectResult(requestId, underlayHandle, true);
1063 }
1064 
ConflictOnConnectFailed(uint32_t requestId,int32_t reason)1065 static void ConflictOnConnectFailed(uint32_t requestId, int32_t reason)
1066 {
1067     (void)reason;
1068     SoftbusBleConflictNotifyConnectResult(requestId, INVALID_UNDERLAY_HANDLE, false);
1069 }
1070 
BleReuseConnectionRequestOnConnectingState(const ConnBleReuseConnectionContext * ctx)1071 static int32_t BleReuseConnectionRequestOnConnectingState(const ConnBleReuseConnectionContext *ctx)
1072 {
1073     char anomizeAddress[BT_MAC_LEN] = { 0 };
1074     ConvertAnonymizeMacAddress(anomizeAddress, BT_MAC_LEN, ctx->addr, BT_MAC_LEN);
1075     int32_t result = BleReuseConnectionCommon(ctx->udid, anomizeAddress, ctx->protocol);
1076     if (result != SOFTBUS_CONN_BLE_CONNECTION_NOT_EXIST_ERR) {
1077         return result;
1078     }
1079 
1080     if ((BleProtocolType)ctx->protocol != g_bleManager.connecting->protocol ||
1081         !IsSameDevice(ctx->udid, g_bleManager.connecting->udid)) {
1082         return SOFTBUS_CONN_BLE_REUSE_FAILED;
1083     }
1084 
1085     // merge connect request
1086     ConnBleRequest *request = SoftBusCalloc(sizeof(ConnBleRequest));
1087     if (request == NULL) {
1088         return SOFTBUS_MALLOC_ERR;
1089     }
1090     ListInit(&request->node);
1091     request->requestId = ctx->requestId;
1092     request->result.OnConnectSuccessed = ConflictOnConnectSuccessed;
1093     request->result.OnConnectFailed = ConflictOnConnectFailed;
1094     ListAdd(&g_bleManager.connecting->requests, &request->node);
1095     return CONFLICT_REUSE_CONNECTING;
1096 }
1097 
BlePreventTimeout(const char * udid)1098 static void BlePreventTimeout(const char *udid)
1099 {
1100     CONN_CHECK_AND_RETURN_LOGE(SoftBusMutexLock(&g_bleManager.prevents->lock) == SOFTBUS_OK, CONN_BLE,
1101         "ATTENTION UNEXPECTED ERROR! ble prevent timeout handle failed: try to lock failed");
1102     do {
1103         size_t udidLen = strlen(udid);
1104         BlePrevent *it = NULL;
1105         BlePrevent *next = NULL;
1106         LIST_FOR_EACH_ENTRY_SAFE(it, next, &g_bleManager.prevents->list, BlePrevent, node) {
1107             if (udidLen == strlen((char *)it->udid) && memcmp(udid, it->udid, udidLen) == 0) {
1108                 ListDelete(&it->node);
1109                 SoftBusFree(it);
1110             }
1111         }
1112     } while (false);
1113     (void)SoftBusMutexUnlock(&g_bleManager.prevents->lock);
1114 }
1115 
BleReset(int32_t reason)1116 static void BleReset(int32_t reason)
1117 {
1118     CONN_LOGW(CONN_BLE, "ble manager start process RESET event, reason=%{public}d", reason);
1119     if (g_bleManager.connecting != NULL) {
1120         ConnBleConnection *connection = ConnBleGetConnectionByAddr(
1121             g_bleManager.connecting->addr, CONN_SIDE_CLIENT, g_bleManager.connecting->protocol);
1122         if (connection != NULL) {
1123             ConnRemoveMsgFromLooper(
1124                 &g_bleManagerSyncHandler, BLE_MGR_MSG_CONNECT_TIMEOUT, connection->connectionId, 0, NULL);
1125             ConnBleReturnConnection(&connection);
1126         }
1127         BleNotifyDeviceConnectResult(g_bleManager.connecting, NULL, SOFTBUS_CONN_BLUETOOTH_OFF, false);
1128         FreeDevice(g_bleManager.connecting);
1129         g_bleManager.connecting = NULL;
1130     }
1131     ConnBleDevice *deviceIt = NULL;
1132     ConnBleDevice *deviceNext = NULL;
1133     LIST_FOR_EACH_ENTRY_SAFE(deviceIt, deviceNext, &g_bleManager.waitings, ConnBleDevice, node) {
1134         ListDelete(&deviceIt->node);
1135         BleNotifyDeviceConnectResult(deviceIt, NULL, SOFTBUS_CONN_BLUETOOTH_OFF, false);
1136         FreeDevice(deviceIt);
1137     }
1138 
1139     int32_t status = SoftBusMutexLock(&g_bleManager.prevents->lock);
1140     if (status != SOFTBUS_OK) {
1141         CONN_LOGE(CONN_BLE, "try to lock prevents failed, err=%{public}d", status);
1142         return;
1143     }
1144     BlePrevent *preventIt = NULL;
1145     BlePrevent *preventNext = NULL;
1146     LIST_FOR_EACH_ENTRY_SAFE(preventIt, preventNext, &g_bleManager.prevents->list, BlePrevent, node) {
1147         ConnRemoveMsgFromLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_PREVENT_TIMEOUT, 0, 0, preventIt->udid);
1148         ListDelete(&preventIt->node);
1149         SoftBusFree(preventIt);
1150         g_bleManager.prevents->cnt--;
1151     }
1152     SoftBusMutexUnlock(&g_bleManager.prevents->lock);
1153 
1154     status = SoftBusMutexLock(&g_bleManager.connections->lock);
1155     if (status != SOFTBUS_OK) {
1156         CONN_LOGE(CONN_BLE, "try to lock connections failed, err=%{public}d", status);
1157         return;
1158     }
1159     ConnBleConnection *connectionIt = NULL;
1160     LIST_FOR_EACH_ENTRY(connectionIt, &g_bleManager.connections->list, ConnBleConnection, node) {
1161         // MUST NOT remove connection, connection close notify will cleanup
1162         ConnBleDisconnectNow(connectionIt, BLE_DISCONNECT_REASON_RESET);
1163     }
1164     SoftBusMutexUnlock(&g_bleManager.connections->lock);
1165     TransitionToState(BLE_MGR_STATE_AVAILABLE);
1166 }
1167 
BleKeepAliveTimeout(uint32_t connectionId,uint32_t requestId)1168 static void BleKeepAliveTimeout(uint32_t connectionId, uint32_t requestId)
1169 {
1170     ConnBleConnection *connection = ConnBleGetConnectionById(connectionId);
1171     CONN_CHECK_AND_RETURN_LOGW(connection != NULL, CONN_BLE,
1172         "connection not exist, connectionId=%{public}u", connectionId);
1173     int32_t status = ConnBleUpdateConnectionRc(connection, 0, -1);
1174     if (status != SOFTBUS_OK) {
1175         CONN_LOGE(CONN_BLE, "update rc failed, status=%{public}d, connectionId=%{public}u, requestId=%{public}u",
1176             status, connectionId, requestId);
1177     }
1178     ConnBleReturnConnection(&connection);
1179 }
1180 
AllocateConnectionIdUnsafe()1181 static uint32_t AllocateConnectionIdUnsafe()
1182 {
1183     static uint16_t nextId = 0;
1184     uint32_t connectionId = (CONNECT_BLE << CONNECT_TYPE_SHIFT) + (++nextId);
1185     ConnBleConnection *it = NULL;
1186     LIST_FOR_EACH_ENTRY(it, &g_bleManager.connections->list, ConnBleConnection, node) {
1187         if (connectionId == it->connectionId) {
1188             return 0;
1189         }
1190     }
1191     return connectionId;
1192 }
1193 
ConnBleSaveConnection(ConnBleConnection * connection)1194 int32_t ConnBleSaveConnection(ConnBleConnection *connection)
1195 {
1196     CONN_CHECK_AND_RETURN_RET_LOGW(
1197         connection != NULL, SOFTBUS_INVALID_PARAM, CONN_BLE, "invalid param, ble connection is null");
1198 
1199     int32_t status = SoftBusMutexLock(&g_bleManager.connections->lock);
1200     if (status != SOFTBUS_OK) {
1201         CONN_LOGW(CONN_BLE, "try to get ble manager connections lock failed, err=%{public}d", status);
1202         return status;
1203     }
1204     uint32_t connectionId = 0;
1205     do {
1206         connectionId = AllocateConnectionIdUnsafe();
1207     } while (connectionId == 0);
1208 
1209     connection->connectionId = connectionId;
1210     connection->objectRc += 1;
1211     ListAdd(&g_bleManager.connections->list, &connection->node);
1212     (void)SoftBusMutexUnlock(&g_bleManager.connections->lock);
1213     return SOFTBUS_OK;
1214 }
1215 
ConnBleRemoveConnection(ConnBleConnection * connection)1216 void ConnBleRemoveConnection(ConnBleConnection *connection)
1217 {
1218     CONN_CHECK_AND_RETURN_LOGW(connection != NULL, CONN_BLE, "invalid param, connection is null");
1219     CONN_CHECK_AND_RETURN_LOGE(SoftBusMutexLock(&g_bleManager.connections->lock) == SOFTBUS_OK, CONN_BLE,
1220         "try to get ble manager connections lock failed");
1221     bool exist = false;
1222     ConnBleConnection *it = NULL;
1223     LIST_FOR_EACH_ENTRY(it, &g_bleManager.connections->list, ConnBleConnection, node) {
1224         if (it->connectionId == connection->connectionId) {
1225             exist = true;
1226             break;
1227         }
1228     }
1229     if (exist) {
1230         ListDelete(&connection->node);
1231         ConnBleReturnConnection(&connection);
1232     } else {
1233         CONN_LOGW(CONN_BLE,
1234             "ble connection is not exist in global connection list, call remove duplicate? connectionId=%{public}u",
1235             connection->connectionId);
1236     }
1237     (void)SoftBusMutexUnlock(&g_bleManager.connections->lock);
1238 }
1239 
ConnectionCompareByConnectId(ConnBleConnection * connection,const BleConnectionCompareOption * option)1240 static bool ConnectionCompareByConnectId(ConnBleConnection *connection, const BleConnectionCompareOption *option)
1241 {
1242     return connection->connectionId == option->connectionIdOption.connectionId;
1243 }
1244 
ConnectionCompareByAddress(ConnBleConnection * connection,const BleConnectionCompareOption * option)1245 static bool ConnectionCompareByAddress(ConnBleConnection *connection, const BleConnectionCompareOption *option)
1246 {
1247     return StrCmpIgnoreCase(connection->addr, option->addressOption.addr) == 0 &&
1248         (option->addressOption.side == CONN_SIDE_ANY ? true : connection->side == option->addressOption.side) &&
1249         ((BleProtocolType)option->addressOption.protocol == BLE_PROTOCOL_ANY ?
1250                 true :
1251                 connection->protocol == (BleProtocolType)option->addressOption.protocol);
1252 }
1253 
ConnectionCompareByUnderlayHandle(ConnBleConnection * connection,const BleConnectionCompareOption * option)1254 static bool ConnectionCompareByUnderlayHandle(ConnBleConnection *connection, const BleConnectionCompareOption *option)
1255 {
1256     return connection->underlayerHandle == option->underlayerHandleOption.underlayerHandle &&
1257         (option->underlayerHandleOption.side == CONN_SIDE_ANY ?
1258                 true :
1259                 connection->side == option->underlayerHandleOption.side) &&
1260         ((BleProtocolType)option->underlayerHandleOption.protocol == BLE_PROTOCOL_ANY ?
1261                 true :
1262                 connection->protocol == (BleProtocolType)option->underlayerHandleOption.protocol);
1263 }
1264 
ConnectionCompareByUdidIgnoreAddress(ConnBleConnection * connection,const BleConnectionCompareOption * option)1265 static bool ConnectionCompareByUdidIgnoreAddress(ConnBleConnection *connection,
1266     const BleConnectionCompareOption *option)
1267 {
1268     ConnBleInnerComplementDeviceId(connection);
1269     if (StrCmpIgnoreCase(connection->addr, option->udidAddressOption.addr) != 0) {
1270         char animizeAddr[BT_MAC_LEN] = { 0 };
1271         char optionAnimizeAddr[BT_MAC_LEN] = { 0 };
1272         ConvertAnonymizeMacAddress(animizeAddr, BT_MAC_LEN, connection->addr, BT_MAC_LEN);
1273         ConvertAnonymizeMacAddress(optionAnimizeAddr, BT_MAC_LEN, option->udidAddressOption.addr, BT_MAC_LEN);
1274         CONN_LOGW(CONN_BLE, "ble mac address are different. connectionId=%{public}u, addr=%{public}s, "
1275             "optionaddr=%{public}s", connection->connectionId, animizeAddr, optionAnimizeAddr);
1276     }
1277     return IsSameDevice(connection->udid, option->udidAddressOption.udid) &&
1278         ((BleProtocolType)option->udidAddressOption.protocol == BLE_PROTOCOL_ANY ?
1279                 true :
1280                 connection->protocol == (BleProtocolType)option->udidAddressOption.protocol);
1281 }
1282 
ConnectionCompareByUdidClientSide(ConnBleConnection * connection,const BleConnectionCompareOption * option)1283 static bool ConnectionCompareByUdidClientSide(ConnBleConnection *connection, const BleConnectionCompareOption *option)
1284 {
1285     ConnBleInnerComplementDeviceId(connection);
1286     return connection->side == CONN_SIDE_CLIENT && IsSameDevice(connection->udid, option->udidClientOption.udid) &&
1287         ((BleProtocolType)option->udidClientOption.protocol == BLE_PROTOCOL_ANY ?
1288                 true :
1289                 connection->protocol == option->udidClientOption.protocol);
1290 }
1291 
GetConnectionByOption(const BleConnectionCompareOption * option)1292 static ConnBleConnection *GetConnectionByOption(const BleConnectionCompareOption *option)
1293 {
1294     BleConnectionCompareFunc compareFunc = NULL;
1295     switch (option->type) {
1296         case BLE_CONNECTION_COMPARE_TYPE_CONNECTION_ID:
1297             compareFunc = ConnectionCompareByConnectId;
1298             break;
1299         case BLE_CONNECTION_COMPARE_TYPE_ADDRESS:
1300             compareFunc = ConnectionCompareByAddress;
1301             break;
1302         case BLE_CONNECTION_COMPARE_TYPE_UNDERLAY_HANDLE:
1303             compareFunc = ConnectionCompareByUnderlayHandle;
1304             break;
1305         case BLE_CONNECTION_COMPARE_TYPE_UDID_IGNORE_ADDRESS:
1306             compareFunc = ConnectionCompareByUdidIgnoreAddress;
1307             break;
1308         case BLE_CONNECTION_COMPARE_TYPE_UDID_CLIENT_SIDE:
1309             compareFunc = ConnectionCompareByUdidClientSide;
1310             break;
1311         default:
1312             CONN_LOGW(
1313                 CONN_BLE, "there is no compare function implement for unkown type, type=%{public}d", option->type);
1314             return NULL;
1315     }
1316     int32_t status = SoftBusMutexLock(&g_bleManager.connections->lock);
1317     if (status != SOFTBUS_OK) {
1318         CONN_LOGE(CONN_BLE, "try to get manager connections lock failed, err=%{public}d", status);
1319         return NULL;
1320     }
1321     ConnBleConnection *it = NULL;
1322     ConnBleConnection *target = NULL;
1323     LIST_FOR_EACH_ENTRY(it, &g_bleManager.connections->list, ConnBleConnection, node) {
1324         if (compareFunc(it, option)) {
1325             target = it;
1326             break;
1327         }
1328     }
1329     if (target != NULL) {
1330         status = SoftBusMutexLock(&target->lock);
1331         if (status != SOFTBUS_OK) {
1332             CONN_LOGE(CONN_BLE, "try to get connection lock failed, err=%{public}d", status);
1333             SoftBusMutexUnlock(&g_bleManager.connections->lock);
1334             return NULL;
1335         }
1336         target->objectRc += 1;
1337         SoftBusMutexUnlock(&target->lock);
1338     }
1339     SoftBusMutexUnlock(&g_bleManager.connections->lock);
1340     return target;
1341 }
1342 
ConnBleGetConnectionByAddr(const char * addr,ConnSideType side,BleProtocolType protocol)1343 ConnBleConnection *ConnBleGetConnectionByAddr(const char *addr, ConnSideType side, BleProtocolType protocol)
1344 {
1345     CONN_CHECK_AND_RETURN_RET_LOGW(addr != NULL, NULL, CONN_BLE, "invalid param, ble addr is null");
1346     BleConnectionCompareOption option = {
1347         .type = BLE_CONNECTION_COMPARE_TYPE_ADDRESS,
1348         .addressOption = {
1349             .addr = addr,
1350             .side = side,
1351             .protocol = protocol,
1352         },
1353     };
1354     return GetConnectionByOption(&option);
1355 }
1356 
ConnBleGetConnectionById(uint32_t connectionId)1357 ConnBleConnection *ConnBleGetConnectionById(uint32_t connectionId)
1358 {
1359     BleConnectionCompareOption option = {
1360         .type = BLE_CONNECTION_COMPARE_TYPE_CONNECTION_ID,
1361         .connectionIdOption = {
1362             .connectionId = connectionId,
1363         },
1364     };
1365     return GetConnectionByOption(&option);
1366 }
1367 
ConnBleGetConnectionByHandle(int32_t underlayerHandle,ConnSideType side,BleProtocolType protocol)1368 ConnBleConnection *ConnBleGetConnectionByHandle(int32_t underlayerHandle, ConnSideType side, BleProtocolType protocol)
1369 {
1370     BleConnectionCompareOption option = {
1371         .type = BLE_CONNECTION_COMPARE_TYPE_UNDERLAY_HANDLE,
1372         .underlayerHandleOption = { .underlayerHandle = underlayerHandle, .side = side, .protocol = protocol },
1373     };
1374     return GetConnectionByOption(&option);
1375 }
1376 
ConnBleGetConnectionByUdid(const char * addr,const char * udid,BleProtocolType protocol)1377 ConnBleConnection *ConnBleGetConnectionByUdid(const char *addr, const char *udid, BleProtocolType protocol)
1378 {
1379     BleConnectionCompareOption option = {
1380         .type = BLE_CONNECTION_COMPARE_TYPE_UDID_IGNORE_ADDRESS,
1381         .udidAddressOption = {
1382             .addr = addr,
1383             .udid = udid,
1384             .protocol = protocol,
1385         },
1386     };
1387     return GetConnectionByOption(&option);
1388 }
1389 
ConnBleGetClientConnectionByUdid(const char * udid,BleProtocolType protocol)1390 ConnBleConnection *ConnBleGetClientConnectionByUdid(const char *udid, BleProtocolType protocol)
1391 {
1392     BleConnectionCompareOption option = {
1393         .type = BLE_CONNECTION_COMPARE_TYPE_UDID_CLIENT_SIDE,
1394         .udidClientOption = {
1395             .udid = udid,
1396             .protocol = protocol,
1397         },
1398     };
1399     return GetConnectionByOption(&option);
1400 }
1401 
ConnBleReturnConnection(ConnBleConnection ** connection)1402 void ConnBleReturnConnection(ConnBleConnection **connection)
1403 {
1404     CONN_CHECK_AND_RETURN_LOGW(connection != NULL, CONN_BLE, "invalid param, ble connnetion is null");
1405     CONN_CHECK_AND_RETURN_LOGW(
1406         *connection != NULL, CONN_BLE, "invalid param, ble *connnetion is null, use after return or remove action?");
1407 
1408     ConnBleConnection *underlayer = *connection;
1409     CONN_CHECK_AND_RETURN_LOGE(SoftBusMutexLock(&underlayer->lock) == SOFTBUS_OK, CONN_BLE,
1410         "ble connection lock failed. connectionId=%{public}u", underlayer->connectionId);
1411     underlayer->objectRc -= 1;
1412     int32_t objectRc = underlayer->objectRc;
1413     SoftBusMutexUnlock(&underlayer->lock);
1414     if (objectRc <= 0) {
1415         CONN_LOGI(CONN_BLE, "release ble connection. connectionId=%{public}u", underlayer->connectionId);
1416         ConnBleFreeConnection(*connection);
1417     }
1418     *connection = NULL;
1419 }
1420 
NotifyReusedConnected(uint32_t connectionId,uint16_t challengeCode)1421 void NotifyReusedConnected(uint32_t connectionId, uint16_t challengeCode)
1422 {
1423     ConnBleConnection *connection = ConnBleGetConnectionById(connectionId);
1424     CONN_CHECK_AND_RETURN_LOGW(connection != NULL, CONN_BLE, "connection not exist, connId=%{public}u", connectionId);
1425 
1426     ConnectionInfo info = { 0 };
1427     int32_t status = BleConvert2ConnectionInfo(connection, &info);
1428     if (status != SOFTBUS_OK) {
1429         CONN_LOGE(
1430             CONN_BLE, "convert connection info failed. It can not backoff now, just ahead. err=%{public}d", status);
1431     }
1432     info.bleInfo.challengeCode = challengeCode;
1433     g_connectCallback.OnReusedConnected(connectionId, &info);
1434 }
1435 
ConnBleKeepAlive(uint32_t connectionId,uint32_t requestId,uint32_t time)1436 int32_t ConnBleKeepAlive(uint32_t connectionId, uint32_t requestId, uint32_t time)
1437 {
1438     CONN_CHECK_AND_RETURN_RET_LOGW(time != 0 && time <= BLE_CONNECT_KEEP_ALIVE_TIMEOUT_MILLIS,
1439         SOFTBUS_INVALID_PARAM, CONN_BLE, "time is invaliad, time=%{public}u", time);
1440     ConnBleConnection *connection = ConnBleGetConnectionById(connectionId);
1441     CONN_CHECK_AND_RETURN_RET_LOGE(connection != NULL, SOFTBUS_CONN_BLE_INTERNAL_ERR, CONN_BLE,
1442         "connection not exist, connectionId=%{public}u", connectionId);
1443     int32_t status = ConnBleUpdateConnectionRc(connection, 0, 1);
1444     if (status != SOFTBUS_OK) {
1445         CONN_LOGE(CONN_BLE, "update rc failed, status=%{public}d, connectionId=%{public}u, requestId=%{public}u",
1446             status, connectionId, requestId);
1447         ConnBleReturnConnection(&connection);
1448         return SOFTBUS_CONN_BLE_INTERNAL_ERR;
1449     }
1450     ConnBleReturnConnection(&connection);
1451     ConnPostMsgToLooper(&g_bleManagerSyncHandler, BLE_MRG_MSG_KEEP_ALIVE_TIMEOUT, connectionId, requestId, NULL, time);
1452     CONN_LOGI(CONN_BLE, "ble keep alive success, duration time is %{public}u, connId=%{public}u", time, connectionId);
1453     return SOFTBUS_OK;
1454 }
1455 
ConnBleRemoveKeepAlive(uint32_t connectionId,uint32_t requestId)1456 int32_t ConnBleRemoveKeepAlive(uint32_t connectionId, uint32_t requestId)
1457 {
1458     ConnBleConnection *connection = ConnBleGetConnectionById(connectionId);
1459     CONN_CHECK_AND_RETURN_RET_LOGD(connection != NULL, SOFTBUS_CONN_BLE_INTERNAL_ERR, CONN_BLE,
1460         "connection not exist, connectionId=%{public}u", connectionId);
1461     bool isExist = false;
1462     ConnRemoveMsgFromLooper(
1463         &g_bleManagerSyncHandler, BLE_MRG_MSG_KEEP_ALIVE_TIMEOUT, connectionId, requestId, &isExist);
1464     int32_t status = SOFTBUS_CONN_BLE_INTERNAL_ERR;
1465     do {
1466         if (!isExist) {
1467             status = SOFTBUS_OK;
1468             break;
1469         }
1470         status = ConnBleUpdateConnectionRc(connection, 0, -1);
1471         if (status != SOFTBUS_OK) {
1472             CONN_LOGE(CONN_BLE, "update rc failed, status=%{public}d, connectionId=%{public}u, requestId=%{public}u",
1473                 status, connectionId, requestId);
1474             break;
1475         }
1476     } while (false);
1477     ConnBleReturnConnection(&connection);
1478     return status;
1479 }
1480 
TransitionToState(enum BleMgrState target)1481 static void TransitionToState(enum BleMgrState target)
1482 {
1483     static ConnBleState statesTable[BLE_MGR_STATE_MAX] = {
1484         [BLE_MGR_STATE_AVAILABLE] = {
1485             .name = BleNameAvailableState,
1486             .enter = BleEnterAvailableState,
1487             .exit = BleExitAvailableState,
1488             .connectRequest = BleConnectRequestOnAvailableState,
1489             .handlePendingRequest = BleHandlePendingRequestOnAvailableState,
1490             .serverAccepted = BleServerAccepted,
1491             .clientConnected = BleClientConnected,
1492             .clientConnectFailed = BleClientConnectFailed,
1493             .clientConnectTimeout = NULL,
1494             .dataReceived = BleDataReceived,
1495             .connectionClosed = BleConnectionClosed,
1496             .connectionResume = BleConnectionResume,
1497             .disconnectRequest = BleDisconnectRequest,
1498             .reuseConnectionRequest = BleReuseConnectionRequestOnAvailableState,
1499             .preventTimeout = BlePreventTimeout,
1500             .reset = BleReset,
1501             .keepAliveTimeout = BleKeepAliveTimeout,
1502         },
1503         [BLE_MGR_STATE_CONNECTING] = {
1504             .name = BleNameConnectingState,
1505             .enter = BleEnterConnectingState,
1506             .exit = BleExitConnectingState,
1507             .connectRequest = BleConnectRequestOnConnectingState,
1508             .handlePendingRequest = NULL,
1509             .serverAccepted = BleServerAccepted,
1510             .clientConnected = BleClientConnected,
1511             .clientConnectFailed = BleClientConnectFailed,
1512             .clientConnectTimeout = BleClientConnectTimeoutOnConnectingState,
1513             .dataReceived = BleDataReceived,
1514             .connectionClosed = BleConnectionClosed,
1515             .connectionResume = BleConnectionResume,
1516             .disconnectRequest = BleDisconnectRequest,
1517             .reuseConnectionRequest = BleReuseConnectionRequestOnConnectingState,
1518             .preventTimeout = BlePreventTimeout,
1519             .reset = BleReset,
1520             .keepAliveTimeout = BleKeepAliveTimeout,
1521         },
1522     };
1523 
1524     if (g_bleManager.state == statesTable + target) {
1525         return;
1526     }
1527     if (g_bleManager.state != NULL) {
1528         g_bleManager.state->exit();
1529     }
1530     g_bleManager.state = statesTable + target;
1531     g_bleManager.state->enter();
1532 }
1533 
1534 typedef struct {
1535     int32_t cmd;
1536     void (*func)(SoftBusMessage *msg);
1537 } MsgHandlerCommand;
1538 
HandlePendingRequestFunc(SoftBusMessage * msg)1539 static void HandlePendingRequestFunc(SoftBusMessage *msg)
1540 {
1541     (void)msg;
1542     if (g_bleManager.state->handlePendingRequest != NULL) {
1543         g_bleManager.state->handlePendingRequest();
1544         return;
1545     }
1546 }
1547 
ConnectRequestFunc(SoftBusMessage * msg)1548 static void ConnectRequestFunc(SoftBusMessage *msg)
1549 {
1550     if (g_bleManager.state->connectRequest == NULL) {
1551         return;
1552     }
1553     CONN_CHECK_AND_RETURN_LOGW(msg->obj != NULL, CONN_BLE, "obj is null");
1554     ConnBleConnectRequestContext *ctx = (ConnBleConnectRequestContext *)msg->obj;
1555     g_bleManager.state->connectRequest(ctx);
1556 }
1557 
ClientConnectedFunc(SoftBusMessage * msg)1558 static void ClientConnectedFunc(SoftBusMessage *msg)
1559 {
1560     if (g_bleManager.state->clientConnected != NULL) {
1561         g_bleManager.state->clientConnected((uint32_t)msg->arg1);
1562         return;
1563     }
1564 }
1565 
ClientConnectTimeoutFunc(SoftBusMessage * msg)1566 static void ClientConnectTimeoutFunc(SoftBusMessage *msg)
1567 {
1568     if (g_bleManager.state->clientConnectTimeout != NULL) {
1569         g_bleManager.state->clientConnectTimeout((uint32_t)msg->arg1, (char *)msg->obj);
1570         return;
1571     }
1572 }
1573 
ClientConnectFailedFunc(SoftBusMessage * msg)1574 static void ClientConnectFailedFunc(SoftBusMessage *msg)
1575 {
1576     if (g_bleManager.state->clientConnectFailed == NULL) {
1577         return;
1578     }
1579     CONN_CHECK_AND_RETURN_LOGW(msg->obj != NULL, CONN_BLE, "obj is null");
1580     BleStatusContext *ctx = (BleStatusContext *)(msg->obj);
1581     g_bleManager.state->clientConnectFailed(ctx->connectionId, ctx->status);
1582 }
1583 
ServerAcceptedFunc(SoftBusMessage * msg)1584 static void ServerAcceptedFunc(SoftBusMessage *msg)
1585 {
1586     if (g_bleManager.state->serverAccepted != NULL) {
1587         g_bleManager.state->serverAccepted((uint32_t)msg->arg1);
1588         return;
1589     }
1590 }
1591 
DataReceivedFunc(SoftBusMessage * msg)1592 static void DataReceivedFunc(SoftBusMessage *msg)
1593 {
1594     CONN_CHECK_AND_RETURN_LOGW(msg->obj != NULL, CONN_BLE, "obj is null");
1595     ConnBleDataReceivedContext *ctx = (ConnBleDataReceivedContext *)msg->obj;
1596     if (g_bleManager.state->dataReceived == NULL) {
1597         SoftBusFree(ctx->data);
1598         return;
1599     }
1600     g_bleManager.state->dataReceived(ctx);
1601 }
1602 
ConnectionClosedFunc(SoftBusMessage * msg)1603 static void ConnectionClosedFunc(SoftBusMessage *msg)
1604 {
1605     if (g_bleManager.state->connectionClosed == NULL) {
1606         return;
1607     }
1608     CONN_CHECK_AND_RETURN_LOGW(msg->obj != NULL, CONN_BLE, "obj is null");
1609     BleStatusContext *ctx = (BleStatusContext *)(msg->obj);
1610     g_bleManager.state->connectionClosed(ctx->connectionId, ctx->status);
1611 }
1612 
ConnectionResumeFunc(SoftBusMessage * msg)1613 static void ConnectionResumeFunc(SoftBusMessage *msg)
1614 {
1615     if (g_bleManager.state->connectionResume != NULL) {
1616         g_bleManager.state->connectionResume((uint32_t)msg->arg1);
1617         return;
1618     }
1619 }
1620 
DisconnectRequestFunc(SoftBusMessage * msg)1621 static void DisconnectRequestFunc(SoftBusMessage *msg)
1622 {
1623     if (g_bleManager.state->disconnectRequest != NULL) {
1624         g_bleManager.state->disconnectRequest((uint32_t)msg->arg1);
1625         return;
1626     }
1627 }
1628 
PreventTimeoutFunc(SoftBusMessage * msg)1629 static void PreventTimeoutFunc(SoftBusMessage *msg)
1630 {
1631     CONN_CHECK_AND_RETURN_LOGW(msg->obj != NULL, CONN_BLE, "obj is null");
1632     if (g_bleManager.state->preventTimeout != NULL) {
1633         char *udid = (char *)msg->obj;
1634         g_bleManager.state->preventTimeout(udid);
1635         return;
1636     }
1637 }
1638 
ResetFunc(SoftBusMessage * msg)1639 static void ResetFunc(SoftBusMessage *msg)
1640 {
1641     if (g_bleManager.state->reset == NULL) {
1642         return;
1643     }
1644     CONN_CHECK_AND_RETURN_LOGW(msg->obj != NULL, CONN_BLE, "obj is null");
1645     BleStatusContext *ctx = (BleStatusContext *)(msg->obj);
1646     g_bleManager.state->reset(ctx->status);
1647 }
1648 
KeepAliveTimeoutFunc(SoftBusMessage * msg)1649 static void KeepAliveTimeoutFunc(SoftBusMessage *msg)
1650 {
1651     if (g_bleManager.state->keepAliveTimeout != NULL) {
1652         g_bleManager.state->keepAliveTimeout((uint32_t)msg->arg1, (uint32_t)msg->arg2);
1653         return;
1654     }
1655 }
1656 
1657 static MsgHandlerCommand g_commands[] = {
1658     {BLE_MGR_MSG_NEXT_CMD, HandlePendingRequestFunc},
1659     {BLE_MGR_MSG_CONNECT_REQUEST, ConnectRequestFunc},
1660     {BLE_MGR_MSG_CONNECT_SUCCESS, ClientConnectedFunc},
1661     {BLE_MGR_MSG_CONNECT_TIMEOUT, ClientConnectTimeoutFunc},
1662     {BLE_MGR_MSG_CONNECT_FAIL, ClientConnectFailedFunc},
1663     {BLE_MGR_MSG_SERVER_ACCEPTED, ServerAcceptedFunc},
1664     {BLE_MGR_MSG_DATA_RECEIVED, DataReceivedFunc},
1665     {BLE_MGR_MSG_CONNECTION_CLOSED, ConnectionClosedFunc},
1666     {BLE_MGR_MSG_CONNECTION_RESUME, ConnectionResumeFunc},
1667     {BLE_MGR_MSG_DISCONNECT_REQUEST, DisconnectRequestFunc},
1668     {BLE_MGR_MSG_PREVENT_TIMEOUT, PreventTimeoutFunc},
1669     {BLE_MGR_MSG_RESET, ResetFunc},
1670     {BLE_MRG_MSG_KEEP_ALIVE_TIMEOUT, KeepAliveTimeoutFunc},
1671 };
1672 
BleManagerMsgHandler(SoftBusMessage * msg)1673 static void BleManagerMsgHandler(SoftBusMessage *msg)
1674 {
1675     CONN_CHECK_AND_RETURN_LOGW(msg != NULL, CONN_BLE, "msg is null");
1676     if (msg->what != BLE_MGR_MSG_DATA_RECEIVED && msg->what != BLE_MGR_MSG_NEXT_CMD &&
1677         msg->what != BLE_MGR_MSG_CONNECTION_CLOSED) {
1678         CONN_LOGI(CONN_BLE, "ble msg looper recv msg=%{public}d, curState=%{public}s",
1679             msg->what, g_bleManager.state->name());
1680     }
1681     size_t commandSize = sizeof(g_commands) / sizeof(g_commands[0]);
1682     for (size_t i = 0; i < commandSize; i++) {
1683         if (g_commands[i].cmd == msg->what) {
1684             g_commands[i].func(msg);
1685             return;
1686         }
1687     }
1688     CONN_LOGE(CONN_BLE,
1689         "ble manager looper receive unexpected msg just ignore, FIX it quickly. what=%{public}d", msg->what);
1690 }
1691 
BleCompareManagerLooperEventFunc(const SoftBusMessage * msg,void * args)1692 static int BleCompareManagerLooperEventFunc(const SoftBusMessage *msg, void *args)
1693 {
1694     SoftBusMessage *ctx = (SoftBusMessage *)args;
1695     if (msg->what != ctx->what) {
1696         return COMPARE_FAILED;
1697     }
1698     switch (ctx->what) {
1699         case BLE_MGR_MSG_CONNECT_TIMEOUT: {
1700             if (msg->arg1 == ctx->arg1) {
1701                 return COMPARE_SUCCESS;
1702             }
1703             return COMPARE_FAILED;
1704         }
1705         case BLE_MGR_MSG_PREVENT_TIMEOUT: {
1706             if (memcmp(msg->obj, ctx->obj, UDID_BUF_LEN) == 0) {
1707                 return COMPARE_SUCCESS;
1708             }
1709             return COMPARE_FAILED;
1710         }
1711         case BLE_MRG_MSG_KEEP_ALIVE_TIMEOUT: {
1712             if (msg->arg1 == ctx->arg1 && msg->arg2 == ctx->arg2) {
1713                 *(bool *)ctx->obj = true;
1714                 return COMPARE_SUCCESS;
1715             }
1716             return COMPARE_FAILED;
1717         }
1718         default:
1719             break;
1720     }
1721     if (ctx->arg1 != 0 || ctx->arg2 != 0 || ctx->obj != NULL) {
1722         CONN_LOGE(CONN_BLE,
1723             "there is compare context value not use, forgot implement? "
1724             "compare failed to avoid fault silence, what=%{public}d, arg1=%{public}" PRIu64 ", arg2=%{public}" PRIu64
1725             ", objIsNull=%{public}d",
1726             ctx->what, ctx->arg1, ctx->arg2, ctx->obj == NULL);
1727         return COMPARE_FAILED;
1728     }
1729     return COMPARE_SUCCESS;
1730 }
1731 
BleConnectDevice(const ConnectOption * option,uint32_t requestId,const ConnectResult * result)1732 static int32_t BleConnectDevice(const ConnectOption *option, uint32_t requestId, const ConnectResult *result)
1733 {
1734     CONN_CHECK_AND_RETURN_RET_LOGW(option != NULL, SOFTBUS_INVALID_PARAM, CONN_BLE,
1735         "ble connect device failed: option is null, reqId=%{public}u", requestId);
1736     CONN_CHECK_AND_RETURN_RET_LOGW(option->type == CONNECT_BLE, SOFTBUS_INVALID_PARAM, CONN_BLE,
1737         "ble connect device failed: not ble connect type, reqId=%{public}u, type=%{public}d", requestId, option->type);
1738     CONN_CHECK_AND_RETURN_RET_LOGW(result != NULL, SOFTBUS_INVALID_PARAM, CONN_BLE,
1739         "ble connect device failed: result callback is null, reqId=%{public}u", requestId);
1740     CONN_CHECK_AND_RETURN_RET_LOGW(result->OnConnectSuccessed != NULL, SOFTBUS_INVALID_PARAM, CONN_BLE,
1741         "ble connect device failed: result callback OnConnectSuccessed is null, reqId=%{public}u", requestId);
1742     CONN_CHECK_AND_RETURN_RET_LOGW(result->OnConnectFailed != NULL, SOFTBUS_INVALID_PARAM, CONN_BLE,
1743         "ble connect device failed: result callback onConnectFailed is null, reqId=%{public}u", requestId);
1744 
1745     // only use first SHORT_UDID_HASH_LEN bytes hash, keep same with share
1746     char udidHashStr[HEXIFY_LEN(SHORT_UDID_HASH_LEN)] = { 0 };
1747     int32_t status = ConvertBytesToHexString(udidHashStr, HEXIFY_LEN(SHORT_UDID_HASH_LEN),
1748         (unsigned char *)option->bleOption.deviceIdHash, SHORT_UDID_HASH_LEN);
1749     CONN_CHECK_AND_RETURN_RET_LOGW(status == SOFTBUS_OK, SOFTBUS_INVALID_PARAM, CONN_BLE,
1750         "ble connect device failed: convert device id hash to string failed, reqId=%{public}u, err=%{public}d",
1751         requestId, status);
1752 
1753     char anomizeAddress[BT_MAC_LEN] = { 0 };
1754     ConvertAnonymizeMacAddress(anomizeAddress, BT_MAC_LEN, option->bleOption.bleMac, BT_MAC_LEN);
1755     char anomizeUdid[UDID_BUF_LEN] = { 0 };
1756     ConvertAnonymizeSensitiveString(anomizeUdid, UDID_BUF_LEN, udidHashStr);
1757 
1758     ConnBleConnectRequestContext *ctx = SoftBusCalloc(sizeof(ConnBleConnectRequestContext));
1759     CONN_CHECK_AND_RETURN_RET_LOGE(ctx != NULL, SOFTBUS_MEM_ERR, CONN_BLE,
1760         "calloc connect request context object failed: reqId=%{public}u, addr=%{public}s, udid=%{public}s",
1761         requestId, anomizeAddress, anomizeUdid);
1762     ctx->statistics.startTime = SoftBusGetSysTimeMs();
1763     ctx->statistics.connectTraceId = SoftbusGetConnectTraceId();
1764     ctx->requestId = requestId;
1765     if (strcpy_s(ctx->addr, BT_MAC_LEN, option->bleOption.bleMac) != EOK ||
1766         strcpy_s(ctx->udid, UDID_BUF_LEN, udidHashStr) != EOK) {
1767         CONN_LOGE(CONN_BLE,
1768             "strcpy_s address or device identifier failed, reqId=%{public}u, addr=%{public}s, udid=%{public}s",
1769             requestId, anomizeAddress, anomizeUdid);
1770         SoftBusFree(ctx);
1771         return SOFTBUS_STRCPY_ERR;
1772     }
1773     ctx->fastestConnectEnable = option->bleOption.fastestConnectEnable;
1774     ctx->result = *result;
1775     // keep compatibility if protocol is undefined
1776     if (option->bleOption.protocol != BLE_GATT && option->bleOption.protocol != BLE_COC) {
1777         CONN_LOGW(CONN_BLE, "ble connect device warning, protocol is unknown, use GATT forcely. protocol=%{public}d",
1778             option->bleOption.protocol);
1779         ctx->protocol = BLE_GATT;
1780         ctx->psm = 0;
1781     } else {
1782         ctx->protocol = option->bleOption.protocol;
1783         ctx->psm = option->bleOption.psm;
1784     }
1785     ctx->challengeCode = option->bleOption.challengeCode;
1786     CONN_LOGI(CONN_BLE,
1787         "ble connect device: receive connect request, "
1788         "reqId=%{public}u, addr=%{public}s, protocol=%{public}d, udid=%{public}s, "
1789         "fastestConnectEnable=%{public}d, connectTraceId=%{public}u",
1790         requestId, anomizeAddress, ctx->protocol, anomizeUdid, ctx->fastestConnectEnable,
1791         ctx->statistics.connectTraceId);
1792     status = ConnPostMsgToLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_CONNECT_REQUEST, 0, 0, ctx, 0);
1793     if (status != SOFTBUS_OK) {
1794         CONN_LOGE(CONN_BLE,
1795             "post connect msg to manager looper failed, "
1796             "reqId=%{public}u, addr=%{public}s, udid=%{public}s, err=%{public}d",
1797             requestId, anomizeAddress, anomizeUdid, status);
1798         SoftBusFree(ctx);
1799         return status;
1800     }
1801     ConnEventExtra extra = {
1802         .connProtocol = option->bleOption.protocol,
1803         .peerBleMac = option->bleOption.bleMac,
1804         .peerUdid = anomizeUdid,
1805         .linkType = CONNECT_BLE,
1806         .requestId = (int32_t)requestId,
1807         .result = EVENT_STAGE_RESULT_OK
1808     };
1809     CONN_EVENT(EVENT_SCENE_CONNECT, EVENT_STAGE_CONNECT_DEVICE, extra);
1810     return SOFTBUS_OK;
1811 }
1812 
ConnBlePostBytes(uint32_t connectionId,uint8_t * data,uint32_t dataLen,int32_t pid,int32_t flag,int32_t module,int64_t seq)1813 static int32_t ConnBlePostBytes(
1814     uint32_t connectionId, uint8_t *data, uint32_t dataLen, int32_t pid, int32_t flag, int32_t module, int64_t seq)
1815 {
1816     return ConnBlePostBytesInner(connectionId, data, dataLen, pid, flag, module, seq, NULL);
1817 }
1818 
BleDisconnectDevice(uint32_t connectionId)1819 static int32_t BleDisconnectDevice(uint32_t connectionId)
1820 {
1821     ConnBleConnection *connection = ConnBleGetConnectionById(connectionId);
1822     CONN_CHECK_AND_RETURN_RET_LOGW(connection != NULL, SOFTBUS_CONN_BLE_CONNECTION_NOT_EXIST_ERR, CONN_BLE,
1823         "ble disconnect device failed: connection is not exist, reqId=%{public}u", connectionId);
1824     char animizeAddress[BT_MAC_LEN] = { 0 };
1825     ConvertAnonymizeMacAddress(animizeAddress, BT_MAC_LEN, connection->addr, BT_MAC_LEN);
1826     ConnBleReturnConnection(&connection);
1827 
1828     int32_t status =
1829         ConnPostMsgToLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_DISCONNECT_REQUEST, connectionId, 0, NULL, 0);
1830     CONN_LOGI(CONN_BLE, "ble disconnect device, connId=%{public}u, addr=%{public}s, status=%{public}d",
1831         connectionId, animizeAddress, status);
1832     return status;
1833 }
1834 
BleDisconnectDeviceNow(const ConnectOption * option)1835 static int32_t BleDisconnectDeviceNow(const ConnectOption *option)
1836 {
1837     CONN_CHECK_AND_RETURN_RET_LOGW(option != NULL, SOFTBUS_INVALID_PARAM, CONN_BLE,
1838         "ble disconnect device now failed: invaliad param, option is null");
1839     CONN_CHECK_AND_RETURN_RET_LOGW(option->type == CONNECT_BLE, SOFTBUS_INVALID_PARAM, CONN_BLE,
1840         "ble disconnect device now failed: invaliad param, not ble connect type. type=%{public}d", option->type);
1841 
1842     char animizeAddress[BT_MAC_LEN] = { 0 };
1843     ConvertAnonymizeMacAddress(animizeAddress, BT_MAC_LEN, option->bleOption.bleMac, BT_MAC_LEN);
1844     CONN_LOGI(CONN_BLE, "ble disconnect device now, addr=%{public}s", animizeAddress);
1845 
1846     ConnBleConnection *connection =
1847         ConnBleGetConnectionByAddr(option->bleOption.bleMac, CONN_SIDE_ANY, option->bleOption.protocol);
1848     CONN_CHECK_AND_RETURN_RET_LOGW(connection != NULL, SOFTBUS_CONN_BLE_CONNECTION_NOT_EXIST_ERR, CONN_BLE,
1849         "ble disconnect device now failed: connection is not exist");
1850 
1851     int32_t status = ConnBleDisconnectNow(connection, BLE_DISCONNECT_REASON_FORCELY);
1852     ConnBleReturnConnection(&connection);
1853     return status;
1854 }
1855 
BleGetConnectionInfo(uint32_t connectionId,ConnectionInfo * info)1856 static int32_t BleGetConnectionInfo(uint32_t connectionId, ConnectionInfo *info)
1857 {
1858     CONN_CHECK_AND_RETURN_RET_LOGW(info != NULL, SOFTBUS_INVALID_PARAM, CONN_BLE, "invaliad param, info is null");
1859     ConnBleConnection *connection = ConnBleGetConnectionById(connectionId);
1860     CONN_CHECK_AND_RETURN_RET_LOGW(connection != NULL, SOFTBUS_CONN_BLE_CONNECTION_NOT_EXIST_ERR, CONN_BLE,
1861         "connection is not exist, connId=%{public}u", connectionId);
1862 
1863     int32_t status = BleConvert2ConnectionInfo(connection, info);
1864     ConnBleReturnConnection(&connection);
1865     return status;
1866 }
1867 
BleStartLocalListening(const LocalListenerInfo * info)1868 static int32_t BleStartLocalListening(const LocalListenerInfo *info)
1869 {
1870     (void)info;
1871     return ConnBleStartServer();
1872 }
1873 
BleStopLocalListening(const LocalListenerInfo * info)1874 static int32_t BleStopLocalListening(const LocalListenerInfo *info)
1875 {
1876     (void)info;
1877     return ConnBleStopServer();
1878 }
1879 
BleCheckActiveConnection(const ConnectOption * option,bool needOccupy)1880 static bool BleCheckActiveConnection(const ConnectOption *option, bool needOccupy)
1881 {
1882     CONN_CHECK_AND_RETURN_RET_LOGW(option != NULL, false, CONN_BLE, "invaliad param, option is null");
1883     CONN_CHECK_AND_RETURN_RET_LOGW(
1884         option->type == CONNECT_BLE, false, CONN_BLE, "invaliad param, option->type is not ble, type=%{public}d",
1885         option->type);
1886     char hashStr[HEXIFY_LEN(SHORT_UDID_HASH_LEN)] = { 0 };
1887     if (ConvertBytesToHexString(hashStr, HEXIFY_LEN(SHORT_UDID_HASH_LEN),
1888         (unsigned char *)option->bleOption.deviceIdHash, SHORT_UDID_HASH_LEN) != SOFTBUS_OK) {
1889         CONN_LOGE(CONN_BLE, "convert bytes to array failed");
1890         return false;
1891     }
1892     ConnBleConnection *connection = ConnBleGetConnectionByUdid(NULL, hashStr, option->bleOption.protocol);
1893     CONN_CHECK_AND_RETURN_RET_LOGW(
1894         connection != NULL, false, CONN_BLE, "ble check action connection: connection is not exist");
1895     bool isActive = (connection->state == BLE_CONNECTION_STATE_EXCHANGED_BASIC_INFO);
1896     if (isActive && needOccupy) {
1897         ConnBleRefreshIdleTimeout(connection);
1898         ConnBleOccupy(connection);
1899     }
1900     ConnBleReturnConnection(&connection);
1901     return isActive;
1902 }
1903 
BleUpdateConnection(uint32_t connectionId,UpdateOption * option)1904 static int32_t BleUpdateConnection(uint32_t connectionId, UpdateOption *option)
1905 {
1906     CONN_CHECK_AND_RETURN_RET_LOGW(option != NULL, SOFTBUS_INVALID_PARAM, CONN_BLE, "invaliad param, option is null");
1907     CONN_CHECK_AND_RETURN_RET_LOGW(option->type == CONNECT_BLE, SOFTBUS_INVALID_PARAM, CONN_BLE,
1908         "invaliad param, not ble connect type. type=%{public}d", option->type);
1909     CONN_LOGI(CONN_BLE, "priority=%{public}d", option->bleOption.priority);
1910 
1911     ConnBleConnection *connection = ConnBleGetConnectionById(connectionId);
1912     CONN_CHECK_AND_RETURN_RET_LOGW(connection != NULL, SOFTBUS_CONN_BLE_CONNECTION_NOT_EXIST_ERR, CONN_BLE,
1913         "connection is not exist, connId=%{public}u", connectionId);
1914 
1915     int32_t status = ConnBleUpdateConnectionPriority(connection, option->bleOption.priority);
1916     ConnBleReturnConnection(&connection);
1917     return status;
1918 }
1919 
OnServerAccepted(uint32_t connectionId)1920 static void OnServerAccepted(uint32_t connectionId)
1921 {
1922     ConnPostMsgToLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_SERVER_ACCEPTED, connectionId, 0, NULL, 0);
1923 }
1924 
OnConnected(uint32_t connectionId)1925 static void OnConnected(uint32_t connectionId)
1926 {
1927     ConnPostMsgToLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_CONNECT_SUCCESS, connectionId, 0, NULL, 0);
1928 }
1929 
OnConnectFailed(uint32_t connectionId,int32_t error)1930 static void OnConnectFailed(uint32_t connectionId, int32_t error)
1931 {
1932     CONN_LOGW(CONN_BLE,
1933         "receive ble client connect failed notify, connId=%{public}u, err=%{public}d", connectionId, error);
1934     BleStatusContext *ctx = (BleStatusContext *)SoftBusCalloc(sizeof(BleStatusContext));
1935     CONN_CHECK_AND_RETURN_LOGW(ctx != NULL, CONN_BLE, "on connect failed failed, calloc error context failed");
1936     ctx->connectionId = connectionId;
1937     ctx->status = error;
1938     int32_t ret = ConnPostMsgToLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_CONNECT_FAIL, 0, 0, ctx, 0);
1939     if (ret != SOFTBUS_OK) {
1940         CONN_LOGE(CONN_BLE,
1941             "post msg to looper failed, connectionId=%{public}u, error=%{public}d", connectionId, ret);
1942         SoftBusFree(ctx);
1943     }
1944 }
1945 
OnDataReceived(uint32_t connectionId,bool isConnCharacteristic,uint8_t * data,uint32_t dataLen)1946 static void OnDataReceived(uint32_t connectionId, bool isConnCharacteristic, uint8_t *data, uint32_t dataLen)
1947 {
1948     ConnBleDataReceivedContext *ctx = SoftBusCalloc(sizeof(ConnBleDataReceivedContext));
1949     if (ctx == NULL) {
1950         CONN_LOGE(CONN_BLE,
1951             "calloc data received context failed, "
1952             "connectionId=%{public}u, isConnCharacteristic=%{public}d, dataLen=%{public}u",
1953             connectionId, isConnCharacteristic, dataLen);
1954         SoftBusFree(data);
1955         return;
1956     }
1957     ctx->connectionId = connectionId;
1958     ctx->isConnCharacteristic = isConnCharacteristic;
1959     ctx->data = data;
1960     ctx->dataLen = dataLen;
1961     int32_t status = ConnPostMsgToLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_DATA_RECEIVED, 0, 0, ctx, 0);
1962     if (status != SOFTBUS_OK) {
1963         CONN_LOGE(CONN_BLE,
1964             "post msg to looper failed, connectionId=%{public}u, isConnCharacteristic=%{public}d, dataLen=%{public}u",
1965             connectionId, isConnCharacteristic, dataLen);
1966         SoftBusFree(data);
1967         SoftBusFree(ctx);
1968     }
1969 }
1970 
OnConnectionClosed(uint32_t connectionId,int32_t status)1971 static void OnConnectionClosed(uint32_t connectionId, int32_t status)
1972 {
1973     BleStatusContext *ctx = SoftBusCalloc(sizeof(BleStatusContext));
1974     CONN_CHECK_AND_RETURN_LOGW(ctx != NULL, CONN_BLE, "on connect failed failed, calloc error context failed");
1975     ctx->connectionId = connectionId;
1976     ctx->status = status;
1977     int32_t ret = ConnPostMsgToLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_CONNECTION_CLOSED, 0, 0, ctx, 0);
1978     if (ret != SOFTBUS_OK) {
1979         CONN_LOGE(CONN_BLE,
1980             "post msg to looper failed, connectionId=%{public}u, error=%{public}d", connectionId, ret);
1981         SoftBusFree(ctx);
1982     }
1983 }
1984 
OnConnectionResume(uint32_t connectionId)1985 static void OnConnectionResume(uint32_t connectionId)
1986 {
1987     ConnPostMsgToLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_CONNECTION_RESUME, connectionId, 0, NULL, 0);
1988 }
1989 
onPostBytesFinished(uint32_t connectionId,uint32_t len,int32_t pid,int32_t flag,int32_t module,int64_t seq,int32_t error)1990 static void onPostBytesFinished(
1991     uint32_t connectionId, uint32_t len, int32_t pid, int32_t flag, int32_t module, int64_t seq, int32_t error)
1992 {
1993     CONN_LOGD(CONN_BLE,
1994         "ble post bytes finished, connId=%{public}u, pid=%{public}u, "
1995         "Len=%{public}u, Flg=%{public}d, Module=%{public}d, Seq=%{public}" PRId64 ", err=%{public}d",
1996         connectionId, pid, len, flag, module, seq, error);
1997 
1998     if (error != SOFTBUS_OK) {
1999         ConnBleConnection *connection = ConnBleGetConnectionById(connectionId);
2000         if (connection == NULL) {
2001             // maybe fail reason is that connection not exist, so log level is warning
2002             CONN_LOGW(CONN_BLE, "ble post bytes finished, send failed, connection not exist, connId=%{public}u",
2003                 connectionId);
2004             return;
2005         }
2006         ConnBleDisconnectNow(connection, BLE_DISCONNECT_REASON_POST_BYTES_FAILED);
2007         ConnBleReturnConnection(&connection);
2008     }
2009 }
2010 
OnBtStateChanged(int listenerId,int state)2011 static void OnBtStateChanged(int listenerId, int state)
2012 {
2013     (void)listenerId;
2014     int32_t status = SOFTBUS_OK;
2015     if (state == SOFTBUS_BLE_STATE_TURN_ON) {
2016         status = ConnBleStartServer();
2017         CONN_LOGI(CONN_BLE, "ble manager receive bt on event, start server, status=%{public}d", status);
2018         return;
2019     }
2020 
2021     if (state == SOFTBUS_BLE_STATE_TURN_OFF) {
2022         status = ConnBleStopServer();
2023         CONN_LOGI(CONN_BLE, "ble manager receive bt off event, stop server, status=%{public}d", status);
2024         BleStatusContext *ctx = SoftBusCalloc(sizeof(BleStatusContext));
2025         if (ctx == NULL) {
2026             CONN_LOGE(CONN_BLE,
2027                 "ble manager receive bt off event, send reset event failed: calloc ctx object failed");
2028             return;
2029         }
2030         ctx->status = SOFTBUS_CONN_BLUETOOTH_OFF;
2031         status = ConnPostMsgToLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_RESET, 0, 0, ctx, 0);
2032         if (status != SOFTBUS_OK) {
2033             CONN_LOGE(CONN_BLE,
2034                 "ble manager receive bt off event, send reset event failed: post msg to looper failed");
2035             SoftBusFree(ctx);
2036         }
2037         return;
2038     }
2039 }
2040 
2041 // reuse connected or connecting connection, MUST NOT request connect
ConflictReuseConnection(const char * address,const char * udid,uint32_t requestId)2042 static int32_t ConflictReuseConnection(const char *address, const char *udid, uint32_t requestId)
2043 {
2044     CONN_CHECK_AND_RETURN_RET_LOGW(address != NULL, SOFTBUS_INVALID_PARAM, CONN_BLE,
2045         "conflict reuse connection failed: invalid param, address is null");
2046     CONN_CHECK_AND_RETURN_RET_LOGW(
2047         udid != NULL, SOFTBUS_INVALID_PARAM, CONN_BLE, "conflict reuse connection failed: invalid param, udid is null");
2048 
2049     char anomizeAddress[BT_MAC_LEN] = { 0 };
2050     ConvertAnonymizeMacAddress(anomizeAddress, BT_MAC_LEN, address, BT_MAC_LEN);
2051     char anomizeUdid[UDID_BUF_LEN] = { 0 };
2052     ConvertAnonymizeSensitiveString(anomizeUdid, UDID_BUF_LEN, udid);
2053     CONN_LOGW(CONN_BLE,
2054         "conflict reuse connection, receive reuse request, reqId=%{public}u, addr=%{public}s, udid=%{public}s",
2055         requestId, anomizeAddress, anomizeUdid);
2056 
2057     size_t addressLen = strlen(address);
2058     size_t udidLen = strlen(udid);
2059     ConnBleReuseConnectionContext ctx = { 0 };
2060     if (memcpy_s(ctx.addr, BT_MAC_LEN - 1, address, addressLen) != EOK ||
2061         memcpy_s(ctx.udid, UDID_BUF_LEN - 1, udid, udidLen) != EOK) {
2062         CONN_LOGE(CONN_BLE,
2063             "memcpy_s address or udid failed, "
2064             "addressLen=%{public}zu, udidLen=%{public}zu, reqId=%{public}u, addr=%{public}s, udid=%{public}s",
2065             addressLen, udidLen, requestId, anomizeAddress, anomizeUdid);
2066         return SOFTBUS_MEM_ERR;
2067     }
2068     ctx.requestId = requestId;
2069     ctx.protocol = BLE_GATT;
2070 
2071     if (g_bleManager.state->reuseConnectionRequest == NULL) {
2072         CONN_LOGE(CONN_BLE, "reuseConnectionRequest is null");
2073         return SOFTBUS_CONN_BLE_REUSE_FAILED;
2074     }
2075     int32_t result = g_bleManager.state->reuseConnectionRequest(&ctx);
2076     CONN_LOGE(CONN_BLE,
2077         "conflict reuse connection, reqId=%{public}u, addr=%{public}s, udid=%{public}s, result=%{public}d",
2078         requestId, anomizeAddress, anomizeUdid, result);
2079     return result;
2080 }
2081 
ConflictPostBytes(int32_t underlayHandle,uint8_t * data,uint32_t dataLen)2082 static bool ConflictPostBytes(int32_t underlayHandle, uint8_t *data, uint32_t dataLen)
2083 {
2084     static int64_t conflictSeqGenerator = 0;
2085 
2086     CONN_CHECK_AND_RETURN_RET_LOGW(data != NULL, false, CONN_BLE, "conflict post bytes failed: data is null");
2087     CONN_CHECK_AND_RETURN_RET_LOGW(dataLen != 0, false, CONN_BLE, "conflict post bytes failed: data length is 0");
2088 
2089     ConnBleConnection *connection = ConnBleGetConnectionByHandle(underlayHandle, CONN_SIDE_ANY, BLE_GATT);
2090     CONN_CHECK_AND_RETURN_RET_LOGW(connection != NULL, false, CONN_BLE,
2091         "conflict post bytes failed: connection not exist, underlayHandle=%{public}d", underlayHandle);
2092     uint32_t connectionId = connection->connectionId;
2093     ConnBleReturnConnection(&connection);
2094 
2095     uint32_t payloadLen = ConnGetHeadSize() + dataLen;
2096     uint8_t *payload = SoftBusCalloc(payloadLen);
2097     CONN_CHECK_AND_RETURN_RET_LOGE(payload != NULL, false, CONN_BLE,
2098         "conflict post bytes failed: alloc payload failed, underlayHandle=%{public}d", underlayHandle);
2099 
2100     uint32_t seq = conflictSeqGenerator++;
2101     ConnPktHead *head = (ConnPktHead *)payload;
2102     head->magic = MAGIC_NUMBER;
2103     head->flag = 0;
2104     head->module = MODULE_OLD_NEARBY;
2105     head->len = dataLen;
2106     head->seq = seq;
2107     PackConnPktHead(head);
2108     if (memcpy_s(payload + ConnGetHeadSize(), payloadLen - ConnGetHeadSize(), data, dataLen) != EOK) {
2109         SoftBusFree(payload);
2110         return false;
2111     }
2112     return ConnBlePostBytesInner(connectionId, payload, payloadLen, 0, 0, MODULE_OLD_NEARBY, seq, NULL) == SOFTBUS_OK;
2113 }
2114 
ConflictDisconnect(int32_t handle,bool isForce)2115 static void ConflictDisconnect(int32_t handle, bool isForce)
2116 {
2117     CONN_LOGW(CONN_BLE,
2118         "conflict disconnect, receive disconnect request, handle=%{public}d, isForce=%{public}d", handle, isForce);
2119     ConnBleConnection *connection = ConnBleGetConnectionByHandle(handle, CONN_SIDE_ANY, BLE_GATT);
2120     CONN_CHECK_AND_RETURN_LOGW(
2121         connection != NULL, CONN_BLE, "conflict disconnect failed: connection not exist, handle=%{public}d", handle);
2122     if (isForce) {
2123         ConnBleDisconnectNow(connection, BLE_DISCONNECT_REASON_CONFLICT);
2124     } else {
2125         BleDisconnectDevice(connection->connectionId);
2126     }
2127     ConnBleReturnConnection(&connection);
2128 }
2129 
ConflictOccupy(const char * udid,int32_t timeout)2130 static void ConflictOccupy(const char *udid, int32_t timeout)
2131 {
2132     CONN_CHECK_AND_RETURN_LOGW(udid != NULL, CONN_BLE, "conflict occupy failed: invalid param, udid is null");
2133     CONN_CHECK_AND_RETURN_LOGW(timeout > 0, CONN_BLE,
2134         "conflict occupy failed: invalid param, timeout=%{public}d", timeout);
2135 
2136     char anomizeUdid[UDID_BUF_LEN] = { 0 };
2137     ConvertAnonymizeSensitiveString(anomizeUdid, UDID_BUF_LEN, udid);
2138     CONN_LOGW(CONN_BLE, "receive conflict occupy, udid=%{public}s, timeout=%{public}d", anomizeUdid, timeout);
2139 
2140     CONN_CHECK_AND_RETURN_LOGE(SoftBusMutexLock(&g_bleManager.prevents->lock) == SOFTBUS_OK, CONN_BLE,
2141         "ATTENTION UNEXPECTED ERROR! conflict occupy failed: try to lock failed, udid=%{public}s", anomizeUdid);
2142     do {
2143         char *copyUdid = SoftBusCalloc(UDID_BUF_LEN);
2144         if (copyUdid == NULL) {
2145             CONN_LOGE(CONN_BLE, "calloc udid failed, udid=%{public}s", anomizeUdid);
2146             break;
2147         }
2148         size_t udidLen = strlen(udid);
2149         if (memcpy_s(copyUdid, UDID_BUF_LEN - 1, udid, udidLen) != EOK) {
2150             CONN_LOGE(CONN_BLE,
2151                 "memcpy_s udid failed, sourceLen=%{public}zu, destinationLen=%{public}u, udid=%{public}s",
2152                 udidLen, UDID_BUF_LEN, anomizeUdid);
2153             SoftBusFree(copyUdid);
2154             break;
2155         }
2156         BlePrevent *exist = NULL;
2157         BlePrevent *it = NULL;
2158         LIST_FOR_EACH_ENTRY(it, &g_bleManager.prevents->list, BlePrevent, node) {
2159             if (udidLen == strlen((char *)it->udid) && memcmp(udid, it->udid, udidLen) == 0) {
2160                 exist = it;
2161                 break;
2162             }
2163         }
2164         int32_t ret = SOFTBUS_OK;
2165         if (exist != NULL) {
2166             CONN_LOGW(CONN_BLE, "dumplicate occupy, refresh timeout, udid=%{public}s", anomizeUdid);
2167             exist->timeout = timeout;
2168             ConnRemoveMsgFromLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_PREVENT_TIMEOUT, 0, 0, copyUdid);
2169             ret = ConnPostMsgToLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_PREVENT_TIMEOUT, 0, 0, copyUdid, timeout);
2170             if (ret != SOFTBUS_OK) {
2171                 CONN_LOGE(CONN_BLE, "post msg to looper failed, udid=%{public}s, error=%{public}d", anomizeUdid, ret);
2172                 SoftBusFree(copyUdid);
2173             }
2174             break;
2175         }
2176         BlePrevent *prevent = SoftBusCalloc(sizeof(BlePrevent));
2177         if (prevent == NULL) {
2178             SoftBusFree(copyUdid);
2179             CONN_LOGE(CONN_BLE, "calloc prevent object failed, udid=%{public}s", anomizeUdid);
2180             break;
2181         }
2182         if (memcpy_s(prevent->udid, UDID_BUF_LEN - 1, udid, udidLen) != EOK) {
2183             CONN_LOGE(CONN_BLE,
2184                 "memcpy_s udid to prevent object failed, sourceLen=%{public}zu, destinationLen=%{public}u, "
2185                 "udid=%{public}s", udidLen, UDID_BUF_LEN, anomizeUdid);
2186             SoftBusFree(copyUdid);
2187             SoftBusFree(prevent);
2188             break;
2189         }
2190         ListAdd(&g_bleManager.prevents->list, &prevent->node);
2191         g_bleManager.prevents->cnt++;
2192         ret = ConnPostMsgToLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_PREVENT_TIMEOUT, 0, 0, copyUdid, timeout);
2193         if (ret != SOFTBUS_OK) {
2194             CONN_LOGE(CONN_BLE, "post msg to looper failed, udid=%{public}s, error=%{public}d", anomizeUdid, ret);
2195             SoftBusFree(copyUdid);
2196             SoftBusFree(prevent);
2197             break;
2198         }
2199     } while (false);
2200     SoftBusMutexUnlock(&g_bleManager.prevents->lock);
2201     CONN_LOGI(CONN_BLE, "conflict occupy, add udid prevent done, udid=%{public}s", anomizeUdid);
2202 }
2203 
ConflictCancelOccupy(const char * udid)2204 static void ConflictCancelOccupy(const char *udid)
2205 {
2206     CONN_CHECK_AND_RETURN_LOGW(udid != NULL, CONN_BLE, "conflict cancel occupy failed: invalid param, udid is null");
2207 
2208     char anomizeUdid[UDID_BUF_LEN] = { 0 };
2209     ConvertAnonymizeSensitiveString(anomizeUdid, UDID_BUF_LEN, udid);
2210     CONN_LOGI(CONN_BLE, "conflict cancel occupy, udid=%{public}s", anomizeUdid);
2211 
2212     CONN_CHECK_AND_RETURN_LOGE(SoftBusMutexLock(&g_bleManager.prevents->lock) == SOFTBUS_OK, CONN_BLE,
2213         "ATTENTION UNEXPECTED ERROR! conflict cancel occupy failed: try to lock failed, udid=%{public}s", anomizeUdid);
2214     size_t udidLen = strlen(udid);
2215     BlePrevent *it = NULL;
2216     BlePrevent *next = NULL;
2217     LIST_FOR_EACH_ENTRY_SAFE(it, next, &g_bleManager.prevents->list, BlePrevent, node) {
2218         if (udidLen == strlen((char *)it->udid) && memcmp(udid, it->udid, udidLen) == 0) {
2219             g_bleManager.prevents->cnt--;
2220             ListDelete(&it->node);
2221             SoftBusFree(it);
2222             ConnRemoveMsgFromLooper(&g_bleManagerSyncHandler, BLE_MGR_MSG_PREVENT_TIMEOUT, 0, 0, (char *)udid);
2223             break;
2224         }
2225     }
2226     SoftBusMutexUnlock(&g_bleManager.prevents->lock);
2227 }
2228 
ConflictGetConnection(const char * udid)2229 static int32_t ConflictGetConnection(const char *udid)
2230 {
2231     CONN_CHECK_AND_RETURN_RET_LOGW(
2232         udid != NULL, SOFTBUS_INVALID_PARAM, CONN_BLE, "conflict get connection failed: invalid param, udid is null");
2233 
2234     char anomizeUdid[UDID_BUF_LEN] = { 0 };
2235     ConvertAnonymizeSensitiveString(anomizeUdid, UDID_BUF_LEN, udid);
2236     CONN_LOGI(CONN_BLE, "conflict get connection, udid=%{public}s", anomizeUdid);
2237 
2238     ConnBleConnection *connection = ConnBleGetClientConnectionByUdid(udid, BLE_GATT);
2239     CONN_CHECK_AND_RETURN_RET_LOGW(connection != NULL, SOFTBUS_CONN_BLE_CONNECTION_NOT_EXIST_ERR, CONN_BLE,
2240         "conflict get connection failed: connection not exist, udid=%{public}s", anomizeUdid);
2241     int32_t result = SOFTBUS_CONN_BLE_INTERNAL_ERR;
2242     do {
2243         if (SoftBusMutexLock(&connection->lock) != SOFTBUS_OK) {
2244             CONN_LOGE(CONN_BLE, "try to lock failed, connId=%{public}u, udid=%{public}s", connection->connectionId,
2245                 anomizeUdid);
2246             result = SOFTBUS_LOCK_ERR;
2247             break;
2248         }
2249         result = connection->underlayerHandle;
2250         SoftBusMutexUnlock(&connection->lock);
2251     } while (false);
2252     CONN_LOGI(CONN_BLE, "conflict get connection, connId=%{public}u, udid=%{public}s, result=%{public}d",
2253         connection->connectionId, anomizeUdid, result);
2254     ConnBleReturnConnection(&connection);
2255     return result;
2256 }
2257 
BleInitLooper(void)2258 static int32_t BleInitLooper(void)
2259 {
2260     g_bleManagerSyncHandler.handler.looper = GetLooper(LOOP_TYPE_CONN);
2261     if (g_bleManagerSyncHandler.handler.looper == NULL) {
2262         CONN_LOGE(CONN_INIT, "init conn ble looper failed");
2263         return SOFTBUS_NO_INIT;
2264     }
2265     return SOFTBUS_OK;
2266 }
2267 
InitBleManager(const ConnectCallback * callback)2268 static int32_t InitBleManager(const ConnectCallback *callback)
2269 {
2270     SoftBusList *connections = CreateSoftBusList();
2271     SoftBusList *prevents = CreateSoftBusList();
2272     CONN_CHECK_AND_RETURN_RET_LOGE(
2273         connections != NULL && prevents != NULL, SOFTBUS_CREATE_LIST_ERR,
2274         CONN_INIT, "init ble manager failed: create list failed");
2275     g_bleManager.connections = connections;
2276     g_bleManager.prevents = prevents;
2277     ListInit(&g_bleManager.waitings);
2278     g_bleManager.state = NULL;
2279     g_bleManager.connecting = NULL;
2280 
2281     static SoftBusBtStateListener btStateListener = {
2282         .OnBtAclStateChanged = NULL,
2283         .OnBtStateChanged = OnBtStateChanged,
2284     };
2285     int32_t listenerId = SoftBusAddBtStateListener(&btStateListener);
2286     CONN_CHECK_AND_RETURN_RET_LOGW(listenerId >= 0, SOFTBUS_INVALID_NUM, CONN_INIT,
2287         "int ble manager failed: add bluetooth state change listener failed, invalid listener id=%{public}d",
2288         listenerId);
2289     static SoftBusBleConflictListener bleConflictListener = {
2290         .reuseConnection = ConflictReuseConnection,
2291         .postBytes = ConflictPostBytes,
2292         .disconnect = ConflictDisconnect,
2293         .occupy = ConflictOccupy,
2294         .cancelOccupy = ConflictCancelOccupy,
2295         .getConnection = ConflictGetConnection,
2296     };
2297     SoftbusBleConflictRegisterListener(&bleConflictListener);
2298 
2299     g_connectCallback = *callback;
2300     TransitionToState(BLE_MGR_STATE_AVAILABLE);
2301     return SOFTBUS_OK;
2302 }
2303 
ConnInitBle(const ConnectCallback * callback)2304 ConnectFuncInterface *ConnInitBle(const ConnectCallback *callback)
2305 {
2306     CONN_CHECK_AND_RETURN_RET_LOGW(
2307         callback != NULL, NULL, CONN_INIT, "conn init ble failed: invalid param, callback is null");
2308     CONN_CHECK_AND_RETURN_RET_LOGW(callback->OnConnected != NULL, NULL, CONN_INIT,
2309         "conn init ble failed: invalid param, callback OnConnected  is null");
2310     CONN_CHECK_AND_RETURN_RET_LOGW(callback->OnDataReceived != NULL, NULL, CONN_INIT,
2311         "conn init ble failed: invalid param, callback OnDataReceived is null");
2312     CONN_CHECK_AND_RETURN_RET_LOGW(callback->OnDisconnected != NULL, NULL, CONN_INIT,
2313         "conn init ble failed: invalid param, callback OnDisconnected is null");
2314 
2315     int32_t status = BleInitLooper();
2316     CONN_CHECK_AND_RETURN_RET_LOGW(
2317         status == SOFTBUS_OK, NULL, CONN_INIT, "conn init ble failed: init ble manager looper failed, err=%{public}d",
2318         status);
2319 
2320     ConnBleConnectionEventListener connectionEventListener = {
2321         .onServerAccepted = OnServerAccepted,
2322         .onConnected = OnConnected,
2323         .onConnectFailed = OnConnectFailed,
2324         .onDataReceived = OnDataReceived,
2325         .onConnectionClosed = OnConnectionClosed,
2326         .onConnectionResume = OnConnectionResume,
2327     };
2328     status = ConnBleInitConnectionMudule(g_bleManagerSyncHandler.handler.looper, &connectionEventListener);
2329     CONN_CHECK_AND_RETURN_RET_LOGW(status == SOFTBUS_OK, NULL, CONN_INIT,
2330         "conn init ble failed: init ble connection mudule failed, err=%{public}d", status);
2331 
2332     ConnBleTransEventListener transEventListener = {
2333         .onPostBytesFinished = onPostBytesFinished,
2334     };
2335     status = ConnBleInitTransModule(&transEventListener);
2336     CONN_CHECK_AND_RETURN_RET_LOGW(status == SOFTBUS_OK, NULL, CONN_INIT,
2337         "conn init ble failed: init ble trans mudule failed, err=%{public}d", status);
2338     status = InitBleManager(callback);
2339     CONN_CHECK_AND_RETURN_RET_LOGW(status == SOFTBUS_OK, NULL, CONN_INIT,
2340         "conn init ble failed: init ble manager failed, err=%{public}d", status);
2341 
2342     static ConnectFuncInterface bleFuncInterface = {
2343         .ConnectDevice = BleConnectDevice,
2344         .PostBytes = ConnBlePostBytes,
2345         .DisconnectDevice = BleDisconnectDevice,
2346         .DisconnectDeviceNow = BleDisconnectDeviceNow,
2347         .GetConnectionInfo = BleGetConnectionInfo,
2348         .StartLocalListening = BleStartLocalListening,
2349         .StopLocalListening = BleStopLocalListening,
2350         .CheckActiveConnection = BleCheckActiveConnection,
2351         .UpdateConnection = BleUpdateConnection,
2352         .PreventConnection = NULL,
2353         .ConfigPostLimit = ConnBleTransConfigPostLimit,
2354     };
2355     CONN_LOGI(CONN_INIT, "conn init ble successfully");
2356     return &bleFuncInterface;
2357 }
2358 
LnnOnlineEventListener(const LnnEventBasicInfo * info)2359 static void LnnOnlineEventListener(const LnnEventBasicInfo *info)
2360 {
2361     CONN_CHECK_AND_RETURN_LOGW(info != NULL, CONN_BLE, "receive lnn online event, null info");
2362     CONN_CHECK_AND_RETURN_LOGW(info->event == LNN_EVENT_NODE_ONLINE_STATE_CHANGED, CONN_BLE,
2363         "receive lnn online event, unconcerned event=%{public}d", info->event);
2364 
2365     CONN_LOGI(CONN_BLE, "receive lnn online event, start auto-complementation coc connection udid");
2366     int32_t status = SoftBusMutexLock(&g_bleManager.connections->lock);
2367     CONN_CHECK_AND_RETURN_LOGE(status == SOFTBUS_OK, CONN_BLE,
2368         "complementation coc connection udid failed: try to lock connections failed, err=%{public}d", status);
2369 
2370     do {
2371         ConnBleConnection *it = NULL;
2372         LIST_FOR_EACH_ENTRY(it, &g_bleManager.connections->list, ConnBleConnection, node) {
2373             if (it->protocol == BLE_GATT) {
2374                 continue;
2375             }
2376             status = SoftBusMutexLock(&it->lock);
2377             if (status != SOFTBUS_OK) {
2378                 CONN_LOGE(CONN_BLE, "complementation coc connection udid failed: try to get connection "
2379                       "lock failed, connId=%{public}u, err=%{public}d", it->connectionId, status);
2380                 continue;
2381             }
2382             ConnBleInnerComplementDeviceId(it);
2383             (void)SoftBusMutexUnlock(&it->lock);
2384         }
2385     } while (false);
2386     (void)SoftBusMutexUnlock(&g_bleManager.connections->lock);
2387 }
2388 
2389 // register lnn online listener to complementation coc connection udid
DelayRegisterLnnOnlineListener(void)2390 static void DelayRegisterLnnOnlineListener(void)
2391 {
2392     static bool registered = false;
2393     if (registered) {
2394         return;
2395     }
2396 
2397     int32_t status = LnnRegisterEventHandler(LNN_EVENT_NODE_ONLINE_STATE_CHANGED, LnnOnlineEventListener);
2398     if (status != SOFTBUS_OK) {
2399         CONN_LOGE(CONN_BLE, "delay register lnn online listener failed, err=%{public}d", status);
2400         return;
2401     }
2402     registered = true;
2403     CONN_LOGI(CONN_BLE, "delay register lnn online listener successfully");
2404 }