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 /*
17 * 注意:
18 * - 注意点1:本文件原则上只处理与IPC无关的业务逻辑
19 * - 注意点2:This document, in principle, captures all exceptions.
20 * Prevent exceptions from spreading to insecure modules.
21 */
22 #include "module_ipc/service.h"
23
24 #include <algorithm>
25 #include <chrono>
26 #include <cerrno>
27 #include <cstddef>
28 #include <cstdint>
29 #include <cstring>
30 #include <regex>
31
32 #include <fcntl.h>
33 #include <iomanip>
34 #include <sys/stat.h>
35 #include <sys/types.h>
36 #include <sys/vfs.h>
37
38 #include <directory_ex.h>
39
40 #include "ability_manager_client.h"
41 #include "accesstoken_kit.h"
42 #include "b_anony/b_anony.h"
43 #include "b_error/b_error.h"
44 #include "b_error/b_excep_utils.h"
45 #include "b_file_info.h"
46 #include "b_json/b_json_cached_entity.h"
47 #include "b_jsonutil/b_jsonutil.h"
48 #include "b_ohos/startup/backup_para.h"
49 #include "b_process/b_multiuser.h"
50 #include "b_radar/b_radar.h"
51 #include "b_resources/b_constants.h"
52 #include "b_sa/b_sa_utils.h"
53 #include "b_utils/b_time.h"
54 #include "bundle_mgr_client.h"
55 #include "filemgmt_libhilog.h"
56 #include "hisysevent.h"
57 #include "hitrace_meter.h"
58 #include "ipc_skeleton.h"
59 #include "access_token.h"
60 #include "tokenid_kit.h"
61 #include "module_app_gallery/app_gallery_dispose_proxy.h"
62 #include "module_external/bms_adapter.h"
63 #include "module_external/sms_adapter.h"
64 #include "module_ipc/svc_backup_connection.h"
65 #include "module_ipc/svc_restore_deps_manager.h"
66 #include "module_notify/notify_work_service.h"
67 #include "parameter.h"
68 #include "parameters.h"
69 #include "system_ability_definition.h"
70
71 namespace OHOS::FileManagement::Backup {
72 using namespace std;
73
74 REGISTER_SYSTEM_ABILITY_BY_ID(Service, FILEMANAGEMENT_BACKUP_SERVICE_SA_ID, false);
75
76 namespace {
77 constexpr int32_t DEBUG_ID = 100;
78 constexpr int32_t INDEX = 3;
79 constexpr int32_t MS_1000 = 1000;
80 constexpr int DEFAULT_FD_SEND_RATE = 60;
81 const static string BROADCAST_TYPE = "broadcast";
82 const std::string FILE_BACKUP_EVENTS = "FILE_BACKUP_EVENTS";
83 const static string UNICAST_TYPE = "unicast";
84 const int32_t CONNECT_WAIT_TIME_S = 15;
85 const std::string BACKUPSERVICE_WORK_STATUS_KEY = "persist.backupservice.workstatus";
86 const std::string BACKUPSERVICE_WORK_STATUS_ON = "true";
87 const std::string BACKUPSERVICE_WORK_STATUS_OFF = "false";
88 const std::string BACKUP_PERMISSION = "ohos.permission.BACKUP";
89 const int32_t MAX_TRY_CLEAR_DISPOSE_NUM = 3;
90 } // namespace
91
92 /* Shell/Xts user id equal to 0/1, we need set default 100 */
GetUserIdDefault()93 static inline int32_t GetUserIdDefault()
94 {
95 auto [isDebug, debugId] = BackupPara().GetBackupDebugOverrideAccount();
96 if (isDebug && debugId > DEBUG_ID) {
97 return debugId;
98 }
99 auto multiuser = BMultiuser::ParseUid(IPCSkeleton::GetCallingUid());
100 HILOGI("GetUserIdDefault userId=%{public}d.", multiuser.userId);
101 if ((multiuser.userId == BConstants::SYSTEM_UID) || (multiuser.userId == BConstants::XTS_UID)) {
102 return BConstants::DEFAULT_USER_ID;
103 }
104 return multiuser.userId;
105 }
106
OnStartResRadarReport(const std::vector<std::string> & bundleNameList,int32_t stage)107 void OnStartResRadarReport(const std::vector<std::string> &bundleNameList, int32_t stage)
108 {
109 std::stringstream ss;
110 ss << "failedBundles:{";
111 for (auto &bundleName : bundleNameList) {
112 ss << bundleName << ", ";
113 }
114 ss << "}";
115 AppRadar::Info info("", "", ss.str());
116 AppRadar::GetInstance().RecordDefaultFuncRes(info, "Service::OnStart", GetUserIdDefault(),
117 static_cast<BizStageBackup>(stage), ERR_OK);
118 }
119
ClearFailedBundles()120 void Service::ClearFailedBundles()
121 {
122 std::lock_guard<std::mutex> lock(failedBundlesLock_);
123 failedBundles_.clear();
124 }
125
UpdateFailedBundles(const std::string & bundleName,BundleTaskInfo taskInfo)126 void Service::UpdateFailedBundles(const std::string &bundleName, BundleTaskInfo taskInfo)
127 {
128 std::lock_guard<std::mutex> lock(failedBundlesLock_);
129 failedBundles_[bundleName] = taskInfo;
130 }
131
BundleBeginRadarReport(const std::string & bundleName,const ErrCode errCode,const IServiceReverse::Scenario scenario)132 void Service::BundleBeginRadarReport(const std::string &bundleName, const ErrCode errCode,
133 const IServiceReverse::Scenario scenario)
134 {
135 if (errCode == ERR_OK || errCode == BError(BError::Codes::SA_BOOT_EXT_FAIL).GetCode()) {
136 return;
137 }
138 BundleTaskInfo taskInfo;
139 taskInfo.reportTime = TimeUtils::GetCurrentTime();
140 taskInfo.errCode = errCode;
141 UpdateFailedBundles(bundleName, taskInfo);
142 AppRadar::Info info(bundleName, "", "");
143 if (scenario == IServiceReverse::Scenario::RESTORE) {
144 AppRadar::GetInstance().RecordRestoreFuncRes(info, "Service::BundleBeginRadarReport",
145 GetUserIdDefault(), BizStageRestore::BIZ_STAGE_APPEND_BUNDLES_FAIL, errCode);
146 } else if (scenario == IServiceReverse::Scenario::BACKUP) {
147 AppRadar::GetInstance().RecordBackupFuncRes(info, "Service::BundleBeginRadarReport",
148 GetUserIdDefault(), BizStageBackup::BIZ_STAGE_APPEND_BUNDLES_FAIL, errCode);
149 }
150 }
151
BundleEndRadarReport(const std::string & bundleName,const ErrCode errCode,const IServiceReverse::Scenario scenario)152 void Service::BundleEndRadarReport(const std::string &bundleName, const ErrCode errCode,
153 const IServiceReverse::Scenario scenario)
154 {
155 if (errCode == ERR_OK) {
156 successBundlesNum_++;
157 return;
158 }
159 BundleTaskInfo taskInfo;
160 taskInfo.reportTime = TimeUtils::GetCurrentTime();
161 taskInfo.errCode = errCode;
162 UpdateFailedBundles(bundleName, taskInfo);
163 AppRadar::Info info(bundleName, "", "");
164 if (scenario == IServiceReverse::Scenario::RESTORE) {
165 AppRadar::GetInstance().RecordRestoreFuncRes(info, "Service::BundleEndRadarReport",
166 GetUserIdDefault(), BizStageRestore::BIZ_STAGE_EXECU_FAIL, errCode);
167 } else if (scenario == IServiceReverse::Scenario::BACKUP) {
168 AppRadar::GetInstance().RecordBackupFuncRes(info, "Service::BundleEndRadarReport",
169 GetUserIdDefault(), BizStageBackup::BIZ_STAGE_EXECU_FAIL, errCode);
170 }
171 }
172
FileReadyRadarReport(const std::string & bundleName,const std::string & fileName,const ErrCode errCode,const IServiceReverse::Scenario scenario)173 void Service::FileReadyRadarReport(const std::string &bundleName, const std::string &fileName, const ErrCode errCode,
174 const IServiceReverse::Scenario scenario)
175 {
176 if (errCode == ERR_OK) {
177 return;
178 }
179 std::string fileNameReport = std::string("fileName:\"") + GetAnonyPath(fileName) + "\"";
180 AppRadar::Info info(bundleName, "", fileNameReport);
181 if (scenario == IServiceReverse::Scenario::RESTORE) {
182 AppRadar::GetInstance().RecordRestoreFuncRes(info, "Service::FileReadyRadarReport",
183 GetUserIdDefault(), BizStageRestore::BIZ_STAGE_GET_FILE_HANDLE_FAIL, errCode);
184 } else if (scenario == IServiceReverse::Scenario::BACKUP) {
185 AppRadar::GetInstance().RecordBackupFuncRes(info, "Service::FileReadyRadarReport",
186 GetUserIdDefault(), BizStageBackup::BIZ_STAGE_DO_BACKUP, errCode);
187 }
188 }
189
ExtensionConnectFailRadarReport(const std::string & bundleName,const ErrCode errCode,const IServiceReverse::Scenario scenario)190 void Service::ExtensionConnectFailRadarReport(const std::string &bundleName, const ErrCode errCode,
191 const IServiceReverse::Scenario scenario)
192 {
193 std::stringstream ss;
194 ss << "errCode:" << errCode;
195 AppRadar::Info info(bundleName, "", ss.str());
196 if (scenario == IServiceReverse::Scenario::RESTORE) {
197 AppRadar::GetInstance().RecordRestoreFuncRes(info, "Service::ExtensionConnectFailRadarReport",
198 GetUserIdDefault(), BizStageRestore::BIZ_STAGE_CONNECT_EXTENSION_FAIL,
199 BError(BError::Codes::SA_BOOT_EXT_FAIL).GetCode());
200 } else if (scenario == IServiceReverse::Scenario::BACKUP) {
201 AppRadar::GetInstance().RecordBackupFuncRes(info, "Service::ExtensionConnectFailRadarReport",
202 GetUserIdDefault(), BizStageBackup::BIZ_STAGE_CONNECT_EXTENSION_FAIL,
203 BError(BError::Codes::SA_BOOT_EXT_FAIL).GetCode());
204 }
205 }
206
OnStart()207 void Service::OnStart()
208 {
209 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
210 HILOGI("SA OnStart Begin.");
211 std::vector<std::string> bundleNameList;
212 if (disposal_ != nullptr) {
213 bundleNameList = disposal_->GetBundleNameFromConfigFile();
214 }
215 std::vector<std::string> residualBundleNameList;
216 if (clearRecorder_ != nullptr) {
217 residualBundleNameList = clearRecorder_->GetAllClearBundleRecords();
218 }
219 if (!bundleNameList.empty() || !residualBundleNameList.empty()) {
220 if (!bundleNameList.empty()) {
221 OnStartResRadarReport(bundleNameList,
222 static_cast<int32_t>(BizStageBackup::BIZ_STAGE_ONSTART_DISPOSE));
223 }
224 if (!residualBundleNameList.empty()) {
225 OnStartResRadarReport(residualBundleNameList,
226 static_cast<int32_t>(BizStageBackup::BIZ_STAGE_ONSTART_RESIDUAL));
227 }
228 session_->Active(
229 {
230 .clientToken = IPCSkeleton::GetCallingTokenID(),
231 .scenario = IServiceReverse::Scenario::CLEAN,
232 .clientProxy = nullptr,
233 .userId = GetUserIdDefault(),
234 },
235 true);
236 isCleanService_.store(true);
237 HILOGE("SA OnStart, cleaning up backup data");
238 }
239 bool res = SystemAbility::Publish(sptr(this));
240 if (sched_ != nullptr) {
241 sched_->StartTimer();
242 }
243 ClearDisposalOnSaStart();
244 auto ret = AppendBundlesClearSession(residualBundleNameList);
245 if (isCleanService_.load() && ret) {
246 isCleanService_.store(false);
247 StopAll(nullptr, true);
248 }
249 HILOGI("SA OnStart End, res = %{public}d", res);
250 }
251
OnStop()252 void Service::OnStop()
253 {
254 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
255 HILOGI("SA OnStop Begin.");
256 int32_t oldMemoryParaSize = BConstants::DEFAULT_VFS_CACHE_PRESSURE;
257 if (session_ != nullptr) {
258 oldMemoryParaSize = session_->GetMemParaCurSize();
259 }
260 StorageMgrAdapter::UpdateMemPara(oldMemoryParaSize);
261 HILOGI("SA OnStop End.");
262 }
263
GetLocalCapabilities()264 UniqueFd Service::GetLocalCapabilities()
265 {
266 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
267 try {
268 /*
269 Only called by restore app before InitBackupSession,
270 so there must be set init userId.
271 */
272 HILOGI("Begin");
273 if (session_ == nullptr || isCleanService_.load()) {
274 HILOGE("GetLocalCapabilities error, session is empty.");
275 return UniqueFd(-EPERM);
276 }
277 session_->IncreaseSessionCnt(__PRETTY_FUNCTION__);
278 session_->SetSessionUserId(GetUserIdDefault());
279 VerifyCaller();
280 string path = BConstants::GetSaBundleBackupRootDir(session_->GetSessionUserId());
281 BExcepUltils::VerifyPath(path, false);
282 CreateDirIfNotExist(path);
283 UniqueFd fd(open(path.data(), O_TMPFILE | O_RDWR, S_IRUSR | S_IWUSR));
284 if (fd < 0) {
285 HILOGE("Failed to open config file = %{private}s, err = %{public}d", path.c_str(), errno);
286 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
287 return UniqueFd(-EPERM);
288 }
289 BJsonCachedEntity<BJsonEntityCaps> cachedEntity(std::move(fd));
290
291 auto cache = cachedEntity.Structuralize();
292
293 cache.SetSystemFullName(GetOSFullName());
294 cache.SetDeviceType(GetDeviceType());
295 auto bundleInfos = BundleMgrAdapter::GetFullBundleInfos(session_->GetSessionUserId());
296 cache.SetBundleInfos(bundleInfos);
297 cachedEntity.Persist();
298 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
299 HILOGI("End");
300 return move(cachedEntity.GetFd());
301 } catch (const BError &e) {
302 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
303 HILOGE("GetLocalCapabilities failed, errCode = %{public}d", e.GetCode());
304 return UniqueFd(-e.GetCode());
305 } catch (const exception &e) {
306 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
307 HILOGI("Catched an unexpected low-level exception %{public}s", e.what());
308 return UniqueFd(-EPERM);
309 } catch (...) {
310 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
311 HILOGI("Unexpected exception");
312 return UniqueFd(-EPERM);
313 }
314 }
315
StopAll(const wptr<IRemoteObject> & obj,bool force)316 void Service::StopAll(const wptr<IRemoteObject> &obj, bool force)
317 {
318 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
319 std::lock_guard<std::mutex> lock(failedBundlesLock_);
320 int32_t fail_cnt = failedBundles_.size();
321 int32_t totalBundles = fail_cnt + successBundlesNum_.load();
322 if (totalBundles != 0) {
323 int32_t result = 0;
324 if (fail_cnt != 0) {
325 result = BError::BackupErrorCode::E_TASKFAIL;
326 }
327 std::stringstream ss;
328 ss << "successBundleNum:" << successBundlesNum_ << "," << "failedBundleNum:" <<
329 fail_cnt << "," << "failedBundles:{";
330 for (auto &failBundle : failedBundles_) {
331 ss << "\"" << failBundle.first << "\":" << "{errCode:" << failBundle.second.errCode << ","
332 << "reportTime:" << failBundle.second.reportTime << "},";
333 }
334 ss << "}";
335 string resultInfo = ss.str();
336 AppRadar::StatInfo statInfo("", resultInfo);
337 IServiceReverse::Scenario scenario = session_->GetScenario();
338 AppRadar::GetInstance().RecordStatisticRes(statInfo, GetUserIdDefault(), scenario,
339 successBundlesNum_.load(), fail_cnt, result);
340 }
341 failedBundles_.clear();
342 successBundlesNum_ = 0;
343 session_->Deactive(obj, force);
344 }
345
PermissionCheckFailRadar(const std::string & info,const std::string & func)346 static inline void PermissionCheckFailRadar(const std::string &info, const std::string &func)
347 {
348 std::string funcPos = "Service::";
349 AppRadar::Info resInfo("", "", info);
350 AppRadar::GetInstance().RecordDefaultFuncRes(resInfo, funcPos.append(func),
351 GetUserIdDefault(), BizStageBackup::BIZ_STAGE_PERMISSION_CHECK_FAIL,
352 BError(BError::Codes::SA_REFUSED_ACT).GetCode());
353 }
354
VerifyCallerAndGetCallerName()355 string Service::VerifyCallerAndGetCallerName()
356 {
357 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
358 uint32_t tokenCaller = IPCSkeleton::GetCallingTokenID();
359 int tokenType = Security::AccessToken::AccessTokenKit::GetTokenType(tokenCaller);
360 if (tokenType == Security::AccessToken::ATokenTypeEnum::TOKEN_HAP) {
361 Security::AccessToken::HapTokenInfo hapTokenInfo;
362 if (Security::AccessToken::AccessTokenKit::GetHapTokenInfo(tokenCaller, hapTokenInfo) != 0) {
363 PermissionCheckFailRadar("Get hap token info failed", "VerifyCallerAndGetCallerName");
364 throw BError(BError::Codes::SA_INVAL_ARG, "Get hap token info failed");
365 }
366 std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(hapTokenInfo.bundleName,
367 hapTokenInfo.instIndex);
368 session_->VerifyBundleName(bundleNameIndexInfo);
369 return bundleNameIndexInfo;
370 } else {
371 string str = to_string(tokenCaller);
372 HILOGE("tokenID = %{private}s", GetAnonyString(str).c_str());
373 std::string info = string("Invalid token type").append(to_string(tokenType)).append(string("\"}"));
374 PermissionCheckFailRadar(info, "VerifyCallerAndGetCallerName");
375 throw BError(BError::Codes::SA_INVAL_ARG, string("Invalid token type ").append(to_string(tokenType)));
376 }
377 }
378
VerifyCaller()379 void Service::VerifyCaller()
380 {
381 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
382 uint32_t tokenCaller = IPCSkeleton::GetCallingTokenID();
383 int tokenType = Security::AccessToken::AccessTokenKit::GetTokenType(tokenCaller);
384 switch (tokenType) {
385 case Security::AccessToken::ATokenTypeEnum::TOKEN_NATIVE: { /* Update Service */
386 if (Security::AccessToken::AccessTokenKit::VerifyAccessToken(tokenCaller, BACKUP_PERMISSION) !=
387 Security::AccessToken::PermissionState::PERMISSION_GRANTED) {
388 std::string info = "Permission denied, token type is " + to_string(tokenType);
389 PermissionCheckFailRadar(info, "VerifyCaller");
390 throw BError(BError::Codes::SA_REFUSED_ACT,
391 string("Permission denied, token type is ").append(to_string(tokenType)));
392 }
393 break;
394 }
395 case Security::AccessToken::ATokenTypeEnum::TOKEN_HAP: {
396 if (Security::AccessToken::AccessTokenKit::VerifyAccessToken(tokenCaller, BACKUP_PERMISSION) !=
397 Security::AccessToken::PermissionState::PERMISSION_GRANTED) {
398 std::string info = "Permission denied, token type is " + to_string(tokenType);
399 PermissionCheckFailRadar(info, "VerifyCaller");
400 throw BError(BError::Codes::SA_REFUSED_ACT,
401 string("Permission denied, token type is ").append(to_string(tokenType)));
402 }
403 uint64_t fullTokenId = OHOS::IPCSkeleton::GetCallingFullTokenID();
404 if (!Security::AccessToken::TokenIdKit::IsSystemAppByFullTokenID(fullTokenId)) {
405 std::string info = "Permission denied, token type is " + to_string(tokenType);
406 PermissionCheckFailRadar(info, "VerifyCaller");
407 throw BError(BError::Codes::SA_REFUSED_ACT,
408 string("Permission denied, token type is ").append(to_string(tokenType)));
409 }
410 break;
411 }
412 case Security::AccessToken::ATokenTypeEnum::TOKEN_SHELL:
413 if (IPCSkeleton::GetCallingUid() != BConstants::SYSTEM_UID) {
414 std::string info = "invalid calling uid";
415 PermissionCheckFailRadar(info, "VerifyCaller");
416 throw BError(BError::Codes::SA_REFUSED_ACT, "Calling uid is invalid");
417 }
418 break;
419 default:
420 std::string info = "Permission denied, token type is " + to_string(tokenType);
421 PermissionCheckFailRadar(info, "VerifyCaller");
422 throw BError(BError::Codes::SA_REFUSED_ACT, string("Invalid token type ").append(to_string(tokenType)));
423 break;
424 }
425 }
426
VerifyCaller(IServiceReverse::Scenario scenario)427 void Service::VerifyCaller(IServiceReverse::Scenario scenario)
428 {
429 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
430 session_->VerifyCallerAndScenario(IPCSkeleton::GetCallingTokenID(), scenario);
431 VerifyCaller();
432 }
433
InitRestoreSession(sptr<IServiceReverse> remote)434 ErrCode Service::InitRestoreSession(sptr<IServiceReverse> remote)
435 {
436 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
437 try {
438 VerifyCaller();
439 ErrCode errCode = session_->Active({
440 .clientToken = IPCSkeleton::GetCallingTokenID(),
441 .scenario = IServiceReverse::Scenario::RESTORE,
442 .clientProxy = remote,
443 .userId = GetUserIdDefault(),
444 });
445 if (errCode == 0) {
446 ClearFailedBundles();
447 successBundlesNum_ = 0;
448 }
449 return errCode;
450 } catch (const BError &e) {
451 StopAll(nullptr, true);
452 return e.GetCode();
453 } catch (const exception &e) {
454 HILOGI("Catched an unexpected low-level exception %{public}s", e.what());
455 return EPERM;
456 } catch (...) {
457 HILOGI("Unexpected exception");
458 return EPERM;
459 }
460 }
461
InitBackupSession(sptr<IServiceReverse> remote)462 ErrCode Service::InitBackupSession(sptr<IServiceReverse> remote)
463 {
464 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
465 try {
466 VerifyCaller();
467 int32_t oldSize = StorageMgrAdapter::UpdateMemPara(BConstants::BACKUP_VFS_CACHE_PRESSURE);
468 HILOGE("InitBackupSession oldSize %{public}d", oldSize);
469 session_->SetMemParaCurSize(oldSize);
470 ErrCode errCode = session_->Active({
471 .clientToken = IPCSkeleton::GetCallingTokenID(),
472 .scenario = IServiceReverse::Scenario::BACKUP,
473 .clientProxy = remote,
474 .userId = GetUserIdDefault(),
475 });
476 if (errCode == 0) {
477 ClearFailedBundles();
478 successBundlesNum_ = 0;
479 }
480 return errCode;
481 } catch (const BError &e) {
482 StopAll(nullptr, true);
483 return e.GetCode();
484 } catch (const exception &e) {
485 HILOGI("Catched an unexpected low-level exception %{public}s", e.what());
486 return EPERM;
487 } catch (...) {
488 HILOGI("Unexpected exception");
489 return EPERM;
490 }
491 }
492
Start()493 ErrCode Service::Start()
494 {
495 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
496 try {
497 VerifyCaller(session_->GetScenario());
498 session_->Start();
499 OnStartSched();
500 return BError(BError::Codes::OK);
501 } catch (const BError &e) {
502 HILOGE("Failde to Start");
503 return e.GetCode();
504 }
505 }
506
SpecialVersion(const string & versionName)507 static bool SpecialVersion(const string &versionName)
508 {
509 string versionNameFlag = versionName.substr(0, versionName.find_first_of(BConstants::VERSION_NAME_SEPARATOR_CHAR));
510 auto iter = find_if(BConstants::DEFAULT_VERSION_NAMES_VEC.begin(), BConstants::DEFAULT_VERSION_NAMES_VEC.end(),
511 [&versionNameFlag](const auto &version) { return version == versionNameFlag; });
512 if (iter != BConstants::DEFAULT_VERSION_NAMES_VEC.end()) {
513 return true;
514 }
515 return false;
516 }
517
OnBundleStarted(BError error,sptr<SvcSessionManager> session,const BundleName & bundleName)518 void Service::OnBundleStarted(BError error, sptr<SvcSessionManager> session, const BundleName &bundleName)
519 {
520 IServiceReverse::Scenario scenario = session->GetScenario();
521 if (scenario == IServiceReverse::Scenario::RESTORE && BackupPara().GetBackupOverrideIncrementalRestore() &&
522 session->ValidRestoreDataType(RestoreTypeEnum::RESTORE_DATA_WAIT_SEND)) {
523 session->GetServiceReverseProxy()->IncrementalRestoreOnBundleStarted(error, bundleName);
524 } else if (scenario == IServiceReverse::Scenario::RESTORE) {
525 session->GetServiceReverseProxy()->RestoreOnBundleStarted(error, bundleName);
526 }
527 BundleBeginRadarReport(bundleName, error.GetCode(), scenario);
528 }
529
GetRestoreBundleNames(UniqueFd fd,sptr<SvcSessionManager> session,const vector<BundleName> & bundleNames)530 static vector<BJsonEntityCaps::BundleInfo> GetRestoreBundleNames(UniqueFd fd,
531 sptr<SvcSessionManager> session,
532 const vector<BundleName> &bundleNames)
533 {
534 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
535 // BundleMgrAdapter::GetBundleInfos可能耗时
536 auto restoreInfos = BundleMgrAdapter::GetBundleInfos(bundleNames, session->GetSessionUserId());
537 BJsonCachedEntity<BJsonEntityCaps> cachedEntity(move(fd));
538 auto cache = cachedEntity.Structuralize();
539 auto bundleInfos = cache.GetBundleInfos();
540 if (!bundleInfos.size()) {
541 throw BError(BError::Codes::SA_INVAL_ARG, "Json entity caps is empty");
542 }
543 vector<BJsonEntityCaps::BundleInfo> restoreBundleInfos {};
544 for (auto &restoreInfo : restoreInfos) {
545 if (SAUtils::IsSABundleName(restoreInfo.name)) {
546 BJsonEntityCaps::BundleInfo info = {.name = restoreInfo.name,
547 .appIndex = restoreInfo.appIndex,
548 .versionCode = restoreInfo.versionCode,
549 .versionName = restoreInfo.versionName,
550 .spaceOccupied = restoreInfo.spaceOccupied,
551 .allToBackup = restoreInfo.allToBackup,
552 .fullBackupOnly = restoreInfo.fullBackupOnly,
553 .extensionName = restoreInfo.extensionName,
554 .restoreDeps = restoreInfo.restoreDeps};
555 restoreBundleInfos.emplace_back(info);
556 continue;
557 }
558 auto it = find_if(bundleInfos.begin(), bundleInfos.end(), [&restoreInfo](const auto &obj) {
559 return obj.name == restoreInfo.name && obj.appIndex == restoreInfo.appIndex;
560 });
561 if (it == bundleInfos.end()) {
562 HILOGE("Bundle not need restore, bundleName is %{public}s.", restoreInfo.name.c_str());
563 continue;
564 }
565 BJsonEntityCaps::BundleInfo info = {.name = (*it).name,
566 .appIndex = (*it).appIndex,
567 .versionCode = (*it).versionCode,
568 .versionName = (*it).versionName,
569 .spaceOccupied = (*it).spaceOccupied,
570 .allToBackup = (*it).allToBackup,
571 .fullBackupOnly = (*it).fullBackupOnly,
572 .extensionName = restoreInfo.extensionName,
573 .restoreDeps = restoreInfo.restoreDeps};
574 restoreBundleInfos.emplace_back(info);
575 }
576 return restoreBundleInfos;
577 }
578
HandleExceptionOnAppendBundles(sptr<SvcSessionManager> session,const vector<BundleName> & appendBundleNames,const vector<BundleName> & restoreBundleNames)579 void Service::HandleExceptionOnAppendBundles(sptr<SvcSessionManager> session,
580 const vector<BundleName> &appendBundleNames, const vector<BundleName> &restoreBundleNames)
581 {
582 if (appendBundleNames.size() != restoreBundleNames.size()) {
583 HILOGE("AppendBundleNames not equal restoreBundleNames, appendBundleNames size:%{public}zu,"
584 "restoreBundleNames size:%{public}zu", appendBundleNames.size(), restoreBundleNames.size());
585 for (auto bundleName : appendBundleNames) {
586 auto it = find_if(restoreBundleNames.begin(), restoreBundleNames.end(),
587 [&bundleName](const auto &obj) { return obj == bundleName; });
588 if (it == restoreBundleNames.end()) {
589 HILOGE("AppendBundles failed, bundleName = %{public}s.", bundleName.c_str());
590 OnBundleStarted(BError(BError::Codes::SA_BUNDLE_INFO_EMPTY), session, bundleName);
591 }
592 }
593 }
594 }
595
AppendBundlesRestoreSession(UniqueFd fd,const vector<BundleName> & bundleNames,const std::vector<std::string> & bundleInfos,RestoreTypeEnum restoreType,int32_t userId)596 ErrCode Service::AppendBundlesRestoreSession(UniqueFd fd, const vector<BundleName> &bundleNames,
597 const std::vector<std::string> &bundleInfos, RestoreTypeEnum restoreType, int32_t userId)
598 {
599 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
600 try {
601 if (session_ == nullptr || isCleanService_.load()) {
602 HILOGE("Init Incremental backup session error, session is empty");
603 return BError(BError::Codes::SA_INVAL_ARG);
604 }
605 session_->IncreaseSessionCnt(__PRETTY_FUNCTION__);
606 session_->SetImplRestoreType(restoreType);
607 if (userId != DEFAULT_INVAL_VALUE) { /* multi user scenario */
608 session_->SetSessionUserId(userId);
609 } else {
610 session_->SetSessionUserId(GetUserIdDefault());
611 }
612 VerifyCaller(IServiceReverse::Scenario::RESTORE);
613 std::vector<std::string> bundleNamesOnly;
614 std::map<std::string, bool> isClearDataFlags;
615 std::map<std::string, std::vector<BJsonUtil::BundleDetailInfo>> bundleNameDetailMap =
616 BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly,
617 session_->GetSessionUserId(), isClearDataFlags);
618 auto restoreInfos = GetRestoreBundleNames(move(fd), session_, bundleNames);
619 auto restoreBundleNames = SvcRestoreDepsManager::GetInstance().GetRestoreBundleNames(restoreInfos, restoreType);
620 HandleExceptionOnAppendBundles(session_, bundleNames, restoreBundleNames);
621 if (restoreBundleNames.empty()) {
622 HILOGE("AppendBundlesRestoreSession failed, restoreBundleNames is empty.");
623 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
624 return BError(BError::Codes::OK);
625 }
626 session_->AppendBundles(restoreBundleNames);
627 SetCurrentSessProperties(restoreInfos, restoreBundleNames, bundleNameDetailMap,
628 isClearDataFlags, restoreType);
629 OnStartSched();
630 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
631 HILOGI("End");
632 return BError(BError::Codes::OK);
633 } catch (const BError &e) {
634 HILOGE("Catch exception");
635 HandleExceptionOnAppendBundles(session_, bundleNames, {});
636 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
637 return e.GetCode();
638 } catch (...) {
639 HILOGE("Unexpected exception");
640 HandleExceptionOnAppendBundles(session_, bundleNames, {});
641 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
642 return EPERM;
643 }
644 }
645
SetCurrentSessProperties(std::vector<BJsonEntityCaps::BundleInfo> & restoreBundleInfos,std::vector<std::string> & restoreBundleNames,RestoreTypeEnum restoreType)646 void Service::SetCurrentSessProperties(std::vector<BJsonEntityCaps::BundleInfo> &restoreBundleInfos,
647 std::vector<std::string> &restoreBundleNames, RestoreTypeEnum restoreType)
648 {
649 HILOGI("Start");
650 for (auto restoreInfo : restoreBundleInfos) {
651 auto it = find_if(restoreBundleNames.begin(), restoreBundleNames.end(), [&restoreInfo](const auto &bundleName) {
652 std::string bundleNameIndex = BJsonUtil::BuildBundleNameIndexInfo(restoreInfo.name, restoreInfo.appIndex);
653 return bundleName == bundleNameIndex;
654 });
655 if (it == restoreBundleNames.end()) {
656 throw BError(BError::Codes::SA_BUNDLE_INFO_EMPTY, "Can't find bundle name");
657 }
658 HILOGI("bundleName: %{public}s, extensionName: %{public}s", restoreInfo.name.c_str(),
659 restoreInfo.extensionName.c_str());
660 std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(restoreInfo.name, restoreInfo.appIndex);
661 if ((!restoreInfo.allToBackup && !SpecialVersion(restoreInfo.versionName)) ||
662 (restoreInfo.extensionName.empty() && !SAUtils::IsSABundleName(restoreInfo.name))) {
663 OnBundleStarted(BError(BError::Codes::SA_FORBID_BACKUP_RESTORE), session_, bundleNameIndexInfo);
664 session_->RemoveExtInfo(bundleNameIndexInfo);
665 continue;
666 }
667 session_->SetBundleRestoreType(bundleNameIndexInfo, restoreType);
668 session_->SetBundleVersionCode(bundleNameIndexInfo, restoreInfo.versionCode);
669 session_->SetBundleVersionName(bundleNameIndexInfo, restoreInfo.versionName);
670 session_->SetBundleDataSize(bundleNameIndexInfo, restoreInfo.spaceOccupied);
671 if (BundleMgrAdapter::IsUser0BundleName(bundleNameIndexInfo, session_->GetSessionUserId())) {
672 SendUserIdToApp(bundleNameIndexInfo, session_->GetSessionUserId());
673 }
674 session_->SetBackupExtName(bundleNameIndexInfo, restoreInfo.extensionName);
675 session_->SetIsReadyLaunch(bundleNameIndexInfo);
676 }
677 HILOGI("End");
678 }
679
AppendBundlesRestoreSession(UniqueFd fd,const vector<BundleName> & bundleNames,RestoreTypeEnum restoreType,int32_t userId)680 ErrCode Service::AppendBundlesRestoreSession(UniqueFd fd,
681 const vector<BundleName> &bundleNames,
682 RestoreTypeEnum restoreType,
683 int32_t userId)
684 {
685 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
686 try {
687 if (session_ == nullptr || isCleanService_.load()) {
688 HILOGE("Init Incremental backup session error, session is empty");
689 return BError(BError::Codes::SA_INVAL_ARG);
690 }
691 session_->IncreaseSessionCnt(__PRETTY_FUNCTION__);
692 session_->SetImplRestoreType(restoreType);
693 if (userId != DEFAULT_INVAL_VALUE) { /* multi user scenario */
694 session_->SetSessionUserId(userId);
695 } else {
696 session_->SetSessionUserId(GetUserIdDefault());
697 }
698 VerifyCaller(IServiceReverse::Scenario::RESTORE);
699 auto restoreInfos = GetRestoreBundleNames(move(fd), session_, bundleNames);
700 auto restoreBundleNames = SvcRestoreDepsManager::GetInstance().GetRestoreBundleNames(restoreInfos, restoreType);
701 HandleExceptionOnAppendBundles(session_, bundleNames, restoreBundleNames);
702 if (restoreBundleNames.empty()) {
703 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
704 HILOGW("RestoreBundleNames is empty.");
705 return BError(BError::Codes::OK);
706 }
707 session_->AppendBundles(restoreBundleNames);
708 SetCurrentSessProperties(restoreInfos, restoreBundleNames, restoreType);
709 OnStartSched();
710 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
711 return BError(BError::Codes::OK);
712 } catch (const BError &e) {
713 HILOGE("Catch exception");
714 HandleExceptionOnAppendBundles(session_, bundleNames, {});
715 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
716 return e.GetCode();
717 } catch (...) {
718 HILOGE("Unexpected exception");
719 HandleExceptionOnAppendBundles(session_, bundleNames, {});
720 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
721 return EPERM;
722 }
723 }
724
SetCurrentSessProperties(std::vector<BJsonEntityCaps::BundleInfo> & restoreBundleInfos,std::vector<std::string> & restoreBundleNames,std::map<std::string,std::vector<BJsonUtil::BundleDetailInfo>> & bundleNameDetailMap,std::map<std::string,bool> & isClearDataFlags,RestoreTypeEnum restoreType)725 void Service::SetCurrentSessProperties(std::vector<BJsonEntityCaps::BundleInfo> &restoreBundleInfos,
726 std::vector<std::string> &restoreBundleNames,
727 std::map<std::string, std::vector<BJsonUtil::BundleDetailInfo>> &bundleNameDetailMap,
728 std::map<std::string, bool> &isClearDataFlags, RestoreTypeEnum restoreType)
729 {
730 HILOGI("Start");
731 for (auto restoreInfo : restoreBundleInfos) {
732 auto it = find_if(restoreBundleNames.begin(), restoreBundleNames.end(),
733 [&restoreInfo](const auto &bundleName) {
734 std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(restoreInfo.name,
735 restoreInfo.appIndex);
736 return bundleName == bundleNameIndexInfo;
737 });
738 if (it == restoreBundleNames.end()) {
739 throw BError(BError::Codes::SA_BUNDLE_INFO_EMPTY, "Can't find bundle name");
740 }
741 HILOGD("bundleName: %{public}s, extensionName: %{public}s", restoreInfo.name.c_str(),
742 restoreInfo.extensionName.c_str());
743 std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(restoreInfo.name, restoreInfo.appIndex);
744 if ((!restoreInfo.allToBackup && !SpecialVersion(restoreInfo.versionName)) ||
745 (restoreInfo.extensionName.empty() && !SAUtils::IsSABundleName(restoreInfo.name))) {
746 OnBundleStarted(BError(BError::Codes::SA_FORBID_BACKUP_RESTORE), session_, bundleNameIndexInfo);
747 session_->RemoveExtInfo(bundleNameIndexInfo);
748 continue;
749 }
750 session_->SetBundleRestoreType(bundleNameIndexInfo, restoreType);
751 session_->SetBundleVersionCode(bundleNameIndexInfo, restoreInfo.versionCode);
752 session_->SetBundleVersionName(bundleNameIndexInfo, restoreInfo.versionName);
753 session_->SetBundleDataSize(bundleNameIndexInfo, restoreInfo.spaceOccupied);
754 auto iter = isClearDataFlags.find(bundleNameIndexInfo);
755 if (iter != isClearDataFlags.end()) {
756 session_->SetClearDataFlag(bundleNameIndexInfo, iter->second);
757 }
758 BJsonUtil::BundleDetailInfo broadCastInfo;
759 BJsonUtil::BundleDetailInfo uniCastInfo;
760 bool broadCastRet = BJsonUtil::FindBundleInfoByName(bundleNameDetailMap, bundleNameIndexInfo, BROADCAST_TYPE,
761 broadCastInfo);
762 if (broadCastRet) {
763 bool notifyRet =
764 DelayedSingleton<NotifyWorkService>::GetInstance()->NotifyBundleDetail(broadCastInfo);
765 HILOGI("Publish event end, notify result is:%{public}d", notifyRet);
766 }
767 bool uniCastRet = BJsonUtil::FindBundleInfoByName(bundleNameDetailMap, bundleNameIndexInfo, UNICAST_TYPE,
768 uniCastInfo);
769 if (uniCastRet) {
770 HILOGI("current bundle, unicast info:%{public}s", GetAnonyString(uniCastInfo.detail).c_str());
771 session_->SetBackupExtInfo(bundleNameIndexInfo, uniCastInfo.detail);
772 }
773 session_->SetBackupExtName(bundleNameIndexInfo, restoreInfo.extensionName);
774 session_->SetIsReadyLaunch(bundleNameIndexInfo);
775 }
776 HILOGI("End");
777 }
778
AppendBundlesBackupSession(const vector<BundleName> & bundleNames)779 ErrCode Service::AppendBundlesBackupSession(const vector<BundleName> &bundleNames)
780 {
781 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
782 try {
783 if (session_ == nullptr || isCleanService_.load()) {
784 HILOGE("Init Incremental backup session error, session is empty");
785 return BError(BError::Codes::SA_INVAL_ARG);
786 }
787 session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); // BundleMgrAdapter::GetBundleInfos可能耗时
788 VerifyCaller(IServiceReverse::Scenario::BACKUP);
789 auto bundleDetails = MakeDetailList(bundleNames);
790 auto backupInfos = BundleMgrAdapter::GetBundleInfosForAppend(bundleDetails, session_->GetSessionUserId());
791 std::vector<std::string> supportBackupNames = GetSupportBackupBundleNames(backupInfos, false);
792 session_->AppendBundles(supportBackupNames);
793 SetCurrentBackupSessProperties(supportBackupNames, session_->GetSessionUserId(), backupInfos, false);
794 OnStartSched();
795 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
796 return BError(BError::Codes::OK);
797 } catch (const BError &e) {
798 HILOGE("Failed, errCode = %{public}d", e.GetCode());
799 HandleExceptionOnAppendBundles(session_, bundleNames, {});
800 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
801 return e.GetCode();
802 } catch (const exception &e) {
803 HILOGE("Catched an unexpected low-level exception %{public}s", e.what());
804 HandleExceptionOnAppendBundles(session_, bundleNames, {});
805 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
806 return EPERM;
807 } catch (...) {
808 HILOGE("Unexpected exception");
809 HandleExceptionOnAppendBundles(session_, bundleNames, {});
810 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
811 return EPERM;
812 }
813 }
814
AppendBundlesDetailsBackupSession(const vector<BundleName> & bundleNames,const vector<std::string> & bundleInfos)815 ErrCode Service::AppendBundlesDetailsBackupSession(const vector<BundleName> &bundleNames,
816 const vector<std::string> &bundleInfos)
817 {
818 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
819 try {
820 if (session_ == nullptr || isCleanService_.load()) {
821 HILOGE("Init Incremental backup session error, session is empty");
822 return BError(BError::Codes::SA_INVAL_ARG);
823 }
824 session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); // BundleMgrAdapter::GetBundleInfos可能耗时
825 VerifyCaller(IServiceReverse::Scenario::BACKUP);
826 std::vector<std::string> bundleNamesOnly;
827 std::map<std::string, bool> isClearDataFlags;
828 std::map<std::string, std::vector<BJsonUtil::BundleDetailInfo>> bundleNameDetailMap =
829 BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly,
830 session_->GetSessionUserId(), isClearDataFlags);
831 auto bundleDetails = MakeDetailList(bundleNames);
832 auto backupInfos = BundleMgrAdapter::GetBundleInfosForAppend(bundleDetails, session_->GetSessionUserId());
833 std::vector<std::string> supportBackupNames = GetSupportBackupBundleNames(backupInfos, false);
834 session_->AppendBundles(supportBackupNames);
835 HandleCurGroupBackupInfos(backupInfos, bundleNameDetailMap, isClearDataFlags);
836 OnStartSched();
837 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
838 return BError(BError::Codes::OK);
839 } catch (const BError &e) {
840 HILOGE("Failed, errCode = %{public}d", e.GetCode());
841 HandleExceptionOnAppendBundles(session_, bundleNames, {});
842 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
843 return e.GetCode();
844 } catch(...) {
845 HILOGE("Unexpected exception");
846 HandleExceptionOnAppendBundles(session_, bundleNames, {});
847 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
848 return EPERM;
849 }
850 }
851
HandleCurGroupBackupInfos(std::vector<BJsonEntityCaps::BundleInfo> & backupInfos,std::map<std::string,std::vector<BJsonUtil::BundleDetailInfo>> & bundleNameDetailMap,std::map<std::string,bool> & isClearDataFlags)852 void Service::HandleCurGroupBackupInfos(std::vector<BJsonEntityCaps::BundleInfo> &backupInfos,
853 std::map<std::string, std::vector<BJsonUtil::BundleDetailInfo>> &bundleNameDetailMap,
854 std::map<std::string, bool> &isClearDataFlags)
855 {
856 for (auto &info : backupInfos) {
857 HILOGI("Current backupInfo bundleName:%{public}s, extName:%{public}s, appIndex:%{public}d",
858 info.name.c_str(), info.extensionName.c_str(), info.appIndex);
859 std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(info.name, info.appIndex);
860 SetCurrentSessProperties(info, isClearDataFlags, bundleNameIndexInfo);
861 BJsonUtil::BundleDetailInfo uniCastInfo;
862 if (BJsonUtil::FindBundleInfoByName(bundleNameDetailMap, bundleNameIndexInfo, UNICAST_TYPE, uniCastInfo)) {
863 HILOGI("current bundle:%{public}s, unicast info:%{public}s, unicast info size:%{public}zu",
864 bundleNameIndexInfo.c_str(), GetAnonyString(uniCastInfo.detail).c_str(), uniCastInfo.detail.size());
865 session_->SetBackupExtInfo(bundleNameIndexInfo, uniCastInfo.detail);
866 }
867 session_->SetBackupExtName(bundleNameIndexInfo, info.extensionName);
868 session_->SetIsReadyLaunch(bundleNameIndexInfo);
869 }
870 }
871
ServiceResultReport(const std::string restoreRetInfo,BackupRestoreScenario sennario,ErrCode errCode)872 ErrCode Service::ServiceResultReport(const std::string restoreRetInfo,
873 BackupRestoreScenario sennario, ErrCode errCode)
874 {
875 string callerName = "";
876 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
877 try {
878 callerName = VerifyCallerAndGetCallerName();
879 SendEndAppGalleryNotify(callerName);
880 if (sennario == BackupRestoreScenario::FULL_RESTORE) {
881 session_->GetServiceReverseProxy()->RestoreOnResultReport(restoreRetInfo, callerName, errCode);
882 NotifyCloneBundleFinish(callerName, sennario);
883 } else if (sennario == BackupRestoreScenario::INCREMENTAL_RESTORE) {
884 session_->GetServiceReverseProxy()->IncrementalRestoreOnResultReport(restoreRetInfo, callerName, errCode);
885 NotifyCloneBundleFinish(callerName, sennario);
886 } else if (sennario == BackupRestoreScenario::FULL_BACKUP) {
887 session_->GetServiceReverseProxy()->BackupOnResultReport(restoreRetInfo, callerName);
888 } else if (sennario == BackupRestoreScenario::INCREMENTAL_BACKUP) {
889 session_->GetServiceReverseProxy()->IncrementalBackupOnResultReport(restoreRetInfo, callerName);
890 }
891 return BError(BError::Codes::OK);
892 } catch (const BError &e) {
893 NotifyCloneBundleFinish(callerName, sennario);
894 return e.GetCode(); // 任意异常产生,终止监听该任务
895 } catch (const exception &e) {
896 NotifyCloneBundleFinish(callerName, sennario);
897 HILOGI("Catched an unexpected low-level exception %{public}s", e.what());
898 return EPERM;
899 } catch (...) {
900 NotifyCloneBundleFinish(callerName, sennario);
901 HILOGI("Unexpected exception");
902 return EPERM;
903 }
904 }
905
SAResultReport(const std::string bundleName,const std::string restoreRetInfo,const ErrCode errCode,const BackupRestoreScenario sennario)906 ErrCode Service::SAResultReport(const std::string bundleName, const std::string restoreRetInfo,
907 const ErrCode errCode, const BackupRestoreScenario sennario)
908 {
909 if (sennario == BackupRestoreScenario::FULL_RESTORE) {
910 session_->GetServiceReverseProxy()->RestoreOnResultReport(restoreRetInfo, bundleName);
911 } else if (sennario == BackupRestoreScenario::INCREMENTAL_RESTORE) {
912 session_->GetServiceReverseProxy()->IncrementalRestoreOnResultReport(restoreRetInfo, bundleName);
913 } else if (sennario == BackupRestoreScenario::FULL_BACKUP) {
914 session_->GetServiceReverseProxy()->BackupOnResultReport(restoreRetInfo, bundleName);
915 session_->GetServiceReverseProxy()->BackupOnBundleFinished(errCode, bundleName);
916 } else if (sennario == BackupRestoreScenario::INCREMENTAL_BACKUP) {
917 session_->GetServiceReverseProxy()->IncrementalBackupOnResultReport(restoreRetInfo, bundleName);
918 }
919 if (sennario == BackupRestoreScenario::FULL_RESTORE || sennario == BackupRestoreScenario::INCREMENTAL_RESTORE) {
920 BundleEndRadarReport(bundleName, errCode, IServiceReverse::Scenario::RESTORE);
921 } else if (sennario == BackupRestoreScenario::FULL_BACKUP ||
922 sennario == BackupRestoreScenario::INCREMENTAL_BACKUP) {
923 BundleEndRadarReport(bundleName, errCode, IServiceReverse::Scenario::BACKUP);
924 }
925 return SADone(errCode, bundleName);
926 }
927
NotifyCloneBundleFinish(std::string bundleName,const BackupRestoreScenario sennario)928 void Service::NotifyCloneBundleFinish(std::string bundleName, const BackupRestoreScenario sennario)
929 {
930 try {
931 if (sennario != BackupRestoreScenario::FULL_RESTORE &&
932 sennario != BackupRestoreScenario::INCREMENTAL_RESTORE) {
933 return;
934 }
935 if (session_->OnBundleFileReady(bundleName)) {
936 std::shared_ptr<ExtensionMutexInfo> mutexPtr = GetExtensionMutex(bundleName);
937 if (mutexPtr == nullptr) {
938 HILOGE("extension mutex ptr is nullptr");
939 return;
940 }
941 std::lock_guard<std::mutex> lock(mutexPtr->callbackMutex);
942 auto backUpConnection = session_->GetExtConnection(bundleName);
943 if (backUpConnection == nullptr) {
944 throw BError(BError::Codes::SA_INVAL_ARG, "backUpConnection is empty");
945 }
946 auto proxy = backUpConnection->GetBackupExtProxy();
947 if (!proxy) {
948 throw BError(BError::Codes::SA_INVAL_ARG, "Extension backup Proxy is empty");
949 }
950 proxy->HandleClear();
951 session_->StopFwkTimer(bundleName);
952 session_->StopExtTimer(bundleName);
953 backUpConnection->DisconnectBackupExtAbility();
954 ClearSessionAndSchedInfo(bundleName);
955 }
956 RemoveExtensionMutex(bundleName);
957 OnAllBundlesFinished(BError(BError::Codes::OK));
958 } catch (...) {
959 HILOGI("Unexpected exception");
960 ReleaseOnException();
961 }
962 }
963
LaunchBackupSAExtension(const BundleName & bundleName)964 ErrCode Service::LaunchBackupSAExtension(const BundleName &bundleName)
965 {
966 string extInfo = session_->GetBackupExtInfo(bundleName);
967 IServiceReverse::Scenario scenario = session_->GetScenario();
968 if (SAUtils::IsSABundleName(bundleName)) {
969 auto saBackUpConnection = session_->GetSAExtConnection(bundleName);
970 std::shared_ptr<SABackupConnection> saConnection = saBackUpConnection.lock();
971 if (saConnection == nullptr) {
972 HILOGE("lock sa connection ptr is nullptr");
973 return BError(BError::Codes::SA_INVAL_ARG);
974 }
975 if (scenario == IServiceReverse::Scenario::BACKUP) {
976 return saConnection->ConnectBackupSAExt(bundleName, BConstants::EXTENSION_BACKUP, extInfo);
977 } else if (scenario == IServiceReverse::Scenario::RESTORE) {
978 return saConnection->ConnectBackupSAExt(bundleName, BConstants::EXTENSION_RESTORE, extInfo);
979 }
980 }
981 return BError(BError::Codes::OK);
982 }
983
GetFileHandle(const string & bundleName,const string & fileName)984 ErrCode Service::GetFileHandle(const string &bundleName, const string &fileName)
985 {
986 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
987 try {
988 VerifyCaller(IServiceReverse::Scenario::RESTORE);
989
990 bool updateRes = SvcRestoreDepsManager::GetInstance().UpdateToRestoreBundleMap(bundleName, fileName);
991 if (updateRes) {
992 return BError(BError::Codes::OK);
993 }
994 auto action = session_->GetServiceSchedAction(bundleName);
995 if (action == BConstants::ServiceSchedAction::RUNNING) {
996 auto backUpConnection = session_->GetExtConnection(bundleName);
997 if (backUpConnection == nullptr) {
998 HILOGE("GetFileHandle error, backUpConnection is empty");
999 return BError(BError::Codes::SA_INVAL_ARG);
1000 }
1001 auto proxy = backUpConnection->GetBackupExtProxy();
1002 if (!proxy) {
1003 HILOGE("GetFileHandle error, Extension backup Proxy is empty");
1004 return BError(BError::Codes::SA_INVAL_ARG);
1005 }
1006 int32_t errCode = 0;
1007 UniqueFd fd = proxy->GetFileHandle(fileName, errCode);
1008 if (errCode != ERR_OK) {
1009 AppRadar::Info info (bundleName, "", "");
1010 AppRadar::GetInstance().RecordRestoreFuncRes(info, "Service::GetFileHandle", GetUserIdDefault(),
1011 BizStageRestore::BIZ_STAGE_GET_FILE_HANDLE_FAIL, errCode);
1012 }
1013 session_->GetServiceReverseProxy()->RestoreOnFileReady(bundleName, fileName, move(fd), errCode);
1014 FileReadyRadarReport(bundleName, fileName, errCode, IServiceReverse::Scenario::RESTORE);
1015 } else {
1016 session_->SetExtFileNameRequest(bundleName, fileName);
1017 }
1018 return BError(BError::Codes::OK);
1019 } catch (const BError &e) {
1020 return e.GetCode();
1021 } catch (const exception &e) {
1022 HILOGI("Catched an unexpected low-level exception %{public}s", e.what());
1023 return EPERM;
1024 } catch (...) {
1025 HILOGI("Unexpected exception");
1026 return EPERM;
1027 }
1028 }
1029
OnBackupExtensionDied(const string && bundleName,bool isSecondCalled)1030 void Service::OnBackupExtensionDied(const string &&bundleName, bool isSecondCalled)
1031 {
1032 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1033 try {
1034 string callName = move(bundleName);
1035 HILOGE("Backup <%{public}s> Extension Process Died", callName.c_str());
1036 session_->VerifyBundleName(callName);
1037 // 重新连接清理缓存
1038 HILOGI("Clear backup extension data, bundleName: %{public}s", callName.c_str());
1039 ExtConnectDied(callName);
1040 } catch (...) {
1041 HILOGE("Unexpected exception, bundleName: %{public}s", bundleName.c_str());
1042 ExtConnectDied(bundleName);
1043 return;
1044 }
1045 }
1046
ExtConnectDied(const string & callName)1047 void Service::ExtConnectDied(const string &callName)
1048 {
1049 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1050 try {
1051 HILOGI("Begin, bundleName: %{public}s", callName.c_str());
1052 std::shared_ptr<ExtensionMutexInfo> mutexPtr = GetExtensionMutex(callName);
1053 if (mutexPtr == nullptr) {
1054 HILOGE("extension mutex ptr is nullptr");
1055 return;
1056 }
1057 std::lock_guard<std::mutex> lock(mutexPtr->callbackMutex);
1058 /* Clear Timer */
1059 session_->StopFwkTimer(callName);
1060 session_->StopExtTimer(callName);
1061 auto backUpConnection = session_->GetExtConnection(callName);
1062 if (backUpConnection != nullptr && backUpConnection->IsExtAbilityConnected()) {
1063 backUpConnection->DisconnectBackupExtAbility();
1064 }
1065 session_->SetServiceSchedAction(callName, BConstants::ServiceSchedAction::CLEAN);
1066 auto ret = LaunchBackupExtension(callName);
1067 if (ret) {
1068 /* Clear Session before notice client finish event */
1069 ClearSessionAndSchedInfo(callName);
1070 }
1071 /* Notice Client Ext Ability Process Died */
1072 NoticeClientFinish(callName, BError(BError::Codes::EXT_ABILITY_DIED));
1073 } catch (...) {
1074 HILOGE("Unexpected exception, bundleName: %{public}s", callName.c_str());
1075 ClearSessionAndSchedInfo(callName);
1076 NoticeClientFinish(callName, BError(BError::Codes::EXT_ABILITY_DIED));
1077 }
1078 RemoveExtensionMutex(callName);
1079 }
1080
ExtStart(const string & bundleName)1081 void Service::ExtStart(const string &bundleName)
1082 {
1083 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1084 try {
1085 HILOGE("begin ExtStart, bundle name:%{public}s", bundleName.data());
1086 if (SAUtils::IsSABundleName(bundleName)) {
1087 BackupSA(bundleName);
1088 return;
1089 }
1090 if (IncrementalBackup(bundleName)) {
1091 return;
1092 }
1093 IServiceReverse::Scenario scenario = session_->GetScenario();
1094 auto backUpConnection = session_->GetExtConnection(bundleName);
1095 if (backUpConnection == nullptr) {
1096 throw BError(BError::Codes::SA_INVAL_ARG, "ExtStart bundle task error, backUpConnection is empty");
1097 }
1098 auto proxy = backUpConnection->GetBackupExtProxy();
1099 if (!proxy) {
1100 throw BError(BError::Codes::SA_INVAL_ARG, "ExtStart bundle task error, Extension backup Proxy is empty");
1101 }
1102 std::string name = bundleName;
1103 proxy->UpdateFdSendRate(name, DEFAULT_FD_SEND_RATE);
1104 if (scenario == IServiceReverse::Scenario::BACKUP) {
1105 auto ret = proxy->HandleBackup(session_->GetClearDataFlag(bundleName));
1106 session_->GetServiceReverseProxy()->BackupOnBundleStarted(ret, bundleName);
1107 BundleBeginRadarReport(bundleName, ret, scenario);
1108 if (ret) {
1109 ClearSessionAndSchedInfo(bundleName);
1110 NoticeClientFinish(bundleName, BError(BError::Codes::SA_INVAL_ARG));
1111 }
1112 return;
1113 } else if (scenario != IServiceReverse::Scenario::RESTORE) {
1114 throw BError(BError::Codes::SA_INVAL_ARG, "Failed to scenario");
1115 }
1116 auto ret = proxy->HandleRestore(session_->GetClearDataFlag(bundleName));
1117 session_->GetServiceReverseProxy()->RestoreOnBundleStarted(ret, bundleName);
1118 BundleBeginRadarReport(bundleName, ret, scenario);
1119 auto fileNameVec = session_->GetExtFileNameRequest(bundleName);
1120 for (auto &fileName : fileNameVec) {
1121 int32_t errCode = 0;
1122 UniqueFd fd = proxy->GetFileHandle(fileName, errCode);
1123 session_->GetServiceReverseProxy()->RestoreOnFileReady(bundleName, fileName, move(fd), errCode);
1124 FileReadyRadarReport(bundleName, fileName, errCode, scenario);
1125 }
1126 } catch (...) {
1127 HILOGI("Unexpected exception, bundleName: %{public}s", bundleName.c_str());
1128 ClearSessionAndSchedInfo(bundleName);
1129 NoticeClientFinish(bundleName, BError(BError::Codes::SA_INVAL_ARG));
1130 }
1131 }
1132
Dump(int fd,const vector<u16string> & args)1133 int Service::Dump(int fd, const vector<u16string> &args)
1134 {
1135 if (fd < 0) {
1136 HILOGI("HiDumper handle invalid");
1137 return -1;
1138 }
1139
1140 session_->DumpInfo(fd, args);
1141 return 0;
1142 }
1143
ReportOnExtConnectFailed(const IServiceReverse::Scenario scenario,const std::string & bundleName,const ErrCode ret)1144 void Service::ReportOnExtConnectFailed(const IServiceReverse::Scenario scenario,
1145 const std::string &bundleName, const ErrCode ret)
1146 {
1147 try {
1148 if (session_ == nullptr) {
1149 HILOGE("Report extConnectfailed error, session info is empty");
1150 return;
1151 }
1152 if (scenario == IServiceReverse::Scenario::BACKUP && session_->GetIsIncrementalBackup()) {
1153 session_->GetServiceReverseProxy()->IncrementalBackupOnBundleStarted(ret, bundleName);
1154 BundleBeginRadarReport(bundleName, ret, scenario);
1155 } else if (scenario == IServiceReverse::Scenario::RESTORE &&
1156 BackupPara().GetBackupOverrideIncrementalRestore() &&
1157 session_->ValidRestoreDataType(RestoreTypeEnum::RESTORE_DATA_WAIT_SEND)) {
1158 session_->GetServiceReverseProxy()->IncrementalRestoreOnBundleStarted(ret, bundleName);
1159 BundleBeginRadarReport(bundleName, ret, scenario);
1160 DisposeErr disposeErr = AppGalleryDisposeProxy::GetInstance()->EndRestore(bundleName);
1161 HILOGI("ExtConnectFailed EndRestore, code=%{public}d, bundleName=%{public}s", disposeErr,
1162 bundleName.c_str());
1163 } else if (scenario == IServiceReverse::Scenario::BACKUP) {
1164 session_->GetServiceReverseProxy()->BackupOnBundleStarted(ret, bundleName);
1165 BundleBeginRadarReport(bundleName, ret, scenario);
1166 } else if (scenario == IServiceReverse::Scenario::RESTORE) {
1167 session_->GetServiceReverseProxy()->RestoreOnBundleStarted(ret, bundleName);
1168 BundleBeginRadarReport(bundleName, ret, scenario);
1169 DisposeErr disposeErr = AppGalleryDisposeProxy::GetInstance()->EndRestore(bundleName);
1170 HILOGI("ExtConnectFailed EndRestore, code=%{public}d, bundleName=%{public}s", disposeErr,
1171 bundleName.c_str());
1172 }
1173 } catch (...) {
1174 HILOGE("Report extConnectfailed error");
1175 }
1176 }
1177
ExtConnectFailed(const string & bundleName,ErrCode ret)1178 void Service::ExtConnectFailed(const string &bundleName, ErrCode ret)
1179 {
1180 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1181 IServiceReverse::Scenario scenario = IServiceReverse::Scenario::UNDEFINED;
1182 try {
1183 HILOGE("begin %{public}s", bundleName.data());
1184 scenario = session_->GetScenario();
1185 ReportOnExtConnectFailed(scenario, bundleName, ret);
1186 ClearSessionAndSchedInfo(bundleName);
1187 NoticeClientFinish(bundleName, BError(BError::Codes::EXT_ABILITY_DIED));
1188 return;
1189 } catch (const BError &e) {
1190 return;
1191 } catch (const exception &e) {
1192 HILOGI("Catched an unexpected low-level exception %{public}s", e.what());
1193 return;
1194 } catch (...) {
1195 HILOGI("Unexpected exception");
1196 return;
1197 }
1198 }
1199
NoticeClientFinish(const string & bundleName,ErrCode errCode)1200 void Service::NoticeClientFinish(const string &bundleName, ErrCode errCode)
1201 {
1202 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1203 HILOGI("begin %{public}s", bundleName.c_str());
1204 try {
1205 SendEndAppGalleryNotify(bundleName);
1206 auto scenario = session_->GetScenario();
1207 if (scenario == IServiceReverse::Scenario::BACKUP && session_->GetIsIncrementalBackup()) {
1208 session_->GetServiceReverseProxy()->IncrementalBackupOnBundleFinished(errCode, bundleName);
1209 } else if (scenario == IServiceReverse::Scenario::RESTORE &&
1210 BackupPara().GetBackupOverrideIncrementalRestore() &&
1211 session_->ValidRestoreDataType(RestoreTypeEnum::RESTORE_DATA_WAIT_SEND)) {
1212 session_->GetServiceReverseProxy()->IncrementalRestoreOnBundleFinished(errCode, bundleName);
1213 } else if (scenario == IServiceReverse::Scenario::BACKUP) {
1214 session_->GetServiceReverseProxy()->BackupOnBundleFinished(errCode, bundleName);
1215 } else if (scenario == IServiceReverse::Scenario::RESTORE) {
1216 session_->GetServiceReverseProxy()->RestoreOnBundleFinished(errCode, bundleName);
1217 };
1218 BundleEndRadarReport(bundleName, errCode, scenario);
1219 /* If all bundle ext process finish, notice client. */
1220 OnAllBundlesFinished(BError(BError::Codes::OK));
1221 } catch(const BError &e) {
1222 ReleaseOnException();
1223 } catch (...) {
1224 ReleaseOnException();
1225 HILOGI("Unexpected exception");
1226 return;
1227 }
1228 }
1229
ExtConnectDone(string bundleName)1230 void Service::ExtConnectDone(string bundleName)
1231 {
1232 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1233 try {
1234 HILOGE("begin %{public}s", bundleName.data());
1235 auto timeoutCallback = TimeOutCallback(wptr<Service>(this), bundleName);
1236 auto scenario = session_->GetScenario();
1237 if (scenario == IServiceReverse::Scenario::BACKUP) {
1238 session_->StartExtTimer(bundleName, timeoutCallback);
1239 } else if (scenario == IServiceReverse::Scenario::RESTORE) {
1240 session_->StartFwkTimer(bundleName, timeoutCallback);
1241 }
1242
1243 BConstants::ServiceSchedAction curSchedAction = session_->GetServiceSchedAction(bundleName);
1244 if (curSchedAction == BConstants::ServiceSchedAction::CLEAN) {
1245 sched_->Sched(bundleName);
1246 return;
1247 }
1248 if (curSchedAction == BConstants::ServiceSchedAction::START &&
1249 clearRecorder_->FindClearBundleRecord(bundleName)) {
1250 session_->SetServiceSchedAction(bundleName, BConstants::ServiceSchedAction::CLEAN);
1251 } else {
1252 session_->SetServiceSchedAction(bundleName, BConstants::ServiceSchedAction::RUNNING);
1253 AddClearBundleRecord(bundleName);
1254 }
1255 sched_->Sched(bundleName);
1256 } catch (...) {
1257 HILOGE("Unexpected exception, bundleName: %{public}s", bundleName.c_str());
1258 ClearSessionAndSchedInfo(bundleName);
1259 NoticeClientFinish(bundleName, BError(BError::Codes::SDK_INVAL_ARG));
1260 return;
1261 }
1262 }
1263
ClearSessionAndSchedInfo(const string & bundleName)1264 void Service::ClearSessionAndSchedInfo(const string &bundleName)
1265 {
1266 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1267 try {
1268 HILOGI("begin %{public}s", bundleName.c_str());
1269 session_->RemoveExtInfo(bundleName);
1270 sched_->RemoveExtConn(bundleName);
1271 HandleRestoreDepsBundle(bundleName);
1272 DelClearBundleRecord({bundleName});
1273 if (isCleanService_.load() && session_->IsOnAllBundlesFinished()) {
1274 isCleanService_.store(false);
1275 StopAll(nullptr, true);
1276 return;
1277 }
1278 sched_->Sched();
1279 } catch (const BError &e) {
1280 return;
1281 } catch (const exception &e) {
1282 HILOGI("Catched an unexpected low-level exception %{public}s", e.what());
1283 return;
1284 } catch (...) {
1285 HILOGI("Unexpected exception");
1286 return;
1287 }
1288 }
1289
HandleRestoreDepsBundle(const string & bundleName)1290 void Service::HandleRestoreDepsBundle(const string &bundleName)
1291 {
1292 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1293 if (session_->GetScenario() != IServiceReverse::Scenario::RESTORE) {
1294 return;
1295 }
1296 HILOGI("Begin, bundleName: %{public}s", bundleName.c_str());
1297 SvcRestoreDepsManager::GetInstance().AddRestoredBundles(bundleName);
1298 // 该应用恢复完成,判断依赖hap的前置hap是否全部恢复完成,如果成了,追加该依赖hap
1299 auto restoreBundleMap = SvcRestoreDepsManager::GetInstance().GetRestoreBundleMap();
1300 if (restoreBundleMap.empty()) {
1301 HILOGI("restoreBundleMap is empty.");
1302 return;
1303 }
1304 // 启动恢复会话
1305 vector<string> restoreBundleNames {};
1306 for (const auto &bundle : restoreBundleMap) {
1307 HILOGI("Start restore session, bundle: %{public}s", bundle.first.c_str());
1308 restoreBundleNames.emplace_back(bundle.first);
1309 }
1310 session_->AppendBundles(restoreBundleNames);
1311 for (const auto &bundle : restoreBundleMap) {
1312 for (auto &bundleInfo : SvcRestoreDepsManager::GetInstance().GetAllBundles()) {
1313 if (bundle.first != bundleInfo.name) {
1314 continue;
1315 }
1316 SvcRestoreDepsManager::RestoreInfo info = bundle.second;
1317 session_->SetBundleRestoreType(bundleInfo.name, info.restoreType_);
1318 session_->SetBundleVersionCode(bundleInfo.name, bundleInfo.versionCode);
1319 session_->SetBundleVersionName(bundleInfo.name, bundleInfo.versionName);
1320 session_->SetBundleDataSize(bundleInfo.name, bundleInfo.spaceOccupied);
1321 session_->SetBackupExtName(bundleInfo.name, bundleInfo.extensionName);
1322 for (auto &fileName : info.fileNames_) {
1323 session_->SetExtFileNameRequest(bundleInfo.name, fileName);
1324 }
1325 }
1326 }
1327 HILOGI("End");
1328 }
1329
OnAllBundlesFinished(ErrCode errCode)1330 void Service::OnAllBundlesFinished(ErrCode errCode)
1331 {
1332 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1333 HILOGI("called begin.");
1334 if (session_->IsOnAllBundlesFinished()) {
1335 IServiceReverse::Scenario scenario = session_->GetScenario();
1336 if (isInRelease_.load() && (scenario == IServiceReverse::Scenario::RESTORE)) {
1337 SessionDeactive();
1338 }
1339 if (scenario == IServiceReverse::Scenario::BACKUP && session_->GetIsIncrementalBackup()) {
1340 session_->GetServiceReverseProxy()->IncrementalBackupOnAllBundlesFinished(errCode);
1341 } else if (scenario == IServiceReverse::Scenario::RESTORE &&
1342 BackupPara().GetBackupOverrideIncrementalRestore() &&
1343 session_->ValidRestoreDataType(RestoreTypeEnum::RESTORE_DATA_WAIT_SEND)) {
1344 session_->GetServiceReverseProxy()->IncrementalRestoreOnAllBundlesFinished(errCode);
1345 } else if (scenario == IServiceReverse::Scenario::BACKUP) {
1346 session_->GetServiceReverseProxy()->BackupOnAllBundlesFinished(errCode);
1347 } else if (scenario == IServiceReverse::Scenario::RESTORE) {
1348 session_->GetServiceReverseProxy()->RestoreOnAllBundlesFinished(errCode);
1349 }
1350 if (!BackupPara().GetBackupOverrideBackupSARelease()) {
1351 sched_->TryUnloadServiceTimer(true);
1352 }
1353 }
1354 HILOGI("called end.");
1355 }
1356
OnStartSched()1357 void Service::OnStartSched()
1358 {
1359 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1360 if (session_->IsOnOnStartSched()) {
1361 for (int num = 0; num < BConstants::EXT_CONNECT_MAX_COUNT; num++) {
1362 sched_->Sched();
1363 }
1364 }
1365 }
1366
SendStartAppGalleryNotify(const BundleName & bundleName)1367 void Service::SendStartAppGalleryNotify(const BundleName &bundleName)
1368 {
1369 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1370 if (SAUtils::IsSABundleName(bundleName)) {
1371 HILOGI("SA does not need to StartRestore");
1372 return;
1373 }
1374 IServiceReverse::Scenario scenario = session_->GetScenario();
1375 if (scenario != IServiceReverse::Scenario::RESTORE) {
1376 return;
1377 }
1378 if (!disposal_->IfBundleNameInDisposalConfigFile(bundleName)) {
1379 HILOGE("WriteDisposalConfigFile Failed");
1380 return;
1381 }
1382 HILOGI("AppendIntoDisposalConfigFile OK, bundleName=%{public}s", bundleName.c_str());
1383 DisposeErr disposeErr = AppGalleryDisposeProxy::GetInstance()->StartRestore(bundleName);
1384 HILOGI("StartRestore, code=%{public}d, bundleName=%{public}s", disposeErr,
1385 bundleName.c_str());
1386 }
1387
SendEndAppGalleryNotify(const BundleName & bundleName)1388 void Service::SendEndAppGalleryNotify(const BundleName &bundleName)
1389 {
1390 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1391 if (SAUtils::IsSABundleName(bundleName)) {
1392 HILOGI("SA does not need to EndRestore");
1393 return;
1394 }
1395 IServiceReverse::Scenario scenario = session_->GetScenario();
1396 if (scenario != IServiceReverse::Scenario::RESTORE) {
1397 return;
1398 }
1399 DisposeErr disposeErr = AppGalleryDisposeProxy::GetInstance()->EndRestore(bundleName);
1400 HILOGI("EndRestore, code=%{public}d, bundleName=%{public}s", disposeErr,
1401 bundleName.c_str());
1402 if (disposeErr != DisposeErr::OK) {
1403 HILOGE("Error code=%{public}d, disposal will be clear in the end", disposeErr);
1404 return;
1405 }
1406 if (!disposal_->DeleteFromDisposalConfigFile(bundleName)) {
1407 HILOGE("DeleteFromDisposalConfigFile Failed, bundleName=%{public}s", bundleName.c_str());
1408 return;
1409 }
1410 HILOGI("DeleteFromDisposalConfigFile OK, bundleName=%{public}s", bundleName.c_str());
1411 }
1412
TryToClearDispose(const BundleName & bundleName)1413 void Service::TryToClearDispose(const BundleName &bundleName)
1414 {
1415 int32_t maxAtt = MAX_TRY_CLEAR_DISPOSE_NUM;
1416 int32_t att = 0;
1417 while (att < maxAtt) {
1418 DisposeErr disposeErr = AppGalleryDisposeProxy::GetInstance()->EndRestore(bundleName);
1419 HILOGI("EndRestore, code=%{public}d, bundleName=%{public}s", disposeErr, bundleName.c_str());
1420 if (disposeErr == DisposeErr::OK) {
1421 break;
1422 }
1423 ++att;
1424 HILOGI("Try to clear dispose, num = %{public}d", att);
1425 }
1426 if (!disposal_->DeleteFromDisposalConfigFile(bundleName)) {
1427 HILOGE("DeleteFromDisposalConfigFile Failed, bundleName=%{public}s", bundleName.c_str());
1428 }
1429 }
1430
SendErrAppGalleryNotify()1431 void Service::SendErrAppGalleryNotify()
1432 {
1433 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1434 IServiceReverse::Scenario scenario = session_->GetScenario();
1435 if (scenario != IServiceReverse::Scenario::RESTORE) {
1436 return;
1437 }
1438 vector<string> bundleNameList = disposal_->GetBundleNameFromConfigFile();
1439 if (bundleNameList.empty()) {
1440 HILOGI("End, All disposal pasitions have been cleared");
1441 return;
1442 }
1443 for (vector<string>::iterator it = bundleNameList.begin(); it != bundleNameList.end(); ++it) {
1444 string bundleName = *it;
1445 TryToClearDispose(bundleName);
1446 }
1447 }
1448
ClearDisposalOnSaStart()1449 void Service::ClearDisposalOnSaStart()
1450 {
1451 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1452 vector<string> bundleNameList = disposal_->GetBundleNameFromConfigFile();
1453 if (!bundleNameList.empty()) {
1454 for (vector<string>::iterator it = bundleNameList.begin(); it != bundleNameList.end(); ++it) {
1455 string bundleName = *it;
1456 HILOGE("dispose has residual, clear now, bundelName =%{public}s", bundleName.c_str());
1457 TryToClearDispose(bundleName);
1458 }
1459 }
1460 HILOGI("SA start, All Errdisposal pasitions have been cleared");
1461 }
1462
DeleteDisConfigFile()1463 void Service::DeleteDisConfigFile()
1464 {
1465 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1466 IServiceReverse::Scenario scenario = session_->GetScenario();
1467 if (scenario != IServiceReverse::Scenario::RESTORE) {
1468 return;
1469 }
1470 vector<string> bundleNameList = disposal_->GetBundleNameFromConfigFile();
1471 if (!bundleNameList.empty()) {
1472 HILOGE("DisposalConfigFile is not empty");
1473 return;
1474 }
1475 if (!disposal_->DeleteConfigFile()) {
1476 HILOGE("DeleteConfigFile failed");
1477 }
1478 }
1479
SessionDeactive()1480 void Service::SessionDeactive()
1481 {
1482 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1483 try {
1484 HILOGI("Begin");
1485 isInRelease_.store(true);
1486 //清理处置状态
1487 if (session_ == nullptr) {
1488 HILOGE("Session deactive error, session is empty");
1489 return;
1490 }
1491 ErrCode ret = BError(BError::Codes::OK);
1492 std::vector<std::string> bundleNameList;
1493 if (session_->GetScenario() == IServiceReverse::Scenario::RESTORE &&
1494 session_->CleanAndCheckIfNeedWait(ret, bundleNameList)) {
1495 if (ret != ERR_OK) {
1496 isRmConfigFile_.store(false);
1497 }
1498 if (!bundleNameList.empty()) {
1499 DelClearBundleRecord(bundleNameList);
1500 }
1501 return;
1502 }
1503 isInRelease_.store(false);
1504 if (!bundleNameList.empty()) {
1505 DelClearBundleRecord(bundleNameList);
1506 }
1507 SendErrAppGalleryNotify();
1508 DeleteDisConfigFile();
1509 // 结束定时器
1510 if (sched_ == nullptr) {
1511 HILOGE("Session deactive error, sched is empty");
1512 return;
1513 }
1514 sched_->ClearSchedulerData();
1515 // 清除缓存数据
1516 if (session_ == nullptr) {
1517 HILOGE("Session deactive error, session is empty");
1518 return;
1519 }
1520 ret = session_->ClearSessionData();
1521 if (clearRecorder_ != nullptr && !ret && isRmConfigFile_.load()) {
1522 clearRecorder_->DeleteConfigFile();
1523 }
1524 // close session
1525 StopAll(nullptr, true);
1526 if (session_->GetSessionCnt() <= 0) {
1527 HILOGI("do unload Service.");
1528 sched_->TryUnloadService();
1529 }
1530 } catch (...) {
1531 HILOGE("Unexpected exception");
1532 return;
1533 }
1534 }
1535
GetBackupInfoConnectDone(wptr<Service> obj,std::string & bundleName)1536 std::function<void(const std::string &&)> Service::GetBackupInfoConnectDone(wptr<Service> obj, std::string &bundleName)
1537 {
1538 return [obj](const string &&bundleName) {
1539 HILOGI("GetBackupInfoConnectDone, bundleName: %{public}s", bundleName.c_str());
1540 auto thisPtr = obj.promote();
1541 if (!thisPtr) {
1542 HILOGW("this pointer is null.");
1543 return;
1544 }
1545 thisPtr->getBackupInfoCondition_.notify_one();
1546 };
1547 }
1548
GetBackupInfoConnectDied(wptr<Service> obj,std::string & bundleName)1549 std::function<void(const std::string &&, bool)> Service::GetBackupInfoConnectDied(
1550 wptr<Service> obj, std::string &bundleName)
1551 {
1552 return [obj](const string &&bundleName, bool isSecondCalled) {
1553 HILOGI("GetBackupInfoConnectDied, bundleName: %{public}s", bundleName.c_str());
1554 auto thisPtr = obj.promote();
1555 if (!thisPtr) {
1556 HILOGW("this pointer is null.");
1557 return;
1558 }
1559 thisPtr->isConnectDied_.store(true);
1560 thisPtr->getBackupInfoCondition_.notify_one();
1561 };
1562 }
1563
ClearResidualBundleData(const std::string & bundleName)1564 ErrCode Service::ClearResidualBundleData(const std::string &bundleName)
1565 {
1566 if (session_ == nullptr) {
1567 return BError(BError::Codes::SA_INVAL_ARG);
1568 }
1569 auto backUpConnection = session_->GetExtConnection(bundleName);
1570 if (backUpConnection == nullptr) {
1571 throw BError(BError::Codes::SA_INVAL_ARG, "backUpConnection is empty");
1572 }
1573 auto proxy = backUpConnection->GetBackupExtProxy();
1574 if (!proxy) {
1575 throw BError(BError::Codes::SA_INVAL_ARG, "Extension backup Proxy is empty");
1576 }
1577 // 通知ext清理
1578 ErrCode res = proxy->HandleClear();
1579 if (backUpConnection->IsExtAbilityConnected()) {
1580 backUpConnection->DisconnectBackupExtAbility();
1581 }
1582 ClearSessionAndSchedInfo(bundleName);
1583 // 非清理任务,需要上报
1584 if (session_->GetScenario() != IServiceReverse::Scenario::CLEAN) {
1585 OnAllBundlesFinished(BError(BError::Codes::OK));
1586 }
1587 return res;
1588 }
1589
GetBackupInfoCmdHandle(BundleName & bundleName,std::string & result)1590 ErrCode Service::GetBackupInfoCmdHandle(BundleName &bundleName, std::string &result)
1591 {
1592 if (session_ == nullptr) {
1593 HILOGE("Get BackupInfo error, session is empty.");
1594 return BError(BError::Codes::SA_INVAL_ARG);
1595 }
1596 session_->SetSessionUserId(GetUserIdDefault());
1597 auto backupConnection = session_->CreateBackupConnection(bundleName);
1598 if (backupConnection == nullptr) {
1599 HILOGE("backupConnection is null. bundleName: %{public}s", bundleName.c_str());
1600 return BError(BError::Codes::SA_INVAL_ARG);
1601 }
1602 auto callConnected = GetBackupInfoConnectDone(wptr(this), bundleName);
1603 auto callDied = GetBackupInfoConnectDied(wptr(this), bundleName);
1604 backupConnection->SetCallback(callConnected);
1605 backupConnection->SetCallDied(callDied);
1606 AAFwk::Want want = CreateConnectWant(bundleName);
1607 auto ret = backupConnection->ConnectBackupExtAbility(want, session_->GetSessionUserId());
1608 if (ret) {
1609 HILOGE("ConnectBackupExtAbility faild, bundleName:%{public}s, ret:%{public}d", bundleName.c_str(), ret);
1610 return BError(BError::Codes::SA_BOOT_EXT_FAIL);
1611 }
1612 std::unique_lock<std::mutex> lock(getBackupInfoSyncLock_);
1613 getBackupInfoCondition_.wait_for(lock, std::chrono::seconds(CONNECT_WAIT_TIME_S));
1614 if (isConnectDied_.load()) {
1615 HILOGE("GetBackupInfoConnectDied, please check bundleName: %{public}s", bundleName.c_str());
1616 isConnectDied_.store(false);
1617 return BError(BError::Codes::EXT_ABILITY_DIED);
1618 }
1619 auto proxy = backupConnection->GetBackupExtProxy();
1620 if (!proxy) {
1621 HILOGE("Extension backup Proxy is empty.");
1622 return BError(BError::Codes::SA_INVAL_ARG);
1623 }
1624 ret = proxy->GetBackupInfo(result);
1625 backupConnection->DisconnectBackupExtAbility();
1626 if (ret != ERR_OK) {
1627 HILOGE("Call Ext GetBackupInfo faild.");
1628 AppRadar::Info info(bundleName, "", "Call Ext GetBackupInfo faild");
1629 Backup::AppRadar::GetInstance().RecordBackupFuncRes(info, "Service::GetBackupInfoCmdHandle", GetUserIdDefault(),
1630 BizStageBackup::BIZ_STAGE_GET_BACKUP_INFO_FAIL, ret);
1631 return BError(BError::Codes::SA_INVAL_ARG);
1632 }
1633
1634 return BError(BError::Codes::OK);
1635 }
1636
GetBackupInfo(BundleName & bundleName,std::string & result)1637 ErrCode Service::GetBackupInfo(BundleName &bundleName, std::string &result)
1638 {
1639 try {
1640 std::lock_guard<std::mutex> lock(getBackupInfoProcLock_);
1641 HILOGI("Service::GetBackupInfo begin.");
1642 if (session_ == nullptr || isCleanService_.load()) {
1643 HILOGE("Get BackupInfo error, session is empty.");
1644 return BError(BError::Codes::SA_INVAL_ARG);
1645 }
1646 if (session_->GetImpl().clientToken) {
1647 return BError(BError::Codes::SA_REFUSED_ACT, "Already have an active session");
1648 }
1649 session_->IncreaseSessionCnt(__PRETTY_FUNCTION__);
1650 auto ret = GetBackupInfoCmdHandle(bundleName, result);
1651 HILOGI("Service::GetBackupInfo end. result: %{public}s", result.c_str());
1652 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
1653 return ret;
1654 } catch (...) {
1655 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
1656 HILOGI("Unexpected exception");
1657 return EPERM;
1658 }
1659 }
1660
StartExtTimer(bool & isExtStart)1661 ErrCode Service::StartExtTimer(bool &isExtStart)
1662 {
1663 try {
1664 HILOGI("Service::StartExtTimer begin.");
1665 if (session_ == nullptr) {
1666 HILOGE("StartExtTimer error, session_ is nullptr.");
1667 isExtStart = false;
1668 return BError(BError::Codes::SA_INVAL_ARG);
1669 }
1670 session_->IncreaseSessionCnt(__PRETTY_FUNCTION__);
1671 string bundleName = VerifyCallerAndGetCallerName();
1672 auto timeoutCallback = TimeOutCallback(wptr<Service>(this), bundleName);
1673 session_->StopFwkTimer(bundleName);
1674 isExtStart = session_->StartExtTimer(bundleName, timeoutCallback);
1675 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
1676 return BError(BError::Codes::OK);
1677 } catch (...) {
1678 isExtStart = false;
1679 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
1680 HILOGI("Unexpected exception");
1681 return EPERM;
1682 }
1683 }
1684
StartFwkTimer(bool & isFwkStart)1685 ErrCode Service::StartFwkTimer(bool &isFwkStart)
1686 {
1687 try {
1688 HILOGI("Service::StartFwkTimer begin.");
1689 if (session_ == nullptr) {
1690 HILOGE("StartFwkTimer error, session_ is nullptr.");
1691 isFwkStart = false;
1692 return BError(BError::Codes::SA_INVAL_ARG);
1693 }
1694 session_->IncreaseSessionCnt(__PRETTY_FUNCTION__);
1695 string bundleName = VerifyCallerAndGetCallerName();
1696 auto timeoutCallback = TimeOutCallback(wptr<Service>(this), bundleName);
1697 session_->StopExtTimer(bundleName);
1698 isFwkStart = session_->StartFwkTimer(bundleName, timeoutCallback);
1699 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
1700 return BError(BError::Codes::OK);
1701 } catch (...) {
1702 isFwkStart = false;
1703 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
1704 HILOGI("Unexpected exception");
1705 return EPERM;
1706 }
1707 }
1708
AppendBundlesClearSession(const std::vector<BundleName> & bundleNames)1709 ErrCode Service::AppendBundlesClearSession(const std::vector<BundleName> &bundleNames)
1710 {
1711 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1712 try {
1713 if (bundleNames.empty() || session_ == nullptr) {
1714 HILOGE("Init Incremental backup session error, session is empty");
1715 return EPERM;
1716 }
1717 session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); // BundleMgrAdapter::GetBundleInfos可能耗时
1718 auto backupInfos = BundleMgrAdapter::GetBundleInfos(bundleNames, session_->GetSessionUserId());
1719 std::vector<std::string> supportBundleNames;
1720 for (auto info : backupInfos) {
1721 std::string bundleNameIndexStr = BJsonUtil::BuildBundleNameIndexInfo(info.name, info.appIndex);
1722 supportBundleNames.emplace_back(bundleNameIndexStr);
1723 }
1724 session_->AppendBundles(supportBundleNames);
1725 for (auto info : backupInfos) {
1726 std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(info.name, info.appIndex);
1727 session_->SetBackupExtName(bundleNameIndexInfo, info.extensionName);
1728 session_->SetIsReadyLaunch(bundleNameIndexInfo);
1729 }
1730 OnStartSched();
1731 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
1732 return BError(BError::Codes::OK);
1733 } catch (const BError &e) {
1734 HandleExceptionOnAppendBundles(session_, bundleNames, {});
1735 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
1736 HILOGE("Failed, errCode = %{public}d", e.GetCode());
1737 return e.GetCode();
1738 } catch (const exception &e) {
1739 HandleExceptionOnAppendBundles(session_, bundleNames, {});
1740 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
1741 HILOGE("Catched an unexpected low-level exception %{public}s", e.what());
1742 return EPERM;
1743 } catch (...) {
1744 HandleExceptionOnAppendBundles(session_, bundleNames, {});
1745 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
1746 HILOGE("Unexpected exception");
1747 return EPERM;
1748 }
1749 }
1750
UpdateTimer(BundleName & bundleName,uint32_t timeout,bool & result)1751 ErrCode Service::UpdateTimer(BundleName &bundleName, uint32_t timeout, bool &result)
1752 {
1753 try {
1754 HILOGI("Service::UpdateTimer begin.");
1755 if (session_ == nullptr || isCleanService_.load()) {
1756 HILOGE("Update Timer error, session is empty.");
1757 result = false;
1758 return BError(BError::Codes::SA_INVAL_ARG);
1759 }
1760 session_->IncreaseSessionCnt(__PRETTY_FUNCTION__);
1761 VerifyCaller();
1762 auto timeoutCallback = TimeOutCallback(wptr<Service>(this), bundleName);
1763 result = session_->UpdateTimer(bundleName, timeout, timeoutCallback);
1764 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
1765 return BError(BError::Codes::OK);
1766 } catch (...) {
1767 result = false;
1768 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
1769 HILOGI("Unexpected exception");
1770 return EPERM;
1771 }
1772 }
1773
UpdateSendRate(std::string & bundleName,int32_t sendRate,bool & result)1774 ErrCode Service::UpdateSendRate(std::string &bundleName, int32_t sendRate, bool &result)
1775 {
1776 try {
1777 HILOGI("Begin, bundle name:%{public}s, sendRate is:%{public}d", bundleName.c_str(), sendRate);
1778 if (session_ == nullptr || isCleanService_.load()) {
1779 HILOGE("Update Send Rate error, session is empty.");
1780 result = false;
1781 return BError(BError::Codes::SA_INVAL_ARG);
1782 }
1783 session_->IncreaseSessionCnt(__PRETTY_FUNCTION__);
1784 VerifyCaller();
1785 IServiceReverse::Scenario scenario = session_ -> GetScenario();
1786 if (scenario != IServiceReverse::Scenario::BACKUP) {
1787 HILOGE("This method is applicable to the backup scenario");
1788 result = false;
1789 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
1790 return BError(BError::Codes::SA_INVAL_ARG);
1791 }
1792 auto backupConnection = session_->GetExtConnection(bundleName);
1793 auto proxy = backupConnection->GetBackupExtProxy();
1794 if (!proxy) {
1795 throw BError(BError::Codes::SA_INVAL_ARG, "Extension backup Proxy is empty");
1796 }
1797 auto ret = proxy->UpdateFdSendRate(bundleName, sendRate);
1798 if (ret != NO_ERROR) {
1799 result = false;
1800 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
1801 return BError(BError::Codes::EXT_BROKEN_IPC);
1802 }
1803 result = true;
1804 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
1805 return BError(BError::Codes::OK);
1806 } catch (...) {
1807 result = false;
1808 session_->DecreaseSessionCnt(__PRETTY_FUNCTION__);
1809 HILOGI("Unexpected exception");
1810 return EPERM;
1811 }
1812 }
1813
CreateConnectWant(BundleName & bundleName)1814 AAFwk::Want Service::CreateConnectWant (BundleName &bundleName)
1815 {
1816 BConstants::ExtensionAction action = BConstants::ExtensionAction::BACKUP;
1817 AAFwk::Want want;
1818 string backupExtName = BundleMgrAdapter::GetExtName(bundleName, session_->GetSessionUserId());
1819 want.SetElementName(bundleName, backupExtName);
1820 want.SetParam(BConstants::EXTENSION_ACTION_PARA, static_cast<int>(action));
1821 return want;
1822 }
1823
BackupSA(std::string bundleName)1824 ErrCode Service::BackupSA(std::string bundleName)
1825 {
1826 HILOGI("BackupSA begin %{public}s", bundleName.c_str());
1827 IServiceReverse::Scenario scenario = session_->GetScenario();
1828 auto backUpConnection = session_->GetSAExtConnection(bundleName);
1829 std::shared_ptr<SABackupConnection> saConnection = backUpConnection.lock();
1830 if (saConnection == nullptr) {
1831 HILOGE("lock sa connection ptr is nullptr");
1832 return BError(BError::Codes::SA_INVAL_ARG);
1833 }
1834 if (scenario == IServiceReverse::Scenario::BACKUP) {
1835 auto ret = saConnection->CallBackupSA();
1836 session_->GetServiceReverseProxy()->BackupOnBundleStarted(ret, bundleName);
1837 BundleBeginRadarReport(bundleName, ret, scenario);
1838 if (ret) {
1839 HILOGI("BackupSA ret is %{public}d", ret);
1840 ClearSessionAndSchedInfo(bundleName);
1841 NoticeClientFinish(bundleName, BError(BError::Codes::EXT_ABILITY_DIED));
1842 return BError(ret);
1843 }
1844 } else if (scenario == IServiceReverse::Scenario::RESTORE) {
1845 session_->GetServiceReverseProxy()->IncrementalRestoreOnBundleStarted(BError(BError::Codes::OK), bundleName);
1846 }
1847 return BError(BError::Codes::OK);
1848 }
1849
OnSABackup(const std::string & bundleName,const int & fd,const std::string & result,const ErrCode & errCode)1850 void Service::OnSABackup(const std::string &bundleName, const int &fd, const std::string &result,
1851 const ErrCode &errCode)
1852 {
1853 auto task = [bundleName, fd, result, errCode, this]() {
1854 HILOGI("OnSABackup bundleName: %{public}s, fd: %{public}d, result: %{public}s, err: %{public}d",
1855 bundleName.c_str(), fd, result.c_str(), errCode);
1856 session_->GetServiceReverseProxy()->BackupOnFileReady(bundleName, "", move(fd), errCode);
1857 FileReadyRadarReport(bundleName, "", errCode, IServiceReverse::Scenario::BACKUP);
1858 SAResultReport(bundleName, result, errCode, BackupRestoreScenario::FULL_BACKUP);
1859 };
1860 threadPool_.AddTask([task]() {
1861 try {
1862 task();
1863 } catch (...) {
1864 HILOGE("Failed to add task to thread pool");
1865 }
1866 });
1867 }
1868
OnSARestore(const std::string & bundleName,const std::string & result,const ErrCode & errCode)1869 void Service::OnSARestore(const std::string &bundleName, const std::string &result, const ErrCode &errCode)
1870 {
1871 auto task = [bundleName, result, errCode, this]() {
1872 HILOGI("OnSARestore bundleName: %{public}s, result: %{public}s, err: %{public}d",
1873 bundleName.c_str(), result.c_str(), errCode);
1874 SAResultReport(bundleName, result, errCode, BackupRestoreScenario::INCREMENTAL_RESTORE);
1875 };
1876 threadPool_.AddTask([task]() {
1877 try {
1878 task();
1879 } catch (...) {
1880 HILOGE("Failed to add task to thread pool");
1881 }
1882 });
1883 }
1884
SADone(ErrCode errCode,std::string bundleName)1885 ErrCode Service::SADone(ErrCode errCode, std::string bundleName)
1886 {
1887 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1888 try {
1889 if (session_->OnBundleFileReady(bundleName)) {
1890 auto backupConnection = session_->GetSAExtConnection(bundleName);
1891 std::shared_ptr<SABackupConnection> saConnection = backupConnection.lock();
1892 if (saConnection == nullptr) {
1893 HILOGE("lock sa connection ptr is nullptr");
1894 return BError(BError::Codes::SA_INVAL_ARG);
1895 }
1896 session_->StopFwkTimer(bundleName);
1897 session_->StopExtTimer(bundleName);
1898 saConnection->DisconnectBackupSAExt();
1899 ClearSessionAndSchedInfo(bundleName);
1900 }
1901 OnAllBundlesFinished(BError(BError::Codes::OK));
1902 return BError(BError::Codes::OK);
1903 } catch (const BError &e) {
1904 ReleaseOnException();
1905 return e.GetCode(); // 任意异常产生,终止监听该任务
1906 } catch (const exception &e) {
1907 ReleaseOnException();
1908 HILOGE("Catched an unexpected low-level exception %{public}s", e.what());
1909 return EPERM;
1910 } catch(...) {
1911 ReleaseOnException();
1912 HILOGE("Unexpected exception");
1913 return EPERM;
1914 }
1915 }
1916
NotifyCallerCurAppDone(ErrCode errCode,const std::string & callerName)1917 void Service::NotifyCallerCurAppDone(ErrCode errCode, const std::string &callerName)
1918 {
1919 IServiceReverse::Scenario scenario = session_->GetScenario();
1920 if (scenario == IServiceReverse::Scenario::BACKUP) {
1921 HILOGI("will notify clone data, scenario is Backup");
1922 session_->GetServiceReverseProxy()->BackupOnBundleFinished(errCode, callerName);
1923 auto now = std::chrono::system_clock::now();
1924 auto time = std::chrono::system_clock::to_time_t(now);
1925 auto ms = std::chrono::duration_cast<std::chrono::milliseconds>(now.time_since_epoch());
1926 std::stringstream strTime;
1927 strTime << (std::put_time(std::localtime(&time), "%Y-%m-%d %H:%M:%S:")) << (std::setfill('0'))
1928 << (std::setw(INDEX)) << (ms.count() % MS_1000);
1929 HiSysEventWrite(
1930 OHOS::HiviewDFX::HiSysEvent::Domain::FILEMANAGEMENT,
1931 FILE_BACKUP_EVENTS,
1932 OHOS::HiviewDFX::HiSysEvent::EventType::BEHAVIOR,
1933 "PROC_NAME", "ohos.appfileservice",
1934 "BUNDLENAME", callerName,
1935 "PID", getpid(),
1936 "TIME", strTime.str()
1937 );
1938 } else if (scenario == IServiceReverse::Scenario::RESTORE) {
1939 HILOGI("will notify clone data, scenario is Restore");
1940 session_->GetServiceReverseProxy()->RestoreOnBundleFinished(errCode, callerName);
1941 }
1942 BundleEndRadarReport(callerName, errCode, scenario);
1943 }
1944
ReportAppProcessInfo(const std::string processInfo,BackupRestoreScenario sennario)1945 ErrCode Service::ReportAppProcessInfo(const std::string processInfo, BackupRestoreScenario sennario)
1946 {
1947 HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__);
1948 try {
1949 string bundleName = VerifyCallerAndGetCallerName();
1950 if (sennario == BackupRestoreScenario::FULL_RESTORE) {
1951 session_->GetServiceReverseProxy()->RestoreOnProcessInfo(bundleName, processInfo);
1952 } else if (sennario == BackupRestoreScenario::INCREMENTAL_RESTORE) {
1953 session_->GetServiceReverseProxy()->IncrementalRestoreOnProcessInfo(bundleName, processInfo);
1954 } else if (sennario == BackupRestoreScenario::FULL_BACKUP) {
1955 session_->GetServiceReverseProxy()->BackupOnProcessInfo(bundleName, processInfo);
1956 } else if (sennario == BackupRestoreScenario::INCREMENTAL_BACKUP) {
1957 session_->GetServiceReverseProxy()->IncrementalBackupOnProcessInfo(bundleName, processInfo);
1958 }
1959 return BError(BError::Codes::OK);
1960 } catch (const BError &e) {
1961 return e.GetCode(); // 任意异常产生,终止监听该任务
1962 } catch (const exception &e) {
1963 HILOGI("Catched an unexpected low-level exception %{public}s", e.what());
1964 return EPERM;
1965 }
1966 }
1967
TimeOutCallback(wptr<Service> ptr,std::string bundleName)1968 std::function<void()> Service::TimeOutCallback(wptr<Service> ptr, std::string bundleName)
1969 {
1970 return [ptr, bundleName, this]() {
1971 HILOGI("begin timeoutCallback bundleName = %{public}s", bundleName.c_str());
1972 auto thisPtr = ptr.promote();
1973 if (!thisPtr) {
1974 HILOGE("ServicePtr is nullptr.");
1975 return;
1976 }
1977 try {
1978 DoTimeout(thisPtr, bundleName);
1979 } catch (...) {
1980 HILOGE("Unexpected exception, bundleName: %{public}s", bundleName.c_str());
1981 thisPtr->ClearSessionAndSchedInfo(bundleName);
1982 thisPtr->NoticeClientFinish(bundleName, BError(BError::Codes::EXT_ABILITY_TIMEOUT));
1983 }
1984 };
1985 }
1986
TimeoutRadarReport(IServiceReverse::Scenario scenario,std::string & bundleName)1987 void Service::TimeoutRadarReport(IServiceReverse::Scenario scenario, std::string &bundleName)
1988 {
1989 int32_t errCode = BError(BError::Codes::EXT_ABILITY_TIMEOUT).GetCode();
1990 if (scenario == IServiceReverse::Scenario::BACKUP) {
1991 AppRadar::Info info(bundleName, "", "on backup timeout");
1992 AppRadar::GetInstance().RecordBackupFuncRes(info, "Service::TimeOutCallback", GetUserIdDefault(),
1993 BizStageBackup::BIZ_STAGE_ON_BACKUP, errCode);
1994 } else if (scenario == IServiceReverse::Scenario::RESTORE) {
1995 AppRadar::Info info(bundleName, "", "on restore timeout");
1996 AppRadar::GetInstance().RecordRestoreFuncRes(info, "Service::TimeOutCallback", GetUserIdDefault(),
1997 BizStageRestore::BIZ_STAGE_ON_RESTORE, errCode);
1998 }
1999 }
2000
DoTimeout(wptr<Service> ptr,std::string bundleName)2001 void Service::DoTimeout(wptr<Service> ptr, std::string bundleName)
2002 {
2003 auto thisPtr = ptr.promote();
2004 if (!thisPtr) {
2005 HILOGE("ServicePtr is nullptr.");
2006 return;
2007 }
2008 auto sessionPtr = thisPtr->session_;
2009 if (sessionPtr == nullptr) {
2010 HILOGE("SessionPtr is nullptr.");
2011 return;
2012 }
2013 IServiceReverse::Scenario scenario = sessionPtr->GetScenario();
2014 TimeoutRadarReport(scenario, bundleName);
2015 try {
2016 std::shared_ptr<ExtensionMutexInfo> mutexPtr = GetExtensionMutex(bundleName);
2017 if (mutexPtr == nullptr) {
2018 HILOGE("extension mutex ptr is nullptr");
2019 return;
2020 }
2021 std::lock_guard<std::mutex> lock(mutexPtr->callbackMutex);
2022 if (SAUtils::IsSABundleName(bundleName)) {
2023 auto sessionConnection = sessionPtr->GetSAExtConnection(bundleName);
2024 shared_ptr<SABackupConnection> saConnection = sessionConnection.lock();
2025 if (saConnection == nullptr) {
2026 HILOGE("lock sa connection ptr is nullptr");
2027 return;
2028 }
2029 saConnection->DisconnectBackupSAExt();
2030 } else {
2031 auto sessionConnection = sessionPtr->GetExtConnection(bundleName);
2032 sessionConnection->DisconnectBackupExtAbility();
2033 }
2034 sessionPtr->StopFwkTimer(bundleName);
2035 sessionPtr->StopExtTimer(bundleName);
2036 thisPtr->ClearSessionAndSchedInfo(bundleName);
2037 thisPtr->NoticeClientFinish(bundleName, BError(BError::Codes::EXT_ABILITY_TIMEOUT));
2038 } catch (...) {
2039 HILOGE("Unexpected exception, bundleName: %{public}s", bundleName.c_str());
2040 thisPtr->ClearSessionAndSchedInfo(bundleName);
2041 thisPtr->NoticeClientFinish(bundleName, BError(BError::Codes::EXT_ABILITY_TIMEOUT));
2042 }
2043 RemoveExtensionMutex(bundleName);
2044 }
2045
AddClearBundleRecord(const std::string & bundleName)2046 void Service::AddClearBundleRecord(const std::string &bundleName)
2047 {
2048 // 添加清理记录
2049 if (!clearRecorder_->InsertClearBundleRecord(bundleName)) {
2050 HILOGE("Failed to add clear bundle record, bundleName=%{public}s", bundleName.c_str());
2051 return;
2052 }
2053 HILOGI("Add clear bundle record OK, bundleName=%{public}s", bundleName.c_str());
2054 }
2055
DelClearBundleRecord(const std::vector<std::string> & bundleNames)2056 void Service::DelClearBundleRecord(const std::vector<std::string> &bundleNames)
2057 {
2058 // 删除清理记录
2059 for (const auto &it : bundleNames) {
2060 if (!clearRecorder_->DeleteClearBundleRecord(it)) {
2061 HILOGE("Failed to delete clear bundle record, bundleName=%{public}s", it.c_str());
2062 continue;
2063 }
2064 HILOGI("Delete clear bundle record OK, bundleName=%{public}s", it.c_str());
2065 }
2066 }
2067
ReleaseOnException()2068 void Service::ReleaseOnException()
2069 {
2070 try {
2071 if (session_->IsOnAllBundlesFinished()) {
2072 IServiceReverse::Scenario scenario = session_->GetScenario();
2073 if (isInRelease_.load() && (scenario == IServiceReverse::Scenario::RESTORE)) {
2074 SessionDeactive();
2075 }
2076 }
2077 } catch (...) {
2078 HILOGE("Unexpected exception");
2079 }
2080 }
2081 } // namespace OHOS::FileManagement::Backup
2082