1 /*
2 * Copyright (c) 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
16 #include "form_render_mgr.h"
17
18 #include <mutex>
19
20 #include "fms_log_wrapper.h"
21 #include "form_ams_helper.h"
22 #include "form_bms_helper.h"
23 #include "form_cache_mgr.h"
24 #include "form_constants.h"
25 #include "form_data_mgr.h"
26 #include "form_event_report.h"
27 #include "form_host_interface.h"
28 #include "form_mgr_errors.h"
29 #include "form_sandbox_render_mgr_inner.h"
30 #include "form_supply_callback.h"
31 #include "form_task_mgr.h"
32 #include "form_trust_mgr.h"
33 #include "form_util.h"
34 #include "ipc_skeleton.h"
35 #include "os_account_manager.h"
36 #include "want.h"
37
38 namespace OHOS {
39 namespace AppExecFwk {
40 namespace {
41 constexpr size_t LAST_CONNECTION = 1;
42 }
43 using Want = OHOS::AAFwk::Want;
FormRenderMgr()44 FormRenderMgr::FormRenderMgr()
45 {
46 }
~FormRenderMgr()47 FormRenderMgr::~FormRenderMgr()
48 {
49 }
50
GetFormRenderState()51 void FormRenderMgr::GetFormRenderState()
52 {
53 // Check whether the account is authenticated.
54 bool isVerified = false;
55 AccountSA::OsAccountManager::IsOsAccountVerified(FormUtil::GetCurrentAccountId(), isVerified);
56 HILOG_INFO("isVerified:%{public}d, isVerified_:%{public}d, screen:%{public}d",
57 isVerified, isVerified_, isScreenUnlocked_);
58
59 std::lock_guard<std::mutex> lock(isVerifiedMutex_);
60 if (isVerified_ == isVerified) {
61 return;
62 }
63
64 isVerified_ = isVerified;
65 if (!isVerified) {
66 return;
67 }
68 if (!isScreenUnlocked_) {
69 PostOnUnlockTask();
70 }
71 ExecAcquireProviderTask();
72 }
73
GetIsVerified() const74 bool FormRenderMgr::GetIsVerified() const
75 {
76 HILOG_DEBUG("GetIsVerified");
77 std::lock_guard<std::mutex> lock(isVerifiedMutex_);
78 return isVerified_;
79 }
80
RenderForm( const FormRecord &formRecord, const WantParams &wantParams, const sptr<IRemoteObject> &hostToken)81 ErrCode FormRenderMgr::RenderForm(
82 const FormRecord &formRecord, const WantParams &wantParams, const sptr<IRemoteObject> &hostToken)
83 {
84 HILOG_INFO("formId:%{public}" PRId64 ", formUserId:%{public}d", formRecord.formId, formRecord.userId);
85 GetFormRenderState();
86 HILOG_INFO("the current user authentication status:%{public}d,%{public}d", isVerified_, isScreenUnlocked_);
87 if (formRecord.uiSyntax != FormType::ETS) {
88 return ERR_OK;
89 }
90 if (formRecord.formId <= 0) {
91 HILOG_ERROR("formId not greater than 0");
92 return ERR_APPEXECFWK_FORM_INVALID_PARAM;
93 }
94
95 Want want;
96 want.SetParams(wantParams);
97 std::string recordUid = std::to_string(formRecord.providerUserId) + formRecord.bundleName;
98 want.SetParam(Constants::FORM_SUPPLY_UID, recordUid);
99 {
100 std::lock_guard<std::mutex> lock(isVerifiedMutex_);
101 want.SetParam(Constants::FORM_RENDER_STATE, isVerified_ || isScreenUnlocked_);
102 }
103 if (formRecord.privacyLevel > 0) {
104 InitRenderInner(true, formRecord.userId);
105 return sandboxInners_[formRecord.userId]->RenderForm(formRecord, want, hostToken);
106 } else {
107 InitRenderInner(false, formRecord.userId);
108 return renderInners_[formRecord.userId]->RenderForm(formRecord, want, hostToken);
109 }
110 }
111
UpdateRenderingForm(int64_t formId, const FormProviderData &formProviderData, const WantParams &wantParams, bool mergeData)112 ErrCode FormRenderMgr::UpdateRenderingForm(int64_t formId, const FormProviderData &formProviderData,
113 const WantParams &wantParams, bool mergeData)
114 {
115 HILOG_INFO("update formId:%{public}" PRId64 ",%{public}zu", formId, formProviderData.GetDataString().length());
116
117 FormRecord formRecord;
118 bool isGetFormRecord = FormDataMgr::GetInstance().GetFormRecord(formId, formRecord);
119 if (!isGetFormRecord) {
120 HILOG_ERROR("get FormRecord fail, not exist such form, formId:%{public}" PRId64 "", formId);
121 return ERR_APPEXECFWK_FORM_NOT_EXIST_ID;
122 }
123 int32_t formUserId = formRecord.userId;
124 HILOG_INFO("update formUserId:%{public}d", formUserId);
125 if (formRecord.privacyLevel > 0) {
126 auto iter = sandboxInners_.find(formUserId);
127 if (iter == sandboxInners_.end()) {
128 return ERR_APPEXECFWK_FORM_INVALID_PARAM;
129 }
130 return iter->second->UpdateRenderingForm(formRecord, formProviderData, wantParams, mergeData);
131 } else {
132 auto iter = renderInners_.find(formUserId);
133 if (iter == renderInners_.end()) {
134 return ERR_APPEXECFWK_FORM_INVALID_PARAM;
135 }
136 return iter->second->UpdateRenderingForm(formRecord, formProviderData, wantParams, mergeData);
137 }
138 }
139
ReloadForm( const std::vector<FormRecord> &&formRecords, const std::string &bundleName, int32_t userId)140 ErrCode FormRenderMgr::ReloadForm(
141 const std::vector<FormRecord> &&formRecords, const std::string &bundleName, int32_t userId)
142 {
143 HILOG_INFO("userId:%{public}d", userId);
144 std::vector<FormRecord> sandboxRecords;
145 std::vector<FormRecord> normalRecords;
146 for (const auto &record : formRecords) {
147 if (record.privacyLevel > 0) {
148 sandboxRecords.emplace_back(record);
149 } else {
150 normalRecords.emplace_back(record);
151 }
152 }
153 auto renderIter = renderInners_.find(userId);
154 if (!normalRecords.empty() && renderIter != renderInners_.end()) {
155 renderIter->second->ReloadForm(std::move(normalRecords), bundleName, userId);
156 }
157 auto sandboxIter = sandboxInners_.find(userId);
158 if (!sandboxRecords.empty() && sandboxIter != sandboxInners_.end()) {
159 sandboxIter->second->ReloadForm(std::move(sandboxRecords), bundleName, userId);
160 }
161 return ERR_OK;
162 }
163
PostOnUnlockTask()164 void FormRenderMgr::PostOnUnlockTask()
165 {
166 int32_t userId = FormUtil::GetCurrentAccountId();
167 auto renderIter = renderInners_.find(userId);
168 if (renderIter != renderInners_.end()) {
169 renderIter->second->PostOnUnlockTask();
170 }
171 auto sandboxIter = sandboxInners_.find(userId);
172 if (sandboxIter != sandboxInners_.end()) {
173 sandboxIter->second->PostOnUnlockTask();
174 }
175 }
176
AddAcquireProviderFormInfoTask(std::function<void()> task)177 void FormRenderMgr::AddAcquireProviderFormInfoTask(std::function<void()> task)
178 {
179 HILOG_DEBUG("call");
180 std::lock_guard<std::mutex> lock(taskQueueMutex_);
181 taskQueue_.push(task);
182 }
183
ExecAcquireProviderTask()184 void FormRenderMgr::ExecAcquireProviderTask()
185 {
186 HILOG_INFO("start");
187 // start to execute asynchronous tasks in the queue
188 std::lock_guard<std::mutex> lock(taskQueueMutex_);
189 while (!taskQueue_.empty()) {
190 auto task = taskQueue_.front();
191 task();
192 taskQueue_.pop();
193 }
194 }
195
NotifyScreenOn()196 void FormRenderMgr::NotifyScreenOn()
197 {
198 int32_t userId = FormUtil::GetCurrentAccountId();
199 auto renderIter = renderInners_.find(userId);
200 if (renderIter != renderInners_.end()) {
201 renderIter->second->NotifyScreenOn();
202 }
203 auto sandboxIter = sandboxInners_.find(userId);
204 if (sandboxIter != sandboxInners_.end()) {
205 sandboxIter->second->NotifyScreenOn();
206 }
207 }
208
OnScreenUnlock()209 void FormRenderMgr::OnScreenUnlock()
210 {
211 HILOG_INFO("call. %{public}d,%{public}d", isVerified_, isScreenUnlocked_);
212 if (isScreenUnlocked_) {
213 return;
214 }
215
216 // el2 path maybe not unlocked, should not acquire data
217 std::lock_guard<std::mutex> lock(isVerifiedMutex_);
218 isScreenUnlocked_ = true;
219 if (!isVerified_) {
220 PostOnUnlockTask();
221 }
222 }
223
OnUnlock()224 void FormRenderMgr::OnUnlock()
225 {
226 HILOG_INFO("call. %{public}d,%{public}d", isVerified_, isScreenUnlocked_);
227 if (isVerified_) {
228 return;
229 }
230
231 {
232 std::lock_guard<std::mutex> lock(isVerifiedMutex_);
233 isVerified_ = true;
234 if (!isScreenUnlocked_) {
235 PostOnUnlockTask();
236 }
237 }
238 ExecAcquireProviderTask();
239 }
240
StopRenderingForm( int64_t formId, const FormRecord &formRecord, const std::string &compId, const sptr<IRemoteObject> &hostToken)241 ErrCode FormRenderMgr::StopRenderingForm(
242 int64_t formId, const FormRecord &formRecord, const std::string &compId, const sptr<IRemoteObject> &hostToken)
243 {
244 HILOG_INFO("formUserId:%{public}d", formRecord.userId);
245 if (formRecord.privacyLevel > 0) {
246 auto iter = sandboxInners_.find(formRecord.userId);
247 if (iter == sandboxInners_.end()) {
248 return ERR_APPEXECFWK_FORM_INVALID_PARAM;
249 }
250 return iter->second->StopRenderingForm(formId, formRecord, compId, hostToken);
251 } else {
252 auto iter = renderInners_.find(formRecord.userId);
253 if (iter == renderInners_.end()) {
254 return ERR_APPEXECFWK_FORM_INVALID_PARAM;
255 }
256 return iter->second->StopRenderingForm(formId, formRecord, compId, hostToken);
257 }
258 }
259
RenderFormCallback(int64_t formId, const Want &want)260 ErrCode FormRenderMgr::RenderFormCallback(int64_t formId, const Want &want)
261 {
262 HILOG_DEBUG("call");
263 return ERR_OK;
264 }
265
StopRenderingFormCallback(int64_t formId, const Want &want)266 ErrCode FormRenderMgr::StopRenderingFormCallback(int64_t formId, const Want &want)
267 {
268 int32_t callingUserId = IPCSkeleton::GetCallingUid() / Constants::CALLING_UID_TRANSFORM_DIVISOR;
269 HILOG_INFO("formId:%{public}" PRId64 ", callingUserId:%{public}d", formId, callingUserId);
270 auto renderIter = renderInners_.find(callingUserId);
271 if (renderIter != renderInners_.end()) {
272 renderIter->second->StopRenderingFormCallback(formId, want);
273 }
274 auto sandboxIter = sandboxInners_.find(callingUserId);
275 if (sandboxIter != sandboxInners_.end()) {
276 sandboxIter->second->StopRenderingFormCallback(formId, want);
277 }
278 return ERR_OK;
279 }
280
ReleaseRenderer(int64_t formId, const FormRecord &formRecord, const std::string &compId)281 ErrCode FormRenderMgr::ReleaseRenderer(int64_t formId, const FormRecord &formRecord, const std::string &compId)
282 {
283 HILOG_INFO("formId:%{public}" PRId64 ", formUserId:%{public}d", formId, formRecord.userId);
284 if (formRecord.privacyLevel > 0) {
285 auto iter = sandboxInners_.find(formRecord.userId);
286 if (iter == sandboxInners_.end()) {
287 return ERR_APPEXECFWK_FORM_INVALID_PARAM;
288 }
289 return iter->second->ReleaseRenderer(formId, formRecord, compId);
290 } else {
291 auto iter = renderInners_.find(formRecord.userId);
292 if (iter == renderInners_.end()) {
293 return ERR_APPEXECFWK_FORM_INVALID_PARAM;
294 }
295 return iter->second->ReleaseRenderer(formId, formRecord, compId);
296 }
297 }
298
AddConnection( int64_t formId, sptr<FormRenderConnection> connection, const FormRecord &formRecord)299 ErrCode FormRenderMgr::AddConnection(
300 int64_t formId, sptr<FormRenderConnection> connection, const FormRecord &formRecord)
301 {
302 HILOG_INFO("formUserId:%{public}d", formRecord.userId);
303 if (formRecord.privacyLevel > 0) {
304 auto iter = sandboxInners_.find(formRecord.userId);
305 if (iter == sandboxInners_.end()) {
306 return ERR_APPEXECFWK_FORM_INVALID_PARAM;
307 }
308 return iter->second->AddConnection(formId, connection);
309 } else {
310 auto iter = renderInners_.find(formRecord.userId);
311 if (iter == renderInners_.end()) {
312 return ERR_APPEXECFWK_FORM_INVALID_PARAM;
313 }
314 return iter->second->AddConnection(formId, connection);
315 }
316 }
317
RemoveConnection(int64_t formId, const FormRecord &formRecord)318 void FormRenderMgr::RemoveConnection(int64_t formId, const FormRecord &formRecord)
319 {
320 HILOG_INFO("formId:%{public}" PRId64 ", formUserId:%{public}d", formId, formRecord.userId);
321 if (formRecord.privacyLevel > 0) {
322 auto iter = sandboxInners_.find(formRecord.userId);
323 if (iter != sandboxInners_.end()) {
324 iter->second->RemoveConnection(formId);
325 }
326 } else {
327 auto iter = renderInners_.find(formRecord.userId);
328 if (iter != renderInners_.end()) {
329 iter->second->RemoveConnection(formId);
330 }
331 }
332 }
333
CleanFormHost(const sptr<IRemoteObject> &host, const int hostCallingUid)334 void FormRenderMgr::CleanFormHost(const sptr<IRemoteObject> &host, const int hostCallingUid)
335 {
336 int32_t hostUserId = hostCallingUid / Constants::CALLING_UID_TRANSFORM_DIVISOR;
337 if (hostUserId == 0) {
338 HILOG_WARN("hostUserId is 0,get current active userId ");
339 hostUserId = FormUtil::GetCurrentAccountId();
340 }
341 HILOG_INFO("hostUserId:%{public}d", hostUserId);
342 auto renderIter = renderInners_.find(hostUserId);
343 if (renderIter != renderInners_.end()) {
344 renderIter->second->CleanFormHost(host);
345 }
346 auto sandboxIter = sandboxInners_.find(hostUserId);
347 if (sandboxIter != sandboxInners_.end()) {
348 sandboxIter->second->CleanFormHost(host);
349 }
350 }
351
AddRenderDeathRecipient(const sptr<IRemoteObject> &remoteObject, const FormRecord &formRecord)352 void FormRenderMgr::AddRenderDeathRecipient(const sptr<IRemoteObject> &remoteObject, const FormRecord &formRecord)
353 {
354 HILOG_INFO("formUserId:%{public}d", formRecord.userId);
355 if (formRecord.privacyLevel > 0) {
356 auto iter = sandboxInners_.find(formRecord.userId);
357 if (iter != sandboxInners_.end()) {
358 iter->second->AddRenderDeathRecipient(remoteObject);
359 }
360 } else {
361 auto iter = renderInners_.find(formRecord.userId);
362 if (iter != renderInners_.end()) {
363 iter->second->AddRenderDeathRecipient(remoteObject);
364 }
365 }
366 }
367
OnRenderingBlock(const std::string &bundleName)368 void FormRenderMgr::OnRenderingBlock(const std::string &bundleName)
369 {
370 HILOG_INFO("bundleName:%{public}s", bundleName.c_str());
371 FormEventInfo eventInfo;
372 eventInfo.bundleName = bundleName;
373 FormEventReport::SendSecondFormEvent(
374 FormEventName::FORM_RENDER_BLOCK, HiSysEventType::FAULT, eventInfo);
375
376 FormTrustMgr::GetInstance().MarkTrustFlag(bundleName, false);
377
378 Want want;
379 want.SetElementName(Constants::FRS_BUNDLE_NAME, "ServiceExtension");
380 want.AddFlags(Want::FLAG_ABILITY_FORM_ENABLED);
381 FormAmsHelper::GetInstance().StopExtensionAbility(want);
382 }
383
IsNeedRender(int64_t formId)384 bool FormRenderMgr::IsNeedRender(int64_t formId)
385 {
386 FormRecord formRecord;
387 bool isGetFormRecord = FormDataMgr::GetInstance().GetFormRecord(formId, formRecord);
388 if (!isGetFormRecord) {
389 HILOG_ERROR("not exist such form, formId:%{public}" PRId64 "", formId);
390 return false;
391 }
392 if (formRecord.uiSyntax != FormType::ETS) {
393 HILOG_DEBUG("no need render, formId:%{public}" PRId64 "", formId);
394 return false;
395 }
396 return true;
397 }
398
HandleConnectFailed(int64_t formId, int32_t errorCode) const399 void FormRenderMgr::HandleConnectFailed(int64_t formId, int32_t errorCode) const
400 {
401 HILOG_ERROR("Connect render service failed, formId:%{public}" PRId64 ", errorCode:%{public}d",
402 formId, errorCode);
403 std::vector<sptr<IRemoteObject>> formHostObjs;
404 FormDataMgr::GetInstance().GetFormHostRemoteObj(formId, formHostObjs);
405 for (const auto &host : formHostObjs) {
406 auto hostClient = iface_cast<IFormHost>(host);
407 if (hostClient == nullptr) {
408 HILOG_ERROR("null hostClient");
409 continue;
410 }
411 hostClient->OnError(errorCode, "Connect FormRenderService failed");
412 }
413 }
414
IsRerenderForRenderServiceDied(int64_t formId)415 bool FormRenderMgr::IsRerenderForRenderServiceDied(int64_t formId)
416 {
417 int32_t rerenderCount = 0;
418 int32_t reSandboxRenderCount = 0;
419 FormRecord formRecord;
420 bool isGetFormRecord = FormDataMgr::GetInstance().GetFormRecord(formId, formRecord);
421 if (!isGetFormRecord) {
422 HILOG_ERROR("get FormRecord fail, not exist such form, formId:%{public}" PRId64 "", formId);
423 return ERR_APPEXECFWK_FORM_NOT_EXIST_ID;
424 }
425 HILOG_INFO("formId:%{public}" PRId64 ", formUserId:%{public}d", formId, formRecord.userId);
426 auto renderIter = renderInners_.find(formRecord.userId);
427 if (renderIter != renderInners_.end()) {
428 rerenderCount = renderIter->second->GetReRenderCount();
429 }
430 auto sandboxIter = sandboxInners_.find(formRecord.userId);
431 if (sandboxIter != sandboxInners_.end()) {
432 reSandboxRenderCount = sandboxIter->second->GetReRenderCount();
433 }
434 bool ret = IsNeedRender(formId) && (rerenderCount > 0 || reSandboxRenderCount > 0);
435 HILOG_DEBUG("Is need to rerender:%{public}d", ret);
436 return ret;
437 }
438
InitRenderInner(bool isSandbox, int32_t userId)439 void FormRenderMgr::InitRenderInner(bool isSandbox, int32_t userId)
440 {
441 HILOG_INFO("isSandbox:%{public}d userId:%{public}d", isSandbox, userId);
442 std::lock_guard<std::mutex> lock(renderInnerMutex_);
443 if (isSandbox) {
444 auto iter = sandboxInners_.find(userId);
445 if (iter == sandboxInners_.end()) {
446 auto formSandboxRenderMgr = std::make_shared<FormSandboxRenderMgrInner>();
447 formSandboxRenderMgr->SetUserId(userId);
448 sandboxInners_.emplace(userId, formSandboxRenderMgr);
449 }
450 } else {
451 auto iter = renderInners_.find(userId);
452 if (iter == renderInners_.end()) {
453 auto formRenderMgr = std::make_shared<FormRenderMgrInner>();
454 formRenderMgr->SetUserId(userId);
455 renderInners_.emplace(userId, formRenderMgr);
456 }
457 }
458 }
459
RecycleForms( const std::vector<int64_t> &formIds, const Want &want, const sptr<IRemoteObject> &remoteObjectOfHost)460 ErrCode FormRenderMgr::RecycleForms(
461 const std::vector<int64_t> &formIds, const Want &want, const sptr<IRemoteObject> &remoteObjectOfHost)
462 {
463 int callingUserId = want.GetIntParam(Constants::RECYCLE_FORMS_USER_ID, 0);
464 if (callingUserId == 0) {
465 callingUserId = IPCSkeleton::GetCallingUid() / Constants::CALLING_UID_TRANSFORM_DIVISOR;
466 HILOG_INFO("callingUserId is 0, update callingUserId:%{public}d", callingUserId);
467 }
468 auto renderIter = renderInners_.find(callingUserId);
469 if (renderIter != renderInners_.end()) {
470 return renderIter->second->RecycleForms(formIds, want, remoteObjectOfHost);
471 }
472 auto sandboxIter = sandboxInners_.find(callingUserId);
473 if (sandboxIter != sandboxInners_.end()) {
474 return sandboxIter->second->RecycleForms(formIds, want, remoteObjectOfHost);
475 }
476 return ERR_APPEXECFWK_FORM_RENDER_SERVICE_DIED;
477 }
478
RecoverForms(const std::vector<int64_t> &formIds, const WantParams &wantParams)479 ErrCode FormRenderMgr::RecoverForms(const std::vector<int64_t> &formIds, const WantParams &wantParams)
480 {
481 int32_t callingUserId = IPCSkeleton::GetCallingUid() / Constants::CALLING_UID_TRANSFORM_DIVISOR;
482 auto renderIter = renderInners_.find(callingUserId);
483 if (renderIter != renderInners_.end()) {
484 return renderIter->second->RecoverForms(formIds, wantParams);
485 }
486 auto sandboxIter = sandboxInners_.find(callingUserId);
487 if (sandboxIter != sandboxInners_.end()) {
488 return sandboxIter->second->RecoverForms(formIds, wantParams);
489 }
490 return ERR_APPEXECFWK_FORM_RENDER_SERVICE_DIED;
491 }
492
DisconnectAllRenderConnections(int userId)493 void FormRenderMgr::DisconnectAllRenderConnections(int userId)
494 {
495 HILOG_INFO("userId:%{public}d", userId);
496 auto renderIter = renderInners_.find(userId);
497 if (renderIter != renderInners_.end()) {
498 renderIter->second->DisconnectAllRenderConnections();
499 }
500 auto sandboxIter = sandboxInners_.find(userId);
501 if (sandboxIter != sandboxInners_.end()) {
502 sandboxIter->second->DisconnectAllRenderConnections();
503 }
504 }
505
RerenderAllFormsImmediate(int userId)506 void FormRenderMgr::RerenderAllFormsImmediate(int userId)
507 {
508 HILOG_INFO("userId:%{public}d", userId);
509 auto renderIter = renderInners_.find(userId);
510 if (renderIter != renderInners_.end()) {
511 renderIter->second->RerenderAllFormsImmediate();
512 }
513 auto sandboxIter = sandboxInners_.find(userId);
514 if (sandboxIter != sandboxInners_.end()) {
515 sandboxIter->second->RerenderAllFormsImmediate();
516 }
517 }
518 } // namespace AppExecFwk
519 } // namespace OHOS
520