• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2022-2023 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 #include "enrollment_impl.h"
16 
17 #include "hdi_wrapper.h"
18 #include "iam_hitrace_helper.h"
19 #include "iam_logger.h"
20 #include "iam_ptr.h"
21 
22 #include "credential_info_impl.h"
23 #include "schedule_node_helper.h"
24 #include "user_idm_database.h"
25 
26 #define LOG_LABEL UserIam::Common::LABEL_USER_AUTH_SA
27 
28 namespace OHOS {
29 namespace UserIam {
30 namespace UserAuth {
EnrollmentImpl(int32_t userId,AuthType authType)31 EnrollmentImpl::EnrollmentImpl(int32_t userId, AuthType authType) : userId_(userId), authType_(authType)
32 {
33 }
34 
~EnrollmentImpl()35 EnrollmentImpl::~EnrollmentImpl()
36 {
37     Cancel();
38 }
39 
SetLatestError(int32_t error)40 void EnrollmentImpl::SetLatestError(int32_t error)
41 {
42     if (error != ResultCode::SUCCESS) {
43         latestError_ = error;
44     }
45 }
46 
GetLatestError() const47 int32_t EnrollmentImpl::GetLatestError() const
48 {
49     return latestError_;
50 }
51 
SetExecutorSensorHint(uint32_t executorSensorHint)52 void EnrollmentImpl::SetExecutorSensorHint(uint32_t executorSensorHint)
53 {
54     executorSensorHint_ = executorSensorHint;
55 }
56 
SetAuthToken(const std::vector<uint8_t> & authToken)57 void EnrollmentImpl::SetAuthToken(const std::vector<uint8_t> &authToken)
58 {
59     authToken_ = authToken;
60 }
61 
SetAccessTokenId(uint32_t tokenId)62 void EnrollmentImpl::SetAccessTokenId(uint32_t tokenId)
63 {
64     tokenId_ = tokenId;
65 }
66 
GetAccessTokenId() const67 uint32_t EnrollmentImpl::GetAccessTokenId() const
68 {
69     return tokenId_;
70 }
71 
SetPinSubType(PinSubType pinSubType)72 void EnrollmentImpl::SetPinSubType(PinSubType pinSubType)
73 {
74     pinSubType_ = pinSubType;
75 }
76 
SetIsUpdate(bool isUpdate)77 void EnrollmentImpl::SetIsUpdate(bool isUpdate)
78 {
79     isUpdate_ = isUpdate;
80 }
81 
Start(std::vector<std::shared_ptr<ScheduleNode>> & scheduleList,std::shared_ptr<ScheduleNodeCallback> callback)82 bool EnrollmentImpl::Start(std::vector<std::shared_ptr<ScheduleNode>> &scheduleList,
83     std::shared_ptr<ScheduleNodeCallback> callback)
84 {
85     auto hdi = HdiWrapper::GetHdiInstance();
86     if (!hdi) {
87         IAM_LOGE("bad hdi");
88         return false;
89     }
90     // cache secUserId first in case of update
91     if (isUpdate_ && !GetSecUserId(secUserId_)) {
92         IAM_LOGE("get and cache secUserId fail");
93         return false;
94     }
95 
96     HdiScheduleInfo info = {};
97     HdiEnrollParam param = {
98         .authType = static_cast<HdiAuthType>(authType_),
99         .executorSensorHint = executorSensorHint_,
100     };
101     IamHitraceHelper traceHelper("hdi BeginEnrollment");
102     auto result = hdi->BeginEnrollmentV1_1(userId_, authToken_, param, info);
103     if (result != HDF_SUCCESS) {
104         IAM_LOGE("hdi BeginEnrollment failed, err is %{public}d", result);
105         SetLatestError(result);
106         return false;
107     }
108 
109     std::vector<HdiScheduleInfo> infos = {};
110     infos.emplace_back(info);
111 
112     ScheduleNodeHelper::NodeOptionalPara para;
113     para.tokenId = tokenId_;
114 
115     if (!ScheduleNodeHelper::BuildFromHdi(infos, callback, scheduleList, para)) {
116         IAM_LOGE("BuildFromHdi failed");
117         return false;
118     }
119 
120     running_ = true;
121     return true;
122 }
123 
GetSecUserId(std::optional<uint64_t> & secUserId)124 bool EnrollmentImpl::GetSecUserId(std::optional<uint64_t> &secUserId)
125 {
126     secUserId = std::nullopt;
127     if (authType_ != PIN) {
128         IAM_LOGI("no need return sec user id");
129         return true;
130     }
131     auto userInfo = UserIdmDatabase::Instance().GetSecUserInfo(userId_);
132     if (userInfo != nullptr) {
133         secUserId = userInfo->GetSecUserId();
134         return true;
135     }
136 
137     // do not delete users in case of updates
138     if (isUpdate_) {
139         return false;
140     }
141 
142     IAM_LOGE("current user id %{public}d get fail", userId_);
143     std::vector<std::shared_ptr<CredentialInfoInterface>> credInfos;
144     if (UserIdmDatabase::Instance().DeleteUserEnforce(userId_, credInfos) != SUCCESS) {
145         IAM_LOGE("failed to enforce delete user");
146     }
147     return false;
148 }
149 
Update(const std::vector<uint8_t> & scheduleResult,uint64_t & credentialId,std::shared_ptr<CredentialInfoInterface> & info,std::vector<uint8_t> & rootSecret,std::optional<uint64_t> & secUserId)150 bool EnrollmentImpl::Update(const std::vector<uint8_t> &scheduleResult, uint64_t &credentialId,
151     std::shared_ptr<CredentialInfoInterface> &info, std::vector<uint8_t> &rootSecret,
152     std::optional<uint64_t> &secUserId)
153 {
154     auto hdi = HdiWrapper::GetHdiInstance();
155     if (!hdi) {
156         IAM_LOGE("bad hdi");
157         return false;
158     }
159 
160     HdiEnrollResultInfo resultInfo = {};
161     auto result = hdi->UpdateEnrollmentResult(userId_, scheduleResult, resultInfo);
162     if (result != HDF_SUCCESS) {
163         IAM_LOGE("hdi UpdateEnrollmentResult failed, err is %{public}d, userId is %{public}d", result, userId_);
164         SetLatestError(result);
165         return false;
166     }
167     IAM_LOGI("hdi UpdateEnrollmentResult success, userId is %{public}d", userId_);
168 
169     credentialId = resultInfo.credentialId;
170     rootSecret = resultInfo.rootSecret;
171     if (isUpdate_) {
172         secUserId = secUserId_;
173     } else {
174         if (!GetSecUserId(secUserId)) {
175             IAM_LOGE("enroll get secUserId fail");
176             return false;
177         }
178         IAM_LOGI("enroll not need to delete old cred");
179         info = nullptr;
180         return true;
181     }
182 
183     info = Common::MakeShared<CredentialInfoImpl>(userId_, resultInfo.oldInfo);
184     if (info == nullptr) {
185         IAM_LOGE("bad alloc");
186         return false;
187     }
188     return true;
189 }
190 
Cancel()191 bool EnrollmentImpl::Cancel()
192 {
193     if (!running_) {
194         return false;
195     }
196     running_ = false;
197 
198     auto hdi = HdiWrapper::GetHdiInstance();
199     if (!hdi) {
200         IAM_LOGE("bad hdi");
201         return false;
202     }
203 
204     auto result = hdi->CancelEnrollment(userId_);
205     if (result != HDF_SUCCESS) {
206         IAM_LOGE("hdi CancelEnrollment failed, err is %{public}d", result);
207         SetLatestError(result);
208         return false;
209     }
210     return true;
211 }
212 } // namespace UserAuth
213 } // namespace UserIam
214 } // namespace OHOS