1 /*
2 * Copyright (c) 2021-2024 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include <unistd.h>
17
18 #include "disc_manager.h"
19 #include "bus_center_event.h"
20 #include "common_list.h"
21 #include "disc_ble_dispatcher.h"
22 #include "disc_coap.h"
23 #include "disc_event.h"
24 #include "disc_log.h"
25 #include "disc_usb_dispatcher.h"
26 #include "securec.h"
27 #include "softbus_adapter_mem.h"
28 #include "softbus_adapter_thread.h"
29 #include "softbus_adapter_timer.h"
30 #include "softbus_def.h"
31 #include "softbus_error_code.h"
32 #include "softbus_json_utils.h"
33 #include "legacy/softbus_hisysevt_discreporter.h"
34 #include "lnn_devicename_info.h"
35 #include "softbus_utils.h"
36
37 #define SKIP_VALID_PID_VALUE (-1)
38 #define DEVICE_TYPE_SIZE_MAX 3
39 #define DUMP_STR_LEN 256
40 #define DISC_INFO_LIST_SIZE_MAX 1024
41 #define DISPLAY_NAME_BUF_LEN 128
42 #define DISPLAY_NAME_LEN_24 24
43 #define DISPLAY_NAME_LEN_21 21
44 #define DISPLAY_NAME_LEN_18 18
45 #define JSON_KEY_RAW_NAME "raw"
46 #define JSON_KEY_NAME_LEN_24 "name24"
47 #define JSON_KEY_NAME_LEN_21 "name21"
48 #define JSON_KEY_NAME_LEN_18 "name18"
49
50 static bool g_isInited = false;
51
52 static SoftBusList *g_publishInfoList = NULL;
53 static SoftBusList *g_discoveryInfoList = NULL;
54
55 static DiscoveryFuncInterface *g_discCoapInterface = NULL;
56 static DiscoveryFuncInterface *g_discBleInterface = NULL;
57 static DiscoveryFuncInterface *g_discUsbInterface = NULL;
58
59 static DiscInnerCallback g_discMgrMediumCb;
60
61 static ListNode g_capabilityList[CAPABILITY_MAX_BITNUM];
62
63 typedef struct {
64 char raw[DISPLAY_NAME_BUF_LEN];
65 char name18[DISPLAY_NAME_LEN_18 + 1];
66 char name21[DISPLAY_NAME_LEN_21 + 1];
67 char name24[DISPLAY_NAME_LEN_24 + 1];
68 } DisplayNameList;
69
70 static DisplayNameList g_displayName = { 0 };
71
72 static const char *g_discModuleMap[] = {
73 "MODULE_LNN",
74 "MODULE_CONN",
75 };
76
77 typedef enum {
78 MIN_SERVICE = 0,
79 PUBLISH_SERVICE = MIN_SERVICE,
80 PUBLISH_INNER_SERVICE = 1,
81 SUBSCRIBE_SERVICE = 2,
82 SUBSCRIBE_INNER_SERVICE = 3,
83 MAX_SERVICE = SUBSCRIBE_INNER_SERVICE,
84 } ServiceType;
85
86 typedef union {
87 PublishOption publishOption;
88 SubscribeOption subscribeOption;
89 } InnerOption;
90
91 typedef union {
92 IServerDiscInnerCallback serverCb;
93 DiscInnerCallback innerCb;
94 } InnerCallback;
95
96 typedef struct {
97 ListNode node;
98 char packageName[PKG_NAME_SIZE_MAX];
99 InnerCallback callback;
100 uint32_t infoNum;
101 ListNode InfoList;
102 } DiscItem;
103
104 typedef struct {
105 ListNode node;
106 int32_t id;
107 DiscoverMode mode;
108 ExchangeMedium medium;
109 ListNode capNode;
110 DiscItem *item;
111 DiscoveryStatistics statistics;
112 InnerOption option;
113 int32_t pid;
114 } DiscInfo;
115
116 typedef struct {
117 ListNode node;
118 int32_t id;
119 char *pkgName;
120 int32_t pid;
121 } IdContainer;
122
123 #define DFX_RECORD_DISC_CALL_START(infoNode, packageName, interfaceType) \
124 do { \
125 DiscEventExtra extra = { 0 }; \
126 DiscEventExtraInit(&extra); \
127 BuildDiscCallEvent(&extra, infoNode, packageName, interfaceType); \
128 DISC_EVENT(EVENT_SCENE_DISC, EVENT_STAGE_CALL_INTERFACE, extra); \
129 } while (0)
130
UpdateDiscEventAndReport(DiscEventExtra * extra,const DeviceInfo * device)131 static void UpdateDiscEventAndReport(DiscEventExtra *extra, const DeviceInfo *device)
132 {
133 if (device == NULL) {
134 DISC_EVENT(EVENT_SCENE_DISC, EVENT_STAGE_DEVICE_FOUND, *extra);
135 DISC_LOGI(DISC_CONTROL, "device info is null");
136 return;
137 }
138 if (device->addrNum <= CONNECTION_ADDR_WLAN || device->addrNum > CONNECTION_ADDR_MAX) {
139 DISC_EVENT(EVENT_SCENE_DISC, EVENT_STAGE_DEVICE_FOUND, *extra);
140 DISC_LOGI(DISC_CONTROL, "unknown device info");
141 return;
142 }
143
144 for (uint32_t i = 0; i < device->addrNum; i++) {
145 switch (device->addr[i].type) {
146 case CONNECTION_ADDR_BR:
147 extra->peerBrMac = device->addr[i].info.br.brMac;
148 break;
149 case CONNECTION_ADDR_BLE:
150 extra->peerBleMac = device->addr[i].info.ble.bleMac;
151 break;
152 case CONNECTION_ADDR_WLAN:
153 /* fall-through */
154 case CONNECTION_ADDR_ETH:
155 extra->peerIp = device->addr[i].info.ip.ip;
156 break;
157 default:
158 DISC_LOGI(DISC_CONTROL, "unknown param type!");
159 break;
160 }
161 }
162
163 char *deviceType = SoftBusCalloc(DEVICE_TYPE_SIZE_MAX + 1);
164 DISC_CHECK_AND_RETURN_LOGE(deviceType != NULL, DISC_CONTROL, "SoftBusCalloc failed");
165 if (snprintf_s(deviceType, DEVICE_TYPE_SIZE_MAX + 1, DEVICE_TYPE_SIZE_MAX, "%03X", device->devType) >= 0) {
166 extra->peerDeviceType = deviceType;
167 }
168 DISC_EVENT(EVENT_SCENE_DISC, EVENT_STAGE_DEVICE_FOUND, *extra);
169 SoftBusFree(deviceType);
170 extra->peerDeviceType = NULL;
171 }
172
DfxRecordStartDiscoveryDevice(DiscInfo * infoNode)173 static void DfxRecordStartDiscoveryDevice(DiscInfo *infoNode)
174 {
175 infoNode->statistics.startTime = SoftBusGetSysTimeMs();
176 infoNode->statistics.repTimes = 0;
177 infoNode->statistics.devNum = 0;
178 infoNode->statistics.discTimes = 0;
179 }
180
UpdateDdmpStartDiscoveryTime(DiscInfo * info)181 static void UpdateDdmpStartDiscoveryTime(DiscInfo *info)
182 {
183 if (info->medium != AUTO && info->medium != COAP) {
184 DISC_LOGD(DISC_CONTROL, "no need update ddmp start discovery time");
185 return;
186 }
187
188 DiscInfo *infoNode = NULL;
189 LIST_FOR_EACH_ENTRY(infoNode, &(g_capabilityList[DDMP_CAPABILITY_BITMAP]), DiscInfo, capNode) {
190 if (infoNode->statistics.repTimes == 0) {
191 DISC_LOGD(DISC_CONTROL, "update ddmp callback id=%{public}d", infoNode->id);
192 infoNode->statistics.startTime = info->statistics.startTime;
193 }
194 }
195 }
196
DfxRecordDeviceFound(DiscInfo * infoNode,const DeviceInfo * device,const InnerDeviceInfoAddtions * additions)197 static void DfxRecordDeviceFound(DiscInfo *infoNode, const DeviceInfo *device, const InnerDeviceInfoAddtions *additions)
198 {
199 DISC_LOGD(DISC_CONTROL, "record device found");
200 if (infoNode->statistics.repTimes == 0) {
201 uint64_t costTime = 0;
202 uint64_t sysTime = SoftBusGetSysTimeMs();
203 if (sysTime >= infoNode->statistics.startTime) {
204 costTime = sysTime - infoNode->statistics.startTime;
205 } else {
206 DISC_LOGE(DISC_CONTROL, "CurTime < startTime");
207 }
208 SoftbusRecordFirstDiscTime((SoftBusDiscMedium)additions->medium, costTime);
209 DiscEventExtra extra = { 0 };
210 DiscEventExtraInit(&extra);
211 extra.discMode = infoNode == NULL ? 0 : infoNode->mode;
212 extra.discType = additions == NULL ? 0 : additions->medium + 1;
213 extra.costTime = costTime;
214 extra.result = EVENT_STAGE_RESULT_OK;
215 UpdateDiscEventAndReport(&extra, device);
216 }
217 infoNode->statistics.repTimes++;
218 infoNode->statistics.devNum++;
219 }
220
DfxRecordStopDiscoveryDevice(const char * packageName,DiscInfo * infoNode)221 static void DfxRecordStopDiscoveryDevice(const char *packageName, DiscInfo *infoNode)
222 {
223 DiscoveryStatistics *statistics = &infoNode->statistics;
224 uint64_t totalTime = SoftBusGetSysTimeMs() - statistics->startTime;
225 SoftbusRecordBleDiscDetails((char *)packageName, totalTime, statistics->repTimes, statistics->devNum,
226 statistics->discTimes);
227 }
228
BitmapSet(uint32_t * bitMap,uint32_t pos)229 static void BitmapSet(uint32_t *bitMap, uint32_t pos)
230 {
231 *bitMap |= 1U << pos;
232 }
233
IsBitmapSet(const uint32_t * bitMap,uint32_t pos)234 static bool IsBitmapSet(const uint32_t *bitMap, uint32_t pos)
235 {
236 return ((1U << pos) & (*bitMap)) ? true : false;
237 }
238
BuildDiscCallEvent(DiscEventExtra * extra,const DiscInfo * info,const char * packageName,const InterfaceFuncType type)239 static void BuildDiscCallEvent(DiscEventExtra *extra, const DiscInfo *info, const char *packageName,
240 const InterfaceFuncType type)
241 {
242 DISC_CHECK_AND_RETURN_LOGE(extra != NULL, DISC_CONTROL, "discEventExtra is null");
243
244 if (info != NULL) {
245 extra->discType = info->medium + 1;
246 extra->discMode = info->mode;
247 }
248 if (IsValidString(packageName, PKG_NAME_SIZE_MAX - 1)) {
249 extra->callerPkg = packageName;
250 }
251 extra->interFuncType = type + 1;
252 }
253
CallSpecificInterfaceFunc(const InnerOption * option,const DiscoveryFuncInterface * interface,const DiscoverMode mode,InterfaceFuncType type)254 static int32_t CallSpecificInterfaceFunc(const InnerOption *option,
255 const DiscoveryFuncInterface *interface, const DiscoverMode mode, InterfaceFuncType type)
256 {
257 DISC_CHECK_AND_RETURN_RET_LOGW(interface != NULL, SOFTBUS_DISCOVER_MANAGER_INNERFUNCTION_FAIL,
258 DISC_CONTROL, "interface is null");
259 switch (type) {
260 case PUBLISH_FUNC:
261 return ((mode == DISCOVER_MODE_ACTIVE) ? (interface->Publish(&(option->publishOption))) :
262 (interface->StartScan(&(option->publishOption))));
263 case UNPUBLISH_FUNC:
264 return ((mode == DISCOVER_MODE_ACTIVE) ? (interface->Unpublish(&(option->publishOption))) :
265 (interface->StopScan(&(option->publishOption))));
266 case STARTDISCOVERTY_FUNC:
267 return ((mode == DISCOVER_MODE_ACTIVE) ? (interface->StartAdvertise(&(option->subscribeOption))) :
268 (interface->Subscribe(&(option->subscribeOption))));
269 case STOPDISCOVERY_FUNC:
270 return ((mode == DISCOVER_MODE_ACTIVE) ? (interface->StopAdvertise(&(option->subscribeOption))) :
271 (interface->Unsubscribe(&(option->subscribeOption))));
272 default:
273 return SOFTBUS_DISCOVER_MANAGER_INNERFUNCTION_FAIL;
274 }
275 }
276
DfxCallInterfaceByMedium(const DiscInfo * infoNode,const char * packageName,const InterfaceFuncType type,int32_t reason)277 static void DfxCallInterfaceByMedium(
278 const DiscInfo *infoNode, const char *packageName, const InterfaceFuncType type, int32_t reason)
279 {
280 DiscEventExtra extra = {0};
281 DiscEventExtraInit(&extra);
282 extra.errcode = reason;
283 BuildDiscCallEvent(&extra, infoNode, packageName, type);
284 extra.result = (reason == SOFTBUS_OK) ? EVENT_STAGE_RESULT_OK : EVENT_STAGE_RESULT_FAILED;
285 DISC_EVENT(EVENT_SCENE_DISC, EVENT_STAGE_CALL_INTERFACE, extra);
286 }
287
CallInterfaceByMedium(const DiscInfo * info,const char * packageName,const InterfaceFuncType type)288 static int32_t CallInterfaceByMedium(const DiscInfo *info, const char *packageName, const InterfaceFuncType type)
289 {
290 int32_t ret = SOFTBUS_OK;
291 switch (info->medium) {
292 case COAP:
293 ret = CallSpecificInterfaceFunc(&(info->option), g_discCoapInterface, info->mode, type);
294 DfxCallInterfaceByMedium(info, packageName, type, ret);
295 return ret;
296 case BLE:
297 ret = CallSpecificInterfaceFunc(&(info->option), g_discBleInterface, info->mode, type);
298 DfxCallInterfaceByMedium(info, packageName, type, ret);
299 return ret;
300 case AUTO: {
301 int32_t coapRet = CallSpecificInterfaceFunc(&(info->option), g_discCoapInterface, info->mode, type);
302 DfxCallInterfaceByMedium(info, packageName, type, coapRet);
303 int32_t bleRet = CallSpecificInterfaceFunc(&(info->option), g_discBleInterface, info->mode, type);
304 DfxCallInterfaceByMedium(info, packageName, type, bleRet);
305
306 DISC_CHECK_AND_RETURN_RET_LOGE(coapRet == SOFTBUS_OK || bleRet == SOFTBUS_OK,
307 SOFTBUS_DISCOVER_MANAGER_INNERFUNCTION_FAIL, DISC_CONTROL, "all medium failed");
308 return SOFTBUS_OK;
309 }
310 case USB:
311 ret = CallSpecificInterfaceFunc(&(info->option), g_discUsbInterface, info->mode, type);
312 DfxCallInterfaceByMedium(info, packageName, type, ret);
313 return ret;
314 default:
315 return SOFTBUS_DISCOVER_MANAGER_INNERFUNCTION_FAIL;
316 }
317 }
318
TransferStringCapToBitmap(const char * capability)319 static int32_t TransferStringCapToBitmap(const char *capability)
320 {
321 DISC_CHECK_AND_RETURN_RET_LOGW(capability != NULL, SOFTBUS_DISCOVER_MANAGER_CAPABILITY_INVALID,
322 DISC_CONTROL, "capability is null");
323
324 for (uint32_t i = 0; i < sizeof(g_capabilityMap) / sizeof(g_capabilityMap[0]); i++) {
325 if (strcmp(capability, g_capabilityMap[i].capability) == 0) {
326 DISC_LOGD(DISC_CONTROL, "capability=%{public}s", capability);
327 return g_capabilityMap[i].bitmap;
328 }
329 }
330
331 return SOFTBUS_DISCOVER_MANAGER_CAPABILITY_INVALID;
332 }
333
AddDiscInfoToCapabilityList(DiscInfo * info,const ServiceType type)334 static void AddDiscInfoToCapabilityList(DiscInfo *info, const ServiceType type)
335 {
336 if (type != SUBSCRIBE_SERVICE && type != SUBSCRIBE_INNER_SERVICE) {
337 DISC_LOGD(DISC_CONTROL, "publish no need to add");
338 return;
339 }
340
341 for (uint32_t tmp = 0; tmp < CAPABILITY_MAX_BITNUM; tmp++) {
342 if (IsBitmapSet(&(info->option.subscribeOption.capabilityBitmap[0]), tmp) == true) {
343 if (type == SUBSCRIBE_SERVICE) {
344 ListTailInsert(&(g_capabilityList[tmp]), &(info->capNode));
345 } else {
346 ListNodeInsert(&(g_capabilityList[tmp]), &(info->capNode));
347 }
348 break;
349 }
350 }
351 }
352
RemoveDiscInfoFromCapabilityList(DiscInfo * info,const ServiceType type)353 static void RemoveDiscInfoFromCapabilityList(DiscInfo *info, const ServiceType type)
354 {
355 if (type != SUBSCRIBE_SERVICE && type != SUBSCRIBE_INNER_SERVICE) {
356 DISC_LOGD(DISC_CONTROL, "publish no need to delete");
357 return;
358 }
359 ListDelete(&(info->capNode));
360 }
361
FreeDiscInfo(DiscInfo * info,const ServiceType type)362 static void FreeDiscInfo(DiscInfo *info, const ServiceType type)
363 {
364 if ((type == PUBLISH_SERVICE) || (type == PUBLISH_INNER_SERVICE)) {
365 SoftBusFree(info->option.publishOption.capabilityData);
366 info->option.publishOption.capabilityData = NULL;
367 }
368
369 if ((type == SUBSCRIBE_SERVICE) || (type == SUBSCRIBE_INNER_SERVICE)) {
370 SoftBusFree(info->option.subscribeOption.capabilityData);
371 info->option.subscribeOption.capabilityData = NULL;
372 }
373 SoftBusFree(info);
374 info = NULL;
375 }
376
IsInnerModule(const DiscInfo * infoNode)377 static bool IsInnerModule(const DiscInfo *infoNode)
378 {
379 for (uint32_t i = 0; i < MODULE_MAX; i++) {
380 DISC_LOGD(DISC_CONTROL, "packageName=%{public}s", infoNode->item->packageName);
381 if (strcmp(infoNode->item->packageName, g_discModuleMap[i]) == 0) {
382 DISC_LOGD(DISC_CONTROL, "true");
383 return true;
384 }
385 }
386 DISC_LOGD(DISC_CONTROL, "false");
387 return false;
388 }
389
InnerDeviceFound(DiscInfo * infoNode,const DeviceInfo * device,const InnerDeviceInfoAddtions * additions)390 static void InnerDeviceFound(DiscInfo *infoNode, const DeviceInfo *device,
391 const InnerDeviceInfoAddtions *additions)
392 {
393 if (infoNode->item != NULL && infoNode->item->callback.serverCb.OnServerDeviceFound != NULL &&
394 !IsInnerModule(infoNode)) {
395 (void)infoNode->item->callback.serverCb.OnServerDeviceFound(infoNode->item->packageName, device, additions);
396 return;
397 }
398
399 DISC_LOGD(DISC_CONTROL, "call from inner module.");
400 if (infoNode->item != NULL && infoNode->item->callback.innerCb.OnDeviceFound != NULL) {
401 DfxRecordDeviceFound(infoNode, device, additions);
402 infoNode->item->callback.innerCb.OnDeviceFound(device, additions);
403 }
404 }
405
DiscOnDeviceFound(const DeviceInfo * device,const InnerDeviceInfoAddtions * additions)406 static void DiscOnDeviceFound(const DeviceInfo *device, const InnerDeviceInfoAddtions *additions)
407 {
408 DISC_CHECK_AND_RETURN_LOGE(device != NULL, DISC_CONTROL, "device is null");
409 DISC_CHECK_AND_RETURN_LOGE(additions != NULL, DISC_CONTROL, "additions is null");
410
411 DISC_LOGD(DISC_CONTROL,
412 "capabilityBitmap=%{public}d, medium=%{public}d", device->capabilityBitmap[0], additions->medium);
413 for (uint32_t tmp = 0; tmp < CAPABILITY_MAX_BITNUM; tmp++) {
414 if (IsBitmapSet((uint32_t *)device->capabilityBitmap, tmp) == false) {
415 continue;
416 }
417
418 if (SoftBusMutexLock(&(g_discoveryInfoList->lock)) != SOFTBUS_OK) {
419 DISC_LOGE(DISC_CONTROL, "lock failed");
420 return;
421 }
422 DiscInfo *infoNode = NULL;
423 LIST_FOR_EACH_ENTRY(infoNode, &(g_capabilityList[tmp]), DiscInfo, capNode) {
424 DISC_LOGD(DISC_CONTROL, "find callback id=%{public}d", infoNode->id);
425 infoNode->statistics.discTimes++;
426 InnerDeviceFound(infoNode, device, additions);
427 }
428 (void)SoftBusMutexUnlock(&(g_discoveryInfoList->lock));
429 }
430 }
431
CheckPublishInfo(const PublishInfo * info)432 static int32_t CheckPublishInfo(const PublishInfo *info)
433 {
434 DISC_CHECK_AND_RETURN_RET_LOGW(info->mode == DISCOVER_MODE_PASSIVE || info->mode == DISCOVER_MODE_ACTIVE,
435 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "mode is invalid");
436 DISC_CHECK_AND_RETURN_RET_LOGW(info->medium >= AUTO && info->medium <= COAP,
437 SOFTBUS_DISCOVER_MANAGER_INVALID_MEDIUM, DISC_CONTROL, "mode is invalid");
438 DISC_CHECK_AND_RETURN_RET_LOGW(info->freq >= LOW && info->freq < FREQ_BUTT,
439 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "freq is invalid");
440
441 if (info->capabilityData == NULL) {
442 if (info->dataLen == 0) {
443 return SOFTBUS_OK;
444 } else {
445 DISC_LOGE(DISC_CONTROL, "capabilityData is NULL, dataLen != 0");
446 return SOFTBUS_INVALID_PARAM;
447 }
448 } else {
449 if (info->dataLen == 0) {
450 DISC_LOGE(DISC_CONTROL, "capabilityData is not NULL, dataLen == 0");
451 return SOFTBUS_INVALID_PARAM;
452 }
453 if (info->dataLen > MAX_CAPABILITYDATA_LEN) {
454 DISC_LOGE(DISC_CONTROL, "dataLen > max length. dataLen=%{public}u", info->dataLen);
455 return SOFTBUS_INVALID_PARAM;
456 }
457 uint32_t len = strlen((char *)info->capabilityData);
458 if (info->capabilityData[info->dataLen] != '\0') {
459 DISC_LOGE(DISC_CONTROL, "capabilityData is not c-string format: len=%{public}u, dataLen=%{public}u",
460 len, info->dataLen);
461 return SOFTBUS_INVALID_PARAM;
462 }
463 if (len != info->dataLen) {
464 DISC_LOGE(DISC_CONTROL, "capabilityData len != dataLen. len=%{public}u, dataLen=%{public}u",
465 len, info->dataLen);
466 return SOFTBUS_INVALID_PARAM;
467 }
468 }
469 return SOFTBUS_OK;
470 }
471
CheckSubscribeInfo(const SubscribeInfo * info)472 static int32_t CheckSubscribeInfo(const SubscribeInfo *info)
473 {
474 DISC_CHECK_AND_RETURN_RET_LOGW(info->mode == DISCOVER_MODE_PASSIVE || info->mode == DISCOVER_MODE_ACTIVE,
475 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "mode is invalid");
476 DISC_CHECK_AND_RETURN_RET_LOGW(info->medium >= AUTO && info->medium <= USB,
477 SOFTBUS_DISCOVER_MANAGER_INVALID_MEDIUM, DISC_CONTROL, "medium is invalid");
478 DISC_CHECK_AND_RETURN_RET_LOGW(info->freq >= LOW && info->freq < FREQ_BUTT,
479 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "freq is invalid");
480 DISC_CHECK_AND_RETURN_RET_LOGW(!(info->medium == USB && info->mode == DISCOVER_MODE_ACTIVE),
481 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "usb is not support active mode");
482
483 if (info->capabilityData == NULL) {
484 if (info->dataLen == 0) {
485 return SOFTBUS_OK;
486 } else {
487 DISC_LOGE(DISC_CONTROL, "capabilityData is NULL, dataLen != 0");
488 return SOFTBUS_INVALID_PARAM;
489 }
490 } else {
491 if (info->dataLen == 0) {
492 DISC_LOGE(DISC_CONTROL, "capabilityData is not NULL, dataLen == 0");
493 return SOFTBUS_INVALID_PARAM;
494 }
495 if (info->dataLen > MAX_CAPABILITYDATA_LEN) {
496 DISC_LOGE(DISC_CONTROL, "dataLen > max length. dataLen=%{public}u", info->dataLen);
497 return SOFTBUS_INVALID_PARAM;
498 }
499 uint32_t len = strlen((char *)info->capabilityData);
500 if (info->capabilityData[info->dataLen] != '\0') {
501 DISC_LOGE(DISC_CONTROL, "capabilityData is not c-string format: len=%{public}u, dataLen=%{public}u",
502 len, info->dataLen);
503 return SOFTBUS_INVALID_PARAM;
504 }
505 if (len != info->dataLen) {
506 DISC_LOGE(DISC_CONTROL, "capabilityData len != dataLen. len=%{public}u, dataLen=%{public}u",
507 len, info->dataLen);
508 return SOFTBUS_INVALID_PARAM;
509 }
510 }
511 return SOFTBUS_OK;
512 }
513
SetDiscItemCallback(DiscItem * itemNode,const InnerCallback * cb,const ServiceType type)514 static void SetDiscItemCallback(DiscItem *itemNode, const InnerCallback *cb, const ServiceType type)
515 {
516 if ((type != SUBSCRIBE_INNER_SERVICE && type != SUBSCRIBE_SERVICE) || cb == NULL) {
517 return;
518 }
519 if (type == SUBSCRIBE_SERVICE) {
520 itemNode->callback.serverCb.OnServerDeviceFound = cb->serverCb.OnServerDeviceFound;
521 return;
522 }
523 if ((itemNode->callback.innerCb.OnDeviceFound != NULL) && (cb->innerCb.OnDeviceFound == NULL)) {
524 return;
525 }
526 itemNode->callback.innerCb.OnDeviceFound = cb->innerCb.OnDeviceFound;
527 }
528
CreateDiscItem(SoftBusList * serviceList,const char * packageName,const InnerCallback * cb,const ServiceType type)529 static DiscItem *CreateDiscItem(SoftBusList *serviceList, const char *packageName, const InnerCallback *cb,
530 const ServiceType type)
531 {
532 DiscItem *itemNode = (DiscItem *)SoftBusCalloc(sizeof(DiscItem));
533 DISC_CHECK_AND_RETURN_RET_LOGE(itemNode != NULL, NULL, DISC_CONTROL, "calloc item node failed");
534
535 if (strcpy_s(itemNode->packageName, PKG_NAME_SIZE_MAX, packageName) != EOK) {
536 SoftBusFree(itemNode);
537 return NULL;
538 }
539
540 if ((type == PUBLISH_INNER_SERVICE) || (type == SUBSCRIBE_INNER_SERVICE)) {
541 ListNodeInsert(&(serviceList->list), &(itemNode->node));
542 } else if ((type == PUBLISH_SERVICE) || (type == SUBSCRIBE_SERVICE)) {
543 ListTailInsert(&(serviceList->list), &(itemNode->node));
544 }
545
546 SetDiscItemCallback(itemNode, cb, type);
547
548 serviceList->cnt++;
549 ListInit(&(itemNode->InfoList));
550 return itemNode;
551 }
552
CreateDiscInfoForPublish(const PublishInfo * info,int32_t callingPid)553 static DiscInfo *CreateDiscInfoForPublish(const PublishInfo *info, int32_t callingPid)
554 {
555 DiscInfo *infoNode = (DiscInfo *)SoftBusCalloc(sizeof(DiscInfo));
556 DISC_CHECK_AND_RETURN_RET_LOGE(infoNode != NULL, NULL, DISC_CONTROL, "calloc info node failed");
557
558 ListInit(&(infoNode->node));
559 ListInit(&(infoNode->capNode));
560
561 infoNode->id = info->publishId;
562 infoNode->medium = info->medium;
563 infoNode->mode = info->mode;
564 infoNode->pid = callingPid;
565
566 PublishOption *option = &infoNode->option.publishOption;
567 option->freq = info->freq;
568 option->ranging = info->ranging;
569 option->dataLen = info->dataLen;
570
571 if (info->dataLen != 0) {
572 option->capabilityData = (uint8_t *)SoftBusCalloc(info->dataLen + 1);
573 if (option->capabilityData == NULL) {
574 DISC_LOGE(DISC_CONTROL, "alloc capability data failed");
575 SoftBusFree(infoNode);
576 return NULL;
577 }
578 if (memcpy_s(option->capabilityData, info->dataLen, info->capabilityData, info->dataLen) != EOK) {
579 DISC_LOGE(DISC_CONTROL, "memcpy_s failed");
580 FreeDiscInfo(infoNode, PUBLISH_SERVICE);
581 return NULL;
582 }
583 }
584
585 int32_t bitmap = TransferStringCapToBitmap(info->capability);
586 if (bitmap < 0) {
587 DISC_LOGE(DISC_CONTROL, "capability not found");
588 FreeDiscInfo(infoNode, PUBLISH_SERVICE);
589 return NULL;
590 }
591 BitmapSet(option->capabilityBitmap, (uint32_t)bitmap);
592
593 return infoNode;
594 }
595
CreateDiscInfoForSubscribe(const SubscribeInfo * info,int32_t callingPid)596 static DiscInfo *CreateDiscInfoForSubscribe(const SubscribeInfo *info, int32_t callingPid)
597 {
598 DiscInfo *infoNode = (DiscInfo *)SoftBusCalloc(sizeof(DiscInfo));
599 DISC_CHECK_AND_RETURN_RET_LOGE(infoNode != NULL, NULL, DISC_CONTROL, "alloc info node failed");
600
601 ListInit(&(infoNode->node));
602 ListInit(&(infoNode->capNode));
603
604 infoNode->id = info->subscribeId;
605 infoNode->medium = info->medium;
606 infoNode->mode = info->mode;
607 infoNode->pid = callingPid;
608
609 SubscribeOption *option = &infoNode->option.subscribeOption;
610 option->freq = info->freq;
611 option->dataLen = info->dataLen;
612 option->isSameAccount = info->isSameAccount;
613 option->isWakeRemote = info->isWakeRemote;
614
615 if (info->dataLen != 0) {
616 option->capabilityData = (uint8_t *)SoftBusCalloc(info->dataLen + 1);
617 if (option->capabilityData == NULL) {
618 DISC_LOGE(DISC_CONTROL, "alloc capability data failed");
619 SoftBusFree(infoNode);
620 return NULL;
621 }
622 if (memcpy_s(option->capabilityData, info->dataLen, info->capabilityData, info->dataLen) != EOK) {
623 DISC_LOGE(DISC_CONTROL, "memcpy_s failed");
624 FreeDiscInfo(infoNode, SUBSCRIBE_SERVICE);
625 return NULL;
626 }
627 }
628
629 int32_t bimap = TransferStringCapToBitmap(info->capability);
630 if (bimap < 0) {
631 DISC_LOGE(DISC_CONTROL, "capability not found");
632 FreeDiscInfo(infoNode, SUBSCRIBE_SERVICE);
633 return NULL;
634 }
635 BitmapSet(option->capabilityBitmap, (uint32_t)bimap);
636 DfxRecordStartDiscoveryDevice(infoNode);
637 return infoNode;
638 }
639
DumpDiscInfoList(const DiscItem * itemNode)640 static void DumpDiscInfoList(const DiscItem *itemNode)
641 {
642 char dumpStr[DUMP_STR_LEN] = {0};
643 int32_t dumpStrPos = 0;
644 int32_t itemStrLen = 0;
645 DiscInfo *infoNode = NULL;
646
647 LIST_FOR_EACH_ENTRY(infoNode, &(itemNode->InfoList), DiscInfo, node) {
648 itemStrLen = sprintf_s(&dumpStr[dumpStrPos], DUMP_STR_LEN - dumpStrPos, "%d,", infoNode->id);
649 if (itemStrLen <= 0) {
650 DISC_LOGI(DISC_CONTROL, "info id=%{public}s", dumpStr);
651 dumpStrPos = 0;
652 itemStrLen = sprintf_s(&dumpStr[dumpStrPos], DUMP_STR_LEN - dumpStrPos, "%d,", infoNode->id);
653 DISC_CHECK_AND_RETURN_LOGW(itemStrLen > 0, DISC_CONTROL, "sprintf_s failed");
654 }
655 dumpStrPos += itemStrLen;
656 }
657
658 if (dumpStrPos > 0) {
659 DISC_LOGI(DISC_CONTROL, "info id=%{public}s", dumpStr);
660 }
661 }
662
AddDiscInfoToList(SoftBusList * serviceList,const char * packageName,const InnerCallback * cb,DiscInfo * info,ServiceType type)663 static int32_t AddDiscInfoToList(SoftBusList *serviceList, const char *packageName, const InnerCallback *cb,
664 DiscInfo *info, ServiceType type)
665 {
666 bool isDumpable = (strcmp(g_discModuleMap[0], packageName) != 0);
667 if (isDumpable) {
668 DISC_LOGI(DISC_CONTROL, "packageName=%{public}s, id=%{public}d", packageName, info->id);
669 }
670
671 DiscItem *itemNode = NULL;
672 bool exist = false;
673 LIST_FOR_EACH_ENTRY(itemNode, &(serviceList->list), DiscItem, node) {
674 if (strcmp(itemNode->packageName, packageName) != 0) {
675 continue;
676 }
677
678 if (isDumpable) {
679 DumpDiscInfoList(itemNode);
680 }
681
682 DiscInfo *infoNode = NULL;
683 LIST_FOR_EACH_ENTRY(infoNode, &(itemNode->InfoList), DiscInfo, node) {
684 if (infoNode->id == info->id) {
685 DISC_LOGI(DISC_CONTROL, "id already existed");
686 return SOFTBUS_DISCOVER_MANAGER_DUPLICATE_PARAM;
687 }
688 }
689 DISC_CHECK_AND_RETURN_RET_LOGE(
690 itemNode->infoNum < DISC_INFO_LIST_SIZE_MAX, SOFTBUS_DISCOVER_MANAGER_ID_MAX_ERR,
691 DISC_CONTROL, "infolist size limit reached, packageName=%{public}s", packageName);
692
693 SetDiscItemCallback(itemNode, cb, type);
694 exist = true;
695 itemNode->infoNum++;
696 info->item = itemNode;
697 ListTailInsert(&(itemNode->InfoList), &(info->node));
698 AddDiscInfoToCapabilityList(info, type);
699 break;
700 }
701
702 if (exist == false) {
703 itemNode = CreateDiscItem(serviceList, packageName, cb, type);
704 if (itemNode == NULL) {
705 DISC_LOGE(DISC_CONTROL, "itemNode create failed");
706 return SOFTBUS_DISCOVER_MANAGER_ITEM_NOT_CREATE;
707 }
708
709 itemNode->infoNum++;
710 info->item = itemNode;
711 ListTailInsert(&(itemNode->InfoList), &(info->node));
712 AddDiscInfoToCapabilityList(info, type);
713 }
714
715 return SOFTBUS_OK;
716 }
717
AddDiscInfoToPublishList(const char * packageName,const InnerCallback * cb,DiscInfo * info,ServiceType type)718 static int32_t AddDiscInfoToPublishList(const char *packageName, const InnerCallback *cb, DiscInfo *info,
719 ServiceType type)
720 {
721 return AddDiscInfoToList(g_publishInfoList, packageName, cb, info, type);
722 }
723
AddDiscInfoToDiscoveryList(const char * packageName,const InnerCallback * cb,DiscInfo * info,ServiceType type)724 static int32_t AddDiscInfoToDiscoveryList(const char *packageName, const InnerCallback *cb, DiscInfo *info,
725 ServiceType type)
726 {
727 return AddDiscInfoToList(g_discoveryInfoList, packageName, cb, info, type);
728 }
729
RemoveInfoFromList(SoftBusList * serviceList,const char * packageName,const int32_t id,const ServiceType type,int32_t callingPid)730 static DiscInfo *RemoveInfoFromList(SoftBusList *serviceList, const char *packageName, const int32_t id,
731 const ServiceType type, int32_t callingPid)
732 {
733 bool isDumpable = (strcmp(g_discModuleMap[0], packageName) != 0);
734 if (isDumpable) {
735 DISC_LOGI(DISC_CONTROL, "packageName=%{public}s, id=%{public}d", packageName, id);
736 }
737
738 bool isIdExist = false;
739 DiscItem *itemNode = NULL;
740 DiscInfo *infoNode = NULL;
741 LIST_FOR_EACH_ENTRY(itemNode, &(serviceList->list), DiscItem, node) {
742 if (strcmp(itemNode->packageName, packageName) != 0) {
743 continue;
744 }
745
746 if (isDumpable) {
747 DumpDiscInfoList(itemNode);
748 }
749
750 if (itemNode->infoNum == 0) {
751 serviceList->cnt--;
752 ListDelete(&(itemNode->node));
753 SoftBusFree(itemNode);
754 return NULL;
755 }
756
757 LIST_FOR_EACH_ENTRY(infoNode, &(itemNode->InfoList), DiscInfo, node) {
758 if (infoNode->pid != callingPid) {
759 continue;
760 }
761 if (infoNode->id != id) {
762 continue;
763 }
764 isIdExist = true;
765 itemNode->infoNum--;
766 RemoveDiscInfoFromCapabilityList(infoNode, type);
767 ListDelete(&(infoNode->node));
768
769 if (itemNode->infoNum == 0) {
770 serviceList->cnt--;
771 ListDelete(&(itemNode->node));
772 SoftBusFree(itemNode);
773 }
774 break;
775 }
776 break;
777 }
778
779 if (isIdExist == false) {
780 DISC_LOGD(DISC_CONTROL, "can not find publishId");
781 return NULL;
782 }
783 return infoNode;
784 }
785
RemoveInfoFromPublishList(const char * packageName,const int32_t id,const ServiceType type,int32_t callingPid)786 static DiscInfo *RemoveInfoFromPublishList(const char *packageName, const int32_t id, const ServiceType type,
787 int32_t callingPid)
788 {
789 return RemoveInfoFromList(g_publishInfoList, packageName, id, type, callingPid);
790 }
791
RemoveInfoFromDiscoveryList(const char * packageName,const int32_t id,const ServiceType type,int32_t callingPid)792 static DiscInfo *RemoveInfoFromDiscoveryList(const char *packageName, const int32_t id, const ServiceType type,
793 int32_t callingPid)
794 {
795 return RemoveInfoFromList(g_discoveryInfoList, packageName, id, type, callingPid);
796 }
797
InnerPublishService(const char * packageName,DiscInfo * info,const ServiceType type)798 static int32_t InnerPublishService(const char *packageName, DiscInfo *info, const ServiceType type)
799 {
800 int32_t ret = SoftBusMutexLock(&g_publishInfoList->lock);
801 DISC_CHECK_AND_RETURN_RET_LOGE(ret == SOFTBUS_OK, SOFTBUS_LOCK_ERR, DISC_CONTROL, "lock failed");
802
803 do {
804 ret = AddDiscInfoToPublishList(packageName, NULL, info, type);
805 if (ret != SOFTBUS_OK) {
806 DISC_LOGE(DISC_CONTROL, "add info to list failed");
807 break;
808 }
809
810 DFX_RECORD_DISC_CALL_START(info, packageName, PUBLISH_FUNC);
811 ret = CallInterfaceByMedium(info, packageName, PUBLISH_FUNC);
812 if (ret != SOFTBUS_OK) {
813 DISC_LOGE(DISC_CONTROL, "call interface by medium failed");
814 ListDelete(&(info->node));
815 info->item->infoNum--;
816 }
817 } while (false);
818
819 SoftBusMutexUnlock(&g_publishInfoList->lock);
820 return ret;
821 }
822
InnerUnPublishService(const char * packageName,int32_t publishId,const ServiceType type,int32_t callingPid)823 static int32_t InnerUnPublishService(const char *packageName, int32_t publishId, const ServiceType type,
824 int32_t callingPid)
825 {
826 int32_t ret = SoftBusMutexLock(&g_publishInfoList->lock);
827 DISC_CHECK_AND_RETURN_RET_LOGE(ret == SOFTBUS_OK, SOFTBUS_LOCK_ERR, DISC_CONTROL, "lock failed");
828
829 DiscInfo *infoNode = NULL;
830 do {
831 infoNode = RemoveInfoFromPublishList(packageName, publishId, type, callingPid);
832 if (infoNode == NULL) {
833 DISC_LOGE(DISC_CONTROL, "delete info from list failed");
834 ret = SOFTBUS_DISCOVER_MANAGER_INFO_NOT_DELETE;
835 break;
836 }
837
838 DFX_RECORD_DISC_CALL_START(infoNode, packageName, UNPUBLISH_FUNC);
839 ret = CallInterfaceByMedium(infoNode, packageName, UNPUBLISH_FUNC);
840 if (ret != SOFTBUS_OK) {
841 DISC_LOGE(DISC_CONTROL, "call interface by medium failed");
842 }
843 FreeDiscInfo(infoNode, type);
844 } while (false);
845
846 SoftBusMutexUnlock(&g_publishInfoList->lock);
847 return ret;
848 }
849
InnerStartDiscovery(const char * packageName,DiscInfo * info,const IServerDiscInnerCallback * cb,const ServiceType type)850 static int32_t InnerStartDiscovery(const char *packageName, DiscInfo *info, const IServerDiscInnerCallback *cb,
851 const ServiceType type)
852 {
853 InnerCallback callback;
854 callback.serverCb.OnServerDeviceFound = NULL;
855 if (cb != NULL) {
856 callback.serverCb.OnServerDeviceFound = cb->OnServerDeviceFound;
857 }
858
859 int32_t ret = SoftBusMutexLock(&g_discoveryInfoList->lock);
860 DISC_CHECK_AND_RETURN_RET_LOGE(ret == SOFTBUS_OK, SOFTBUS_LOCK_ERR, DISC_CONTROL, "lock failed");
861
862 do {
863 ret = AddDiscInfoToDiscoveryList(packageName, &callback, info, type);
864 if (ret != SOFTBUS_OK) {
865 DISC_LOGE(DISC_CONTROL, "add info to list failed");
866 break;
867 }
868
869 UpdateDdmpStartDiscoveryTime(info);
870 DFX_RECORD_DISC_CALL_START(info, packageName, STARTDISCOVERTY_FUNC);
871 ret = CallInterfaceByMedium(info, packageName, STARTDISCOVERTY_FUNC);
872 if (ret != SOFTBUS_OK) {
873 DISC_LOGE(DISC_CONTROL, "call interface by medium failed");
874 RemoveDiscInfoFromCapabilityList(info, type);
875 ListDelete(&(info->node));
876 info->item->infoNum--;
877 }
878 } while (false);
879
880 SoftBusMutexUnlock(&g_discoveryInfoList->lock);
881 return ret;
882 }
883
InnerStopDiscovery(const char * packageName,int32_t subscribeId,const ServiceType type,int32_t callingPid)884 static int32_t InnerStopDiscovery(const char *packageName, int32_t subscribeId, const ServiceType type,
885 int32_t callingPid)
886 {
887 int32_t ret = SoftBusMutexLock(&g_discoveryInfoList->lock);
888 DISC_CHECK_AND_RETURN_RET_LOGE(ret == SOFTBUS_OK, SOFTBUS_LOCK_ERR, DISC_CONTROL, "lock failed");
889
890 DiscInfo *infoNode = NULL;
891 do {
892 infoNode = RemoveInfoFromDiscoveryList(packageName, subscribeId, type, callingPid);
893 if (infoNode == NULL) {
894 DISC_LOGE(DISC_CONTROL, "delete info from list failed");
895 ret = SOFTBUS_DISCOVER_MANAGER_INFO_NOT_DELETE;
896 break;
897 }
898
899 DFX_RECORD_DISC_CALL_START(infoNode, packageName, STOPDISCOVERY_FUNC);
900 ret = CallInterfaceByMedium(infoNode, packageName, STOPDISCOVERY_FUNC);
901 if (ret != SOFTBUS_OK) {
902 DISC_LOGE(DISC_CONTROL, "call interface by medium failed");
903 } else {
904 DfxRecordStopDiscoveryDevice(packageName, infoNode);
905 }
906 FreeDiscInfo(infoNode, type);
907 } while (false);
908
909 SoftBusMutexUnlock(&g_discoveryInfoList->lock);
910 return ret;
911 }
912
TransferModuleIdToPackageName(DiscModule moduleId)913 static const char* TransferModuleIdToPackageName(DiscModule moduleId)
914 {
915 return g_discModuleMap[moduleId - 1];
916 }
917
InnerSetDiscoveryCallback(const char * packageName,const DiscInnerCallback * cb)918 static int32_t InnerSetDiscoveryCallback(const char *packageName, const DiscInnerCallback *cb)
919 {
920 if (SoftBusMutexLock(&(g_discoveryInfoList->lock)) != SOFTBUS_OK) {
921 DISC_LOGE(DISC_CONTROL, "lock failed");
922 return SOFTBUS_LOCK_ERR;
923 }
924
925 bool isIdExist = false;
926 DiscItem *itemNode = NULL;
927 InnerCallback callback;
928 LIST_FOR_EACH_ENTRY(itemNode, &(g_discoveryInfoList->list), DiscItem, node) {
929 if (strcmp(itemNode->packageName, packageName) != 0) {
930 continue;
931 }
932 itemNode->callback.innerCb.OnDeviceFound = cb->OnDeviceFound;
933 isIdExist = true;
934 break;
935 }
936 if (isIdExist == false) {
937 callback.innerCb.OnDeviceFound = cb->OnDeviceFound;
938 itemNode = CreateDiscItem(g_discoveryInfoList, packageName, &callback, SUBSCRIBE_INNER_SERVICE);
939 if (itemNode == NULL) {
940 DISC_LOGE(DISC_CONTROL, "itemNode create failed");
941 (void)SoftBusMutexUnlock(&(g_discoveryInfoList->lock));
942 return SOFTBUS_DISCOVER_MANAGER_ITEM_NOT_CREATE;
943 }
944 }
945 (void)SoftBusMutexUnlock(&(g_discoveryInfoList->lock));
946 return SOFTBUS_OK;
947 }
948
DiscSetDiscoverCallback(DiscModule moduleId,const DiscInnerCallback * callback)949 int32_t DiscSetDiscoverCallback(DiscModule moduleId, const DiscInnerCallback *callback)
950 {
951 DISC_CHECK_AND_RETURN_RET_LOGW(moduleId >= MODULE_MIN && moduleId <= MODULE_MAX && callback != NULL,
952 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "invalid parameters");
953 DISC_CHECK_AND_RETURN_RET_LOGW(g_isInited == true, SOFTBUS_DISCOVER_MANAGER_NOT_INIT, DISC_CONTROL,
954 "manager is not inited");
955 return InnerSetDiscoveryCallback(TransferModuleIdToPackageName(moduleId), callback);
956 }
957
DiscPublish(DiscModule moduleId,const PublishInfo * info)958 int32_t DiscPublish(DiscModule moduleId, const PublishInfo *info)
959 {
960 DISC_CHECK_AND_RETURN_RET_LOGW(moduleId >= MODULE_MIN && moduleId <= MODULE_MAX && info != NULL,
961 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "invalid parameters");
962 DISC_CHECK_AND_RETURN_RET_LOGW(info->mode == DISCOVER_MODE_ACTIVE, SOFTBUS_INVALID_PARAM, DISC_CONTROL,
963 "mode is not active");
964 DISC_CHECK_AND_RETURN_RET_LOGE(CheckPublishInfo(info) == SOFTBUS_OK, SOFTBUS_INVALID_PARAM, DISC_CONTROL,
965 "invalid info");
966 DISC_CHECK_AND_RETURN_RET_LOGE(g_isInited == true, SOFTBUS_DISCOVER_MANAGER_NOT_INIT, DISC_CONTROL,
967 "manager is not inited");
968
969 DiscInfo *infoNode = CreateDiscInfoForPublish(info, 0);
970 DISC_CHECK_AND_RETURN_RET_LOGW(infoNode != NULL, SOFTBUS_DISCOVER_MANAGER_INFO_NOT_CREATE, DISC_CONTROL,
971 "create info failed");
972
973 int32_t ret = InnerPublishService(TransferModuleIdToPackageName(moduleId), infoNode, PUBLISH_INNER_SERVICE);
974 if (ret != SOFTBUS_OK) {
975 FreeDiscInfo(infoNode, PUBLISH_INNER_SERVICE);
976 }
977 return ret;
978 }
979
DiscStartScan(DiscModule moduleId,const PublishInfo * info,int32_t callingPid)980 int32_t DiscStartScan(DiscModule moduleId, const PublishInfo *info, int32_t callingPid)
981 {
982 DISC_CHECK_AND_RETURN_RET_LOGW(moduleId >= MODULE_MIN && moduleId <= MODULE_MAX && info != NULL,
983 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "invalid parameters");
984 DISC_CHECK_AND_RETURN_RET_LOGW(info->mode == DISCOVER_MODE_PASSIVE, SOFTBUS_INVALID_PARAM, DISC_CONTROL,
985 "mode is not passive");
986 DISC_CHECK_AND_RETURN_RET_LOGE(CheckPublishInfo(info) == SOFTBUS_OK, SOFTBUS_INVALID_PARAM, DISC_CONTROL,
987 "invalid info");
988 DISC_CHECK_AND_RETURN_RET_LOGE(g_isInited == true, SOFTBUS_DISCOVER_MANAGER_NOT_INIT, DISC_CONTROL,
989 "manager is not inited");
990
991 DiscInfo *infoNode = CreateDiscInfoForPublish(info, callingPid);
992 DISC_CHECK_AND_RETURN_RET_LOGE(infoNode != NULL, SOFTBUS_DISCOVER_MANAGER_INFO_NOT_CREATE, DISC_CONTROL,
993 "create info failed");
994
995 int32_t ret = InnerPublishService(TransferModuleIdToPackageName(moduleId), infoNode, PUBLISH_INNER_SERVICE);
996 if (ret != SOFTBUS_OK) {
997 FreeDiscInfo(infoNode, PUBLISH_INNER_SERVICE);
998 }
999 return ret;
1000 }
1001
DiscUnpublish(DiscModule moduleId,int32_t publishId,int32_t callingPid)1002 int32_t DiscUnpublish(DiscModule moduleId, int32_t publishId, int32_t callingPid)
1003 {
1004 DISC_CHECK_AND_RETURN_RET_LOGW(moduleId >= MODULE_MIN && moduleId <= MODULE_MAX,
1005 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "invalid moduleId");
1006 DISC_CHECK_AND_RETURN_RET_LOGW(g_isInited == true, SOFTBUS_DISCOVER_MANAGER_NOT_INIT, DISC_CONTROL,
1007 "manager is not inited");
1008
1009 return InnerUnPublishService(TransferModuleIdToPackageName(moduleId), publishId, PUBLISH_INNER_SERVICE,
1010 callingPid);
1011 }
1012
DiscStartAdvertise(DiscModule moduleId,const SubscribeInfo * info,int32_t callingPid)1013 int32_t DiscStartAdvertise(DiscModule moduleId, const SubscribeInfo *info, int32_t callingPid)
1014 {
1015 DISC_CHECK_AND_RETURN_RET_LOGW(moduleId >= MODULE_MIN && moduleId <= MODULE_MAX && info != NULL,
1016 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "invalid parameters");
1017 DISC_CHECK_AND_RETURN_RET_LOGW(info->mode == DISCOVER_MODE_ACTIVE, SOFTBUS_INVALID_PARAM, DISC_CONTROL,
1018 "mode is not active");
1019 DISC_CHECK_AND_RETURN_RET_LOGE(CheckSubscribeInfo(info) == SOFTBUS_OK, SOFTBUS_INVALID_PARAM, DISC_CONTROL,
1020 "invalid info");
1021 DISC_CHECK_AND_RETURN_RET_LOGE(g_isInited == true, SOFTBUS_DISCOVER_MANAGER_NOT_INIT, DISC_CONTROL,
1022 "manager is not inited");
1023
1024 DiscInfo *infoNode = CreateDiscInfoForSubscribe(info, callingPid);
1025 DISC_CHECK_AND_RETURN_RET_LOGE(infoNode != NULL, SOFTBUS_DISCOVER_MANAGER_INFO_NOT_CREATE, DISC_CONTROL,
1026 "create info failed");
1027
1028 int32_t ret = InnerStartDiscovery(TransferModuleIdToPackageName(moduleId), infoNode, NULL, SUBSCRIBE_INNER_SERVICE);
1029 if (ret != SOFTBUS_OK) {
1030 FreeDiscInfo(infoNode, SUBSCRIBE_INNER_SERVICE);
1031 }
1032 return ret;
1033 }
1034
DiscSubscribe(DiscModule moduleId,const SubscribeInfo * info)1035 int32_t DiscSubscribe(DiscModule moduleId, const SubscribeInfo *info)
1036 {
1037 DISC_CHECK_AND_RETURN_RET_LOGW(moduleId >= MODULE_MIN && moduleId <= MODULE_MAX && info != NULL,
1038 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "invalid parameters");
1039 DISC_CHECK_AND_RETURN_RET_LOGW(info->mode == DISCOVER_MODE_PASSIVE, SOFTBUS_INVALID_PARAM, DISC_CONTROL,
1040 "mode is not passive");
1041 DISC_CHECK_AND_RETURN_RET_LOGE(CheckSubscribeInfo(info) == SOFTBUS_OK, SOFTBUS_INVALID_PARAM, DISC_CONTROL,
1042 "invalid info");
1043 DISC_CHECK_AND_RETURN_RET_LOGE(g_isInited == true, SOFTBUS_DISCOVER_MANAGER_NOT_INIT, DISC_CONTROL,
1044 "manager is not inited");
1045
1046 DiscInfo *infoNode = CreateDiscInfoForSubscribe(info, 0);
1047 DISC_CHECK_AND_RETURN_RET_LOGE(infoNode != NULL, SOFTBUS_DISCOVER_MANAGER_INFO_NOT_CREATE, DISC_CONTROL,
1048 "create info failed");
1049
1050 int32_t ret = InnerStartDiscovery(TransferModuleIdToPackageName(moduleId), infoNode, NULL, SUBSCRIBE_INNER_SERVICE);
1051 if (ret != SOFTBUS_OK) {
1052 FreeDiscInfo(infoNode, SUBSCRIBE_INNER_SERVICE);
1053 }
1054 return ret;
1055 }
1056
DiscStopAdvertise(DiscModule moduleId,int32_t subscribeId,int32_t callingPid)1057 int32_t DiscStopAdvertise(DiscModule moduleId, int32_t subscribeId, int32_t callingPid)
1058 {
1059 DISC_CHECK_AND_RETURN_RET_LOGW(moduleId >= MODULE_MIN && moduleId <= MODULE_MAX,
1060 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "invalid moduleId");
1061 DISC_CHECK_AND_RETURN_RET_LOGW(g_isInited == true, SOFTBUS_DISCOVER_MANAGER_NOT_INIT, DISC_CONTROL,
1062 "manager is not inited");
1063
1064 return InnerStopDiscovery(TransferModuleIdToPackageName(moduleId), subscribeId, SUBSCRIBE_INNER_SERVICE,
1065 callingPid);
1066 }
1067
IsInnerPackageName(const char * packageName)1068 static bool IsInnerPackageName(const char *packageName)
1069 {
1070 for (uint32_t i = 0; i < MODULE_MAX; i++) {
1071 if (strcmp(packageName, g_discModuleMap[i]) == 0) {
1072 DISC_LOGD(DISC_CONTROL, "true");
1073 return true;
1074 }
1075 }
1076 DISC_LOGD(DISC_CONTROL, "false");
1077 return false;
1078 }
1079
DiscPublishService(const char * packageName,const PublishInfo * info,int32_t callingPid)1080 int32_t DiscPublishService(const char *packageName, const PublishInfo *info, int32_t callingPid)
1081 {
1082 DISC_CHECK_AND_RETURN_RET_LOGE(packageName != NULL && info != NULL, SOFTBUS_INVALID_PARAM, DISC_CONTROL,
1083 "invalid parameters");
1084 DISC_CHECK_AND_RETURN_RET_LOGW(strlen(packageName) < PKG_NAME_SIZE_MAX,
1085 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "package name too long");
1086 DISC_CHECK_AND_RETURN_RET_LOGE(!IsInnerPackageName(packageName), SOFTBUS_INVALID_PARAM,
1087 DISC_CONTROL, "package name is reserved, not allowed");
1088 DISC_CHECK_AND_RETURN_RET_LOGW(CheckPublishInfo(info) == SOFTBUS_OK, SOFTBUS_INVALID_PARAM, DISC_CONTROL,
1089 "invalid info");
1090 DISC_CHECK_AND_RETURN_RET_LOGE(g_isInited == true, SOFTBUS_DISCOVER_MANAGER_NOT_INIT, DISC_CONTROL,
1091 "manager is not inited");
1092
1093 DiscInfo *infoNode = CreateDiscInfoForPublish(info, callingPid);
1094 DISC_CHECK_AND_RETURN_RET_LOGE(infoNode != NULL, SOFTBUS_DISCOVER_MANAGER_INFO_NOT_CREATE, DISC_CONTROL,
1095 "create info failed");
1096
1097 int32_t ret = InnerPublishService(packageName, infoNode, PUBLISH_SERVICE);
1098 if (ret != SOFTBUS_OK) {
1099 FreeDiscInfo(infoNode, PUBLISH_SERVICE);
1100 }
1101 return ret;
1102 }
1103
DiscUnPublishService(const char * packageName,int32_t publishId,int32_t callingPid)1104 int32_t DiscUnPublishService(const char *packageName, int32_t publishId, int32_t callingPid)
1105 {
1106 DISC_CHECK_AND_RETURN_RET_LOGW(packageName != NULL && strlen(packageName) < PKG_NAME_SIZE_MAX,
1107 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "invalid parameters");
1108 DISC_CHECK_AND_RETURN_RET_LOGE(!IsInnerPackageName(packageName), SOFTBUS_INVALID_PARAM,
1109 DISC_CONTROL, "package name is reserved, not allowed");
1110 DISC_CHECK_AND_RETURN_RET_LOGW(g_isInited == true, SOFTBUS_DISCOVER_MANAGER_NOT_INIT, DISC_CONTROL,
1111 "manager is not inited");
1112
1113 return InnerUnPublishService(packageName, publishId, PUBLISH_SERVICE, callingPid);
1114 }
1115
DiscStartDiscovery(const char * packageName,const SubscribeInfo * info,const IServerDiscInnerCallback * cb,int32_t callingPid)1116 int32_t DiscStartDiscovery(const char *packageName, const SubscribeInfo *info,
1117 const IServerDiscInnerCallback *cb, int32_t callingPid)
1118 {
1119 DISC_CHECK_AND_RETURN_RET_LOGW(packageName != NULL && strlen(packageName) < PKG_NAME_SIZE_MAX,
1120 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "invalid package name");
1121 DISC_CHECK_AND_RETURN_RET_LOGE(!IsInnerPackageName(packageName), SOFTBUS_INVALID_PARAM,
1122 DISC_CONTROL, "package name is reserved, not allowed");
1123 DISC_CHECK_AND_RETURN_RET_LOGW(info != NULL && cb != NULL, SOFTBUS_INVALID_PARAM, DISC_CONTROL,
1124 "invalid parameters");
1125 DISC_CHECK_AND_RETURN_RET_LOGE(g_isInited == true, SOFTBUS_DISCOVER_MANAGER_NOT_INIT, DISC_CONTROL,
1126 "manager is not inited");
1127 DISC_CHECK_AND_RETURN_RET_LOGE(CheckSubscribeInfo(info) == SOFTBUS_OK, SOFTBUS_INVALID_PARAM, DISC_CONTROL,
1128 "invalid info");
1129
1130 DiscInfo *infoNode = CreateDiscInfoForSubscribe(info, callingPid);
1131 DISC_CHECK_AND_RETURN_RET_LOGE(infoNode != NULL, SOFTBUS_DISCOVER_MANAGER_INFO_NOT_CREATE, DISC_CONTROL,
1132 "create info failed");
1133
1134 int32_t ret = InnerStartDiscovery(packageName, infoNode, cb, SUBSCRIBE_SERVICE);
1135 if (ret != SOFTBUS_OK) {
1136 FreeDiscInfo(infoNode, SUBSCRIBE_SERVICE);
1137 }
1138 return ret;
1139 }
1140
DiscStopDiscovery(const char * packageName,int32_t subscribeId,int32_t callingPid)1141 int32_t DiscStopDiscovery(const char *packageName, int32_t subscribeId, int32_t callingPid)
1142 {
1143 DISC_CHECK_AND_RETURN_RET_LOGW(packageName != NULL && strlen(packageName) < PKG_NAME_SIZE_MAX,
1144 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "invalid parameters");
1145 DISC_CHECK_AND_RETURN_RET_LOGE(!IsInnerPackageName(packageName), SOFTBUS_INVALID_PARAM,
1146 DISC_CONTROL, "package name is reserved, not allowed");
1147 DISC_CHECK_AND_RETURN_RET_LOGW(g_isInited == true, SOFTBUS_DISCOVER_MANAGER_NOT_INIT, DISC_CONTROL,
1148 "manager is not inited");
1149
1150 return InnerStopDiscovery(packageName, subscribeId, SUBSCRIBE_SERVICE, callingPid);
1151 }
1152
DiscLinkStatusChanged(LinkStatus status,ExchangeMedium medium)1153 void DiscLinkStatusChanged(LinkStatus status, ExchangeMedium medium)
1154 {
1155 if (medium == COAP) {
1156 if (g_discCoapInterface != NULL) {
1157 g_discCoapInterface->LinkStatusChanged(status);
1158 }
1159 } else {
1160 DISC_LOGE(DISC_CONTROL, "not support medium=%{public}d", medium);
1161 }
1162 }
1163
DiscDeviceInfoChanged(InfoTypeChanged type)1164 void DiscDeviceInfoChanged(InfoTypeChanged type)
1165 {
1166 DISC_LOGI(DISC_CONTROL, "type=%{public}d", type);
1167 if (g_discBleInterface != NULL && g_discBleInterface->UpdateLocalDeviceInfo != NULL) {
1168 g_discBleInterface->UpdateLocalDeviceInfo(type);
1169 }
1170 if (g_discCoapInterface != NULL && g_discCoapInterface->UpdateLocalDeviceInfo != NULL) {
1171 g_discCoapInterface->UpdateLocalDeviceInfo(type);
1172 }
1173 }
1174
CreateIdContainer(int32_t id,const char * pkgName,int32_t pid)1175 static IdContainer* CreateIdContainer(int32_t id, const char *pkgName, int32_t pid)
1176 {
1177 IdContainer *container = SoftBusCalloc(sizeof(IdContainer));
1178 if (container == NULL) {
1179 DISC_LOGE(DISC_CONTROL, "container calloc failed");
1180 return NULL;
1181 }
1182
1183 ListInit(&container->node);
1184 container->id = id;
1185 container->pid = pid;
1186
1187 uint32_t nameLen = strlen(pkgName) + 1;
1188 container->pkgName = SoftBusCalloc(nameLen);
1189 if (container->pkgName == NULL) {
1190 DISC_LOGE(DISC_CONTROL, "Container pkgName calloc failed");
1191 SoftBusFree(container);
1192 return NULL;
1193 }
1194
1195 if (strcpy_s(container->pkgName, nameLen, pkgName) != EOK) {
1196 DISC_LOGE(DISC_CONTROL, "strcpy_s failed");
1197 SoftBusFree(container->pkgName);
1198 container->pkgName = NULL;
1199 SoftBusFree(container);
1200 return NULL;
1201 }
1202
1203 return container;
1204 }
1205
DestroyIdContainer(IdContainer * container)1206 static void DestroyIdContainer(IdContainer* container)
1207 {
1208 SoftBusFree(container->pkgName);
1209 SoftBusFree(container);
1210 }
1211
CleanupPublishDiscovery(ListNode * ids,ServiceType type)1212 static void CleanupPublishDiscovery(ListNode *ids, ServiceType type)
1213 {
1214 IdContainer *it = NULL;
1215 int32_t ret = SOFTBUS_DISCOVER_MANAGER_INFO_NOT_DELETE;
1216
1217 LIST_FOR_EACH_ENTRY(it, ids, IdContainer, node) {
1218 if (type == PUBLISH_SERVICE) {
1219 ret = DiscUnPublishService(it->pkgName, it->id, it->pid);
1220 DISC_LOGI(DISC_CONTROL, "clean publish pkgName=%{public}s, id=%{public}d, ret=%{public}d",
1221 it->pkgName, it->id, ret);
1222 } else if (type == SUBSCRIBE_SERVICE) {
1223 ret = DiscStopDiscovery(it->pkgName, it->id, it->pid);
1224 DISC_LOGI(DISC_CONTROL, "clean subscribe pkgName=%{public}s, id=%{public}d, ret=%{public}d",
1225 it->pkgName, it->id, ret);
1226 }
1227 }
1228 }
1229
RemoveDiscInfoByPackageName(SoftBusList * itemList,const ServiceType type,const char * pkgName,int32_t pid)1230 static void RemoveDiscInfoByPackageName(SoftBusList *itemList, const ServiceType type, const char *pkgName,
1231 int32_t pid)
1232 {
1233 ListNode ids;
1234 ListInit(&ids);
1235
1236 if (SoftBusMutexLock(&itemList->lock) != SOFTBUS_OK) {
1237 DISC_LOGE(DISC_CONTROL, "lock failed");
1238 return;
1239 }
1240
1241 DiscItem *itemNode = NULL;
1242 IdContainer *container = NULL;
1243 LIST_FOR_EACH_ENTRY(itemNode, &itemList->list, DiscItem, node) {
1244 if (pkgName != NULL) {
1245 if (strcmp(itemNode->packageName, pkgName) != 0) {
1246 continue;
1247 }
1248 }
1249
1250 DiscInfo *infoNode = NULL;
1251 LIST_FOR_EACH_ENTRY(infoNode, &itemNode->InfoList, DiscInfo, node) {
1252 if (pid != SKIP_VALID_PID_VALUE && infoNode->pid != pid) {
1253 continue;
1254 }
1255 container = CreateIdContainer(infoNode->id, itemNode->packageName, infoNode->pid);
1256 if (container == NULL) {
1257 DISC_LOGE(DISC_CONTROL, "CreateIdContainer failed");
1258 (void)SoftBusMutexUnlock(&itemList->lock);
1259 goto CLEANUP;
1260 }
1261 ListTailInsert(&ids, &container->node);
1262 }
1263 }
1264
1265 (void)SoftBusMutexUnlock(&itemList->lock);
1266 CleanupPublishDiscovery(&ids, type);
1267
1268 CLEANUP:
1269 while (!IsListEmpty(&ids)) {
1270 container = LIST_ENTRY(ids.next, IdContainer, node);
1271 ListDelete(&container->node);
1272 DestroyIdContainer(container);
1273 }
1274 }
1275
RemoveAllDiscInfoForPublish(void)1276 static void RemoveAllDiscInfoForPublish(void)
1277 {
1278 RemoveDiscInfoByPackageName(g_publishInfoList, PUBLISH_SERVICE, NULL, SKIP_VALID_PID_VALUE);
1279 DestroySoftBusList(g_publishInfoList);
1280 g_publishInfoList = NULL;
1281 }
1282
RemoveAllDiscInfoForDiscovery(void)1283 static void RemoveAllDiscInfoForDiscovery(void)
1284 {
1285 RemoveDiscInfoByPackageName(g_discoveryInfoList, SUBSCRIBE_SERVICE, NULL, SKIP_VALID_PID_VALUE);
1286 DestroySoftBusList(g_discoveryInfoList);
1287 g_discoveryInfoList = NULL;
1288 }
1289
RemoveDiscInfoForPublish(const char * pkgName,int32_t pid)1290 static void RemoveDiscInfoForPublish(const char *pkgName, int32_t pid)
1291 {
1292 RemoveDiscInfoByPackageName(g_publishInfoList, PUBLISH_SERVICE, pkgName, pid);
1293 }
1294
RemoveDiscInfoForDiscovery(const char * pkgName,int32_t pid)1295 static void RemoveDiscInfoForDiscovery(const char *pkgName, int32_t pid)
1296 {
1297 RemoveDiscInfoByPackageName(g_discoveryInfoList, SUBSCRIBE_SERVICE, pkgName, pid);
1298 }
1299
DiscMgrDeathCallback(const char * pkgName,int32_t pid)1300 void DiscMgrDeathCallback(const char *pkgName, int32_t pid)
1301 {
1302 DISC_CHECK_AND_RETURN_LOGE(pkgName != NULL, DISC_CONTROL, "pkgName is null");
1303 DISC_CHECK_AND_RETURN_LOGE(!IsInnerPackageName(pkgName), DISC_CONTROL, "package name is reserved, not allowed");
1304 DISC_CHECK_AND_RETURN_LOGE(g_isInited == true, DISC_CONTROL, "disc manager is not inited");
1305
1306 DISC_LOGD(DISC_CONTROL, "pkg is dead. pkgName=%{public}s", pkgName);
1307 DISC_CHECK_AND_RETURN_LOGE(pid != getpid(), DISC_CONTROL, "pid is different");
1308 RemoveDiscInfoForPublish(pkgName, pid);
1309 RemoveDiscInfoForDiscovery(pkgName, pid);
1310 }
1311
DiscMgrInit(void)1312 int32_t DiscMgrInit(void)
1313 {
1314 DISC_CHECK_AND_RETURN_RET_LOGE(g_isInited == false, SOFTBUS_OK, DISC_INIT, "already inited");
1315
1316 g_discMgrMediumCb.OnDeviceFound = DiscOnDeviceFound;
1317
1318 g_discCoapInterface = DiscCoapInit(&g_discMgrMediumCb);
1319 g_discBleInterface = DiscBleInit(&g_discMgrMediumCb);
1320 g_discUsbInterface = DiscUsbDispatcherInit(&g_discMgrMediumCb);
1321
1322 DISC_CHECK_AND_RETURN_RET_LOGE(g_discBleInterface != NULL || g_discCoapInterface != NULL ||
1323 g_discUsbInterface != NULL, SOFTBUS_DISCOVER_MANAGER_INIT_FAIL, DISC_INIT, "ble coap and usb init failed");
1324
1325 g_publishInfoList = CreateSoftBusList();
1326 DISC_CHECK_AND_RETURN_RET_LOGE(g_publishInfoList != NULL, SOFTBUS_DISCOVER_MANAGER_INIT_FAIL, DISC_INIT,
1327 "init publish info list failed");
1328 g_discoveryInfoList = CreateSoftBusList();
1329 if (g_discoveryInfoList == NULL) {
1330 DISC_LOGE(DISC_INIT, "init discovery Info List failed");
1331 DestroySoftBusList(g_publishInfoList);
1332 g_publishInfoList = NULL;
1333 return SOFTBUS_DISCOVER_MANAGER_INIT_FAIL;
1334 }
1335
1336 for (int32_t i = 0; i < CAPABILITY_MAX_BITNUM; i++) {
1337 ListInit(&g_capabilityList[i]);
1338 }
1339
1340 g_isInited = true;
1341 return SOFTBUS_OK;
1342 }
1343
DiscMgrDeinit(void)1344 void DiscMgrDeinit(void)
1345 {
1346 DISC_CHECK_AND_RETURN_LOGW(g_isInited == true, DISC_INIT, "disc manager is not inited");
1347
1348 RemoveAllDiscInfoForPublish();
1349 RemoveAllDiscInfoForDiscovery();
1350
1351 g_discCoapInterface = NULL;
1352 g_discBleInterface = NULL;
1353 g_discUsbInterface = NULL;
1354
1355 DiscCoapDeinit();
1356 DiscBleDeinit();
1357 DiscUsbDispatcherDeinit();
1358
1359 g_isInited = false;
1360 DISC_LOGI(DISC_INIT, "disc manager deinit success");
1361 }
1362
DiscSetDisplayName(const char * pkgName,const char * nameData,uint32_t len)1363 int32_t DiscSetDisplayName(const char *pkgName, const char *nameData, uint32_t len)
1364 {
1365 DISC_CHECK_AND_RETURN_RET_LOGE(
1366 (pkgName != NULL && nameData != NULL), SOFTBUS_INVALID_PARAM, DISC_CONTROL, "invalid param");
1367 int ret = SOFTBUS_PARSE_JSON_ERR;
1368 if (memset_s(&g_displayName, sizeof(g_displayName), 0, sizeof(g_displayName)) != EOK) {
1369 DISC_LOGE(DISC_CONTROL, "DiscSetDisplayName failed");
1370 return SOFTBUS_MEM_ERR;
1371 }
1372 cJSON *json = cJSON_ParseWithLength(nameData, len);
1373 DISC_CHECK_AND_RETURN_RET_LOGE(json != NULL, SOFTBUS_PARSE_JSON_ERR, DISC_CONTROL, "parse cJSON failed");
1374
1375 if (!GetJsonObjectStringItem(json, JSON_KEY_RAW_NAME, g_displayName.raw, DISPLAY_NAME_BUF_LEN)) {
1376 DISC_LOGE(DISC_CONTROL, "GetJsonObjectStringItem raw name failed. displayName=%{public}s", g_displayName.raw);
1377 goto CLEANUP;
1378 }
1379
1380 if (LnnSetLocalDeviceName(g_displayName.raw) != SOFTBUS_OK) {
1381 DISC_LOGE(DISC_CONTROL, "LnnSetLocalDeviceName fail");
1382 goto CLEANUP;
1383 }
1384
1385 if (!GetJsonObjectStringItem(json, JSON_KEY_NAME_LEN_18, g_displayName.name18, sizeof(g_displayName.name18))) {
1386 DISC_LOGE(DISC_CONTROL, "GetJsonObjectStringItem name18 failed. displayName=%{public}s", g_displayName.name18);
1387 goto CLEANUP;
1388 }
1389
1390 if (!GetJsonObjectStringItem(json, JSON_KEY_NAME_LEN_21, g_displayName.name21, sizeof(g_displayName.name21))) {
1391 DISC_LOGE(DISC_CONTROL, "GetJsonObjectStringItem name21 failed. displayName=%{public}s", g_displayName.name21);
1392 goto CLEANUP;
1393 }
1394
1395 if (!GetJsonObjectStringItem(json, JSON_KEY_NAME_LEN_24, g_displayName.name24, sizeof(g_displayName.name24))) {
1396 DISC_LOGE(DISC_CONTROL, "GetJsonObjectStringItem name24 failed. displayName=%{public}s", g_displayName.name24);
1397 goto CLEANUP;
1398 }
1399 DiscDeviceInfoChanged(TYPE_LOCAL_DEVICE_NAME);
1400 ret = SOFTBUS_OK;
1401 CLEANUP:
1402 cJSON_Delete(json);
1403 return ret;
1404 }
1405
DiscGetDisplayName(char * displayName,uint32_t length,uint32_t remainLen)1406 int32_t DiscGetDisplayName(char *displayName, uint32_t length, uint32_t remainLen)
1407 {
1408 DISC_CHECK_AND_RETURN_RET_LOGE((displayName != NULL && remainLen > 0 && remainLen <= DISPLAY_NAME_BUF_LEN),
1409 SOFTBUS_INVALID_PARAM, DISC_CONTROL, "invalid param");
1410 char *source = NULL;
1411 uint32_t len = 0;
1412 if (remainLen > strlen(g_displayName.raw)) {
1413 source = g_displayName.raw;
1414 len = strlen(g_displayName.raw);
1415 goto END;
1416 }
1417 if (remainLen > DISPLAY_NAME_LEN_24) {
1418 source = g_displayName.name24;
1419 len = DISPLAY_NAME_LEN_24;
1420 goto END;
1421 }
1422 if (remainLen > DISPLAY_NAME_LEN_21) {
1423 source = g_displayName.name21;
1424 len = DISPLAY_NAME_LEN_21;
1425 goto END;
1426 }
1427 if (remainLen > DISPLAY_NAME_LEN_18) {
1428 source = g_displayName.name18;
1429 len = DISPLAY_NAME_LEN_18;
1430 goto END;
1431 } else {
1432 source = g_displayName.name18;
1433 len = remainLen;
1434 }
1435
1436 END:
1437 DISC_CHECK_AND_RETURN_RET_LOGW(len < length, SOFTBUS_INVALID_PARAM, DISC_CONTROL, "length too long");
1438 if (memcpy_s(displayName, length, source, len) != EOK) {
1439 DISC_LOGE(DISC_CONTROL, "memcpy reply fail");
1440 return SOFTBUS_MEM_ERR;
1441 }
1442 displayName[len] = '\0';
1443 return SOFTBUS_OK;
1444 }
1445