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 "executor.h"
17
18 #include <sstream>
19
20 #include "framework_executor_callback.h"
21 #include "iam_check.h"
22 #include "iam_common_defines.h"
23 #include "iam_logger.h"
24 #include "iam_mem.h"
25 #include "iam_para2str.h"
26 #include "iam_ptr.h"
27
28 #define LOG_TAG "USER_AUTH_EXECUTOR"
29
30 namespace OHOS {
31 namespace UserIam {
32 namespace UserAuth {
Executor(std::shared_ptr<ExecutorMgrWrapper> executorMgrWrapper,std::shared_ptr<IAuthExecutorHdi> executorHdi,uint16_t hdiId)33 Executor::Executor(std::shared_ptr<ExecutorMgrWrapper> executorMgrWrapper,
34 std::shared_ptr<IAuthExecutorHdi> executorHdi, uint16_t hdiId)
35 : executorMgrWrapper_(executorMgrWrapper),
36 executorHdi_(executorHdi),
37 hdiId_(hdiId)
38 {
39 auto hdi = executorHdi_;
40 IF_FALSE_LOGE_AND_RETURN(hdi != nullptr);
41 ExecutorInfo executorInfo = {};
42 IF_FALSE_LOGE_AND_RETURN(hdi->GetExecutorInfo(executorInfo) == ResultCode::SUCCESS);
43 authType_ = executorInfo.authType;
44 executorRole_ = executorInfo.executorRole;
45 std::ostringstream ss;
46 uint32_t combineExecutorId =
47 Common::CombineUint16ToUint32(hdiId_, static_cast<uint16_t>(executorInfo.executorSensorHint));
48 const uint32_t uint32HexWidth = 8;
49 ss << "Executor(Id:0x" << std::setfill('0') << std::setw(uint32HexWidth) << std::hex << combineExecutorId
50 << ", role:" << executorRole_ << ", authType:" << authType_ << ")";
51 description_ = ss.str();
52 }
53
OnHdiDisconnect()54 void Executor::OnHdiDisconnect()
55 {
56 IAM_LOGI("%{public}s start", GetDescription());
57 {
58 std::lock_guard<std::recursive_mutex> lock(mutex_);
59 executorHdi_ = nullptr;
60 }
61 RespondCallbackOnDisconnect();
62 UnregisterExecutorCallback();
63 }
64
Register()65 void Executor::Register()
66 {
67 IAM_LOGI("%{public}s start", GetDescription());
68 ExecutorInfo executorInfo = {};
69 auto hdi = GetExecutorHdi();
70 if (hdi == nullptr) {
71 IAM_LOGE("executorHdi_ is disconnected, skip framework ready process");
72 return;
73 }
74 ResultCode ret = hdi->GetExecutorInfo(executorInfo);
75 if (ret != ResultCode::SUCCESS) {
76 IAM_LOGE("Get executor info failed");
77 return;
78 }
79 RegisterExecutorCallback(executorInfo);
80 }
81
RegisterExecutorCallback(ExecutorInfo & executorInfo)82 void Executor::RegisterExecutorCallback(ExecutorInfo &executorInfo)
83 {
84 IAM_LOGI("%{public}s start", GetDescription());
85 std::lock_guard<std::recursive_mutex> lockRegister(registerMutex_);
86 uint32_t combineExecutorId =
87 Common::CombineUint16ToUint32(hdiId_, static_cast<uint16_t>(executorInfo.executorSensorHint));
88 executorInfo.executorSensorHint = combineExecutorId;
89 std::shared_ptr<ExecutorRegisterCallback> executorCallback = nullptr;
90 bool isExecutorRegistered = false;
91 {
92 std::lock_guard<std::recursive_mutex> lockCallback(mutex_);
93 if (executorCallback_ == nullptr) {
94 executorCallback_ = Common::MakeShared<FrameworkExecutorCallback>(weak_from_this());
95 IF_FALSE_LOGE_AND_RETURN(executorCallback_ != nullptr);
96 }
97 executorCallback = executorCallback_;
98
99 if (executorIndex_.has_value()) {
100 isExecutorRegistered = true;
101 }
102 }
103 if (isExecutorRegistered) {
104 IAM_LOGI("%{public}s executor already registered, try unregister", GetDescription());
105 UnregisterExecutorCallback();
106 }
107 IF_FALSE_LOGE_AND_RETURN(executorMgrWrapper_ != nullptr);
108 uint64_t executorIndex = executorMgrWrapper_->Register(executorInfo, executorCallback);
109 IF_FALSE_LOGE_AND_RETURN(executorIndex != INVALID_EXECUTOR_INDEX);
110 {
111 std::lock_guard<std::recursive_mutex> lockExecutorIndex(mutex_);
112 executorIndex_ = executorIndex;
113 }
114 IAM_LOGI("%{public}s register executor callback ok, executor index %{public}s", GetDescription(),
115 GET_MASKED_STRING(executorIndex).c_str());
116 }
117
UnregisterExecutorCallback()118 void Executor::UnregisterExecutorCallback()
119 {
120 IAM_LOGI("%{public}s start", GetDescription());
121 std::lock_guard<std::recursive_mutex> lockRegister(registerMutex_);
122 uint64_t executorIndex = 0;
123 {
124 std::lock_guard<std::recursive_mutex> lockExecutorIndex(mutex_);
125 if (!executorIndex_.has_value()) {
126 IAM_LOGI("not registered, no need unregister");
127 return;
128 }
129 executorIndex = executorIndex_.value();
130 executorIndex_ = std::nullopt;
131 }
132
133 IF_FALSE_LOGE_AND_RETURN(executorMgrWrapper_ != nullptr);
134 executorMgrWrapper_->Unregister(executorIndex);
135 IAM_LOGI("%{public}s unregister executor callback ok, executor index %{public}s", GetDescription(),
136 GET_MASKED_STRING(executorIndex).c_str());
137 }
138
AddCommand(std::shared_ptr<IAsyncCommand> command)139 void Executor::AddCommand(std::shared_ptr<IAsyncCommand> command)
140 {
141 IAM_LOGD("%{public}s start", GetDescription());
142 IF_FALSE_LOGE_AND_RETURN(command != nullptr);
143 std::lock_guard<std::recursive_mutex> lock(mutex_);
144 command2Respond_.insert(command);
145 }
146
RemoveCommand(std::shared_ptr<IAsyncCommand> command)147 void Executor::RemoveCommand(std::shared_ptr<IAsyncCommand> command)
148 {
149 IAM_LOGD("%{public}s start", GetDescription());
150 std::lock_guard<std::recursive_mutex> lock(mutex_);
151 command2Respond_.erase(command);
152 }
153
RespondCallbackOnDisconnect()154 void Executor::RespondCallbackOnDisconnect()
155 {
156 IAM_LOGI("%{public}s start", GetDescription());
157 std::set<std::shared_ptr<IAsyncCommand>> command2NotifyOnHdiDisconnect;
158 {
159 // cmd->OnHdiDisconnect will invoke RemoveCommand thus modify command2Respond_, make a copy before call
160 std::lock_guard<std::recursive_mutex> lock(mutex_);
161 command2NotifyOnHdiDisconnect =
162 std::set<std::shared_ptr<IAsyncCommand>>(command2Respond_.begin(), command2Respond_.end());
163 }
164
165 for (const auto &cmd : command2NotifyOnHdiDisconnect) {
166 if (cmd == nullptr) {
167 IAM_LOGE("cmd is null");
168 continue;
169 }
170 cmd->OnHdiDisconnect();
171 }
172 IAM_LOGI("success");
173 }
174
GetExecutorHdi()175 std::shared_ptr<IAuthExecutorHdi> Executor::GetExecutorHdi()
176 {
177 std::lock_guard<std::recursive_mutex> lock(mutex_);
178 return executorHdi_;
179 }
180
GetDescription()181 const char *Executor::GetDescription()
182 {
183 return description_.c_str();
184 }
185
GetAuthType() const186 int32_t Executor::GetAuthType() const
187 {
188 return authType_;
189 }
190
GetExecutorRole() const191 int32_t Executor::GetExecutorRole() const
192 {
193 return executorRole_;
194 }
195 } // namespace UserAuth
196 } // namespace UserIam
197 } // namespace OHOS
198