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 }