• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 "cert_operation.h"
17 
18 #include "account_task_manager.h"
19 #include "account_related_group_auth.h"
20 #include "alg_loader.h"
21 #include "asy_token_manager.h"
22 #include "group_data_manager.h"
23 #include "group_auth_data_operation.h"
24 #include "group_operation_common.h"
25 #include "hc_log.h"
26 #include "hc_types.h"
27 #include "identity_common.h"
28 #include "pseudonym_manager.h"
29 #include "sym_token_manager.h"
30 #include "hisysevent_common.h"
31 
32 #define FIELD_SHARED_SECRET "sharedSecret"
33 
SetProtocolsForUidType(IdentityInfo * info)34 static int32_t SetProtocolsForUidType(IdentityInfo *info)
35 {
36 #ifdef ENABLE_ACCOUNT_AUTH_ISO
37     ProtocolEntity *entity = (ProtocolEntity *)HcMalloc(sizeof(ProtocolEntity), 0);
38     if (entity == NULL) {
39         LOGE("Failed to alloc memory for entity!");
40         return HC_ERR_ALLOC_MEMORY;
41     }
42     entity->protocolType = ALG_ISO;
43     entity->expandProcessCmds = CMD_ADD_TRUST_DEVICE;
44     if (info->protocolVec.pushBack(&info->protocolVec, (const ProtocolEntity **)&entity) == NULL) {
45         LOGE("Failed to push entity to vec");
46         HcFree(entity);
47         return HC_ERR_ALLOC_MEMORY;
48     }
49 #else
50     (void)info;
51 #endif
52 
53     return HC_SUCCESS;
54 }
55 
GetIdentityInfoByType(int32_t keyType,int32_t trustType,const char * groupId,IdentityInfo * info)56 static int32_t GetIdentityInfoByType(int32_t keyType, int32_t trustType, const char *groupId, IdentityInfo *info)
57 {
58     CJson *urlJson = CreateJson();
59     if (urlJson == NULL) {
60         LOGE("Failed to create url json!");
61         return HC_ERR_JSON_CREATE;
62     }
63     if (AddIntToJson(urlJson, PRESHARED_URL_CREDENTIAL_TYPE, PRE_SHARED) != HC_SUCCESS) {
64         LOGE("Failed to add credential type!");
65         FreeJson(urlJson);
66         return HC_ERR_JSON_ADD;
67     }
68     if (AddIntToJson(urlJson, PRESHARED_URL_KEY_TYPE, keyType) != HC_SUCCESS) {
69         LOGE("Failed to add key type!");
70         FreeJson(urlJson);
71         return HC_ERR_JSON_ADD;
72     }
73     if (AddIntToJson(urlJson, PRESHARED_URL_TRUST_TYPE, trustType) != HC_SUCCESS) {
74         LOGE("Failed to add trust type!");
75         FreeJson(urlJson);
76         return HC_ERR_JSON_ADD;
77     }
78     if ((trustType == TRUST_TYPE_P2P || trustType == TRUST_TYPE_UID) &&
79         AddStringToJson(urlJson, FIELD_GROUP_ID, groupId) != HC_SUCCESS) {
80         LOGE("Failed to add group id!");
81         FreeJson(urlJson);
82         return HC_ERR_JSON_ADD;
83     }
84     char *urlStr = PackJsonToString(urlJson);
85     FreeJson(urlJson);
86     if (urlStr == NULL) {
87         LOGE("Failed to pack url json to string!");
88         return HC_ERR_PACKAGE_JSON_TO_STRING_FAIL;
89     }
90 
91     int32_t ret = SetPreSharedUrlForProof(urlStr, &info->proof.preSharedUrl);
92     FreeJsonString(urlStr);
93     if (ret != HC_SUCCESS) {
94         LOGE("Failed to set preSharedUrl of proof!");
95         return ret;
96     }
97 
98     ret = SetProtocolsForUidType(info);
99     if (ret != HC_SUCCESS) {
100         LOGE("Failed to set protocols!");
101         return ret;
102     }
103 
104     info->proofType = PRE_SHARED;
105     return ret;
106 }
107 
AddCertInfoToJson(const CertInfo * certInfo,CJson * out)108 int32_t AddCertInfoToJson(const CertInfo *certInfo, CJson *out)
109 {
110     if (certInfo == NULL || out == NULL) {
111         LOGE("Invalid cert info or out!");
112         return HC_ERR_INVALID_PARAMS;
113     }
114     if (AddIntToJson(out, FIELD_SIGN_ALG, certInfo->signAlg) != HC_SUCCESS) {
115         LOGE("add sign alg to json failed!");
116         return HC_ERR_JSON_ADD;
117     }
118     if (AddStringToJson(out, FIELD_PK_INFO, (const char *)certInfo->pkInfoStr.val) != HC_SUCCESS) {
119         LOGE("add pk info str to json failed!");
120         return HC_ERR_JSON_ADD;
121     }
122     if (AddByteToJson(out, FIELD_PK_INFO_SIGNATURE, certInfo->pkInfoSignature.val,
123         certInfo->pkInfoSignature.length) != HC_SUCCESS) {
124         LOGE("add pk info sign to json failed!");
125         return HC_ERR_JSON_ADD;
126     }
127     return HC_SUCCESS;
128 }
129 
GetSelfUserId(int32_t osAccountId,char * userId,uint32_t userIdLen)130 static int32_t GetSelfUserId(int32_t osAccountId, char *userId, uint32_t userIdLen)
131 {
132     GroupEntryVec accountVec = CreateGroupEntryVec();
133     QueryGroupParams queryParams = InitQueryGroupParams();
134     queryParams.groupType = IDENTICAL_ACCOUNT_GROUP;
135     do {
136         if (QueryGroups(osAccountId, &queryParams, &accountVec) != HC_SUCCESS) {
137             LOGD("No identical-account group in db, no identical-account auth!");
138             break;
139         }
140         uint32_t index = 0;
141         TrustedGroupEntry **ptr = NULL;
142         while (index < accountVec.size(&accountVec)) {
143             ptr = accountVec.getp(&accountVec, index);
144             if ((ptr == NULL) || (*ptr == NULL)) {
145                 index++;
146                 continue;
147             }
148             if (memcpy_s(userId, userIdLen, StringGet(&(*ptr)->userId), StringLength(&(*ptr)->userId)) != EOK) {
149                 LOGE("Error occurs, copy userId failed.");
150                 ClearGroupEntryVec(&accountVec);
151                 return HC_ERROR;
152             }
153             index++;
154         }
155     } while (0);
156     ClearGroupEntryVec(&accountVec);
157     return HC_SUCCESS;
158 }
159 
GetLocalIdenticalGroup(int32_t osAccountId,CJson * param,QueryGroupParams * queryParams,GroupEntryVec * groupEntryVec)160 static void GetLocalIdenticalGroup(int32_t osAccountId, CJson *param, QueryGroupParams *queryParams,
161     GroupEntryVec *groupEntryVec)
162 {
163     char selfUserId[USER_ID_LEN] = { 0 };
164     int32_t ret = GetSelfUserId(osAccountId, selfUserId, USER_ID_LEN);
165     if (ret != HC_SUCCESS) {
166         LOGE("Get user id fail");
167         return;
168     }
169 
170     ret = AddStringToJson(param, FIELD_USER_ID, selfUserId);
171     if (ret != HC_SUCCESS) {
172         LOGE("add self userId to params fail");
173         return;
174     }
175 
176     BaseGroupAuth *groupAuth = GetAccountRelatedGroupAuth();
177     if (groupAuth == NULL) {
178         LOGE("Failed to get account group auth!");
179         return;
180     }
181 
182     ((AccountRelatedGroupAuth *)groupAuth)
183         ->getAccountCandidateGroup(osAccountId, param, queryParams, groupEntryVec);
184     if (groupEntryVec->size(groupEntryVec) == 0) {
185         LOGE("group not found by self user id!");
186     }
187 }
188 
GetSelfGroupEntryByPeerCert(int32_t osAccountId,const CertInfo * certInfo)189 static TrustedGroupEntry *GetSelfGroupEntryByPeerCert(int32_t osAccountId, const CertInfo *certInfo)
190 {
191     CJson *peerPkInfoJson = CreateJsonFromString((const char *)certInfo->pkInfoStr.val);
192     if (peerPkInfoJson == NULL) {
193         LOGE("Failed to create peer pkInfoJson!");
194         return NULL;
195     }
196     const char *peerUserId = GetStringFromJson(peerPkInfoJson, FIELD_USER_ID);
197     if (peerUserId == NULL) {
198         LOGE("Failed to get peer userId!");
199         FreeJson(peerPkInfoJson);
200         return NULL;
201     }
202     CJson *param = CreateJson();
203     if (param == NULL) {
204         LOGE("Failed to create query param!");
205         FreeJson(peerPkInfoJson);
206         return NULL;
207     }
208     if (AddStringToJson(param, FIELD_USER_ID, peerUserId) != HC_SUCCESS) {
209         LOGE("Failed to add peer userId to param!");
210         FreeJson(param);
211         FreeJson(peerPkInfoJson);
212         return NULL;
213     }
214     FreeJson(peerPkInfoJson);
215     BaseGroupAuth *groupAuth = GetAccountRelatedGroupAuth();
216     if (groupAuth == NULL) {
217         LOGE("Failed to get account group auth!");
218         FreeJson(param);
219         return NULL;
220     }
221     GroupEntryVec groupEntryVec = CreateGroupEntryVec();
222     QueryGroupParams queryParams = InitQueryGroupParams();
223     ((AccountRelatedGroupAuth *)groupAuth)
224         ->getAccountCandidateGroup(osAccountId, param, &queryParams, &groupEntryVec);
225     if (groupEntryVec.size(&groupEntryVec) == 0) {
226         LOGE("group not found by peer user id!");
227         (void)GetLocalIdenticalGroup(osAccountId, param, &queryParams, &groupEntryVec);
228         if (groupEntryVec.size(&groupEntryVec) == 0) {
229             LOGE("can not find group");
230             ClearGroupEntryVec(&groupEntryVec);
231             FreeJson(param);
232             return NULL;
233         }
234     }
235     FreeJson(param);
236     TrustedGroupEntry *returnEntry = DeepCopyGroupEntry(groupEntryVec.get(&groupEntryVec, 0));
237     ClearGroupEntryVec(&groupEntryVec);
238     return returnEntry;
239 }
240 
GetSelfDeviceEntryByPeerCert(int32_t osAccountId,const CertInfo * certInfo,TrustedDeviceEntry * deviceEntry)241 static int32_t GetSelfDeviceEntryByPeerCert(
242     int32_t osAccountId, const CertInfo *certInfo, TrustedDeviceEntry *deviceEntry)
243 {
244     TrustedGroupEntry *groupEntry = GetSelfGroupEntryByPeerCert(osAccountId, certInfo);
245     if (groupEntry == NULL) {
246         LOGE("Failed to get self group entry!");
247         return HC_ERR_GROUP_NOT_EXIST;
248     }
249     const char *groupId = StringGet(&groupEntry->id);
250     int32_t ret = GetSelfDeviceEntry(osAccountId, groupId, deviceEntry);
251     DestroyGroupEntry(groupEntry);
252     return ret;
253 }
254 
VerifyPeerCertInfo(int32_t osAccountId,const char * selfUserId,const char * selfAuthId,const CertInfo * certInfo)255 static int32_t VerifyPeerCertInfo(int32_t osAccountId, const char *selfUserId, const char *selfAuthId,
256     const CertInfo *certInfo)
257 {
258     uint8_t *keyAliasValue = (uint8_t *)HcMalloc(SHA256_LEN, 0);
259     if (keyAliasValue == NULL) {
260         LOGE("Failed to alloc memory for key alias value!");
261         return HC_ERR_ALLOC_MEMORY;
262     }
263     Uint8Buff keyAlias = { .val = keyAliasValue, .length = SHA256_LEN };
264     int32_t ret = GetAccountAuthTokenManager()->generateKeyAlias(selfUserId, selfAuthId, &keyAlias, true);
265     if (ret != HC_SUCCESS) {
266         LOGE("Failed to generate server pk alias!");
267         HcFree(keyAliasValue);
268         return ret;
269     }
270     KeyParams keyParams = { { keyAlias.val, keyAlias.length, true }, false, osAccountId };
271     ret = GetLoaderInstance()->verify(
272         &keyParams, &certInfo->pkInfoStr, certInfo->signAlg, &certInfo->pkInfoSignature);
273     HcFree(keyAliasValue);
274     if (ret != HC_SUCCESS) {
275         return HC_ERR_VERIFY_FAILED;
276     }
277     return HC_SUCCESS;
278 }
279 
GetPeerPubKeyFromCert(const CertInfo * peerCertInfo,Uint8Buff * peerPkBuff)280 static int32_t GetPeerPubKeyFromCert(const CertInfo *peerCertInfo, Uint8Buff *peerPkBuff)
281 {
282     CJson *pkInfoPeer = CreateJsonFromString((const char *)peerCertInfo->pkInfoStr.val);
283     if (pkInfoPeer == NULL) {
284         LOGE("Failed to create peer pkInfo json!");
285         return HC_ERR_JSON_CREATE;
286     }
287     const char *devicePk = GetStringFromJson(pkInfoPeer, FIELD_DEVICE_PK);
288     if (devicePk == NULL) {
289         LOGE("Failed to get peer devicePk!");
290         FreeJson(pkInfoPeer);
291         return HC_ERR_JSON_GET;
292     }
293     uint32_t pkSize = HcStrlen(devicePk) / BYTE_TO_HEX_OPER_LENGTH;
294     peerPkBuff->val = (uint8_t *)HcMalloc(pkSize, 0);
295     if (peerPkBuff->val == NULL) {
296         LOGE("Failed to alloc memory for peerPk!");
297         FreeJson(pkInfoPeer);
298         return HC_ERR_ALLOC_MEMORY;
299     }
300     if (GetByteFromJson(pkInfoPeer, FIELD_DEVICE_PK, peerPkBuff->val, pkSize) != HC_SUCCESS) {
301         LOGE("Failed to get peer public key!");
302         HcFree(peerPkBuff->val);
303         FreeJson(pkInfoPeer);
304         return HC_ERR_JSON_GET;
305     }
306     FreeJson(pkInfoPeer);
307     peerPkBuff->length = pkSize;
308     return HC_SUCCESS;
309 }
310 
GetSharedSecretForAccountInPake(int32_t osAccountId,const char * userId,const char * authId,const CertInfo * peerCertInfo,Uint8Buff * sharedSecret)311 static int32_t GetSharedSecretForAccountInPake(int32_t osAccountId, const char *userId, const char *authId,
312     const CertInfo *peerCertInfo, Uint8Buff *sharedSecret)
313 {
314     uint8_t *priAliasVal = (uint8_t *)HcMalloc(SHA256_LEN, 0);
315     if (priAliasVal == NULL) {
316         LOGE("Failed to alloc memory for self key alias!");
317         return HC_ERR_ALLOC_MEMORY;
318     }
319     Uint8Buff aliasBuff = { priAliasVal, SHA256_LEN };
320     int32_t ret = GetAccountAuthTokenManager()->generateKeyAlias(userId, authId, &aliasBuff, false);
321     if (ret != HC_SUCCESS) {
322         HcFree(priAliasVal);
323         return ret;
324     }
325     Uint8Buff peerPkBuff = { 0 };
326     ret = GetPeerPubKeyFromCert(peerCertInfo, &peerPkBuff);
327     if (ret != HC_SUCCESS) {
328         HcFree(priAliasVal);
329         return ret;
330     }
331 
332     uint32_t sharedKeyAliasLen = HcStrlen(SHARED_KEY_ALIAS) + 1;
333     sharedSecret->val = (uint8_t *)HcMalloc(sharedKeyAliasLen, 0);
334     if (sharedSecret->val == NULL) {
335         LOGE("Failed to malloc for psk alias.");
336         HcFree(priAliasVal);
337         ClearFreeUint8Buff(&peerPkBuff);
338         return HC_ERR_ALLOC_MEMORY;
339     }
340     sharedSecret->length = sharedKeyAliasLen;
341     (void)memcpy_s(sharedSecret->val, sharedKeyAliasLen, SHARED_KEY_ALIAS, sharedKeyAliasLen);
342     KeyParams privKeyParams = { { aliasBuff.val, aliasBuff.length, true }, false, osAccountId };
343     KeyBuff pubKeyBuff = { peerPkBuff.val, peerPkBuff.length, false };
344     ret = GetLoaderInstance()->agreeSharedSecretWithStorage(
345         &privKeyParams, &pubKeyBuff, P256, P256_SHARED_SECRET_KEY_SIZE, sharedSecret);
346     HcFree(priAliasVal);
347     ClearFreeUint8Buff(&peerPkBuff);
348     if (ret != HC_SUCCESS) {
349         LOGE("Failed to agree shared secret!");
350         ReportRadarEvent(ret);
351         FreeBuffData(sharedSecret);
352     }
353     return ret;
354 }
355 
GenerateCertInfo(const Uint8Buff * pkInfoStr,const Uint8Buff * pkInfoSignature,CertInfo * certInfo)356 int32_t GenerateCertInfo(const Uint8Buff *pkInfoStr, const Uint8Buff *pkInfoSignature, CertInfo *certInfo)
357 {
358     if (!(IsUint8BuffValid(pkInfoStr, pkInfoStr->length) &&
359         IsUint8BuffValid(pkInfoSignature, pkInfoSignature->length) &&
360         certInfo != NULL)) {
361         LOGE("input invailed!");
362         return HC_ERR_INVALID_PARAMS;
363     }
364     uint32_t pkInfoLen = pkInfoStr->length;
365     certInfo->pkInfoStr.val = (uint8_t *)HcMalloc(pkInfoLen, 0);
366     if (certInfo->pkInfoStr.val == NULL) {
367         LOGE("Failed to alloc pkInfo memory!");
368         return HC_ERR_ALLOC_MEMORY;
369     }
370     if (memcpy_s(certInfo->pkInfoStr.val, pkInfoLen, pkInfoStr->val, pkInfoLen) != EOK) {
371         LOGE("Failed to copy pkInfo!");
372         FreeBuffData(&certInfo->pkInfoStr);
373         return HC_ERR_MEMORY_COPY;
374     }
375     certInfo->pkInfoStr.length = pkInfoLen;
376 
377     uint32_t signatureLen = pkInfoSignature->length;
378     certInfo->pkInfoSignature.val = (uint8_t *)HcMalloc(signatureLen, 0);
379     if (certInfo->pkInfoSignature.val == NULL) {
380         LOGE("Failed to alloc pkInfoSignature memory!");
381         FreeBuffData(&certInfo->pkInfoStr);
382         return HC_ERR_ALLOC_MEMORY;
383     }
384     if (memcpy_s(certInfo->pkInfoSignature.val, signatureLen, pkInfoSignature->val, signatureLen) != EOK) {
385         LOGE("Failed to copy pkInfoSignature!");
386         FreeBuffData(&certInfo->pkInfoStr);
387         FreeBuffData(&certInfo->pkInfoSignature);
388         return HC_ERR_MEMORY_COPY;
389     }
390     certInfo->pkInfoSignature.length = signatureLen;
391     return HC_SUCCESS;
392 }
393 
GetCertInfo(int32_t osAccountId,const char * userId,const char * authId,CertInfo * certInfo)394 static int32_t GetCertInfo(int32_t osAccountId, const char *userId, const char *authId, CertInfo *certInfo)
395 {
396     AccountToken *token = CreateAccountToken();
397     if (token == NULL) {
398         LOGE("Failed to create account token.");
399         return HC_ERR_ALLOC_MEMORY;
400     }
401     int32_t ret = GetAccountAuthTokenManager()->getToken(osAccountId, token, userId, authId);
402     if (ret != HC_SUCCESS) {
403         LOGE("Failed to get account token!");
404         DestroyAccountToken(token);
405         return ret;
406     }
407     ret = GenerateCertInfo(&token->pkInfoStr, &token->pkInfoSignature, certInfo);
408     DestroyAccountToken(token);
409     if (ret != HC_SUCCESS) {
410         LOGE("Failed to generate cert info!");
411         return ret;
412     }
413     certInfo->signAlg = P256;
414     return HC_SUCCESS;
415 }
416 
GetAccountAsymIdentityInfo(int32_t osAccountId,const char * userId,const char * authId,IdentityInfo * info,bool isNeedGeneratePdid)417 static int32_t GetAccountAsymIdentityInfo(
418     int32_t osAccountId, const char *userId, const char *authId, IdentityInfo *info, bool isNeedGeneratePdid)
419 {
420     int32_t ret = GetCertInfo(osAccountId, userId, authId, &info->proof.certInfo);
421     if (ret != HC_SUCCESS) {
422         LOGE("Failed to generate certInfo!");
423         return ret;
424     }
425 
426 #ifdef ENABLE_ACCOUNT_AUTH_EC_SPEKE
427     ProtocolEntity *ecSpekeEntity = (ProtocolEntity *)HcMalloc(sizeof(ProtocolEntity), 0);
428     if (ecSpekeEntity == NULL) {
429         LOGE("Failed to alloc memory for ec speke entity!");
430         return HC_ERR_ALLOC_MEMORY;
431     }
432     ecSpekeEntity->protocolType = ALG_EC_SPEKE;
433     ecSpekeEntity->expandProcessCmds = CMD_ADD_TRUST_DEVICE;
434 #ifdef ENABLE_PSEUDONYM
435     if (isNeedGeneratePdid) {
436         ecSpekeEntity->expandProcessCmds |= CMD_MK_AGREE;
437     }
438 #else
439     (void)isNeedGeneratePdid;
440 #endif
441     if (info->protocolVec.pushBack(&info->protocolVec, (const ProtocolEntity **)&ecSpekeEntity) == NULL) {
442         LOGE("Failed to push ecSpeke entity!");
443         HcFree(ecSpekeEntity);
444         return HC_ERR_ALLOC_MEMORY;
445     }
446 #else
447     (void)isNeedGeneratePdid;
448 #endif
449 
450     info->proofType = CERTIFICATED;
451     return HC_SUCCESS;
452 }
453 
GetLocalDeviceType(int32_t osAccountId,const CJson * in,const char * groupId,int32_t * localDevType)454 static int32_t GetLocalDeviceType(int32_t osAccountId, const CJson *in, const char *groupId, int32_t *localDevType)
455 {
456     TrustedDeviceEntry *deviceEntry = CreateDeviceEntry();
457     if (deviceEntry == NULL) {
458         LOGE("Failed to alloc memory for deviceEntry!");
459         return HC_ERR_ALLOC_MEMORY;
460     }
461     int32_t ret = GetPeerDeviceEntry(osAccountId, in, groupId, deviceEntry);
462     if (ret != HC_SUCCESS) {
463         LOGI("Peer device not found, set local device type to accessory!");
464         *localDevType = DEVICE_TYPE_ACCESSORY;
465         DestroyDeviceEntry(deviceEntry);
466         return HC_SUCCESS;
467     }
468     if (deviceEntry->source == SELF_CREATED) {
469         LOGI("Peer device is self created, set local device type to accessory!");
470         *localDevType = DEVICE_TYPE_ACCESSORY;
471     }
472     DestroyDeviceEntry(deviceEntry);
473     return HC_SUCCESS;
474 }
475 
GenerateAuthTokenForAccessory(int32_t osAccountId,const char * groupId,Uint8Buff * authToken)476 static int32_t GenerateAuthTokenForAccessory(int32_t osAccountId, const char *groupId, Uint8Buff *authToken)
477 {
478     TrustedDeviceEntry *deviceEntry = CreateDeviceEntry();
479     if (deviceEntry == NULL) {
480         LOGE("Failed to create device entry!");
481         return HC_ERR_ALLOC_MEMORY;
482     }
483     int32_t ret = GetSelfDeviceEntry(osAccountId, groupId, deviceEntry);
484     if (ret != HC_SUCCESS) {
485         LOGE("Failed to get self device entry with osAcccountId and groupId!");
486         DestroyDeviceEntry(deviceEntry);
487         return ret;
488     }
489     const char *userIdSelf = StringGet(&deviceEntry->userId);
490     const char *devIdSelf = StringGet(&deviceEntry->authId);
491     uint8_t keyAliasVal[SHA256_LEN] = { 0 };
492     Uint8Buff keyAlias = { keyAliasVal, SHA256_LEN };
493     ret = GetSymTokenManager()->generateKeyAlias(userIdSelf, devIdSelf, &keyAlias);
494     if (ret != HC_SUCCESS) {
495         LOGE("Failed to generate key alias for authCode!");
496         DestroyDeviceEntry(deviceEntry);
497         return ret;
498     }
499 
500     authToken->val = (uint8_t *)HcMalloc(AUTH_TOKEN_SIZE, 0);
501     if (authToken->val == NULL) {
502         LOGE("Failed to alloc memory for auth token!");
503         DestroyDeviceEntry(deviceEntry);
504         return HC_ERR_ALLOC_MEMORY;
505     }
506     authToken->length = AUTH_TOKEN_SIZE;
507     Uint8Buff userIdBuff = { (uint8_t *)userIdSelf, HcStrlen(userIdSelf) };
508     Uint8Buff challenge = { (uint8_t *)KEY_INFO_PERSISTENT_TOKEN, HcStrlen(KEY_INFO_PERSISTENT_TOKEN) };
509     KeyParams keyAliasParams = { { keyAlias.val, keyAlias.length, true }, false, osAccountId };
510     ret = GetLoaderInstance()->computeHkdf(&keyAliasParams, &userIdBuff, &challenge, authToken);
511     DestroyDeviceEntry(deviceEntry);
512     if (ret != HC_SUCCESS) {
513         LOGE("Failed to computeHkdf from authCode to authToken!");
514         FreeBuffData(authToken);
515     }
516     return ret;
517 }
518 
GenerateTokenAliasForController(int32_t osAccountId,const CJson * in,const char * groupId,Uint8Buff * authTokenAlias)519 static int32_t GenerateTokenAliasForController(
520     int32_t osAccountId, const CJson *in, const char *groupId, Uint8Buff *authTokenAlias)
521 {
522     TrustedDeviceEntry *deviceEntry = CreateDeviceEntry();
523     if (deviceEntry == NULL) {
524         LOGE("Failed to create device entry!");
525         return HC_ERR_ALLOC_MEMORY;
526     }
527     int32_t ret = GetPeerDeviceEntry(osAccountId, in, groupId, deviceEntry);
528     if (ret != HC_SUCCESS) {
529         LOGE("Error occurs, failed to get peer device entry!");
530         DestroyDeviceEntry(deviceEntry);
531         return ret;
532     }
533     authTokenAlias->val = (uint8_t *)HcMalloc(SHA256_LEN, 0);
534     if (authTokenAlias->val == NULL) {
535         LOGE("Failed to alloc memory for auth token alias!");
536         DestroyDeviceEntry(deviceEntry);
537         return HC_ERR_ALLOC_MEMORY;
538     }
539     authTokenAlias->length = SHA256_LEN;
540     const char *userIdPeer = StringGet(&deviceEntry->userId);
541     const char *devIdPeer = StringGet(&deviceEntry->authId);
542     ret = GetSymTokenManager()->generateKeyAlias(userIdPeer, devIdPeer, authTokenAlias);
543     DestroyDeviceEntry(deviceEntry);
544     if (ret != HC_SUCCESS) {
545         LOGE("Failed to generate key alias for authToken!");
546         FreeBuffData(authTokenAlias);
547     }
548     return ret;
549 }
550 
GenerateAuthTokenByDevType(const CJson * in,const CJson * urlJson,Uint8Buff * authToken,bool * isTokenStored)551 static int32_t GenerateAuthTokenByDevType(
552     const CJson *in, const CJson *urlJson, Uint8Buff *authToken, bool *isTokenStored)
553 {
554     int32_t osAccountId = INVALID_OS_ACCOUNT;
555     if (GetIntFromJson(in, FIELD_OS_ACCOUNT_ID, &osAccountId) != HC_SUCCESS) {
556         LOGE("Failed to get osAccountId!");
557         return HC_ERR_JSON_GET;
558     }
559     const char *groupId = GetStringFromJson(urlJson, FIELD_GROUP_ID);
560     if (groupId == NULL) {
561         LOGE("Failed to get groupId!");
562         return HC_ERR_JSON_GET;
563     }
564     int32_t localDevType = DEVICE_TYPE_CONTROLLER;
565     int32_t ret = GetLocalDeviceType(osAccountId, in, groupId, &localDevType);
566     if (ret != HC_SUCCESS) {
567         LOGE("Failed to get local device type!");
568         return ret;
569     }
570     if (localDevType == DEVICE_TYPE_ACCESSORY) {
571         *isTokenStored = false;
572         ret = GenerateAuthTokenForAccessory(osAccountId, groupId, authToken);
573     } else {
574         ret = GenerateTokenAliasForController(osAccountId, in, groupId, authToken);
575     }
576     return ret;
577 }
578 
GetSelfAccountIdentityInfo(int32_t osAccountId,const char * groupId,IdentityInfo * info,bool isNeedGeneratePdid)579 static int32_t GetSelfAccountIdentityInfo(
580     int32_t osAccountId, const char *groupId, IdentityInfo *info, bool isNeedGeneratePdid)
581 {
582     TrustedDeviceEntry *deviceEntry = CreateDeviceEntry();
583     if (deviceEntry == NULL) {
584         LOGE("Failed to create device entry!");
585         return HC_ERR_ALLOC_MEMORY;
586     }
587     int32_t ret = GetSelfDeviceEntry(osAccountId, groupId, deviceEntry);
588     if (ret != HC_SUCCESS) {
589         LOGE("Failed to get self device entry!");
590         DestroyDeviceEntry(deviceEntry);
591         return ret;
592     }
593     if (deviceEntry->credential == SYMMETRIC_CRED) {
594         ret = GetIdentityInfoByType(KEY_TYPE_SYM, TRUST_TYPE_UID, groupId, info);
595     } else {
596         const char *userId = StringGet(&deviceEntry->userId);
597         const char *authId = StringGet(&deviceEntry->authId);
598         ret = GetAccountAsymIdentityInfo(osAccountId, userId, authId, info, isNeedGeneratePdid);
599     }
600     DestroyDeviceEntry(deviceEntry);
601     return ret;
602 }
603 
isNeedGeneratePdidByPeerCert(int32_t osAccountId,const CertInfo * certInfo)604 static bool isNeedGeneratePdidByPeerCert(int32_t osAccountId, const CertInfo *certInfo)
605 {
606 #ifdef ENABLE_PSEUDONYM
607     CJson *pkInfoJson = CreateJsonFromString((const char *)certInfo->pkInfoStr.val);
608     if (pkInfoJson == NULL) {
609         LOGE("Failed to create pkInfo json!");
610         return false;
611     }
612     const char *userId = GetStringFromJson(pkInfoJson, FIELD_USER_ID);
613     if (userId == NULL) {
614         LOGE("Failed to get userId!");
615         FreeJson(pkInfoJson);
616         return false;
617     }
618     bool isNeedGenerate = GetPseudonymInstance()->isNeedRefreshPseudonymId(osAccountId, userId);
619     FreeJson(pkInfoJson);
620     return isNeedGenerate;
621 #else
622     (void)osAccountId;
623     (void)certInfo;
624     return false;
625 #endif
626 }
627 
GetAccountRelatedCredInfo(int32_t osAccountId,const char * groupId,const char * deviceId,bool isUdid,IdentityInfo * info)628 int32_t GetAccountRelatedCredInfo(
629     int32_t osAccountId, const char *groupId, const char *deviceId, bool isUdid, IdentityInfo *info)
630 {
631     if (groupId == NULL || deviceId == NULL || info == NULL) {
632         LOGE("Invalid input params!");
633         return HC_ERR_INVALID_PARAMS;
634     }
635     TrustedDeviceEntry *deviceEntry = CreateDeviceEntry();
636     if (deviceEntry == NULL) {
637         LOGE("Failed to create device entry!");
638         return HC_ERR_ALLOC_MEMORY;
639     }
640     int32_t ret = GaGetTrustedDeviceEntryById(osAccountId, deviceId, isUdid, groupId, deviceEntry);
641     if (ret != HC_SUCCESS) {
642         LOGI("peer device not exist, get self identity info.");
643         DestroyDeviceEntry(deviceEntry);
644         return GetSelfAccountIdentityInfo(osAccountId, groupId, info, true);
645     }
646     bool isNeedGeneratePdid = false;
647 #ifdef ENABLE_PSEUDONYM
648     const char *peerUserId = StringGet(&deviceEntry->userId);
649     isNeedGeneratePdid = GetPseudonymInstance()->isNeedRefreshPseudonymId(osAccountId, peerUserId);
650 #endif
651     if (deviceEntry->source == SELF_CREATED) {
652         LOGI("peer device is from self created, get self identity info.");
653         DestroyDeviceEntry(deviceEntry);
654         return GetSelfAccountIdentityInfo(osAccountId, groupId, info, isNeedGeneratePdid);
655     }
656     int credType = deviceEntry->credential;
657     DestroyDeviceEntry(deviceEntry);
658     if (credType == SYMMETRIC_CRED) {
659         LOGI("credential type is symmetric, get sym identity info.");
660         return GetIdentityInfoByType(KEY_TYPE_SYM, TRUST_TYPE_UID, groupId, info);
661     } else {
662         LOGI("credential type is asymmetric, get self identity info.");
663         return GetSelfAccountIdentityInfo(osAccountId, groupId, info, isNeedGeneratePdid);
664     }
665 }
666 
GetSharedSecretByPeerCertFromPlugin(int32_t osAccountId,const char * id,const char * idField,const CertInfo * peerCertInfo,Uint8Buff * sharedSecret)667 static int32_t GetSharedSecretByPeerCertFromPlugin(int32_t osAccountId, const char *id, const char *idField,
668     const CertInfo *peerCertInfo, Uint8Buff *sharedSecret)
669 {
670     CJson *input = CreateJson();
671     if (input == NULL) {
672         LOGE("Create input params json failed!");
673         return HC_ERR_JSON_CREATE;
674     }
675     CJson *output = CreateJson();
676     if (output == NULL) {
677         LOGE("Create output results json failed!");
678         FreeJson(input);
679         return HC_ERR_JSON_CREATE;
680     }
681     int32_t res = HC_ERR_JSON_ADD;
682     if ((id != NULL) && (idField != NULL) && (AddStringToJson(input, idField, id) != HC_SUCCESS)) {
683         LOGE("Across-account cred eixsts, but add cred id to json failed!");
684         goto ERR;
685     }
686     GOTO_ERR_AND_SET_RET(AddCertInfoToJson(peerCertInfo, input), res);
687     GOTO_ERR_AND_SET_RET(ExecuteAccountAuthCmd(osAccountId, GET_SHARED_SECRET_BY_PEER_CERT, input, output), res);
688     res = HC_ERR_JSON_GET;
689     const char *sharedKeyAlias = GetStringFromJson(output, FIELD_SHARED_SECRET);
690     if (sharedKeyAlias == NULL) {
691         LOGE("Get alias failed!");
692         goto ERR;
693     }
694     uint32_t sharedKeyAliasLen = HcStrlen(sharedKeyAlias) + 1;
695     uint8_t *aliasVal = (uint8_t *)HcMalloc(sharedKeyAliasLen, 0);
696     GOTO_IF_CHECK_NULL(aliasVal, FIELD_SHARED_SECRET);
697     if (memcpy_s(aliasVal, sharedKeyAliasLen, sharedKeyAlias, sharedKeyAliasLen) != EOK) {
698         LOGE("parse output result set memcpy alias failed!");
699         HcFree(aliasVal);
700         aliasVal = NULL;
701         goto ERR;
702     }
703     sharedSecret->val = aliasVal;
704     sharedSecret->length = sharedKeyAliasLen;
705     res = HC_SUCCESS;
706 ERR:
707     FreeJson(input);
708     FreeJson(output);
709     return res;
710 }
711 
GetAccountAsymSharedSecret(int32_t osAccountId,const char * id,const char * idField,const CertInfo * peerCertInfo,Uint8Buff * sharedSecret)712 int32_t GetAccountAsymSharedSecret(int32_t osAccountId, const char *id, const char *idField,
713     const CertInfo *peerCertInfo, Uint8Buff *sharedSecret)
714 {
715     if ((peerCertInfo == NULL) || (sharedSecret == NULL)) {
716         LOGE("Invalid input params!");
717         return HC_ERR_INVALID_PARAMS;
718     }
719     if (HasAccountPlugin()) {
720         return GetSharedSecretByPeerCertFromPlugin(osAccountId, id, idField, peerCertInfo, sharedSecret);
721     }
722     TrustedDeviceEntry *deviceEntry = CreateDeviceEntry();
723     if (deviceEntry == NULL) {
724         LOGE("Failed to create self device entry!");
725         return HC_ERR_ALLOC_MEMORY;
726     }
727     int32_t ret = GetSelfDeviceEntryByPeerCert(osAccountId, peerCertInfo, deviceEntry);
728     if (ret != HC_SUCCESS) {
729         LOGE("Failed to get self device entry!");
730         DestroyDeviceEntry(deviceEntry);
731         return ret;
732     }
733     const char *selfUserId = StringGet(&deviceEntry->userId);
734     const char *selfAuthId = StringGet(&deviceEntry->authId);
735     ret = VerifyPeerCertInfo(osAccountId, selfUserId, selfAuthId, peerCertInfo);
736     if (ret != HC_SUCCESS) {
737         LOGE("Failed to verify peer cert! [Res]: %" LOG_PUB "d", ret);
738         DestroyDeviceEntry(deviceEntry);
739         return ret;
740     }
741     ret = GetSharedSecretForAccountInPake(osAccountId, selfUserId, selfAuthId, peerCertInfo, sharedSecret);
742     DestroyDeviceEntry(deviceEntry);
743     return ret;
744 }
745 
GetAccountSymSharedSecret(const CJson * in,const CJson * urlJson,Uint8Buff * sharedSecret)746 int32_t GetAccountSymSharedSecret(const CJson *in, const CJson *urlJson, Uint8Buff *sharedSecret)
747 {
748     if (in == NULL || urlJson == NULL || sharedSecret == NULL) {
749         LOGE("Invalid input params!");
750         return HC_ERR_INVALID_PARAMS;
751     }
752     int32_t osAccountId;
753     if (GetIntFromJson(in, FIELD_OS_ACCOUNT_ID, &osAccountId) != HC_SUCCESS) {
754         LOGE("Failed to get osAccountId!");
755         return HC_ERR_JSON_GET;
756     }
757     bool isTokenStored = true;
758     Uint8Buff authToken = { NULL, 0 };
759     int32_t ret = GenerateAuthTokenByDevType(in, urlJson, &authToken, &isTokenStored);
760     if (ret != HC_SUCCESS) {
761         LOGE("Failed to generate auth token by devType!");
762         return ret;
763     }
764     uint8_t seed[SEED_SIZE] = { 0 };
765     Uint8Buff seedBuff = { seed, SEED_SIZE };
766     ret = GetByteFromJson(in, FIELD_SEED, seed, SEED_SIZE);
767     if (ret != HC_SUCCESS) {
768         LOGE("Failed to get seed form json!");
769         FreeBuffData(&authToken);
770         return HC_ERR_JSON_GET;
771     }
772     sharedSecret->val = (uint8_t *)HcMalloc(ISO_PSK_LEN, 0);
773     if (sharedSecret->val == NULL) {
774         LOGE("Failed to alloc shared secret memory!");
775         FreeBuffData(&authToken);
776         return HC_ERR_ALLOC_MEMORY;
777     }
778     sharedSecret->length = ISO_PSK_LEN;
779     KeyParams keyParams = { { authToken.val, authToken.length, isTokenStored }, false, osAccountId };
780     ret = GetLoaderInstance()->computeHmac(&keyParams, &seedBuff, sharedSecret);
781     FreeBuffData(&authToken);
782     if (ret != HC_SUCCESS) {
783         LOGE("ComputeHmac for psk failed, ret: %" LOG_PUB "d.", ret);
784         FreeBuffData(sharedSecret);
785     }
786     return ret;
787 }
788 
GetAccountAsymCredInfo(int32_t osAccountId,const CertInfo * certInfo,IdentityInfo ** returnInfo)789 int32_t GetAccountAsymCredInfo(int32_t osAccountId, const CertInfo *certInfo, IdentityInfo **returnInfo)
790 {
791     if (certInfo == NULL || returnInfo == NULL) {
792         LOGE("Invalid input params!");
793         return HC_ERR_INVALID_PARAMS;
794     }
795     TrustedDeviceEntry *deviceEntry = CreateDeviceEntry();
796     if (deviceEntry == NULL) {
797         LOGE("Failed to create self device entry!");
798         return HC_ERR_ALLOC_MEMORY;
799     }
800     int32_t ret = GetSelfDeviceEntryByPeerCert(osAccountId, certInfo, deviceEntry);
801     if (ret != HC_SUCCESS) {
802         LOGE("Failed to get self device entry!");
803         DestroyDeviceEntry(deviceEntry);
804         return ret;
805     }
806     IdentityInfo *info = CreateIdentityInfo();
807     if (info == NULL) {
808         LOGE("Failed to create identity info!");
809         DestroyDeviceEntry(deviceEntry);
810         return HC_ERR_ALLOC_MEMORY;
811     }
812     const char *selfUserId = StringGet(&deviceEntry->userId);
813     const char *selfAuthId = StringGet(&deviceEntry->authId);
814     bool isNeedGeneratePdid = isNeedGeneratePdidByPeerCert(osAccountId, certInfo);
815     ret = GetAccountAsymIdentityInfo(osAccountId, selfUserId, selfAuthId, info, isNeedGeneratePdid);
816     DestroyDeviceEntry(deviceEntry);
817     if (ret != HC_SUCCESS) {
818         LOGE("Failed to get account asym identity info!");
819         DestroyIdentityInfo(info);
820         return ret;
821     }
822     *returnInfo = info;
823     return HC_SUCCESS;
824 }
825 
GetAccountSymCredInfoByPeerUrl(const CJson * in,const CJson * urlJson,IdentityInfo * info)826 int32_t GetAccountSymCredInfoByPeerUrl(const CJson *in, const CJson *urlJson, IdentityInfo *info)
827 {
828     if (in == NULL || urlJson == NULL || info == NULL) {
829         LOGE("Invalid input params!");
830         return HC_ERR_INVALID_PARAMS;
831     }
832     int32_t osAccountId = INVALID_OS_ACCOUNT;
833     if (GetIntFromJson(in, FIELD_OS_ACCOUNT_ID, &osAccountId) != HC_SUCCESS) {
834         LOGE("Failed to get osAccountId!");
835         return HC_ERR_JSON_GET;
836     }
837     const char *groupId = GetStringFromJson(urlJson, FIELD_GROUP_ID);
838     if (groupId == NULL) {
839         LOGE("Failed to get group id!");
840         return HC_ERR_JSON_GET;
841     }
842     int32_t ret = CheckGroupExist(osAccountId, groupId);
843     if (ret != HC_SUCCESS) {
844         LOGE("group not exist!");
845         return ret;
846     }
847     return GetIdentityInfoByType(KEY_TYPE_SYM, TRUST_TYPE_UID, groupId, info);
848 }