1 /*
2 * Copyright (c) 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 "auth_normalize_request.h"
17
18 #include <securec.h>
19
20 #include "anonymizer.h"
21 #include "auth_common.h"
22 #include "auth_manager.h"
23 #include "auth_log.h"
24 #include "softbus_adapter_mem.h"
25 #include "softbus_def.h"
26
27 #define UDID_SHORT_HASH_STR 16
28
29 static ListNode g_normalizeRequestList = {&g_normalizeRequestList, &g_normalizeRequestList};
30
GetSameRequestNum(char * udidHash)31 static uint32_t GetSameRequestNum(char *udidHash)
32 {
33 uint32_t num = 0;
34 NormalizeRequest *item = NULL;
35 char *anonyUdidHash = NULL;
36 Anonymize(udidHash, &anonyUdidHash);
37 AUTH_LOGI(AUTH_HICHAIN, "udidHash=%{public}s", anonyUdidHash);
38 AnonymizeFree(anonyUdidHash);
39 LIST_FOR_EACH_ENTRY(item, &g_normalizeRequestList, NormalizeRequest, node) {
40 if (strncmp(item->udidHash, udidHash, UDID_SHORT_HASH_STR) != 0) {
41 continue;
42 }
43 num++;
44 }
45 return num;
46 }
47
GetRequestListByUdidHash(char * udidHash,bool isNeedClear,NormalizeRequest ** requests,uint32_t * num)48 static int32_t GetRequestListByUdidHash(char *udidHash, bool isNeedClear,
49 NormalizeRequest **requests, uint32_t *num)
50 {
51 if (udidHash == NULL) {
52 AUTH_LOGE(AUTH_HICHAIN, "udidHash is null");
53 return SOFTBUS_INVALID_PARAM;
54 }
55 *num = GetSameRequestNum(udidHash);
56 if ((*num) == 0) {
57 AUTH_LOGI(AUTH_HICHAIN, "no other requests exist.");
58 return SOFTBUS_OK;
59 }
60 *requests = (NormalizeRequest *)SoftBusCalloc(sizeof(NormalizeRequest) * (*num));
61 if (*requests == NULL) {
62 AUTH_LOGE(AUTH_HICHAIN, "malloc fail.");
63 return SOFTBUS_MEM_ERR;
64 }
65 NormalizeRequest *item = NULL;
66 NormalizeRequest *next = NULL;
67 uint32_t index = 0;
68 LIST_FOR_EACH_ENTRY_SAFE(item, next, &g_normalizeRequestList, NormalizeRequest, node) {
69 if (strncmp(item->udidHash, udidHash, UDID_SHORT_HASH_STR) != 0 || index >= (*num)) {
70 continue;
71 }
72 (*requests)[index++] = *item;
73 if (!isNeedClear) {
74 continue;
75 }
76 ListDelete(&item->node);
77 SoftBusFree(item);
78 }
79 return SOFTBUS_OK;
80 }
81
FindAndDelNormalizeRequest(int64_t authSeq,NormalizeRequest * request)82 static int32_t FindAndDelNormalizeRequest(int64_t authSeq, NormalizeRequest *request)
83 {
84 if (request == NULL) {
85 return SOFTBUS_INVALID_PARAM;
86 }
87 NormalizeRequest *item = NULL;
88 LIST_FOR_EACH_ENTRY(item, &g_normalizeRequestList, NormalizeRequest, node) {
89 if (item->authSeq == authSeq) {
90 *request = *item;
91 ListDelete(&item->node);
92 SoftBusFree(item);
93 return SOFTBUS_OK;
94 }
95 }
96 return SOFTBUS_ERR;
97 }
98
GetNormalizeRequestList(int64_t authSeq,bool isNeedClear,NormalizeRequest * request,NormalizeRequest ** requests,uint32_t * num)99 static int32_t GetNormalizeRequestList(int64_t authSeq, bool isNeedClear, NormalizeRequest *request,
100 NormalizeRequest **requests, uint32_t *num)
101 {
102 if (num == NULL) {
103 return SOFTBUS_INVALID_PARAM;
104 }
105 if (!RequireAuthLock()) {
106 AUTH_LOGE(AUTH_HICHAIN, "RequireAuthLock fail");
107 return SOFTBUS_ERR;
108 }
109 if (FindAndDelNormalizeRequest(authSeq, request) != SOFTBUS_OK) {
110 AUTH_LOGE(AUTH_HICHAIN, "not found normalize request");
111 ReleaseAuthLock();
112 return SOFTBUS_AUTH_INNER_ERR;
113 }
114 int32_t ret = GetRequestListByUdidHash(request->udidHash, isNeedClear, requests, num);
115 ReleaseAuthLock();
116 return ret;
117 }
118
DelAuthNormalizeRequest(int64_t authSeq)119 void DelAuthNormalizeRequest(int64_t authSeq)
120 {
121 if (!RequireAuthLock()) {
122 AUTH_LOGE(AUTH_HICHAIN, "RequireAuthLock fail");
123 return;
124 }
125 NormalizeRequest *item = NULL;
126 LIST_FOR_EACH_ENTRY(item, &g_normalizeRequestList, NormalizeRequest, node) {
127 if (item->authSeq == authSeq) {
128 ListDelete(&item->node);
129 SoftBusFree(item);
130 AUTH_LOGI(AUTH_HICHAIN, "del normalize request authSeq=%{public}" PRId64, authSeq);
131 break;
132 }
133 }
134 ReleaseAuthLock();
135 }
136
AuthIsRepeatedAuthRequest(int64_t authSeq)137 bool AuthIsRepeatedAuthRequest(int64_t authSeq)
138 {
139 if (!RequireAuthLock()) {
140 AUTH_LOGE(AUTH_HICHAIN, "RequireAuthLock fail");
141 return false;
142 }
143 NormalizeRequest *item = NULL;
144 LIST_FOR_EACH_ENTRY(item, &g_normalizeRequestList, NormalizeRequest, node) {
145 if (item->authSeq == authSeq) {
146 ReleaseAuthLock();
147 return true;
148 }
149 }
150 ReleaseAuthLock();
151 return false;
152 }
153
AddNormalizeRequest(const NormalizeRequest * request)154 uint32_t AddNormalizeRequest(const NormalizeRequest *request)
155 {
156 CHECK_NULL_PTR_RETURN_VALUE(request, 0);
157 NormalizeRequest *newRequest = SoftBusCalloc(sizeof(NormalizeRequest));
158 if (newRequest == NULL) {
159 AUTH_LOGE(AUTH_CONN, "malloc AuthRequest fail");
160 return 0;
161 }
162 *newRequest = *request;
163 if (!RequireAuthLock()) {
164 AUTH_LOGE(AUTH_CONN, "lock fail");
165 SoftBusFree(newRequest);
166 return 0;
167 }
168 ListTailInsert(&g_normalizeRequestList, &newRequest->node);
169 uint32_t waitNum = GetSameRequestNum(newRequest->udidHash);
170 ReleaseAuthLock();
171 return waitNum;
172 }
173
NotifyNormalizeRequestSuccess(int64_t authSeq,bool isSupportNego)174 void NotifyNormalizeRequestSuccess(int64_t authSeq, bool isSupportNego)
175 {
176 NormalizeRequest *requests = NULL;
177 NormalizeRequest request = { 0 };
178 uint32_t num = 0;
179 if (GetNormalizeRequestList(authSeq, true, &request, &requests, &num) != SOFTBUS_OK) {
180 AUTH_LOGI(AUTH_HICHAIN, "get hichain request fail: authSeq=%{public}" PRId64, authSeq);
181 return;
182 }
183 if (num == 0 || requests == NULL) {
184 AUTH_LOGE(AUTH_HICHAIN, "requests is NULL");
185 return;
186 }
187 AUTH_LOGI(AUTH_HICHAIN, "request num=%{public}d", num);
188 for (uint32_t i = 0; i < num; i++) {
189 if (isSupportNego && requests[i].connInfo.type == request.connInfo.type) {
190 continue;
191 }
192 AUTH_LOGI(AUTH_HICHAIN, "notify AuthSessionSaveSessionKey: authSeq=%{public}" PRId64,
193 requests[i].authSeq);
194 (void)AuthNotifyRequestVerify(requests[i].authSeq);
195 }
196 SoftBusFree(requests);
197 }
198
NotifyNormalizeRequestFail(int64_t authSeq,int32_t ret)199 void NotifyNormalizeRequestFail(int64_t authSeq, int32_t ret)
200 {
201 (void)ret;
202 NormalizeRequest *requests = NULL;
203 NormalizeRequest request = { 0 };
204 uint32_t num = 0;
205 if (GetNormalizeRequestList(authSeq, false, &request, &requests, &num) != SOFTBUS_OK) {
206 AUTH_LOGI(AUTH_HICHAIN, "get hichain request fail: authSeq=%{public}" PRId64, authSeq);
207 return;
208 }
209 if (num == 0 || requests == NULL) {
210 return;
211 }
212 for (uint32_t i = 0; i < num; i++) {
213 if (AuthNotifyRequestVerify(requests[i].authSeq) == SOFTBUS_OK) {
214 AUTH_LOGI(AUTH_HICHAIN, "continue auth, authSeq=%{public}" PRId64, requests[i].authSeq);
215 break;
216 }
217 }
218 SoftBusFree(requests);
219 }