1 /*
2  * Copyright (c) 2022 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 "auth_request.h"
17 
18 #include <securec.h>
19 
20 #include "auth_common.h"
21 #include "auth_log.h"
22 #include "softbus_adapter_mem.h"
23 #include "softbus_def.h"
24 
25 static ListNode g_authRequestList = {&g_authRequestList, &g_authRequestList};
26 
FindAuthRequestByRequestId(uint64_t requestId)27 static AuthRequest *FindAuthRequestByRequestId(uint64_t requestId)
28 {
29     AuthRequest *item = NULL;
30     LIST_FOR_EACH_ENTRY(item, &g_authRequestList, AuthRequest, node) {
31         if (item->requestId == requestId) {
32             return item;
33         }
34     }
35     return NULL;
36 }
37 
GetAuthRequestWaitNum(AuthRequest * request)38 static uint32_t GetAuthRequestWaitNum(AuthRequest *request)
39 {
40     uint32_t num = 0;
41     AuthRequest *item = NULL;
42     AuthRequest *next = NULL;
43     LIST_FOR_EACH_ENTRY_SAFE(item, next, &g_authRequestList, AuthRequest, node) {
44         if (item->type != request->type || !CompareConnInfo(&request->connInfo, &item->connInfo, true)) {
45             continue;
46         }
47         if (item->requestId == request->requestId) {
48             num++;
49             continue;
50         }
51         if (request->addTime - item->addTime < AUTH_REQUEST_TIMTOUR) {
52             AUTH_LOGD(AUTH_CONN,
53                 "The two request addr are same. requestId1=%{public}u, requestId2=%{public}u",
54                 request->requestId, item->requestId);
55             num++;
56             continue;
57         }
58         if (CheckAuthConnCallback(&item->connCb)) {
59             item->connCb.onConnOpenFailed(item->requestId, SOFTBUS_AUTH_CONN_FAIL);
60         } else if (CheckVerifyCallback(&item->verifyCb)) {
61             item->verifyCb.onVerifyFailed(item->requestId, SOFTBUS_AUTH_CONN_FAIL);
62         }
63         ListDelete(&item->node);
64         SoftBusFree(item);
65         num++;
66     }
67     return num;
68 }
69 
AddAuthRequest(const AuthRequest * request)70 uint32_t AddAuthRequest(const AuthRequest *request)
71 {
72     CHECK_NULL_PTR_RETURN_VALUE(request, 0);
73     AuthRequest *newRequest = SoftBusCalloc(sizeof(AuthRequest));
74     if (newRequest == NULL) {
75         AUTH_LOGE(AUTH_CONN, "malloc AuthRequest fail");
76         return 0;
77     }
78     *newRequest = *request;
79     if (!RequireAuthLock()) {
80         SoftBusFree(newRequest);
81         return 0;
82     }
83     newRequest->addTime = GetCurrentTimeMs();
84     ListTailInsert(&g_authRequestList, &newRequest->node);
85     uint32_t waitNum = GetAuthRequestWaitNum(newRequest);
86     ReleaseAuthLock();
87     return waitNum;
88 }
89 
GetAuthRequest(uint32_t requestId,AuthRequest * request)90 int32_t GetAuthRequest(uint32_t requestId, AuthRequest *request)
91 {
92     CHECK_NULL_PTR_RETURN_VALUE(request, SOFTBUS_INVALID_PARAM);
93     if (!RequireAuthLock()) {
94         return SOFTBUS_LOCK_ERR;
95     }
96     AuthRequest *item = FindAuthRequestByRequestId(requestId);
97     if (item == NULL) {
98         ReleaseAuthLock();
99         return SOFTBUS_NOT_FIND;
100     }
101     *request = *item;
102     ReleaseAuthLock();
103     return SOFTBUS_OK;
104 }
105 
GetAuthRequestNoLock(uint32_t requestId,AuthRequest * request)106 int32_t GetAuthRequestNoLock(uint32_t requestId, AuthRequest *request)
107 {
108     CHECK_NULL_PTR_RETURN_VALUE(request, SOFTBUS_INVALID_PARAM);
109     AuthRequest *item = FindAuthRequestByRequestId(requestId);
110     if (item == NULL) {
111         return SOFTBUS_NOT_FIND;
112     }
113     *request = *item;
114     return SOFTBUS_OK;
115 }
116 
FindAuthRequestByConnInfo(const AuthConnInfo * connInfo,AuthRequest * request)117 int32_t FindAuthRequestByConnInfo(const AuthConnInfo *connInfo, AuthRequest *request)
118 {
119     CHECK_NULL_PTR_RETURN_VALUE(connInfo, SOFTBUS_INVALID_PARAM);
120     CHECK_NULL_PTR_RETURN_VALUE(request, SOFTBUS_INVALID_PARAM);
121     if (!RequireAuthLock()) {
122         return SOFTBUS_LOCK_ERR;
123     }
124     AuthRequest *item = NULL;
125     LIST_FOR_EACH_ENTRY(item, &g_authRequestList, AuthRequest, node) {
126         if (item->type != REQUEST_TYPE_VERIFY ||
127             !CompareConnInfo(&item->connInfo, connInfo, true)) {
128             continue;
129         }
130         *request = *item;
131         ReleaseAuthLock();
132         return SOFTBUS_OK;
133     }
134     ReleaseAuthLock();
135     return SOFTBUS_NOT_FIND;
136 }
137 
FindAndDelAuthRequestByConnInfo(uint32_t requestId,const AuthConnInfo * connInfo)138 int32_t FindAndDelAuthRequestByConnInfo(uint32_t requestId, const AuthConnInfo *connInfo)
139 {
140     CHECK_NULL_PTR_RETURN_VALUE(connInfo, SOFTBUS_INVALID_PARAM);
141     if (!RequireAuthLock()) {
142         return SOFTBUS_LOCK_ERR;
143     }
144     AuthRequest *item = NULL;
145     AuthRequest *next = NULL;
146     LIST_FOR_EACH_ENTRY_SAFE(item, next, &g_authRequestList, AuthRequest, node) {
147         if (!CompareConnInfo(&item->connInfo, connInfo, true)) {
148             continue;
149         }
150         if (item->requestId == requestId) {
151             ListDelete(&item->node);
152             SoftBusFree(item);
153             continue;
154         }
155         if (CheckAuthConnCallback(&item->connCb)) {
156             item->connCb.onConnOpenFailed(item->requestId, SOFTBUS_AUTH_CONN_FAIL);
157         } else if (CheckVerifyCallback(&item->verifyCb)) {
158             item->verifyCb.onVerifyFailed(item->requestId, SOFTBUS_AUTH_CONN_FAIL);
159         }
160         ListDelete(&item->node);
161         SoftBusFree(item);
162     }
163     ReleaseAuthLock();
164     return SOFTBUS_NOT_FIND;
165 }
166 
DelAuthRequest(uint32_t requestId)167 void DelAuthRequest(uint32_t requestId)
168 {
169     if (!RequireAuthLock()) {
170         return;
171     }
172     AuthRequest *item = FindAuthRequestByRequestId(requestId);
173     if (item == NULL) {
174         ReleaseAuthLock();
175         return;
176     }
177     AUTH_LOGD(AUTH_CONN, "del auth request requestId=%{public}u", requestId);
178     ListDelete(&item->node);
179     SoftBusFree(item);
180     ReleaseAuthLock();
181 }
182 
ClearAuthRequest(void)183 void ClearAuthRequest(void)
184 {
185     if (!RequireAuthLock()) {
186         return;
187     }
188     AuthRequest *item = NULL;
189     AuthRequest *next = NULL;
190     LIST_FOR_EACH_ENTRY_SAFE(item, next, &g_authRequestList, AuthRequest, node) {
191         ListDelete(&item->node);
192         SoftBusFree(item);
193     }
194     ListInit(&g_authRequestList);
195     ReleaseAuthLock();
196 }
197 
CheckVerifyCallback(const AuthVerifyCallback * verifyCb)198 bool CheckVerifyCallback(const AuthVerifyCallback *verifyCb)
199 {
200     if (verifyCb == NULL) {
201         return false;
202     }
203     if (verifyCb->onVerifyPassed == NULL || verifyCb->onVerifyFailed == NULL) {
204         return false;
205     }
206     return true;
207 }
208 
CheckAuthConnCallback(const AuthConnCallback * connCb)209 bool CheckAuthConnCallback(const AuthConnCallback *connCb)
210 {
211     if (connCb == NULL) {
212         return false;
213     }
214     if (connCb->onConnOpened == NULL || connCb->onConnOpenFailed == NULL) {
215         return false;
216     }
217     return true;
218 }
219 
PerformVerifyCallback(uint32_t requestId,int32_t result,AuthHandle authHandle,const NodeInfo * info)220 void PerformVerifyCallback(uint32_t requestId, int32_t result, AuthHandle authHandle, const NodeInfo *info)
221 {
222     if (authHandle.type < AUTH_LINK_TYPE_WIFI || authHandle.type >= AUTH_LINK_TYPE_MAX) {
223         AUTH_LOGE(AUTH_CONN, "authHandle type error");
224         return;
225     }
226     AuthRequest request;
227     if (GetAuthRequest(requestId, &request) != SOFTBUS_OK) {
228         return;
229     }
230     if (!CheckVerifyCallback(&request.verifyCb)) {
231         return;
232     }
233     if (result == SOFTBUS_OK) {
234         request.verifyCb.onVerifyPassed(request.requestId, authHandle, info);
235     } else {
236         request.verifyCb.onVerifyFailed(request.requestId, result);
237     }
238 }
239 
PerformAuthConnCallback(uint32_t requestId,int32_t result,int64_t authId)240 void PerformAuthConnCallback(uint32_t requestId, int32_t result, int64_t authId)
241 {
242     AuthRequest request;
243     if (GetAuthRequest(requestId, &request) != SOFTBUS_OK) {
244         AUTH_LOGE(AUTH_CONN, "get auth request failed");
245         return;
246     }
247     if (!CheckAuthConnCallback(&request.connCb)) {
248         AUTH_LOGE(AUTH_CONN, "check connCb failed");
249         return;
250     }
251     AuthHandle authHandle = { .authId = authId, .type = request.connInfo.type };
252     if (result == SOFTBUS_OK) {
253         request.connCb.onConnOpened(request.requestId, authHandle);
254     } else {
255         request.connCb.onConnOpenFailed(request.requestId, result);
256     }
257 }
258