• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021 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 "p2plink_interface.h"
17 
18 #include <securec.h>
19 #include <semaphore.h>
20 
21 #include "p2plink_common.h"
22 #include "p2plink_device.h"
23 #include "p2plink_loop.h"
24 #include "p2plink_manager.h"
25 #include "p2plink_negotiation.h"
26 
27 #include "softbus_adapter_mem.h"
28 #include "softbus_def.h"
29 #include "softbus_errcode.h"
30 #include "softbus_log.h"
31 
32 typedef struct {
33     RoleIsConflictInfo requestInfo;
34     sem_t wait;
35     int32_t result;
36 } RoleIsConfictLoopInfo;
37 
38 typedef struct {
39     char peerIp[P2P_IP_LEN];
40     char peerMac[P2P_MAC_LEN];
41     sem_t wait;
42 } QueryP2pMacLoopInfo;
43 
44 typedef struct {
45     char peerMac[P2P_MAC_LEN];
46     int32_t result;
47     sem_t wait;
48 } QueryP2pDevIsOnline;
49 
P2pLinkGetRequestId(void)50 int32_t P2pLinkGetRequestId(void)
51 {
52     static int32_t requestId = 0;
53     requestId++;
54     if (requestId == 0) {
55         requestId++;
56     }
57     return requestId;
58 }
59 
P2pLinkInit(void)60 int32_t P2pLinkInit(void)
61 {
62     return P2pLinkManagerInit();
63 }
64 
P2pLinkConnectDevice(const P2pLinkConnectInfo * info)65 int32_t P2pLinkConnectDevice(const P2pLinkConnectInfo *info)
66 {
67     int32_t ret;
68 
69     if (info == NULL) {
70         return SOFTBUS_ERR;
71     }
72     ConnectingNode *arg = SoftBusCalloc(sizeof(ConnectingNode));
73     if (arg == NULL) {
74         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "P2p Link connect malloc fail.");
75         return SOFTBUS_ERR;
76     }
77     ret = memcpy_s(&arg->connInfo, sizeof(P2pLinkConnectInfo), info, sizeof(P2pLinkConnectInfo));
78     if (ret != SOFTBUS_OK) {
79         SoftBusFree(arg);
80         return SOFTBUS_ERR;
81     }
82     SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_INFO, "conn info reqid %d, pid %d role %d",
83                info->requestId, info->pid, info->expectedRole);
84     ret = P2pLoopProc(P2pLinkLoopConnectDevice, (void *)arg, P2PLOOP_INTERFACE_LOOP_CONNECT);
85     if (ret != SOFTBUS_OK) {
86         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "P2pLinkLoopConnectDevice loop fail.");
87         SoftBusFree(arg);
88     }
89     SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_INFO, "P2pLinkLoopConnectDevice loop ok.");
90     return ret;
91 }
92 
P2pLinkDisconnectDevice(const P2pLinkDisconnectInfo * info)93 int32_t P2pLinkDisconnectDevice(const P2pLinkDisconnectInfo *info)
94 {
95     int32_t ret;
96 
97     if (info == NULL) {
98         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "P2p Link Disconnect arg err.");
99         return SOFTBUS_ERR;
100     }
101     P2pLinkDisconnectInfo *arg = SoftBusCalloc(sizeof(P2pLinkDisconnectInfo));
102     if (arg == NULL) {
103         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "P2p Link Disconnect malloc fail.");
104         return SOFTBUS_ERR;
105     }
106     SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_INFO, "disconn info, pid %d", info->pid);
107     ret = memcpy_s(arg, sizeof(P2pLinkDisconnectInfo), info, sizeof(P2pLinkDisconnectInfo));
108     if (ret != SOFTBUS_OK) {
109         SoftBusFree(arg);
110         return SOFTBUS_ERR;
111     }
112     ret = P2pLoopProc(P2pLinkLoopDisconnectDev, (void *)arg, P2PLOOP_INTERFACE_LOOP_DISCONNECT);
113     if (ret != SOFTBUS_OK) {
114         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "P2pLinkLoopConnectDevice loop fail.");
115         SoftBusFree(arg);
116         return ret;
117     }
118     SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_INFO, "disconnect loop ok.");
119     return SOFTBUS_OK;
120 }
121 
LoopP2pLinkIsRoleConfict(P2pLoopMsg msgType,void * arg)122 static void LoopP2pLinkIsRoleConfict(P2pLoopMsg msgType, void *arg)
123 {
124     RoleIsConfictLoopInfo *loopInfo = NULL;
125     ConnectedNode *connedItem = NULL;
126     RoleIsConflictInfo *requestInfo = NULL;
127 
128     (void)msgType;
129     if (arg == NULL) {
130         return;
131     }
132 
133     loopInfo = (RoleIsConfictLoopInfo *)arg;
134     if (P2pLinkIsEnable() == false) {
135         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_INFO, "in role p2p state is closed");
136         loopInfo->result = SOFTBUS_ERR;
137         sem_post(&loopInfo->wait);
138         return;
139     }
140     requestInfo = &loopInfo->requestInfo;
141     connedItem = P2pLinkGetConnedDevByMac(requestInfo->peerMac);
142     if (connedItem != NULL) {
143         if (strlen(connedItem->peerIp) == 0) {
144             SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_INFO, "dev is used by others");
145             loopInfo->result = ERROR_LINK_USED_BY_ANOTHER_SERVICE;
146             sem_post(&loopInfo->wait);
147             return;
148         }
149         if ((requestInfo->expectedRole != ROLE_AUTO) &&
150             (requestInfo->expectedRole != P2pLinkGetRole())) {
151             SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_INFO, "role is confict");
152             loopInfo->result = ERROR_CONNECTED_WITH_MISMATCHED_ROLE;
153             sem_post(&loopInfo->wait);
154             return;
155         }
156         loopInfo->result = SOFTBUS_OK;
157         sem_post(&loopInfo->wait);
158     } else {
159         loopInfo->result = P2pLinkNegoGetFinalRole(requestInfo->peerRole, requestInfo->peerRole,
160             requestInfo->peerGoMac, requestInfo->isBridgeSupported);
161         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_INFO, "P2pLinkNegoGetFinalRole ret %d", loopInfo->result);
162         sem_post(&loopInfo->wait);
163     }
164     return;
165 }
166 
P2pLinkIsRoleConflict(const RoleIsConflictInfo * info)167 int32_t P2pLinkIsRoleConflict(const RoleIsConflictInfo *info)
168 {
169     RoleIsConfictLoopInfo loopInfo;
170     (void)memset_s(&loopInfo, sizeof(loopInfo), 0, sizeof(loopInfo));
171     int32_t ret;
172 
173     if (info == NULL) {
174         return SOFTBUS_ERR;
175     }
176 
177     ret = memcpy_s(&loopInfo.requestInfo, sizeof(loopInfo.requestInfo),
178                    info, sizeof(RoleIsConflictInfo));
179     if (ret != SOFTBUS_OK) {
180         return SOFTBUS_ERR;
181     }
182 
183     if (sem_init(&loopInfo.wait, 0, 0)) {
184         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_INFO, "sem init fail");
185         return SOFTBUS_ERR;
186     }
187 
188     ret = P2pLoopProc(LoopP2pLinkIsRoleConfict, (void *)&loopInfo, P2PLOOP_INTERFACE_ROLE_CONFICT);
189     if (ret != SOFTBUS_OK) {
190         sem_destroy(&loopInfo.wait);
191         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_INFO, "LoopP2pLinkIsRoleConfict loop fail");
192         return SOFTBUS_ERR;
193     }
194     sem_wait(&loopInfo.wait);
195     sem_destroy(&loopInfo.wait);
196     SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_INFO, "role confict res %d.", loopInfo.result);
197     if (loopInfo.result < 0) {
198         return SOFTBUS_ERR;
199     }
200     return SOFTBUS_OK;
201 }
202 
LoopP2pLinkQueryIpByMac(P2pLoopMsg msgType,void * arg)203 static void LoopP2pLinkQueryIpByMac(P2pLoopMsg msgType, void *arg)
204 {
205     QueryP2pMacLoopInfo *queryInfo = NULL;
206     ConnectedNode *connedItem = NULL;
207 
208     (void)msgType;
209     if (arg == NULL) {
210         return;
211     }
212 
213     queryInfo = (QueryP2pMacLoopInfo *)arg;
214     connedItem = P2pLinkGetConnedDevByPeerIp(queryInfo->peerIp);
215     if (connedItem != NULL) {
216         if (strcpy_s(queryInfo->peerMac, sizeof(queryInfo->peerMac), connedItem->peerMac) != EOK) {
217             SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "strcpy fail.");
218         }
219     }
220     sem_post(&queryInfo->wait);
221     return;
222 }
223 
P2pLinkGetPeerMacByPeerIp(const char * peerIp,char * peerMac,int32_t macLen)224 int32_t P2pLinkGetPeerMacByPeerIp(const char *peerIp, char* peerMac, int32_t macLen)
225 {
226     QueryP2pMacLoopInfo queryInfo;
227     int32_t ret;
228 
229     if (peerIp == NULL || peerMac == NULL) {
230         return SOFTBUS_ERR;
231     }
232     if (P2pLinkGetRole() == ROLE_NONE) {
233         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "p2p role is none");
234         return SOFTBUS_ERR;
235     }
236 
237     (void)memset_s(&queryInfo, sizeof(queryInfo), 0, sizeof(queryInfo));
238     ret = strcpy_s(queryInfo.peerIp, sizeof(queryInfo.peerIp), peerIp);
239     if (ret != EOK) {
240         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "copy fail");
241         return SOFTBUS_ERR;
242     }
243 
244     if (sem_init(&queryInfo.wait, 0, 0)) {
245         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "sem init fail");
246         return SOFTBUS_ERR;
247     }
248 
249     ret = P2pLoopProc(LoopP2pLinkQueryIpByMac, (void *)&queryInfo, P2PLOOP_MSG_PROC);
250     if (ret != SOFTBUS_OK) {
251         sem_destroy(&queryInfo.wait);
252         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "LoopP2pLinkIsRoleConfict loop fail");
253         return SOFTBUS_ERR;
254     }
255     sem_wait(&queryInfo.wait);
256     sem_destroy(&queryInfo.wait);
257     if (strlen(queryInfo.peerMac) == 0) {
258         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "peerMac is null");
259         return SOFTBUS_ERR;
260     }
261     ret = strcpy_s(peerMac, macLen, queryInfo.peerMac);
262     if (ret != EOK) {
263         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "strcpy fail");
264         return SOFTBUS_ERR;
265     }
266     SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_INFO, "query ok ip");
267     return SOFTBUS_OK;
268 }
269 
P2pLinkRegPeerDevStateChange(const P2pLinkPeerDevStateCb * cb)270 void P2pLinkRegPeerDevStateChange(const P2pLinkPeerDevStateCb *cb)
271 {
272     if (cb == NULL) {
273         return;
274     }
275     P2pLinkSetDevStateCallback(cb);
276 }
277 
P2pLinkGetLocalIp(char * localIp,int32_t localIpLen)278 int32_t P2pLinkGetLocalIp(char *localIp, int32_t localIpLen)
279 {
280     char tmpIp[P2P_IP_LEN] = {0};
281     int32_t ret;
282 
283     ret = strcpy_s(tmpIp, sizeof(tmpIp), P2pLinkGetMyIp());
284     if (ret != EOK) {
285         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "get myIp fail");
286         return SOFTBUS_ERR;
287     }
288 
289     if (strlen(tmpIp) == 0) {
290         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "myIp is null");
291         return SOFTBUS_ERR;
292     }
293 
294     ret = strcpy_s(localIp, localIpLen, tmpIp);
295     if (ret != EOK) {
296         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "copy tmpIp fail");
297         return SOFTBUS_ERR;
298     }
299     return SOFTBUS_OK;
300 }
301 
LoopP2pLinkQueryDevOnline(P2pLoopMsg msgType,void * arg)302 static void LoopP2pLinkQueryDevOnline(P2pLoopMsg msgType, void *arg)
303 {
304     QueryP2pDevIsOnline *queryInfo = NULL;
305     ConnectedNode *connedItem = NULL;
306 
307     (void)msgType;
308     if (arg == NULL) {
309         return;
310     }
311 
312     queryInfo = (QueryP2pDevIsOnline *)arg;
313     connedItem = P2pLinkGetConnedDevByMac(queryInfo->peerMac);
314     if (connedItem != NULL) {
315         queryInfo->result = SOFTBUS_OK;
316     } else {
317         queryInfo->result = SOFTBUS_ERR;
318     }
319     sem_post(&queryInfo->wait);
320     return;
321 }
322 
P2pLinkQueryDevIsOnline(const char * peerMac)323 int32_t P2pLinkQueryDevIsOnline(const char *peerMac)
324 {
325     QueryP2pDevIsOnline queryInfo;
326     int32_t ret;
327 
328     if (peerMac == NULL) {
329         return SOFTBUS_ERR;
330     }
331 
332     (void)memset_s(&queryInfo, sizeof(queryInfo), 0, sizeof(queryInfo));
333     if (P2pLinkGetRole() == ROLE_NONE) {
334         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "isonline role is none");
335         return SOFTBUS_ERR;
336     }
337 
338     (void)memset_s(&queryInfo, sizeof(queryInfo), 0, sizeof(queryInfo));
339     ret = strcpy_s(queryInfo.peerMac, sizeof(queryInfo.peerMac), peerMac);
340     if (ret != EOK) {
341         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "copy fail");
342         return SOFTBUS_ERR;
343     }
344 
345     if (sem_init(&queryInfo.wait, 0, 0)) {
346         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "sem init fail");
347         return SOFTBUS_ERR;
348     }
349 
350     ret = P2pLoopProc(LoopP2pLinkQueryDevOnline, (void *)&queryInfo, P2PLOOP_MSG_PROC);
351     if (ret != SOFTBUS_OK) {
352         sem_destroy(&queryInfo.wait);
353         SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_ERROR, "LoopP2pLinkIsRoleConfict loop fail");
354         return SOFTBUS_ERR;
355     }
356     sem_wait(&queryInfo.wait);
357     sem_destroy(&queryInfo.wait);
358     SoftBusLog(SOFTBUS_LOG_CONN, SOFTBUS_LOG_INFO, "query result %d", queryInfo.result);
359     return queryInfo.result;
360 }
361