• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2022-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 "v4_0/user_auth_interface_service.h"
17 
18 #include <cinttypes>
19 #include <mutex>
20 #include <hdf_base.h>
21 #include "securec.h"
22 #include <set>
23 #include <string>
24 
25 #include "iam_logger.h"
26 #include "iam_para2str.h"
27 #include "iam_ptr.h"
28 
29 #include "adaptor_time.h"
30 #include "useriam_common.h"
31 #include "auth_level.h"
32 #include "buffer.h"
33 #include "coauth_funcs.h"
34 #include "executor_message.h"
35 #include "hmac_key.h"
36 #include "identify_funcs.h"
37 #include "idm_database.h"
38 #include "idm_session.h"
39 #include "ed25519_key.h"
40 #include "udid_manager.h"
41 #include "user_auth_hdi.h"
42 #include "user_auth_funcs.h"
43 #include "user_idm_funcs.h"
44 #include "user_sign_centre.h"
45 #include "enroll_specification_check.h"
46 
47 #undef LOG_TAG
48 #define LOG_TAG "USER_AUTH_HDI"
49 
50 namespace OHOS {
51 namespace HDI {
52 namespace UserAuth {
53 namespace {
54 static std::mutex g_mutex;
55 static std::string g_localUdid;
56 constexpr uint32_t INVALID_CAPABILITY_LEVEL = 100;
57 const std::string SETTRINGS_NAME = "settings";
58 constexpr uint32_t MAX_TOKEN_ALLOWABLE_DURATION = 24 * 60 * 60 * 1000;
59 
60 enum UserAuthCallerType : int32_t {
61     TOKEN_INVALID = -1,
62     TOKEN_HAP = 0,
63     TOKEN_NATIVE,
64 };
65 const uint32_t PUBLIC_KEY_STR_LEN = 33;
FormatHexString(uint8_t * data,int32_t dataSize,char * outBuffer,int32_t outBufferSize)66 void FormatHexString(uint8_t* data, int32_t dataSize, char* outBuffer, int32_t outBufferSize)
67 {
68     int32_t writeIndex = 0;
69     do {
70         for (int i = 0; i < dataSize; i++) {
71             int ret = sprintf_s(outBuffer + writeIndex, outBufferSize - writeIndex, "%X", data[i]);
72             if (ret < 0) {
73                 writeIndex = 0;
74                 break;
75             }
76             writeIndex += ret;
77         }
78     } while (0);
79 
80     if (writeIndex == 0) {
81         memset_s(outBuffer, outBufferSize, 0, outBufferSize);
82     }
83 }
84 
ConvertResultCode(const int32_t in)85 int32_t ConvertResultCode(const int32_t in)
86 {
87     static const std::map<ResultCode, InnerKitResultCode> data = {
88         {ResultCode::RESULT_TOKEN_TIMEOUT, InnerKitResultCode::INNER_RESULT_AUTH_TOKEN_EXPIRED},
89         {ResultCode::RESULT_VERIFY_TOKEN_FAIL, InnerKitResultCode::INNER_RESULT_AUTH_TOKEN_CHECK_FAILED},
90     };
91     auto iter = data.find(static_cast<ResultCode>(in));
92     if (iter != data.end()) {
93         return iter->second;
94     }
95     return in;
96 }
97 } // namespace
98 
99 using namespace std;
100 
UserAuthInterfaceImplGetInstance(void)101 extern "C" IUserAuthInterface *UserAuthInterfaceImplGetInstance(void)
102 {
103     auto userAuthInterfaceService = new (std::nothrow) UserAuthInterfaceService();
104     if (userAuthInterfaceService == nullptr) {
105         IAM_LOGE("userAuthInterfaceService is nullptr");
106         return nullptr;
107     }
108     std::lock_guard<std::mutex> lock(g_mutex);
109     OHOS::UserIam::Common::Init();
110     return userAuthInterfaceService;
111 }
112 
Init(const std::string & deviceUdid)113 int32_t UserAuthInterfaceService::Init(const std::string &deviceUdid)
114 {
115     IAM_LOGI("start");
116     std::lock_guard<std::mutex> lock(g_mutex);
117     g_localUdid = deviceUdid;
118     bool ret = SetLocalUdid(g_localUdid.c_str());
119     IF_TRUE_LOGE_AND_RETURN_VAL(!ret, HDF_FAILURE);
120     OHOS::UserIam::Common::Close();
121     return OHOS::UserIam::Common::Init();
122 }
123 
CopyScheduleInfo(const CoAuthSchedule * in,HdiScheduleInfo * out)124 static bool CopyScheduleInfo(const CoAuthSchedule *in, HdiScheduleInfo *out)
125 {
126     IAM_LOGI("start");
127     if (in->executorSize == 0 || (in->templateIds.data == NULL && in->templateIds.len != 0)) {
128         IAM_LOGE("executorSize is zero");
129         return false;
130     }
131     out->executorIndexes.clear();
132     out->templateIds.clear();
133     out->scheduleId = in->scheduleId;
134     out->authType = static_cast<AuthType>(in->authType);
135     for (uint32_t i = 0; i < in->templateIds.len; ++i) {
136         out->templateIds.push_back(in->templateIds.data[i]);
137     }
138     out->executorMatcher = static_cast<uint32_t>(in->executors[0].executorMatcher);
139     out->scheduleMode = static_cast<ScheduleMode>(in->scheduleMode);
140     for (uint32_t i = 0; i < in->executorSize; ++i) {
141         out->executorIndexes.push_back(in->executors[i].executorIndex);
142     }
143     out->executorMessages.clear();
144     return true;
145 }
146 
SetAttributeToCoAuthExecMsg(AuthParamHal paramHal,HdiScheduleInfo & info,Uint8Array publicKey,Attribute * attribute)147 static int32_t SetAttributeToCoAuthExecMsg(AuthParamHal paramHal, HdiScheduleInfo &info,
148     Uint8Array publicKey, Attribute *attribute)
149 {
150     IF_TRUE_LOGE_AND_RETURN_VAL(attribute == nullptr, RESULT_GENERAL_ERROR);
151 
152     if (SetAttributeUint64(attribute, ATTR_SCHEDULE_ID, info.scheduleId) != RESULT_SUCCESS) {
153         IAM_LOGE("SetAttributeUint64 scheduleId failed");
154         return RESULT_GENERAL_ERROR;
155     }
156 
157     Uint8Array localUdidIn = { paramHal.localUdid, sizeof(paramHal.localUdid) };
158     if (SetAttributeUint8Array(attribute, ATTR_VERIFIER_UDID, localUdidIn) != RESULT_SUCCESS) {
159         IAM_LOGE("SetAttributeUint8Array verifierUdid failed");
160         return RESULT_GENERAL_ERROR;
161     }
162     if (SetAttributeUint8Array(attribute, ATTR_LOCAL_UDID, localUdidIn) != RESULT_SUCCESS) {
163         IAM_LOGE("SetAttributeUint8Array localUdid failed");
164         return RESULT_GENERAL_ERROR;
165     }
166     Uint8Array peerUdidIn = { paramHal.collectorUdid, sizeof(paramHal.collectorUdid) };
167     if (SetAttributeUint8Array(attribute, ATTR_COLLECTOR_UDID, peerUdidIn) != RESULT_SUCCESS) {
168         IAM_LOGE("SetAttributeUint8Array collectorUdid failed");
169         return RESULT_GENERAL_ERROR;
170     }
171     if (SetAttributeUint8Array(attribute, ATTR_PEER_UDID, peerUdidIn) != RESULT_SUCCESS) {
172         IAM_LOGE("SetAttributeUint8Array peerUdid failed");
173         return RESULT_GENERAL_ERROR;
174     }
175     char publicKeyStrBuffer[PUBLIC_KEY_STR_LEN] = {0};
176     FormatHexString(&publicKey.data[0], publicKey.len, publicKeyStrBuffer, PUBLIC_KEY_STR_LEN);
177     IAM_LOGI("public key: %{public}s", publicKeyStrBuffer);
178     if (SetAttributeUint8Array(attribute, ATTR_PUBLIC_KEY, publicKey) != RESULT_SUCCESS) {
179         IAM_LOGE("SetAttributeUint8Array publicKey failed");
180         return RESULT_GENERAL_ERROR;
181     }
182     Uint8Array challenge = { paramHal.challenge, CHALLENGE_LEN };
183     if (SetAttributeUint8Array(attribute, ATTR_CHALLENGE, challenge) != RESULT_SUCCESS) {
184         IAM_LOGE("SetAttributeUint8Array challenge failed");
185         return RESULT_GENERAL_ERROR;
186     }
187 
188     return RESULT_SUCCESS;
189 }
190 
SetAttributeToCollectorExecMsg(AuthParamHal paramHal,HdiScheduleInfo & info,Uint8Array publicKey,Uint8Array * retExtraInfo)191 static int32_t SetAttributeToCollectorExecMsg(AuthParamHal paramHal, HdiScheduleInfo &info,
192     Uint8Array publicKey, Uint8Array *retExtraInfo)
193 {
194     Attribute *attribute = CreateEmptyAttribute();
195     IF_TRUE_LOGE_AND_RETURN_VAL(attribute == nullptr, RESULT_GENERAL_ERROR);
196 
197     ResultCode ret = RESULT_GENERAL_ERROR;
198     do {
199         if (SetAttributeUint32(attribute, ATTR_TYPE, paramHal.authType) != RESULT_SUCCESS) {
200             IAM_LOGE("SetAttributeUint32 authType failed");
201             break;
202         }
203         if (SetAttributeUint32(attribute, ATTR_EXECUTOR_MATCHER, info.executorMatcher) != RESULT_SUCCESS) {
204             IAM_LOGE("SetAttributeUint64 executorMatcher failed");
205             break;
206         }
207         if (SetAttributeInt32(attribute, ATTR_SCHEDULE_MODE, info.scheduleMode) != RESULT_SUCCESS) {
208             IAM_LOGE("SetAttributeUint64 scheduleMode failed");
209             break;
210         }
211         if (SetAttributeUint32(attribute, ATTR_EXECUTOR_ROLE, COLLECTOR) != RESULT_SUCCESS) {
212             IAM_LOGE("SetAttributeUint32 executorRole failed");
213             break;
214         }
215         if (SetAttributeToCoAuthExecMsg(paramHal, info, publicKey, attribute) != RESULT_SUCCESS) {
216             IAM_LOGE("SetAttributeToCoAuthExecMsg failed");
217             break;
218         }
219 
220         SignParam signParam = { .needSignature = true };
221         Uint8Array collectorUdid = { paramHal.collectorUdid, sizeof(paramHal.collectorUdid) };
222         if (IsLocalUdid(collectorUdid)) {
223             signParam.keyType = KEY_TYPE_EXECUTOR;
224         } else {
225             signParam.keyType = KEY_TYPE_CROSS_DEVICE;
226             signParam.peerUdid = collectorUdid;
227         }
228 
229         if (GetAttributeExecutorMsg(attribute, retExtraInfo, signParam) != RESULT_SUCCESS) {
230             IAM_LOGE("GetAttributeExecutorMsg failed");
231             break;
232         }
233         ret = RESULT_SUCCESS;
234     } while (0);
235 
236     FreeAttribute(&attribute);
237     return ret;
238 }
239 
GetCapabilityLevel(int32_t userId,HdiScheduleInfo & info,uint32_t & capabilityLevel)240 static int32_t GetCapabilityLevel(int32_t userId, HdiScheduleInfo &info, uint32_t &capabilityLevel)
241 {
242     capabilityLevel = INVALID_CAPABILITY_LEVEL;
243     LinkedList *credList = nullptr;
244     int32_t ret = QueryCredentialFunc(userId, info.authType, &credList);
245     if (ret != RESULT_SUCCESS) {
246         IAM_LOGE("query credential failed");
247         return ret;
248     }
249     LinkedListNode *temp = credList->head;
250     while (temp != nullptr) {
251         if (temp->data == nullptr) {
252             IAM_LOGE("list node is invalid");
253             DestroyLinkedList(credList);
254             return RESULT_UNKNOWN;
255         }
256         auto credentialHal = static_cast<CredentialInfoHal *>(temp->data);
257         // Only the lowest acl is returned
258         capabilityLevel = (capabilityLevel < credentialHal->capabilityLevel) ?
259             capabilityLevel : credentialHal->capabilityLevel;
260         temp = temp->next;
261     }
262 
263     DestroyLinkedList(credList);
264     return RESULT_SUCCESS;
265 }
266 
GetExpiredSysTime(AuthParamHal paramHal)267 static uint64_t GetExpiredSysTime(AuthParamHal paramHal)
268 {
269     UserAuthContext *context = GetContext(paramHal.contextId);
270     if (context == NULL) {
271         IAM_LOGE("context is null");
272         return NO_CHECK_PIN_EXPIRED_PERIOD;
273     }
274 
275     if (!context->isExpiredReturnSuccess) {
276         return context->authExpiredSysTime;
277     }
278 
279     return NO_CHECK_PIN_EXPIRED_PERIOD;
280 }
281 
SetAttributeToVerifierExecMsg(AuthParamHal paramHal,HdiScheduleInfo & info,Uint8Array publicKey,Uint8Array * retExtraInfo)282 static int32_t SetAttributeToVerifierExecMsg(AuthParamHal paramHal, HdiScheduleInfo &info,
283     Uint8Array publicKey, Uint8Array *retExtraInfo)
284 {
285     Attribute *attribute = CreateEmptyAttribute();
286     IF_TRUE_LOGE_AND_RETURN_VAL(attribute == nullptr, RESULT_GENERAL_ERROR);
287 
288     ResultCode ret = RESULT_GENERAL_ERROR;
289     do {
290         Uint64Array templateIdsIn = {info.templateIds.data(), info.templateIds.size()};
291         if (SetAttributeUint64Array(attribute, ATTR_TEMPLATE_ID_LIST, templateIdsIn) != RESULT_SUCCESS) {
292             IAM_LOGE("SetAttributeUint64Array templateIdsIn failed");
293             break;
294         }
295         uint32_t capabilityLevel = INVALID_CAPABILITY_LEVEL;
296         int32_t result = GetCapabilityLevel(paramHal.userId, info, capabilityLevel);
297         if (result != RESULT_SUCCESS) {
298             IAM_LOGE("GetCapabilityLevel fail");
299             return result;
300         }
301         if (capabilityLevel != INVALID_CAPABILITY_LEVEL &&
302             SetAttributeUint32(attribute, ATTR_CAPABILITY_LEVEL, capabilityLevel) != RESULT_SUCCESS) {
303             IAM_LOGE("SetAttributeUint32 capabilityLevel failed");
304             break;
305         }
306         if (SetAttributeUint64(attribute, ATTR_EXPIRED_SYS_TIME, GetExpiredSysTime(paramHal)) != RESULT_SUCCESS) {
307             IAM_LOGE("SetAttributeUint64 authExpiredSysTime failed");
308             break;
309         }
310         if (SetAttributeToCoAuthExecMsg(paramHal, info, publicKey, attribute) != RESULT_SUCCESS) {
311             IAM_LOGE("SetAttributeToCoAuthExecMsg failed");
312             break;
313         }
314 
315         SignParam signParam = { .needSignature = true, .keyType = KEY_TYPE_EXECUTOR };
316         if (GetAttributeExecutorMsg(attribute, retExtraInfo, signParam) != RESULT_SUCCESS) {
317             IAM_LOGE("GetAttributeExecutorMsg failed");
318             break;
319         }
320         ret = RESULT_SUCCESS;
321     } while (0);
322 
323     FreeAttribute(&attribute);
324     return ret;
325 }
326 
SetAttributeToExtraInfo(HdiScheduleInfo & info,uint32_t capabilityLevel,uint64_t scheduleId)327 static int32_t SetAttributeToExtraInfo(HdiScheduleInfo &info, uint32_t capabilityLevel, uint64_t scheduleId)
328 {
329     Attribute *attribute = CreateEmptyAttribute();
330     IF_TRUE_LOGE_AND_RETURN_VAL(attribute == nullptr, RESULT_GENERAL_ERROR);
331 
332     ResultCode ret = RESULT_GENERAL_ERROR;
333     do {
334         Uint64Array templateIdsIn = {info.templateIds.data(), info.templateIds.size()};
335         if (SetAttributeUint64Array(attribute, ATTR_TEMPLATE_ID_LIST, templateIdsIn) != RESULT_SUCCESS) {
336             IAM_LOGE("SetAttributeUint64Array templateIdsIn failed");
337             break;
338         }
339         if (capabilityLevel != INVALID_CAPABILITY_LEVEL &&
340             SetAttributeUint32(attribute, ATTR_CAPABILITY_LEVEL, capabilityLevel) != RESULT_SUCCESS) {
341             IAM_LOGE("SetAttributeUint32 capabilityLevel failed");
342             break;
343         }
344         if (SetAttributeUint64(attribute, ATTR_SCHEDULE_ID, scheduleId) != RESULT_SUCCESS) {
345             IAM_LOGE("SetAttributeUint64 scheduleId failed");
346             break;
347         }
348 
349         info.executorMessages.resize(1);
350         info.executorMessages[0].resize(MAX_EXECUTOR_MSG_LEN);
351         Uint8Array retExtraInfo = { info.executorMessages[0].data(), MAX_EXECUTOR_MSG_LEN };
352         SignParam signParam = { .needSignature = true, .keyType = KEY_TYPE_EXECUTOR };
353         if (GetAttributeExecutorMsg(attribute, &retExtraInfo, signParam) != RESULT_SUCCESS) {
354             IAM_LOGE("GetAttributeExecutorMsg failed");
355             info.executorMessages.clear();
356             break;
357         }
358         info.executorMessages[0].resize(retExtraInfo.len);
359         ret = RESULT_SUCCESS;
360     } while (0);
361 
362     FreeAttribute(&attribute);
363     return ret;
364 }
365 
SetAttributeToAllInOneExecMsg(AuthParamHal paramHal,HdiScheduleInfo & info,Uint8Array * retExtraInfo)366 static int32_t SetAttributeToAllInOneExecMsg(AuthParamHal paramHal, HdiScheduleInfo &info, Uint8Array *retExtraInfo)
367 {
368     uint32_t capabilityLevel = INVALID_CAPABILITY_LEVEL;
369     int32_t result = GetCapabilityLevel(paramHal.userId, info, capabilityLevel);
370     if (result != RESULT_SUCCESS) {
371         IAM_LOGE("GetCapabilityLevel fail");
372         return result;
373     }
374 
375     Attribute *attribute = CreateEmptyAttribute();
376     IF_TRUE_LOGE_AND_RETURN_VAL(attribute == nullptr, RESULT_GENERAL_ERROR);
377 
378     ResultCode ret = RESULT_GENERAL_ERROR;
379     do {
380         Uint64Array templateIdsIn = {info.templateIds.data(), info.templateIds.size()};
381         if (SetAttributeUint64Array(attribute, ATTR_TEMPLATE_ID_LIST, templateIdsIn) != RESULT_SUCCESS) {
382             IAM_LOGE("SetAttributeUint64Array templateIdsIn failed");
383             break;
384         }
385         if (capabilityLevel != INVALID_CAPABILITY_LEVEL &&
386             SetAttributeUint32(attribute, ATTR_CAPABILITY_LEVEL, capabilityLevel) != RESULT_SUCCESS) {
387             IAM_LOGE("SetAttributeUint32 capabilityLevel failed");
388             break;
389         }
390         if (SetAttributeUint64(attribute, ATTR_SCHEDULE_ID, info.scheduleId) != RESULT_SUCCESS) {
391             IAM_LOGE("SetAttributeUint64 scheduleId failed");
392             break;
393         }
394 
395         if (SetAttributeUint64(attribute, ATTR_EXPIRED_SYS_TIME, GetExpiredSysTime(paramHal)) != RESULT_SUCCESS) {
396             IAM_LOGE("SetAttributeUint64 authExpiredSysTime failed");
397             break;
398         }
399 
400         Uint8Array challenge = { paramHal.challenge, CHALLENGE_LEN };
401         if (SetAttributeUint8Array(attribute, ATTR_CHALLENGE, challenge) != RESULT_SUCCESS) {
402             IAM_LOGE("SetAttributeUint8Array challenge failed");
403             break;
404         }
405         if (SetAttributeInt32(attribute, ATTR_AUTH_PURPOSE, paramHal.authIntent) != RESULT_SUCCESS) {
406             IAM_LOGE("SetAttributeUint32 auth purpose failed");
407             break;
408         }
409         SignParam signParam = { .needSignature = true, .keyType = KEY_TYPE_EXECUTOR };
410         if (GetAttributeExecutorMsg(attribute, retExtraInfo, signParam) != RESULT_SUCCESS) {
411             IAM_LOGE("GetAttributeExecutorMsg failed");
412             break;
413         }
414         ret = RESULT_SUCCESS;
415     } while (0);
416 
417     FreeAttribute(&attribute);
418     return ret;
419 }
420 
GetAuthExecutorMsg(uint32_t executorRole,AuthParamHal paramHal,Uint8Array publicKey,HdiScheduleInfo & info,Uint8Array * retMsg)421 static int32_t GetAuthExecutorMsg(uint32_t executorRole, AuthParamHal paramHal,
422     Uint8Array publicKey, HdiScheduleInfo &info, Uint8Array *retMsg)
423 {
424     if (executorRole == COLLECTOR) {
425         if (SetAttributeToCollectorExecMsg(paramHal, info, publicKey, retMsg) != RESULT_SUCCESS) {
426             IAM_LOGE("SetAttributeToCollectorExecMsg failed");
427             return RESULT_GENERAL_ERROR;
428         }
429     } else if (executorRole == VERIFIER) {
430         if (SetAttributeToVerifierExecMsg(paramHal, info, publicKey, retMsg) != RESULT_SUCCESS) {
431             IAM_LOGE("SetAttributeToVerifierExecMsg failed");
432             return RESULT_GENERAL_ERROR;
433         }
434     } else if (executorRole == ALL_IN_ONE) {
435         if (SetAttributeToAllInOneExecMsg(paramHal, info, retMsg) != RESULT_SUCCESS) {
436             IAM_LOGE("SetAttributeToAllInOneExecMsg fail");
437             return RESULT_GENERAL_ERROR;
438         }
439     } else {
440         IAM_LOGE("Unsupported executorRole %{public}u", executorRole);
441         return RESULT_GENERAL_ERROR;
442     }
443     return RESULT_SUCCESS;
444 }
445 
SetBufferToAttribute(Attribute * attribute,AttributeKey key,Buffer * buf)446 static int32_t SetBufferToAttribute(Attribute *attribute, AttributeKey key, Buffer *buf)
447 {
448     if ((attribute == NULL) || !IsBufferValid(buf)) {
449         LOG_ERROR("SetBufferToAttribute bad param!");
450         return RESULT_BAD_PARAM;
451     }
452     Uint8Array uint8Array = {
453         .data = buf->buf,
454         .len = buf->contentSize,
455     };
456     return SetAttributeUint8Array(attribute, key, uint8Array);
457 }
458 
SetAttributeToAbandonMsg(HdiScheduleInfo & info,uint64_t scheduleId,Buffer * oldRootSecret,Buffer * newRootSecret)459 static int32_t SetAttributeToAbandonMsg(HdiScheduleInfo &info, uint64_t scheduleId, Buffer *oldRootSecret,
460     Buffer *newRootSecret)
461 {
462     IF_TRUE_LOGE_AND_RETURN_VAL(oldRootSecret == nullptr, RESULT_GENERAL_ERROR);
463     IF_TRUE_LOGE_AND_RETURN_VAL(newRootSecret == nullptr, RESULT_GENERAL_ERROR);
464 
465     Attribute *attribute = CreateEmptyAttribute();
466     IF_TRUE_LOGE_AND_RETURN_VAL(attribute == nullptr, RESULT_GENERAL_ERROR);
467     ResultCode ret = RESULT_GENERAL_ERROR;
468     do {
469         Uint64Array templateIdsIn = {info.templateIds.data(), info.templateIds.size()};
470         if (SetAttributeUint64Array(attribute, ATTR_TEMPLATE_ID_LIST, templateIdsIn) != RESULT_SUCCESS) {
471             IAM_LOGE("SetAttributeUint64Array templateIdsIn failed");
472             break;
473         }
474         if (SetAttributeUint64(attribute, ATTR_SCHEDULE_ID, scheduleId) != RESULT_SUCCESS) {
475             IAM_LOGE("SetAttributeUint64 scheduleId failed");
476             break;
477         }
478         if (SetBufferToAttribute(attribute, ATTR_OLD_ROOT_SECRET, oldRootSecret) != RESULT_SUCCESS) {
479             IAM_LOGE("SetAttributeUint64 old root secret failed");
480             break;
481         }
482         if (SetBufferToAttribute(attribute, ATTR_ROOT_SECRET, newRootSecret) != RESULT_SUCCESS) {
483             IAM_LOGE("SetAttributeUint64 new root secret failed");
484             break;
485         }
486         info.executorMessages.resize(1);
487         info.executorMessages[0].resize(MAX_EXECUTOR_MSG_LEN);
488         Uint8Array retExtraInfo = { info.executorMessages[0].data(), MAX_EXECUTOR_MSG_LEN };
489         SignParam signParam = { .needSignature = true, .keyType = KEY_TYPE_EXECUTOR };
490         if (GetAttributeExecutorMsg(attribute, &retExtraInfo, signParam) != RESULT_SUCCESS) {
491             IAM_LOGE("GetAttributeExecutorMsg failed");
492             info.executorMessages.clear();
493             break;
494         }
495         info.executorMessages[0].resize(retExtraInfo.len);
496         ret = RESULT_SUCCESS;
497     } while (0);
498 
499     FreeAttribute(&attribute);
500     return ret;
501 }
502 
CopyAuthScheduleInfo(AuthParamHal paramHal,const CoAuthSchedule * in,HdiScheduleInfo * out)503 static bool CopyAuthScheduleInfo(AuthParamHal paramHal, const CoAuthSchedule *in, HdiScheduleInfo *out)
504 {
505     IAM_LOGI("CopyAuthScheduleInfo start");
506     if (in->executorSize == 0 || (in->templateIds.data == NULL && in->templateIds.len != 0)) {
507         IAM_LOGE("executorSize is zero");
508         return false;
509     }
510     out->executorIndexes.clear();
511     out->templateIds.clear();
512     out->scheduleId = in->scheduleId;
513     out->authType = static_cast<AuthType>(in->authType);
514     for (uint32_t i = 0; i < in->templateIds.len; ++i) {
515         out->templateIds.push_back(in->templateIds.data[i]);
516     }
517     out->executorMatcher = static_cast<uint32_t>(in->executors[0].executorMatcher);
518     out->scheduleMode = static_cast<ScheduleMode>(in->scheduleMode);
519 
520     out->executorIndexes.resize(in->executorSize);
521     out->executorMessages.resize(in->executorSize);
522     for (uint32_t i = 0; i < in->executorSize; ++i) {
523         out->executorIndexes[i] = in->executors[i].executorIndex;
524         out->executorMessages[i].resize(MAX_EXECUTOR_MSG_LEN);
525         Uint8Array retExtraInfo = { out->executorMessages[i].data(), MAX_EXECUTOR_MSG_LEN };
526         uint32_t executorRoleTemp = static_cast<ExecutorRole>(in->executors[i].executorRole);
527         Uint8Array publicKeyInfo = { (uint8_t *)in->executors[1 - i].pubKey, PUBLIC_KEY_LEN };
528         if (GetAuthExecutorMsg(executorRoleTemp, paramHal, publicKeyInfo, *out, &retExtraInfo) != RESULT_SUCCESS) {
529             IAM_LOGE("GetAuthExecutorMsg failed");
530             out->executorIndexes.clear();
531             out->templateIds.clear();
532             out->executorMessages.clear();
533             return false;
534         }
535         out->executorMessages[i].resize(retExtraInfo.len);
536     }
537     return true;
538 }
539 
CopyAuthParamToHal(uint64_t contextId,const HdiAuthParam & param,AuthParamHal & paramHal)540 static int32_t CopyAuthParamToHal(uint64_t contextId, const HdiAuthParam &param,
541     AuthParamHal &paramHal)
542 {
543     paramHal.contextId = contextId;
544     paramHal.userId = param.baseParam.userId;
545     paramHal.authType = static_cast<int32_t>(param.authType);
546     paramHal.authTrustLevel = param.baseParam.authTrustLevel;
547     if (!param.baseParam.challenge.empty() && memcpy_s(paramHal.challenge, CHALLENGE_LEN,
548         param.baseParam.challenge.data(), param.baseParam.challenge.size()) != EOK) {
549         IAM_LOGE("challenge copy failed");
550         return RESULT_BAD_COPY;
551     }
552     paramHal.authIntent = param.authIntent;
553     paramHal.isExpiredReturnSuccess = false;
554     if (param.baseParam.callerType == TOKEN_HAP &&
555         (param.baseParam.callerName.find(SETTRINGS_NAME) != std::string::npos ||
556         param.authIntent == HdiAuthIntent::UNLOCK)) {
557         paramHal.isExpiredReturnSuccess = true;
558     }
559     if (!param.collectorUdid.empty()) {
560         if (memcpy_s(paramHal.collectorUdid, sizeof(paramHal.collectorUdid),
561             (uint8_t *)param.collectorUdid.c_str(), param.collectorUdid.length()) != EOK) {
562             IAM_LOGE("collectorUdid copy failed");
563             return RESULT_BAD_COPY;
564         }
565     }
566     Uint8Array localUdid = { paramHal.localUdid, sizeof(paramHal.localUdid) };
567     if (!GetLocalUdid(&localUdid)) {
568         IAM_LOGE("GetLocalUdid failed");
569         return RESULT_GENERAL_ERROR;
570     }
571     return RESULT_SUCCESS;
572 }
573 
BeginAuthentication(uint64_t contextId,const HdiAuthParam & param,std::vector<HdiScheduleInfo> & infos)574 int32_t UserAuthInterfaceService::BeginAuthentication(uint64_t contextId, const HdiAuthParam &param,
575     std::vector<HdiScheduleInfo> &infos)
576 {
577     IAM_LOGI("start");
578     infos.clear();
579     AuthParamHal paramHal = {};
580     int32_t ret = CopyAuthParamToHal(contextId, param, paramHal);
581     if (ret != RESULT_SUCCESS) {
582         IAM_LOGE("copy CopyAuthParamToHal failed %{public}d", ret);
583         return ret;
584     }
585     std::lock_guard<std::mutex> lock(g_mutex);
586     LinkedList *schedulesGet = nullptr;
587     ret = GenerateSolutionFunc(paramHal, &schedulesGet);
588     if (ret != RESULT_SUCCESS) {
589         IAM_LOGE("generate solution failed %{public}d", ret);
590         return ret;
591     }
592     if (schedulesGet == nullptr) {
593         IAM_LOGE("get null schedule");
594         return RESULT_GENERAL_ERROR;
595     }
596     LinkedListNode *tempNode = schedulesGet->head;
597     while (tempNode != nullptr) {
598         if (tempNode->data == nullptr) {
599             IAM_LOGE("node data is invalid");
600             DestroyLinkedList(schedulesGet);
601             return RESULT_UNKNOWN;
602         }
603         HdiScheduleInfo temp = {};
604         auto coAuthSchedule = static_cast<CoAuthSchedule *>(tempNode->data);
605         if (!CopyAuthScheduleInfo(paramHal, coAuthSchedule, &temp)) {
606             infos.clear();
607             IAM_LOGE("copy schedule info failed");
608             DestroyLinkedList(schedulesGet);
609             return RESULT_GENERAL_ERROR;
610         }
611         infos.push_back(temp);
612         tempNode = tempNode->next;
613     }
614     DestroyLinkedList(schedulesGet);
615     return ret;
616 }
617 
GetAllUserInfo(std::vector<UserInfo> & userInfos)618 int32_t UserAuthInterfaceService::GetAllUserInfo(std::vector<UserInfo> &userInfos)
619 {
620     IAM_LOGI("GetAllUserInfo mock start");
621     static_cast<void>(userInfos);
622 
623     return RESULT_SUCCESS;
624 }
625 
CreateExecutorCommand(int32_t userId,HdiAuthResultInfo & info)626 static int32_t CreateExecutorCommand(int32_t userId, HdiAuthResultInfo &info)
627 {
628     LinkedList *executorSendMsg = nullptr;
629     AuthPropertyMode authPropMode;
630     if (info.result == RESULT_SUCCESS) {
631         authPropMode = PROPERTY_MODE_UNFREEZE;
632     } else if (info.remainAttempts == 0) {
633         authPropMode = PROPERTY_MODE_FREEZE;
634     } else {
635         return RESULT_SUCCESS;
636     }
637     ResultCode ret = GetExecutorMsgList(userId, authPropMode, &executorSendMsg);
638     if (ret != RESULT_SUCCESS) {
639         IAM_LOGE("get executor msg failed");
640         return ret;
641     }
642 
643     LinkedListNode *temp = executorSendMsg->head;
644     while (temp != nullptr) {
645         if (temp->data == nullptr) {
646             IAM_LOGE("list node is invalid");
647             DestroyLinkedList(executorSendMsg);
648             return RESULT_UNKNOWN;
649         }
650         auto nodeData = static_cast<ExecutorMsg *>(temp->data);
651         Buffer *nodeMsgBuffer = nodeData->msg;
652         if (!IsBufferValid(nodeMsgBuffer)) {
653             IAM_LOGE("node's buffer invalid");
654             DestroyLinkedList(executorSendMsg);
655             return RESULT_UNKNOWN;
656         }
657         HdiExecutorSendMsg msg = {};
658         msg.executorIndex = nodeData->executorIndex;
659         msg.commandId = static_cast<int32_t>(authPropMode);
660         msg.msg.resize(nodeMsgBuffer->contentSize);
661         if (memcpy_s(msg.msg.data(), msg.msg.size(), nodeMsgBuffer->buf, nodeMsgBuffer->contentSize) != EOK) {
662             IAM_LOGE("copy failed");
663             msg.msg.clear();
664             DestroyLinkedList(executorSendMsg);
665             return RESULT_BAD_COPY;
666         }
667         info.msgs.push_back(msg);
668         temp = temp->next;
669     }
670     DestroyLinkedList(executorSendMsg);
671     return RESULT_SUCCESS;
672 }
673 
CopyAuthResult(AuthResult & infoIn,UserAuthTokenHal & authTokenIn,HdiAuthResultInfo & infoOut,HdiEnrolledState & enrolledStateOut)674 static int32_t CopyAuthResult(AuthResult &infoIn, UserAuthTokenHal &authTokenIn, HdiAuthResultInfo &infoOut,
675     HdiEnrolledState &enrolledStateOut)
676 {
677     IAM_LOGI("start");
678     infoOut.result = infoIn.result;
679     infoOut.remainAttempts = infoIn.remainTimes;
680     infoOut.lockoutDuration = infoIn.freezingTime;
681     enrolledStateOut.credentialDigest = infoIn.credentialDigest;
682     enrolledStateOut.credentialCount = infoIn.credentialCount;
683     infoOut.pinExpiredInfo = infoIn.pinExpiredInfo;
684     if (infoOut.result == RESULT_SUCCESS) {
685         infoOut.userId = infoIn.userId;
686         infoOut.credentialId = infoIn.credentialId;
687         IAM_LOGI("matched userId: %{public}d, credentialId: %{public}s.",
688             infoOut.userId, GET_MASKED_STRING(infoOut.credentialId).c_str());
689         infoOut.token.resize(sizeof(UserAuthTokenHal));
690         if (memcpy_s(infoOut.token.data(), infoOut.token.size(), &authTokenIn, sizeof(UserAuthTokenHal)) != EOK) {
691                 IAM_LOGE("copy authToken failed");
692                 infoOut.token.clear();
693                 return RESULT_BAD_COPY;
694         }
695         if (infoIn.rootSecret != nullptr) {
696             infoOut.rootSecret.resize(infoIn.rootSecret->contentSize);
697             if (memcpy_s(infoOut.rootSecret.data(), infoOut.rootSecret.size(),
698                 infoIn.rootSecret->buf, infoIn.rootSecret->contentSize) != EOK) {
699                 IAM_LOGE("copy secret failed");
700                 infoOut.rootSecret.clear();
701                 infoOut.token.clear();
702                 return RESULT_BAD_COPY;
703             }
704         }
705     }
706     if (infoIn.remoteAuthResultMsg != nullptr) {
707         infoOut.remoteAuthResultMsg.resize(infoIn.remoteAuthResultMsg->contentSize);
708         if (memcpy_s(infoOut.remoteAuthResultMsg.data(), infoOut.remoteAuthResultMsg.size(),
709             infoIn.remoteAuthResultMsg->buf, infoIn.remoteAuthResultMsg->contentSize) != EOK) {
710             IAM_LOGE("copy remoteAuthResultMsg failed");
711             infoOut.remoteAuthResultMsg.clear();
712             infoOut.rootSecret.clear();
713             infoOut.token.clear();
714             return RESULT_BAD_COPY;
715         }
716     }
717     infoOut.userId = infoIn.userId;
718     IAM_LOGI("matched userId: %{public}d.", infoOut.userId);
719     return RESULT_SUCCESS;
720 }
721 
UpdateAuthenticationResultInner(uint64_t contextId,Buffer * scheduleResultBuffer,HdiAuthResultInfo & info,HdiEnrolledState & enrolledState)722 static int32_t UpdateAuthenticationResultInner(uint64_t contextId,
723     Buffer *scheduleResultBuffer, HdiAuthResultInfo &info, HdiEnrolledState &enrolledState)
724 {
725     UserAuthTokenHal authTokenHal = {};
726     AuthResult authResult = {};
727     int32_t funcRet = RESULT_GENERAL_ERROR;
728     do {
729         UserAuthContext *userAuthContext = GetContext(contextId);
730         if (userAuthContext == NULL) {
731             IAM_LOGE("context is not found");
732             return RESULT_GENERAL_ERROR;
733         }
734         int32_t authIntent = userAuthContext->authIntent;
735         int32_t ret = RequestAuthResultFunc(contextId, scheduleResultBuffer, &authTokenHal, &authResult);
736         if (ret != RESULT_SUCCESS) {
737             IAM_LOGE("execute func failed");
738             break;
739         }
740         ret = CopyAuthResult(authResult, authTokenHal, info, enrolledState);
741         if (ret != RESULT_SUCCESS) {
742             IAM_LOGE("Copy auth result failed");
743             break;
744         }
745         if (authResult.authType != PIN_AUTH) {
746             IAM_LOGI("type not pin");
747         } else {
748             IAM_LOGI("type pin");
749             if (authIntent == ABANDONED_PIN_AUTH) {
750                 IAM_LOGI("authIntent is old pin auth");
751                 funcRet = RESULT_SUCCESS;
752                 break;
753             }
754             ret = CreateExecutorCommand(authResult.userId, info);
755             if (ret != RESULT_SUCCESS) {
756                 IAM_LOGE("create executor command failed");
757                 break;
758             }
759         }
760         funcRet = RESULT_SUCCESS;
761     } while (0);
762 
763     DestroyAuthResult(&authResult);
764     return funcRet;
765 }
766 
UpdateAuthenticationResult(uint64_t contextId,const std::vector<uint8_t> & scheduleResult,HdiAuthResultInfo & info,HdiEnrolledState & enrolledState)767 int32_t UserAuthInterfaceService::UpdateAuthenticationResult(uint64_t contextId,
768     const std::vector<uint8_t> &scheduleResult, HdiAuthResultInfo &info, HdiEnrolledState &enrolledState)
769 {
770     IAM_LOGI("start");
771     if (scheduleResult.size() == 0) {
772         IAM_LOGE("param is invalid");
773         DestroyContextbyId(contextId);
774         return RESULT_BAD_PARAM;
775     }
776     Buffer *scheduleResultBuffer = CreateBufferByData(&scheduleResult[0], scheduleResult.size());
777     if (!IsBufferValid(scheduleResultBuffer)) {
778         IAM_LOGE("scheduleTokenBuffer is invalid");
779         DestroyContextbyId(contextId);
780         return RESULT_NO_MEMORY;
781     }
782     std::lock_guard<std::mutex> lock(g_mutex);
783     int32_t ret = UpdateAuthenticationResultInner(contextId, scheduleResultBuffer, info, enrolledState);
784     DestoryBuffer(scheduleResultBuffer);
785     return ret;
786 }
787 
CancelAuthentication(uint64_t contextId)788 int32_t UserAuthInterfaceService::CancelAuthentication(uint64_t contextId)
789 {
790     IAM_LOGI("start");
791     std::lock_guard<std::mutex> lock(g_mutex);
792     return DestroyContextbyId(contextId);
793 }
794 
BeginIdentification(uint64_t contextId,int32_t authType,const std::vector<uint8_t> & challenge,uint32_t executorSensorHint,HdiScheduleInfo & scheduleInfo)795 int32_t UserAuthInterfaceService::BeginIdentification(uint64_t contextId, int32_t authType,
796     const std::vector<uint8_t> &challenge, uint32_t executorSensorHint, HdiScheduleInfo &scheduleInfo)
797 {
798     IAM_LOGI("start");
799     if (authType == PIN) {
800         IAM_LOGE("param is invalid");
801         return RESULT_BAD_PARAM;
802     }
803     IdentifyParam param = {};
804     param.contextId = contextId;
805     param.authType = static_cast<uint32_t>(authType);
806     param.executorSensorHint = executorSensorHint;
807     if (!challenge.empty() && memcpy_s(param.challenge, CHALLENGE_LEN, challenge.data(), challenge.size()) != EOK) {
808         IAM_LOGE("challenge copy failed");
809         return RESULT_BAD_COPY;
810     }
811     std::lock_guard<std::mutex> lock(g_mutex);
812     LinkedList *scheduleGet = nullptr;
813     int32_t ret = DoIdentify(param, &scheduleGet);
814     if (ret != RESULT_SUCCESS) {
815         IAM_LOGE("generate solution failed");
816         return ret;
817     }
818     if (scheduleGet == nullptr) {
819         IAM_LOGE("get null schedule");
820         return RESULT_GENERAL_ERROR;
821     }
822     if (scheduleGet->head == nullptr || scheduleGet->head->data == nullptr) {
823         IAM_LOGE("scheduleGet is invalid");
824         DestroyLinkedList(scheduleGet);
825         return RESULT_UNKNOWN;
826     }
827     auto data = static_cast<CoAuthSchedule *>(scheduleGet->head->data);
828     if (!CopyScheduleInfo(data, &scheduleInfo)) {
829         IAM_LOGE("copy schedule failed");
830         ret = RESULT_BAD_COPY;
831     }
832     DestroyLinkedList(scheduleGet);
833     return ret;
834 }
835 
UpdateIdentificationResult(uint64_t contextId,const std::vector<uint8_t> & scheduleResult,IdentifyResultInfo & info)836 int32_t UserAuthInterfaceService::UpdateIdentificationResult(uint64_t contextId,
837     const std::vector<uint8_t> &scheduleResult, IdentifyResultInfo &info)
838 {
839     IAM_LOGI("start");
840     if (scheduleResult.size() == 0) {
841         IAM_LOGE("param is invalid");
842         return RESULT_BAD_PARAM;
843     }
844     Buffer *scheduleResultBuffer = CreateBufferByData(&scheduleResult[0], scheduleResult.size());
845     if (!IsBufferValid(scheduleResultBuffer)) {
846         IAM_LOGE("scheduleTokenBuffer is invalid");
847         return RESULT_NO_MEMORY;
848     }
849     std::lock_guard<std::mutex> lock(g_mutex);
850     UserAuthTokenHal token = {};
851     int32_t ret = DoUpdateIdentify(contextId, scheduleResultBuffer, &info.userId, &token, &info.result);
852     DestoryBuffer(scheduleResultBuffer);
853     if (ret != RESULT_SUCCESS) {
854         IAM_LOGE("DoUpdateIdentify failed");
855         return ret;
856     }
857     if (info.result == RESULT_SUCCESS) {
858         info.token.resize(sizeof(UserAuthTokenHal));
859         if (memcpy_s(info.token.data(), info.token.size(), &token, sizeof(token)) != EOK) {
860             IAM_LOGE("copy authToken failed");
861             info.token.clear();
862             return RESULT_BAD_COPY;
863         }
864     }
865     return RESULT_SUCCESS;
866 }
867 
CancelIdentification(uint64_t contextId)868 int32_t UserAuthInterfaceService::CancelIdentification(uint64_t contextId)
869 {
870     IAM_LOGI("start");
871     std::lock_guard<std::mutex> lock(g_mutex);
872     return DestroyContextbyId(contextId);
873 }
874 
GetAvailableStatus(int32_t userId,int32_t authType,uint32_t authTrustLevel,int32_t & checkResult)875 int32_t UserAuthInterfaceService::GetAvailableStatus(int32_t userId, int32_t authType, uint32_t authTrustLevel,
876     int32_t &checkResult)
877 {
878     IAM_LOGI("start");
879     std::lock_guard<std::mutex> lock(g_mutex);
880     checkResult = GetAvailableStatusFunc(userId, authType, authTrustLevel);
881     if (checkResult != RESULT_SUCCESS) {
882         IAM_LOGE("GetAvailableStatusFunc failed");
883     }
884     return RESULT_SUCCESS;
885 }
886 
GetValidSolution(int32_t userId,const std::vector<int32_t> & authTypes,uint32_t authTrustLevel,std::vector<int32_t> & validTypes)887 int32_t UserAuthInterfaceService::GetValidSolution(int32_t userId, const std::vector<int32_t> &authTypes,
888     uint32_t authTrustLevel, std::vector<int32_t> &validTypes)
889 {
890     IAM_LOGI("start userId:%{public}d authTrustLevel:%{public}u", userId, authTrustLevel);
891     static int32_t resultPriority[] = {RESULT_GENERAL_ERROR, RESULT_TYPE_NOT_SUPPORT, RESULT_TRUST_LEVEL_NOT_SUPPORT,
892         RESULT_NOT_ENROLLED, RESULT_PIN_EXPIRED};
893     int32_t result = RESULT_GENERAL_ERROR;
894     validTypes.clear();
895     std::lock_guard<std::mutex> lock(g_mutex);
896     for (auto &authType : authTypes) {
897         int32_t checkRet = GetAvailableStatusFunc(userId, authType, authTrustLevel);
898         if (checkRet == RESULT_SUCCESS) {
899             IAM_LOGI("get valid authType:%{public}d", authType);
900             validTypes.push_back(authType);
901             continue;
902         }
903         bool isResultFound = false;
904         for (uint32_t i = 0; i < sizeof(resultPriority) / sizeof(int32_t); i++) {
905             if (resultPriority[i] == result) {
906                 isResultFound = true;
907             }
908             if (resultPriority[i] == checkRet && isResultFound) {
909                 IAM_LOGI("checkRet:%{public}d higher priority than result:%{public}d", checkRet, result);
910                 result = checkRet;
911                 break;
912             }
913         }
914     }
915     if (validTypes.empty()) {
916         IAM_LOGE("no auth type valid");
917         return result;
918     }
919     return RESULT_SUCCESS;
920 }
921 
OpenSession(int32_t userId,std::vector<uint8_t> & challenge)922 int32_t UserAuthInterfaceService::OpenSession(int32_t userId, std::vector<uint8_t> &challenge)
923 {
924     IAM_LOGI("start");
925     std::lock_guard<std::mutex> lock(g_mutex);
926     challenge.resize(CHALLENGE_LEN);
927     int32_t ret = OpenEditSession(userId, challenge.data(), challenge.size());
928     if (ret != RESULT_SUCCESS) {
929         IAM_LOGE("failed to open session");
930         challenge.clear();
931     }
932     return ret;
933 }
934 
CloseSession(int32_t userId)935 int32_t UserAuthInterfaceService::CloseSession(int32_t userId)
936 {
937     IAM_LOGI("start");
938     std::lock_guard<std::mutex> lock(g_mutex);
939     return CloseEditSession();
940 }
941 
CheckOperatePermission(const std::vector<uint8_t> & authToken,const HdiEnrollParam & param,PermissionCheckParam * checkParam,ScheduleType * scheduleType)942 static int32_t CheckOperatePermission(const std::vector<uint8_t> &authToken, const HdiEnrollParam &param,
943     PermissionCheckParam *checkParam, ScheduleType *scheduleType)
944 {
945     IAM_LOGI("start");
946     if ((authToken.size() != sizeof(UserAuthTokenHal) && authToken.size() != 0) ||
947         checkParam == NULL || scheduleType == NULL) {
948         IAM_LOGE("authToken len is invalid");
949         return RESULT_BAD_PARAM;
950     }
951     if (authToken.size() == sizeof(UserAuthTokenHal) &&
952         memcpy_s(checkParam->token, AUTH_TOKEN_LEN, &authToken[0], authToken.size()) != EOK) {
953         return RESULT_BAD_COPY;
954     }
955     checkParam->authType = param.authType;
956     checkParam->userId = param.userId;
957     checkParam->executorSensorHint = param.executorSensorHint;
958     checkParam->userType = param.userType;
959     std::lock_guard<std::mutex> lock(g_mutex);
960     int32_t ret;
961     if (authToken.size() == sizeof(UserAuthTokenHal) && param.authType == HdiAuthType::PIN) {
962         ret = CheckUpdatePermission(checkParam);
963         if (ret != RESULT_SUCCESS) {
964             IAM_LOGE("check update permission failed");
965             return ret;
966         }
967         *scheduleType = SCHEDULE_TYPE_UPDATE;
968     } else {
969         ret = CheckEnrollPermission(checkParam);
970         if (ret != RESULT_SUCCESS) {
971             IAM_LOGE("check enroll permission failed");
972             return ret;
973         }
974         *scheduleType = SCHEDULE_TYPE_ENROLL;
975     }
976 
977     return RESULT_SUCCESS;
978 }
979 
BeginEnrollment(const std::vector<uint8_t> & authToken,const HdiEnrollParam & param,HdiScheduleInfo & info)980 int32_t UserAuthInterfaceService::BeginEnrollment(
981     const std::vector<uint8_t> &authToken, const HdiEnrollParam &param, HdiScheduleInfo &info)
982 {
983     IAM_LOGI("start");
984     PermissionCheckParam checkParam = {};
985     ScheduleType scheduleType = SCHEDULE_TYPE_ENROLL;
986     int32_t ret = CheckOperatePermission(authToken, param, &checkParam, &scheduleType);
987     if (ret != RESULT_SUCCESS) {
988         IAM_LOGE("CheckOperatePermission failed, ret:%{public}d", ret);
989         return ret;
990     }
991 
992     CoAuthSchedule *scheduleInfo = GenerateCoAuthSchedule(&checkParam, scheduleType);
993     if (scheduleInfo == nullptr) {
994         IAM_LOGE("get schedule info failed");
995         return RESULT_UNKNOWN;
996     }
997     if (!CopyScheduleInfo(scheduleInfo, &info)) {
998         IAM_LOGE("copy schedule info failed");
999         DestroyCoAuthSchedule(scheduleInfo);
1000         BreakOffCoauthSchedule();
1001         return RESULT_BAD_COPY;
1002     }
1003     ret = SetAttributeToExtraInfo(info, INVALID_CAPABILITY_LEVEL, scheduleInfo->scheduleId);
1004     if (ret != RESULT_SUCCESS) {
1005         IAM_LOGE("SetAttributeToExtraInfo failed");
1006         BreakOffCoauthSchedule();
1007     }
1008     DestroyCoAuthSchedule(scheduleInfo);
1009     IAM_LOGI("end");
1010     return ret;
1011 }
1012 
CancelEnrollment(int32_t userId)1013 int32_t UserAuthInterfaceService::CancelEnrollment(int32_t userId)
1014 {
1015     IAM_LOGI("start");
1016     std::lock_guard<std::mutex> lock(g_mutex);
1017     BreakOffCoauthSchedule();
1018     return RESULT_SUCCESS;
1019 }
1020 
CopyCredentialInfo(const CredentialInfoHal & in,HdiCredentialInfo & out)1021 static void CopyCredentialInfo(const CredentialInfoHal &in, HdiCredentialInfo &out)
1022 {
1023     out.authType = static_cast<AuthType>(in.authType);
1024     out.authSubType = in.credentialType;
1025     out.credentialId = in.credentialId;
1026     out.templateId = in.templateId;
1027     out.executorMatcher = in.executorMatcher;
1028     out.executorSensorHint = in.executorSensorHint;
1029     out.executorIndex = QueryCredentialExecutorIndex(in.authType, in.executorSensorHint);
1030     out.isAbandoned = in.isAbandoned;
1031     out.validityPeriod = CalcCredentialValidPeriod(&in);
1032     IAM_LOGI("credentialId:%{public}u, authType:%{public}u, isAbandoned:%{public}d, validityPeriod:%{public}" PRId64,
1033         static_cast<uint16_t>(out.credentialId), out.authType, out.isAbandoned, out.validityPeriod);
1034 }
1035 
CopyCredentialOpeateResult(OperateResult & in,HdiCredentialOperateResult & out)1036 static void CopyCredentialOpeateResult(OperateResult &in, HdiCredentialOperateResult &out)
1037 {
1038     out.operateType = static_cast<HdiCredentialOperateType>(in.operateType);
1039     if (in.operateType == DELETE_CREDENTIAL) {
1040         for (uint32_t index = 0; index < in.credentialCount && index < MAX_CREDENTIAL_NUM_OF_ENROLL; index++) {
1041             HdiCredentialInfo credentialInfo = {};
1042             CopyCredentialInfo(in.credentialInfos[index], credentialInfo);
1043             out.credentialInfos.push_back(credentialInfo);
1044         }
1045     } else if (in.operateType == ABANDON_CREDENTIAL) {
1046         CopyScheduleInfo(&(in.scheduleInfo), &(out.scheduleInfo));
1047     }
1048 }
1049 
GetUpdateResult(int32_t userId,HdiEnrollResultInfo & info,Buffer * scheduleResultBuffer)1050 static int32_t GetUpdateResult(int32_t userId, HdiEnrollResultInfo &info, Buffer *scheduleResultBuffer)
1051 {
1052     UpdateCredentialOutput output = {};
1053     int32_t ret = UpdateCredentialFunc(userId, scheduleResultBuffer, &output);
1054     if (ret == RESULT_SUCCESS) {
1055         /* Only update pin have oldRootSecret and rootSecret */
1056         info.rootSecret.resize(ROOT_SECRET_LEN);
1057         if (memcpy_s(info.rootSecret.data(), ROOT_SECRET_LEN, output.rootSecret->buf, ROOT_SECRET_LEN) != EOK) {
1058             IAM_LOGE("failed to copy rootSecret");
1059             ret = RESULT_BAD_COPY;
1060             goto ERROR;
1061         }
1062         info.oldRootSecret.resize(ROOT_SECRET_LEN);
1063         if (memcpy_s(info.oldRootSecret.data(), ROOT_SECRET_LEN, output.oldRootSecret->buf, ROOT_SECRET_LEN) != EOK) {
1064             IAM_LOGE("failed to copy oldRootSecret");
1065             ret = RESULT_BAD_COPY;
1066             goto ERROR;
1067         }
1068         info.authToken.resize(AUTH_TOKEN_LEN);
1069         if (memcpy_s(info.authToken.data(), AUTH_TOKEN_LEN, output.authToken->buf, AUTH_TOKEN_LEN) != EOK) {
1070             IAM_LOGE("failed to copy authToken");
1071             ret = RESULT_BAD_COPY;
1072             goto ERROR;
1073         }
1074         info.credentialId = output.credentialId;
1075         CopyCredentialInfo(output.deletedCredential, info.oldInfo);
1076         goto EXIT;
1077     }
1078 
1079 ERROR:
1080     (void)memset_s(info.rootSecret.data(), info.rootSecret.size(), 0, info.rootSecret.size());
1081     info.rootSecret.clear();
1082     (void)memset_s(info.oldRootSecret.data(), info.oldRootSecret.size(), 0, info.oldRootSecret.size());
1083     info.oldRootSecret.clear();
1084     (void)memset_s(info.authToken.data(), info.authToken.size(), 0, info.authToken.size());
1085     info.authToken.clear();
1086 
1087 EXIT:
1088     DestoryBuffer(output.rootSecret);
1089     DestoryBuffer(output.oldRootSecret);
1090     DestoryBuffer(output.authToken);
1091     return ret;
1092 }
1093 
GetEnrollResult(int32_t userId,HdiEnrollResultInfo & info,Buffer * scheduleResultBuffer)1094 static int32_t GetEnrollResult(int32_t userId, HdiEnrollResultInfo &info, Buffer *scheduleResultBuffer)
1095 {
1096     Buffer *authToken = nullptr;
1097     Buffer *rootSecret = nullptr;
1098     int32_t ret = AddCredentialFunc(userId, scheduleResultBuffer, &info.credentialId, &rootSecret, &authToken);
1099     if (ret == RESULT_SUCCESS) {
1100         /* Only enroll pin have authToken and rootSecret */
1101         if (authToken != nullptr) {
1102             info.authToken.resize(authToken->contentSize);
1103             if (memcpy_s(info.authToken.data(), info.authToken.size(), authToken->buf, authToken->contentSize) != EOK) {
1104                 IAM_LOGE("failed to copy authToken");
1105                 info.authToken.clear();
1106                 DestoryBuffer(authToken);
1107                 DestoryBuffer(rootSecret);
1108                 return RESULT_BAD_COPY;
1109             }
1110         }
1111         if (rootSecret != nullptr) {
1112             info.rootSecret.resize(rootSecret->contentSize);
1113             if (memcpy_s(info.rootSecret.data(), info.rootSecret.size(), rootSecret->buf,
1114                 rootSecret->contentSize) != EOK) {
1115                 IAM_LOGE("failed to copy rootSecret");
1116                 info.rootSecret.clear();
1117                 ret = RESULT_BAD_COPY;
1118             }
1119         }
1120     }
1121     DestoryBuffer(authToken);
1122     DestoryBuffer(rootSecret);
1123     return ret;
1124 }
1125 
UpdateEnrollmentResult(int32_t userId,const std::vector<uint8_t> & scheduleResult,HdiEnrollResultInfo & info)1126 int32_t UserAuthInterfaceService::UpdateEnrollmentResult(int32_t userId, const std::vector<uint8_t> &scheduleResult,
1127     HdiEnrollResultInfo &info)
1128 {
1129     IAM_LOGI("start");
1130     if (scheduleResult.size() == 0) {
1131         IAM_LOGE("enrollToken is invalid");
1132         return RESULT_BAD_PARAM;
1133     }
1134     Buffer *scheduleResultBuffer = CreateBufferByData(&scheduleResult[0], scheduleResult.size());
1135     if (scheduleResultBuffer == nullptr) {
1136         IAM_LOGE("scheduleTokenBuffer is null");
1137         return RESULT_NO_MEMORY;
1138     }
1139     std::lock_guard<std::mutex> lock(g_mutex);
1140     ScheduleType scheduleType;
1141     int32_t ret = GetScheduleType(&scheduleType);
1142     if (ret != RESULT_SUCCESS) {
1143         IAM_LOGE("get isUpdate failed");
1144         DestoryBuffer(scheduleResultBuffer);
1145         return ret;
1146     }
1147     if (scheduleType == SCHEDULE_TYPE_UPDATE) {
1148         ret = GetUpdateResult(userId, info, scheduleResultBuffer);
1149         if (ret != RESULT_SUCCESS) {
1150             IAM_LOGE("GetUpdateResult failed");
1151         }
1152     } else if (scheduleType == SCHEDULE_TYPE_ENROLL) {
1153         ret = GetEnrollResult(userId, info, scheduleResultBuffer);
1154         if (ret != RESULT_SUCCESS) {
1155             IAM_LOGE("GetEnrollResult failed");
1156         }
1157     }
1158 
1159     DestoryBuffer(scheduleResultBuffer);
1160     return ret;
1161 }
1162 
DeleteCredential(int32_t userId,uint64_t credentialId,const std::vector<uint8_t> & authToken,HdiCredentialOperateResult & hdiOperateResult)1163 int32_t UserAuthInterfaceService::DeleteCredential(int32_t userId, uint64_t credentialId,
1164     const std::vector<uint8_t> &authToken, HdiCredentialOperateResult &hdiOperateResult)
1165 {
1166     IAM_LOGI("start");
1167     if (authToken.size() != sizeof(UserAuthTokenHal)) {
1168         IAM_LOGE("authToken len is invalid");
1169         return RESULT_BAD_PARAM;
1170     }
1171     std::lock_guard<std::mutex> lock(g_mutex);
1172     CredentialDeleteParam param = {};
1173     if (memcpy_s(param.token, AUTH_TOKEN_LEN, &authToken[0], authToken.size()) != EOK) {
1174         IAM_LOGE("param token copy failed");
1175         return RESULT_BAD_COPY;
1176     }
1177     param.userId = userId;
1178     param.credentialId = credentialId;
1179 
1180     OperateResult operateResult = {};
1181     int32_t ret = DeleteCredentialFunc(param, &operateResult);
1182     if (ret != RESULT_SUCCESS) {
1183         IAM_LOGE("delete credential failed");
1184         BreakOffCoauthSchedule();
1185         return ret;
1186     }
1187 
1188     CopyCredentialOpeateResult(operateResult, hdiOperateResult);
1189     if (operateResult.operateType == ABANDON_CREDENTIAL) {
1190         Buffer *oldRootSecret = nullptr;
1191         Buffer *newRootSecret = GetNewRootSecret(userId);
1192         PinChangeScence pinChangeScence = GetPinChangeScence(userId);
1193         if (pinChangeScence == PIN_RESET_SCENCE) {
1194             oldRootSecret = GetOldRootSecret(userId);
1195         } else {
1196             oldRootSecret = GetCurRootSecret(userId);
1197         }
1198         ret = SetAttributeToAbandonMsg(hdiOperateResult.scheduleInfo,
1199             hdiOperateResult.scheduleInfo.scheduleId, oldRootSecret, newRootSecret);
1200         if (ret != RESULT_SUCCESS) {
1201             IAM_LOGE("SetAttributeToAbandonMsg failed");
1202             BreakOffCoauthSchedule();
1203             return ret;
1204         }
1205     }
1206     return RESULT_SUCCESS;
1207 }
1208 
GetCredential(int32_t userId,int32_t authType,std::vector<CredentialInfo> & infos)1209 int32_t UserAuthInterfaceService::GetCredential(int32_t userId, int32_t authType, std::vector<CredentialInfo> &infos)
1210 {
1211     IAM_LOGI("start");
1212     std::lock_guard<std::mutex> lock(g_mutex);
1213     LinkedList *credList = nullptr;
1214     int32_t ret = QueryCredentialFunc(userId, authType, &credList);
1215     if (ret != RESULT_SUCCESS) {
1216         IAM_LOGE("query credential failed");
1217         return ret;
1218     }
1219     infos.reserve(credList->getSize(credList));
1220     LinkedListNode *temp = credList->head;
1221     CredentialInfo abandonCredential = {};
1222     bool hasAbandonedCredential = false;
1223     while (temp != nullptr) {
1224         if (temp->data == nullptr) {
1225             IAM_LOGE("list node is invalid");
1226             DestroyLinkedList(credList);
1227             return RESULT_UNKNOWN;
1228         }
1229         auto credentialHal = static_cast<CredentialInfoHal *>(temp->data);
1230         if (credentialHal->isAbandoned) {
1231             if (!hasAbandonedCredential) {
1232                 CopyCredentialInfo(*credentialHal, abandonCredential);
1233                 hasAbandonedCredential = true;
1234             } else {
1235                 IAM_LOGE("abandoned credenttial excced limit");
1236                 DestroyLinkedList(credList);
1237                 return RESULT_GENERAL_ERROR;
1238             }
1239         } else {
1240             CredentialInfo credentialInfo = {};
1241             CopyCredentialInfo(*credentialHal, credentialInfo);
1242             infos.push_back(credentialInfo);
1243         }
1244         temp = temp->next;
1245     }
1246     if (hasAbandonedCredential) {
1247         infos.push_back(abandonCredential);
1248     }
1249     DestroyLinkedList(credList);
1250     return RESULT_SUCCESS;
1251 }
1252 
GetUserInfo(int32_t userId,uint64_t & secureUid,int32_t & pinSubType,std::vector<EnrolledInfo> & infos)1253 int32_t UserAuthInterfaceService::GetUserInfo(int32_t userId, uint64_t &secureUid, int32_t &pinSubType,
1254     std::vector<EnrolledInfo> &infos)
1255 {
1256     IAM_LOGI("start");
1257     std::lock_guard<std::mutex> lock(g_mutex);
1258     EnrolledInfoHal *enrolledInfoHals = nullptr;
1259     uint32_t num = 0;
1260     uint64_t pinSubTypeGet;
1261     int32_t ret = GetUserInfoFunc(userId, &secureUid, &pinSubTypeGet, &enrolledInfoHals, &num);
1262     if (ret == RESULT_NOT_FOUND) {
1263         IAM_LOGE("user not found");
1264         return RESULT_SUCCESS;
1265     }
1266     if (ret != RESULT_SUCCESS) {
1267         IAM_LOGE("get user info failed");
1268         return ret;
1269     }
1270     pinSubType = static_cast<PinSubType>(pinSubTypeGet);
1271     for (uint32_t i = 0; i < num; ++i) {
1272         EnrolledInfo enrolledInfo = {};
1273         enrolledInfo.authType = static_cast<AuthType>(enrolledInfoHals[i].authType);
1274         enrolledInfo.enrolledId = enrolledInfoHals[i].enrolledId;
1275         infos.push_back(enrolledInfo);
1276     }
1277     free(enrolledInfoHals);
1278     return RESULT_SUCCESS;
1279 }
1280 
DeleteUser(int32_t userId,const std::vector<uint8_t> & authToken,std::vector<CredentialInfo> & deletedInfos,std::vector<uint8_t> & rootSecret)1281 int32_t UserAuthInterfaceService::DeleteUser(int32_t userId, const std::vector<uint8_t> &authToken,
1282     std::vector<CredentialInfo> &deletedInfos, std::vector<uint8_t> &rootSecret)
1283 {
1284     IAM_LOGI("start");
1285     if (authToken.size() != sizeof(UserAuthTokenHal)) {
1286         IAM_LOGE("authToken is invalid");
1287         return RESULT_VERIFY_TOKEN_FAIL;
1288     }
1289     UserAuthTokenHal authTokenStruct = {};
1290     if (memcpy_s(&authTokenStruct, sizeof(UserAuthTokenHal), &authToken[0], authToken.size()) != EOK) {
1291         IAM_LOGE("authTokenStruct copy failed");
1292         return RESULT_BAD_COPY;
1293     }
1294     int32_t ret = CheckIdmOperationToken(userId, &authTokenStruct);
1295     if (ret != RESULT_SUCCESS) {
1296         IAM_LOGE("failed to verify token");
1297         return RESULT_VERIFY_TOKEN_FAIL;
1298     }
1299     ret = EnforceDeleteUser(userId, deletedInfos);
1300     if (ret != RESULT_SUCCESS) {
1301         IAM_LOGE("EnforceDeleteUser fail");
1302         return RESULT_GENERAL_ERROR;
1303     }
1304 
1305     rootSecret.resize(ROOT_SECRET_LEN);
1306     Buffer *oldRootSecret = GetCurRootSecret(userId);
1307     if (!IsBufferValid(oldRootSecret)) {
1308         IAM_LOGE("get GetCurRootSecret failed");
1309         return RESULT_SUCCESS;
1310     }
1311     if (memcpy_s(rootSecret.data(), rootSecret.size(), oldRootSecret->buf, oldRootSecret->contentSize) != EOK) {
1312         IAM_LOGE("rootSecret copy failed");
1313         ret = RESULT_BAD_COPY;
1314     }
1315 
1316     return ret;
1317 }
1318 
EnforceDeleteUser(int32_t userId,std::vector<CredentialInfo> & deletedInfos)1319 int32_t UserAuthInterfaceService::EnforceDeleteUser(int32_t userId, std::vector<CredentialInfo> &deletedInfos)
1320 {
1321     IAM_LOGI("start");
1322     std::lock_guard<std::mutex> lock(g_mutex);
1323     LinkedList *credList = nullptr;
1324     int32_t ret = DeleteUserInfo(userId, &credList);
1325     if (ret != RESULT_SUCCESS) {
1326         IAM_LOGE("query credential failed");
1327         return ret;
1328     }
1329     RefreshValidTokenTime();
1330     LinkedListNode *temp = credList->head;
1331     while (temp != nullptr) {
1332         if (temp->data == nullptr) {
1333             IAM_LOGE("list node is invalid");
1334             DestroyLinkedList(credList);
1335             return RESULT_UNKNOWN;
1336         }
1337         auto credentialHal = static_cast<CredentialInfoHal *>(temp->data);
1338         CredentialInfo credentialInfo = {};
1339         CopyCredentialInfo(*credentialHal, credentialInfo);
1340         deletedInfos.push_back(credentialInfo);
1341         temp = temp->next;
1342     }
1343     DestroyLinkedList(credList);
1344     return RESULT_SUCCESS;
1345 }
1346 
verifyExecutorRegisterInfo(const HdiExecutorRegisterInfo & in,ExecutorInfoHal & out)1347 static bool verifyExecutorRegisterInfo(const HdiExecutorRegisterInfo &in, ExecutorInfoHal &out)
1348 {
1349     Buffer *execInfoMsg = CreateBufferByData(&in.signedRemoteExecutorInfo[0], in.signedRemoteExecutorInfo.size());
1350     if (!IsBufferValid(execInfoMsg)) {
1351         IAM_LOGE("execInfoMsg is invalid");
1352         return false;
1353     }
1354 
1355     bool isOk = CheckRemoteExecutorInfo(execInfoMsg, &out);
1356     DestoryBuffer(execInfoMsg);
1357     return isOk;
1358 }
1359 
CopyExecutorInfo(const HdiExecutorRegisterInfo & in,ExecutorInfoHal & out)1360 static bool CopyExecutorInfo(const HdiExecutorRegisterInfo &in, ExecutorInfoHal &out)
1361 {
1362     out.authType = in.authType;
1363     out.executorMatcher = in.executorMatcher;
1364     out.esl = in.esl;
1365     out.maxTemplateAcl = in.maxTemplateAcl;
1366     out.executorRole = in.executorRole;
1367     out.executorSensorHint = in.executorSensorHint;
1368     if (memcpy_s(out.pubKey, PUBLIC_KEY_LEN, &in.publicKey[0], in.publicKey.size()) != EOK) {
1369         IAM_LOGE("memcpy failed");
1370         return false;
1371     }
1372 
1373     std::string deviceUdid = in.deviceUdid;
1374     if (deviceUdid.empty()) {
1375         deviceUdid = g_localUdid;
1376     }
1377 
1378     if (memcpy_s(out.deviceUdid, sizeof(out.deviceUdid), deviceUdid.c_str(), deviceUdid.length()) != EOK) {
1379         IAM_LOGE("memcpy failed");
1380         return false;
1381     }
1382 
1383     if (g_localUdid != deviceUdid) {
1384         IAM_LOGI("verify remote executor register info");
1385         if (!verifyExecutorRegisterInfo(in, out)) {
1386             IAM_LOGE("verifyExecutorRegisterInfo failed");
1387             return false;
1388         }
1389         IAM_LOGI("add remote executor authType %{public}d executorRole %{public}d", in.authType, in.executorRole);
1390     } else {
1391         IAM_LOGI("add local executor authType %{public}d executorRole %{public}d", in.authType, in.executorRole);
1392     }
1393     return true;
1394 }
1395 
ObtainReconciliationData(uint32_t authType,uint32_t sensorHint,std::vector<uint64_t> & templateIds)1396 static int32_t ObtainReconciliationData(uint32_t authType, uint32_t sensorHint, std::vector<uint64_t> &templateIds)
1397 {
1398     CredentialCondition condition = {};
1399     SetCredentialConditionAuthType(&condition, authType);
1400     SetCredentialConditionExecutorSensorHint(&condition, sensorHint);
1401     SetCredentialConditionNeedCachePin(&condition);
1402     SetCredentialConditionNeedAbandonPin(&condition);
1403     LinkedList *credList = QueryCredentialLimit(&condition);
1404     if (credList == nullptr) {
1405         IAM_LOGE("query credential failed");
1406         return RESULT_NOT_FOUND;
1407     }
1408     LinkedListNode *temp = credList->head;
1409     while (temp != nullptr) {
1410         if (temp->data == nullptr) {
1411             IAM_LOGE("list node is invalid");
1412             DestroyLinkedList(credList);
1413             return RESULT_UNKNOWN;
1414         }
1415         auto credentialInfo = static_cast<CredentialInfoHal *>(temp->data);
1416         templateIds.push_back(credentialInfo->templateId);
1417         temp = temp->next;
1418     }
1419     DestroyLinkedList(credList);
1420     return RESULT_SUCCESS;
1421 }
1422 
AddExecutor(const HdiExecutorRegisterInfo & info,uint64_t & index,std::vector<uint8_t> & publicKey,std::vector<uint64_t> & templateIds)1423 int32_t UserAuthInterfaceService::AddExecutor(const HdiExecutorRegisterInfo &info, uint64_t &index,
1424     std::vector<uint8_t> &publicKey, std::vector<uint64_t> &templateIds)
1425 {
1426     IAM_LOGI("start");
1427     if (info.publicKey.size() != PUBLIC_KEY_LEN) {
1428         IAM_LOGE("invalid info");
1429         return RESULT_BAD_PARAM;
1430     }
1431     templateIds.clear();
1432     const Buffer *frameworkPubKey = GetPubKey();
1433     if (!IsBufferValid(frameworkPubKey)) {
1434         IAM_LOGE("get public key failed");
1435         return RESULT_UNKNOWN;
1436     }
1437     publicKey.resize(PUBLIC_KEY_LEN);
1438     if (memcpy_s(&publicKey[0], publicKey.size(), frameworkPubKey->buf, frameworkPubKey->contentSize) != EOK) {
1439         IAM_LOGE("copy public key failed");
1440         publicKey.clear();
1441         return RESULT_UNKNOWN;
1442     }
1443     std::lock_guard<std::mutex> lock(g_mutex);
1444     ExecutorInfoHal executorInfoHal = {};
1445     bool copyRet = CopyExecutorInfo(info, executorInfoHal);
1446     if (!copyRet) {
1447         IAM_LOGE("copy executor info failed");
1448         return RESULT_UNKNOWN;
1449     }
1450     int32_t ret = RegisterExecutor(&executorInfoHal, &index);
1451     if (ret != RESULT_SUCCESS) {
1452         IAM_LOGE("register executor failed");
1453         return ret;
1454     }
1455     if (info.executorRole == ALL_IN_ONE) {
1456         return ObtainReconciliationData(executorInfoHal.authType, executorInfoHal.executorSensorHint, templateIds);
1457     }
1458     return RESULT_SUCCESS;
1459 }
1460 
DeleteExecutor(uint64_t index)1461 int32_t UserAuthInterfaceService::DeleteExecutor(uint64_t index)
1462 {
1463     IAM_LOGI("start");
1464     std::lock_guard<std::mutex> lock(g_mutex);
1465     return UnRegisterExecutor(index);
1466 }
1467 
GetAllExtUserInfo(std::vector<ExtUserInfo> & userInfos)1468 int32_t UserAuthInterfaceService::GetAllExtUserInfo(std::vector<ExtUserInfo> &userInfos)
1469 {
1470     IAM_LOGI("start");
1471     UserInfoResult *userInfoResult = (UserInfoResult *)Malloc(sizeof(UserInfoResult) * MAX_USER);
1472     if (userInfoResult == NULL) {
1473         IAM_LOGE("malloc failed");
1474         return RESULT_GENERAL_ERROR;
1475     }
1476     uint32_t userInfoCount = 0;
1477     ResultCode ret = QueryAllExtUserInfoFunc(userInfoResult, MAX_USER, &userInfoCount);
1478     if (ret != RESULT_SUCCESS) {
1479         Free(userInfoResult);
1480         IAM_LOGE("QueryAllExtUserInfoFunc failed");
1481         return RESULT_GENERAL_ERROR;
1482     }
1483 
1484     for (uint32_t i = 0; i < userInfoCount; i++) {
1485         ExtUserInfo info = {};
1486         info.userId = userInfoResult[i].userId;
1487         info.userInfo.secureUid = userInfoResult[i].secUid;
1488         info.userInfo.pinSubType = static_cast<PinSubType>(userInfoResult[i].pinSubType);
1489         for (uint32_t j = 0; j < userInfoResult[i].enrollNum; j++) {
1490             EnrolledInfo enrolledInfo = {};
1491             enrolledInfo.authType = static_cast<AuthType>(userInfoResult[i].enrolledInfo[j].authType);
1492             enrolledInfo.enrolledId = userInfoResult[i].enrolledInfo[j].enrolledId;
1493             info.userInfo.enrolledInfos.push_back(enrolledInfo);
1494         }
1495         userInfos.push_back(info);
1496     }
1497 
1498     Free(userInfoResult);
1499     return RESULT_SUCCESS;
1500 }
1501 
GetEnrolledState(int32_t userId,int32_t authType,HdiEnrolledState & enrolledState)1502 int32_t UserAuthInterfaceService::GetEnrolledState(int32_t userId, int32_t authType, HdiEnrolledState &enrolledState)
1503 {
1504     IAM_LOGI("start");
1505     EnrolledStateHal *enrolledStateHal = (EnrolledStateHal *) Malloc(sizeof(EnrolledStateHal));
1506     if (enrolledStateHal == NULL) {
1507         IAM_LOGE("malloc failed");
1508         return RESULT_GENERAL_ERROR;
1509     }
1510     int32_t ret = GetEnrolledStateFunc(userId, authType, enrolledStateHal);
1511     if (ret != RESULT_SUCCESS) {
1512         Free(enrolledStateHal);
1513         IAM_LOGE("GetEnrolledState failed");
1514         return ret;
1515     }
1516     enrolledState.credentialDigest = enrolledStateHal->credentialDigest;
1517     enrolledState.credentialCount = enrolledStateHal->credentialCount;
1518 
1519     Free(enrolledStateHal);
1520     return RESULT_SUCCESS;
1521 }
1522 
CheckReuseUnlockResult(const ReuseUnlockParam & param,ReuseUnlockInfo & info)1523 int32_t UserAuthInterfaceService::CheckReuseUnlockResult(const ReuseUnlockParam& param,
1524     ReuseUnlockInfo& info)
1525 {
1526     IAM_LOGI("start reuseMode: %{public}u, reuseDuration: %{public}" PRIu64 ".", param.reuseUnlockResultMode,
1527         param.reuseUnlockResultDuration);
1528     if (param.authTypes.empty() || param.authTypes.size() > MAX_AUTH_TYPE_LEN ||
1529         param.reuseUnlockResultDuration == 0 || param.reuseUnlockResultDuration > REUSED_UNLOCK_TOKEN_PERIOD ||
1530         (param.reuseUnlockResultMode != AUTH_TYPE_RELEVANT && param.reuseUnlockResultMode != AUTH_TYPE_IRRELEVANT &&
1531         param.reuseUnlockResultMode != CALLER_IRRELEVANT_AUTH_TYPE_RELEVANT &&
1532         param.reuseUnlockResultMode != CALLER_IRRELEVANT_AUTH_TYPE_IRRELEVANT)) {
1533         IAM_LOGE("checkReuseUnlockResult bad param");
1534         return RESULT_BAD_PARAM;
1535     }
1536     ReuseUnlockParamHal paramHal = {};
1537     paramHal.userId = param.baseParam.userId;
1538     paramHal.authTrustLevel = param.baseParam.authTrustLevel;
1539     paramHal.reuseUnlockResultDuration = param.reuseUnlockResultDuration;
1540     paramHal.reuseUnlockResultMode = param.reuseUnlockResultMode;
1541     if (!param.baseParam.challenge.empty() &&
1542         memcpy_s(paramHal.challenge, CHALLENGE_LEN,
1543             param.baseParam.challenge.data(), param.baseParam.challenge.size()) != EOK) {
1544         IAM_LOGE("challenge copy failed");
1545         return RESULT_BAD_COPY;
1546     }
1547     paramHal.authTypeSize = param.authTypes.size();
1548     for (uint32_t i = 0; i < param.authTypes.size(); i++) {
1549         paramHal.authTypes[i] = static_cast<uint32_t>(param.authTypes[i]);
1550     }
1551     ReuseUnlockResult reuseResult = {};
1552     int32_t ret = CheckReuseUnlockResultFunc(&paramHal, &reuseResult);
1553     if (ret != RESULT_SUCCESS) {
1554         info.token.clear();
1555         IAM_LOGE("check reuse unlock result failed, ret:%{public}d", ret);
1556         return ret;
1557     }
1558     info.authType = reuseResult.authType;
1559     info.enrolledState.credentialDigest = reuseResult.enrolledState.credentialDigest;
1560     info.enrolledState.credentialCount = reuseResult.enrolledState.credentialCount;
1561     info.token.resize(AUTH_TOKEN_LEN);
1562     if (memcpy_s(info.token.data(), info.token.size(), reuseResult.token, AUTH_TOKEN_LEN) != EOK) {
1563         IAM_LOGE("copy authToken failed");
1564         info.token.clear();
1565         return RESULT_BAD_COPY;
1566     }
1567     IAM_LOGI("check reuse unlock result finish success");
1568     return RESULT_SUCCESS;
1569 }
1570 
SendMessage(uint64_t scheduleId,int32_t srcRole,const std::vector<uint8_t> & msg)1571 int32_t UserAuthInterfaceService::SendMessage(uint64_t scheduleId, int32_t srcRole, const std::vector<uint8_t>& msg)
1572 {
1573     static_cast<void>(scheduleId);
1574     static_cast<void>(srcRole);
1575     static_cast<void>(msg);
1576     return HDF_SUCCESS;
1577 }
1578 
RegisterMessageCallback(const sptr<IMessageCallback> & messageCallback)1579 int32_t UserAuthInterfaceService::RegisterMessageCallback(const sptr<IMessageCallback>& messageCallback)
1580 {
1581     static_cast<void>(messageCallback);
1582     return HDF_SUCCESS;
1583 }
1584 
PrepareRemoteAuth(const std::string & remoteUdid)1585 int32_t UserAuthInterfaceService::PrepareRemoteAuth(const std::string &remoteUdid)
1586 {
1587     IAM_LOGI("PrepareRemoteAuth");
1588     return RESULT_SUCCESS;
1589 }
1590 
CopyHdiScheduleInfo(const ScheduleInfoParam * in,HdiScheduleInfo * out)1591 static bool CopyHdiScheduleInfo(const ScheduleInfoParam *in, HdiScheduleInfo *out)
1592 {
1593     IAM_LOGI("CopyHdiScheduleInfo start");
1594     out->executorIndexes.clear();
1595     out->templateIds.clear();
1596     out->executorMessages.clear();
1597     out->scheduleId = in->scheduleId;
1598     out->authType = static_cast<AuthType>(in->authType);
1599     out->executorMatcher = static_cast<uint32_t>(in->executorMatcher);
1600     out->scheduleMode = static_cast<ScheduleMode>(in->scheduleMode);
1601     out->executorIndexes.push_back(in->executorIndex);
1602     out->executorMessages.resize(1);
1603     out->executorMessages[0].resize(in->executorMessages->contentSize);
1604     if (memcpy_s(out->executorMessages[0].data(), out->executorMessages[0].size(),
1605         in->executorMessages->buf, in->executorMessages->contentSize) != EOK) {
1606         IAM_LOGE("copy executorMessages failed");
1607         out->executorMessages.clear();
1608         out->executorIndexes.clear();
1609         return false;
1610     }
1611     return true;
1612 }
1613 
DestroyScheduleInfoParam(ScheduleInfoParam * result)1614 static void DestroyScheduleInfoParam(ScheduleInfoParam *result)
1615 {
1616     if (result == NULL) {
1617         return;
1618     }
1619     if (result->executorMessages != NULL) {
1620         DestoryBuffer(result->executorMessages);
1621     }
1622     Free(result);
1623 }
1624 
GetLocalScheduleFromMessage(const std::string & remoteUdid,const std::vector<uint8_t> & message,HdiScheduleInfo & scheduleInfo)1625 int32_t UserAuthInterfaceService::GetLocalScheduleFromMessage(const std::string &remoteUdid,
1626     const std::vector<uint8_t> &message, HdiScheduleInfo& scheduleInfo)
1627 {
1628     IAM_LOGI("GetLocalScheduleFromMessage start");
1629     if ((g_localUdid.empty()) || (remoteUdid.empty()) || (message.size() == 0)) {
1630         IAM_LOGE("param is invalid");
1631         return RESULT_BAD_PARAM;
1632     }
1633     Buffer *messageBuffer = CreateBufferByData(&message[0], message.size());
1634     if (!IsBufferValid(messageBuffer)) {
1635         IAM_LOGE("messageBuffer is invalid");
1636         return RESULT_NO_MEMORY;
1637     }
1638     std::lock_guard<std::mutex> lock(g_mutex);
1639     ScheduleInfoParam *scheduleParam = (ScheduleInfoParam *)Malloc(sizeof(ScheduleInfoParam));
1640     if (scheduleParam == NULL) {
1641         IAM_LOGE("schedule is null");
1642         DestoryBuffer(messageBuffer);
1643         return RESULT_GENERAL_ERROR;
1644     }
1645 
1646     int32_t funcRet = RESULT_GENERAL_ERROR;
1647     int32_t ret = RESULT_GENERAL_ERROR;
1648     Uint8Array remoteUdidArray = {};
1649     if (memcpy_s(scheduleParam->localUdid, sizeof(scheduleParam->localUdid), g_localUdid.c_str(),
1650         g_localUdid.length()) != EOK) {
1651         IAM_LOGE("localUdid copy failed");
1652         goto FAIL;
1653     }
1654 
1655     if (memcpy_s(scheduleParam->remoteUdid, sizeof(scheduleParam->remoteUdid), remoteUdid.c_str(),
1656         remoteUdid.length()) != EOK) {
1657         IAM_LOGE("remoteUdid copy failed");
1658         goto FAIL;
1659     }
1660 
1661     remoteUdidArray = { scheduleParam->remoteUdid, sizeof(scheduleParam->remoteUdid) };
1662 
1663     ret = GenerateScheduleFunc(messageBuffer, remoteUdidArray, scheduleParam);
1664     if (ret != RESULT_SUCCESS) {
1665         IAM_LOGE("GenerateScheduleFunc failed");
1666         goto FAIL;
1667     }
1668     if (!CopyHdiScheduleInfo(scheduleParam, &scheduleInfo)) {
1669         IAM_LOGE("copy schedule info failed");
1670         goto FAIL;
1671     }
1672 
1673     funcRet = RESULT_SUCCESS;
1674 FAIL:
1675     DestoryBuffer(messageBuffer);
1676     DestroyScheduleInfoParam(scheduleParam);
1677     return funcRet;
1678 }
1679 
DestroyExecutorInfo(void * data)1680 static void DestroyExecutorInfo(void *data)
1681 {
1682     if (data == nullptr) {
1683         IAM_LOGE("data is null");
1684         return;
1685     }
1686     Free(data);
1687 }
1688 
GetSignedExecutorInfo(const std::vector<int32_t> & authTypes,int32_t executorRole,const std::string & remoteUdid,std::vector<uint8_t> & signedExecutorInfo)1689 int32_t UserAuthInterfaceService::GetSignedExecutorInfo(const std::vector<int32_t>& authTypes, int32_t executorRole,
1690     const std::string& remoteUdid, std::vector<uint8_t>& signedExecutorInfo)
1691 {
1692     IAM_LOGI("GetSignedExecutorInfo start");
1693     if ((g_localUdid.empty()) || (remoteUdid.empty()) || (authTypes.size() == 0)) {
1694         IAM_LOGE("param is invalid");
1695         return RESULT_BAD_PARAM;
1696     }
1697     ResultCode result = RESULT_GENERAL_ERROR;
1698     LinkedList *linkedList = CreateLinkedList(DestroyExecutorInfo);
1699     if (linkedList == NULL) {
1700         IAM_LOGE("create linkedList failed");
1701         return result;
1702     }
1703     std::lock_guard<std::mutex> lock(g_mutex);
1704     for (uint32_t i = 0; i < authTypes.size(); i++) {
1705         result = GetExecutorInfoLinkedList(authTypes[i], executorRole, linkedList);
1706         if (result != RESULT_SUCCESS) {
1707             IAM_LOGE("GetExecutorInfo failed");
1708             DestroyLinkedList(linkedList);
1709             return result;
1710         }
1711     }
1712     uint8_t remoteUdidData[UDID_LEN] = {};
1713     if (memcpy_s(remoteUdidData, UDID_LEN, remoteUdid.c_str(), remoteUdid.length()) != EOK) {
1714         IAM_LOGE("remoteUdidData copy failed");
1715         DestroyLinkedList(linkedList);
1716         return RESULT_BAD_COPY;
1717     }
1718 
1719     Uint8Array remoteUdidArray = { remoteUdidData, sizeof(remoteUdidData) };
1720     Buffer *signInfo = GetSignExecutorInfoFunc(remoteUdidArray, linkedList);
1721     if (!IsBufferValid(signInfo)) {
1722         IAM_LOGE("signInfo is invalid");
1723         DestroyLinkedList(linkedList);
1724         return RESULT_NO_MEMORY;
1725     }
1726     signedExecutorInfo.resize(signInfo->contentSize);
1727     if (memcpy_s(&signedExecutorInfo[0], signedExecutorInfo.size(), signInfo->buf, signInfo->contentSize) != EOK) {
1728         IAM_LOGE("sign copy failed");
1729         result = RESULT_BAD_COPY;
1730     }
1731     DestoryBuffer(signInfo);
1732     DestroyLinkedList(linkedList);
1733     return result;
1734 }
1735 
CopyHdiAuthResultInfo(const AuthResultParam * in,HdiAuthResultInfo * out,const std::vector<uint8_t> & message)1736 static bool CopyHdiAuthResultInfo(const AuthResultParam *in, HdiAuthResultInfo *out,
1737     const std::vector<uint8_t>& message)
1738 {
1739     IAM_LOGI("CopyHdiAuthResultInfo start");
1740     out->token.clear();
1741     out->rootSecret.clear();
1742     out->remoteAuthResultMsg.clear();
1743     out->result = in->result;
1744     out->lockoutDuration = in->lockoutDuration;
1745     out->remainAttempts = in->remainAttempts;
1746     out->userId = in->userId;
1747 
1748     out->token.resize(in->token->contentSize);
1749     if (memcpy_s(out->token.data(), out->token.size(), in->token->buf, in->token->contentSize) != EOK) {
1750         IAM_LOGE("copy token failed");
1751         return false;
1752     }
1753 
1754     out->remoteAuthResultMsg.resize(message.size());
1755     if (memcpy_s(out->remoteAuthResultMsg.data(), out->remoteAuthResultMsg.size(),
1756         message.data(), message.size()) != EOK) {
1757         IAM_LOGE("copy remoteAuthResultMsg failed");
1758         return false;
1759     }
1760     return true;
1761 }
1762 
DestroyAuthResultParam(AuthResultParam * result)1763 static void DestroyAuthResultParam(AuthResultParam *result)
1764 {
1765     if (result == NULL) {
1766         return;
1767     }
1768     if (result->token != NULL) {
1769         DestoryBuffer(result->token);
1770     }
1771     if (result->remoteAuthResultMsg != NULL) {
1772         DestoryBuffer(result->remoteAuthResultMsg);
1773     }
1774     Free(result);
1775 }
1776 
GetAuthResultFromMessage(const std::string & remoteUdid,const std::vector<uint8_t> & message,HdiAuthResultInfo & authResultInfo)1777 int32_t UserAuthInterfaceService::GetAuthResultFromMessage(const std::string& remoteUdid,
1778     const std::vector<uint8_t>& message, HdiAuthResultInfo& authResultInfo)
1779 {
1780     IAM_LOGI("GetAuthResultFromMessage start");
1781     if ((g_localUdid.empty()) || (remoteUdid.empty()) || (message.size() == 0)) {
1782         IAM_LOGE("param is invalid");
1783         return RESULT_BAD_PARAM;
1784     }
1785     Buffer *messageBuffer = CreateBufferByData(&message[0], message.size());
1786     if (!IsBufferValid(messageBuffer)) {
1787         IAM_LOGE("messageBuffer is invalid");
1788         return RESULT_NO_MEMORY;
1789     }
1790     std::lock_guard<std::mutex> lock(g_mutex);
1791     AuthResultParam *authResultParam = (AuthResultParam *)Malloc(sizeof(AuthResultParam));
1792     if (authResultParam == NULL) {
1793         IAM_LOGE("authResultParam is null");
1794         DestoryBuffer(messageBuffer);
1795         return RESULT_GENERAL_ERROR;
1796     }
1797 
1798     int32_t funcRet = RESULT_GENERAL_ERROR;
1799     int32_t ret = RESULT_GENERAL_ERROR;
1800     if (memcpy_s(authResultParam->localUdid, sizeof(authResultParam->localUdid), g_localUdid.c_str(),
1801         g_localUdid.length()) != EOK) {
1802         IAM_LOGE("localUdid copy failed");
1803         goto FAIL;
1804     }
1805 
1806     if (memcpy_s(authResultParam->remoteUdid, sizeof(authResultParam->remoteUdid), remoteUdid.c_str(),
1807         remoteUdid.length()) != EOK) {
1808         IAM_LOGE("remoteUdid copy failed");
1809         goto FAIL;
1810     }
1811 
1812     ret = GenerateAuthResultFunc(messageBuffer, authResultParam);
1813     if (ret != RESULT_SUCCESS) {
1814         IAM_LOGE("GenerateAuthResultFunc failed");
1815         goto FAIL;
1816     }
1817     if (!CopyHdiAuthResultInfo(authResultParam, &authResultInfo, message)) {
1818         IAM_LOGE("copy authResult info failed");
1819         goto FAIL;
1820     }
1821     ret = CreateExecutorCommand(authResultInfo.userId, authResultInfo);
1822     if (ret != RESULT_SUCCESS) {
1823         IAM_LOGE("CreateExecutorCommand failed");
1824         goto FAIL;
1825     }
1826 
1827     funcRet = RESULT_SUCCESS;
1828 FAIL:
1829     DestoryBuffer(messageBuffer);
1830     DestroyAuthResultParam(authResultParam);
1831     return ret;
1832 }
1833 
CopyGlobalConfigParam(const HdiGlobalConfigParam & param,GlobalConfigParamHal & paramHal)1834 static int32_t CopyGlobalConfigParam(const HdiGlobalConfigParam &param, GlobalConfigParamHal &paramHal)
1835 {
1836     switch (param.type) {
1837         case PIN_EXPIRED_PERIOD:
1838             paramHal.value.pinExpiredPeriod = NO_CHECK_PIN_EXPIRED_PERIOD;
1839             if (param.value.pinExpiredPeriod > 0) {
1840                 paramHal.value.pinExpiredPeriod = param.value.pinExpiredPeriod;
1841             }
1842             break;
1843         case ENABLE_STATUS:
1844             paramHal.value.enableStatus = param.value.enableStatus;
1845             break;
1846         default:
1847             IAM_LOGE("bad global config type");
1848             return RESULT_BAD_PARAM;
1849     }
1850     paramHal.type = static_cast<GlobalConfigTypeHal>(param.type);
1851 
1852     for (uint32_t i = 0; i < param.userIds.size(); i++) {
1853         paramHal.userIds[i] = param.userIds[i];
1854     }
1855     paramHal.userIdNum = param.userIds.size();
1856     for (uint32_t i = 0; i < param.authTypes.size(); i++) {
1857         paramHal.authTypes[i] = static_cast<uint32_t>(param.authTypes[i]);
1858     }
1859     paramHal.authTypeNum = param.authTypes.size();
1860     return RESULT_SUCCESS;
1861 }
1862 
SetGlobalConfigParam(const HdiGlobalConfigParam & param)1863 int32_t UserAuthInterfaceService::SetGlobalConfigParam(const HdiGlobalConfigParam &param)
1864 {
1865     IAM_LOGI("start, global config type is %{public}d, userIds size %{public}zu, authTypes size %{public}zu",
1866         param.type, param.userIds.size(), param.authTypes.size());
1867     if (param.authTypes.size() > MAX_AUTH_TYPE_LEN || param.authTypes.size() == 0 ||
1868         param.userIds.size() > MAX_USER) {
1869         IAM_LOGE("SetGlobalConfigParam bad param");
1870         return RESULT_BAD_PARAM;
1871     }
1872     GlobalConfigParamHal paramHal = {};
1873     int32_t ret = CopyGlobalConfigParam(param, paramHal);
1874     if (ret != RESULT_SUCCESS) {
1875         IAM_LOGE("CopyGlobalConfigParam failed");
1876         return ret;
1877     }
1878 
1879     ret = SetGlobalConfigParamFunc(&paramHal);
1880     if (ret != RESULT_SUCCESS) {
1881         IAM_LOGE("SetGlobalConfigParamFunc failed");
1882     }
1883     return ret;
1884 }
1885 
GetCredentialById(uint64_t credentialId,HdiCredentialInfo & info)1886 int32_t UserAuthInterfaceService::GetCredentialById(uint64_t credentialId, HdiCredentialInfo &info)
1887 {
1888     IAM_LOGI("start");
1889     std::lock_guard<std::mutex> lock(g_mutex);
1890     LinkedList *credList = nullptr;
1891     int32_t ret = QueryCredentialByIdFunc(credentialId, &credList);
1892     if (ret != RESULT_SUCCESS || credList == NULL) {
1893         IAM_LOGE("query credential failed");
1894         return RESULT_GENERAL_ERROR;
1895     }
1896     if (credList->head == NULL || credList->head->data == NULL) {
1897         IAM_LOGE("credential is null");
1898         DestroyLinkedList(credList);
1899         return RESULT_NOT_ENROLLED;
1900     }
1901     auto credentialHal = static_cast<CredentialInfoHal *>(credList->head->data);
1902     CopyCredentialInfo(*credentialHal, info);
1903     DestroyLinkedList(credList);
1904     return RESULT_SUCCESS;
1905 }
1906 
CopyAuthTokenPlainHal(const UserAuthTokenPlainHal & tokenIn,HdiUserAuthTokenPlain & tokenOut)1907 static bool CopyAuthTokenPlainHal(const UserAuthTokenPlainHal &tokenIn, HdiUserAuthTokenPlain &tokenOut)
1908 {
1909     tokenOut.userId = tokenIn.tokenDataToEncrypt.userId;
1910     tokenOut.challenge.resize(CHALLENGE_LEN);
1911     if (tokenOut.challenge.size() != 0 && memcpy_s(tokenOut.challenge.data(), CHALLENGE_LEN,
1912         tokenIn.tokenDataPlain.challenge, CHALLENGE_LEN) != EOK) {
1913         IAM_LOGE("copy challenge fail");
1914         return RESULT_BAD_COPY;
1915     }
1916     uint64_t currentTime = GetSystemTime();
1917     if (currentTime < tokenIn.tokenDataPlain.time) {
1918         LOG_ERROR("bad time, current:%" PRIu64 ", tokenTime:%" PRIu64, currentTime, tokenIn.tokenDataPlain.time);
1919         return RESULT_GENERAL_ERROR;
1920     }
1921     tokenOut.timeInterval = currentTime - tokenIn.tokenDataPlain.time;
1922     tokenOut.authTrustLevel = tokenIn.tokenDataPlain.authTrustLevel;
1923     tokenOut.authType = tokenIn.tokenDataPlain.authType;
1924     tokenOut.authMode = tokenIn.tokenDataPlain.authMode;
1925     tokenOut.securityLevel = tokenIn.tokenDataPlain.securityLevel;
1926     tokenOut.tokenType = tokenIn.tokenDataPlain.tokenType;
1927     tokenOut.secureUid = tokenIn.tokenDataToEncrypt.secureUid;
1928     tokenOut.enrolledId = tokenIn.tokenDataToEncrypt.enrolledId;
1929     tokenOut.credentialId = tokenIn.tokenDataToEncrypt.credentialId;
1930     tokenOut.collectorUdid.resize(UDID_LEN);
1931     if (tokenOut.collectorUdid.length() != 0 && memcpy_s(tokenOut.collectorUdid.data(), UDID_LEN,
1932         tokenIn.tokenDataToEncrypt.collectorUdid, UDID_LEN) != EOK) {
1933         IAM_LOGE("copy collectorUdid fail");
1934         return RESULT_BAD_COPY;
1935     }
1936     tokenOut.verifierUdid.resize(UDID_LEN);
1937     if (tokenOut.verifierUdid.length() != 0 && memcpy_s(tokenOut.verifierUdid.data(), UDID_LEN,
1938         tokenIn.tokenDataToEncrypt.verifierUdid, UDID_LEN) != EOK) {
1939         IAM_LOGE("copy verifierUdid fail");
1940         return RESULT_BAD_COPY;
1941     }
1942     return RESULT_SUCCESS;
1943 }
1944 
GetRootSecret(const UserAuthTokenPlainHal & token,std::vector<uint8_t> & rootSecret)1945 static void GetRootSecret(const UserAuthTokenPlainHal &token, std::vector<uint8_t> &rootSecret)
1946 {
1947     rootSecret.resize(0);
1948     if (CheckSessionTimeout() != RESULT_SUCCESS) {
1949         LOG_ERROR("CheckSessionTimeout fail");
1950         return;
1951     }
1952     if (!IsValidTokenTime(token.tokenDataPlain.time)) {
1953         LOG_ERROR("check token time failed, token is invalid");
1954         return;
1955     }
1956     if (CheckChallenge(token.tokenDataPlain.challenge, CHALLENGE_LEN) != RESULT_SUCCESS) {
1957         LOG_ERROR("check challenge failed, token is invalid");
1958         return;
1959     }
1960     if (token.tokenDataPlain.authType != PIN_AUTH) {
1961         LOG_ERROR("token authType is not pin");
1962         return;
1963     }
1964 
1965     Buffer *rootSecretBuffer = GetCurRootSecret(token.tokenDataToEncrypt.userId);
1966     if (!IsBufferValid(rootSecretBuffer)) {
1967         IAM_LOGE("get curRootSecret failed");
1968         return;
1969     }
1970     rootSecret.resize(ROOT_SECRET_LEN);
1971     if (memcpy_s(rootSecret.data(), rootSecret.size(), rootSecretBuffer->buf, rootSecretBuffer->contentSize) != EOK) {
1972         IAM_LOGE("rootSecret copy failed");
1973         (void)memset_s(rootSecret.data(), rootSecret.size(), 0, rootSecret.size());
1974         rootSecret.clear();
1975     }
1976 
1977     return;
1978 }
1979 
VerifyAuthToken(const std::vector<uint8_t> & tokenIn,uint64_t allowableDuration,HdiUserAuthTokenPlain & tokenPlainOut,std::vector<uint8_t> & rootSecret)1980 int32_t UserAuthInterfaceService::VerifyAuthToken(const std::vector<uint8_t> &tokenIn, uint64_t allowableDuration,
1981     HdiUserAuthTokenPlain &tokenPlainOut, std::vector<uint8_t> &rootSecret)
1982 {
1983     IAM_LOGI("start, allowableDuration:%{public}" PRIu64, allowableDuration);
1984     if (tokenIn.size() != sizeof(UserAuthTokenHal) || tokenIn.data() == NULL ||
1985         allowableDuration > MAX_TOKEN_ALLOWABLE_DURATION) {
1986         IAM_LOGE("VerifyAuthToken bad param");
1987         return RESULT_BAD_PARAM;
1988     }
1989     UserAuthTokenPlainHal tokenPlain = {};
1990     int32_t result = UserAuthTokenVerify((UserAuthTokenHal *)(tokenIn.data()), allowableDuration, &tokenPlain);
1991     if (result != RESULT_SUCCESS) {
1992         IAM_LOGE("UserAuthTokenVerify failed");
1993         return ConvertResultCode(result);
1994     }
1995     GetRootSecret(tokenPlain, rootSecret);
1996     result = CopyAuthTokenPlainHal(tokenPlain, tokenPlainOut);
1997     if (result != RESULT_SUCCESS) {
1998         IAM_LOGE("CopyAuthTokenPlainHal failed");
1999         return result;
2000     }
2001     return result;
2002 }
2003 
UpdateAbandonResult(int32_t userId,const std::vector<uint8_t> & scheduleResult,std::vector<HdiCredentialInfo> & infos)2004 int32_t UserAuthInterfaceService::UpdateAbandonResult(int32_t userId, const std::vector<uint8_t> &scheduleResult,
2005     std::vector<HdiCredentialInfo> &infos)
2006 {
2007     IAM_LOGI("start");
2008     if (scheduleResult.size() == 0) {
2009         IAM_LOGE("enrollToken is invalid");
2010         return RESULT_BAD_PARAM;
2011     }
2012     Buffer *scheduleResultBuffer = CreateBufferByData(&scheduleResult[0], scheduleResult.size());
2013     if (scheduleResultBuffer == nullptr) {
2014         IAM_LOGE("scheduleTokenBuffer is null");
2015         return RESULT_NO_MEMORY;
2016     }
2017     std::lock_guard<std::mutex> lock(g_mutex);
2018     bool isDelete = false;
2019     CredentialInfoHal credentialInfo = {};
2020     int32_t ret = UpdateAbandonResultFunc(userId, scheduleResultBuffer, &isDelete, &credentialInfo);
2021     if (ret != RESULT_SUCCESS) {
2022         IAM_LOGE("UpdateAbandonResultFunc fail");
2023         goto EXIT;
2024     }
2025 
2026     if (isDelete) {
2027         HdiCredentialInfo hdiCredentialInfo = {};
2028         CopyCredentialInfo(credentialInfo, hdiCredentialInfo);
2029         infos.push_back(hdiCredentialInfo);
2030     }
2031 
2032 EXIT:
2033     DestoryBuffer(scheduleResultBuffer);
2034     BreakOffCoauthSchedule();
2035     return ret;
2036 }
2037 
ClearUnavailableCredential(const std::vector<int32_t> & userIds,std::vector<HdiCredentialInfo> & infos)2038 int32_t UserAuthInterfaceService::ClearUnavailableCredential(const std::vector<int32_t> &userIds,
2039     std::vector<HdiCredentialInfo> &infos)
2040 {
2041     IAM_LOGI("start");
2042     std::lock_guard<std::mutex> lock(g_mutex);
2043     for (auto &iter : userIds) {
2044         CredentialInfoHal credentialInfo = {};
2045         int32_t ret = ClearUnavailableCredentialFunc(iter, &credentialInfo);
2046         if (ret != RESULT_SUCCESS) {
2047             IAM_LOGE("ClearUnavailableCredentialFunc fail");
2048             continue;
2049         }
2050 
2051         HdiCredentialInfo hdiCredentialInfo = {};
2052         CopyCredentialInfo(credentialInfo, hdiCredentialInfo);
2053         infos.push_back(hdiCredentialInfo);
2054     }
2055 
2056     return RESULT_SUCCESS;
2057 }
2058 } // Userauth
2059 } // HDI
2060 } // OHOS