• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2022 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "user_idm_service.h"
17 
18 #include "string_ex.h"
19 #include "accesstoken_kit.h"
20 
21 #include "context_helper.h"
22 #include "context_pool.h"
23 #include "hdi_wrapper.h"
24 #include "iam_check.h"
25 #include "iam_logger.h"
26 #include "iam_para2str.h"
27 #include "iam_defines.h"
28 #include "iam_time.h"
29 #include "ipc_common.h"
30 #include "ipc_skeleton.h"
31 #include "iam_common_defines.h"
32 #include "publish_event_adapter.h"
33 #include "resource_node_pool.h"
34 #include "resource_node_utils.h"
35 #include "system_param_manager.h"
36 #include "user_idm_callback_proxy.h"
37 #include "user_idm_database.h"
38 #include "user_idm_session_controller.h"
39 
40 #define LOG_LABEL UserIam::Common::LABEL_USER_AUTH_SA
41 
42 namespace OHOS {
43 namespace UserIam {
44 namespace UserAuth {
45 REGISTER_SYSTEM_ABILITY_BY_ID(UserIdmService, SUBSYS_USERIAM_SYS_ABILITY_USERIDM, true);
46 constexpr int32_t USERIAM_IPC_THREAD_NUM = 4;
47 
UserIdmService(int32_t systemAbilityId,bool runOnCreate)48 UserIdmService::UserIdmService(int32_t systemAbilityId, bool runOnCreate) : SystemAbility(systemAbilityId, runOnCreate)
49 {
50 }
51 
OnStart()52 void UserIdmService::OnStart()
53 {
54     IAM_LOGI("start service");
55     IPCSkeleton::SetMaxWorkThreadNum(USERIAM_IPC_THREAD_NUM);
56     if (!Publish(this)) {
57         IAM_LOGE("failed to publish service");
58     }
59 }
60 
OnStop()61 void UserIdmService::OnStop()
62 {
63     IAM_LOGI("stop service");
64 }
65 
OpenSession(int32_t userId,std::vector<uint8_t> & challenge)66 int32_t UserIdmService::OpenSession(int32_t userId, std::vector<uint8_t> &challenge)
67 {
68     IAM_LOGI("start");
69     if (!IpcCommon::CheckPermission(*this, MANAGE_USER_IDM_PERMISSION)) {
70         IAM_LOGE("failed to check permission");
71         return CHECK_PERMISSION_FAILED;
72     }
73 
74     auto contextList = ContextPool::Instance().Select(CONTEXT_ENROLL);
75     for (const auto &context : contextList) {
76         if (auto ctx = context.lock(); ctx != nullptr) {
77             IAM_LOGE("force stop the old context ****%{public}hx", static_cast<uint16_t>(ctx->GetContextId()));
78             ctx->Stop();
79             ContextPool::Instance().Delete(ctx->GetContextId());
80         }
81     }
82 
83     if (!UserIdmSessionController::Instance().OpenSession(userId, challenge)) {
84         IAM_LOGE("failed to open session");
85         return GENERAL_ERROR;
86     }
87 
88     return SUCCESS;
89 }
90 
CloseSession(int32_t userId)91 void UserIdmService::CloseSession(int32_t userId)
92 {
93     IAM_LOGI("start");
94     if (!IpcCommon::CheckPermission(*this, MANAGE_USER_IDM_PERMISSION)) {
95         IAM_LOGE("failed to check permission");
96         return;
97     }
98 
99     if (!UserIdmSessionController::Instance().CloseSession(userId)) {
100         IAM_LOGE("failed to get close session");
101     }
102 }
103 
GetCredentialInfoInner(int32_t userId,AuthType authType,std::vector<CredentialInfo> & credInfoList)104 int32_t UserIdmService::GetCredentialInfoInner(int32_t userId, AuthType authType,
105     std::vector<CredentialInfo> &credInfoList)
106 {
107     IAM_LOGI("start");
108     if (!IpcCommon::CheckPermission(*this, USE_USER_IDM_PERMISSION)) {
109         IAM_LOGE("failed to check permission");
110         return CHECK_PERMISSION_FAILED;
111     }
112     auto credInfos = UserIdmDatabase::Instance().GetCredentialInfo(userId, authType);
113     if (credInfos.empty()) {
114         IAM_LOGE("no cred enrolled");
115         return NOT_ENROLLED;
116     }
117     for (const auto &credInfo : credInfos) {
118         if (credInfo == nullptr) {
119             IAM_LOGE("credInfo is nullptr");
120             return GENERAL_ERROR;
121         }
122         CredentialInfo info = {};
123         info.credentialId = credInfo->GetCredentialId();
124         info.templateId = credInfo->GetTemplateId();
125         info.authType = credInfo->GetAuthType();
126         if (info.authType == PIN) {
127             auto userInfo = UserIdmDatabase::Instance().GetSecUserInfo(userId);
128             if (userInfo == nullptr) {
129                 IAM_LOGE("failed to get userInfo");
130                 return GENERAL_ERROR;
131             }
132             info.pinType = userInfo->GetPinSubType();
133         }
134         credInfoList.push_back(info);
135     }
136     return SUCCESS;
137 }
138 
GetCredentialInfo(int32_t userId,AuthType authType,const sptr<IdmGetCredInfoCallbackInterface> & callback)139 int32_t UserIdmService::GetCredentialInfo(int32_t userId, AuthType authType,
140     const sptr<IdmGetCredInfoCallbackInterface> &callback)
141 {
142     if (callback == nullptr) {
143         IAM_LOGE("callback is nullptr");
144         return INVALID_PARAMETERS;
145     }
146 
147     std::vector<CredentialInfo> credInfoList;
148     int32_t ret = GetCredentialInfoInner(userId, authType, credInfoList);
149     if (ret != SUCCESS) {
150         IAM_LOGE("GetCredentialInfoInner fail, ret: %{public}d", ret);
151         credInfoList.clear();
152     }
153     callback->OnCredentialInfos(credInfoList);
154 
155     return ret;
156 }
157 
GetSecInfoInner(int32_t userId,SecUserInfo & secUserInfo)158 int32_t UserIdmService::GetSecInfoInner(int32_t userId, SecUserInfo &secUserInfo)
159 {
160     IAM_LOGI("start");
161     if (!IpcCommon::CheckPermission(*this, USE_USER_IDM_PERMISSION)) {
162         IAM_LOGE("failed to check permission");
163         return CHECK_PERMISSION_FAILED;
164     }
165     auto userInfos = UserIdmDatabase::Instance().GetSecUserInfo(userId);
166     if (userInfos == nullptr) {
167         IAM_LOGE("current userid %{public}d is not existed", userId);
168         return INVALID_PARAMETERS;
169     }
170     std::vector<std::shared_ptr<EnrolledInfoInterface>> enrolledInfos = userInfos->GetEnrolledInfo();
171     for (const auto &enrolledInfo : enrolledInfos) {
172         if (enrolledInfo == nullptr) {
173             IAM_LOGE("enrolledInfo is nullptr");
174             return GENERAL_ERROR;
175         }
176         EnrolledInfo info = {enrolledInfo->GetAuthType(), enrolledInfo->GetEnrolledId()};
177         secUserInfo.enrolledInfo.push_back(info);
178     }
179     secUserInfo.secureUid = userInfos->GetSecUserId();
180     return SUCCESS;
181 }
182 
GetSecInfo(int32_t userId,const sptr<IdmGetSecureUserInfoCallbackInterface> & callback)183 int32_t UserIdmService::GetSecInfo(int32_t userId, const sptr<IdmGetSecureUserInfoCallbackInterface> &callback)
184 {
185     if (callback == nullptr) {
186         IAM_LOGE("callback is nullptr");
187         return INVALID_PARAMETERS;
188     }
189 
190     SecUserInfo secUserInfo = {};
191     int32_t ret = GetSecInfoInner(userId, secUserInfo);
192     if (ret != SUCCESS) {
193         IAM_LOGE("GetSecInfoInner fail, ret: %{public}d", ret);
194         secUserInfo.secureUid = 0;
195         secUserInfo.enrolledInfo.clear();
196     }
197     callback->OnSecureUserInfo(secUserInfo);
198 
199     return ret;
200 }
201 
CheckEnrollPermissionAndEnableStatus(const std::shared_ptr<ContextCallback> & contextCallback,AuthType authType)202 bool UserIdmService::CheckEnrollPermissionAndEnableStatus(
203     const std::shared_ptr<ContextCallback> &contextCallback, AuthType authType)
204 {
205     Attributes extraInfo;
206     if (!IpcCommon::CheckPermission(*this, MANAGE_USER_IDM_PERMISSION)) {
207         IAM_LOGE("failed to check permission");
208         contextCallback->OnResult(CHECK_PERMISSION_FAILED, extraInfo);
209         return false;
210     }
211 
212     if (!SystemParamManager::GetInstance().IsAuthTypeEnable(authType)) {
213         IAM_LOGE("authType not support");
214         contextCallback->OnResult(TYPE_NOT_SUPPORT, extraInfo);
215         return false;
216     }
217     return true;
218 }
219 
AddCredential(int32_t userId,const CredentialPara & credPara,const sptr<IdmCallbackInterface> & callback,bool isUpdate)220 void UserIdmService::AddCredential(int32_t userId, const CredentialPara &credPara,
221     const sptr<IdmCallbackInterface> &callback, bool isUpdate)
222 {
223     IF_FALSE_LOGE_AND_RETURN(callback != nullptr);
224 
225     Attributes extraInfo;
226     auto contextCallback = ContextCallback::NewInstance(callback,
227         isUpdate ? TRACE_UPDATE_CREDENTIAL : TRACE_ADD_CREDENTIAL);
228     if (contextCallback == nullptr) {
229         IAM_LOGE("failed to construct context callback");
230         callback->OnResult(GENERAL_ERROR, extraInfo);
231         return;
232     }
233     bool isBundleName = false;
234     std::string callerName = "";
235     static_cast<void>(IpcCommon::GetCallerName(*this, isBundleName, callerName));
236     contextCallback->SetTraceCallerName(callerName);
237     contextCallback->SetTraceUserId(userId);
238     contextCallback->SetTraceAuthType(credPara.authType);
239 
240     if (!CheckEnrollPermissionAndEnableStatus(contextCallback, credPara.authType)) {
241         IAM_LOGE("CheckEnrollPermissionAndEnableStatus fail");
242         return;
243     }
244 
245     std::lock_guard<std::mutex> lock(mutex_);
246     CancelCurrentEnrollIfExist();
247     Enrollment::EnrollmentPara para = {};
248     para.authType = credPara.authType;
249     para.userId = userId;
250     para.pinType = credPara.pinType;
251     para.tokenId = IpcCommon::GetAccessTokenId(*this);
252     para.token = credPara.token;
253     para.isUpdate = isUpdate;
254     para.sdkVersion = INNER_API_VERSION_10000;
255     if (isBundleName) {
256         para.callerName = callerName;
257     }
258     auto context = ContextFactory::CreateEnrollContext(para, contextCallback);
259     if (context == nullptr || !ContextPool::Instance().Insert(context)) {
260         IAM_LOGE("failed to insert context");
261         contextCallback->OnResult(GENERAL_ERROR, extraInfo);
262         return;
263     }
264     contextCallback->SetTraceRequestContextId(context->GetContextId());
265     auto cleaner = ContextHelper::Cleaner(context);
266     contextCallback->SetCleaner(cleaner);
267 
268     if (!context->Start()) {
269         IAM_LOGE("failed to start enroll");
270         contextCallback->OnResult(context->GetLatestError(), extraInfo);
271     }
272 }
273 
UpdateCredential(int32_t userId,const CredentialPara & credPara,const sptr<IdmCallbackInterface> & callback)274 void UserIdmService::UpdateCredential(int32_t userId, const CredentialPara &credPara,
275     const sptr<IdmCallbackInterface> &callback)
276 {
277     if (callback == nullptr) {
278         IAM_LOGE("callback is nullptr");
279         return;
280     }
281 
282     auto credInfos = UserIdmDatabase::Instance().GetCredentialInfo(userId, credPara.authType);
283     if (credInfos.empty()) {
284         IAM_LOGE("current userid %{public}d has no credential for type %{public}u", userId, credPara.authType);
285         Attributes extraInfo;
286         callback->OnResult(NOT_ENROLLED, extraInfo);
287         return;
288     }
289 
290     AddCredential(userId, credPara, callback, true);
291 }
292 
Cancel(int32_t userId)293 int32_t UserIdmService::Cancel(int32_t userId)
294 {
295     if (!IpcCommon::CheckPermission(*this, MANAGE_USER_IDM_PERMISSION)) {
296         IAM_LOGE("failed to check permission");
297         return CHECK_PERMISSION_FAILED;
298     }
299     if (!UserIdmSessionController::Instance().IsSessionOpened(userId)) {
300         IAM_LOGE("both user id and challenge are invalid");
301         return GENERAL_ERROR;
302     }
303 
304     std::lock_guard<std::mutex> lock(mutex_);
305     return CancelCurrentEnroll();
306 }
307 
CancelCurrentEnrollIfExist()308 void UserIdmService::CancelCurrentEnrollIfExist()
309 {
310     if (ContextPool::Instance().Select(CONTEXT_ENROLL).size() == 0) {
311         return;
312     }
313 
314     IAM_LOGI("cancel current enroll due to new add credential request or delete");
315     CancelCurrentEnroll();
316 }
317 
CancelCurrentEnroll()318 int32_t UserIdmService::CancelCurrentEnroll()
319 {
320     IAM_LOGD("start");
321     auto contextList = ContextPool::Instance().Select(CONTEXT_ENROLL);
322     int32_t ret = GENERAL_ERROR;
323     for (const auto &context : contextList) {
324         if (auto ctx = context.lock(); ctx != nullptr) {
325             IAM_LOGE("stop the old context %{public}s", GET_MASKED_STRING(ctx->GetContextId()).c_str());
326             ctx->Stop();
327             ContextPool::Instance().Delete(ctx->GetContextId());
328             ret = SUCCESS;
329         }
330     }
331     IAM_LOGI("result %{public}d", ret);
332     return ret;
333 }
334 
EnforceDelUser(int32_t userId,const sptr<IdmCallbackInterface> & callback)335 int32_t UserIdmService::EnforceDelUser(int32_t userId, const sptr<IdmCallbackInterface> &callback)
336 {
337     IAM_LOGI("to delete userid: %{public}d", userId);
338     IF_FALSE_LOGE_AND_RETURN_VAL(callback != nullptr, INVALID_PARAMETERS);
339 
340     Attributes extraInfo;
341     auto contextCallback = ContextCallback::NewInstance(callback, TRACE_ENFORCE_DELETE_USER);
342     if (contextCallback == nullptr) {
343         IAM_LOGE("failed to construct context callback");
344         callback->OnResult(GENERAL_ERROR, extraInfo);
345         return GENERAL_ERROR;
346     }
347     bool isBundleName = false;
348     std::string callerName = "";
349     static_cast<void>(IpcCommon::GetCallerName(*this, isBundleName, callerName));
350     contextCallback->SetTraceUserId(userId);
351 
352     if (!IpcCommon::CheckPermission(*this, ENFORCE_USER_IDM)) {
353         IAM_LOGE("failed to check permission");
354         contextCallback->OnResult(CHECK_PERMISSION_FAILED, extraInfo);
355         return CHECK_PERMISSION_FAILED;
356     }
357 
358     std::lock_guard<std::mutex> lock(mutex_);
359     CancelCurrentEnrollIfExist();
360 
361     auto userInfo = UserIdmDatabase::Instance().GetSecUserInfo(userId);
362     if (userInfo == nullptr) {
363         IAM_LOGE("current userid %{public}d is not existed", userId);
364         contextCallback->OnResult(INVALID_PARAMETERS, extraInfo);
365         return INVALID_PARAMETERS;
366     }
367     int32_t ret = EnforceDelUserInner(userId, contextCallback, "EnforceDeleteUser");
368     if (ret != SUCCESS) {
369         IAM_LOGE("failed to enforce delete user");
370         static_cast<void>(extraInfo.SetUint64Value(Attributes::ATTR_CREDENTIAL_ID, 0));
371         contextCallback->OnResult(ret, extraInfo);
372         return ret;
373     }
374 
375     IAM_LOGI("delete user success");
376     contextCallback->OnResult(SUCCESS, extraInfo);
377     return SUCCESS;
378 }
379 
DelUser(int32_t userId,const std::vector<uint8_t> authToken,const sptr<IdmCallbackInterface> & callback)380 void UserIdmService::DelUser(int32_t userId, const std::vector<uint8_t> authToken,
381     const sptr<IdmCallbackInterface> &callback)
382 {
383     IF_FALSE_LOGE_AND_RETURN(callback != nullptr);
384 
385     Attributes extraInfo;
386     auto contextCallback = ContextCallback::NewInstance(callback, TRACE_DELETE_USER);
387     if (contextCallback == nullptr) {
388         IAM_LOGE("failed to construct context callback");
389         callback->OnResult(GENERAL_ERROR, extraInfo);
390         return;
391     }
392     bool isBundleName = false;
393     std::string callerName = "";
394     static_cast<void>(IpcCommon::GetCallerName(*this, isBundleName, callerName));
395     contextCallback->SetTraceUserId(userId);
396 
397     if (!IpcCommon::CheckPermission(*this, MANAGE_USER_IDM_PERMISSION)) {
398         IAM_LOGE("failed to check permission");
399         contextCallback->OnResult(CHECK_PERMISSION_FAILED, extraInfo);
400         return;
401     }
402 
403     std::lock_guard<std::mutex> lock(mutex_);
404     CancelCurrentEnrollIfExist();
405 
406     std::vector<std::shared_ptr<CredentialInfoInterface>> credInfos;
407     int32_t ret = UserIdmDatabase::Instance().DeleteUser(userId, authToken, credInfos);
408     if (ret != SUCCESS) {
409         IAM_LOGE("failed to delete user");
410         contextCallback->OnResult(ret, extraInfo);
411         return;
412     }
413     SetAuthTypeTrace(credInfos, contextCallback);
414 
415     ret = ResourceNodeUtils::NotifyExecutorToDeleteTemplates(credInfos, "DeleteUser");
416     if (ret != SUCCESS) {
417         IAM_LOGE("failed to delete executor info, error code : %{public}d", ret);
418     }
419     IAM_LOGI("delete user end");
420     PublishEventAdapter::PublishDeletedEvent(userId);
421     contextCallback->OnResult(ret, extraInfo);
422 }
423 
DelCredential(int32_t userId,uint64_t credentialId,const std::vector<uint8_t> & authToken,const sptr<IdmCallbackInterface> & callback)424 void UserIdmService::DelCredential(int32_t userId, uint64_t credentialId,
425     const std::vector<uint8_t> &authToken, const sptr<IdmCallbackInterface> &callback)
426 {
427     IF_FALSE_LOGE_AND_RETURN(callback != nullptr);
428 
429     Attributes extraInfo;
430     auto contextCallback = ContextCallback::NewInstance(callback, TRACE_DELETE_CREDENTIAL);
431     if (contextCallback == nullptr) {
432         IAM_LOGE("failed to construct context callback");
433         callback->OnResult(GENERAL_ERROR, extraInfo);
434         return;
435     }
436     bool isBundleName = false;
437     std::string callerName = "";
438     static_cast<void>(IpcCommon::GetCallerName(*this, isBundleName, callerName));
439     contextCallback->SetTraceUserId(userId);
440 
441     if (!IpcCommon::CheckPermission(*this, MANAGE_USER_IDM_PERMISSION)) {
442         IAM_LOGE("failed to check permission");
443         contextCallback->OnResult(CHECK_PERMISSION_FAILED, extraInfo);
444         return;
445     }
446 
447     std::lock_guard<std::mutex> lock(mutex_);
448     CancelCurrentEnrollIfExist();
449 
450     std::shared_ptr<CredentialInfoInterface> oldInfo;
451     auto ret = UserIdmDatabase::Instance().DeleteCredentialInfo(userId, credentialId, authToken, oldInfo);
452     if (ret != SUCCESS) {
453         IAM_LOGE("failed to delete CredentialInfo");
454         contextCallback->OnResult(ret, extraInfo);
455         return;
456     }
457     if (oldInfo != nullptr) {
458         contextCallback->SetTraceAuthType(oldInfo->GetAuthType());
459     }
460 
461     IAM_LOGI("delete credentialInfo success");
462     std::vector<std::shared_ptr<CredentialInfoInterface>> list = {oldInfo};
463     ret = ResourceNodeUtils::NotifyExecutorToDeleteTemplates(list, "DeleteTemplate");
464     if (ret != SUCCESS) {
465         IAM_LOGE("failed to delete executor info, error code : %{public}d", ret);
466     }
467 
468     contextCallback->OnResult(ret, extraInfo);
469 }
470 
Dump(int fd,const std::vector<std::u16string> & args)471 int UserIdmService::Dump(int fd, const std::vector<std::u16string> &args)
472 {
473     IAM_LOGI("start");
474     if (fd < 0) {
475         IAM_LOGE("invalid parameters");
476         dprintf(fd, "Invalid parameters.\n");
477         return INVALID_PARAMETERS;
478     }
479     std::string arg0 = (args.empty() ? "" : Str16ToStr8(args[0]));
480     if (arg0.empty() || arg0.compare("-h") == 0) {
481         dprintf(fd, "Usage:\n");
482         dprintf(fd, "      -h: command help.\n");
483         dprintf(fd, "      -l: active user info dump.\n");
484         return SUCCESS;
485     }
486     if (arg0.compare("-l") != 0) {
487         IAM_LOGE("invalid option");
488         dprintf(fd, "Invalid option\n");
489         return GENERAL_ERROR;
490     }
491 
492     std::optional<int32_t> activeUserId;
493     if (IpcCommon::GetActiveUserId(activeUserId) != SUCCESS) {
494         dprintf(fd, "Internal error.\n");
495         IAM_LOGE("failed to get active id");
496         return GENERAL_ERROR;
497     }
498     dprintf(fd, "Active user is %d\n", activeUserId.value());
499     auto userInfo = UserIdmDatabase::Instance().GetSecUserInfo(activeUserId.value());
500     if (userInfo == nullptr) {
501         IAM_LOGE("userInfo is null");
502         return SUCCESS;
503     }
504     auto enrolledInfo = userInfo->GetEnrolledInfo();
505     for (auto &info : enrolledInfo) {
506         if (info != nullptr) {
507             dprintf(fd, "AuthType %s is enrolled.\n", Common::AuthTypeToStr(info->GetAuthType()));
508         }
509     }
510     return SUCCESS;
511 }
512 
SetAuthTypeTrace(const std::vector<std::shared_ptr<CredentialInfoInterface>> & credInfos,const std::shared_ptr<ContextCallback> & contextCallback)513 void UserIdmService::SetAuthTypeTrace(const std::vector<std::shared_ptr<CredentialInfoInterface>> &credInfos,
514     const std::shared_ptr<ContextCallback> &contextCallback)
515 {
516     int32_t authTypeTrace = 0;
517     for (const auto &credInfo : credInfos) {
518         if (credInfo == nullptr) {
519             IAM_LOGE("credInfo is nullptr");
520             continue;
521         }
522         authTypeTrace |= credInfo->GetAuthType();
523     }
524     contextCallback->SetTraceAuthType(authTypeTrace);
525 }
526 
EnforceDelUserInner(int32_t userId,std::shared_ptr<ContextCallback> callbackForTrace,std::string changeReasonTrace)527 int32_t UserIdmService::EnforceDelUserInner(int32_t userId, std::shared_ptr<ContextCallback> callbackForTrace,
528     std::string changeReasonTrace)
529 {
530     std::vector<std::shared_ptr<CredentialInfoInterface>> credInfos;
531     int32_t ret = UserIdmDatabase::Instance().DeleteUserEnforce(userId, credInfos);
532     if (ret != SUCCESS) {
533         IAM_LOGE("failed to enforce delete user, ret:%{public}d", ret);
534         return ret;
535     }
536     SetAuthTypeTrace(credInfos, callbackForTrace);
537     ret = ResourceNodeUtils::NotifyExecutorToDeleteTemplates(credInfos, changeReasonTrace);
538     if (ret != SUCCESS) {
539         IAM_LOGE("failed to delete executor info, error code : %{public}d", ret);
540         // The caller doesn't need to care executor delete result.
541         return SUCCESS;
542     }
543 
544     PublishEventAdapter::PublishDeletedEvent(userId);
545     IAM_LOGI("delete user success, userId:%{public}d", userId);
546     return SUCCESS;
547 }
548 
ClearRedundancyCredentialInner()549 void UserIdmService::ClearRedundancyCredentialInner()
550 {
551     IAM_LOGE("start");
552     std::vector<int32_t> accountInfo;
553     int32_t ret = IpcCommon::GetAllUserId(accountInfo);
554     if (ret != SUCCESS) {
555         IAM_LOGE("GetAllUserId failed");
556         return;
557     }
558 
559     auto userInfos = UserIdmDatabase::Instance().GetAllExtUserInfo();
560     if (userInfos.empty()) {
561         IAM_LOGE("no userInfo");
562         return;
563     }
564     bool isBundleName = false;
565     std::string callerName = "";
566     static_cast<void>(IpcCommon::GetCallerName(*this, isBundleName, callerName));
567 
568     for (const auto &iter : userInfos) {
569         int32_t userId = iter->GetUserId();
570         auto callbackForTrace = ContextCallback::NewDummyInstance(TRACE_DELETE_REDUNDANCY);
571         if (callbackForTrace == nullptr) {
572             IAM_LOGE("failed to get callbackForTrace");
573             continue;
574         }
575         callbackForTrace->SetTraceUserId(userId);
576         callbackForTrace->SetTraceCallerName(callerName);
577         std::vector<int32_t>::iterator it = std::find(accountInfo.begin(), accountInfo.end(), userId);
578         if (it == accountInfo.end()) {
579             ret = EnforceDelUserInner(userId, callbackForTrace, "DeleteRedundancy");
580             Attributes extraInfo;
581             callbackForTrace->OnResult(ret, extraInfo);
582             IAM_LOGE("ClearRedundancytCredential, userId: %{public}d", userId);
583         }
584     }
585 }
586 
ClearRedundancyCredential(const sptr<IdmCallbackInterface> & callback)587 void UserIdmService::ClearRedundancyCredential(const sptr<IdmCallbackInterface> &callback)
588 {
589     IAM_LOGE("start");
590     IF_FALSE_LOGE_AND_RETURN(callback != nullptr);
591 
592     Attributes extraInfo;
593     auto contextCallback = ContextCallback::NewInstance(callback, NO_NEED_TRACE);
594     if (contextCallback == nullptr) {
595         IAM_LOGE("failed to construct context callback");
596         callback->OnResult(GENERAL_ERROR, extraInfo);
597         return;
598     }
599 
600     if (!IpcCommon::CheckPermission(*this, CLEAR_REDUNDANCY_PERMISSION)) {
601         IAM_LOGE("failed to check permission");
602         contextCallback->OnResult(CHECK_PERMISSION_FAILED, extraInfo);
603         return;
604     }
605 
606     std::lock_guard<std::mutex> lock(mutex_);
607     CancelCurrentEnrollIfExist();
608 
609     this->ClearRedundancyCredentialInner();
610     contextCallback->OnResult(SUCCESS, extraInfo);
611 }
612 
613 } // namespace UserAuth
614 } // namespace UserIam
615 } // namespace OHOS