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 "user_auth_client_impl.h"
17
18 #include "system_ability_definition.h"
19
20 #include "auth_common.h"
21 #include "callback_manager.h"
22 #include "iam_check.h"
23 #include "iam_logger.h"
24 #include "iam_para2str.h"
25 #include "iam_ptr.h"
26 #include "ipc_client_utils.h"
27 #include "user_auth_callback_service.h"
28 #include "widget_callback_service.h"
29
30 #define LOG_TAG "USER_AUTH_SDK"
31 namespace OHOS {
32 namespace UserIam {
33 namespace UserAuth {
34 namespace {
35 class NorthAuthenticationCallback : public AuthenticationCallback, public NoCopyable {
36 public:
37 explicit NorthAuthenticationCallback(std::shared_ptr<AuthenticationCallback> innerCallback);
38 void OnAcquireInfo(int32_t module, uint32_t acquireInfo, const Attributes &extraInfo) override;
39 void OnResult(int32_t result, const Attributes &extraInfo) override;
40
41 private:
42 std::shared_ptr<AuthenticationCallback> innerCallback_ = nullptr;
43 };
44
NorthAuthenticationCallback(std::shared_ptr<AuthenticationCallback> innerCallback)45 NorthAuthenticationCallback::NorthAuthenticationCallback(std::shared_ptr<AuthenticationCallback> innerCallback)
46 : innerCallback_(innerCallback) {};
47
OnAcquireInfo(int32_t module,uint32_t acquireInfo,const Attributes & extraInfo)48 void NorthAuthenticationCallback::OnAcquireInfo(int32_t module, uint32_t acquireInfo, const Attributes &extraInfo)
49 {
50 if (innerCallback_ == nullptr) {
51 IAM_LOGE("callback is nullptr");
52 return;
53 }
54
55 if (module == AuthType::FACE) {
56 if (acquireInfo == 0 || acquireInfo > FACE_AUTH_TIP_MAX) {
57 IAM_LOGI("skip undefined face auth tip %{public}u", acquireInfo);
58 return;
59 }
60 } else if (module == AuthType::FINGERPRINT) {
61 if (acquireInfo > FINGERPRINT_AUTH_TIP_MAX) {
62 IAM_LOGI("skip undefined fingerprint auth tip %{public}u", acquireInfo);
63 return;
64 }
65 }
66
67 innerCallback_->OnAcquireInfo(module, acquireInfo, extraInfo);
68 }
69
OnResult(int32_t result,const Attributes & extraInfo)70 void NorthAuthenticationCallback::OnResult(int32_t result, const Attributes &extraInfo)
71 {
72 if (innerCallback_ == nullptr) {
73 IAM_LOGE("callback is nullptr");
74 return;
75 }
76
77 innerCallback_->OnResult(result, extraInfo);
78 }
79 } // namespace
80
GetAvailableStatus(AuthType authType,AuthTrustLevel authTrustLevel)81 int32_t UserAuthClientImpl::GetAvailableStatus(AuthType authType, AuthTrustLevel authTrustLevel)
82 {
83 IAM_LOGI("start, authType:%{public}d authTrustLevel:%{public}u", authType, authTrustLevel);
84 return GetAvailableStatus(INT32_MAX, authType, authTrustLevel);
85 }
86
GetAvailableStatus(int32_t apiVersion,AuthType authType,AuthTrustLevel authTrustLevel)87 int32_t UserAuthClientImpl::GetAvailableStatus(int32_t apiVersion, AuthType authType, AuthTrustLevel authTrustLevel)
88 {
89 IAM_LOGI("start, apiVersion:%{public}d authType:%{public}d authTrustLevel:%{public}u",
90 apiVersion, authType, authTrustLevel);
91 auto proxy = GetProxy();
92 if (!proxy) {
93 IAM_LOGE("proxy is nullptr");
94 return GENERAL_ERROR;
95 }
96 return proxy->GetAvailableStatus(apiVersion, authType, authTrustLevel);
97 }
98
GetProperty(int32_t userId,const GetPropertyRequest & request,const std::shared_ptr<GetPropCallback> & callback)99 void UserAuthClientImpl::GetProperty(int32_t userId, const GetPropertyRequest &request,
100 const std::shared_ptr<GetPropCallback> &callback)
101 {
102 IAM_LOGI("start, userId:%{public}d authType:%{public}d", userId, request.authType);
103 if (!callback) {
104 IAM_LOGE("get prop callback is nullptr");
105 return;
106 }
107
108 auto proxy = GetProxy();
109 if (!proxy) {
110 IAM_LOGE("proxy is nullptr");
111 Attributes extraInfo;
112 callback->OnResult(GENERAL_ERROR, extraInfo);
113 return;
114 }
115
116 sptr<GetExecutorPropertyCallbackInterface> wrapper(
117 new (std::nothrow) GetExecutorPropertyCallbackService(callback));
118 if (wrapper == nullptr) {
119 IAM_LOGE("failed to create wrapper");
120 Attributes extraInfo;
121 callback->OnResult(GENERAL_ERROR, extraInfo);
122 return;
123 }
124 proxy->GetProperty(userId, request.authType, request.keys, wrapper);
125 }
126
SetPropertyInner(int32_t userId,const SetPropertyRequest & request,const std::shared_ptr<SetPropCallback> & callback)127 ResultCode UserAuthClientImpl::SetPropertyInner(int32_t userId, const SetPropertyRequest &request,
128 const std::shared_ptr<SetPropCallback> &callback)
129 {
130 auto proxy = GetProxy();
131 if (!proxy) {
132 IAM_LOGE("proxy is nullptr");
133 return GENERAL_ERROR;
134 }
135
136 auto keys = request.attrs.GetKeys();
137 IF_FALSE_LOGE_AND_RETURN_VAL(keys.size() == 1, GENERAL_ERROR);
138
139 Attributes::AttributeKey key = keys[0];
140 Attributes attr;
141
142 std::vector<uint8_t> extraInfo;
143 bool getArrayRet = request.attrs.GetUint8ArrayValue(static_cast<Attributes::AttributeKey>(key), extraInfo);
144 IF_FALSE_LOGE_AND_RETURN_VAL(getArrayRet, GENERAL_ERROR);
145
146 bool setModeRet = attr.SetUint32Value(Attributes::ATTR_PROPERTY_MODE, static_cast<uint32_t>(key));
147 IF_FALSE_LOGE_AND_RETURN_VAL(setModeRet, GENERAL_ERROR);
148
149 bool setArrayRet = attr.SetUint8ArrayValue(Attributes::ATTR_EXTRA_INFO, extraInfo);
150 IF_FALSE_LOGE_AND_RETURN_VAL(setArrayRet, GENERAL_ERROR);
151
152 sptr<SetExecutorPropertyCallbackInterface> wrapper(
153 new (std::nothrow) SetExecutorPropertyCallbackService(callback));
154 IF_FALSE_LOGE_AND_RETURN_VAL(wrapper != nullptr, GENERAL_ERROR);
155 proxy->SetProperty(userId, request.authType, attr, wrapper);
156 return SUCCESS;
157 }
158
SetProperty(int32_t userId,const SetPropertyRequest & request,const std::shared_ptr<SetPropCallback> & callback)159 void UserAuthClientImpl::SetProperty(int32_t userId, const SetPropertyRequest &request,
160 const std::shared_ptr<SetPropCallback> &callback)
161 {
162 IAM_LOGI("start, userId:%{public}d authType:%{public}d", userId, request.authType);
163 if (!callback) {
164 IAM_LOGE("set prop callback is nullptr");
165 return;
166 }
167
168 ResultCode result = SetPropertyInner(userId, request, callback);
169 if (result != SUCCESS) {
170 IAM_LOGE("result is not success");
171 Attributes retExtraInfo;
172 callback->OnResult(GENERAL_ERROR, retExtraInfo);
173 return;
174 }
175 }
176
BeginAuthentication(const AuthParam & authParam,const std::shared_ptr<AuthenticationCallback> & callback)177 uint64_t UserAuthClientImpl::BeginAuthentication(const AuthParam &authParam,
178 const std::shared_ptr<AuthenticationCallback> &callback)
179 {
180 IAM_LOGI("start, userId:%{public}d authType:%{public}d atl:%{public}u remoteAuthParamHasValue:%{public}s",
181 authParam.userId, authParam.authType, authParam.authTrustLevel,
182 Common::GetBoolStr(authParam.remoteAuthParam.has_value()));
183 if (authParam.remoteAuthParam.has_value()) {
184 IAM_LOGI("verifierNetworkIdHasValue:%{public}s collectorNetworkIdHasValue:%{public}s"
185 "collectorTokenIdHasValue:%{public}s",
186 Common::GetBoolStr(authParam.remoteAuthParam->verifierNetworkId.has_value()),
187 Common::GetBoolStr(authParam.remoteAuthParam->collectorNetworkId.has_value()),
188 Common::GetBoolStr(authParam.remoteAuthParam->collectorTokenId.has_value()));
189 }
190
191 if (!callback) {
192 IAM_LOGE("auth callback is nullptr");
193 return INVALID_SESSION_ID;
194 }
195
196 auto proxy = GetProxy();
197 if (!proxy) {
198 IAM_LOGE("proxy is nullptr");
199 Attributes extraInfo;
200 callback->OnResult(GENERAL_ERROR, extraInfo);
201 return INVALID_SESSION_ID;
202 }
203
204 sptr<UserAuthCallbackInterface> wrapper(new (std::nothrow) UserAuthCallbackService(callback));
205 if (wrapper == nullptr) {
206 IAM_LOGE("failed to create wrapper");
207 Attributes extraInfo;
208 callback->OnResult(GENERAL_ERROR, extraInfo);
209 return INVALID_SESSION_ID;
210 }
211 AuthParamInner authParamInner = {
212 .userId = authParam.userId,
213 .challenge = authParam.challenge,
214 .authType = authParam.authType,
215 .authTrustLevel = authParam.authTrustLevel,
216 .authIntent = authParam.authIntent
217 };
218 std::optional<RemoteAuthParam> remoteAuthParam = authParam.remoteAuthParam;
219 return proxy->AuthUser(authParamInner, remoteAuthParam, wrapper);
220 }
221
BeginNorthAuthentication(int32_t apiVersion,const std::vector<uint8_t> & challenge,AuthType authType,AuthTrustLevel atl,const std::shared_ptr<AuthenticationCallback> & callback)222 uint64_t UserAuthClientImpl::BeginNorthAuthentication(int32_t apiVersion, const std::vector<uint8_t> &challenge,
223 AuthType authType, AuthTrustLevel atl, const std::shared_ptr<AuthenticationCallback> &callback)
224 {
225 IAM_LOGI("start, apiVersion:%{public}d authType:%{public}d atl:%{public}u", apiVersion, authType, atl);
226 if (!callback) {
227 IAM_LOGE("auth callback is nullptr");
228 return INVALID_SESSION_ID;
229 }
230
231 auto northCallback = Common::MakeShared<NorthAuthenticationCallback>(callback);
232 if (!northCallback) {
233 IAM_LOGE("auth callback is nullptr");
234 Attributes extraInfo;
235 callback->OnResult(GENERAL_ERROR, extraInfo);
236 return INVALID_SESSION_ID;
237 }
238
239 auto proxy = GetProxy();
240 if (!proxy) {
241 IAM_LOGE("proxy is nullptr");
242 Attributes extraInfo;
243 callback->OnResult(GENERAL_ERROR, extraInfo);
244 return INVALID_SESSION_ID;
245 }
246
247 sptr<UserAuthCallbackInterface> wrapper(new (std::nothrow) UserAuthCallbackService(northCallback));
248 if (wrapper == nullptr) {
249 IAM_LOGE("failed to create wrapper");
250 Attributes extraInfo;
251 callback->OnResult(GENERAL_ERROR, extraInfo);
252 return INVALID_SESSION_ID;
253 }
254 return proxy->Auth(apiVersion, challenge, authType, atl, wrapper);
255 }
256
CancelAuthentication(uint64_t contextId)257 int32_t UserAuthClientImpl::CancelAuthentication(uint64_t contextId)
258 {
259 IAM_LOGI("start");
260 auto proxy = GetProxy();
261 if (!proxy) {
262 IAM_LOGE("proxy is nullptr");
263 return GENERAL_ERROR;
264 }
265
266 return proxy->CancelAuthOrIdentify(contextId);
267 }
268
BeginIdentification(const std::vector<uint8_t> & challenge,AuthType authType,const std::shared_ptr<IdentificationCallback> & callback)269 uint64_t UserAuthClientImpl::BeginIdentification(const std::vector<uint8_t> &challenge, AuthType authType,
270 const std::shared_ptr<IdentificationCallback> &callback)
271 {
272 IAM_LOGI("start, authType:%{public}d", authType);
273 if (!callback) {
274 IAM_LOGE("identify callback is nullptr");
275 return INVALID_SESSION_ID;
276 }
277
278 auto proxy = GetProxy();
279 if (!proxy) {
280 IAM_LOGE("proxy is nullptr");
281 Attributes extraInfo;
282 callback->OnResult(GENERAL_ERROR, extraInfo);
283 return INVALID_SESSION_ID;
284 }
285
286 sptr<UserAuthCallbackInterface> wrapper(new (std::nothrow) UserAuthCallbackService(callback));
287 if (wrapper == nullptr) {
288 IAM_LOGE("failed to create wrapper");
289 Attributes extraInfo;
290 callback->OnResult(GENERAL_ERROR, extraInfo);
291 return INVALID_SESSION_ID;
292 }
293 return proxy->Identify(challenge, authType, wrapper);
294 }
295
CancelIdentification(uint64_t contextId)296 int32_t UserAuthClientImpl::CancelIdentification(uint64_t contextId)
297 {
298 IAM_LOGI("start");
299 auto proxy = GetProxy();
300 if (!proxy) {
301 IAM_LOGE("proxy is nullptr");
302 return GENERAL_ERROR;
303 }
304
305 return proxy->CancelAuthOrIdentify(contextId);
306 }
307
GetVersion(int32_t & version)308 int32_t UserAuthClientImpl::GetVersion(int32_t &version)
309 {
310 IAM_LOGI("start");
311 auto proxy = GetProxy();
312 if (!proxy) {
313 IAM_LOGE("proxy is nullptr");
314 return GENERAL_ERROR;
315 }
316
317 return proxy->GetVersion(version);
318 }
319
SetGlobalConfigParam(const GlobalConfigParam & param)320 int32_t UserAuthClientImpl::SetGlobalConfigParam(const GlobalConfigParam ¶m)
321 {
322 IAM_LOGI("start");
323 auto proxy = GetProxy();
324 if (!proxy) {
325 IAM_LOGE("proxy is nullptr");
326 return GENERAL_ERROR;
327 }
328
329 return proxy->SetGlobalConfigParam(param);
330 }
331
GetProxy()332 sptr<UserAuthInterface> UserAuthClientImpl::GetProxy()
333 {
334 std::lock_guard<std::mutex> lock(mutex_);
335 if (proxy_ != nullptr) {
336 return proxy_;
337 }
338 sptr<IRemoteObject> obj = IpcClientUtils::GetRemoteObject(SUBSYS_USERIAM_SYS_ABILITY_USERAUTH);
339 if (obj == nullptr) {
340 IAM_LOGE("remote object is null");
341 return proxy_;
342 }
343 sptr<IRemoteObject::DeathRecipient> dr(new (std::nothrow) UserAuthImplDeathRecipient());
344 if ((dr == nullptr) || (obj->IsProxyObject() && !obj->AddDeathRecipient(dr))) {
345 IAM_LOGE("add death recipient fail");
346 return proxy_;
347 }
348
349 proxy_ = iface_cast<UserAuthInterface>(obj);
350 deathRecipient_ = dr;
351 return proxy_;
352 }
353
ResetProxy(const wptr<IRemoteObject> & remote)354 void UserAuthClientImpl::ResetProxy(const wptr<IRemoteObject> &remote)
355 {
356 IAM_LOGI("start");
357 std::lock_guard<std::mutex> lock(mutex_);
358 if (proxy_ == nullptr) {
359 IAM_LOGE("proxy_ is null");
360 return;
361 }
362 auto serviceRemote = proxy_->AsObject();
363 if ((serviceRemote != nullptr) && (serviceRemote == remote.promote())) {
364 IAM_LOGI("need reset");
365 serviceRemote->RemoveDeathRecipient(deathRecipient_);
366 proxy_ = nullptr;
367 deathRecipient_ = nullptr;
368 }
369 IAM_LOGI("end reset proxy");
370 }
371
OnRemoteDied(const wptr<IRemoteObject> & remote)372 void UserAuthClientImpl::UserAuthImplDeathRecipient::OnRemoteDied(const wptr<IRemoteObject> &remote)
373 {
374 IAM_LOGI("start");
375 if (remote == nullptr) {
376 IAM_LOGE("remote is nullptr");
377 return;
378 }
379 CallbackManager::GetInstance().OnServiceDeath();
380 UserAuthClientImpl::Instance().ResetProxy(remote);
381 }
382
Instance()383 UserAuthClientImpl &UserAuthClientImpl::Instance()
384 {
385 static UserAuthClientImpl impl;
386 return impl;
387 }
388
GetInstance()389 UserAuthClient &UserAuthClient::GetInstance()
390 {
391 return UserAuthClientImpl::Instance();
392 }
393
BeginWidgetAuth(int32_t apiVersion,const AuthParamInner & authParam,const WidgetParam & widgetParam,const std::shared_ptr<AuthenticationCallback> & callback)394 uint64_t UserAuthClientImpl::BeginWidgetAuth(int32_t apiVersion, const AuthParamInner &authParam,
395 const WidgetParam &widgetParam, const std::shared_ptr<AuthenticationCallback> &callback)
396 {
397 IAM_LOGI("start, apiVersion:%{public}d authTypeSize:%{public}zu authTrustLevel:%{public}u",
398 apiVersion, authParam.authTypes.size(), authParam.authTrustLevel);
399 // parameter verification
400 if (!callback) {
401 IAM_LOGE("auth callback is nullptr");
402 return INVALID_SESSION_ID;
403 }
404 auto proxy = GetProxy();
405 if (!proxy) {
406 IAM_LOGE("proxy is nullptr");
407 Attributes extraInfo;
408 callback->OnResult(static_cast<int32_t>(ResultCode::GENERAL_ERROR), extraInfo);
409 return INVALID_SESSION_ID;
410 }
411
412 sptr<UserAuthCallbackInterface> wrapper(new (std::nothrow) UserAuthCallbackService(callback));
413 if (wrapper == nullptr) {
414 IAM_LOGE("failed to create wrapper");
415 Attributes extraInfo;
416 callback->OnResult(static_cast<int32_t>(ResultCode::GENERAL_ERROR), extraInfo);
417 return INVALID_SESSION_ID;
418 }
419 return proxy->AuthWidget(apiVersion, authParam, widgetParam, wrapper);
420 }
421
SetWidgetCallback(int32_t version,const std::shared_ptr<IUserAuthWidgetCallback> & callback)422 int32_t UserAuthClientImpl::SetWidgetCallback(int32_t version, const std::shared_ptr<IUserAuthWidgetCallback> &callback)
423 {
424 IAM_LOGI("start, version:%{public}d", version);
425 if (!callback) {
426 IAM_LOGE("widget callback is nullptr");
427 return GENERAL_ERROR;
428 }
429 auto proxy = GetProxy();
430 if (!proxy) {
431 IAM_LOGE("proxy is nullptr");
432 return GENERAL_ERROR;
433 }
434
435 sptr<WidgetCallbackInterface> wrapper(new (std::nothrow) WidgetCallbackService(callback));
436 if (wrapper == nullptr) {
437 IAM_LOGE("failed to create wrapper");
438 return GENERAL_ERROR;
439 }
440 return proxy->RegisterWidgetCallback(version, wrapper);
441 }
442
Notice(NoticeType noticeType,const std::string & eventData)443 int32_t UserAuthClientImpl::Notice(NoticeType noticeType, const std::string &eventData)
444 {
445 IAM_LOGI("start, noticeType:%{public}d", noticeType);
446 auto proxy = GetProxy();
447 if (!proxy) {
448 IAM_LOGE("proxy is nullptr");
449 return GENERAL_ERROR;
450 }
451 IAM_LOGI("UserAuthClientImpl::Notice noticeType:%{public}d, eventDat:%{public}s",
452 static_cast<int32_t>(noticeType), eventData.c_str());
453 return proxy->Notice(noticeType, eventData);
454 }
455
GetEnrolledState(int32_t apiVersion,AuthType authType,EnrolledState & enrolledState)456 int32_t UserAuthClientImpl::GetEnrolledState(int32_t apiVersion, AuthType authType, EnrolledState &enrolledState)
457 {
458 IAM_LOGI("start, apiVersion:%{public}d authType:%{public}d ", apiVersion, authType);
459 auto proxy = GetProxy();
460 if (!proxy) {
461 IAM_LOGE("proxy is nullptr");
462 return GENERAL_ERROR;
463 }
464 int32_t ret = proxy->GetEnrolledState(apiVersion, authType, enrolledState);
465 if (ret != SUCCESS) {
466 IAM_LOGE("proxy GetEnrolledState failed");
467 return ret;
468 }
469 return ret;
470 }
471
RegistUserAuthSuccessEventListener(const std::vector<AuthType> & authType,const sptr<AuthEventListenerInterface> & listener)472 int32_t UserAuthClientImpl::RegistUserAuthSuccessEventListener(const std::vector<AuthType> &authType,
473 const sptr<AuthEventListenerInterface> &listener)
474 {
475 IAM_LOGI("start");
476 if (!listener) {
477 IAM_LOGE("listener is nullptr");
478 return GENERAL_ERROR;
479 }
480
481 auto proxy = GetProxy();
482 if (!proxy) {
483 IAM_LOGE("proxy is nullptr");
484 return GENERAL_ERROR;
485 }
486
487 int32_t ret = proxy->RegistUserAuthSuccessEventListener(authType, listener);
488 if (ret != SUCCESS) {
489 IAM_LOGE("Regist userAuth success event listener failed");
490 return ret;
491 }
492
493 return SUCCESS;
494 }
495
UnRegistUserAuthSuccessEventListener(const sptr<AuthEventListenerInterface> & listener)496 int32_t UserAuthClientImpl::UnRegistUserAuthSuccessEventListener(const sptr<AuthEventListenerInterface> &listener)
497 {
498 IAM_LOGI("start");
499 if (!listener) {
500 IAM_LOGE("listener is nullptr");
501 return GENERAL_ERROR;
502 }
503
504 auto proxy = GetProxy();
505 if (!proxy) {
506 IAM_LOGE("proxy is nullptr");
507 return GENERAL_ERROR;
508 }
509
510 int32_t ret = proxy->UnRegistUserAuthSuccessEventListener(listener);
511 if (ret != SUCCESS) {
512 IAM_LOGE("unRegist userAuth success event listener failed");
513 return ret;
514 }
515
516 return SUCCESS;
517 }
518
PrepareRemoteAuth(const std::string & networkId,const std::shared_ptr<PrepareRemoteAuthCallback> & callback)519 int32_t UserAuthClientImpl::PrepareRemoteAuth(const std::string &networkId,
520 const std::shared_ptr<PrepareRemoteAuthCallback> &callback)
521 {
522 IAM_LOGI("start");
523 if (!callback) {
524 IAM_LOGE("prepare remote auth callback is nullptr");
525 return GENERAL_ERROR;
526 }
527
528 auto proxy = GetProxy();
529 if (!proxy) {
530 IAM_LOGE("proxy is nullptr");
531 callback->OnResult(GENERAL_ERROR);
532 return GENERAL_ERROR;
533 }
534
535 sptr<UserAuthCallbackInterface> wrapper(new (std::nothrow) UserAuthCallbackService(callback));
536 if (wrapper == nullptr) {
537 IAM_LOGE("failed to create wrapper");
538 callback->OnResult(GENERAL_ERROR);
539 return GENERAL_ERROR;
540 }
541
542 return proxy->PrepareRemoteAuth(networkId, wrapper);
543 }
544 } // namespace UserAuth
545 } // namespace UserIam
546 } // namespace OHOS
547