diff --git a/.gitee/PULL_REQUEST_TEMPLATE.zh-CN.md b/.gitee/PULL_REQUEST_TEMPLATE.zh-CN.md deleted file mode 100644 index ee9bdcda8e97fab7ba41902f52636a6a8f623420..0000000000000000000000000000000000000000 --- a/.gitee/PULL_REQUEST_TEMPLATE.zh-CN.md +++ /dev/null @@ -1,71 +0,0 @@ -**Description:** - -**Issue number:** - -**Test & Result:** - -**CodeCheck:** - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
类型自检项自检结果
多线程相关在类的成员变量中定义了vector/map/list等容器类型,且在多个成员函数中有操作时,需要加锁保护自检结果:
定义全局变量,在多个函数中都有操作时,需要加锁保护自检结果:
内存相关调用外部接口时,确认是否对返回值做了判断,尤其外部接口返回了nullptr的情况,避免进程崩溃自检结果:
调用安全函数时,如memcpy_s等,是否检查其返回值自检结果:
检查函数中是否涉及了内存或资源申请(如文件句柄),注意每个异常退出流程,是否都已经将资源释放(推荐使用RAII)自检结果:
隐式内存分配场景:realpath、ReadParcelable序列化、cJSON相关函数时等,需主动释放或使用智能指针自检结果:
校验外部输入使用nlohmann:json解析外部输入时,需判断参数类型是否符合预期自检结果:
所有外部输入均不可信,需判断外部输入是否直接作为内存分配的大小,数组下标、循环条件、SQL查询等自检结果:
外部输入的路径不可信,需使用realpath做标准化处理,并判断路径的合法性自检结果:
外部输入包括对外提供的接口,IPC的proxy/stub接口,序列化/反序列化接口等自检结果:
数学运算代码中是否混合了加减乘除等运算,需检查是否可能导致整数溢出或符号翻转自检结果:
需检查代码是否有高精度数字转换为低精度的操作,如果必须,建议使用C++安全类型转换接口自检结果:
秘钥相关如变量临时保存了口令、秘钥等,需要在使用完成后及时清空(内存memset掉)自检结果:
权限相关作为系统服务对外提供了接口,是否做了权限保护和校验(如需要),只允许申请了权限的应用访问自检结果:
内核对外提供了设备节点,是否做了权限保护,只允许特定的系统服务访问自检结果:
内核操作如有mmap操作,并使用remap_pfn_range进行地址映射时,校验起始地址是否是用户态输入且没有做合法性校验自检结果:
是否有copy_from_user,并对外部输入的数据做了长度校验,以防止缓冲区溢出自检结果:
是否有使用copy_to_user,并在返回到用户态时,对数据做了完整初始化,或使用memset清空后再赋值自检结果:
diff --git a/bundle.json b/bundle.json index f3659913c22757a7cc5ff36257501c8611fb3c58..44ff318f2c21f5effa015ba18f882a4d700472c3 100644 --- a/bundle.json +++ b/bundle.json @@ -37,6 +37,7 @@ "ipc", "init", "napi", + "os_account", "safwk", "samgr", "storage_service", @@ -48,10 +49,7 @@ "openssl" ] }, - "adapted_system_type": [ - "small", - "standard" - ], + "adapted_system_type": [ "small", "standard" ], "rom": "1024KB", "ram": "1024KB", "hisysevent_config": [ diff --git a/frameworks/native/backup_ext/BUILD.gn b/frameworks/native/backup_ext/BUILD.gn index bc32d5e264a8d4286930a3cef8083fcd334881a1..6c5b10fd21bcd21549c14e8f553e10bae6ee2972 100644 --- a/frameworks/native/backup_ext/BUILD.gn +++ b/frameworks/native/backup_ext/BUILD.gn @@ -34,6 +34,7 @@ ohos_shared_library("backup_extension_ability_native") { "src/ext_backup_loader.cpp", "src/ext_extension.cpp", "src/ext_extension_stub.cpp", + "src/sub_ext_extension.cpp", "src/tar_file.cpp", "src/untar_file.cpp", ] @@ -64,8 +65,6 @@ ohos_shared_library("backup_extension_ability_native") { "ability_runtime:abilitykit_native", "ability_runtime:app_context", "ability_runtime:appkit_native", - "ability_runtime:extensionkit_native", - "ability_runtime:napi_common", "ability_runtime:runtime", "access_token:libaccesstoken_sdk", "bundle_framework:appexecfwk_core", diff --git a/frameworks/native/backup_ext/include/ext_backup.h b/frameworks/native/backup_ext/include/ext_backup.h index dae003248c1e2b6ff501356e91946bbe82a37834..570bdac446ea509a775d3de3b2b157d448d6cfb1 100644 --- a/frameworks/native/backup_ext/include/ext_backup.h +++ b/frameworks/native/backup_ext/include/ext_backup.h @@ -26,6 +26,7 @@ namespace OHOS::FileManagement::Backup { class ExtBackup; using CreatorFunc = std::function &runtime)>; +class BackupExtExtension; class ExtBackup : public AbilityRuntime::ExtensionBase { public: @@ -146,6 +147,11 @@ public: */ virtual ErrCode GetBackupInfo(std::function callback); + /** + * @brief Called do OnProcess + */ + virtual ErrCode OnProcess(std::function callback); + /** * @brief 数据迁移判断 * @@ -181,6 +187,8 @@ public: static void SetCreator(const CreatorFunc &creator); + void SetBackupExtExtension(const wptr &extExtension); + protected: std::string appVersionStr_; std::string restoreRetInfo_; @@ -195,6 +203,7 @@ private: BConstants::ExtensionAction extAction_ {BConstants::ExtensionAction::INVALID}; ErrCode GetParament(const AAFwk::Want &want); static CreatorFunc creator_; + wptr bakExtExtension_; }; } // namespace OHOS::FileManagement::Backup diff --git a/frameworks/native/backup_ext/include/ext_backup_js.h b/frameworks/native/backup_ext/include/ext_backup_js.h index cd32e0ce4c901e778ddda467c4a5a8583a449ed3..c69cc77a0c9e3bfcf02d46cfb9f8337cd71a41f7 100644 --- a/frameworks/native/backup_ext/include/ext_backup_js.h +++ b/frameworks/native/backup_ext/include/ext_backup_js.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2022-2024 Huawei Device Co., Ltd. + * Copyright (c) 2022-2025 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at @@ -73,6 +73,13 @@ struct CallbackInfoEx { } }; +struct OnProcessCallBackInfo { + std::function onProcessCallback; + OnProcessCallBackInfo(std::function param) : onProcessCallback(param) + { + } +}; + class ExtBackupJs : public ExtBackup { public: /** @@ -123,13 +130,16 @@ public: */ ErrCode InvokeAppExtMethod(ErrCode, const std::string) override; -public: - explicit ExtBackupJs(AbilityRuntime::JsRuntime &jsRuntime) : jsRuntime_(jsRuntime) {} - ~ExtBackupJs() - { - jsRuntime_.FreeNativeReference(std::move(jsObj_)); - } + /** + * @brief get app onProcess info + * + * @param callback The callBack. + */ + ErrCode OnProcess(std::function callback) override; +public: + explicit ExtBackupJs(AbilityRuntime::JsRuntime &jsRuntime); + ~ExtBackupJs(); private: int CallJsMethod(const std::string &funcName, AbilityRuntime::JsRuntime &jsRuntime, @@ -141,7 +151,6 @@ private: std::function &argv)> ParseRestoreInfo(); std::function &argv)> ParseBackupExInfo(); - std::function &argv)> ParseBackupInfo(); ErrCode CallJSRestoreEx(); ErrCode CallJSRestore(); @@ -149,12 +158,14 @@ private: ErrCode CallJsOnBackup(); void ExportJsContext(void); + void InitTempPath(const std::string &bundleName); AbilityRuntime::JsRuntime &jsRuntime_; std::unique_ptr jsObj_; std::shared_ptr callbackInfoBackup_; std::shared_ptr callbackInfoEx_; std::shared_ptr callbackInfo_; + std::shared_ptr onProcessCallback_; std::condition_variable callJsCon_; std::mutex callJsMutex_; std::atomic callExtDefaultFunc_ {false}; // extension default method, onBackup or onRestore diff --git a/frameworks/native/backup_ext/include/ext_extension.h b/frameworks/native/backup_ext/include/ext_extension.h index b93bdbb3e3c7a906f7df550b377b5d8b5ad0d8d3..c8bd321cdddc29985a3fd505c5df2c961325f6cd 100644 --- a/frameworks/native/backup_ext/include/ext_extension.h +++ b/frameworks/native/backup_ext/include/ext_extension.h @@ -27,12 +27,15 @@ #include "b_json/b_json_entity_extension_config.h" #include "b_json/b_json_entity_ext_manage.h" #include "b_json/b_report_entity.h" +#include "b_radar/b_radar.h" #include "ext_backup_js.h" #include "ext_extension_stub.h" #include "i_service.h" #include "tar_file.h" #include "thread_pool.h" +#include "timer.h" #include "unique_fd.h" +#include "untar_file.h" namespace OHOS::FileManagement::Backup { using CompareFilesResult = tuple, @@ -43,28 +46,42 @@ public: UniqueFd GetFileHandle(const std::string &fileName, int32_t &errCode) override; ErrCode HandleClear() override; ErrCode PublishFile(const std::string &fileName) override; - ErrCode HandleBackup() override; - ErrCode HandleRestore() override; + ErrCode HandleBackup(bool isClearData) override; + ErrCode HandleRestore(bool isClearData) override; ErrCode GetIncrementalFileHandle(const std::string &fileName) override; ErrCode PublishIncrementalFile(const std::string &fileName) override; ErrCode HandleIncrementalBackup(UniqueFd incrementalFd, UniqueFd manifestFd) override; - ErrCode IncrementalOnBackup() override; + ErrCode IncrementalOnBackup(bool isClearData) override; std::tuple GetIncrementalBackupFileHandle() override; ErrCode GetBackupInfo(std::string &result) override; ErrCode UpdateFdSendRate(std::string &bundleName, int32_t sendRate) override; - void AsyncTaskRestoreForUpgrade(void); void ExtClear(void); void AsyncTaskIncrementalRestoreForUpgrade(void); + ErrCode User0OnBackup() override; public: - explicit BackupExtExtension(const std::shared_ptr &extension) : extension_(extension) + explicit BackupExtExtension(const std::shared_ptr &extension, + const std::string &bundleName) : extension_(extension) { + if (extension_ != nullptr) { + extension_->SetBackupExtExtension(this); + } + bundleName_ = bundleName; threadPool_.Start(BConstants::EXTENSION_THREAD_POOL_COUNT); + onProcessTaskPool_.Start(BConstants::EXTENSION_THREAD_POOL_COUNT); + reportOnProcessRetPool_.Start(BConstants::EXTENSION_THREAD_POOL_COUNT); + SetStagingPathProperties(); } ~BackupExtExtension() { + onProcessTimeoutTimer_.Shutdown(); threadPool_.Stop(); + onProcessTaskPool_.Stop(); + reportOnProcessRetPool_.Stop(); + if (callJsOnProcessThread_.joinable()) { + callJsOnProcessThread_.join(); + } } private: @@ -86,7 +103,7 @@ private: * * @param fileName name of the file that to be untar */ - int DoRestore(const string &fileName); + int DoRestore(const string &fileName, const off_t fileSize); /** * @brief incremental restore @@ -112,6 +129,14 @@ private: void AppResultReport(const std::string restoreRetInfo, BackupRestoreScenario scenario, ErrCode errCode = 0); + /** + * @brief extension process Info + * + * @param restoreRetInfo app processInfo + * @param scenario backup or restore + */ + void ReportAppProcessInfo(const std::string processInfo, BackupRestoreScenario scenario); + /** * @brief Executing Backup Tasks Asynchronously * @@ -141,6 +166,14 @@ private: void AsyncTaskOnBackup(); + bool IfAllowToBackupRestore(); + + void AsyncTaskUser0Backup(); + + void DoUser0Backup(const BJsonEntityExtensionConfig &usrConfig); + + int User0DoBackup(const BJsonEntityExtensionConfig &usrConfig); + int DoIncrementalBackup(const std::vector &allFiles, const std::vector &smallFiles, const std::vector &bigFiles); @@ -153,13 +186,17 @@ private: void AsyncTaskDoIncrementalBackup(UniqueFd incrementalFd, UniqueFd manifestFd); void AsyncTaskOnIncrementalBackup(); + int DoIncrementalBackupTask(UniqueFd incrementalFd, UniqueFd manifestFd); ErrCode IncrementalBigFileReady(const TarMap &pkgInfo, const vector &bigInfos, sptr proxy); - ErrCode BigFileReady(sptr proxy); + ErrCode BigFileReady(const TarMap &bigFileInfo, sptr proxy); void WaitToSendFd(std::chrono::system_clock::time_point &startTime, int &fdSendNum); void RefreshTimeInfo(std::chrono::system_clock::time_point &startTime, int &fdSendNum); void IncrementalPacket(const vector &infos, TarMap &tar, sptr proxy); - + void DoPacket(const map &srcFiles, TarMap &tar, sptr proxy); + void CheckTmpDirFileInfos(bool isSpecialVersion = false); + std::map GetIdxFileInfos(bool isSpecialVersion = false); + tuple> CheckRestoreFileInfos(); /** * @brief extension incremental backup restore is done * @@ -168,45 +205,128 @@ private: void AppIncrementalDone(ErrCode errCode); /** - * @brief get callbackEx for execute onRestore + * @brief start extension timer by ipc * - * @param errCode + * @param result */ - std::function RestoreResultCallbackEx(wptr obj); + void StartExtTimer(bool &isExtStart); /** - * @brief get callbackEx for execute onRestore with string param + * @brief start fwk timer by ipc * * @param errCode */ - std::function IncRestoreResultCallbackEx(wptr obj); + void StartFwkTimer(bool &isFwkStart); /** * @brief get callbackEx for execute onRestore * - * @param errCode + * @param obj + */ + std::function IncreOnRestoreExCallback(wptr obj); + + /** + * @brief get increCallback for execute onRestore with string param + * + * @param obj */ - std::function IncAppDoneCallbackEx(wptr obj); + std::function IncreOnRestoreCallback(wptr obj); + + /** + * @brief get callback for execute onRestore with string param + * + * @param obj + */ + std::function OnRestoreCallback(wptr obj); + + /** + * @brief get increCallbackEx for execute onRestore with string param + * + * @param obj + */ + std::function OnRestoreExCallback(wptr obj); /** * @brief get callbackEx for execute appDone */ std::function AppDoneCallbackEx(wptr obj); - std::function HandleBackupEx(wptr obj); - std::function HandleTaskBackupEx(wptr obj); + + std::function IncOnBackupExCallback(wptr obj); + std::function IncOnBackupCallback(wptr obj); + + std::function OnBackupExCallback(wptr obj); + std::function OnBackupCallback(wptr obj); + + void HandleSpecialVersionRestore(); + void DeleteBackupIncrementalIdxFile(); + void DeleteBackupIdxFile(); + void DeleteBackupIncrementalTars(const string &tarName); + void SetClearDataFlag(bool isClearData); + std::string GetBundlePath(); + std::vector GetExtManageInfo(); + ErrCode RestoreFilesForSpecialCloneCloud(); + void RestoreBigFilesForSpecialCloneCloud(const ExtManageInfo &item); + ErrCode RestoreTarForSpecialCloneCloud(const ExtManageInfo &item); + void RestoreBigFiles(bool appendTargetPath); + void FillEndFileInfos(const std::string &path, const unordered_map &result); + void RestoreBigFileAfter(const string &filePath, const struct stat &sta); + void DealIncreUnPacketResult(const off_t tarFileSize, const std::string &tarFileName, + const std::tuple &result); + + ErrCode StartOnProcessTaskThread(wptr obj, BackupRestoreScenario scenario); + void FinishOnProcessTask(); + void ExecCallOnProcessTask(wptr obj, BackupRestoreScenario scenario); + void AsyncCallJsOnProcessTask(wptr obj, BackupRestoreScenario scenario); + void SyncCallJsOnProcessTask(wptr obj, BackupRestoreScenario scenario); + void StartOnProcessTimeOutTimer(wptr obj, BackupRestoreScenario scenario); + void CloseOnProcessTimeOutTimer(); + void UpdateOnStartTime(); + int32_t GetOnStartTimeCost(); + bool SetStagingPathProperties(); + + std::function ReportErrFileByProc(wptr obj, + BackupRestoreScenario scenario); + ErrCode GetIncreFileHandleForNormalVersion(const std::string &fileName); + void RestoreOneBigFile(const std::string &path, const ExtManageInfo &item, const bool appendTargetPath); + int DealIncreRestoreBigAndTarFile(); + std::function ReportOnProcessResultCallback(wptr obj, + BackupRestoreScenario scenario); + private: std::shared_mutex lock_; std::shared_ptr extension_; std::string backupInfo_; OHOS::ThreadPool threadPool_; std::mutex updateSendRateLock_; - std::atomic isStopSendFd_ {false}; std::condition_variable startSendFdRateCon_; std::condition_variable waitSendFdCon_; std::mutex startSendMutex_; std::mutex waitTimeLock_; std::string bundleName_; int32_t sendRate_ = BConstants::DEFAULT_FD_SEND_RATE; + bool isClearData_ {true}; + bool isDebug_ {true}; + std::map endFileInfos_; + std::map> errFileInfos_; + bool isRpValid_ {false}; + + std::thread callJsOnProcessThread_; + Utils::Timer onProcessTimeoutTimer_ {"onProcessTimeoutTimer_"}; + uint32_t onProcessTimeoutTimerId_ { 0 }; + std::atomic onProcessTimeoutCnt_ { 0 }; + std::atomic stopCallJsOnProcess_ {false}; + std::condition_variable execOnProcessCon_; + std::mutex onProcessLock_; + std::atomic onProcessTimeout_ {false}; + std::chrono::time_point g_onStart; + std::mutex onStartTimeLock_; + AppRadar::DoRestoreInfo radarRestoreInfo_ { 0 }; + OHOS::ThreadPool onProcessTaskPool_; + std::atomic isFirstCallOnProcess_ {false}; + std::atomic isExecAppDone_ {false}; + OHOS::ThreadPool reportOnProcessRetPool_; + + BackupRestoreScenario curScenario_ { BackupRestoreScenario::FULL_BACKUP }; }; } // namespace OHOS::FileManagement::Backup diff --git a/frameworks/native/backup_ext/include/ext_extension_stub.h b/frameworks/native/backup_ext/include/ext_extension_stub.h index 86949011af210e039bee4e19cefc7db7f562b69f..d969b3e9b80d5b8d491ced905c02ab2c7a6a9876 100644 --- a/frameworks/native/backup_ext/include/ext_extension_stub.h +++ b/frameworks/native/backup_ext/include/ext_extension_stub.h @@ -43,6 +43,7 @@ private: ErrCode CmdGetIncrementalBackupFileHandle(MessageParcel &data, MessageParcel &reply); ErrCode CmdGetBackupInfo(MessageParcel &data, MessageParcel &reply); ErrCode CmdUpdateFdSendRate(MessageParcel &data, MessageParcel &reply); + ErrCode CmdHandleUser0Backup(MessageParcel &data, MessageParcel &reply); private: using ExtensionInterface = int32_t (ExtExtensionStub::*)(MessageParcel &data, MessageParcel &reply); diff --git a/frameworks/native/backup_ext/include/tar_file.h b/frameworks/native/backup_ext/include/tar_file.h index 4cfdb490a79026079555a274d8f4299826bbb9d1..2d19e241e20b368869d3a0419f3b6c3366d529aa 100644 --- a/frameworks/native/backup_ext/include/tar_file.h +++ b/frameworks/native/backup_ext/include/tar_file.h @@ -86,7 +86,8 @@ public: bool Packet(const std::vector &srcFiles, const std::string &tarFileName, const std::string &pkPath, - TarMap &tarMap); + TarMap &tarMap, + std::function reportCb); /** * @brief set packet mode @@ -108,7 +109,7 @@ private: * @return true 遍历成功 * @return false 遍历失败 */ - bool TraversalFile(std::string &fileName); + bool TraversalFile(std::string &fileName, int &err); /** * @brief add files to the tar package @@ -116,7 +117,7 @@ private: * @param filename 文件名 * @param st 文件参数结构体 */ - bool AddFile(std::string &fileName, const struct stat &st); + bool AddFile(std::string &fileName, const struct stat &st, int &err); /** * @brief write files to content @@ -124,7 +125,7 @@ private: * @param filename 文件名 * @param size 文件大小 */ - bool WriteFileContent(const std::string &fileName, off_t size); + bool WriteFileContent(const std::string &fileName, off_t size, int &err); /** * @brief split write diff --git a/frameworks/native/backup_ext/include/untar_file.h b/frameworks/native/backup_ext/include/untar_file.h index 8d890b8339cfa3445741b762bb30b80449e8069d..b997490fbbeb619e468bfdadb76d7f54d381920f 100644 --- a/frameworks/native/backup_ext/include/untar_file.h +++ b/frameworks/native/backup_ext/include/untar_file.h @@ -28,13 +28,22 @@ struct FileStatInfo { off_t mtime {0}; std::string longName {}; }; + +using ErrFileInfo = std::map>; +using EndFileInfo = std::map; + +const int FIRST_PARAM = 0; +const int SECOND_PARAM = 1; +const int THIRD_PARAM = 2; class UntarFile { public: typedef enum { ERR_FORMAT = -1 } ErrorCode; static UntarFile &GetInstance(); - int UnPacket(const std::string &tarFile, const std::string &rootPath); - int IncrementalUnPacket(const std::string &tarFile, const std::string &rootPath, - const std::unordered_map &includes); + std::tuple UnPacket( + const std::string &tarFile, const std::string &rootPath); + std::tuple IncrementalUnPacket( + const std::string &tarFile, const std::string &rootPath, + const std::unordered_map &includes); private: UntarFile() = default; @@ -47,14 +56,14 @@ private: * * @param rootpath 解包的目标路径 */ - int ParseTarFile(const std::string &rootPath); + std::tuple ParseTarFile(const std::string &rootPath); /** * @brief parse incremental tar file * * @param rootpath 解包的目标路径 */ - int ParseIncrementalTarFile(const std::string &rootPath); + std::tuple ParseIncrementalTarFile(const std::string &rootPath); /** * @brief verfy check sum @@ -84,16 +93,14 @@ private: * @param path 文件路径名 * @param mode 文件打开模式 */ - void CreateDir(std::string &path, mode_t mode); + ErrFileInfo CreateDir(std::string &path, mode_t mode); /** * @brief creat a file * * @param path 文件路径名 - * @param mode 文件打开模式 - * @param fileType 文件类型 */ - FILE *CreateFile(std::string &path, mode_t mode, char fileType); + FILE *CreateFile(std::string &path); /** * @brief parse regular file @@ -101,7 +108,7 @@ private: * @param info 文件属性结构体 * @param typeFlag 文件类型标志 */ - void ParseRegularFile(FileStatInfo &info, char typeFlag); + ErrFileInfo ParseRegularFile(FileStatInfo &info); /** * @brief handle tar buffer @@ -110,7 +117,7 @@ private: * @param name 文件名 * @param info 文件属性结构体 */ - void HandleTarBuffer(const std::string &buff, const std::string &name, FileStatInfo &info); + off_t HandleTarBuffer(const std::string &buff, const std::string &name, FileStatInfo &info); /** * @brief parse file by typeFlag @@ -118,7 +125,7 @@ private: * @param typeFlag 文件类型标志 * @param info 文件属性结构体 */ - void ParseFileByTypeFlag(char typeFlag, FileStatInfo &info); + std::tuple ParseFileByTypeFlag(char typeFlag, FileStatInfo &info); /** * @brief parse incremental file by typeFlag @@ -126,7 +133,63 @@ private: * @param typeFlag 文件类型标志 * @param info 文件属性结构体 */ - int ParseIncrementalFileByTypeFlag(char typeFlag, FileStatInfo &info); + std::tuple ParseIncrementalFileByTypeFlag(char typeFlag, FileStatInfo &info); + + /** + * @brief Check tar and fill tar size + */ + int CheckAndFillTarSize(); + + /** + * @brief Read long name and recode errinfo + * + * @param info file state info + */ + std::tuple ReadLongName(FileStatInfo &info); + + /** + * @brief deal parse tar file result + * + * @param result parse tar file result info + * @param fileSize size of the file in tar + * @param fileName file state info + * @param fileInfos out param, record file info + * @param errInfos out param, record err file info + */ + int DealParseTarFileResult(const std::tuple &result, + const off_t fileSize, const std::string &fileName, EndFileInfo &fileInfos, ErrFileInfo &errInfos); + + /** + * @brief deal incremental parse tar file result + * + * @param result parse tar file result info + * @param fileSize size of the file in tar + * @param fileName file state info + * @param fileInfos out param, record file info + * @param errInfos out param, record err file info + */ + int DealIncreParseTarFileResult(const std::tuple &result, + const off_t fileSize, const std::string &fileName, EndFileInfo &fileInfos, ErrFileInfo &errInfos); + + /** + * @brief check if tar block valid + * + * @param buff check buff info + * @param header check header info + * @param ret out param, the err info + */ + bool CheckIfTarBlockValid(char *buff, size_t buffLen, TarHeader *header, int &ret); + + /** + * @brief deal file tag info + * + * @param errFileInfo out param, err file info + * @param info out param, file info + * @param isFilter out param, is Filter + * @param tmpFullPath in param, tmpFullPath + */ + bool DealFileTag(ErrFileInfo &errFileInfo, + FileStatInfo &info, bool &isFilter, const std::string &tmpFullPath); private: std::string rootPath_ {}; diff --git a/frameworks/native/backup_ext/src/ext_backup.cpp b/frameworks/native/backup_ext/src/ext_backup.cpp index 2805185963c0be7423dfb13b6363020190c4c0c1..53da3a7ea9b9c2cf6393b9cd3208f7897e3627ef 100644 --- a/frameworks/native/backup_ext/src/ext_backup.cpp +++ b/frameworks/native/backup_ext/src/ext_backup.cpp @@ -45,6 +45,11 @@ void ExtBackup::SetCreator(const CreatorFunc &creator) creator_ = creator; } +void ExtBackup::SetBackupExtExtension(const wptr &extExtension) +{ + bakExtExtension_ = extExtension; +} + void ExtBackup::Init(const shared_ptr &record, const shared_ptr &application, shared_ptr &handler, @@ -100,6 +105,11 @@ string ExtBackup::GetUsrConfig() const if (!client.GetProfileFromAbility(info, "ohos.extension.backup", config)) { throw BError(BError::Codes::EXT_INVAL_ARG, "Failed to invoke the GetProfileFromAbility method."); } + if (config.empty()) { + HILOGE("GetUsrConfig empty."); + } else { + HILOGI("GetUsrConfig:%{public}s", config[0].c_str()); + } return config.empty() ? "" : config[0]; } @@ -188,13 +198,8 @@ sptr ExtBackup::OnConnect(const AAFwk::Want &want) Extension::OnConnect(want); auto remoteObject = - sptr(new BackupExtExtension(std::static_pointer_cast(shared_from_this()))); - - // 排除特殊场景 - if (!WasFromSpecialVersion() && !RestoreDataReady()) { - remoteObject->ExtClear(); - } - + sptr(new BackupExtExtension(std::static_pointer_cast(shared_from_this()), + want.GetBundle())); return remoteObject->AsObject(); } catch (const BError &e) { return nullptr; @@ -211,6 +216,10 @@ void ExtBackup::OnDisconnect(const AAFwk::Want &want) { try { HILOGI("begin disconnect"); + sptr extExtension = bakExtExtension_.promote(); + if (extExtension != nullptr) { + extExtension->ExtClear(); + } Extension::OnDisconnect(want); extAction_ = BConstants::ExtensionAction::INVALID; HILOGI("end"); @@ -291,4 +300,10 @@ ErrCode ExtBackup::InvokeAppExtMethod(ErrCode errCode, const std::string result) return ERR_OK; } +ErrCode ExtBackup::OnProcess(std::function callback) +{ + HILOGI("BackupExtensionAbility(base) OnProcess."); + return ERR_OK; +} + } // namespace OHOS::FileManagement::Backup diff --git a/frameworks/native/backup_ext/src/ext_backup_context.cpp b/frameworks/native/backup_ext/src/ext_backup_context.cpp index 87a8a03ddb2ab4ae805533871ac0b2c7b52703c6..3df12d334c76ba820e9388b8ba3533540f5a8fc2 100644 --- a/frameworks/native/backup_ext/src/ext_backup_context.cpp +++ b/frameworks/native/backup_ext/src/ext_backup_context.cpp @@ -15,6 +15,7 @@ #include "ext_backup_context.h" +#include "b_filesystem/b_file.h" #include "b_resources/b_constants.h" namespace OHOS::FileManagement::Backup { @@ -24,7 +25,16 @@ const std::string ExtBackupContext::GetBackupDir() if (area > 1) { // 1 : el2 area return ""; } - return std::string(BConstants::BACKUP_DIR_PRE) + std::string(BConstants::CONTEXT_ELS[area]) + + + std::string path = std::string(BConstants::BACKUP_DIR_PRE) + std::string(BConstants::CONTEXT_ELS[area]) + std::string(BConstants::BACKUP_DIR_END); + std::string bundleName = GetBundleName(); + if (BFile::EndsWith(bundleName, BConstants::BUNDLE_FILE_MANAGER) && bundleName.size() == BConstants::FM_LEN) { + path = std::string(BConstants::PATH_FILEMANAGE_BACKUP_HOME) + BConstants::FILE_SEPARATOR_CHAR; + } else if (bundleName == BConstants::BUNDLE_MEDIAL_DATA) { + path = std::string(BConstants::PATH_MEDIALDATA_BACKUP_HOME) + BConstants::FILE_SEPARATOR_CHAR; + } + + return path; } } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/frameworks/native/backup_ext/src/ext_backup_js.cpp b/frameworks/native/backup_ext/src/ext_backup_js.cpp index bb3de776cd0ab285aa9396914da0812a13d0afc3..407d151e0317f84ee73602ca4a99f49d365cc2c6 100644 --- a/frameworks/native/backup_ext/src/ext_backup_js.cpp +++ b/frameworks/native/backup_ext/src/ext_backup_js.cpp @@ -1,5 +1,5 @@ /* - * Copyright (c) 2022-2024 Huawei Device Co., Ltd. + * Copyright (c) 2022-2025 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at @@ -35,17 +35,22 @@ #include "napi_remote_object.h" #include "unique_fd.h" +#include "b_anony/b_anony.h" #include "b_error/b_error.h" #include "b_error/b_excep_utils.h" #include "b_json/b_json_cached_entity.h" #include "b_json/b_json_entity_extension_config.h" +#include "b_radar/b_radar.h" #include "b_resources/b_constants.h" +#include "directory_ex.h" #include "ext_extension.h" #include "filemgmt_libhilog.h" namespace OHOS::FileManagement::Backup { using namespace std; constexpr size_t ARGC_ONE = 1; +static std::mutex g_extBackupValidLock; +static int32_t g_extBackupCount = 0; static string GetSrcPath(const AppExecFwk::AbilityInfo &info) { @@ -84,12 +89,10 @@ static napi_status DealNapiStrValue(napi_env env, const napi_value napi_StrValue return status; } -static napi_status DealNapiException(napi_env env, std::string &exceptionInfo) +static napi_status DealNapiException(napi_env env, napi_value &exception, std::string &exceptionInfo) { HILOGI("call DealNapiException start."); - napi_status status; - napi_value exception; - status = napi_get_and_clear_last_exception(env, &exception); + napi_status status = napi_get_and_clear_last_exception(env, &exception); if (status != napi_ok) { HILOGE("call napi_get_and_clear_last_exception failed."); return status; @@ -105,6 +108,11 @@ static napi_status DealNapiException(napi_env env, std::string &exceptionInfo) static napi_value PromiseCallback(napi_env env, napi_callback_info info) { + std::lock_guard lock(g_extBackupValidLock); + if (g_extBackupCount <= 0) { + HILOGE("ExtBackup is invalid, count=%{public}d", g_extBackupCount); + return nullptr; + } HILOGI("Promise callback."); void *data = nullptr; if (napi_get_cb_info(env, info, nullptr, 0, nullptr, &data) != napi_ok) { @@ -124,7 +132,7 @@ static napi_value PromiseCallback(napi_env env, napi_callback_info info) static napi_value PromiseCatchCallback(napi_env env, napi_callback_info info) { - HILOGI("Promise catch callback."); + HILOGI("Promise catch callback begin."); size_t argc = 1; napi_value argv = {nullptr}; void *data = nullptr; @@ -137,13 +145,30 @@ static napi_value PromiseCatchCallback(napi_env env, napi_callback_info info) HILOGE("CallbackInfo is nullptr"); return nullptr; } + napi_status throwStatus = napi_fatal_exception(env, argv); + if (throwStatus != napi_ok) { + HILOGE("Failed to throw an exception, %{public}d", throwStatus); + return nullptr; + } + std::lock_guard lock(g_extBackupValidLock); + if (g_extBackupCount <= 0) { + HILOGE("ExtBackup is invalid, count=%{public}d", g_extBackupCount); + data = nullptr; + return nullptr; + } callbackInfo->callback(BError(BError::Codes::EXT_THROW_EXCEPTION), exceptionInfo); data = nullptr; + HILOGI("Promise catch callback end."); return nullptr; } static napi_value PromiseCallbackEx(napi_env env, napi_callback_info info) { + std::lock_guard lock(g_extBackupValidLock); + if (g_extBackupCount <= 0) { + HILOGE("ExtBackup is invalid, count=%{public}d", g_extBackupCount); + return nullptr; + } HILOGI("PromiseEx callback."); void *data = nullptr; std::string str; @@ -163,7 +188,7 @@ static napi_value PromiseCallbackEx(napi_env env, napi_callback_info info) static napi_value PromiseCatchCallbackEx(napi_env env, napi_callback_info info) { - HILOGI("PromiseEx catch callback."); + HILOGI("PromiseEx catch callback begin."); void *data = nullptr; size_t argc = 1; napi_value argv = {nullptr}; @@ -176,8 +201,20 @@ static napi_value PromiseCatchCallbackEx(napi_env env, napi_callback_info info) HILOGE("CallbackInfo is nullPtr"); return nullptr; } + napi_status throwStatus = napi_fatal_exception(env, argv); + if (throwStatus != napi_ok) { + HILOGE("Failed to throw an exception, %{public}d", throwStatus); + return nullptr; + } + std::lock_guard lock(g_extBackupValidLock); + if (g_extBackupCount <= 0) { + HILOGE("ExtBackup is invalid, count=%{public}d", g_extBackupCount); + data = nullptr; + return nullptr; + } callbackInfoEx->callbackParam(BError(BError::Codes::EXT_THROW_EXCEPTION), exceptionInfo); data = nullptr; + HILOGI("PromiseEx catch callback end."); return nullptr; } @@ -347,6 +384,7 @@ void ExtBackupJs::Init(const shared_ptr &record, // 获取应用扩展的 BackupExtensionAbility 的路径 const AppExecFwk::AbilityInfo &info = *abilityInfo_; string bundleName = info.bundleName; + InitTempPath(bundleName); string moduleName(info.moduleName + "::" + info.name); string modulePath = GetSrcPath(info); int moduleType = static_cast(info.type); @@ -402,16 +440,36 @@ napi_value AttachBackupExtensionContext(napi_env env, void *value, void *) HILOGE("Failed to get backup extension context"); return nullptr; } - napi_wrap( + napi_status status = napi_wrap( env, contextObj, workContext, [](napi_env, void *data, void *) { HILOG_DEBUG("Finalizer for weak_ptr base context is called"); delete static_cast *>(data); }, nullptr, nullptr); + if (status != napi_ok) { + HILOG_DEBUG("Failed to wrap js instance"); + delete workContext; + workContext = nullptr; + } return contextObj; } +ExtBackupJs::ExtBackupJs(AbilityRuntime::JsRuntime &jsRuntime) : jsRuntime_(jsRuntime) +{ + std::lock_guard lock(g_extBackupValidLock); + g_extBackupCount += 1; + HILOGI("ExtBackupJs::ExtBackupJs, count=%{public}d.", g_extBackupCount); +} + +ExtBackupJs::~ExtBackupJs() +{ + jsRuntime_.FreeNativeReference(std::move(jsObj_)); + std::lock_guard lock(g_extBackupValidLock); + g_extBackupCount -= 1; + HILOGI("ExtBackupJs::~ExtBackupJs, count=%{public}d.", g_extBackupCount); +} + void ExtBackupJs::ExportJsContext(void) { auto env = jsRuntime_.GetNapiEnv(); @@ -451,13 +509,18 @@ void ExtBackupJs::ExportJsContext(void) napi_coerce_to_native_binding_object(env, contextObj, AbilityRuntime::DetachCallbackFunc, AttachBackupExtensionContext, workContext, nullptr); HILOGI("Set backup extension ability context pointer is nullptr: %{public}d", context.get() == nullptr); - napi_wrap( + napi_status status = napi_wrap( env, contextObj, workContext, [](napi_env, void *data, void *) { HILOG_DEBUG("Finalizer for weak_ptr base context is called"); delete static_cast *>(data); }, nullptr, nullptr); + if (status != napi_ok) { + HILOG_DEBUG("Failed to wrap js instance"); + delete workContext; + workContext = nullptr; + } } [[maybe_unused]] tuple ExtBackupJs::CallObjectMethod(string_view name, @@ -499,7 +562,9 @@ ErrCode ExtBackupJs::CallJsOnBackupEx() napi_is_exception_pending(envir, &isExceptionPending); HILOGI("napi exception pending = %{public}d.", isExceptionPending); if (isExceptionPending) { - DealNapiException(envir, str); + napi_value exception; + DealNapiException(envir, exception, str); + napi_fatal_exception(envir, exception); callbackInfoEx->callbackParam(BError(BError::Codes::EXT_THROW_EXCEPTION), str); } else { DealNapiStrValue(envir, result, str); @@ -537,7 +602,9 @@ ErrCode ExtBackupJs::CallJsOnBackup() napi_is_exception_pending(env, &isExceptionPending); HILOGI("napi exception pending = %{public}d.", isExceptionPending); if (isExceptionPending) { - DealNapiException(env, str); + napi_value exception; + DealNapiException(env, exception, str); + napi_fatal_exception(env, exception); callbackInfo->callback(BError(BError::Codes::EXT_THROW_EXCEPTION), str); } else { callbackInfo->callback(BError(BError::Codes::OK), str); @@ -580,7 +647,9 @@ ErrCode ExtBackupJs::CallJSRestoreEx() napi_is_exception_pending(envir, &isExceptionPending); HILOGI("napi exception pending = %{public}d.", isExceptionPending); if (isExceptionPending) { - DealNapiException(envir, str); + napi_value exception; + DealNapiException(envir, exception, str); + napi_fatal_exception(envir, exception); callbackInfoEx->callbackParam(BError(BError::Codes::EXT_THROW_EXCEPTION), str); } else { DealNapiStrValue(envir, result, str); @@ -617,7 +686,9 @@ ErrCode ExtBackupJs::CallJSRestore() napi_is_exception_pending(env, &isExceptionPending); HILOGI("napi exception pending = %{public}d.", isExceptionPending); if (isExceptionPending) { - DealNapiException(env, str); + napi_value exception; + DealNapiException(env, exception, str); + napi_fatal_exception(env, exception); callbackInfo->callback(BError(BError::Codes::EXT_THROW_EXCEPTION), str); } else { callbackInfo->callback(BError(BError::Codes::OK), str); @@ -644,6 +715,16 @@ ErrCode ExtBackupJs::GetBackupInfo(std::function bool { if (!CheckPromise(env, result)) { + bool isExceptionPending; + napi_is_exception_pending(env, &isExceptionPending); + HILOGI("napi exception pending = %{public}d.", isExceptionPending); + if (isExceptionPending) { + string str; + napi_value exception; + DealNapiException(env, exception, str); + callBackInfo->callbackParam(BError(BError::Codes::EXT_THROW_EXCEPTION), str); + return false; + } size_t strLen = 0; napi_status status = napi_get_value_string_utf8(env, result, nullptr, -1, &strLen); if (status != napi_ok) { @@ -706,7 +787,7 @@ static int DoCallJsMethod(CallJsParam *param) return EINVAL; } napi_value result; - HILOGI("Extension start do call current js method"); + HILOGI("Extension start do call current js method, methodName:%{public}s", param->funcName.c_str()); napi_call_function(env, value, method, argv.size(), argv.data(), &result); if (!param->retParser(env, handleEscape.Escape(result))) { HILOGE("Parser js result fail."); @@ -753,8 +834,9 @@ int ExtBackupJs::CallJsMethod(const std::string &funcName, } } while (false); HILOGI("will notify current thread info"); + std::unique_lock lock(param->backupOperateMutex); param->isReady.store(true); - param->backupOperateCondition.notify_one(); + param->backupOperateCondition.notify_all(); }); if (ret != 0) { HILOGE("failed to exec uv_queue_work."); @@ -772,7 +854,7 @@ std::function &argv)> ExtBackupJs::Pa auto onBackupExFun = [backupExtInfo(backupExtInfo_)](napi_env env, vector &argv) -> bool { napi_value backupExtInfoVal = nullptr; napi_create_object(env, &backupExtInfoVal); - HILOGI("backupExtInfo is:%{public}s", backupExtInfo.c_str()); + HILOGI("backupExtInfo is:%{public}s", GetAnonyString(backupExtInfo).c_str()); napi_create_string_utf8(env, backupExtInfo.c_str(), backupExtInfo.size(), &backupExtInfoVal); argv.push_back(backupExtInfoVal); return true; @@ -784,7 +866,7 @@ std::function &argv)> ExtBackupJs::Pa { auto onRestoreExFun = [appVersionCode(appVersionCode_), appVersionStr(appVersionStr_), restoreExtInfo(restoreExtInfo_)](napi_env env, vector &argv) -> bool { - HILOGI("restoreExtInfo is:%{public}s", restoreExtInfo.c_str()); + HILOGI("restoreExtInfo is:%{public}s", GetAnonyString(restoreExtInfo).c_str()); napi_value objValue = nullptr; napi_value restoreRetValue = nullptr; napi_create_object(env, &objValue); @@ -838,4 +920,60 @@ ErrCode ExtBackupJs::InvokeAppExtMethod(ErrCode errCode, const std::string resul HILOGI("End Get App onBackupEx/onRestoreEx method result"); return ERR_OK; } + +ErrCode ExtBackupJs::OnProcess(std::function callback) +{ + HILOGI("BackupExtensionAbility(JS) OnProcess begin."); + BExcepUltils::BAssert(jsObj_, BError::Codes::EXT_BROKEN_FRAMEWORK, + "The app does not provide the OnProcess interface."); + onProcessCallback_ = std::make_shared(callback); + auto retParser = [jsRuntime {&jsRuntime_}, callBackInfo {onProcessCallback_}](napi_env env, + napi_value result) -> bool { + string processStr; + bool isExceptionPending; + napi_is_exception_pending(env, &isExceptionPending); + HILOGI("napi exception pending = %{public}d.", isExceptionPending); + if (isExceptionPending) { + napi_value exception; + napi_get_and_clear_last_exception(env, &exception); + callBackInfo->onProcessCallback(BError(BError::Codes::EXT_THROW_EXCEPTION), processStr); + } else { + DealNapiStrValue(env, result, processStr); + callBackInfo->onProcessCallback(BError(BError::Codes::OK), processStr); + } + return true; + }; + auto errCode = CallJsMethod("onProcess", jsRuntime_, jsObj_.get(), {}, retParser); + if (errCode != ERR_OK) { + HILOGE("CallJsMethod error, code:%{public}d.", errCode); + } + HILOGI("BackupExtensionAbulity(JS) OnProcess end."); + return errCode; +} + +void ExtBackupJs::InitTempPath(const std::string &bundleName) +{ + std::string el2BackupDir(BConstants::PATH_BUNDLE_BACKUP_HOME); + if (access(el2BackupDir.c_str(), F_OK) != 0) { + HILOGW("backup home el2 dir not exits, try to create"); + if (!ForceCreateDirectory(el2BackupDir.data())) { + HILOGE("Failed to create directory, err = %{public}d", errno); + AppRadar::Info info(bundleName, "", "Create backup home el2 dir failed"); + AppRadar::GetInstance().RecordDefaultFuncRes(info, "ExtBackupJs::InitTempPath", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_DEFAULT, + static_cast(BError::Codes::EXT_CREATE_DIR_ERROR)); + } + } + std::string el1BackupDir(BConstants::PATH_BUNDLE_BACKUP_HOME_EL1); + if (access(el1BackupDir.c_str(), F_OK) != 0) { + HILOGW("backup home el1 dir not exits, try to create"); + if (!ForceCreateDirectory(el1BackupDir.data())) { + HILOGE("Failed to create home el1 dir, err = %{public}d", errno); + AppRadar::Info info(bundleName, "", "Create backup home el1 dir failed"); + AppRadar::GetInstance().RecordDefaultFuncRes(info, "ExtBackupJs::InitTempPath", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_DEFAULT, + static_cast(BError::Codes::EXT_CREATE_DIR_ERROR)); + } + } +} } // namespace OHOS::FileManagement::Backup diff --git a/frameworks/native/backup_ext/src/ext_extension.cpp b/frameworks/native/backup_ext/src/ext_extension.cpp index 071569fdddcb02111e4cac70bc71abf7ae9cfebd..a10fbcf63efe766ed7cc7951e1c6eef78a344ebb 100644 --- a/frameworks/native/backup_ext/src/ext_extension.cpp +++ b/frameworks/native/backup_ext/src/ext_extension.cpp @@ -46,6 +46,7 @@ #include "b_filesystem/b_file_hash.h" #include "b_json/b_json_cached_entity.h" #include "b_jsonutil/b_jsonutil.h" +#include "b_ohos/startup/backup_para.h" #include "b_tarball/b_tarball_factory.h" #include "filemgmt_libhilog.h" #include "hitrace_meter.h" @@ -53,11 +54,9 @@ #include "sandbox_helper.h" #include "service_proxy.h" #include "tar_file.h" -#include "untar_file.h" #include "b_anony/b_anony.h" namespace OHOS::FileManagement::Backup { -const string DEFAULT_TAR_PKG = "1.tar"; const string INDEX_FILE_BACKUP = string(BConstants::PATH_BUNDLE_BACKUP_HOME). append(BConstants::SA_BUNDLE_BACKUP_BACKUP). append(BConstants::EXT_BACKUP_MANAGE); @@ -66,20 +65,82 @@ const string INDEX_FILE_RESTORE = string(BConstants::PATH_BUNDLE_BACKUP_HOME). append(BConstants::EXT_BACKUP_MANAGE); const string INDEX_FILE_INCREMENTAL_BACKUP = string(BConstants::PATH_BUNDLE_BACKUP_HOME). append(BConstants::SA_BUNDLE_BACKUP_BACKUP); +const string MEDIA_LIBRARY_BUNDLE_NAME = "com.ohos.medialibrary.medialibrarydata"; +const string FILE_MANAGER_BUNDLE_NAME = "com.ohos.filepicker"; using namespace std; -namespace { -const int64_t DEFAULT_SLICE_SIZE = 100 * 1024 * 1024; // 分片文件大小为100M -const uint32_t MAX_FILE_COUNT = 6000; // 单个tar包最多包含6000个文件 -const uint32_t MAX_FD_GROUP_USE_TIME = 1000; // 每组打开最大时间1000ms -const int FILE_AND_MANIFEST_FD_COUNT = 2; // 每组文件和简报数量统计 +static void RecordDoRestoreRes(const std::string &bundleName, const std::string &func, + AppRadar::DoRestoreInfo &restoreInfo) +{ + std::stringstream ss; + ss << R"("bigFileNums": )" << restoreInfo.bigFileNum << ", "; + ss << R"("bigFileSize": )" << restoreInfo.bigFileSize << ", "; + ss << R"("RestoreBigFileTime": )" << restoreInfo.bigFileSpendTime << ", "; + ss << R"("unTarFileNums": )" << restoreInfo.tarFileNum << ", "; + ss << R"("unTarFileSize": )" << restoreInfo.tarFileSize << ", "; + ss << R"("unTarTime": )" << restoreInfo.tarFileSpendTime << ", "; + ss << R"("totalFileNum": )" << restoreInfo.bigFileNum + restoreInfo.tarFileNum << ", "; + ss << R"("totalFileSize": )" << restoreInfo.bigFileSize + restoreInfo.tarFileSize << ", "; + ss << R"("restoreAllFileTime": )" << restoreInfo.totalFileSpendTime; + int32_t err = static_cast(BError::Codes::OK); + AppRadar::Info info (bundleName, "", ss.str()); + AppRadar::GetInstance().RecordRestoreFuncRes(info, func, AppRadar::GetInstance().GetUserId(), + BizStageRestore::BIZ_STAGE_DO_RESTORE, err); +} + +static void RecordDoBackupRes(const std::string &bundleName, const ErrCode errCode, AppRadar::DoBackupInfo &backupInfo) +{ + uint32_t inExcludeNum = backupInfo.includeNum + backupInfo.excludeNum; + if (inExcludeNum >= BConstants::MAX_INEXCLUDE_SIZE) { + AppRadar::Info infoInExclude(bundleName, "", string("\"total inExclude\":").append(to_string(inExcludeNum))); + AppRadar::GetInstance().RecordBackupFuncRes(infoInExclude, "BackupExtExtension::DoBackup", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_DO_BACKUP, ERR_OK); + } + if (errCode == ERR_OK && backupInfo.cost >= BConstants::MAX_TIME_COST) { + std::stringstream ss; + ss << R"("spendTime": )" << backupInfo.cost << "ms, "; + ss << R"("totalFilesNum": )" << backupInfo.allFileNum << ", "; + ss << R"("smallFilesNum": )" << backupInfo.smallFileNum << ", "; + ss << R"("bigFilesNum": )" << backupInfo.allFileNum - backupInfo.tarFileNum; + AppRadar::Info info(bundleName, "", ss.str()); + AppRadar::GetInstance().RecordBackupFuncRes(info, "BackupExtExtension::DoBackup", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_DO_BACKUP, errCode); + } +} + +static string GetIndexFileRestorePath(const string &bundleName) +{ + if (BFile::EndsWith(bundleName, BConstants::BUNDLE_FILE_MANAGER) && bundleName.size() == BConstants::FM_LEN) { + return string(BConstants::PATH_FILEMANAGE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE). + append(BConstants::EXT_BACKUP_MANAGE); + } else if (bundleName == BConstants::BUNDLE_MEDIAL_DATA) { + return string(BConstants::PATH_MEDIALDATA_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE). + append(BConstants::EXT_BACKUP_MANAGE); + } + return INDEX_FILE_RESTORE; } -static std::set GetIdxFileData() +static string GetRestoreTempPath(const string &bundleName) { - UniqueFd idxFd(open(INDEX_FILE_RESTORE.data(), O_RDONLY)); + string path = string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); + if (BFile::EndsWith(bundleName, BConstants::BUNDLE_FILE_MANAGER) && bundleName.size() == BConstants::FM_LEN) { + if (mkdir(string(BConstants::PATH_FILEMANAGE_BACKUP_HOME).data(), S_IRWXU) && errno != EEXIST) { + string str = string("Failed to create .backup folder. ").append(std::generic_category().message(errno)); + throw BError(BError::Codes::EXT_INVAL_ARG, str); + } + path = string(BConstants::PATH_FILEMANAGE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); + } else if (bundleName == BConstants::BUNDLE_MEDIAL_DATA) { + path = string(BConstants::PATH_MEDIALDATA_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); + } + return path; +} + +static std::set GetIdxFileData(const string &bundleName) +{ + string indexFileRestorePath = GetIndexFileRestorePath(bundleName); + UniqueFd idxFd(open(indexFileRestorePath.data(), O_RDONLY)); if (idxFd < 0) { - HILOGE("Failed to open idxFile = %{private}s, err = %{public}d", INDEX_FILE_RESTORE.c_str(), errno); + HILOGE("Failed to open idxFile = %{private}s, err = %{public}d", indexFileRestorePath.c_str(), errno); return std::set(); } BJsonCachedEntity cachedEntity(std::move(idxFd)); @@ -87,9 +148,10 @@ static std::set GetIdxFileData() return cache.GetExtManage(); } -static std::vector GetExtManageInfo() +std::vector BackupExtExtension::GetExtManageInfo() { - string filePath = BExcepUltils::Canonicalize(INDEX_FILE_RESTORE); + string indexFileRestorePath = GetIndexFileRestorePath(bundleName_); + string filePath = BExcepUltils::Canonicalize(indexFileRestorePath); UniqueFd idxFd(open(filePath.data(), O_RDONLY)); if (idxFd < 0) { HILOGE("Failed to open cano_idxFile = %{private}s, err = %{public}d", filePath.c_str(), errno); @@ -105,12 +167,20 @@ void BackupExtExtension::VerifyCaller() uint32_t tokenCaller = IPCSkeleton::GetCallingTokenID(); int tokenType = Security::AccessToken::AccessTokenKit::GetTokenType(tokenCaller); if (tokenType != Security::AccessToken::ATokenTypeEnum::TOKEN_NATIVE) { + AppRadar::Info info(bundleName_, "", "{\"reason\":\"Calling tokenType error\"}"); + AppRadar::GetInstance().RecordDefaultFuncRes( + info, "BackupExtExtension::VerifyCaller", AppRadar::GetInstance().GetUserId(), + BizStageBackup::BIZ_STAGE_PERMISSION_CHECK_FAIL, BError(BError::Codes::EXT_BROKEN_IPC).GetCode()); throw BError(BError::Codes::EXT_BROKEN_IPC, - string("Calling tokenType is error, token type is ").append(to_string(tokenType))); + string("Calling tokenType is error, token type is ").append(to_string(tokenType))); } if (IPCSkeleton::GetCallingUid() != BConstants::BACKUP_UID) { + AppRadar::Info info(bundleName_, "", "{\"reason\":\"Calling uid invalid\"}"); + AppRadar::GetInstance().RecordDefaultFuncRes( + info, "BackupExtExtension::VerifyCaller", AppRadar::GetInstance().GetUserId(), + BizStageBackup::BIZ_STAGE_PERMISSION_CHECK_FAIL, BError(BError::Codes::EXT_BROKEN_IPC).GetCode()); throw BError(BError::Codes::EXT_BROKEN_IPC, - string("Calling uid is invalid, calling uid is ").append(to_string(IPCSkeleton::GetCallingUid()))); + string("Calling uid is invalid, calling uid is ").append(to_string(IPCSkeleton::GetCallingUid()))); } } @@ -141,14 +211,14 @@ static UniqueFd GetFileHandleForSpecialCloneCloud(const string &fileName) size_t filePathPrefix = filePath.find_last_of(BConstants::FILE_SEPARATOR_CHAR); if (filePathPrefix == string::npos) { HILOGE("GetFileHandleForSpecialCloneCloud: Invalid fileName"); - throw BError(BError::Codes::EXT_INVAL_ARG, fileName); + return UniqueFd(-1); } string path = filePath.substr(0, filePathPrefix); if (access(path.c_str(), F_OK) != 0) { bool created = ForceCreateDirectory(path.data()); if (!created) { - string str = string("Failed to create restore folder."); - throw BError(BError::Codes::EXT_INVAL_ARG, str); + HILOGE("Failed to create restore folder."); + return UniqueFd(-1); } } UniqueFd fd(open(fileName.data(), O_RDWR | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR)); @@ -182,7 +252,7 @@ UniqueFd BackupExtExtension::GetFileHandle(const string &fileName, int32_t &errC return fd; } - string path = string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); + string path = GetRestoreTempPath(bundleName_); if (mkdir(path.data(), S_IRWXU) && errno != EEXIST) { string str = string("Failed to create restore folder. ").append(std::generic_category().message(errno)); throw BError(BError::Codes::EXT_INVAL_ARG, str); @@ -214,43 +284,92 @@ static string GetReportFileName(const string &fileName) static ErrCode GetIncreFileHandleForSpecialVersion(const string &fileName) { + ErrCode errCode = ERR_OK; UniqueFd fd = GetFileHandleForSpecialCloneCloud(fileName); if (fd < 0) { HILOGE("Failed to open file = %{private}s, err = %{public}d", fileName.c_str(), errno); - throw BError(BError::Codes::EXT_INVAL_ARG, string("open tar file failed")); + errCode = errno; } string path = string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); if (mkdir(path.data(), S_IRWXU) && errno != EEXIST) { - string str = string("Failed to create restore folder. ").append(std::generic_category().message(errno)); - throw BError(BError::Codes::EXT_INVAL_ARG, str); + HILOGE("Failed to create restore folder : %{private}s, err = %{public}d", path.c_str(), errno); + errCode = errno; } string reportName = path + BConstants::BLANK_REPORT_NAME; UniqueFd reportFd(open(reportName.data(), O_RDWR | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR)); if (reportFd < 0) { HILOGE("Failed to open report file = %{private}s, err = %{public}d", reportName.c_str(), errno); - throw BError(BError::Codes::EXT_INVAL_ARG, string("open report file failed")); + errCode = errno; } auto proxy = ServiceProxy::GetInstance(); if (proxy == nullptr) { - throw BError(BError::Codes::EXT_BROKEN_BACKUP_SA, std::generic_category().message(errno)); + HILOGE("Failed to get file handle for special version clone"); + return BError(BError::Codes::EXT_BROKEN_BACKUP_SA).GetCode(); } - auto ret = proxy->AppIncrementalFileReady(fileName, move(fd), move(reportFd), ERR_OK); + auto ret = proxy->AppIncrementalFileReady(fileName, move(fd), move(reportFd), errCode); if (ret != ERR_OK) { HILOGE("Failed to AppIncrementalFileReady %{public}d", ret); } return ERR_OK; } -static string GetIncrementalFileHandlePath() +static string GetIncrementalFileHandlePath(const string &fileName, const string &bundleName) { string path = string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); + if (BFile::EndsWith(bundleName, BConstants::BUNDLE_FILE_MANAGER) && bundleName.size() == BConstants::FM_LEN) { + if (mkdir(string(BConstants::PATH_FILEMANAGE_BACKUP_HOME).data(), S_IRWXU) && errno != EEXIST) { + string str = string("Failed to create .backup folder. ").append(std::generic_category().message(errno)); + throw BError(BError::Codes::EXT_INVAL_ARG, str); + } + path = string(BConstants::PATH_FILEMANAGE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); + } else if (bundleName == BConstants::BUNDLE_MEDIAL_DATA) { + path = string(BConstants::PATH_MEDIALDATA_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); + } if (mkdir(path.data(), S_IRWXU) && errno != EEXIST) { string str = string("Failed to create restore folder. ").append(std::generic_category().message(errno)); throw BError(BError::Codes::EXT_INVAL_ARG, str); } - return path; + string tarName = path + fileName; + return tarName; +} + +ErrCode BackupExtExtension::GetIncreFileHandleForNormalVersion(const std::string &fileName) +{ + HILOGI("extension: GetIncrementalFileHandle single to single Name:%{public}s", GetAnonyPath(fileName).c_str()); + auto proxy = ServiceProxy::GetInstance(); + if (proxy == nullptr) { + throw BError(BError::Codes::EXT_BROKEN_IPC, string("Failed to AGetInstance")); + } + string tarName = GetIncrementalFileHandlePath(fileName, bundleName_); + int32_t errCode = ERR_OK; + if (access(tarName.c_str(), F_OK) == 0) { + HILOGE("The file already exists, tarname = %{private}s, err =%{public}d", tarName.c_str(), errno); + errCode = errno; + } + UniqueFd fd(open(tarName.data(), O_RDWR | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR)); + if (fd < 0) { + HILOGE("Failed to open tar file = %{private}s, err = %{public}d", tarName.c_str(), errno); + errCode = errno; + } + // 对应的简报文件 + string reportName = GetReportFileName(tarName); + if (access(reportName.c_str(), F_OK) == 0) { + HILOGE("The report file already exists, Name = %{private}s, err =%{public}d", reportName.c_str(), errno); + errCode = errno; + } + UniqueFd reportFd(open(reportName.data(), O_RDWR | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR)); + if (reportFd < 0) { + HILOGE("Failed to open report file = %{private}s, err = %{public}d", reportName.c_str(), errno); + errCode = errno; + } + HILOGI("extension: Will notify AppIncrementalFileReady"); + auto ret = proxy->AppIncrementalFileReady(fileName, move(fd), move(reportFd), errCode); + if (ret != ERR_OK) { + HILOGE("Failed to AppIncrementalFileReady %{public}d", ret); + } + return ERR_OK; } ErrCode BackupExtExtension::GetIncrementalFileHandle(const string &fileName) @@ -262,65 +381,49 @@ ErrCode BackupExtExtension::GetIncrementalFileHandle(const string &fileName) extension_->GetExtensionAction()); throw BError(BError::Codes::EXT_INVAL_ARG, "Action is invalid"); } - HILOGI("extension: Start GetIncrementalFileHandle"); VerifyCaller(); - + if (BDir::CheckFilePathInvalid(fileName)) { + auto proxy = ServiceProxy::GetInstance(); + if (proxy == nullptr) { + throw BError(BError::Codes::EXT_BROKEN_IPC, string("Failed to AGetInstance")); + } + HILOGE("Check file path : %{public}s err, path is forbidden", GetAnonyPath(fileName).c_str()); + auto ret = proxy->AppIncrementalDone(BError(BError::Codes::EXT_INVAL_ARG)); + if (ret != ERR_OK) { + HILOGE("Failed to notify app incre done. err = %{public}d", ret); + } + return BError(BError::Codes::EXT_INVAL_ARG).GetCode(); + } if (extension_->SpecialVersionForCloneAndCloud()) { return GetIncreFileHandleForSpecialVersion(fileName); } - HILOGI("extension: single to single fileName:%{public}s", fileName.c_str()); - string path = GetIncrementalFileHandlePath(); - string tarName = path + fileName; - if (access(tarName.c_str(), F_OK) == 0) { - throw BError(BError::Codes::EXT_INVAL_ARG, string("The file already exists")); - } - int32_t errCode = ERR_OK; - UniqueFd fd(open(tarName.data(), O_RDWR | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR)); - if (fd < 0) { - HILOGE("Failed to open tar file = %{private}s, err = %{public}d", tarName.c_str(), errno); - errCode = errno; - } - // 对应的简报文件 - string reportName = GetReportFileName(tarName); - if (access(reportName.c_str(), F_OK) == 0) { - throw BError(BError::Codes::EXT_INVAL_ARG, string("The report file already exists")); - } - UniqueFd reportFd(open(reportName.data(), O_RDWR | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR)); - if (reportFd < 0) { - HILOGE("Failed to open report file = %{private}s, err = %{public}d", reportName.c_str(), errno); - errCode = errno; - } - HILOGI("extension: Will notify AppIncrementalFileReady"); - auto proxy = ServiceProxy::GetInstance(); - if (proxy == nullptr) { - throw BError(BError::Codes::EXT_BROKEN_IPC, string("Failed to AGetInstance")); - } - auto ret = proxy->AppIncrementalFileReady(fileName, move(fd), move(reportFd), errCode); - if (ret != ERR_OK) { - HILOGE("Failed to AppIncrementalFileReady %{public}d", ret); - } - return ERR_OK; + return GetIncreFileHandleForNormalVersion(fileName); } catch (...) { HILOGE("Failed to get incremental file handle"); DoClear(); - return BError(BError::Codes::EXT_INVAL_ARG).GetCode(); + return BError(BError::Codes::EXT_BROKEN_IPC).GetCode(); } } ErrCode BackupExtExtension::HandleClear() { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); - HILOGI("begin clear"); - if (extension_ == nullptr) { - HILOGE("Failed to handle clear, extension is nullptr"); - return BError(BError::Codes::EXT_INVAL_ARG, "Extension is nullptr").GetCode(); - } - if (extension_->GetExtensionAction() == BConstants::ExtensionAction::INVALID) { - return BError(BError::Codes::EXT_INVAL_ARG, "Action is invalid").GetCode(); + try { + HILOGI("begin clear"); + if (extension_ == nullptr) { + HILOGE("Failed to handle clear, extension is nullptr"); + return BError(BError::Codes::EXT_INVAL_ARG, "Extension is nullptr").GetCode(); + } + if (extension_->GetExtensionAction() == BConstants::ExtensionAction::INVALID) { + return BError(BError::Codes::EXT_INVAL_ARG, "Action is invalid").GetCode(); + } + VerifyCaller(); + DoClear(); + return ERR_OK; + } catch (...) { + HILOGE("Failed to handle clear"); + return BError(BError::Codes::EXT_BROKEN_IPC).GetCode(); } - VerifyCaller(); - DoClear(); - return ERR_OK; } static ErrCode IndexFileReady(const TarMap &pkgInfo, sptr proxy) @@ -352,36 +455,26 @@ static ErrCode IndexFileReady(const TarMap &pkgInfo, sptr proxy) return ret; } -ErrCode BackupExtExtension::BigFileReady(sptr proxy) +ErrCode BackupExtExtension::BigFileReady(const TarMap &bigFileInfo, sptr proxy) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); - UniqueFd fd(open(INDEX_FILE_BACKUP.data(), O_RDONLY)); - if (fd < 0) { - HILOGE("Failed to open index json file = %{private}s, err = %{public}d", INDEX_FILE_BACKUP.c_str(), errno); - return BError::GetCodeByErrno(errno); - } - BJsonCachedEntity cachedEntity(move(fd)); - auto cache = cachedEntity.Structuralize(); - auto pkgInfo = cache.GetExtManageInfo(); - HILOGI("BigFileReady Begin: pkgInfo file size is: %{public}zu", pkgInfo.size()); + HILOGI("BigFileReady Begin: bigFileInfo file size is: %{public}zu", bigFileInfo.size()); ErrCode ret {ERR_OK}; auto startTime = std::chrono::system_clock::now(); int fdNum = 0; - for (auto &item : pkgInfo) { - if (item.hashName.empty() || item.fileName.empty()) { - continue; - } + for (auto &item : bigFileInfo) { WaitToSendFd(startTime, fdNum); int32_t errCode = ERR_OK; - UniqueFd fd(open(item.fileName.data(), O_RDONLY)); + string fllePath = std::get<0>(item.second); + UniqueFd fd(open(fllePath.data(), O_RDONLY)); if (fd < 0) { - HILOGE("open file failed, file name is %{public}s, err = %{public}d", item.fileName.c_str(), errno); + HILOGE("open file failed, file name is %{public}s, err = %{public}d", fllePath.c_str(), errno); errCode = errno; } - ret = proxy->AppFileReady(item.hashName, std::move(fd), errCode); + ret = proxy->AppFileReady(item.first, std::move(fd), errCode); if (SUCCEEDED(ret)) { - HILOGI("The application is packaged successfully, package name is %{public}s", item.hashName.c_str()); + HILOGI("The application is packaged successfully, package name is %{public}s", item.first.c_str()); } else { HILOGW("Current file execute app file ready interface failed, ret is:%{public}d", ret); } @@ -408,7 +501,7 @@ ErrCode BackupExtExtension::PublishFile(const std::string &fileName) VerifyCaller(); // 异步执行解压操作 if (extension_->AllowToBackupRestore()) { - AsyncTaskRestore(GetIdxFileData(), GetExtManageInfo()); + AsyncTaskRestore(GetIdxFileData(bundleName_), GetExtManageInfo()); } HILOGI("End publish file"); return ERR_OK; @@ -441,6 +534,9 @@ ErrCode BackupExtExtension::PublishIncrementalFile(const string &fileName) } VerifyCaller(); // 异步执行解压操作 + if (BackupPara::GetBackupDebugState()) { + isDebug_ = true; + } if (extension_->AllowToBackupRestore()) { if (extension_->SpecialVersionForCloneAndCloud()) { HILOGI("Create task for Incremental SpecialVersion"); @@ -466,26 +562,19 @@ ErrCode BackupExtExtension::PublishIncrementalFile(const string &fileName) } } -ErrCode BackupExtExtension::HandleBackup() +ErrCode BackupExtExtension::HandleBackup(bool isClearData) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); - if (extension_ == nullptr) { - HILOGE("Failed to handle backup, extension is nullptr"); - return BError(BError::Codes::EXT_INVAL_ARG, "Extension is nullptr").GetCode(); - } - string usrConfig = extension_->GetUsrConfig(); - BJsonCachedEntity cachedEntity(usrConfig); - auto cache = cachedEntity.Structuralize(); - if (!cache.GetAllowToBackupRestore()) { - HILOGE("Application does not allow backup or restore"); + SetClearDataFlag(isClearData); + if (!IfAllowToBackupRestore()) { return BError(BError::Codes::EXT_FORBID_BACKUP_RESTORE, "Application does not allow backup or restore") .GetCode(); } AsyncTaskOnBackup(); - return 0; + return ERR_OK; } -static bool IsUserTar(const string &tarFile, const std::vector &extManageInfo) +static bool IsUserTar(const string &tarFile, const std::vector &extManageInfo, off_t &tarFileSize) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); if (tarFile.empty()) { @@ -495,13 +584,14 @@ static bool IsUserTar(const string &tarFile, const std::vector &e [&tarFile](const auto &item) { return item.hashName == tarFile; }); if (iter != extManageInfo.end()) { HILOGI("tarFile:%{public}s isUserTar:%{public}d", tarFile.data(), iter->isUserTar); + tarFileSize = iter->sta.st_size; return iter->isUserTar; } HILOGE("Can not find tarFile %{public}s", tarFile.data()); return false; } -static pair> GetFileInfos(const vector &includes, const vector &excludes) +static pair> GetFileInfos(const vector &includes, const vector &excludes) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); auto [errCode, files, smallFiles] = BDir::GetBigFiles(includes, excludes); @@ -537,10 +627,98 @@ static pair> GetFileInfos(const vector &includes, return {bigFiles, smallFiles}; } +/** + * 全量tar包回传 + */ +static ErrCode TarFileReady(const TarMap &tarFileInfo, sptr proxy) +{ + if (tarFileInfo.empty()) { + HILOGI("TarFileReady: No tar file found"); + return ERR_OK; + } + string tarName = tarFileInfo.begin()->first; + string path = string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_BACKUP); + string tarPath = path + tarName; + int32_t errCode = ERR_OK; + UniqueFd fd(open(tarPath.data(), O_RDONLY)); + if (fd < 0) { + HILOGE("TarFileReady open file failed, file name is %{public}s, err = %{public}d", tarName.c_str(), errno); + errCode = errno; + } + int ret = proxy->AppFileReady(tarName, std::move(fd), errCode); + if (SUCCEEDED(ret)) { + HILOGI("TarFileReady: AppFileReady success for %{public}s", tarName.c_str()); + // 删除文件 + RemoveFile(tarPath); + } else { + HILOGE("TarFileReady AppFileReady fail to be invoked for %{public}s: ret = %{public}d", tarName.c_str(), ret); + } + return ret; +} + +std::function BackupExtExtension::ReportErrFileByProc(wptr obj, + BackupRestoreScenario scenario) +{ + return [obj, scenario](std::string msg, int err) { + auto extPtr = obj.promote(); + if (extPtr == nullptr) { + HILOGE("ReportErr ExtPtr is empty."); + return; + } + string jsonInfo; + BJsonUtil::BuildOnProcessErrInfo(jsonInfo, msg, err); + HILOGI("ReportErr Will notify err info."); + extPtr->ReportAppProcessInfo(jsonInfo, scenario); + }; +} + +void BackupExtExtension::DoPacket(const map &srcFiles, TarMap &tar, sptr proxy) +{ + HILOGI("DoPacket begin, infos count: %{public}zu", srcFiles.size()); + string path = string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_BACKUP); + uint64_t totalSize = 0; + uint32_t fileCount = 0; + vector packFiles; + TarFile::GetInstance().SetPacketMode(true); // 设置下打包模式 + auto startTime = std::chrono::system_clock::now(); + int fdNum = 0; + auto reportCb = ReportErrFileByProc(wptr {this}, curScenario_); + for (auto small : srcFiles) { + totalSize += small.second; + fileCount += 1; + packFiles.emplace_back(small.first); + if (totalSize >= BConstants::DEFAULT_SLICE_SIZE || fileCount >= BConstants::MAX_FILE_COUNT) { + TarMap tarMap {}; + TarFile::GetInstance().Packet(packFiles, "part", path, tarMap, reportCb); + tar.insert(tarMap.begin(), tarMap.end()); + // 执行tar包回传功能 + WaitToSendFd(startTime, fdNum); + TarFileReady(tarMap, proxy); + totalSize = 0; + fileCount = 0; + packFiles.clear(); + fdNum += BConstants::FILE_AND_MANIFEST_FD_COUNT; + RefreshTimeInfo(startTime, fdNum); + } + } + if (fileCount > 0) { + // 打包回传 + TarMap tarMap {}; + TarFile::GetInstance().Packet(packFiles, "part", path, tarMap, reportCb); + TarFileReady(tarMap, proxy); + fdNum = 1; + WaitToSendFd(startTime, fdNum); + tar.insert(tarMap.begin(), tarMap.end()); + packFiles.clear(); + RefreshTimeInfo(startTime, fdNum); + } +} + int BackupExtExtension::DoBackup(const BJsonEntityExtensionConfig &usrConfig) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); HILOGI("Start Do backup"); + auto start = std::chrono::system_clock::now(); if (extension_ == nullptr) { HILOGE("Failed to do backup, extension is nullptr"); throw BError(BError::Codes::EXT_INVAL_ARG, "Extension is nullptr"); @@ -556,6 +734,10 @@ int BackupExtExtension::DoBackup(const BJsonEntityExtensionConfig &usrConfig) vector includes = usrConfig.GetIncludes(); vector excludes = usrConfig.GetExcludes(); + auto proxy = ServiceProxy::GetInstance(); + if (proxy == nullptr) { + throw BError(BError::Codes::EXT_BROKEN_BACKUP_SA, std::generic_category().message(errno)); + } // 大文件处理 HILOGI("Start packet bigfiles and small files"); @@ -567,26 +749,32 @@ int BackupExtExtension::DoBackup(const BJsonEntityExtensionConfig &usrConfig) } } + // 回传大文件 + HILOGI("Will notify BigFileReady"); + auto res = BigFileReady(bigFileInfo, proxy); + HILOGI("Start packet Tar files"); - // 分片打包 + // 分片打包, 回传tar包 TarMap tarMap {}; - TarFile::GetInstance().Packet(smallFiles, "part", path, tarMap); + DoPacket(smallFiles, tarMap, proxy); bigFileInfo.insert(tarMap.begin(), tarMap.end()); - auto proxy = ServiceProxy::GetInstance(); - if (proxy == nullptr) { - throw BError(BError::Codes::EXT_BROKEN_BACKUP_SA, std::generic_category().message(errno)); - } + HILOGI("Do backup, DoPacket end"); + HILOGI("Will notify IndexFileReady"); if (auto ret = IndexFileReady(bigFileInfo, proxy); ret) { return ret; } - HILOGI("Will notify BigFileReady"); - auto res = BigFileReady(proxy); + HILOGI("HandleBackup finish, ret = %{public}d", res); + auto end = std::chrono::system_clock::now(); + auto cost = std::chrono::duration_cast(end - start).count(); + AppRadar::DoBackupInfo doBackupInfo = {cost, bigFileInfo.size(), smallFiles.size(), tarMap.size(), + includes.size(), excludes.size()}; + RecordDoBackupRes(bundleName_, res, doBackupInfo); return res; } -int BackupExtExtension::DoRestore(const string &fileName) +int BackupExtExtension::DoRestore(const string &fileName, const off_t fileSize) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); HILOGI("Do restore"); @@ -599,17 +787,34 @@ int BackupExtExtension::DoRestore(const string &fileName) } // REM: 给定version // REM: 解压启动Extension时即挂载好的备份目录中的数据 - string path = string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); + string path = GetRestoreTempPath(bundleName_); string tarName = path + fileName; // 当用户指定fullBackupOnly字段或指定版本的恢复,解压目录当前在/backup/restore - if (extension_->SpecialVersionForCloneAndCloud() || extension_->UseFullBackupOnly()) { - UntarFile::GetInstance().UnPacket(tarName, path); - } else { - UntarFile::GetInstance().UnPacket(tarName, "/"); + if (!extension_->SpecialVersionForCloneAndCloud() && !extension_->UseFullBackupOnly()) { + path = "/"; + } + auto [ret, fileInfos, errInfos] = UntarFile::GetInstance().UnPacket(tarName, path); + if (isDebug_) { + if (ret != 0) { + endFileInfos_[tarName] = fileSize; + errFileInfos_[tarName] = { ret }; + } + endFileInfos_.merge(fileInfos); + errFileInfos_.merge(errInfos); + } + if (ret != 0) { + HILOGE("Failed to untar file = %{public}s, err = %{public}d", tarName.c_str(), ret); + return ret; } HILOGI("Application recovered successfully, package path is %{public}s", tarName.c_str()); - + if (!isClearData_) { + HILOGI("configured not clear data"); + return ERR_OK; + } + if (!RemoveFile(tarName)) { + HILOGE("Failed to delete the backup tar %{public}s", tarName.c_str()); + } return ERR_OK; } @@ -629,6 +834,26 @@ static unordered_map GetTarIncludes(const string return rp.GetReportInfos(); } +void BackupExtExtension::DealIncreUnPacketResult(const off_t tarFileSize, const std::string &tarFileName, + const std::tuple &result) +{ + if (!isDebug_) { + return; + } + int err = std::get(result); + if (!isRpValid_) { + if (err != ERR_OK) { + endFileInfos_[tarFileName] = tarFileSize; + errFileInfos_[tarFileName] = {err}; + } else { + EndFileInfo tmpEndInfo = std::get(result); + endFileInfos_.merge(tmpEndInfo); + } + } + ErrFileInfo tmpErrInfo = std::get(result); + errFileInfos_.merge(tmpErrInfo); +} + int BackupExtExtension::DoIncrementalRestore() { HILOGI("Do incremental restore"); @@ -636,28 +861,52 @@ int BackupExtExtension::DoIncrementalRestore() HILOGE("Failed to do incremental restore, extension is nullptr"); throw BError(BError::Codes::EXT_INVAL_ARG, "Extension is nullptr"); } - auto fileSet = GetIdxFileData(); + auto fileSet = GetIdxFileData(bundleName_); auto extManageInfo = GetExtManageInfo(); + std::tuple unPacketRes; + ErrCode err = ERR_OK; + auto startTime = std::chrono::system_clock::now(); for (auto item : fileSet) { // 处理要解压的tar文件 - if (ExtractFileExt(item) == "tar" && !IsUserTar(item, extManageInfo)) { + off_t tarFileSize = 0; + if (ExtractFileExt(item) == "tar" && !IsUserTar(item, extManageInfo, tarFileSize)) { if (extension_->GetExtensionAction() != BConstants::ExtensionAction::RESTORE) { return EPERM; } + auto iter = find_if(extManageInfo.begin(), extManageInfo.end(), + [&item](const auto &itemManage) { return itemManage.hashName == item; }); + if (iter != extManageInfo.end()) { + tarFileSize = iter->sta.st_size; + } + radarRestoreInfo_.tarFileNum++; + radarRestoreInfo_.tarFileSize += static_cast(tarFileSize); // REM: 给定version // REM: 解压启动Extension时即挂载好的备份目录中的数据 - string path = string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); + string path = GetRestoreTempPath(bundleName_); string tarName = path + item; // 当用户指定fullBackupOnly字段或指定版本的恢复,解压目录当前在/backup/restore - if (extension_->SpecialVersionForCloneAndCloud() || extension_->UseFullBackupOnly()) { - UntarFile::GetInstance().IncrementalUnPacket(tarName, path, GetTarIncludes(tarName)); - } else { - UntarFile::GetInstance().IncrementalUnPacket(tarName, "/", GetTarIncludes(tarName)); + if (BDir::CheckFilePathInvalid(tarName)) { + HILOGE("Check incre tarfile path : %{public}s err, path is forbidden", GetAnonyPath(tarName).c_str()); + return ERR_INVALID_VALUE; + } + unordered_map result = GetTarIncludes(tarName); + if ((!extension_->SpecialVersionForCloneAndCloud()) && (!extension_->UseFullBackupOnly())) { + path = "/"; + } + if (isDebug_) { + FillEndFileInfos(path, result); } + unPacketRes = UntarFile::GetInstance().IncrementalUnPacket(tarName, path, result); + err = std::get(unPacketRes); + DealIncreUnPacketResult(tarFileSize, item, unPacketRes); HILOGI("Application recovered successfully, package path is %{public}s", tarName.c_str()); + DeleteBackupIncrementalTars(tarName); } } - return ERR_OK; + auto endTime = std::chrono::system_clock::now(); + radarRestoreInfo_.tarFileSpendTime = + std::chrono::duration_cast(endTime - startTime).count(); + return err; } void BackupExtExtension::AsyncTaskBackup(const string config) @@ -667,6 +916,14 @@ void BackupExtExtension::AsyncTaskBackup(const string config) auto ptr = obj.promote(); BExcepUltils::BAssert(ptr, BError::Codes::EXT_BROKEN_FRAMEWORK, "Ext extension handle have been released"); try { + HILOGI("Do backup, start fwk timer begin."); + bool isFwkStart; + ptr->StartFwkTimer(isFwkStart); + if (!isFwkStart) { + HILOGE("Do backup, start fwk timer fail."); + return; + } + HILOGI("Do backup, start fwk timer end."); BJsonCachedEntity cachedEntity(config); auto cache = cachedEntity.Structuralize(); auto ret = ptr->DoBackup(cache); @@ -699,27 +956,38 @@ void BackupExtExtension::AsyncTaskBackup(const string config) }); } -static void RestoreBigFilesForSpecialCloneCloud(ExtManageInfo item) +void BackupExtExtension::RestoreBigFilesForSpecialCloneCloud(const ExtManageInfo &item) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); - struct stat &sta = item.sta; + if (isDebug_) { + endFileInfos_[item.hashName] = item.sta.st_size; + } + const struct stat &sta = item.sta; string fileName = item.hashName; + if (BDir::CheckFilePathInvalid(fileName)) { + HILOGE("Check big spec file path : %{public}s err, path is forbidden", GetAnonyPath(fileName).c_str()); + errFileInfos_[fileName].push_back(DEFAULT_INVAL_VALUE); + return; + } if (chmod(fileName.c_str(), sta.st_mode) != 0) { HILOGE("Failed to chmod filePath, err = %{public}d", errno); + errFileInfos_[fileName].push_back(errno); } struct timespec tv[2] = {sta.st_atim, sta.st_mtim}; UniqueFd fd(open(fileName.data(), O_RDONLY)); if (fd < 0) { HILOGE("Failed to open file = %{public}s, err = %{public}d", GetAnonyPath(fileName).c_str(), errno); + errFileInfos_[fileName].push_back(errno); return; } if (futimens(fd.Get(), tv) != 0) { + errFileInfos_[fileName].push_back(errno); HILOGE("Failed to change the file time. %{public}s , %{public}d", GetAnonyPath(fileName).c_str(), errno); } } -static ErrCode RestoreTarForSpecialCloneCloud(ExtManageInfo item) +ErrCode BackupExtExtension::RestoreTarForSpecialCloneCloud(const ExtManageInfo &item) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); string tarName = item.hashName; @@ -731,19 +999,39 @@ static ErrCode RestoreTarForSpecialCloneCloud(ExtManageInfo item) if (untarPath.back() != BConstants::FILE_SEPARATOR_CHAR) { untarPath += BConstants::FILE_SEPARATOR_CHAR; } - UntarFile::GetInstance().UnPacket(tarName, untarPath); - + HILOGI("Start to untar file = %{public}s, untarPath = %{public}s", GetAnonyPath(item.hashName).c_str(), + GetAnonyPath(untarPath).c_str()); + if (BDir::CheckFilePathInvalid(tarName)) { + HILOGE("Check spec tarfile hash path : %{public}s err, path is forbidden", GetAnonyPath(tarName).c_str()); + return ERR_INVALID_VALUE; + } + if (BDir::CheckFilePathInvalid(untarPath)) { + HILOGE("Check spec tarfile path : %{public}s err, path is forbidden", GetAnonyPath(untarPath).c_str()); + return ERR_INVALID_VALUE; + } + auto [err, fileInfos, errInfos] = UntarFile::GetInstance().UnPacket(tarName, untarPath); + if (isDebug_) { + if (err != 0) { + endFileInfos_[tarName] = item.sta.st_size; + errFileInfos_[tarName] = { err }; + } + endFileInfos_.merge(fileInfos); + errFileInfos_.merge(errInfos); + } + if (err != ERR_OK) { + HILOGE("Failed to untar file = %{public}s, err = %{public}d", tarName.c_str(), err); + return err; + } if (!RemoveFile(tarName)) { HILOGE("Failed to delete the backup tar %{public}s", tarName.c_str()); } return ERR_OK; } -static ErrCode RestoreFilesForSpecialCloneCloud() +ErrCode BackupExtExtension::RestoreFilesForSpecialCloneCloud() { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); // 获取索引文件内容 - string path = string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); UniqueFd fd(open(INDEX_FILE_RESTORE.data(), O_RDONLY)); if (fd < 0) { HILOGE("Failed to open index json file = %{private}s, err = %{public}d", INDEX_FILE_RESTORE.c_str(), errno); @@ -753,16 +1041,27 @@ static ErrCode RestoreFilesForSpecialCloneCloud() auto cache = cachedEntity.Structuralize(); auto info = cache.GetExtManageInfo(); HILOGI("Start do restore for SpecialCloneCloud."); + auto startTime = std::chrono::system_clock::now(); for (auto &item : info) { if (item.hashName.empty()) { + HILOGE("Hash name empty"); continue; } if (item.isUserTar || item.isBigFile) { // 大文件处理 + radarRestoreInfo_.bigFileNum++; + radarRestoreInfo_.bigFileSize += static_cast(item.sta.st_size); RestoreBigFilesForSpecialCloneCloud(item); } else { // 待解压tar文件处理 - if (RestoreTarForSpecialCloneCloud(item) != ERR_OK) { + radarRestoreInfo_.tarFileNum++; + radarRestoreInfo_.tarFileSize += static_cast(item.sta.st_size); + int ret = RestoreTarForSpecialCloneCloud(item); + if (isDebug_ && ret != ERR_OK) { + errFileInfos_[item.hashName].push_back(ret); + endFileInfos_[item.hashName] = item.sta.st_size; + } + if (ret != ERR_OK) { HILOGE("Failed to restore tar file %{public}s", item.hashName.c_str()); return ERR_INVALID_VALUE; } @@ -771,6 +1070,10 @@ static ErrCode RestoreFilesForSpecialCloneCloud() if (!RemoveFile(INDEX_FILE_RESTORE)) { HILOGE("Failed to delete the backup index %{public}s", INDEX_FILE_RESTORE.c_str()); } + auto endTime = std::chrono::system_clock::now(); + radarRestoreInfo_.totalFileSpendTime = + std::chrono::duration_cast(endTime - startTime).count(); + RecordDoRestoreRes(bundleName_, "BackupExtExtension::RestoreFilesForSpecialCloneCloud", radarRestoreInfo_); HILOGI("End do restore for SpecialCloneCloud."); return ERR_OK; } @@ -796,135 +1099,166 @@ static bool RestoreBigFilePrecheck(string &fileName, const string &path, const s return true; } -static void RestoreBigFileAfter(const string &filePath, const struct stat &sta) +void BackupExtExtension::RestoreBigFileAfter(const string &filePath, const struct stat &sta) { if (chmod(filePath.c_str(), sta.st_mode) != 0) { + errFileInfos_[filePath].push_back(errno); HILOGE("Failed to chmod filePath, err = %{public}d", errno); } struct timespec tv[2] = {sta.st_atim, sta.st_mtim}; UniqueFd fd(open(filePath.data(), O_RDONLY)); if (fd < 0) { + errFileInfos_[filePath].push_back(errno); HILOGE("Failed to open file = %{public}s, err = %{public}d", GetAnonyPath(filePath).c_str(), errno); return; } if (futimens(fd.Get(), tv) != 0) { + errFileInfos_[filePath].push_back(errno); HILOGE("failed to change the file time. %{public}s , %{public}d", GetAnonyPath(filePath).c_str(), errno); } } -static void RestoreBigFiles(bool appendTargetPath) +void BackupExtExtension::RestoreOneBigFile(const std::string &path, + const ExtManageInfo &item, const bool appendTargetPath) +{ + radarRestoreInfo_.bigFileNum++; + radarRestoreInfo_.bigFileSize += static_cast(item.sta.st_size); + string itemHashName = item.hashName; + string itemFileName = item.fileName; + // check if item.hasName and fileName need decode by report item attribute + string reportPath = GetReportFileName(path + item.hashName); + UniqueFd fd(open(reportPath.data(), O_RDONLY)); + if (fd < 0) { + HILOGE("Failed to open report file = %{public}s, err = %{public}d", reportPath.c_str(), errno); + errFileInfos_[item.hashName].push_back(errno); + throw BError(BError::Codes::EXT_INVAL_ARG, string("open report file failed")); + } + BReportEntity rp(move(fd)); + rp.CheckAndUpdateIfReportLineEncoded(itemFileName); + + string fileName = path + itemHashName; + string filePath = appendTargetPath ? (path + itemFileName) : itemFileName; + if (BDir::CheckFilePathInvalid(filePath)) { + HILOGE("Check big file path : %{public}s err, path is forbidden", GetAnonyPath(filePath).c_str()); + return; + } + if (isDebug_) { + endFileInfos_[filePath] = item.sta.st_size; + } + + if (!RestoreBigFilePrecheck(fileName, path, item.hashName, filePath)) { + return; + } + if (!BFile::MoveFile(fileName, filePath)) { + errFileInfos_[filePath].push_back(errno); + HILOGE("failed to move the file. err = %{public}d", errno); + return; + } + + RestoreBigFileAfter(filePath, item.sta); +} + +void BackupExtExtension::RestoreBigFiles(bool appendTargetPath) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); // 获取索引文件内容 - string path = string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); - UniqueFd fd(open(INDEX_FILE_RESTORE.data(), O_RDONLY)); + string path = GetRestoreTempPath(bundleName_); + string indexFileRestorePath = GetIndexFileRestorePath(bundleName_); + UniqueFd fd(open(indexFileRestorePath.data(), O_RDONLY)); if (fd < 0) { - HILOGE("Failed to open index json file = %{private}s, err = %{public}d", INDEX_FILE_RESTORE.c_str(), errno); + HILOGE("Failed to open index json file = %{private}s, err = %{public}d", indexFileRestorePath.c_str(), errno); return; } BJsonCachedEntity cachedEntity(move(fd)); auto cache = cachedEntity.Structuralize(); auto info = cache.GetExtManageInfo(); HILOGI("Start Restore Big Files"); + auto start = std::chrono::system_clock::now(); for (auto &item : info) { if (item.hashName.empty() || (!item.isUserTar && !item.isBigFile)) { continue; } - - string itemHashName = item.hashName; - string itemFileName = item.fileName; - // check if item.hasName and fileName need decode by report item attribute - string reportPath = GetReportFileName(path + item.hashName); - UniqueFd fd(open(reportPath.data(), O_RDONLY)); - if (fd < 0) { - HILOGE("Failed to open report file = %{public}s, err = %{public}d", reportPath.c_str(), errno); - throw BError(BError::Codes::EXT_INVAL_ARG, string("open report file failed")); - } - BReportEntity rp(move(fd)); - rp.CheckAndUpdateIfReportLineEncoded(itemFileName); - - string fileName = path + itemHashName; - string filePath = appendTargetPath ? (path + itemFileName) : itemFileName; - - if (!RestoreBigFilePrecheck(fileName, path, item.hashName, filePath)) { - continue; - } - - if (!BFile::MoveFile(fileName, filePath)) { - HILOGE("failed to move the file. err = %{public}d", errno); - continue; - } - - RestoreBigFileAfter(filePath, item.sta); + RestoreOneBigFile(path, item, appendTargetPath); } + auto end = std::chrono::system_clock::now(); + radarRestoreInfo_.bigFileSpendTime = std::chrono::duration_cast(end - start).count(); HILOGI("End Restore Big Files"); } -static void DeleteBackupTars() +void BackupExtExtension::FillEndFileInfos(const std::string &path, + const unordered_map &result) { - HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); - UniqueFd fd(open(INDEX_FILE_RESTORE.data(), O_RDONLY)); - if (fd < 0) { - HILOGE("Failed to open index json file = %{private}s, err = %{public}d", INDEX_FILE_RESTORE.c_str(), errno); + isRpValid_ = result.size() > 0; + if (!isRpValid_) { return; } - // The directory include tars and manage.json which would be deleted - BJsonCachedEntity cachedEntity(move(fd)); - auto cache = cachedEntity.Structuralize(); - auto info = cache.GetExtManage(); - auto path = string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); - auto extManageInfo = GetExtManageInfo(); - for (auto &item : info) { - if (ExtractFileExt(item) != "tar" || IsUserTar(item, extManageInfo)) { - continue; - } - string tarPath = path + item; - if (!RemoveFile(tarPath)) { - HILOGE("Failed to delete the backup tar %{public}s", tarPath.c_str()); + for (const auto &it : result) { + std::string filePath = it.first; + if (!filePath.empty() && filePath.size() <= PATH_MAX) { + endFileInfos_[path + filePath] = it.second.size; + } else { + HILOGE("File name : %{public}s check error", GetAnonyPath(path + filePath).c_str()); } } - if (!RemoveFile(INDEX_FILE_RESTORE)) { - HILOGE("Failed to delete the backup index %{public}s", INDEX_FILE_RESTORE.c_str()); - } - HILOGI("End execute DeleteBackupTars"); } -static void DeleteBackupIncrementalTars() +void BackupExtExtension::DeleteBackupIdxFile() { - UniqueFd fd(open(INDEX_FILE_RESTORE.data(), O_RDONLY)); - if (fd < 0) { - HILOGE("Failed to open index json file = %{private}s, err = %{public}d", INDEX_FILE_RESTORE.c_str(), errno); + if (!isClearData_) { + HILOGI("configured not clear data."); return; } - // The directory include tars and manage.json which would be deleted - BJsonCachedEntity cachedEntity(move(fd)); - auto cache = cachedEntity.Structuralize(); - auto info = cache.GetExtManage(); - auto path = string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); - auto extManageInfo = GetExtManageInfo(); - for (auto &item : info) { - if (ExtractFileExt(item) != "tar" || IsUserTar(item, extManageInfo)) { - continue; - } - string tarPath = path + item; - if (!RemoveFile(tarPath)) { - HILOGE("Failed to delete the backup tar %{private}s, err = %{public}d", tarPath.c_str(), errno); - } - // 删除简报文件 - string reportPath = GetReportFileName(tarPath); - if (!RemoveFile(reportPath)) { - HILOGE("Failed to delete the backup report %{private}s, err = %{public}d", reportPath.c_str(), errno); - } + HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + string indexFileRestorePath = GetIndexFileRestorePath(bundleName_); + if (!RemoveFile(indexFileRestorePath)) { + HILOGE("Failed to delete the backup index %{public}s", indexFileRestorePath.c_str()); } - if (!RemoveFile(INDEX_FILE_RESTORE)) { - HILOGE("Failed to delete the backup index %{public}s", INDEX_FILE_RESTORE.c_str()); + HILOGI("End execute DeleteBackupIdxFile"); +} + +void BackupExtExtension::DeleteBackupIncrementalIdxFile() +{ + if (!isClearData_) { + HILOGI("configured not clear data."); + return; } - string reportManagePath = GetReportFileName(INDEX_FILE_RESTORE); // GetIncrementalFileHandle创建的空fd + string indexFileRestorePath = GetIndexFileRestorePath(bundleName_); + if (!RemoveFile(indexFileRestorePath)) { + HILOGE("Failed to delete the backup index %{public}s", indexFileRestorePath.c_str()); + } + string reportManagePath = GetReportFileName(indexFileRestorePath); // GetIncrementalFileHandle创建的空fd if (!RemoveFile(reportManagePath)) { HILOGE("Failed to delete the backup report index %{public}s", reportManagePath.c_str()); } } +void BackupExtExtension::DeleteBackupIncrementalTars(const string &tarName) +{ + if (!isClearData_) { + HILOGI("configured not need clear data"); + return; + } + if (!RemoveFile(tarName)) { + HILOGE("Failed to delete the backup tar %{private}s, err = %{public}d", tarName.c_str(), errno); + } + // 删除简报文件 + string reportPath = GetReportFileName(tarName); + if (!RemoveFile(reportPath)) { + HILOGE("Failed to delete backup report %{private}s, err = %{public}d", reportPath.c_str(), errno); + } +} + +void BackupExtExtension::HandleSpecialVersionRestore() +{ + auto ret = RestoreFilesForSpecialCloneCloud(); + if (ret == ERR_OK) { + AsyncTaskRestoreForUpgrade(); + } else { + AppDone(ret); + DoClear(); + } +} + void BackupExtExtension::AsyncTaskRestore(std::set fileSet, const std::vector extManageInfo) { @@ -935,27 +1269,22 @@ void BackupExtExtension::AsyncTaskRestore(std::set fileSet, try { int ret = ERR_OK; if (ptr->extension_->SpecialVersionForCloneAndCloud()) { - ret = RestoreFilesForSpecialCloneCloud(); - if (ret == ERR_OK) { - ptr->AsyncTaskRestoreForUpgrade(); - } else { - ptr->AppDone(ret); - ptr->DoClear(); - } + ptr->HandleSpecialVersionRestore(); return; } // 解压 for (auto item : fileSet) { // 处理要解压的tar文件 - if (ExtractFileExt(item) == "tar" && !IsUserTar(item, extManageInfo)) { - ret = ptr->DoRestore(item); + off_t tarFileSize = 0; + if (ExtractFileExt(item) == "tar" && !IsUserTar(item, extManageInfo, tarFileSize)) { + ret = ptr->DoRestore(item, tarFileSize); } } // 恢复用户tar包以及大文件 // 目的地址是否需要拼接path(临时目录),FullBackupOnly为true并且非特殊场景 bool appendTargetPath = ptr->extension_->UseFullBackupOnly() && !ptr->extension_->SpecialVersionForCloneAndCloud(); - RestoreBigFiles(appendTargetPath); - DeleteBackupTars(); + ptr->RestoreBigFiles(appendTargetPath); + ptr->DeleteBackupIdxFile(); if (ret == ERR_OK) { ptr->AsyncTaskRestoreForUpgrade(); } else { @@ -984,6 +1313,37 @@ void BackupExtExtension::AsyncTaskRestore(std::set fileSet, }); } +int BackupExtExtension::DealIncreRestoreBigAndTarFile() +{ + if (isDebug_) { + CheckTmpDirFileInfos(); + } + auto startTime = std::chrono::system_clock::now(); + // 解压 + int ret = ERR_OK; + ret = DoIncrementalRestore(); + if (ret != ERR_OK) { + HILOGE("Do incremental restore err"); + return ret; + } + // 恢复用户tar包以及大文件 + // 目的地址是否需要拼接path(临时目录),FullBackupOnly为true并且非特殊场景 + bool appendTargetPath = + extension_->UseFullBackupOnly() && !extension_->SpecialVersionForCloneAndCloud(); + RestoreBigFiles(appendTargetPath); + // delete 1.tar/manage.json + DeleteBackupIncrementalIdxFile(); + if (isDebug_) { + CheckRestoreFileInfos(); + } + auto endTime = std::chrono::system_clock::now(); + radarRestoreInfo_.totalFileSpendTime = + std::chrono::duration_cast(endTime - startTime).count(); + RecordDoRestoreRes(bundleName_, "BackupExtExtension::AsyncTaskIncrementalRestore", + radarRestoreInfo_); + return ret; +} + void BackupExtExtension::AsyncTaskIncrementalRestore() { auto task = [obj {wptr(this)}]() { @@ -991,17 +1351,7 @@ void BackupExtExtension::AsyncTaskIncrementalRestore() BExcepUltils::BAssert(ptr, BError::Codes::EXT_BROKEN_FRAMEWORK, "Ext extension handle have been released"); BExcepUltils::BAssert(ptr->extension_, BError::Codes::EXT_INVAL_ARG, "Extension handle have been released"); try { - // 解压 - int ret = ptr->DoIncrementalRestore(); - // 恢复用户tar包以及大文件 - // 目的地址是否需要拼接path(临时目录),FullBackupOnly为true并且非特殊场景 - bool appendTargetPath = - ptr->extension_->UseFullBackupOnly() && !ptr->extension_->SpecialVersionForCloneAndCloud(); - RestoreBigFiles(appendTargetPath); - - // delete 1.tar/manage.json - DeleteBackupIncrementalTars(); - + int ret = ptr->DealIncreRestoreBigAndTarFile(); if (ret == ERR_OK) { HILOGI("after extra, do incremental restore."); ptr->AsyncTaskIncrementalRestoreForUpgrade(); @@ -1038,7 +1388,13 @@ void BackupExtExtension::AsyncTaskIncreRestoreSpecialVersion() auto ptr = obj.promote(); BExcepUltils::BAssert(ptr, BError::Codes::EXT_BROKEN_FRAMEWORK, "Ext extension handle have been released"); try { - int ret = RestoreFilesForSpecialCloneCloud(); + if (ptr != nullptr && ptr->isDebug_) { + ptr->CheckTmpDirFileInfos(true); + } + int ret = ptr->RestoreFilesForSpecialCloneCloud(); + if (ptr != nullptr && ptr->isDebug_) { + ptr->CheckRestoreFileInfos(); + } if (ret == ERR_OK) { ptr->AsyncTaskIncrementalRestoreForUpgrade(); } else { @@ -1072,29 +1428,28 @@ void BackupExtExtension::AsyncTaskRestoreForUpgrade() { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); auto task = [obj {wptr(this)}]() { - auto callBackup = [obj](ErrCode errCode, std::string errMsg) { - auto extensionPtr = obj.promote(); - if (extensionPtr == nullptr) { - HILOGE("Ext extension handle have been released"); - return; - } - HILOGI("Current bundle will execute app done"); - if (errMsg.empty()) { - extensionPtr->AppDone(errCode); - } else { - std::string errInfo; - BJsonUtil::BuildRestoreErrInfo(errInfo, errCode, errMsg); - extensionPtr->AppResultReport(errInfo, BackupRestoreScenario::FULL_RESTORE, errCode); - } - extensionPtr->DoClear(); - }; auto ptr = obj.promote(); BExcepUltils::BAssert(ptr, BError::Codes::EXT_BROKEN_FRAMEWORK, "Ext extension handle have been released"); BExcepUltils::BAssert(ptr->extension_, BError::Codes::EXT_INVAL_ARG, "Extension handle have been released"); try { - auto callBackupEx = ptr->RestoreResultCallbackEx(obj); + HILOGI("On restore, start ext timer begin."); + bool isExtStart; + ptr->StartExtTimer(isExtStart); + if (!isExtStart) { + HILOGE("On restore, start ext timer fail."); + return; + } + HILOGI("On restore, start ext timer end."); + ptr->curScenario_ = BackupRestoreScenario::FULL_RESTORE; + ptr->StartOnProcessTaskThread(obj, BackupRestoreScenario::FULL_RESTORE); + auto callBackup = ptr->OnRestoreCallback(obj); + auto callBackupEx = ptr->OnRestoreExCallback(obj); + ptr->UpdateOnStartTime(); ErrCode err = ptr->extension_->OnRestore(callBackup, callBackupEx); - HILOGI("OnRestore done err = %{public}d", err); + if (err != ERR_OK) { + ptr->AppDone(BError::GetCodeByErrno(err)); + ptr->DoClear(); + } } catch (const BError &e) { ptr->AppDone(e.GetCode()); ptr->DoClear(); @@ -1126,29 +1481,29 @@ void BackupExtExtension::ExtClear() void BackupExtExtension::AsyncTaskIncrementalRestoreForUpgrade() { auto task = [obj {wptr(this)}]() { - auto callBackup = [obj](ErrCode errCode, std::string errMsg) { - auto extensionPtr = obj.promote(); - if (extensionPtr == nullptr) { - HILOGE("Ext extension handle have been released"); - return; - } - HILOGI("Current bundle will execute app done"); - if (errMsg.empty()) { - extensionPtr->AppIncrementalDone(errCode); - } else { - std::string errInfo; - BJsonUtil::BuildRestoreErrInfo(errInfo, errCode, errMsg); - extensionPtr->AppResultReport(errInfo, BackupRestoreScenario::INCREMENTAL_RESTORE, errCode); - } - extensionPtr->DoClear(); - }; auto ptr = obj.promote(); BExcepUltils::BAssert(ptr, BError::Codes::EXT_BROKEN_FRAMEWORK, "Ext extension handle have been released"); BExcepUltils::BAssert(ptr->extension_, BError::Codes::EXT_INVAL_ARG, "Extension handle have been released"); try { - auto callBackupEx = ptr->IncRestoreResultCallbackEx(obj); + HILOGI("On incrementalRestore, start ext timer begin."); + bool isExtStart; + ptr->StartExtTimer(isExtStart); + if (!isExtStart) { + HILOGE("On incrementalRestore, start ext timer fail."); + return; + } + HILOGI("On incrementalRestore, start ext timer end."); + ptr->curScenario_ = BackupRestoreScenario::INCREMENTAL_RESTORE; + ptr->StartOnProcessTaskThread(obj, BackupRestoreScenario::INCREMENTAL_RESTORE); + auto callBackup = ptr->IncreOnRestoreCallback(obj); + auto callBackupEx = ptr->IncreOnRestoreExCallback(obj); + ptr->UpdateOnStartTime(); ErrCode err = ptr->extension_->OnRestore(callBackup, callBackupEx); - HILOGI("OnRestore done err = %{public}d", err); + if (err != ERR_OK) { + HILOGE("OnRestore done, err = %{pubilc}d", err); + ptr->AppIncrementalDone(BError::GetCodeByErrno(err)); + ptr->DoClear(); + } } catch (const BError &e) { ptr->AppIncrementalDone(e.GetCode()); ptr->DoClear(); @@ -1179,8 +1534,13 @@ void BackupExtExtension::DoClear() { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); try { + if (!isClearData_) { + HILOGI("configured not clear data."); + return; + } string backupCache = string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_BACKUP); string restoreCache = string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); + string specialRestoreCache = GetRestoreTempPath(bundleName_); if (!ForceRemoveDirectory(backupCache)) { HILOGI("Failed to delete the backup cache %{public}s", backupCache.c_str()); @@ -1189,11 +1549,28 @@ void BackupExtExtension::DoClear() if (!ForceRemoveDirectory(restoreCache)) { HILOGI("Failed to delete the restore cache %{public}s", restoreCache.c_str()); } + + if (!ForceRemoveDirectory(specialRestoreCache)) { + HILOGI("Failed to delete cache for filemanager or medialibrary %{public}s", specialRestoreCache.c_str()); + } // delete el1 backup/restore ForceRemoveDirectory( string(BConstants::PATH_BUNDLE_BACKUP_HOME_EL1).append(BConstants::SA_BUNDLE_BACKUP_BACKUP)); ForceRemoveDirectory( string(BConstants::PATH_BUNDLE_BACKUP_HOME_EL1).append(BConstants::SA_BUNDLE_BACKUP_RESTORE)); + // delete special directory + if (bundleName_.compare(MEDIA_LIBRARY_BUNDLE_NAME) == 0) { + ForceRemoveDirectory( + string(BConstants::PATH_MEDIALDATA_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_BACKUP)); + ForceRemoveDirectory( + string(BConstants::PATH_MEDIALDATA_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE)); + } + if (bundleName_.compare(FILE_MANAGER_BUNDLE_NAME) == 0) { + ForceRemoveDirectory( + string(BConstants::PATH_FILEMANAGE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_BACKUP)); + ForceRemoveDirectory( + string(BConstants::PATH_FILEMANAGE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE)); + } unique_lock lock(lock_); } catch (...) { HILOGE("Failed to clear"); @@ -1205,7 +1582,11 @@ void BackupExtExtension::AppDone(ErrCode errCode) HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); HILOGI("AppDone Begin."); auto proxy = ServiceProxy::GetInstance(); - BExcepUltils::BAssert(proxy, BError::Codes::EXT_BROKEN_IPC, "Failed to obtain the ServiceProxy handle"); + if (proxy == nullptr) { + HILOGE("Failed to obtain the ServiceProxy handle"); + DoClear(); + return; + } auto ret = proxy->AppDone(errCode); if (ret != ERR_OK) { HILOGE("Failed to notify the app done. err = %{public}d", ret); @@ -1224,29 +1605,52 @@ void BackupExtExtension::AppResultReport(const std::string restoreRetInfo, } } +void BackupExtExtension::StartExtTimer(bool &isExtStart) +{ + auto proxy = ServiceProxy::GetInstance(); + BExcepUltils::BAssert(proxy, BError::Codes::EXT_BROKEN_IPC, "Failed to obtain the ServiceProxy handle"); + HILOGI("Start ext timer by ipc."); + auto ret = proxy->StartExtTimer(isExtStart); + if (ret != ERR_OK) { + HILOGE("Start ext timer failed, errCode: %{public}d", ret); + } +} + +void BackupExtExtension::StartFwkTimer(bool &isFwkStart) +{ + auto proxy = ServiceProxy::GetInstance(); + BExcepUltils::BAssert(proxy, BError::Codes::EXT_BROKEN_IPC, "Failed to obtain the ServiceProxy handle"); + HILOGI("Start fwk timer by ipc."); + auto ret = proxy->StartFwkTimer(isFwkStart); + if (ret != ERR_OK) { + HILOGE("Start fwk timer failed, errCode: %{public}d", ret); + } +} + +void BackupExtExtension::UpdateOnStartTime() +{ + std::lock_guard lock(onStartTimeLock_); + g_onStart = std::chrono::system_clock::now(); +} + void BackupExtExtension::AsyncTaskOnBackup() { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); auto task = [obj {wptr(this)}]() { - auto callBackup = [obj](ErrCode errCode, std::string errMsg) { - HILOGI("begin call backup"); - auto extensionPtr = obj.promote(); - if (extensionPtr == nullptr) { - HILOGE("Ext extension handle have been released"); - return; - } - if (extensionPtr->extension_ == nullptr) { - HILOGE("Extension handle have been released"); - return; - } - extensionPtr->AsyncTaskBackup(extensionPtr->extension_->GetUsrConfig()); - }; auto ptr = obj.promote(); BExcepUltils::BAssert(ptr, BError::Codes::EXT_BROKEN_FRAMEWORK, "Ext extension handle have been released"); BExcepUltils::BAssert(ptr->extension_, BError::Codes::EXT_INVAL_ARG, "Extension handle have been released"); try { - auto callBackupEx = ptr->HandleTaskBackupEx(obj); - ptr->extension_->OnBackup(callBackup, callBackupEx); + ptr->curScenario_ = BackupRestoreScenario::FULL_BACKUP; + ptr->StartOnProcessTaskThread(obj, BackupRestoreScenario::FULL_BACKUP); + auto callBackup = ptr->OnBackupCallback(obj); + auto callBackupEx = ptr->OnBackupExCallback(obj); + ptr->UpdateOnStartTime(); + ErrCode err = ptr->extension_->OnBackup(callBackup, callBackupEx); + if (err != ERR_OK) { + HILOGE("OnBackup done, err = %{pubilc}d", err); + ptr->AppDone(BError::GetCodeByErrno(err)); + } } catch (const BError &e) { ptr->AppDone(e.GetCode()); } catch (const exception &e) { @@ -1267,32 +1671,37 @@ void BackupExtExtension::AsyncTaskOnBackup() }); } -ErrCode BackupExtExtension::HandleRestore() +ErrCode BackupExtExtension::HandleRestore(bool isClearData) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); - VerifyCaller(); - if (extension_ == nullptr) { - HILOGE("Failed to handle restore, extension is nullptr"); - throw BError(BError::Codes::EXT_INVAL_ARG, "Extension is nullptr"); - } - if (extension_->GetExtensionAction() != BConstants::ExtensionAction::RESTORE) { - HILOGE("Failed to get file handle, because action is %{public}d invalid", extension_->GetExtensionAction()); - throw BError(BError::Codes::EXT_INVAL_ARG, "Action is invalid"); - } - // read backup_config is allow to backup or restore - if (!extension_->AllowToBackupRestore()) { - HILOGE("Application does not allow backup or restore"); - return BError(BError::Codes::EXT_FORBID_BACKUP_RESTORE, "Application does not allow backup or restore") - .GetCode(); - } + try { + VerifyCaller(); + SetClearDataFlag(isClearData); + if (extension_ == nullptr) { + HILOGE("Failed to handle restore, extension is nullptr"); + return BError(BError::Codes::EXT_INVAL_ARG, "Extension is nullptr").GetCode(); + } + if (extension_->GetExtensionAction() != BConstants::ExtensionAction::RESTORE) { + HILOGE("Failed to get file handle, because action is %{public}d invalid", extension_->GetExtensionAction()); + return BError(BError::Codes::EXT_INVAL_ARG, "Action is invalid").GetCode(); + } + // read backup_config is allow to backup or restore + if (!extension_->AllowToBackupRestore()) { + HILOGE("Application does not allow backup or restore"); + return BError(BError::Codes::EXT_FORBID_BACKUP_RESTORE, "Application does not allow backup or restore") + .GetCode(); + } - // async do restore. - if (extension_->WasFromSpecialVersion() && extension_->RestoreDataReady()) { - HILOGI("Restore directly when upgrading."); - AsyncTaskRestoreForUpgrade(); + // async do restore. + if (extension_->WasFromSpecialVersion() && extension_->RestoreDataReady()) { + HILOGI("Restore directly when upgrading."); + AsyncTaskRestoreForUpgrade(); + } + return ERR_OK; + } catch (...) { + HILOGE("Failed to handle restore"); + return BError(BError::Codes::EXT_BROKEN_IPC).GetCode(); } - - return 0; } static bool CheckTar(const string &fileName) @@ -1374,41 +1783,31 @@ void BackupExtExtension::CompareFiles(UniqueFd incrementalFd, ErrCode BackupExtExtension::HandleIncrementalBackup(UniqueFd incrementalFd, UniqueFd manifestFd) { - HILOGI("Start HandleIncrementalBackup"); HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); - if (extension_ == nullptr) { - HILOGE("Failed to handle incremental backup, extension is nullptr"); - return BError(BError::Codes::EXT_INVAL_ARG, "Extension is nullptr").GetCode(); - } - string usrConfig = extension_->GetUsrConfig(); - BJsonCachedEntity cachedEntity(usrConfig); - auto cache = cachedEntity.Structuralize(); - if (!cache.GetAllowToBackupRestore()) { - HILOGE("Application does not allow backup or restore"); - return BError(BError::Codes::EXT_FORBID_BACKUP_RESTORE, "Application does not allow backup or restore") - .GetCode(); + try { + HILOGI("Start HandleIncrementalBackup"); + if (!IfAllowToBackupRestore()) { + return BError(BError::Codes::EXT_FORBID_BACKUP_RESTORE, "Application does not allow backup or restore") + .GetCode(); + } + AsyncTaskDoIncrementalBackup(move(incrementalFd), move(manifestFd)); + return ERR_OK; + } catch (...) { + HILOGE("Failed to handle incremental backup"); + return BError(BError::Codes::EXT_INVAL_ARG).GetCode(); } - AsyncTaskDoIncrementalBackup(move(incrementalFd), move(manifestFd)); - return 0; } -ErrCode BackupExtExtension::IncrementalOnBackup() +ErrCode BackupExtExtension::IncrementalOnBackup(bool isClearData) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); - if (extension_ == nullptr) { - HILOGE("Failed to handle incremental onBackup, extension is nullptr"); - return BError(BError::Codes::EXT_INVAL_ARG, "Extension is nullptr").GetCode(); - } - string usrConfig = extension_->GetUsrConfig(); - BJsonCachedEntity cachedEntity(usrConfig); - auto cache = cachedEntity.Structuralize(); - if (!cache.GetAllowToBackupRestore()) { - HILOGE("Application does not allow backup or restore"); + SetClearDataFlag(isClearData); + if (!IfAllowToBackupRestore()) { return BError(BError::Codes::EXT_FORBID_BACKUP_RESTORE, "Application does not allow backup or restore") .GetCode(); } AsyncTaskOnIncrementalBackup(); - return 0; + return ERR_OK; } tuple BackupExtExtension::GetIncrementalBackupFileHandle() @@ -1546,16 +1945,46 @@ ErrCode BackupExtExtension::IncrementalBigFileReady(const TarMap &pkgInfo, } else { HILOGE("IncrementalBigFileReady interface fails to be invoked: %{public}d", ret); } - fdNum += FILE_AND_MANIFEST_FD_COUNT; + fdNum += BConstants::FILE_AND_MANIFEST_FD_COUNT; RefreshTimeInfo(startTime, fdNum); } HILOGI("IncrementalBigFileReady End"); return ret; } +int BackupExtExtension::DoIncrementalBackupTask(UniqueFd incrementalFd, UniqueFd manifestFd) +{ + auto start = std::chrono::system_clock::now(); + vector allFiles; + vector smallFiles; + vector bigFiles; + CompareFiles(move(incrementalFd), move(manifestFd), allFiles, smallFiles, bigFiles); + auto ret = DoIncrementalBackup(allFiles, smallFiles, bigFiles); + if (ret == ERR_OK) { + auto end = std::chrono::system_clock::now(); + auto cost = std::chrono::duration_cast(end - start).count(); + if (cost >= BConstants::MAX_TIME_COST) { + std::stringstream ss; + ss << R"("spendTime": )"<< cost << R"(ms, "totalFiles": )" << allFiles.size() << R"(, "smallFiles": )" + << smallFiles.size() << R"(, "bigFiles": )" << bigFiles.size(); + AppRadar::Info info(bundleName_, "", ss.str()); + AppRadar::GetInstance().RecordBackupFuncRes(info, "BackupExtExtension::DoIncrementalBackupTask", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_DO_BACKUP, static_cast(ret)); + } + } + return ret; +} + void BackupExtExtension::AsyncTaskDoIncrementalBackup(UniqueFd incrementalFd, UniqueFd manifestFd) { - HILOGI("Start AsyncTaskDoIncrementalBackup"); + HILOGI("Do IncrementalBackup, start fwk timer begin."); + bool isFwkStart; + StartFwkTimer(isFwkStart); + if (!isFwkStart) { + HILOGE("Do IncrementalBackup, start fwk timer fail."); + return; + } + HILOGI("Do IncrementalBackup, start fwk timer end."); int incrementalFdDup = dup(incrementalFd); int manifestFdDup = dup(manifestFd); if (incrementalFdDup < 0) { @@ -1572,11 +2001,7 @@ void BackupExtExtension::AsyncTaskDoIncrementalBackup(UniqueFd incrementalFd, Un } close(incrementalFdDup); close(manifestFdDup); - vector allFiles; - vector smallFiles; - vector bigFiles; - ptr->CompareFiles(move(incrementalDupFd), move(manifestDupFd), allFiles, smallFiles, bigFiles); - auto ret = ptr->DoIncrementalBackup(allFiles, smallFiles, bigFiles); + auto ret = ptr->DoIncrementalBackupTask(move(incrementalDupFd), move(manifestDupFd)); ptr->AppIncrementalDone(ret); HILOGI("Incremental backup app done %{public}d", ret); } catch (const BError &e) { @@ -1602,21 +2027,20 @@ void BackupExtExtension::AsyncTaskDoIncrementalBackup(UniqueFd incrementalFd, Un void BackupExtExtension::AsyncTaskOnIncrementalBackup() { auto task = [obj {wptr(this)}]() { - auto callBackup = [obj](ErrCode errCode, std::string errMsg) { - HILOGI("App onbackup end"); - auto proxy = ServiceProxy::GetInstance(); - if (proxy == nullptr) { - throw BError(BError::Codes::EXT_BROKEN_BACKUP_SA, std::generic_category().message(errno)); - } - HILOGI("Start GetAppLocalListAndDoIncrementalBackup"); - proxy->GetAppLocalListAndDoIncrementalBackup(); - }; auto ptr = obj.promote(); BExcepUltils::BAssert(ptr, BError::Codes::EXT_BROKEN_FRAMEWORK, "Ext extension handle have been released"); BExcepUltils::BAssert(ptr->extension_, BError::Codes::EXT_INVAL_ARG, "Extension handle have been released"); try { - auto callBackupEx = ptr->HandleBackupEx(obj); - ptr->extension_->OnBackup(callBackup, callBackupEx); + ptr->curScenario_ = BackupRestoreScenario::INCREMENTAL_BACKUP; + ptr->StartOnProcessTaskThread(obj, BackupRestoreScenario::INCREMENTAL_BACKUP); + auto callBackup = ptr->IncOnBackupCallback(obj); + auto callBackupEx = ptr->IncOnBackupExCallback(obj); + ptr->UpdateOnStartTime(); + ErrCode err = ptr->extension_->OnBackup(callBackup, callBackupEx); + if (err != ERR_OK) { + HILOGE("OnBackup done, err = %{pubilc}d", err); + ptr->AppIncrementalDone(BError::GetCodeByErrno(err)); + } } catch (const BError &e) { ptr->AppIncrementalDone(e.GetCode()); } catch (const exception &e) { @@ -1651,7 +2075,7 @@ void BackupExtExtension::IncrementalPacket(const vector & { HILOGI("IncrementalPacket begin, infos count: %{public}zu", infos.size()); string path = string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_BACKUP); - int64_t totalSize = 0; + uint64_t totalSize = 0; uint32_t fileCount = 0; vector packFiles; vector tarInfos; @@ -1659,14 +2083,15 @@ void BackupExtExtension::IncrementalPacket(const vector & auto startTime = std::chrono::system_clock::now(); int fdNum = 0; string partName = GetIncrmentPartName(); + auto reportCb = ReportErrFileByProc(wptr {this}, curScenario_); for (auto small : infos) { - totalSize += small.size; + totalSize += static_cast(small.size); fileCount += 1; packFiles.emplace_back(small.filePath); tarInfos.emplace_back(small); - if (totalSize >= DEFAULT_SLICE_SIZE || fileCount >= MAX_FILE_COUNT) { + if (totalSize >= BConstants::DEFAULT_SLICE_SIZE || fileCount >= BConstants::MAX_FILE_COUNT) { TarMap tarMap {}; - TarFile::GetInstance().Packet(packFiles, partName, path, tarMap); + TarFile::GetInstance().Packet(packFiles, partName, path, tarMap, reportCb); tar.insert(tarMap.begin(), tarMap.end()); // 执行tar包回传功能 WaitToSendFd(startTime, fdNum); @@ -1675,14 +2100,14 @@ void BackupExtExtension::IncrementalPacket(const vector & fileCount = 0; packFiles.clear(); tarInfos.clear(); - fdNum += FILE_AND_MANIFEST_FD_COUNT; + fdNum += BConstants::FILE_AND_MANIFEST_FD_COUNT; RefreshTimeInfo(startTime, fdNum); } } if (fileCount > 0) { // 打包回传 TarMap tarMap {}; - TarFile::GetInstance().Packet(packFiles, partName, path, tarMap); + TarFile::GetInstance().Packet(packFiles, partName, path, tarMap, reportCb); IncrementalTarFileReady(tarMap, tarInfos, proxy); fdNum = 1; WaitToSendFd(startTime, fdNum); @@ -1748,9 +2173,9 @@ int BackupExtExtension::DoIncrementalBackup(const vector if (smallFiles.size() == 0 && bigFiles.size() == 0) { // 没有增量,则不需要上传 TarMap tMap; - IncrementalAllFileReady(tMap, allFiles, proxy); + ErrCode err = IncrementalAllFileReady(tMap, allFiles, proxy); HILOGI("Do increment backup, IncrementalAllFileReady end, file empty"); - return ERR_OK; + return err; } // tar包数据 TarMap tarMap; @@ -1762,230 +2187,9 @@ int BackupExtExtension::DoIncrementalBackup(const vector HILOGI("Do increment backup, IncrementalBigFileReady end"); bigMap.insert(tarMap.begin(), tarMap.end()); // 回传manage.json和全量文件 - IncrementalAllFileReady(bigMap, allFiles, proxy); + ErrCode err = IncrementalAllFileReady(bigMap, allFiles, proxy); HILOGI("End, bigFiles num:%{public}zu, smallFiles num:%{public}zu, allFiles num:%{public}zu", bigFiles.size(), smallFiles.size(), allFiles.size()); - return ERR_OK; -} - -void BackupExtExtension::AppIncrementalDone(ErrCode errCode) -{ - HILOGI("Begin"); - auto proxy = ServiceProxy::GetInstance(); - BExcepUltils::BAssert(proxy, BError::Codes::EXT_BROKEN_IPC, "Failed to obtain the ServiceProxy handle"); - auto ret = proxy->AppIncrementalDone(errCode); - if (ret != ERR_OK) { - HILOGE("Failed to notify the app done. err = %{public}d", ret); - } -} - -ErrCode BackupExtExtension::GetBackupInfo(std::string &result) -{ - auto obj = wptr(this); - auto ptr = obj.promote(); - if (ptr == nullptr) { - HILOGE("Failed to get ext extension."); - return BError(BError::Codes::EXT_INVAL_ARG, "extension getBackupInfo exception").GetCode(); - } - if (ptr->extension_ == nullptr) { - HILOGE("Failed to get extension."); - return BError(BError::Codes::EXT_INVAL_ARG, "extension getBackupInfo exception").GetCode(); - } - auto callBackup = [ptr](ErrCode errCode, const std::string result) { - if (ptr == nullptr) { - HILOGE("Failed to get ext extension."); - return; - } - HILOGI("GetBackupInfo callBackup start. result = %{public}s", result.c_str()); - ptr->backupInfo_ = result; - }; - auto ret = ptr->extension_->GetBackupInfo(callBackup); - if (ret != ERR_OK) { - HILOGE("Failed to get backupInfo. err = %{public}d", ret); - return BError(BError::Codes::EXT_INVAL_ARG, "extension getBackupInfo exception").GetCode(); - } - HILOGD("backupInfo = %s", backupInfo_.c_str()); - result = backupInfo_; - backupInfo_.clear(); - - return ERR_OK; -} - -ErrCode BackupExtExtension::UpdateFdSendRate(std::string &bundleName, int32_t sendRate) -{ - std::lock_guard lock(updateSendRateLock_); - HILOGI("Update SendRate, bundleName:%{public}s, sendRate:%{public}d", bundleName.c_str(), sendRate); - VerifyCaller(); - bundleName_ = bundleName; - sendRate_ = sendRate; - if (sendRate > 0) { - startSendFdRateCon_.notify_one(); - } - return ERR_OK; -} - -std::function BackupExtExtension::RestoreResultCallbackEx(wptr obj) -{ - HILOGI("Begin get callbackEx"); - return [obj](ErrCode errCode, const std::string restoreRetInfo) { - auto extensionPtr = obj.promote(); - if (extensionPtr == nullptr) { - HILOGE("Ext extension handle have been released"); - return; - } - if (extensionPtr->extension_ == nullptr) { - HILOGE("Extension handle have been released"); - return; - } - extensionPtr->extension_->InvokeAppExtMethod(errCode, restoreRetInfo); - if (errCode == ERR_OK) { - if (restoreRetInfo.size()) { - HILOGI("Will notify restore result report"); - extensionPtr->AppResultReport(restoreRetInfo, BackupRestoreScenario::FULL_RESTORE); - } - return; - } - if (restoreRetInfo.empty()) { - extensionPtr->AppDone(errCode); - extensionPtr->DoClear(); - } else { - std::string errInfo; - BJsonUtil::BuildRestoreErrInfo(errInfo, errCode, restoreRetInfo); - extensionPtr->AppResultReport(errInfo, BackupRestoreScenario::FULL_RESTORE, errCode); - extensionPtr->DoClear(); - } - }; -} - -std::function BackupExtExtension::AppDoneCallbackEx(wptr obj) -{ - HILOGI("Begin get callback for appDone"); - return [obj](ErrCode errCode, std::string errMsg) { - HILOGI("begin call callBackupExAppDone"); - auto extensionPtr = obj.promote(); - if (extensionPtr == nullptr) { - HILOGE("Ext extension handle have been released"); - return; - } - extensionPtr->AppDone(errCode); - extensionPtr->DoClear(); - }; -} - -std::function BackupExtExtension::IncRestoreResultCallbackEx(wptr obj) -{ - HILOGI("Begin get callback for onRestore"); - return [obj](ErrCode errCode, const std::string restoreRetInfo) { - HILOGI("begin call restoreEx"); - auto extensionPtr = obj.promote(); - if (extensionPtr == nullptr) { - HILOGE("Ext extension handle have been released"); - return; - } - if (extensionPtr->extension_ == nullptr) { - HILOGE("Extension handle have been released"); - return; - } - extensionPtr->extension_->InvokeAppExtMethod(errCode, restoreRetInfo); - if (errCode == ERR_OK) { - if (restoreRetInfo.size()) { - extensionPtr->AppResultReport(restoreRetInfo, BackupRestoreScenario::INCREMENTAL_RESTORE); - } - return; - } - if (restoreRetInfo.empty()) { - extensionPtr->AppIncrementalDone(errCode); - extensionPtr->DoClear(); - } else { - std::string errInfo; - BJsonUtil::BuildRestoreErrInfo(errInfo, errCode, restoreRetInfo); - extensionPtr->AppResultReport(errInfo, BackupRestoreScenario::INCREMENTAL_RESTORE, errCode); - extensionPtr->DoClear(); - } - }; -} - -std::function BackupExtExtension::HandleBackupEx(wptr obj) -{ - HILOGI("Begin get HandleBackupEx"); - return [obj](ErrCode errCode, const std::string backupExRetInfo) { - auto proxy = ServiceProxy::GetInstance(); - if (proxy == nullptr) { - throw BError(BError::Codes::EXT_BROKEN_BACKUP_SA, std::generic_category().message(errno)); - } - auto extensionPtr = obj.promote(); - if (extensionPtr == nullptr) { - HILOGE("Ext extension handle have been released"); - return; - } - if (extensionPtr->extension_ == nullptr) { - HILOGE("Extension handle have been released"); - return; - } - extensionPtr->extension_->InvokeAppExtMethod(errCode, backupExRetInfo); - if (backupExRetInfo.size()) { - HILOGI("Start GetAppLocalListAndDoIncrementalBackup"); - proxy->GetAppLocalListAndDoIncrementalBackup(); - HILOGI("Will notify backup result report"); - extensionPtr->AppResultReport(backupExRetInfo, BackupRestoreScenario::INCREMENTAL_BACKUP); - } - }; -} - -std::function BackupExtExtension::HandleTaskBackupEx(wptr obj) -{ - HILOGI("Begin get HandleTaskBackupEx"); - return [obj](ErrCode errCode, const std::string backupExRetInfo) { - HILOGI("begin call backup"); - auto extensionPtr = obj.promote(); - if (extensionPtr == nullptr) { - HILOGE("Ext extension handle have been released"); - return; - } - if (extensionPtr->extension_ == nullptr) { - HILOGE("Extension handle have been released"); - return; - } - extensionPtr->extension_->InvokeAppExtMethod(errCode, backupExRetInfo); - if (backupExRetInfo.size()) { - extensionPtr->AsyncTaskBackup(extensionPtr->extension_->GetUsrConfig()); - HILOGI("Will notify backup result report"); - extensionPtr->AppResultReport(backupExRetInfo, BackupRestoreScenario::FULL_BACKUP); - } - }; -} - -void BackupExtExtension::WaitToSendFd(std::chrono::system_clock::time_point &startTime, int &fdSendNum) -{ - HILOGD("WaitToSendFd Begin"); - std::unique_lock lock(startSendMutex_); - startSendFdRateCon_.wait(lock, [this] { return sendRate_ > 0; }); - if (fdSendNum >= sendRate_) { - HILOGI("current time fd num is max rate, bundle name:%{public}s, rate:%{public}d", bundleName_.c_str(), - sendRate_); - auto curTime = std::chrono::system_clock::now(); - auto useTimeMs = std::chrono::duration_cast(curTime - startTime).count(); - if (useTimeMs < MAX_FD_GROUP_USE_TIME) { - int32_t sleepTime = MAX_FD_GROUP_USE_TIME - useTimeMs; - HILOGI("will wait time:%{public}d ms", sleepTime); - std::this_thread::sleep_for(std::chrono::milliseconds(sleepTime)); - } else { - HILOGW("current fd send num exceeds one second"); - } - fdSendNum = 0; - startTime = std::chrono::system_clock::now(); - } - HILOGD("WaitToSendFd End"); -} - -void BackupExtExtension::RefreshTimeInfo(std::chrono::system_clock::time_point &startTime, int &fdSendNum) -{ - auto currentTime = std::chrono::system_clock::now(); - auto useTime = std::chrono::duration_cast(currentTime - startTime).count(); - if (useTime >= MAX_FD_GROUP_USE_TIME) { - HILOGI("RefreshTimeInfo Begin, fdSendNum is:%{public}d", fdSendNum); - startTime = std::chrono::system_clock::now(); - fdSendNum = 0; - } + return err; } } // namespace OHOS::FileManagement::Backup diff --git a/frameworks/native/backup_ext/src/ext_extension_stub.cpp b/frameworks/native/backup_ext/src/ext_extension_stub.cpp index 6930c2982442cc28ec4a863fde44fee1ac5d4be0..9e7b43539084af27b2601d54a57ab45be298fd74 100644 --- a/frameworks/native/backup_ext/src/ext_extension_stub.cpp +++ b/frameworks/native/backup_ext/src/ext_extension_stub.cpp @@ -51,6 +51,8 @@ ExtExtensionStub::ExtExtensionStub() &ExtExtensionStub::CmdIncrementalOnBackup; opToInterfaceMap_[static_cast(IExtensionInterfaceCode::CMD_UPDATE_FD_SENDRATE)] = &ExtExtensionStub::CmdUpdateFdSendRate; + opToInterfaceMap_[static_cast(IExtensionInterfaceCode::CMD_HANDLE_USER_0_BACKUP)] = + &ExtExtensionStub::CmdHandleUser0Backup; } int32_t ExtExtensionStub::OnRemoteRequest(uint32_t code, @@ -106,7 +108,9 @@ ErrCode ExtExtensionStub::CmdHandleClear(MessageParcel &data, MessageParcel &rep ErrCode ExtExtensionStub::CmdHandleBackup(MessageParcel &data, MessageParcel &reply) { - ErrCode res = HandleBackup(); + bool isClearData = true; + isClearData = data.ReadBool(); + ErrCode res = HandleBackup(isClearData); if (!reply.WriteInt32(res)) { stringstream ss; ss << "Failed to send the result " << res; @@ -133,7 +137,9 @@ ErrCode ExtExtensionStub::CmdPublishFile(MessageParcel &data, MessageParcel &rep ErrCode ExtExtensionStub::CmdHandleRestore(MessageParcel &data, MessageParcel &reply) { - ErrCode res = HandleRestore(); + bool isClearData = true; + isClearData = data.ReadBool(); + ErrCode res = HandleRestore(isClearData); if (!reply.WriteInt32(res)) { stringstream ss; ss << "Failed to send the result " << res; @@ -187,7 +193,9 @@ ErrCode ExtExtensionStub::CmdHandleIncrementalBackup(MessageParcel &data, Messag ErrCode ExtExtensionStub::CmdIncrementalOnBackup(MessageParcel &data, MessageParcel &reply) { - ErrCode res = IncrementalOnBackup(); + bool isClearData = true; + isClearData = data.ReadBool(); + ErrCode res = IncrementalOnBackup(isClearData); if (!reply.WriteInt32(res)) { stringstream ss; ss << "Failed to send the result " << res; @@ -239,4 +247,14 @@ ErrCode ExtExtensionStub::CmdUpdateFdSendRate(MessageParcel &data, MessageParcel } return BError(BError::Codes::OK); } + +ErrCode ExtExtensionStub::CmdHandleUser0Backup(MessageParcel &data, MessageParcel &reply) +{ + HILOGD("CmdHandleUser0Backup Begin"); + int ret = User0OnBackup(); + if (!reply.WriteInt32(ret)) { + return BError(BError::Codes::EXT_BROKEN_IPC, "Failed to send out the ret").GetCode(); + } + return BError(BError::Codes::OK); +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/frameworks/native/backup_ext/src/sub_ext_extension.cpp b/frameworks/native/backup_ext/src/sub_ext_extension.cpp new file mode 100644 index 0000000000000000000000000000000000000000..6effe0cc54baa7ec8553464a823fdcf1a083d346 --- /dev/null +++ b/frameworks/native/backup_ext/src/sub_ext_extension.cpp @@ -0,0 +1,994 @@ +/* + * Copyright (c) 2024 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "ext_extension.h" + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include + +#include +#include + +#include "accesstoken_kit.h" +#include "bundle_mgr_client.h" +#include "errors.h" +#include "ipc_skeleton.h" + +#include "b_error/b_error.h" +#include "b_error/b_excep_utils.h" +#include "b_filesystem/b_dir.h" +#include "b_filesystem/b_file.h" +#include "b_filesystem/b_file_hash.h" +#include "b_json/b_json_cached_entity.h" +#include "b_jsonutil/b_jsonutil.h" +#include "b_ohos/startup/backup_para.h" +#include "b_radar/b_radar.h" +#include "b_tarball/b_tarball_factory.h" +#include "filemgmt_libhilog.h" +#include "hitrace_meter.h" +#include "i_service.h" +#include "sandbox_helper.h" +#include "service_proxy.h" +#include "tar_file.h" +#include "b_anony/b_anony.h" + +namespace OHOS::FileManagement::Backup { +const uint32_t MAX_FD_GROUP_USE_TIME = 1000; // 每组打开最大时间1000ms + +void BackupExtExtension::WaitToSendFd(std::chrono::system_clock::time_point &startTime, int &fdSendNum) +{ + HILOGD("WaitToSendFd Begin"); + std::unique_lock lock(startSendMutex_); + startSendFdRateCon_.wait(lock, [this] { return sendRate_ > 0; }); + if (fdSendNum >= sendRate_) { + HILOGI("current time fd num is max rate, bundle name:%{public}s, rate:%{public}d", bundleName_.c_str(), + sendRate_); + auto curTime = std::chrono::system_clock::now(); + auto useTimeMs = std::chrono::duration_cast(curTime - startTime).count(); + if (useTimeMs < MAX_FD_GROUP_USE_TIME) { + int32_t sleepTime = MAX_FD_GROUP_USE_TIME - useTimeMs; + HILOGI("will wait time:%{public}d ms", sleepTime); + std::this_thread::sleep_for(std::chrono::milliseconds(sleepTime)); + } else { + HILOGW("current fd send num exceeds one second"); + } + fdSendNum = 0; + startTime = std::chrono::system_clock::now(); + } + HILOGD("WaitToSendFd End"); +} + +void BackupExtExtension::RefreshTimeInfo(std::chrono::system_clock::time_point &startTime, int &fdSendNum) +{ + auto currentTime = std::chrono::system_clock::now(); + auto useTime = std::chrono::duration_cast(currentTime - startTime).count(); + if (useTime >= MAX_FD_GROUP_USE_TIME) { + HILOGI("RefreshTimeInfo Begin, fdSendNum is:%{public}d", fdSendNum); + startTime = std::chrono::system_clock::now(); + fdSendNum = 0; + } +} + +void BackupExtExtension::SetClearDataFlag(bool isClearData) +{ + isClearData_ = isClearData; + HILOGI("set clear data flag:%{public}d", isClearData); + if (extension_ == nullptr) { + HILOGE("Extension handle have been released"); + return; + } + if (!extension_->WasFromSpecialVersion() && !extension_->RestoreDataReady()) { + DoClear(); + } +} + +string BackupExtExtension::GetBundlePath() +{ + if (bundleName_ == BConstants::BUNDLE_FILE_MANAGER) { + return string(BConstants::PATH_FILEMANAGE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); + } else if (bundleName_ == BConstants::BUNDLE_MEDIAL_DATA) { + return string(BConstants::PATH_MEDIALDATA_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); + } + return string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_RESTORE); +} + +std::map BackupExtExtension::GetIdxFileInfos(bool isSpecialVersion) +{ + string restoreDir = isSpecialVersion ? "" : GetBundlePath(); + auto extManageInfo = GetExtManageInfo(); + std::map idxFileInfos; + for (size_t i = 0; i < extManageInfo.size(); ++i) { + std::string realPath = restoreDir + extManageInfo[i].hashName; + idxFileInfos[realPath] = extManageInfo[i].sta.st_size; + } + return idxFileInfos; +} + +void BackupExtExtension::CheckTmpDirFileInfos(bool isSpecialVersion) +{ + ErrFileInfo errFiles; + auto idxFileInfos = GetIdxFileInfos(isSpecialVersion); + struct stat attr; + for (auto it : idxFileInfos) { + if (it.first.size() >= PATH_MAX || stat(it.first.data(), &attr) == -1) { + HILOGE("(Debug) Failed to get stat of %{public}s, errno = %{public}d", GetAnonyPath(it.first).c_str(), + errno); + errFiles[it.first].push_back(errno); + } else if (it.second != attr.st_size && (!S_ISDIR(attr.st_mode))) { + HILOGE("(Debug) RecFile:%{public}s size err, recSize: %{public}" PRId64 ", idxSize: %{public}" PRId64 "", + GetAnonyPath(it.first).c_str(), attr.st_size, it.second); + errFiles[it.first] = std::vector(); + } + } + HILOGE("(Debug) Temp file check result: Total file: %{public}zu, err file: %{public}zu", idxFileInfos.size(), + errFiles.size()); + if (!errFiles.empty()) { + HILOGE("(Debug) The received file and idx is not same"); + std::stringstream ss; + ss << R"("totalFile": )" << idxFileInfos.size() << R"(, "restoreFile": )" + << idxFileInfos.size() - errFiles.size() << R"(, "info": "different received file and idx")"; + AppRadar::Info info (bundleName_, "", ss.str()); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BackupExtExtension::CheckTmpDirFileInfos", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_CHECK_DATA_FAIL, + static_cast(BError::BackupErrorCode::E_UKERR)); + } else { + HILOGI("(Debug) The received file and idx is same"); + } +} + +tuple> BackupExtExtension::CheckRestoreFileInfos() +{ + vector errFiles; + struct stat curFileStat {}; + for (const auto &it : endFileInfos_) { + if (lstat(it.first.c_str(), &curFileStat) != 0) { + HILOGE("Failed to lstat %{public}s, err = %{public}d", GetAnonyPath(it.first).c_str(), errno); + errFiles.emplace_back(it.first); + errFileInfos_[it.first].push_back(errno); + } else if (curFileStat.st_size != it.second && (!S_ISDIR(curFileStat.st_mode))) { + HILOGE("File size error, file: %{public}s, idx: %{public}" PRId64 ", act: %{public}" PRId64 "", + GetAnonyPath(it.first).c_str(), it.second, curFileStat.st_size); + errFiles.emplace_back(it.first); + errFileInfos_[it.first].push_back(errno); + } + } + for (const auto &it : errFileInfos_) { + for (const auto &codeIt : it.second) { + HILOGE("(Debug) errfileInfos file = %{public}s -> %{public}d", GetAnonyPath(it.first).c_str(), codeIt); + } + } + HILOGE("(Debug) End file check result Total file: %{public}zu, err file: %{public}zu", endFileInfos_.size(), + errFileInfos_.size()); + if (errFiles.size()) { + std::stringstream ss; + ss << R"("totalFile": )" << endFileInfos_.size() << R"(, "restoreFile": )" + << endFileInfos_.size() - errFileInfos_.size(); + AppRadar::Info info (bundleName_, "", ss.str()); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BackupExtExtension::CheckRestoreFileInfos", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_CHECK_DATA_FAIL, + static_cast(BError::BackupErrorCode::E_UKERR)); + return { false, errFiles }; + } + return { true, errFiles }; +} + +std::function BackupExtExtension::OnRestoreCallback(wptr obj) +{ + HILOGI("Begin get full restore onRestore callback"); + return [obj](ErrCode errCode, std::string errMsg) { + auto extensionPtr = obj.promote(); + if (extensionPtr == nullptr) { + HILOGE("Ext extension handle have been released"); + return; + } + if (extensionPtr->isExecAppDone_.load()) { + HILOGE("Appdone has been executed for the current application"); + return; + } + HILOGI("Current bundle will execute app done"); + if (errCode == ERR_OK) { + auto spendTime = extensionPtr->GetOnStartTimeCost(); + if (spendTime >= BConstants::MAX_TIME_COST) { + std::stringstream ss; + ss << R"("spendTime": )"<< spendTime << "ms"; + AppRadar::Info info (extensionPtr->bundleName_, "", ss.str()); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BackupExtExtension::OnRestoreCallback", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_ON_RESTORE, ERR_OK); + } + } + extensionPtr->FinishOnProcessTask(); + if (errMsg.empty()) { + extensionPtr->AppDone(errCode); + } else { + std::string errInfo; + BJsonUtil::BuildExtensionErrInfo(errInfo, errCode, errMsg); + extensionPtr->AppResultReport(errInfo, BackupRestoreScenario::FULL_RESTORE, errCode); + } + extensionPtr->DoClear(); + }; +} + +std::function BackupExtExtension::OnRestoreExCallback(wptr obj) +{ + HILOGI("Begin get full restore onRestoreEx callback"); + return [obj](ErrCode errCode, const std::string restoreRetInfo) { + auto extensionPtr = obj.promote(); + if (extensionPtr == nullptr) { + HILOGE("Ext extension handle have been released"); + return; + } + if (extensionPtr->extension_ == nullptr) { + HILOGE("Extension handle have been released"); + return; + } + if (extensionPtr->isExecAppDone_.load()) { + HILOGE("Appdone has been executed for the current application"); + return; + } + if (errCode == ERR_OK && !restoreRetInfo.empty()) { + auto spendTime = extensionPtr->GetOnStartTimeCost(); + if (spendTime >= BConstants::MAX_TIME_COST) { + std::stringstream ss; + ss << R"("spendTime": )"<< spendTime << "ms"; + AppRadar::Info info (extensionPtr->bundleName_, "", ss.str()); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BackupExtExtension::OnRestoreExCallback", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_ON_RESTORE, ERR_OK); + } + } + extensionPtr->FinishOnProcessTask(); + extensionPtr->extension_->InvokeAppExtMethod(errCode, restoreRetInfo); + if (errCode == ERR_OK) { + if (restoreRetInfo.size()) { + HILOGI("Will notify restore result report"); + extensionPtr->AppResultReport(restoreRetInfo, BackupRestoreScenario::FULL_RESTORE); + } + return; + } + if (restoreRetInfo.empty()) { + extensionPtr->AppDone(errCode); + extensionPtr->DoClear(); + } else { + std::string errInfo; + BJsonUtil::BuildExtensionErrInfo(errInfo, errCode, restoreRetInfo); + extensionPtr->AppResultReport(errInfo, BackupRestoreScenario::FULL_RESTORE, errCode); + extensionPtr->DoClear(); + } + }; +} + +std::function BackupExtExtension::AppDoneCallbackEx(wptr obj) +{ + HILOGI("Begin get callback for appDone"); + return [obj](ErrCode errCode, std::string errMsg) { + HILOGI("begin call callBackupExAppDone"); + auto extensionPtr = obj.promote(); + if (extensionPtr == nullptr) { + HILOGE("Ext extension handle have been released"); + return; + } + extensionPtr->AppDone(errCode); + extensionPtr->DoClear(); + }; +} + +std::function BackupExtExtension::IncreOnRestoreExCallback(wptr obj) +{ + HILOGI("Begin get callback for increment onRestoreEx"); + return [obj](ErrCode errCode, const std::string restoreRetInfo) { + HILOGI("begin call increment restoreEx"); + auto extensionPtr = obj.promote(); + if (extensionPtr == nullptr) { + HILOGE("Ext extension handle have been released"); + return; + } + if (extensionPtr->extension_ == nullptr) { + HILOGE("Extension handle have been released"); + return; + } + if (extensionPtr->isExecAppDone_.load()) { + HILOGE("Appdone has been executed for the current application"); + return; + } + if (errCode == ERR_OK && !restoreRetInfo.empty()) { + auto spendTime = extensionPtr->GetOnStartTimeCost(); + if (spendTime >= BConstants::MAX_TIME_COST) { + std::stringstream ss; + ss << R"("spendTime": )"<< spendTime << "ms"; + AppRadar::Info info (extensionPtr->bundleName_, "", ss.str()); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BackupExtExtension::IncreOnRestoreExCallback", + AppRadar::GetInstance().GetUserId(), + BizStageRestore::BIZ_STAGE_ON_RESTORE, ERR_OK); + } + } + extensionPtr->FinishOnProcessTask(); + extensionPtr->extension_->InvokeAppExtMethod(errCode, restoreRetInfo); + if (errCode == ERR_OK) { + if (restoreRetInfo.size()) { + extensionPtr->AppResultReport(restoreRetInfo, BackupRestoreScenario::INCREMENTAL_RESTORE); + } + return; + } + if (restoreRetInfo.empty()) { + extensionPtr->AppIncrementalDone(errCode); + extensionPtr->DoClear(); + } else { + std::string errInfo; + BJsonUtil::BuildExtensionErrInfo(errInfo, errCode, restoreRetInfo); + extensionPtr->AppResultReport(errInfo, BackupRestoreScenario::INCREMENTAL_RESTORE, errCode); + extensionPtr->DoClear(); + } + }; +} + +std::function BackupExtExtension::IncreOnRestoreCallback(wptr obj) +{ + return [obj](ErrCode errCode, std::string errMsg) { + auto extensionPtr = obj.promote(); + if (extensionPtr == nullptr) { + HILOGE("Ext extension handle have been released"); + return; + } + if (extensionPtr->isExecAppDone_.load()) { + HILOGE("Appdone has been executed for the current application"); + return; + } + HILOGI("Current bundle will execute app done"); + if (errCode == ERR_OK) { + auto spendTime = extensionPtr->GetOnStartTimeCost(); + if (spendTime >= BConstants::MAX_TIME_COST) { + std::stringstream ss; + ss << R"("spendTime": )"<< spendTime << "ms"; + AppRadar::Info info (extensionPtr->bundleName_, "", ss.str()); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BackupExtExtension::IncreOnRestoreCallback", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_ON_RESTORE, ERR_OK); + } + } + extensionPtr->FinishOnProcessTask(); + if (errMsg.empty()) { + extensionPtr->AppIncrementalDone(errCode); + } else { + std::string errInfo; + BJsonUtil::BuildExtensionErrInfo(errInfo, errCode, errMsg); + extensionPtr->AppResultReport(errInfo, BackupRestoreScenario::INCREMENTAL_RESTORE, errCode); + } + extensionPtr->DoClear(); + }; +} + +int32_t BackupExtExtension::GetOnStartTimeCost() +{ + auto onBackupRestoreEnd = std::chrono::system_clock::now(); + std::lock_guard lock(onStartTimeLock_); + auto spendTime = std::chrono::duration_cast(onBackupRestoreEnd - g_onStart).count(); + return spendTime; +} + +std::function BackupExtExtension::OnBackupCallback(wptr obj) +{ + HILOGI("Begin get HandleFullBackupCallbackEx"); + return [obj](ErrCode errCode, std::string errMsg) { + HILOGI("begin call backup"); + auto extensionPtr = obj.promote(); + if (extensionPtr == nullptr) { + HILOGE("Ext extension handle have been released"); + return; + } + if (extensionPtr->extension_ == nullptr) { + HILOGE("Extension handle have been released"); + return; + } + if (extensionPtr->isExecAppDone_.load()) { + HILOGE("Appdone has been executed for the current application"); + return; + } + extensionPtr->FinishOnProcessTask(); + if (errCode == ERR_OK) { + auto spendTime = extensionPtr->GetOnStartTimeCost(); + if (spendTime >= BConstants::MAX_TIME_COST) { + AppRadar::Info info(extensionPtr->bundleName_, "", string("\"spend_time\":\" "). + append(to_string(spendTime)).append(string("ms\""))); + AppRadar::GetInstance().RecordBackupFuncRes(info, "BackupExtExtension::OnBackupCallback", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_ON_BACKUP, + static_cast(ERR_OK)); + } + extensionPtr->AsyncTaskBackup(extensionPtr->extension_->GetUsrConfig()); + return; + } + HILOGE("Call extension onBackup failed, errInfo = %{public}s", errMsg.c_str()); + if (!errMsg.empty()) { + std::string errInfo; + BJsonUtil::BuildExtensionErrInfo(errInfo, errCode, errMsg); + extensionPtr->AppResultReport(errInfo, BackupRestoreScenario::FULL_BACKUP, errCode); + } + extensionPtr->AppDone(errCode); + extensionPtr->DoClear(); + }; +} + +std::function BackupExtExtension::OnBackupExCallback(wptr obj) +{ + HILOGI("Begin get HandleFullBackupCallbackEx"); + return [obj](ErrCode errCode, const std::string backupExRetInfo) { + HILOGI("begin call backup"); + auto extensionPtr = obj.promote(); + if (extensionPtr == nullptr) { + HILOGE("Ext extension handle have been released"); + return; + } + if (extensionPtr->extension_ == nullptr) { + HILOGE("Extension handle have been released"); + return; + } + if (extensionPtr->isExecAppDone_.load()) { + HILOGE("Appdone has been executed for the current application"); + return; + } + extensionPtr->extension_->InvokeAppExtMethod(errCode, backupExRetInfo); + if (errCode == ERR_OK) { + if (backupExRetInfo.size()) { + auto spendTime = extensionPtr->GetOnStartTimeCost(); + if (spendTime >= BConstants::MAX_TIME_COST) { + AppRadar::Info info(extensionPtr->bundleName_, "", string("\"spend_time\":\" "). + append(to_string(spendTime)).append(string("ms\""))); + AppRadar::GetInstance().RecordBackupFuncRes(info, "BackupExtExtension::OnBackupExCallback", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_ON_BACKUP, + static_cast(ERR_OK)); + } + HILOGI("Will notify backup result report"); + extensionPtr->FinishOnProcessTask(); + extensionPtr->AsyncTaskBackup(extensionPtr->extension_->GetUsrConfig()); + extensionPtr->AppResultReport(backupExRetInfo, BackupRestoreScenario::FULL_BACKUP); + } + return; + } + HILOGE("Call extension onBackupEx failed, errInfo = %{public}s", backupExRetInfo.c_str()); + extensionPtr->FinishOnProcessTask(); + if (!backupExRetInfo.empty()) { + std::string errInfo; + BJsonUtil::BuildExtensionErrInfo(errInfo, errCode, backupExRetInfo); + extensionPtr->AppResultReport(errInfo, BackupRestoreScenario::FULL_BACKUP, errCode); + } + extensionPtr->AppDone(errCode); + extensionPtr->DoClear(); + }; +} + +std::function BackupExtExtension::IncOnBackupCallback(wptr obj) +{ + HILOGI("Begin get IncOnBackupCallback"); + return [obj](ErrCode errCode, std::string errMsg) { + HILOGI("App onbackup end"); + auto proxy = ServiceProxy::GetInstance(); + if (proxy == nullptr) { + throw BError(BError::Codes::EXT_BROKEN_BACKUP_SA, std::generic_category().message(errno)); + } + auto extPtr = obj.promote(); + if (extPtr == nullptr) { + HILOGE("Current extension execute call backup error, extPtr is empty"); + return; + } + if (extPtr->isExecAppDone_.load()) { + HILOGE("Appdone has been executed for the current application"); + return; + } + HILOGI("Start GetAppLocalListAndDoIncrementalBackup"); + extPtr->FinishOnProcessTask(); + if (errCode == ERR_OK) { + auto spendTime = extPtr->GetOnStartTimeCost(); + if (spendTime >= BConstants::MAX_TIME_COST) { + AppRadar::Info info(extPtr->bundleName_, "", string("\"spend_time\":\" "). + append(to_string(spendTime)).append(string("ms\""))); + AppRadar::GetInstance().RecordBackupFuncRes(info, "BackupExtExtension::IncOnBackupCallback", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_ON_BACKUP, + static_cast(ERR_OK)); + } + proxy->GetAppLocalListAndDoIncrementalBackup(); + return; + } + HILOGE("Call extension IncOnBackup failed, errInfo = %{public}s", errMsg.c_str()); + if (!errMsg.empty()) { + std::string errInfo; + BJsonUtil::BuildExtensionErrInfo(errInfo, errCode, errMsg); + extPtr->AppResultReport(errInfo, BackupRestoreScenario::INCREMENTAL_BACKUP, errCode); + } + extPtr->AppIncrementalDone(errCode); + extPtr->DoClear(); + }; +} + +std::function BackupExtExtension::IncOnBackupExCallback(wptr obj) +{ + HILOGI("Begin get HandleIncBackupEx callback"); + return [obj](ErrCode errCode, const std::string backupExRetInfo) { + auto proxy = ServiceProxy::GetInstance(); + if (proxy == nullptr) { + throw BError(BError::Codes::EXT_BROKEN_BACKUP_SA, std::generic_category().message(errno)); + } + auto extensionPtr = obj.promote(); + if (extensionPtr == nullptr) { + HILOGE("Ext extension handle have been released"); + return; + } + if (extensionPtr->extension_ == nullptr) { + HILOGE("Extension handle have been released"); + return; + } + if (extensionPtr->isExecAppDone_.load()) { + HILOGE("Appdone has been executed for the current application"); + return; + } + extensionPtr->extension_->InvokeAppExtMethod(errCode, backupExRetInfo); + if (errCode == ERR_OK) { + if (backupExRetInfo.size()) { + auto spendTime = extensionPtr->GetOnStartTimeCost(); + if (spendTime >= BConstants::MAX_TIME_COST) { + AppRadar::Info info(extensionPtr->bundleName_, "", string("\"spend_time\":\" "). + append(to_string(spendTime)).append(string("ms\""))); + AppRadar::GetInstance().RecordBackupFuncRes(info, "BackupExtExtension::IncOnBackupExCallback", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_ON_BACKUP, + static_cast(ERR_OK)); + } + HILOGI("Start GetAppLocalListAndDoIncrementalBackup"); + extensionPtr->FinishOnProcessTask(); + proxy->GetAppLocalListAndDoIncrementalBackup(); + HILOGI("Will notify backup result report"); + extensionPtr->AppResultReport(backupExRetInfo, BackupRestoreScenario::INCREMENTAL_BACKUP); + } + return; + } + HILOGE("Call extension IncOnBackupEx failed, errInfo = %{public}s", backupExRetInfo.c_str()); + extensionPtr->FinishOnProcessTask(); + if (!backupExRetInfo.empty()) { + std::string errInfo; + BJsonUtil::BuildExtensionErrInfo(errInfo, errCode, backupExRetInfo); + extensionPtr->AppResultReport(errInfo, BackupRestoreScenario::INCREMENTAL_BACKUP, errCode); + } + extensionPtr->AppIncrementalDone(errCode); + extensionPtr->DoClear(); + }; +} + +void BackupExtExtension::ReportAppProcessInfo(const std::string processInfo, BackupRestoreScenario scenario) +{ + auto proxy = ServiceProxy::GetInstance(); + if (proxy == nullptr) { + HILOGE("Report app process error, proxy is empty"); + return; + } + HILOGI("Will notify backup sa process result"); + auto ret = proxy->ReportAppProcessInfo(processInfo, scenario); + if (ret != ERR_OK) { + HILOGE("Report app process error, ipc failed, ret:%{public}d", ret); + return; + } +} + +ErrCode BackupExtExtension::StartOnProcessTaskThread(wptr obj, BackupRestoreScenario scenario) +{ + HILOGI("Begin Create onProcess Task Thread"); + onProcessTimeoutTimer_.Setup(); + isFirstCallOnProcess_.store(true); + StartOnProcessTimeOutTimer(obj, scenario); + SyncCallJsOnProcessTask(obj, scenario); + if (isExecAppDone_.load()) { + HILOGE("Call onProcess timeout, Current extension finished"); + return BError(BError::Codes::EXT_ABILITY_TIMEOUT); + } + callJsOnProcessThread_ = std::thread([obj, scenario]() { + auto extPtr = obj.promote(); + if (extPtr == nullptr) { + HILOGE("Create onProcess Task thread failed, extPtr is empty"); + return; + } + extPtr->ExecCallOnProcessTask(obj, scenario); + }); + HILOGI("End Create onProcess Task End"); + return BError(BError::Codes::OK); +} + +void BackupExtExtension::ExecCallOnProcessTask(wptr obj, BackupRestoreScenario scenario) +{ + HILOGI("Begin"); + isFirstCallOnProcess_.store(false); + while (!stopCallJsOnProcess_.load()) { + std::unique_lock lock(onProcessLock_); + execOnProcessCon_.wait_for(lock, std::chrono::seconds(BConstants::CALL_APP_ON_PROCESS_TIME_INTERVAL), + [this] { return this->stopCallJsOnProcess_.load(); }); + if (stopCallJsOnProcess_.load()) { + HILOGE("Current extension execute js onProcess method finished"); + return; + } + HILOGI("Continue call js method onProcess"); + StartOnProcessTimeOutTimer(obj, scenario); + AsyncCallJsOnProcessTask(obj, scenario); + } + HILOGI("End"); +} + +void BackupExtExtension::AsyncCallJsOnProcessTask(wptr obj, BackupRestoreScenario scenario) +{ + HILOGI("Begin"); + if (stopCallJsOnProcess_.load()) { + HILOGE("Current extension execute finished"); + return; + } + auto task = [obj, scenario]() { + auto extPtr = obj.promote(); + if (extPtr == nullptr) { + HILOGE("Async Call js onProcess error, extPtr is empty"); + return; + } + extPtr->SyncCallJsOnProcessTask(obj, scenario); + }; + onProcessTaskPool_.AddTask([task]() { task(); }); + HILOGI("End"); +} + +void BackupExtExtension::SyncCallJsOnProcessTask(wptr obj, BackupRestoreScenario scenario) +{ + HILOGI("Begin"); + if (stopCallJsOnProcess_.load()) { + HILOGE("Current extension execute finished"); + return; + } + auto callBack = ReportOnProcessResultCallback(obj, scenario); + auto extenionPtr = obj.promote(); + if (extenionPtr == nullptr) { + HILOGE("Async call js onProcess failed, extenionPtr is empty"); + return; + } + ErrCode ret = extenionPtr->extension_->OnProcess(callBack); + if (ret != ERR_OK) { + HILOGE("Call OnProcess Failed, ret:%{public}d", ret); + return; + } + HILOGI("End"); +} + +void BackupExtExtension::FinishOnProcessTask() +{ + HILOGI("Begin"); + std::unique_lock lock(onProcessLock_); + stopCallJsOnProcess_.store(true); + isFirstCallOnProcess_.store(false); + isExecAppDone_.store(false); + onProcessTimeoutCnt_ = 0; + execOnProcessCon_.notify_one(); + lock.unlock(); + if (callJsOnProcessThread_.joinable()) { + callJsOnProcessThread_.join(); + } + HILOGI("End"); +} + +void BackupExtExtension::StartOnProcessTimeOutTimer(wptr obj, BackupRestoreScenario scenario) +{ + HILOGI("Begin"); + if (stopCallJsOnProcess_.load()) { + HILOGE("Current extension execute finished"); + return; + } + auto timeoutCallback = [obj, scenario]() { + auto extPtr = obj.promote(); + if (extPtr == nullptr) { + HILOGE("Start Create timeout callback failed, extPtr is empty"); + return; + } + if (extPtr->onProcessTimeoutCnt_.load() >= BConstants::APP_ON_PROCESS_TIMEOUT_MAX_COUNT || + extPtr->isFirstCallOnProcess_.load()) { + HILOGE("The extension invokes the onProcess for more than three times or the first invoking of the " + "onProcess times out, timeoutCnt:%{public}d", extPtr->onProcessTimeoutCnt_.load()); + std::unique_lock lock(extPtr->onProcessLock_); + extPtr->stopCallJsOnProcess_.store(true); + extPtr->isFirstCallOnProcess_.store(false); + extPtr->isExecAppDone_.store(true); + extPtr->onProcessTimeoutCnt_ = 0; + extPtr->execOnProcessCon_.notify_one(); + lock.unlock(); + if (scenario == BackupRestoreScenario::FULL_BACKUP || scenario == BackupRestoreScenario::FULL_RESTORE) { + extPtr->AppDone(BError(BError::Codes::EXT_ABILITY_TIMEOUT)); + } else if (scenario == BackupRestoreScenario::INCREMENTAL_BACKUP || + scenario == BackupRestoreScenario::INCREMENTAL_RESTORE) { + extPtr->AppIncrementalDone(BError(BError::Codes::EXT_ABILITY_TIMEOUT)); + } + return; + } + extPtr->onProcessTimeoutCnt_++; + extPtr->onProcessTimeout_.store(true); + HILOGE("Extension onProcess timeout, Increase cnt:%{public}d", extPtr->onProcessTimeoutCnt_.load()); + }; + int timeout = isFirstCallOnProcess_.load() ? BConstants::FIRST_CALL_APP_ON_PROCESS_MAX_TIMEOUT : + BConstants::APP_ON_PROCESS_MAX_TIMEOUT; + uint32_t timerId = onProcessTimeoutTimer_.Register(timeoutCallback, timeout, true); + onProcessTimeoutTimerId_ = timerId; + HILOGI("End"); +} + +void BackupExtExtension::CloseOnProcessTimeOutTimer() +{ + HILOGI("Begin"); + onProcessTimeoutTimer_.Unregister(onProcessTimeoutTimerId_); + HILOGI("End"); +} + +void BackupExtExtension::AppIncrementalDone(ErrCode errCode) +{ + HILOGI("Begin"); + auto proxy = ServiceProxy::GetInstance(); + if (proxy == nullptr) { + HILOGE("Failed to obtain the ServiceProxy handle"); + DoClear(); + return; + } + auto ret = proxy->AppIncrementalDone(errCode); + if (ret != ERR_OK) { + HILOGE("Failed to notify the app done. err = %{public}d", ret); + } +} + +ErrCode BackupExtExtension::GetBackupInfo(std::string &result) +{ + auto obj = wptr(this); + auto ptr = obj.promote(); + if (ptr == nullptr) { + HILOGE("Failed to get ext extension."); + return BError(BError::Codes::EXT_INVAL_ARG, "extension getBackupInfo exception").GetCode(); + } + if (ptr->extension_ == nullptr) { + HILOGE("Failed to get extension."); + return BError(BError::Codes::EXT_INVAL_ARG, "extension getBackupInfo exception").GetCode(); + } + auto callBackup = [ptr](ErrCode errCode, const std::string result) { + if (ptr == nullptr) { + HILOGE("Failed to get ext extension."); + return; + } + HILOGI("GetBackupInfo callBackup start. errCode = %{public}d, result = %{public}s", errCode, result.c_str()); + if (errCode == ERR_OK) { + ptr->backupInfo_ = result; + } + }; + auto ret = ptr->extension_->GetBackupInfo(callBackup); + if (ret != ERR_OK) { + HILOGE("Failed to get backupInfo. err = %{public}d", ret); + return BError(BError::Codes::EXT_INVAL_ARG, "extension getBackupInfo exception").GetCode(); + } + HILOGD("backupInfo = %s", backupInfo_.c_str()); + result = backupInfo_; + backupInfo_.clear(); + + return ERR_OK; +} + +ErrCode BackupExtExtension::UpdateFdSendRate(std::string &bundleName, int32_t sendRate) +{ + try { + std::lock_guard lock(updateSendRateLock_); + HILOGI("Update SendRate, bundleName:%{public}s, sendRate:%{public}d", bundleName.c_str(), sendRate); + VerifyCaller(); + bundleName_ = bundleName; + sendRate_ = sendRate; + if (sendRate > 0) { + startSendFdRateCon_.notify_one(); + } + return ERR_OK; + } catch (...) { + HILOGE("Failed to UpdateFdSendRate"); + return BError(BError::Codes::EXT_BROKEN_IPC).GetCode(); + } +} + +bool BackupExtExtension::SetStagingPathProperties() +{ + struct stat curBundleStat {}; + if (lstat(BConstants::BUNDLE_BASE_DIR.c_str(), &curBundleStat) != 0) { + HILOGE("Failed to lstat, err = %{public}d", errno); + return false; + } + if (lchown(string(BConstants::PATH_BUNDLE_BACKUP_HOME).c_str(), + curBundleStat.st_uid, curBundleStat.st_gid) != 0) { + HILOGE("Failed to lchown, err = %{public}d", errno); + return false; + } + if (lchown(string(BConstants::PATH_BUNDLE_BACKUP_HOME_EL1).c_str(), + curBundleStat.st_uid, curBundleStat.st_gid) != 0) { + HILOGE("Failed to lchown, err = %{public}d", errno); + return false; + } + return true; +} + +bool BackupExtExtension::IfAllowToBackupRestore() +{ + if (extension_ == nullptr) { + HILOGE("Failed to handle backup, extension is nullptr"); + return false; + } + string usrConfig = extension_->GetUsrConfig(); + BJsonCachedEntity cachedEntity(usrConfig); + auto cache = cachedEntity.Structuralize(); + if (!cache.GetAllowToBackupRestore()) { + HILOGE("Application does not allow backup or restore"); + return false; + } + return true; +} + +ErrCode BackupExtExtension::User0OnBackup() +{ + HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + if (!IfAllowToBackupRestore()) { + return BError(BError::Codes::EXT_FORBID_BACKUP_RESTORE, "Application does not allow backup or restore") + .GetCode(); + } + AsyncTaskUser0Backup(); + return ERR_OK; +} + +void BackupExtExtension::AsyncTaskUser0Backup() +{ + HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + auto task = [obj {wptr(this)}]() { + auto ptr = obj.promote(); + BExcepUltils::BAssert(ptr, BError::Codes::EXT_BROKEN_FRAMEWORK, "Ext extension handle have been released"); + const string config = ptr->extension_->GetUsrConfig(); + try { + HILOGI("Do backup, start fwk timer begin."); + bool isFwkStart; + ptr->StartFwkTimer(isFwkStart); + if (!isFwkStart) { + HILOGE("Do backup, start fwk timer fail."); + return; + } + HILOGI("Do backup, start fwk timer end."); + BJsonCachedEntity cachedEntity(config); + auto cache = cachedEntity.Structuralize(); + auto ret = ptr->User0DoBackup(cache); + if (ret != ERR_OK) { + HILOGE("User0DoBackup, err = %{pubilc}d", ret); + ptr->AppIncrementalDone(BError::GetCodeByErrno(ret)); + } + } catch (const BError &e) { + HILOGE("extension: AsyncTaskBackup error, err code:%{public}d", e.GetCode()); + ptr->AppIncrementalDone(e.GetCode()); + } catch (const exception &e) { + HILOGE("Catched an unexpected low-level exception %{public}s", e.what()); + ptr->AppIncrementalDone(BError(BError::Codes::EXT_INVAL_ARG).GetCode()); + } catch (...) { + HILOGE("Failed to restore the ext bundle"); + ptr->AppIncrementalDone(BError(BError::Codes::EXT_INVAL_ARG).GetCode()); + } + }; + + threadPool_.AddTask([task]() { + try { + task(); + } catch (...) { + HILOGE("Failed to add task to thread pool"); + } + }); +} + +void BackupExtExtension::DoUser0Backup(const BJsonEntityExtensionConfig &usrConfig) +{ + HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + string path = string(BConstants::PATH_BUNDLE_BACKUP_HOME).append(BConstants::SA_BUNDLE_BACKUP_BACKUP); + if (mkdir(path.data(), S_IRWXU) && errno != EEXIST) { + throw BError(errno); + } + vector includes = usrConfig.GetIncludes(); + vector excludes = usrConfig.GetExcludes(); + auto task = [obj {wptr(this)}, includes, excludes]() { + auto ptr = obj.promote(); + BExcepUltils::BAssert(ptr, BError::Codes::EXT_BROKEN_FRAMEWORK, "Ext extension handle have been released"); + try { + auto [bigFile, smallFile] = BDir::GetBackupList(includes, excludes); + vector allFiles; + vector smallFiles; + vector bigFiles; + BDir::GetUser0FileStat(move(bigFile), move(smallFile), allFiles, smallFiles, bigFiles); + auto ret = ptr->DoIncrementalBackup(allFiles, smallFiles, bigFiles); + ptr->AppIncrementalDone(ret); + HILOGI("User0 backup app done %{public}d", ret); + } catch (const BError &e) { + ptr->AppIncrementalDone(e.GetCode()); + } catch (const exception &e) { + ptr->AppIncrementalDone(BError(BError::Codes::EXT_INVAL_ARG).GetCode()); + } catch (...) { + HILOGE("Failed to restore the ext bundle"); + ptr->AppIncrementalDone(BError(BError::Codes::EXT_INVAL_ARG).GetCode()); + } + }; + + threadPool_.AddTask([task]() { + try { + task(); + } catch (...) { + HILOGE("Failed to add task to thread pool"); + } + }); +} + +int BackupExtExtension::User0DoBackup(const BJsonEntityExtensionConfig &usrConfig) +{ + HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + if (extension_ == nullptr) { + HILOGE("Failed to do backup, extension is nullptr"); + return BError(BError::Codes::EXT_INVAL_ARG); + } + if (extension_->GetExtensionAction() != BConstants::ExtensionAction::BACKUP) { + return EPERM; + } + DoUser0Backup(usrConfig); + return ERR_OK; +} + +std::function BackupExtExtension::ReportOnProcessResultCallback( + wptr obj, BackupRestoreScenario scenario) +{ + return [obj, scenario](ErrCode errCode, const std::string processInfo) { + auto extPtr = obj.promote(); + if (extPtr == nullptr) { + HILOGE("Async call js onPreocess callback failed, exPtr is empty"); + return; + } + if (extPtr->onProcessTimeout_.load()) { + HILOGE("The result of invoking onProcess is timeout."); + extPtr->onProcessTimeout_.store(false); + return; + } + extPtr->CloseOnProcessTimeOutTimer(); + extPtr->isFirstCallOnProcess_.store(false); + extPtr->onProcessTimeout_.store(false); + if (extPtr->onProcessTimeoutCnt_.load() > 0) { + extPtr->onProcessTimeoutCnt_ = 0; + HILOGI("onProcess execute success, reset onProcessTimeoutCnt"); + } + if (processInfo.size() == 0) { + HILOGE("Current extension has no js method named onProcess."); + std::unique_lock lock(extPtr->onProcessLock_); + extPtr->isFirstCallOnProcess_.store(false); + extPtr->stopCallJsOnProcess_.store(true); + extPtr->execOnProcessCon_.notify_one(); + lock.unlock(); + return; + } + std::string processInfoJsonStr; + BJsonUtil::BuildOnProcessRetInfo(processInfoJsonStr, processInfo); + auto task = [obj, scenario, processInfoJsonStr]() { + auto reportExtPtr = obj.promote(); + if (reportExtPtr == nullptr) { + HILOGE("Report onProcess Result error, reportExtPtr is empty"); + return; + } + reportExtPtr->ReportAppProcessInfo(processInfoJsonStr, scenario); + }; + extPtr->reportOnProcessRetPool_.AddTask([task]() { task(); }); + }; +} +} // namespace OHOS::FileManagement::Backup diff --git a/frameworks/native/backup_ext/src/tar_file.cpp b/frameworks/native/backup_ext/src/tar_file.cpp index c4c8be795e80859ca77097c62aced9318edd4bdf..6f456bf84184a35f4396e467a211c7cb39144f32 100644 --- a/frameworks/native/backup_ext/src/tar_file.cpp +++ b/frameworks/native/backup_ext/src/tar_file.cpp @@ -51,7 +51,8 @@ TarFile &TarFile::GetInstance() return instance; } -bool TarFile::Packet(const vector &srcFiles, const string &tarFileName, const string &pkPath, TarMap &tarMap) +bool TarFile::Packet(const vector &srcFiles, const string &tarFileName, const string &pkPath, TarMap &tarMap, + std::function reportCb) { if (tarFileName.empty() || pkPath.empty()) { HILOGE("Invalid parameter"); @@ -70,9 +71,14 @@ bool TarFile::Packet(const vector &srcFiles, const string &tarFileName, size_t index = 0; for (const auto &filePath : srcFiles) { + int err = 0; rootPath_ = filePath; - if (!TraversalFile(rootPath_)) { - HILOGE("Failed to traversal file, file path is:%{public}s", GetAnonyPath(filePath).c_str()); + if (!TraversalFile(rootPath_, err)) { + HILOGE("ReportErr Failed to traversal file, file path is:%{public}s, err = %{public}d", + GetAnonyPath(filePath).c_str(), err); + if (err != EACCES) { + reportCb("", err); + } } index++; if (index >= WAIT_INDEX) { @@ -94,9 +100,10 @@ bool TarFile::Packet(const vector &srcFiles, const string &tarFileName, return true; } -bool TarFile::TraversalFile(string &filePath) +bool TarFile::TraversalFile(string &filePath, int &err) { if (access(filePath.c_str(), F_OK) != 0) { + err = errno; HILOGE("File path does not exists, err = %{public}d", errno); return false; } @@ -108,10 +115,11 @@ bool TarFile::TraversalFile(string &filePath) return false; } if (lstat(filePath.c_str(), &curFileStat) != 0) { + err = errno; HILOGE("Failed to lstat, err = %{public}d", errno); return false; } - if (!AddFile(filePath, curFileStat)) { + if (!AddFile(filePath, curFileStat, err)) { HILOGE("Failed to add file to tar package, file path is:%{public}s", GetAnonyPath(filePath).c_str()); return false; } @@ -196,23 +204,23 @@ bool TarFile::I2OcsConvert(const struct stat &st, TarHeader &hdr, string &fileNa if (S_ISREG(st.st_mode)) { hdr.typeFlag = REGTYPE; - off_t hdrSize = st.st_size; - if (sizeof(off_t) <= OFF_T_SIZE || st.st_size <= static_cast(MAX_FILE_SIZE)) { - size = I2Ocs(sizeof(hdr.size), hdrSize); - ret = memcpy_s(hdr.size, sizeof(hdr.size), size.c_str(), min(sizeof(hdr.size) - 1, size.length())); - if (ret != EOK) { - HILOGE("Failed to call memcpy_s, err = %{public}d", ret); - return false; - } - } else { - HILOGE("Invalid tar header size"); - return false; - } } else if (S_ISDIR(st.st_mode)) { hdr.typeFlag = DIRTYPE; } else { return true; } + off_t hdrSize = st.st_size; + if (sizeof(off_t) <= OFF_T_SIZE || st.st_size <= static_cast(MAX_FILE_SIZE)) { + size = I2Ocs(sizeof(hdr.size), hdrSize); + ret = memcpy_s(hdr.size, sizeof(hdr.size), size.c_str(), min(sizeof(hdr.size) - 1, size.length())); + if (ret != EOK) { + HILOGE("Failed to call memcpy_s, err = %{public}d", ret); + return false; + } + } else { + HILOGE("Invalid tar header size"); + return false; + } if (S_ISDIR(st.st_mode) && fileName.back() != '/') { fileName.append("/"); @@ -250,7 +258,7 @@ static bool ReadyHeader(TarHeader &hdr, const string &fileName) return true; } -bool TarFile::AddFile(string &fileName, const struct stat &st) +bool TarFile::AddFile(string &fileName, const struct stat &st, int &err) { HILOGD("tar file %{public}s", fileName.c_str()); currentFileName_ = fileName; @@ -286,7 +294,7 @@ bool TarFile::AddFile(string &fileName, const struct stat &st) return false; } // write src file content to tar file - if (!WriteFileContent(fileName, st.st_size)) { + if (!WriteFileContent(fileName, st.st_size, err)) { HILOGE("Failed to write file content"); return false; } @@ -294,11 +302,12 @@ bool TarFile::AddFile(string &fileName, const struct stat &st) return true; } -bool TarFile::WriteFileContent(const string &fileName, off_t size) +bool TarFile::WriteFileContent(const string &fileName, off_t size, int &err) { int fd = open(fileName.c_str(), O_RDONLY | O_CLOEXEC); if (fd < 0) { - HILOGE("Failed to open file %{public}s, err = %{public}d", fileName.data(), errno); + err = errno; + HILOGE("Failed to open file %{public}s, err = %{public}d", GetAnonyString(fileName).data(), errno); return false; } diff --git a/frameworks/native/backup_ext/src/untar_file.cpp b/frameworks/native/backup_ext/src/untar_file.cpp index 502bd58ad5e9d6c0769525feeb4c0f82f92867db..84dacb0e19461a5e030e9fff3b0fe806e0f88649 100644 --- a/frameworks/native/backup_ext/src/untar_file.cpp +++ b/frameworks/native/backup_ext/src/untar_file.cpp @@ -18,6 +18,7 @@ #include #include "b_anony/b_anony.h" +#include "b_filesystem/b_dir.h" #include "directory_ex.h" #include "filemgmt_libhilog.h" #include "securec.h" @@ -26,6 +27,7 @@ namespace OHOS::FileManagement::Backup { using namespace std; const int32_t PATH_MAX_LEN = 4096; const int32_t OCTAL = 8; +const int DEFAULT_ERR = -1; static bool IsEmptyBlock(const char *p) { @@ -77,23 +79,34 @@ static void RTrimNull(std::string &s) s.erase(iter.base(), s.end()); } -static int ReadLongName(FileStatInfo &info, FILE *tarFilePtr_, off_t tarFileSize_) +std::tuple UntarFile::ReadLongName(FileStatInfo &info) { size_t nameLen = static_cast(tarFileSize_); + int ret = 0; if (nameLen <= PATH_MAX_LEN) { string tempName(""); tempName.resize(nameLen); size_t read = fread(&(tempName[0]), sizeof(char), nameLen, tarFilePtr_); if (read < nameLen) { HILOGE("Failed to fread longName of %{private}s", info.fullPath.c_str()); - return -1; + ret = -1; } info.longName = tempName; } else { HILOGE("longName of %{private}s exceed PATH_MAX_LEN", info.fullPath.c_str()); + ret = -1; } - - return 0; + ErrFileInfo errFileInfo; + if (ret != 0) { + errFileInfo[info.fullPath].push_back(ret); + return {-1, errFileInfo}; + } + if (fseeko(tarFilePtr_, pos_ + tarFileBlockCnt_ * BLOCK_SIZE, SEEK_SET) != 0) { + HILOGE("Failed to fseeko of %{private}s, err = %{public}d", info.fullPath.c_str(), errno); + errFileInfo[info.fullPath].push_back(errno); + return {-1, errFileInfo}; + } + return {0, errFileInfo}; } UntarFile &UntarFile::GetInstance() @@ -102,45 +115,48 @@ UntarFile &UntarFile::GetInstance() return instance; } -int UntarFile::UnPacket(const string &tarFile, const string &rootPath) +std::tuple UntarFile::UnPacket( + const std::string &tarFile, const std::string &rootPath) { tarFilePtr_ = fopen(tarFile.c_str(), "rb"); if (tarFilePtr_ == nullptr) { HILOGE("Failed to open tar file %{public}s, err = %{public}d", tarFile.c_str(), errno); - return errno; + return {errno, {}, {}}; } - if (ParseTarFile(rootPath) != 0) { + auto [ret, fileInfos, errInfos] = ParseTarFile(rootPath); + if (ret != 0) { HILOGE("Failed to parse tar file"); } fclose(tarFilePtr_); tarFilePtr_ = nullptr; - return 0; + return {0, fileInfos, errInfos}; } -int UntarFile::IncrementalUnPacket(const string &tarFile, const string &rootPath, - const unordered_map &includes) +std::tuple UntarFile::IncrementalUnPacket( + const string &tarFile, const string &rootPath, const unordered_map &includes) { includes_ = includes; tarFilePtr_ = fopen(tarFile.c_str(), "rb"); if (tarFilePtr_ == nullptr) { HILOGE("Failed to open tar file %{public}s, err = %{public}d", tarFile.c_str(), errno); - return errno; + return {errno, {}, {}}; } - if (ParseIncrementalTarFile(rootPath) != 0) { + auto [ret, fileInfos, errFileInfos] = ParseIncrementalTarFile(rootPath); + if (ret != 0) { HILOGE("Failed to parse tar file"); } fclose(tarFilePtr_); tarFilePtr_ = nullptr; - return 0; + return {0, fileInfos, errFileInfos}; } -void UntarFile::HandleTarBuffer(const string &buff, const string &name, FileStatInfo &info) +off_t UntarFile::HandleTarBuffer(const string &buff, const string &name, FileStatInfo &info) { info.mode = static_cast(ParseOctalStr(&buff[0] + TMODE_BASE, TMODE_LEN)); info.uid = static_cast(ParseOctalStr(&buff[0] + TUID_BASE, TUID_LEN)); @@ -158,195 +174,281 @@ void UntarFile::HandleTarBuffer(const string &buff, const string &name, FileStat } if (realName.length() > 0 && realName[0] == '/') { info.fullPath = realName.substr(1, realName.length() - 1); - return; + return tarFileSize_; } info.fullPath = realName; + return tarFileSize_; } -int UntarFile::ParseTarFile(const string &rootPath) +int UntarFile::CheckAndFillTarSize() { - // re-parse tar header - rootPath_ = rootPath; - char buff[BLOCK_SIZE] = {0}; - FileStatInfo info {}; - // tarFileSize int ret = fseeko(tarFilePtr_, 0L, SEEK_END); if (ret != 0) { HILOGE("Failed to fseeko tarFileSize SEEK_SET, err = %{public}d", errno); + return ret; } tarFileSize_ = ftello(tarFilePtr_); // reback file to begin ret = fseeko(tarFilePtr_, 0L, SEEK_SET); if (ret != 0) { HILOGE("Failed to fseeko reback SEEK_SET, err = %{public}d", errno); + return ret; } + return ret; +} +int UntarFile::DealParseTarFileResult(const std::tuple &result, + const off_t fileSize, const std::string &fileName, EndFileInfo &fileInfos, ErrFileInfo &errInfos) +{ + auto [ret, isFilter, subErrInfos] = result; + if (ret != 0) { + HILOGE("Failed to parse incremental file by type flag"); + return ret; + } + if (!isFilter) { + fileInfos[fileName] = fileSize; + } + if (!errInfos.empty()) { + errInfos.merge(subErrInfos); + } + return 0; +} + +bool UntarFile::CheckIfTarBlockValid(char *buff, size_t buffLen, TarHeader *header, int &ret) +{ + // two empty continuous block indicate end of file + if (buff == nullptr || buffLen != BLOCK_SIZE || header == nullptr) { + return false; + } + if (IsEmptyBlock(buff) && header->typeFlag != GNUTYPE_LONGNAME) { + char tailBuff[BLOCK_SIZE] = {0}; + size_t tailRead = fread(tailBuff, 1, BLOCK_SIZE, tarFilePtr_); + if (tailRead == BLOCK_SIZE && IsEmptyBlock(tailBuff)) { + HILOGE("Parsing tar file completed, tailBuff is empty."); + ret = 0; + return false; + } + } + // check header + if (!IsValidTarBlock(*header)) { + // when split unpack, ftell size is over than file really size [0,READ_BUFF_SIZE] + if (ftello(tarFilePtr_) > (tarFileSize_ + READ_BUFF_SIZE) || !IsEmptyBlock(buff)) { + HILOGE("Invalid tar file format"); + ret = ERR_FORMAT; + } + HILOGE("invalid tar block header"); + return false; + } + return true; +} + +std::tuple UntarFile::ParseTarFile(const string &rootPath) +{ + // re-parse tar header + rootPath_ = rootPath; + char buff[BLOCK_SIZE] = {0}; + FileStatInfo info {}; + int ret = 0; + if ((ret = CheckAndFillTarSize()) != 0) { + return {ret, {}, {}}; + } + EndFileInfo fileInfos; + ErrFileInfo errInfos; while (1) { readCnt_ = fread(buff, 1, BLOCK_SIZE, tarFilePtr_); if (readCnt_ < BLOCK_SIZE) { HILOGE("Parsing tar file completed, read data count is less then block size."); - return 0; + return {0, fileInfos, errInfos}; } TarHeader *header = reinterpret_cast(buff); - // two empty continuous block indicate end of file - if (IsEmptyBlock(buff) && header->typeFlag != GNUTYPE_LONGNAME) { - char tailBuff[BLOCK_SIZE] = {0}; - size_t tailRead = fread(tailBuff, 1, BLOCK_SIZE, tarFilePtr_); - if (tailRead == BLOCK_SIZE && IsEmptyBlock(tailBuff)) { - HILOGE("Parsing tar file completed, tailBuff is empty."); - return 0; - } + bool isValid = CheckIfTarBlockValid(buff, sizeof(buff), header, ret); + if (!isValid) { + return {ret, fileInfos, errInfos}; } - // check header - if (!IsValidTarBlock(*header)) { - // when split unpack, ftell size is over than file really size [0,READ_BUFF_SIZE] - if (ftello(tarFilePtr_) > (tarFileSize_ + READ_BUFF_SIZE) || !IsEmptyBlock(buff)) { - HILOGE("Invalid tar file format"); - ret = ERR_FORMAT; - } - HILOGE("invalid tar block header"); - return ret; + off_t fileSize = HandleTarBuffer(string(buff, BLOCK_SIZE), header->name, info); + auto result = ParseFileByTypeFlag(header->typeFlag, info); + if ((ret = DealParseTarFileResult(result, fileSize, info.fullPath, fileInfos, errInfos)) != 0) { + return {ret, fileInfos, errInfos}; } - HandleTarBuffer(string(buff, BLOCK_SIZE), header->name, info); - ParseFileByTypeFlag(header->typeFlag, info); } - return ret; + return {ret, fileInfos, errInfos}; } -int UntarFile::ParseIncrementalTarFile(const string &rootPath) +int UntarFile::DealIncreParseTarFileResult(const std::tuple &result, + const off_t fileSize, const std::string &fileName, EndFileInfo &fileInfos, ErrFileInfo &errInfos) { - // re-parse tar header - rootPath_ = rootPath; - char buff[BLOCK_SIZE] = {0}; - FileStatInfo info {}; - - // tarFileSize - int ret = fseeko(tarFilePtr_, 0L, SEEK_END); + auto [ret, isFilter, subErrInfo] = result; if (ret != 0) { - HILOGE("Failed to fseeko tarFile SEEK_END, err = %{public}d", errno); + HILOGE("Failed to parse incremental file by type flag"); return ret; } - tarFileSize_ = ftello(tarFilePtr_); - // reback file to begin - if ((ret = fseeko(tarFilePtr_, 0L, SEEK_SET)) != 0) { - HILOGE("Failed to fseeko tarFile SEEK_SET, err = %{public}d", errno); - return ret; + if (!isFilter) { + fileInfos[fileName] = fileSize; + } + if (!subErrInfo.empty()) { + errInfos.merge(subErrInfo); } + return 0; +} +std::tuple UntarFile::ParseIncrementalTarFile(const string &rootPath) +{ + // re-parse tar header + rootPath_ = rootPath; + char buff[BLOCK_SIZE] = {0}; + FileStatInfo info {}; + int ret = 0; + if ((ret = CheckAndFillTarSize()) != 0) { + return {ret, {}, {}}; + } + EndFileInfo fileInfos; + ErrFileInfo errFileInfo; do { readCnt_ = fread(buff, 1, BLOCK_SIZE, tarFilePtr_); if (readCnt_ < BLOCK_SIZE) { HILOGE("Parsing tar file completed, read data count is less then block size."); - return 0; + return {0, fileInfos, errFileInfo}; } TarHeader *header = reinterpret_cast(buff); - // two empty continuous block indicate end of file - if (IsEmptyBlock(buff) && header->typeFlag != GNUTYPE_LONGNAME) { - char tailBuff[BLOCK_SIZE] = {0}; - size_t tailRead = fread(tailBuff, 1, BLOCK_SIZE, tarFilePtr_); - if (tailRead == BLOCK_SIZE && IsEmptyBlock(tailBuff)) { - HILOGE("Parsing tar file completed, tailBuff is empty."); - return 0; - } + bool isValid = CheckIfTarBlockValid(buff, sizeof(buff), header, ret); + if (!isValid) { + return {ret, fileInfos, errFileInfo}; } - // check header - if (!IsValidTarBlock(*header)) { - // when split unpack, ftell size is over than file really size [0,READ_BUFF_SIZE] - if (ftello(tarFilePtr_) > (tarFileSize_ + READ_BUFF_SIZE) || !IsEmptyBlock(buff)) { - HILOGE("Invalid tar file format"); - ret = ERR_FORMAT; - } - return ret; - } - HandleTarBuffer(string(buff, BLOCK_SIZE), header->name, info); - if ((ret = ParseIncrementalFileByTypeFlag(header->typeFlag, info)) != 0) { - HILOGE("Failed to parse incremental file by type flag"); - return ret; + off_t fileSize = HandleTarBuffer(string(buff, BLOCK_SIZE), header->name, info); + auto result = ParseIncrementalFileByTypeFlag(header->typeFlag, info); + ret = DealIncreParseTarFileResult(result, fileSize, info.fullPath, fileInfos, errFileInfo); + if (ret != 0) { + return {ret, fileInfos, errFileInfo}; } } while (readCnt_ >= BLOCK_SIZE); - return ret; + return {ret, fileInfos, errFileInfo}; } -void UntarFile::ParseFileByTypeFlag(char typeFlag, FileStatInfo &info) +tuple UntarFile::ParseFileByTypeFlag(char typeFlag, FileStatInfo &info) { HILOGD("untar file: %{public}s, rootPath: %{public}s", GetAnonyPath(info.fullPath).c_str(), rootPath_.c_str()); + bool isFilter = true; + ErrFileInfo errFileInfo; switch (typeFlag) { case REGTYPE: case AREGTYPE: info.fullPath = GenRealPath(rootPath_, info.fullPath); - ParseRegularFile(info, typeFlag); + if (BDir::CheckFilePathInvalid(info.fullPath)) { + HILOGE("Check file path : %{public}s err, path is forbidden", GetAnonyPath(info.fullPath).c_str()); + return {DEFAULT_ERR, true, {{info.fullPath, {DEFAULT_ERR}}}}; + } + errFileInfo = ParseRegularFile(info); + isFilter = false; break; case SYMTYPE: break; case DIRTYPE: info.fullPath = GenRealPath(rootPath_, info.fullPath); - CreateDir(info.fullPath, info.mode); + if (BDir::CheckFilePathInvalid(info.fullPath)) { + HILOGE("Check file path : %{public}s err, path is forbidden", GetAnonyPath(info.fullPath).c_str()); + return {DEFAULT_ERR, true, {{info.fullPath, {DEFAULT_ERR}}}}; + } + errFileInfo = CreateDir(info.fullPath, info.mode); + isFilter = false; break; case GNUTYPE_LONGNAME: { - ReadLongName(info, tarFilePtr_, tarFileSize_); - fseeko(tarFilePtr_, pos_ + tarFileBlockCnt_ * BLOCK_SIZE, SEEK_SET); + auto result = ReadLongName(info); + if (BDir::CheckFilePathInvalid(info.fullPath) || BDir::CheckFilePathInvalid(info.longName)) { + HILOGE("Check file path : %{public}s or long name : %{public}s err, path is forbidden", + GetAnonyPath(info.fullPath).c_str(), GetAnonyPath(info.longName).c_str()); + return {DEFAULT_ERR, true, {{info.fullPath, {DEFAULT_ERR}}}}; + } + errFileInfo = std::get(result); + return {std::get(result), isFilter, errFileInfo}; break; } default: { - fseeko(tarFilePtr_, tarFileBlockCnt_ * BLOCK_SIZE, SEEK_CUR); + if (fseeko(tarFilePtr_, tarFileBlockCnt_ * BLOCK_SIZE, SEEK_CUR) != 0) { + HILOGE("Failed to fseeko of %{private}s, err = %{public}d", info.fullPath.c_str(), errno); + return {-1, true, errFileInfo}; + } break; } } + return {0, isFilter, errFileInfo}; +} + +bool UntarFile::DealFileTag(ErrFileInfo &errFileInfo, + FileStatInfo &info, bool &isFilter, const std::string &tmpFullPath) +{ + if (!includes_.empty() && includes_.find(tmpFullPath) == includes_.end()) { // not in includes + if (fseeko(tarFilePtr_, pos_ + tarFileBlockCnt_ * BLOCK_SIZE, SEEK_SET) != 0) { + HILOGE("Failed to fseeko of %{private}s, err = %{public}d", info.fullPath.c_str(), errno); + errFileInfo[info.fullPath].push_back(DEFAULT_ERR); + } + return false; + } + info.fullPath = GenRealPath(rootPath_, info.fullPath); + if (BDir::CheckFilePathInvalid(info.fullPath)) { + HILOGE("Check file path : %{public}s err, path is forbidden", GetAnonyPath(info.fullPath).c_str()); + errFileInfo[info.fullPath].push_back(DEFAULT_ERR); + return false; + } + errFileInfo = ParseRegularFile(info); + isFilter = false; + return true; } -int UntarFile::ParseIncrementalFileByTypeFlag(char typeFlag, FileStatInfo &info) + +std::tuple UntarFile::ParseIncrementalFileByTypeFlag(char typeFlag, FileStatInfo &info) { HILOGD("untar file: %{public}s, rootPath: %{public}s", GetAnonyPath(info.fullPath).c_str(), rootPath_.c_str()); string tmpFullPath = info.fullPath; + bool isFilter = true; + ErrFileInfo errFileInfo; RTrimNull(tmpFullPath); switch (typeFlag) { case REGTYPE: - case AREGTYPE: - if (!includes_.empty() && includes_.find(tmpFullPath) == includes_.end()) { // not in includes - if (fseeko(tarFilePtr_, pos_ + tarFileBlockCnt_ * BLOCK_SIZE, SEEK_SET) != 0) { - HILOGE("Failed to fseeko of %{private}s, err = %{public}d", info.fullPath.c_str(), errno); - return -1; - } - break; + case AREGTYPE: { + if (!DealFileTag(errFileInfo, info, isFilter, tmpFullPath)) { + return {DEFAULT_ERR, true, errFileInfo}; } - info.fullPath = GenRealPath(rootPath_, info.fullPath); - ParseRegularFile(info, typeFlag); break; + } case SYMTYPE: break; case DIRTYPE: info.fullPath = GenRealPath(rootPath_, info.fullPath); - CreateDir(info.fullPath, info.mode); + if (BDir::CheckFilePathInvalid(info.fullPath)) { + HILOGE("Check file path : %{public}s err, path is forbidden", GetAnonyPath(info.fullPath).c_str()); + return {DEFAULT_ERR, true, {{info.fullPath, {DEFAULT_ERR}}}}; + } + errFileInfo = CreateDir(info.fullPath, info.mode); + isFilter = false; break; case GNUTYPE_LONGNAME: { - int ret = ReadLongName(info, tarFilePtr_, tarFileSize_); - if (ret != 0) { - return ret; - } - if (fseeko(tarFilePtr_, pos_ + tarFileBlockCnt_ * BLOCK_SIZE, SEEK_SET) != 0) { - HILOGE("Failed to fseeko of %{private}s, err = %{public}d", info.fullPath.c_str(), errno); - return -1; + auto result = ReadLongName(info); + if (BDir::CheckFilePathInvalid(info.fullPath)) { + HILOGE("Check file path : %{public}s err, path is forbidden", GetAnonyPath(info.fullPath).c_str()); + return {DEFAULT_ERR, true, {{info.fullPath, {DEFAULT_ERR}}}}; } + return {std::get(result), isFilter, std::get(result)}; break; } default: { if (fseeko(tarFilePtr_, tarFileBlockCnt_ * BLOCK_SIZE, SEEK_CUR) != 0) { HILOGE("Failed to fseeko of %{private}s, err = %{public}d", info.fullPath.c_str(), errno); - return -1; + return {DEFAULT_ERR, true, {{info.fullPath, {DEFAULT_ERR}}}}; } break; } } - return 0; + return {0, isFilter, errFileInfo}; } -void UntarFile::ParseRegularFile(FileStatInfo &info, char typeFlag) +ErrFileInfo UntarFile::ParseRegularFile(FileStatInfo &info) { - FILE *destFile = CreateFile(info.fullPath, info.mode, typeFlag); + ErrFileInfo errFileInfo; + FILE *destFile = CreateFile(info.fullPath); if (destFile != nullptr) { string destStr(""); destStr.resize(READ_BUFF_SIZE); @@ -361,27 +463,32 @@ void UntarFile::ParseRegularFile(FileStatInfo &info, char typeFlag) remainSize -= readBuffSize; } fclose(destFile); - chmod(info.fullPath.data(), info.mode); + if (chmod(info.fullPath.data(), info.mode) != 0) { + HILOGE("Failed to chmod of %{public}s, err = %{public}d", GetAnonyPath(info.fullPath).c_str(), errno); + errFileInfo[info.fullPath].push_back(errno); + } struct utimbuf times; struct stat attr; if (stat(info.fullPath.c_str(), &attr) != 0) { - HILOGE("Failed to get stat of %{public}s, err = %{public}d", - GetAnonyPath(info.fullPath).c_str(), errno); + errFileInfo[info.fullPath].push_back(errno); + HILOGE("Failed to get stat of %{public}s, err = %{public}d", GetAnonyPath(info.fullPath).c_str(), errno); times.actime = info.mtime; } else { times.actime = attr.st_atime; } times.modtime = info.mtime; if (info.mtime != 0 && utime(info.fullPath.c_str(), ×) != 0) { - HILOGE("Failed to set mtime of %{public}s, err = %{public}d", - GetAnonyPath(info.fullPath).c_str(), errno); + errFileInfo[info.fullPath].push_back(errno); + HILOGE("Failed to set mtime of %{public}s, err = %{public}d", GetAnonyPath(info.fullPath).c_str(), errno); } // anyway, go to correct fseeko(tarFilePtr_, pos_ + tarFileBlockCnt_ * BLOCK_SIZE, SEEK_SET); } else { HILOGE("Failed to create file %{public}s, err = %{public}d", GetAnonyPath(info.fullPath).c_str(), errno); + errFileInfo[info.fullPath].push_back(errno); fseeko(tarFilePtr_, tarFileBlockCnt_ * BLOCK_SIZE, SEEK_CUR); } + return errFileInfo; } bool UntarFile::VerifyChecksum(TarHeader &header) @@ -409,7 +516,7 @@ bool UntarFile::IsValidTarBlock(TarHeader &header) if (strncmp(header.magic, TMAGIC.c_str(), TMAGIC_LEN - 1) == 0 && VerifyChecksum(header)) { return true; } - HILOGW("Invalid tar block"); + HILOGE("Invalid tar block"); return false; } @@ -430,24 +537,27 @@ string UntarFile::GenRealPath(const string &rootPath, const string &realName) return realPath; } -void UntarFile::CreateDir(string &path, mode_t mode) +ErrFileInfo UntarFile::CreateDir(string &path, mode_t mode) { + ErrFileInfo errFileInfo; if (path.empty()) { - return; + return errFileInfo; } size_t len = path.length(); if (path[len - 1] == '/') { path[len - 1] = '\0'; } if (access(path.c_str(), F_OK) != 0) { - HILOGW("directory does not exist, path:%{public}s, err = %{public}d", path.c_str(), errno); + HILOGE("directory does not exist, path:%{public}s, err = %{public}d", path.c_str(), errno); if (!ForceCreateDirectoryWithMode(path, mode)) { HILOGE("Failed to force create directory %{public}s, err = %{public}d", path.c_str(), errno); + errFileInfo[path].push_back(errno); } } + return errFileInfo; } -FILE *UntarFile::CreateFile(string &filePath, mode_t mode, char fileType) +FILE *UntarFile::CreateFile(string &filePath) { FILE *f = fopen(filePath.c_str(), "wb+"); if (f != nullptr) { @@ -455,7 +565,7 @@ FILE *UntarFile::CreateFile(string &filePath, mode_t mode, char fileType) } uint32_t len = filePath.length(); - HILOGW("Failed to open file %{public}d, %{public}s, err = %{public}d", len, + HILOGE("Failed to open file %{public}d, %{public}s, err = %{public}d", len, GetAnonyPath(filePath).c_str(), errno); size_t pos = filePath.rfind('/'); if (pos == string::npos) { @@ -466,7 +576,7 @@ FILE *UntarFile::CreateFile(string &filePath, mode_t mode, char fileType) if (ForceCreateDirectory(path)) { f = fopen(filePath.c_str(), "wb+"); if (f == nullptr) { - HILOGE("Failed to create file %{public}s, err = %{public}d", GetAnonyPath(filePath).c_str(), errno); + HILOGE("Failed to open file %{public}s, err = %{public}d", GetAnonyPath(filePath).c_str(), errno); } } diff --git a/frameworks/native/backup_kit_inner/include/service_reverse.h b/frameworks/native/backup_kit_inner/include/service_reverse.h index 178bac3c98f7ec62ea4522414b87db51a16def82..3ecb58eaba5dd9964310ca15013e99b5ab85b291 100644 --- a/frameworks/native/backup_kit_inner/include/service_reverse.h +++ b/frameworks/native/backup_kit_inner/include/service_reverse.h @@ -30,6 +30,7 @@ public: void BackupOnResultReport(std::string result, std::string bundleName) override; void BackupOnBundleFinished(int32_t errCode, std::string bundleName) override; void BackupOnAllBundlesFinished(int32_t errCode) override; + void BackupOnProcessInfo(std::string bundleName, std::string processInfo) override; void RestoreOnBundleStarted(int32_t errCode, std::string bundleName) override; void RestoreOnBundleFinished(int32_t errCode, std::string bundleName) override; @@ -37,6 +38,7 @@ public: void RestoreOnFileReady(std::string bundleName, std::string fileName, int fd, int32_t errCode) override; void RestoreOnResultReport(std::string result, std::string bundleName, ErrCode errCode = 0) override; + void RestoreOnProcessInfo(std::string bundleName, std::string processInfo) override; void IncrementalBackupOnFileReady(std::string bundleName, std::string fileName, int fd, int manifestFd, int32_t errCode) override; @@ -44,6 +46,7 @@ public: void IncrementalBackupOnResultReport(std::string result, std::string bundleName) override; void IncrementalBackupOnBundleFinished(int32_t errCode, std::string bundleName) override; void IncrementalBackupOnAllBundlesFinished(int32_t errCode) override; + void IncrementalBackupOnProcessInfo(std::string bundleName, std::string processInfo) override; void IncrementalRestoreOnBundleStarted(int32_t errCode, std::string bundleName) override; void IncrementalRestoreOnBundleFinished(int32_t errCode, std::string bundleName) override; @@ -52,6 +55,7 @@ public: int32_t errCode) override; void IncrementalRestoreOnResultReport(std::string result, std::string bundleName, ErrCode errCode = 0) override; + void IncrementalRestoreOnProcessInfo(std::string bundleName, std::string processInfo) override; public: ServiceReverse() = delete; diff --git a/frameworks/native/backup_kit_inner/include/service_reverse_stub.h b/frameworks/native/backup_kit_inner/include/service_reverse_stub.h index 879eccf1bca385f72eeae8a53ca1174671b5ab9b..0384c01307b7dc005646472fa9105d499dab1525 100644 --- a/frameworks/native/backup_kit_inner/include/service_reverse_stub.h +++ b/frameworks/native/backup_kit_inner/include/service_reverse_stub.h @@ -39,24 +39,29 @@ private: int32_t CmdBackupOnResultReport(MessageParcel &data, MessageParcel &reply); int32_t CmdBackupOnBundleFinished(MessageParcel &data, MessageParcel &reply); int32_t CmdBackupOnAllBundlesFinished(MessageParcel &data, MessageParcel &reply); + int32_t CmdBackupOnProcessInfo(MessageParcel &data, MessageParcel &reply); int32_t CmdRestoreOnBundleStarted(MessageParcel &data, MessageParcel &reply); int32_t CmdRestoreOnBundleFinished(MessageParcel &data, MessageParcel &reply); int32_t CmdRestoreOnAllBundlesFinished(MessageParcel &data, MessageParcel &reply); int32_t CmdRestoreOnFileReady(MessageParcel &data, MessageParcel &reply); int32_t CmdRestoreOnResultReport(MessageParcel &data, MessageParcel &reply); + int32_t CmdRestoreOnProcessInfo(MessageParcel &data, MessageParcel &reply); int32_t CmdIncrementalBackupOnFileReady(MessageParcel &data, MessageParcel &reply); int32_t CmdIncrementalBackupOnBundleStarted(MessageParcel &data, MessageParcel &reply); int32_t CmdIncrementalBackupOnResultReport(MessageParcel &data, MessageParcel &reply); int32_t CmdIncrementalBackupOnBundleFinished(MessageParcel &data, MessageParcel &reply); int32_t CmdIncrementalBackupOnAllBundlesFinished(MessageParcel &data, MessageParcel &reply); + int32_t CmdIncrementalBackupOnProcessInfo(MessageParcel &data, MessageParcel &reply); int32_t CmdIncrementalRestoreOnBundleStarted(MessageParcel &data, MessageParcel &reply); int32_t CmdIncrementalRestoreOnBundleFinished(MessageParcel &data, MessageParcel &reply); int32_t CmdIncrementalRestoreOnAllBundlesFinished(MessageParcel &data, MessageParcel &reply); int32_t CmdIncrementalRestoreOnFileReady(MessageParcel &data, MessageParcel &reply); int32_t CmdIncrementalRestoreOnResultReport(MessageParcel &data, MessageParcel &reply); + int32_t CmdIncrementalRestoreOnProcessInfo(MessageParcel &data, MessageParcel &reply); + void ServiceReverseStubSupplement(); }; } // namespace OHOS::FileManagement::Backup diff --git a/frameworks/native/backup_kit_inner/src/b_incremental_backup_session.cpp b/frameworks/native/backup_kit_inner/src/b_incremental_backup_session.cpp index f747d28c7662c0b22edf870320e7253fee023ee2..0d69e9ba8def6d05197e461e7c378f78d7a40858 100644 --- a/frameworks/native/backup_kit_inner/src/b_incremental_backup_session.cpp +++ b/frameworks/native/backup_kit_inner/src/b_incremental_backup_session.cpp @@ -16,6 +16,7 @@ #include "b_incremental_backup_session.h" #include "b_error/b_error.h" +#include "b_radar/b_radar.h" #include "filemgmt_libhilog.h" #include "service_proxy.h" #include "service_reverse.h" @@ -29,7 +30,7 @@ BIncrementalBackupSession::~BIncrementalBackupSession() HILOGI("Death Recipient is nullptr"); return; } - auto proxy = ServiceProxy::GetInstance(); + auto proxy = ServiceProxy::GetServiceProxyPointer(); if (proxy == nullptr) { return; } @@ -53,8 +54,11 @@ unique_ptr BIncrementalBackupSession::Init(Callbacks } int32_t res = proxy->InitIncrementalBackupSession(sptr(new ServiceReverse(callbacks))); - if (res != 0) { + if (res != ERR_OK) { HILOGE("Failed to Backup because of %{public}d", res); + AppRadar::Info info("", "", ""); + AppRadar::GetInstance().RecordBackupFuncRes(info, "BIncrementalBackupSession::Init", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_CREATE_BACKUP_SESSION_FAIL, res); return nullptr; } @@ -93,7 +97,17 @@ ErrCode BIncrementalBackupSession::AppendBundles(vector bundle return BError(BError::Codes::SDK_BROKEN_IPC, "Failed to get backup service").GetCode(); } - return proxy->AppendBundlesIncrementalBackupSession(bundlesToBackup); + ErrCode res = proxy->AppendBundlesIncrementalBackupSession(bundlesToBackup); + if (res != ERR_OK) { + std::string ss; + for (const auto &bundle : bundlesToBackup) { + ss += bundle.bundleName + ", "; + } + AppRadar::Info info(ss.c_str(), "", ""); + AppRadar::GetInstance().RecordBackupFuncRes(info, "BIncrementalBackupSession::AppendBundles", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_APPEND_BUNDLES_FAIL, res); + } + return res; } ErrCode BIncrementalBackupSession::AppendBundles(vector bundlesToBackup, @@ -104,7 +118,17 @@ ErrCode BIncrementalBackupSession::AppendBundles(vector bundle return BError(BError::Codes::SDK_BROKEN_IPC, "Failed to get backup service").GetCode(); } - return proxy->AppendBundlesIncrementalBackupSession(bundlesToBackup, infos); + int32_t res = proxy->AppendBundlesIncrementalBackupSession(bundlesToBackup, infos); + if (res != ERR_OK) { + std::string ss; + for (const auto &bundle : bundlesToBackup) { + ss += bundle.bundleName + ", "; + } + AppRadar::Info info(ss.c_str(), "", "AppendBundles with infos"); + AppRadar::GetInstance().RecordBackupFuncRes(info, "BIncrementalBackupSession::AppendBundles", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_APPEND_BUNDLES_FAIL, res); + } + return res; } ErrCode BIncrementalBackupSession::Release() diff --git a/frameworks/native/backup_kit_inner/src/b_incremental_restore_session.cpp b/frameworks/native/backup_kit_inner/src/b_incremental_restore_session.cpp index 000241ad00fa33ddcf07acdfb1e09ba657c34a52..0999dac1d385f0ed6add68593f2faf7d8274a6a7 100644 --- a/frameworks/native/backup_kit_inner/src/b_incremental_restore_session.cpp +++ b/frameworks/native/backup_kit_inner/src/b_incremental_restore_session.cpp @@ -16,6 +16,7 @@ #include "b_incremental_restore_session.h" #include "b_error/b_error.h" +#include "b_radar/b_radar.h" #include "filemgmt_libhilog.h" #include "service_proxy.h" #include "service_reverse.h" @@ -29,7 +30,7 @@ BIncrementalRestoreSession::~BIncrementalRestoreSession() HILOGI("Death Recipient is nullptr"); return; } - auto proxy = ServiceProxy::GetInstance(); + auto proxy = ServiceProxy::GetServiceProxyPointer(); if (proxy == nullptr) { return; } @@ -52,8 +53,11 @@ unique_ptr BIncrementalRestoreSession::Init(Callback return nullptr; } int32_t res = proxy->InitRestoreSession(sptr(new ServiceReverse(callbacks))); - if (res != 0) { + if (res != ERR_OK) { HILOGE("Failed to Restore because of %{public}d", res); + AppRadar::Info info ("", "", "create restore session failed"); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BIncrementalRestoreSession::Init", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_CREATE_RESTORE_SESSION_FAIL, res); return nullptr; } @@ -99,7 +103,17 @@ ErrCode BIncrementalRestoreSession::AppendBundles(UniqueFd remoteCap, vectorAppendBundlesRestoreSession(move(remoteCap), bundlesToRestore); + ErrCode res = proxy->AppendBundlesRestoreSession(move(remoteCap), bundlesToRestore); + if (res != ERR_OK) { + std::string ss; + for (const auto &bundle : bundlesToRestore) { + ss += bundle + ", "; + } + AppRadar::Info info(ss.c_str(), "", ""); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BIncrementalRestoreSession::AppendBundles", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_APPEND_BUNDLES_FAIL, res); + } + return res; } ErrCode BIncrementalRestoreSession::AppendBundles(UniqueFd remoteCap, vector bundlesToRestore, @@ -109,8 +123,17 @@ ErrCode BIncrementalRestoreSession::AppendBundles(UniqueFd remoteCap, vectorAppendBundlesRestoreSession(move(remoteCap), bundlesToRestore, detailInfos); + ErrCode res = proxy->AppendBundlesRestoreSession(move(remoteCap), bundlesToRestore, detailInfos); + if (res != ERR_OK) { + std::string ss; + for (const auto &bundle : bundlesToRestore) { + ss += bundle + ", "; + } + AppRadar::Info info(ss.c_str(), "", "AppendBundles with infos"); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BIncrementalRestoreSession::AppendBundles", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_APPEND_BUNDLES_FAIL, res); + } + return res; } ErrCode BIncrementalRestoreSession::Release() diff --git a/frameworks/native/backup_kit_inner/src/b_incremental_session_restore_async.cpp b/frameworks/native/backup_kit_inner/src/b_incremental_session_restore_async.cpp index 84f75d66efc567dbca2fd01b5de3c13ab20f57d3..cb79d416cd0e807b4111af0f65cd331bfadb3ce0 100644 --- a/frameworks/native/backup_kit_inner/src/b_incremental_session_restore_async.cpp +++ b/frameworks/native/backup_kit_inner/src/b_incremental_session_restore_async.cpp @@ -16,6 +16,7 @@ #include "b_incremental_session_restore_async.h" #include "b_error/b_error.h" +#include "b_radar/b_radar.h" #include "b_resources/b_constants.h" #include "filemgmt_libhilog.h" #include "service_proxy.h" @@ -30,7 +31,7 @@ BIncrementalSessionRestoreAsync::~BIncrementalSessionRestoreAsync() HILOGE("Death Recipient is nullptr"); return; } - auto proxy = ServiceProxy::GetInstance(); + auto proxy = ServiceProxy::GetServiceProxyPointer(); if (proxy == nullptr) { return; } @@ -60,8 +61,11 @@ shared_ptr BIncrementalSessionRestoreAsync::Ini .onResultReport = callbacks.onResultReport, .onBackupServiceDied = callbacks.onBackupServiceDied}; int32_t res = proxy->InitRestoreSession(sptr(new ServiceReverse(callbacksTmp))); - if (res != 0) { + if (res != ERR_OK) { HILOGE("Failed to Restore because of %{public}d", res); + AppRadar::Info info ("", "", "create restore session failed"); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BIncrementalSessionRestoreAsync::Init", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_CREATE_RESTORE_SESSION_FAIL, res); return nullptr; } @@ -102,8 +106,18 @@ ErrCode BIncrementalSessionRestoreAsync::AppendBundles(UniqueFd remoteCap, if (proxy == nullptr) { return BError(BError::Codes::SDK_BROKEN_IPC, "Failed to get backup service").GetCode(); } - return proxy->AppendBundlesRestoreSession(move(remoteCap), bundlesToRestore, detailInfos, restoreType, + ErrCode res = proxy->AppendBundlesRestoreSession(move(remoteCap), bundlesToRestore, detailInfos, restoreType, userId); + if (res != ERR_OK) { + std::string ss; + for (const auto &bundle : bundlesToRestore) { + ss += bundle + ", "; + } + AppRadar::Info info(ss.c_str(), "", "AppendBundles with infos"); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BIncrementalSessionRestoreAsync::AppendBundles", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_APPEND_BUNDLES_FAIL, res); + } + return res; } ErrCode BIncrementalSessionRestoreAsync::AppendBundles(UniqueFd remoteCap, @@ -115,8 +129,17 @@ ErrCode BIncrementalSessionRestoreAsync::AppendBundles(UniqueFd remoteCap, if (proxy == nullptr) { return BError(BError::Codes::SDK_BROKEN_IPC, "Failed to get backup service").GetCode(); } - - return proxy->AppendBundlesRestoreSession(move(remoteCap), bundlesToRestore, restoreType, userId); + ErrCode res = proxy->AppendBundlesRestoreSession(move(remoteCap), bundlesToRestore, restoreType, userId); + if (res != ERR_OK) { + std::string ss; + for (const auto &bundle : bundlesToRestore) { + ss += bundle + ", "; + } + AppRadar::Info info(ss.c_str(), "", ""); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BIncrementalSessionRestoreAsync::AppendBundles", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_APPEND_BUNDLES_FAIL, res); + } + return res; } ErrCode BIncrementalSessionRestoreAsync::Release() diff --git a/frameworks/native/backup_kit_inner/src/b_session_backup.cpp b/frameworks/native/backup_kit_inner/src/b_session_backup.cpp index 04176686bd8da61518fe2d153cc41f938d62503d..5086262692d1999cb8711bcab191ab77926862f6 100644 --- a/frameworks/native/backup_kit_inner/src/b_session_backup.cpp +++ b/frameworks/native/backup_kit_inner/src/b_session_backup.cpp @@ -16,6 +16,7 @@ #include "b_session_backup.h" #include "b_error/b_error.h" +#include "b_radar/b_radar.h" #include "filemgmt_libhilog.h" #include "service_proxy.h" #include "service_reverse.h" @@ -29,7 +30,7 @@ BSessionBackup::~BSessionBackup() HILOGI("Death Recipient is nullptr"); return; } - auto proxy = ServiceProxy::GetInstance(); + auto proxy = ServiceProxy::GetServiceProxyPointer(); if (proxy == nullptr) { return; } @@ -53,8 +54,11 @@ unique_ptr BSessionBackup::Init(Callbacks callbacks) } int32_t res = proxy->InitBackupSession(sptr(new ServiceReverse(callbacks))); - if (res != 0) { + if (res != ERR_OK) { HILOGE("Failed to Backup because of %{public}d", res); + AppRadar::Info info("", "", ""); + AppRadar::GetInstance().RecordBackupFuncRes(info, "BSessionBackup::Init", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_CREATE_BACKUP_SESSION_FAIL, res); return nullptr; } @@ -103,7 +107,17 @@ ErrCode BSessionBackup::AppendBundles(vector bundlesToBackup) return BError(BError::Codes::SDK_BROKEN_IPC, "Failed to get backup service").GetCode(); } - return proxy->AppendBundlesBackupSession(bundlesToBackup); + int32_t res = proxy->AppendBundlesBackupSession(bundlesToBackup); + if (res != ERR_OK) { + std::string ss; + for (const auto &bundleName:bundlesToBackup) { + ss += bundleName + ", "; + } + AppRadar::Info info(ss.c_str(), "", ""); + AppRadar::GetInstance().RecordBackupFuncRes(info, "BSessionBackup::AppendBundles", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_APPEND_BUNDLES_FAIL, res); + } + return res; } ErrCode BSessionBackup::AppendBundles(vector bundlesToBackup, vector detailInfos) @@ -113,7 +127,17 @@ ErrCode BSessionBackup::AppendBundles(vector bundlesToBackup, vector return BError(BError::Codes::SDK_BROKEN_IPC, "Failed to get backup service").GetCode(); } - return proxy->AppendBundlesDetailsBackupSession(bundlesToBackup, detailInfos); + int32_t res = proxy->AppendBundlesDetailsBackupSession(bundlesToBackup, detailInfos); + if (res != ERR_OK) { + std::string ss; + for (const auto &bundleName:bundlesToBackup) { + ss += bundleName + ", "; + } + AppRadar::Info info(ss.c_str(), "", "AppendBundles with infos"); + AppRadar::GetInstance().RecordBackupFuncRes(info, "BSessionBackup::AppendBundles", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_APPEND_BUNDLES_FAIL, res); + } + return res; } ErrCode BSessionBackup::Finish() diff --git a/frameworks/native/backup_kit_inner/src/b_session_restore.cpp b/frameworks/native/backup_kit_inner/src/b_session_restore.cpp index 250d68bc7f24b8124536264115c5d79964f7599a..9247c39ffe785d68ca37b484e4841a384dfce082 100644 --- a/frameworks/native/backup_kit_inner/src/b_session_restore.cpp +++ b/frameworks/native/backup_kit_inner/src/b_session_restore.cpp @@ -16,6 +16,7 @@ #include "b_session_restore.h" #include "b_error/b_error.h" +#include "b_radar/b_radar.h" #include "filemgmt_libhilog.h" #include "service_proxy.h" #include "service_reverse.h" @@ -29,7 +30,7 @@ BSessionRestore::~BSessionRestore() HILOGI("Death Recipient is nullptr"); return; } - auto proxy = ServiceProxy::GetInstance(); + auto proxy = ServiceProxy::GetServiceProxyPointer(); if (proxy == nullptr) { return; } @@ -52,8 +53,11 @@ unique_ptr BSessionRestore::Init(Callbacks callbacks) return nullptr; } int32_t res = proxy->InitRestoreSession(new ServiceReverse(callbacks)); - if (res != 0) { + if (res != ERR_OK) { HILOGE("Failed to Restore because of %{public}d", res); + AppRadar::Info info ("", "", "create restore session failed"); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BSessionRestore::Init", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_CREATE_RESTORE_SESSION_FAIL, res); return nullptr; } @@ -101,7 +105,17 @@ ErrCode BSessionRestore::AppendBundles(UniqueFd remoteCap, vector bu if (proxy == nullptr) { return BError(BError::Codes::SDK_BROKEN_IPC, "Failed to get backup service").GetCode(); } - return proxy->AppendBundlesRestoreSession(move(remoteCap), bundlesToRestore, detailInfos); + ErrCode res = proxy->AppendBundlesRestoreSession(move(remoteCap), bundlesToRestore, detailInfos); + if (res != ERR_OK) { + std::string ss; + for (const auto &bundle : bundlesToRestore) { + ss += bundle + ", "; + } + AppRadar::Info info(ss.c_str(), "", "AppendBundles with infos"); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BSessionRestore::AppendBundles", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_APPEND_BUNDLES_FAIL, res); + } + return res; } ErrCode BSessionRestore::AppendBundles(UniqueFd remoteCap, vector bundlesToRestore) @@ -110,8 +124,17 @@ ErrCode BSessionRestore::AppendBundles(UniqueFd remoteCap, vector bu if (proxy == nullptr) { return BError(BError::Codes::SDK_BROKEN_IPC, "Failed to get backup service").GetCode(); } - - return proxy->AppendBundlesRestoreSession(move(remoteCap), bundlesToRestore); + ErrCode res = proxy->AppendBundlesRestoreSession(move(remoteCap), bundlesToRestore); + if (res != ERR_OK) { + std::string ss; + for (const auto &bundle : bundlesToRestore) { + ss += bundle + ", "; + } + AppRadar::Info info(ss.c_str(), "", ""); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BSessionRestore::AppendBundles", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_APPEND_BUNDLES_FAIL, res); + } + return res; } ErrCode BSessionRestore::Finish() diff --git a/frameworks/native/backup_kit_inner/src/b_session_restore_async.cpp b/frameworks/native/backup_kit_inner/src/b_session_restore_async.cpp index 10c388fb58b468f1ea7bf402fa39527ec0d55a50..12b82a250b54e5f06c6c6889b241bb1a83daf8cf 100644 --- a/frameworks/native/backup_kit_inner/src/b_session_restore_async.cpp +++ b/frameworks/native/backup_kit_inner/src/b_session_restore_async.cpp @@ -16,6 +16,7 @@ #include "b_session_restore_async.h" #include "b_error/b_error.h" +#include "b_radar/b_radar.h" #include "b_resources/b_constants.h" #include "b_session_restore.h" #include "filemgmt_libhilog.h" @@ -31,7 +32,7 @@ BSessionRestoreAsync::~BSessionRestoreAsync() HILOGI("Death Recipient is nullptr"); return; } - auto proxy = ServiceProxy::GetInstance(); + auto proxy = ServiceProxy::GetServiceProxyPointer(); if (proxy == nullptr) { return; } @@ -58,10 +59,14 @@ shared_ptr BSessionRestoreAsync::Init(Callbacks callbacks) .onBundleFinished = callbacks.onBundleFinished, .onAllBundlesFinished = callbacks.onAllBundlesFinished, .onResultReport = callbacks.onResultReport, - .onBackupServiceDied = callbacks.onBackupServiceDied}; + .onBackupServiceDied = callbacks.onBackupServiceDied, + .onProcess = callbacks.onProcess}; int32_t res = proxy->InitRestoreSession(sptr(new ServiceReverse(callbacksTmp))); - if (res != 0) { + if (res != ERR_OK) { HILOGE("Failed to Restore because of %{public}d", res); + AppRadar::Info info ("", "", "create restore session failed"); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BSessionRestoreAsync::Init", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_CREATE_RESTORE_SESSION_FAIL, res); return nullptr; } @@ -102,8 +107,18 @@ ErrCode BSessionRestoreAsync::AppendBundles(UniqueFd remoteCap, if (proxy == nullptr) { return BError(BError::Codes::SDK_BROKEN_IPC, "Failed to get backup service").GetCode(); } - return proxy->AppendBundlesRestoreSession(move(remoteCap), bundlesToRestore, detailInfos, restoreType, + ErrCode res = proxy->AppendBundlesRestoreSession(move(remoteCap), bundlesToRestore, detailInfos, restoreType, userId); + if (res != ERR_OK) { + std::string ss; + for (const auto &bundle : bundlesToRestore) { + ss += bundle + ", "; + } + AppRadar::Info info(ss.c_str(), "", "AppendBundles with infos"); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BSessionRestoreAsync::AppendBundles", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_APPEND_BUNDLES_FAIL, res); + } + return res; } ErrCode BSessionRestoreAsync::AppendBundles(UniqueFd remoteCap, @@ -116,7 +131,17 @@ ErrCode BSessionRestoreAsync::AppendBundles(UniqueFd remoteCap, return BError(BError::Codes::SDK_BROKEN_IPC, "Failed to get backup service").GetCode(); } - return proxy->AppendBundlesRestoreSession(move(remoteCap), bundlesToRestore, restoreType, userId); + ErrCode res = proxy->AppendBundlesRestoreSession(move(remoteCap), bundlesToRestore, restoreType, userId); + if (res != ERR_OK) { + std::string ss; + for (const auto &bundle : bundlesToRestore) { + ss += bundle + ", "; + } + AppRadar::Info info(ss.c_str(), "", ""); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "BSessionRestoreAsync::AppendBundles", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_APPEND_BUNDLES_FAIL, res); + } + return res; } ErrCode BSessionRestoreAsync::Release() diff --git a/frameworks/native/backup_kit_inner/src/service_incremental_reverse.cpp b/frameworks/native/backup_kit_inner/src/service_incremental_reverse.cpp index 8c5f4c465643f249622016915befb57b4069b5c0..ba1e761c5fd39867a97fe704e0efbfacb2b9d283 100644 --- a/frameworks/native/backup_kit_inner/src/service_incremental_reverse.cpp +++ b/frameworks/native/backup_kit_inner/src/service_incremental_reverse.cpp @@ -16,6 +16,7 @@ #include "service_reverse.h" #include "b_error/b_error.h" +#include "b_radar/b_radar.h" #include "filemgmt_libhilog.h" namespace OHOS::FileManagement::Backup { @@ -70,6 +71,16 @@ void ServiceReverse::IncrementalBackupOnAllBundlesFinished(int32_t errCode) callbacksIncrementalBackup_.onAllBundlesFinished(errCode); } +void ServiceReverse::IncrementalBackupOnProcessInfo(std::string bundleName, std::string processInfo) +{ + HILOGI("bundleName = %{public}s", bundleName.c_str()); + if (scenario_ != Scenario::BACKUP || !callbacksIncrementalBackup_.onProcess) { + HILOGE("Error scenario or callback is nullptr, scenario = %{public}d", scenario_); + return; + } + callbacksIncrementalBackup_.onProcess(bundleName, processInfo); +} + void ServiceReverse::IncrementalRestoreOnBundleStarted(int32_t errCode, string bundleName) { if (scenario_ != Scenario::RESTORE || !callbacksIncrementalRestore_.onBundleStarted) { @@ -125,6 +136,16 @@ void ServiceReverse::IncrementalRestoreOnResultReport(std::string result, std::s callbacksIncrementalRestore_.onBundleFinished(errCode, bundleName); } +void ServiceReverse::IncrementalRestoreOnProcessInfo(std::string bundleName, std::string processInfo) +{ + HILOGI("begin incremental report processInfo, bundleName:%{public}s", bundleName.c_str()); + if (scenario_ != Scenario::RESTORE || !callbacksIncrementalRestore_.onProcess) { + HILOGE("Error scenario or callback is nullptr, scenario = %{public}d", scenario_); + return; + } + callbacksIncrementalRestore_.onProcess(bundleName, processInfo); +} + ServiceReverse::ServiceReverse(BIncrementalBackupSession::Callbacks callbacks) : scenario_(Scenario::BACKUP), callbacksIncrementalBackup_(callbacks) { diff --git a/frameworks/native/backup_kit_inner/src/service_proxy.cpp b/frameworks/native/backup_kit_inner/src/service_proxy.cpp index 1d004e4f16e346181588c601b4cbfce81328748d..e05fb51381c173b4f8be2c2fa6348fe17f04bfbf 100644 --- a/frameworks/native/backup_kit_inner/src/service_proxy.cpp +++ b/frameworks/native/backup_kit_inner/src/service_proxy.cpp @@ -13,15 +13,16 @@ * limitations under the License. */ -#include "service_proxy.h" - -#include "iservice_registry.h" -#include "system_ability_definition.h" +#include #include "b_error/b_error.h" #include "b_error/b_excep_utils.h" +#include "b_radar/b_radar.h" #include "b_resources/b_constants.h" #include "filemgmt_libhilog.h" +#include "iservice_registry.h" +#include "service_proxy.h" +#include "system_ability_definition.h" #include "svc_death_recipient.h" #include "hitrace_meter.h" @@ -119,6 +120,9 @@ UniqueFd ServiceProxy::GetLocalCapabilities() static_cast(IServiceInterfaceCode::SERVICE_CMD_GET_LOCAL_CAPABILITIES), data, reply, option); if (ret != NO_ERROR) { HILOGE("Received error %{public}d when doing IPC", ret); + AppRadar::Info resInfo("", "", ""); + AppRadar::GetInstance().RecordDefaultFuncRes(resInfo, "ServiceProxy::GetLocalCapabilities", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_GET_LOCAL_CAPABILITIES_FAIL, ret); return UniqueFd(-ret); } UniqueFd fd(reply.ReadFileDescriptor()); @@ -293,7 +297,7 @@ ErrCode ServiceProxy::AppendBundlesRestoreSession(UniqueFd fd, const vectorSendRequest( - static_cast(IServiceInterfaceCode::SERVICE_CMD_APPEND_BUNDLES_RESTORE_SESSION_DETAILS), data, reply, + static_cast(IServiceInterfaceCode::SERVICE_CMD_APPEND_BUNDLES_RESTORE_SESSION_DETAIL), data, reply, option); if (ret != NO_ERROR) { string str = "Failed to send out the request because of " + to_string(ret); @@ -415,6 +419,12 @@ ErrCode ServiceProxy::Finish() return reply.ReadInt32(); } +sptr ServiceProxy::GetServiceProxyPointer() +{ + HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + return serviceProxy_; +} + sptr ServiceProxy::GetInstance() { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); @@ -446,6 +456,10 @@ sptr ServiceProxy::GetInstance() [loadCallback]() { return loadCallback->isLoadSuccess_.load(); }); if (!waitStatus) { HILOGE("Load backup sa timeout"); + AppRadar::Info info("", "", "\"reason\":\"Load backup sa timeout\""); + AppRadar::GetInstance().RecordBackupFuncRes(info, "ServiceProxy::GetInstance", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_BOOT_BACKUP_SA_FAIL, + BError(BError::Codes::SA_INVAL_ARG).GetCode()); return nullptr; } return serviceProxy_; @@ -502,6 +516,10 @@ void ServiceProxy::ServiceProxyLoadCallback::OnLoadSystemAbilityFail(int32_t sys unique_lock lock(proxyMutex_); serviceProxy_ = nullptr; isLoadSuccess_.store(false); + AppRadar::Info info("", "", "\"reason\":\"Load backup sa fail\""); + AppRadar::GetInstance().RecordBackupFuncRes(info, "ServiceProxyLoadCallback::OnLoadSystemAbilityFail", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_BOOT_BACKUP_SA_FAIL, + static_cast(BError::Codes::SA_INVAL_ARG)); proxyConVar_.notify_one(); } @@ -530,7 +548,7 @@ ErrCode ServiceProxy::GetBackupInfo(BundleName &bundleName, std::string &result) return BError(BError::Codes::OK, "success"); } -ErrCode ServiceProxy::UpdateTimer(BundleName &bundleName, uint32_t timeOut, bool &result) +ErrCode ServiceProxy::UpdateTimer(BundleName &bundleName, uint32_t timeout, bool &result) { HILOGI("ServiceProxy UpdateTimer Begin."); BExcepUltils::BAssert(Remote(), BError::Codes::SDK_INVAL_ARG, "Remote is nullptr"); @@ -541,8 +559,8 @@ ErrCode ServiceProxy::UpdateTimer(BundleName &bundleName, uint32_t timeOut, bool if (!data.WriteString(bundleName)) { return BError(BError::Codes::SDK_INVAL_ARG, "Failed to send bundleName").GetCode(); } - if (!data.WriteUint32(timeOut)) { - return BError(BError::Codes::SDK_INVAL_ARG, "Failed to send timeOut").GetCode(); + if (!data.WriteUint32(timeout)) { + return BError(BError::Codes::SDK_INVAL_ARG, "Failed to send timeout").GetCode(); } MessageParcel reply; MessageOption option; @@ -585,4 +603,75 @@ ErrCode ServiceProxy::UpdateSendRate(std::string &bundleName, int32_t sendRate, HILOGI("ServiceProxy UpdateSendRate end. ret = %{public}d", ret); return BError(BError::Codes::OK, "success"); } + +ErrCode ServiceProxy::ReportAppProcessInfo(const std::string processInfo, const BackupRestoreScenario sennario) +{ + HILOGD("ServiceProxy NotifyBundleProcessInfo Begin."); + BExcepUltils::BAssert(Remote(), BError::Codes::SDK_INVAL_ARG, "Remote is nullptr"); + MessageParcel data; + if (!data.WriteInterfaceToken(GetDescriptor())) { + return BError(BError::Codes::SDK_INVAL_ARG, "Failed to write descriptor").GetCode(); + } + if (!data.WriteString(processInfo)) { + return BError(BError::Codes::SDK_INVAL_ARG, "Failed to send bundleName").GetCode(); + } + if (!data.WriteInt32(static_cast(sennario))) { + return BError(BError::Codes::SDK_INVAL_ARG, "Failed to send the scenario").GetCode(); + } + MessageParcel reply; + MessageOption option; + option.SetWaitTime(BConstants::IPC_MAX_WAIT_TIME); + int32_t ret = Remote()-> SendRequest(static_cast( + IServiceInterfaceCode::SERVICE_CMD_REPORT_APP_PROCESS_INFO), data, reply, option); + if (ret != NO_ERROR) { + string str = "Failed to send out the request because of " + to_string(ret); + return BError(BError::Codes::SDK_INVAL_ARG, str.data()).GetCode(); + } + HILOGI("ServiceProxy NotifyBundleProcessInfo end. ret = %{public}d", ret); + return BError(BError::Codes::OK, "success"); +} + +ErrCode ServiceProxy::StartExtTimer(bool &isExtStart) +{ + HILOGI("ServiceProxy StartExtTimer Begin."); + BExcepUltils::BAssert(Remote(), BError::Codes::SDK_INVAL_ARG, "Remote is nullptr"); + MessageParcel data; + if (!data.WriteInterfaceToken(GetDescriptor())) { + return BError(BError::Codes::SDK_INVAL_ARG, "Failed to write descriptor").GetCode(); + } + MessageParcel reply; + MessageOption option; + option.SetWaitTime(BConstants::IPC_MAX_WAIT_TIME); + int32_t ret = Remote()->SendRequest(static_cast(IServiceInterfaceCode::SERVICE_CMD_START_EXT_TIMER), + data, reply, option); + if (ret != NO_ERROR) { + string str = "Failed to send out the request because of " + to_string(ret); + return BError(BError::Codes::SDK_INVAL_ARG, str.data()).GetCode(); + } + reply.ReadBool(isExtStart); + HILOGI("ServiceProxy StartExtTimer end. isExtStart = %d", isExtStart); + return BError(BError::Codes::OK, "success"); +} + +ErrCode ServiceProxy::StartFwkTimer(bool &isFwkStart) +{ + HILOGI("ServiceProxy StartFwkTimer Begin."); + BExcepUltils::BAssert(Remote(), BError::Codes::SDK_INVAL_ARG, "Remote is nullptr"); + MessageParcel data; + if (!data.WriteInterfaceToken(GetDescriptor())) { + return BError(BError::Codes::SDK_INVAL_ARG, "Failed to write descriptor").GetCode(); + } + MessageParcel reply; + MessageOption option; + option.SetWaitTime(BConstants::IPC_MAX_WAIT_TIME); + int32_t ret = Remote()->SendRequest(static_cast(IServiceInterfaceCode::SERVICE_CMD_START_FWK_TIMER), + data, reply, option); + if (ret != NO_ERROR) { + string str = "Failed to send out the request because of " + to_string(ret); + return BError(BError::Codes::SDK_INVAL_ARG, str.data()).GetCode(); + } + reply.ReadBool(isFwkStart); + HILOGI("ServiceProxy StartFwkTimer end. isFwkStart = %d", isFwkStart); + return BError(BError::Codes::OK, "success"); +} } // namespace OHOS::FileManagement::Backup diff --git a/frameworks/native/backup_kit_inner/src/service_reverse.cpp b/frameworks/native/backup_kit_inner/src/service_reverse.cpp index f2e2eb71622403472dda9ca56f61e0fc4af33a40..6328cb70ea63730224ee61a943a8dba13482ed20 100644 --- a/frameworks/native/backup_kit_inner/src/service_reverse.cpp +++ b/frameworks/native/backup_kit_inner/src/service_reverse.cpp @@ -24,7 +24,7 @@ using namespace std; void ServiceReverse::BackupOnFileReady(string bundleName, string fileName, int fd, int32_t errCode) { if (scenario_ != Scenario::BACKUP || !callbacksBackup_.onFileReady) { - HILOGI("Error scenario or callback is nullptr"); + HILOGE("Error scenario or callback is nullptr, scenario = %{public}d", scenario_); return; } BFileInfo bFileInfo(bundleName, fileName, 0); @@ -34,7 +34,7 @@ void ServiceReverse::BackupOnFileReady(string bundleName, string fileName, int f void ServiceReverse::BackupOnBundleStarted(int32_t errCode, string bundleName) { if (scenario_ != Scenario::BACKUP || !callbacksBackup_.onBundleStarted) { - HILOGI("Error scenario or callback is nullptr"); + HILOGE("Error scenario or callback is nullptr, scenario = %{public}d", scenario_); return; } callbacksBackup_.onBundleStarted(errCode, bundleName); @@ -43,7 +43,7 @@ void ServiceReverse::BackupOnBundleStarted(int32_t errCode, string bundleName) void ServiceReverse::BackupOnResultReport(std::string result, std::string bundleName) { if (scenario_ != Scenario::BACKUP || !callbacksBackup_.onResultReport) { - HILOGI("Error scenario or callback is nullptr"); + HILOGE("Error scenario or callback is nullptr, scenario = %{public}d", scenario_); return; } callbacksBackup_.onResultReport(bundleName, result); @@ -52,7 +52,7 @@ void ServiceReverse::BackupOnResultReport(std::string result, std::string bundle void ServiceReverse::BackupOnBundleFinished(int32_t errCode, string bundleName) { if (scenario_ != Scenario::BACKUP || !callbacksBackup_.onBundleFinished) { - HILOGI("Error scenario or callback is nullptr"); + HILOGE("Error scenario or callback is nullptr, scenario = %{public}d", scenario_); return; } HILOGI("errCode = %{public}d, bundleName = %{public}s", errCode, bundleName.c_str()); @@ -63,16 +63,26 @@ void ServiceReverse::BackupOnAllBundlesFinished(int32_t errCode) { HILOGI("errCode = %{public}d", errCode); if (scenario_ != Scenario::BACKUP || !callbacksBackup_.onAllBundlesFinished) { - HILOGI("Error scenario or callback is nullptr"); + HILOGE("Error scenario or callback is nullptr, scenario = %{public}d", scenario_); return; } callbacksBackup_.onAllBundlesFinished(errCode); } +void ServiceReverse::BackupOnProcessInfo(std::string bundleName, std::string processInfo) +{ + HILOGI("bundleName = %{public}s", bundleName.c_str()); + if (scenario_ != Scenario::BACKUP || !callbacksBackup_.onProcess) { + HILOGI("Error scenario or callback is nullptr"); + return; + } + callbacksBackup_.onProcess(bundleName, processInfo); +} + void ServiceReverse::RestoreOnBundleStarted(int32_t errCode, string bundleName) { if (scenario_ != Scenario::RESTORE || !callbacksRestore_.onBundleStarted) { - HILOGI("Error scenario or callback is nullptr"); + HILOGE("Error scenario or callback is nullptr, scenario = %{public}d", scenario_); return; } callbacksRestore_.onBundleStarted(errCode, bundleName); @@ -81,7 +91,7 @@ void ServiceReverse::RestoreOnBundleStarted(int32_t errCode, string bundleName) void ServiceReverse::RestoreOnBundleFinished(int32_t errCode, string bundleName) { if (scenario_ != Scenario::RESTORE || !callbacksRestore_.onBundleFinished) { - HILOGI("Error scenario or callback is nullptr"); + HILOGE("Error scenario or callback is nullptr, scenario = %{public}d", scenario_); return; } HILOGI("errCode = %{public}d, bundleName = %{public}s", errCode, bundleName.c_str()); @@ -92,7 +102,7 @@ void ServiceReverse::RestoreOnAllBundlesFinished(int32_t errCode) { HILOGI("errCode = %{public}d", errCode); if (scenario_ != Scenario::RESTORE || !callbacksRestore_.onAllBundlesFinished) { - HILOGI("Error scenario or callback is nullptr"); + HILOGE("Error scenario or callback is nullptr, scenario = %{public}d", scenario_); return; } callbacksRestore_.onAllBundlesFinished(errCode); @@ -102,7 +112,7 @@ void ServiceReverse::RestoreOnFileReady(string bundleName, string fileName, int { HILOGD("begin, bundleName is:%{public}s", bundleName.c_str()); if (scenario_ != Scenario::RESTORE || !callbacksRestore_.onFileReady) { - HILOGI("Error scenario or callback is nullptr"); + HILOGE("Error scenario or callback is nullptr, scenario = %{public}d", scenario_); return; } BFileInfo bFileInfo(bundleName, fileName, 0); @@ -114,17 +124,27 @@ void ServiceReverse::RestoreOnResultReport(string result, std::string bundleName HILOGI("ServiceReverse RestoreOnResultReport bundle %{public}s begin with result: %{public}s", bundleName.c_str(), result.c_str()); if (scenario_ != Scenario::RESTORE || !callbacksRestore_.onResultReport) { - HILOGI("Error scenario or callback is nullptr"); + HILOGE("Error scenario or callback is nullptr, scenario = %{public}d", scenario_); return; } callbacksRestore_.onResultReport(bundleName, result); if (scenario_ != Scenario::RESTORE || !callbacksRestore_.onBundleFinished) { - HILOGI("Error scenario or callback is nullptr"); + HILOGE("Error scenario or callback is nullptr, scenario = %{public}d", scenario_); return; } callbacksRestore_.onBundleFinished(errCode, bundleName); } +void ServiceReverse::RestoreOnProcessInfo(std::string bundleName, std::string processInfo) +{ + HILOGI("bundleName = %{public}s", bundleName.c_str()); + if (scenario_ != Scenario::RESTORE || !callbacksRestore_.onProcess) { + HILOGI("Error scenario or callback is nullptr"); + return; + } + callbacksRestore_.onProcess(bundleName, processInfo); +} + ServiceReverse::ServiceReverse(BSessionBackup::Callbacks callbacks) : scenario_(Scenario::BACKUP), callbacksBackup_(callbacks) { diff --git a/frameworks/native/backup_kit_inner/src/service_reverse_stub.cpp b/frameworks/native/backup_kit_inner/src/service_reverse_stub.cpp index 0fdeed6c8687a7a16ccd7f6c96914dc55fb6a1d9..8f970cab4fa55ba8f94401d47d6efc36a92f2a52 100644 --- a/frameworks/native/backup_kit_inner/src/service_reverse_stub.cpp +++ b/frameworks/native/backup_kit_inner/src/service_reverse_stub.cpp @@ -43,6 +43,26 @@ int32_t ServiceReverseStub::OnRemoteRequest(uint32_t code, } return (this->*(interfaceIndex->second))(data, reply); } +void ServiceReverseStub::ServiceReverseStubSupplement() +{ + opToInterfaceMap_[static_cast(IServiceReverseInterfaceCode::SERVICER_INCREMENTAL_RESTORE_ON_FILE_READY)] = + &ServiceReverseStub::CmdIncrementalRestoreOnFileReady; + opToInterfaceMap_[static_cast( + IServiceReverseInterfaceCode::SERVICER_INCREMENTAL_RESTORE_ON_SUB_TASK_STARTED)] = + &ServiceReverseStub::CmdIncrementalRestoreOnBundleStarted; + opToInterfaceMap_[static_cast( + IServiceReverseInterfaceCode::SERVICER_INCREMENTAL_RESTORE_ON_RESULT_REPORT)] = + &ServiceReverseStub::CmdIncrementalRestoreOnResultReport; + opToInterfaceMap_[static_cast( + IServiceReverseInterfaceCode::SERVICER_INCREMENTAL_RESTORE_ON_SUB_TASK_FINISHED)] = + &ServiceReverseStub::CmdIncrementalRestoreOnBundleFinished; + opToInterfaceMap_[static_cast( + IServiceReverseInterfaceCode::SERVICER_INCREMENTAL_RESTORE_ON_TASK_FINISHED)] = + &ServiceReverseStub::CmdIncrementalRestoreOnAllBundlesFinished; + opToInterfaceMap_[static_cast( + IServiceReverseInterfaceCode::SERVICER_INCREMENTAL_RESTORE_ON_PROCESS_INFO)] = + &ServiceReverseStub::CmdIncrementalRestoreOnProcessInfo; +} ServiceReverseStub::ServiceReverseStub() { @@ -56,6 +76,8 @@ ServiceReverseStub::ServiceReverseStub() &ServiceReverseStub::CmdBackupOnBundleFinished; opToInterfaceMap_[static_cast(IServiceReverseInterfaceCode::SERVICER_BACKUP_ON_TASK_FINISHED)] = &ServiceReverseStub::CmdBackupOnAllBundlesFinished; + opToInterfaceMap_[static_cast(IServiceReverseInterfaceCode::SERVICER_BACKUP_ON_PROCESS_INFO)] = + &ServiceReverseStub::CmdBackupOnProcessInfo; opToInterfaceMap_[static_cast(IServiceReverseInterfaceCode::SERVICER_RESTORE_ON_FILE_READY)] = &ServiceReverseStub::CmdRestoreOnFileReady; @@ -67,6 +89,8 @@ ServiceReverseStub::ServiceReverseStub() &ServiceReverseStub::CmdRestoreOnBundleFinished; opToInterfaceMap_[static_cast(IServiceReverseInterfaceCode::SERVICER_RESTORE_ON_TASK_FINISHED)] = &ServiceReverseStub::CmdRestoreOnAllBundlesFinished; + opToInterfaceMap_[static_cast(IServiceReverseInterfaceCode::SERVICER_RESTORE_ON_PROCESS_INFO)] = + &ServiceReverseStub::CmdRestoreOnProcessInfo; opToInterfaceMap_[static_cast(IServiceReverseInterfaceCode::SERVICER_INCREMENTAL_BACKUP_ON_FILE_READY)] = &ServiceReverseStub::CmdIncrementalBackupOnFileReady; @@ -81,21 +105,10 @@ ServiceReverseStub::ServiceReverseStub() opToInterfaceMap_[static_cast( IServiceReverseInterfaceCode::SERVICER_INCREMENTAL_BACKUP_ON_TASK_FINISHED)] = &ServiceReverseStub::CmdIncrementalBackupOnAllBundlesFinished; - - opToInterfaceMap_[static_cast(IServiceReverseInterfaceCode::SERVICER_INCREMENTAL_RESTORE_ON_FILE_READY)] = - &ServiceReverseStub::CmdIncrementalRestoreOnFileReady; - opToInterfaceMap_[static_cast( - IServiceReverseInterfaceCode::SERVICER_INCREMENTAL_RESTORE_ON_SUB_TASK_STARTED)] = - &ServiceReverseStub::CmdIncrementalRestoreOnBundleStarted; - opToInterfaceMap_[static_cast( - IServiceReverseInterfaceCode::SERVICER_INCREMENTAL_RESTORE_ON_RESULT_REPORT)] = - &ServiceReverseStub::CmdIncrementalRestoreOnResultReport; opToInterfaceMap_[static_cast( - IServiceReverseInterfaceCode::SERVICER_INCREMENTAL_RESTORE_ON_SUB_TASK_FINISHED)] = - &ServiceReverseStub::CmdIncrementalRestoreOnBundleFinished; - opToInterfaceMap_[static_cast( - IServiceReverseInterfaceCode::SERVICER_INCREMENTAL_RESTORE_ON_TASK_FINISHED)] = - &ServiceReverseStub::CmdIncrementalRestoreOnAllBundlesFinished; + IServiceReverseInterfaceCode::SERVICER_INCREMENTAL_BACKUP_ON_PROCESS_INFO)] = + &ServiceReverseStub::CmdIncrementalBackupOnProcessInfo; + ServiceReverseStubSupplement(); } int32_t ServiceReverseStub::CmdBackupOnFileReady(MessageParcel &data, MessageParcel &reply) @@ -143,6 +156,14 @@ int32_t ServiceReverseStub::CmdBackupOnAllBundlesFinished(MessageParcel &data, M return BError(BError::Codes::OK); } +int32_t ServiceReverseStub::CmdBackupOnProcessInfo(MessageParcel &data, MessageParcel &reply) +{ + std::string bundleName = data.ReadString(); + std::string processInfo = data.ReadString(); + BackupOnProcessInfo(bundleName, processInfo); + return BError(BError::Codes::OK); +} + int32_t ServiceReverseStub::CmdRestoreOnBundleStarted(MessageParcel &data, MessageParcel &reply) { int32_t errCode = data.ReadInt32(); @@ -198,6 +219,14 @@ int32_t ServiceReverseStub::CmdRestoreOnResultReport(MessageParcel &data, Messag return BError(BError::Codes::OK); } +int32_t ServiceReverseStub::CmdRestoreOnProcessInfo(MessageParcel &data, MessageParcel &reply) +{ + std::string bundleName = data.ReadString(); + std::string processInfo = data.ReadString(); + RestoreOnProcessInfo(bundleName, processInfo); + return BError(BError::Codes::OK); +} + int32_t ServiceReverseStub::CmdIncrementalBackupOnFileReady(MessageParcel &data, MessageParcel &reply) { auto bundleName = data.ReadString(); @@ -245,6 +274,14 @@ int32_t ServiceReverseStub::CmdIncrementalBackupOnAllBundlesFinished(MessageParc return BError(BError::Codes::OK); } +int32_t ServiceReverseStub::CmdIncrementalBackupOnProcessInfo(MessageParcel &data, MessageParcel &reply) +{ + std::string bundleName = data.ReadString(); + std::string processInfo = data.ReadString(); + IncrementalBackupOnProcessInfo(bundleName, processInfo); + return BError(BError::Codes::OK); +} + int32_t ServiceReverseStub::CmdIncrementalRestoreOnBundleStarted(MessageParcel &data, MessageParcel &reply) { int32_t errCode = data.ReadInt32(); @@ -292,4 +329,12 @@ int32_t ServiceReverseStub::CmdIncrementalRestoreOnResultReport(MessageParcel &d IncrementalRestoreOnResultReport(result, bundleName, errCode); return BError(BError::Codes::OK); } + +int32_t ServiceReverseStub::CmdIncrementalRestoreOnProcessInfo(MessageParcel &data, MessageParcel &reply) +{ + auto bundleName = data.ReadString(); + auto processInfo = data.ReadString(); + IncrementalRestoreOnProcessInfo(bundleName, processInfo); + return BError(BError::Codes::OK); +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/interfaces/api/js/napi/backup_ext/backup_extension_ability.js b/interfaces/api/js/napi/backup_ext/backup_extension_ability.js index b1801058f4390d545007974492a97ac627a44b1c..a4fdf706d28eecdb68227b6a47079f6ab71e4787 100644 --- a/interfaces/api/js/napi/backup_ext/backup_extension_ability.js +++ b/interfaces/api/js/napi/backup_ext/backup_extension_ability.js @@ -29,6 +29,10 @@ class BackupExtensionAbility { onRestoreEx(versionBackupedBundle, restoreInfo) { console.log(); } + + onProcess() { + console.log(); + } } -export default BackupExtensionAbility \ No newline at end of file +export default BackupExtensionAbility; \ No newline at end of file diff --git a/interfaces/common/src/json_utils.cpp b/interfaces/common/src/json_utils.cpp index 30523ac779f81b5cc879cab00070e1403bc08dc1..3a401b5bb96f472ab1951dd288f0eecdff664258 100644 --- a/interfaces/common/src/json_utils.cpp +++ b/interfaces/common/src/json_utils.cpp @@ -39,7 +39,7 @@ int32_t JsonUtils::GetJsonObjFromPath(nlohmann::json& jsonObj, const std::string jsonFileStream.close(); jsonObj = nlohmann::json::parse(buf.str(), nullptr, false); - if (!jsonObj.is_discarded()) { + if (jsonObj.is_discarded()) { LOGE("Parse json file path %{public}s failed", jsonPath.c_str()); } return 0; diff --git a/interfaces/common/src/sandbox_helper.cpp b/interfaces/common/src/sandbox_helper.cpp index a958e740e8152e9bb7596fbcca898188d3cb0e16..482445d21d67691ce97dbc99ea94ea9fc883c990 100644 --- a/interfaces/common/src/sandbox_helper.cpp +++ b/interfaces/common/src/sandbox_helper.cpp @@ -313,6 +313,7 @@ static void GetNetworkIdFromUri(const std::string &fileUri, string &networkId) if (networkIdInfo.empty()) { return; } + size_t posIndex = networkIdInfo.find('='); if (posIndex == string::npos || posIndex == (networkIdInfo.size() - 1)) { return; @@ -422,7 +423,6 @@ bool SandboxHelper::IsValidPath(const std::string &path) bool SandboxHelper::CheckValidPath(const std::string &filePath) { if (filePath.empty() || filePath.size() >= PATH_MAX) { - LOGE("filePath is invalid, size = %{public}zu", filePath.size()); return false; } diff --git a/interfaces/inner_api/native/backup_kit_inner/BUILD.gn b/interfaces/inner_api/native/backup_kit_inner/BUILD.gn index c84d227f23979db6436a0793c0b705f4ce0d7a81..2ee1a876dd7b91829c20172f45856f18b82206e9 100644 --- a/interfaces/inner_api/native/backup_kit_inner/BUILD.gn +++ b/interfaces/inner_api/native/backup_kit_inner/BUILD.gn @@ -27,6 +27,7 @@ config("private_config") { "${path_backup}/frameworks/native/backup_kit_inner/include", "${path_backup}/interfaces/inner_api/native/backup_kit_inner", "${path_backup}/interfaces/inner_api/native/backup_kit_inner/impl", + "${path_backup}/utils/include", ] } diff --git a/interfaces/inner_api/native/backup_kit_inner/impl/b_incremental_backup_session.h b/interfaces/inner_api/native/backup_kit_inner/impl/b_incremental_backup_session.h index f37aa190e9b9fc802ee1d7d6f11db5d092e020dc..c7c40df0a3ea6bb0c478ab667a438a074c85c3ef 100644 --- a/interfaces/inner_api/native/backup_kit_inner/impl/b_incremental_backup_session.h +++ b/interfaces/inner_api/native/backup_kit_inner/impl/b_incremental_backup_session.h @@ -37,6 +37,7 @@ public: std::function onAllBundlesFinished; // 当整个备份流程结束或意外中止时执行的回调函数 std::function onResultReport; // 某个应用备份流程中自定义错误信息的上报的回调函数 std::function onBackupServiceDied; // 当备份服务意外死亡时执行的回调函数 + std::function onProcess; // 上报备份恢复过程中的进度和异常 }; public: diff --git a/interfaces/inner_api/native/backup_kit_inner/impl/b_incremental_restore_session.h b/interfaces/inner_api/native/backup_kit_inner/impl/b_incremental_restore_session.h index 54b3a25b16ef5b18ca1a56511184024ebc2565b9..3a2e2ec5fd4d3bd87fffdde7ecc9a4da70e0286e 100644 --- a/interfaces/inner_api/native/backup_kit_inner/impl/b_incremental_restore_session.h +++ b/interfaces/inner_api/native/backup_kit_inner/impl/b_incremental_restore_session.h @@ -37,6 +37,7 @@ public: std::function onAllBundlesFinished; // 当整个恢复流程结束或意外中止时执行的回调函数 std::function onResultReport; // 某个应用恢复流程中自定义错误信息的上报的回调函数 std::function onBackupServiceDied; // 当备份服务意外死亡时执行的回调函数 + std::function onProcess; // 上报备份恢复过程中的进度和异常 }; public: @@ -92,7 +93,6 @@ public: * * @param remoteCap 已打开的保存远端设备能力的Json文件。可使用GetLocalCapabilities方法获取 * @param bundlesToRestore 待恢复的应用清单 - * * @return ErrCode 规范错误码 */ ErrCode AppendBundles(UniqueFd remoteCap, std::vector bundlesToRestore); diff --git a/interfaces/inner_api/native/backup_kit_inner/impl/b_incremental_session_restore_async.h b/interfaces/inner_api/native/backup_kit_inner/impl/b_incremental_session_restore_async.h index 8405b9b88aa67fa16d707b336eb6ca0a2e902dcb..fc705c6f63a2996afbae716e4c8405fe689dbeac 100644 --- a/interfaces/inner_api/native/backup_kit_inner/impl/b_incremental_session_restore_async.h +++ b/interfaces/inner_api/native/backup_kit_inner/impl/b_incremental_session_restore_async.h @@ -79,12 +79,15 @@ public: * * @param remoteCap 已打开的保存远端设备能力的Json文件。可使用GetLocalCapabilities方法获取 * @param bundlesToRestore 待恢复的应用清单 + * @param detailInfos bundle的单双映射关系json串 * @param userId 用户ID * @return ErrCode 规范错误码 - */ - ErrCode AppendBundles(UniqueFd remoteCap, std::vector bundlesToRestore, - std::vector detailInfos, RestoreTypeEnum restoreType = RestoreTypeEnum::RESTORE_DATA_WAIT_SEND, - int32_t userId = DEFAULT_INVAL_VALUE); + */ + ErrCode AppendBundles(UniqueFd remoteCap, + std::vector bundlesToRestore, + std::vector detailInfos, + RestoreTypeEnum restoreType = RestoreTypeEnum::RESTORE_DATA_WAIT_SEND, + int32_t userId = DEFAULT_INVAL_VALUE); /** * @brief 用于追加待恢复应用 diff --git a/interfaces/inner_api/native/backup_kit_inner/impl/b_session_backup.h b/interfaces/inner_api/native/backup_kit_inner/impl/b_session_backup.h index 46a6e24b1be69d4be5433a7b94e012190ea4ae66..f08c340be0704f1ec09ab923c9d085fa1dedc527 100644 --- a/interfaces/inner_api/native/backup_kit_inner/impl/b_session_backup.h +++ b/interfaces/inner_api/native/backup_kit_inner/impl/b_session_backup.h @@ -35,6 +35,7 @@ public: std::function onAllBundlesFinished; // 当整个备份流程结束或意外中止时执行的回调函数 std::function onResultReport; // 某个应用备份流程中自定义错误信息的上报的回调函数 std::function onBackupServiceDied; // 当备份服务意外死亡时执行的回调函数 + std::function onProcess; // 上报备份恢复过程中的进度和异常 }; public: diff --git a/interfaces/inner_api/native/backup_kit_inner/impl/b_session_restore.h b/interfaces/inner_api/native/backup_kit_inner/impl/b_session_restore.h index 06e8332303fa170d02170f96cab0b6a78843015d..d953b3067575151a75e0f431222e9b3677d9778f 100644 --- a/interfaces/inner_api/native/backup_kit_inner/impl/b_session_restore.h +++ b/interfaces/inner_api/native/backup_kit_inner/impl/b_session_restore.h @@ -35,6 +35,7 @@ public: std::function onAllBundlesFinished; // 当整个恢复流程结束或意外中止时执行的回调函数 std::function onResultReport; // 某个应用恢复流程中自定义错误信息的上报的回调函数 std::function onBackupServiceDied; // 当备份服务意外死亡时执行的回调函数 + std::function onProcess; // 上报备份恢复过程中的进度和异常 }; public: @@ -63,7 +64,7 @@ public: */ ErrCode GetFileHandle(const std::string &bundleName, const std::string &fileName); - /** + /** * @brief 用于追加应用,现阶段仅支持在Start之前调用 * * @param remoteCap 已打开的保存远端设备能力的Json文件。可使用GetLocalCapabilities方法获取 diff --git a/interfaces/inner_api/native/backup_kit_inner/impl/b_session_restore_async.h b/interfaces/inner_api/native/backup_kit_inner/impl/b_session_restore_async.h index 4d4cdad10cbf52f889485deaddc81c1286fc35b2..96cf0c93003c430b5f3d524672c3844de8540702 100644 --- a/interfaces/inner_api/native/backup_kit_inner/impl/b_session_restore_async.h +++ b/interfaces/inner_api/native/backup_kit_inner/impl/b_session_restore_async.h @@ -39,6 +39,7 @@ public: std::function onAllBundlesFinished; // 当整个恢复流程结束或意外中止时执行的回调函数 std::function onResultReport; // 某个应用恢复流程中自定义错误信息的上报的回调函数 std::function onBackupServiceDied; // 当备份服务意外死亡时执行的回调函数 + std::function onProcess; // 上报备份恢复过程中的进度和异常 }; struct AppendBundleInfo { @@ -82,13 +83,12 @@ public: * @param detailInfos bundle对应的单双映射的json串 * @param userId 用户ID * @return ErrCode 规范错误码 - */ + */ ErrCode AppendBundles(UniqueFd remoteCap, std::vector bundlesToRestore, std::vector detailInfos, RestoreTypeEnum restoreType = RestoreTypeEnum::RESTORE_DATA_WAIT_SEND, int32_t userId = DEFAULT_INVAL_VALUE); - /** * @brief 用于追加待恢复应用 * diff --git a/interfaces/inner_api/native/backup_kit_inner/impl/i_extension.h b/interfaces/inner_api/native/backup_kit_inner/impl/i_extension.h index 364214d2d0c1b70b45b61062c23b6ba20b9358b5..a20fb4cdd8388441513338395e6db6281c5a4387 100644 --- a/interfaces/inner_api/native/backup_kit_inner/impl/i_extension.h +++ b/interfaces/inner_api/native/backup_kit_inner/impl/i_extension.h @@ -30,16 +30,17 @@ public: virtual ~IExtension() = default; virtual UniqueFd GetFileHandle(const std::string &fileName, int32_t &errCode) = 0; virtual ErrCode HandleClear() = 0; - virtual ErrCode HandleBackup() = 0; + virtual ErrCode HandleBackup(bool isClearData) = 0; virtual ErrCode PublishFile(const std::string &fileName) = 0; - virtual ErrCode HandleRestore() = 0; + virtual ErrCode HandleRestore(bool isClearData) = 0; virtual ErrCode GetIncrementalFileHandle(const std::string &fileName) = 0; virtual ErrCode PublishIncrementalFile(const std::string &fileName) = 0; virtual ErrCode HandleIncrementalBackup(UniqueFd incrementalFd, UniqueFd manifestFd) = 0; - virtual ErrCode IncrementalOnBackup() = 0; + virtual ErrCode IncrementalOnBackup(bool isClearData) = 0; virtual std::tuple GetIncrementalBackupFileHandle() = 0; virtual ErrCode GetBackupInfo(std::string &result) = 0; virtual ErrCode UpdateFdSendRate(std::string &bundleName, int32_t sendRate) = 0; + virtual ErrCode User0OnBackup() = 0; }; } // namespace OHOS::FileManagement::Backup diff --git a/interfaces/inner_api/native/backup_kit_inner/impl/i_extension_ipc_interface_code.h b/interfaces/inner_api/native/backup_kit_inner/impl/i_extension_ipc_interface_code.h index 15478e015881ba14a66b3d7f0ef6999acd109665..40c2f120845951b4931cc39a33e58f5bae6afdef 100644 --- a/interfaces/inner_api/native/backup_kit_inner/impl/i_extension_ipc_interface_code.h +++ b/interfaces/inner_api/native/backup_kit_inner/impl/i_extension_ipc_interface_code.h @@ -31,6 +31,7 @@ enum class IExtensionInterfaceCode { CMD_GET_BACKUP_INFO, CMD_INCREMENTAL_ON_BACKUP, CMD_UPDATE_FD_SENDRATE, + CMD_HANDLE_USER_0_BACKUP, }; } // namespace OHOS::FileManagement::Backup diff --git a/interfaces/inner_api/native/backup_kit_inner/impl/i_service.h b/interfaces/inner_api/native/backup_kit_inner/impl/i_service.h index 49348fb58591984d27a328c01487941ac9d8e4ea..6dee18fc376fc35c1ec94c80b39bf7f4593fdf50 100644 --- a/interfaces/inner_api/native/backup_kit_inner/impl/i_service.h +++ b/interfaces/inner_api/native/backup_kit_inner/impl/i_service.h @@ -83,8 +83,11 @@ public: virtual ErrCode AppIncrementalDone(ErrCode errCode) = 0; virtual ErrCode GetIncrementalFileHandle(const std::string &bundleName, const std::string &fileName) = 0; virtual ErrCode GetBackupInfo(BundleName &bundleName, std::string &result) = 0; - virtual ErrCode UpdateTimer(BundleName &bundleName, uint32_t timeOut, bool &result) = 0; + virtual ErrCode UpdateTimer(BundleName &bundleName, uint32_t timeout, bool &result) = 0; virtual ErrCode UpdateSendRate(std::string &bundleName, int32_t sendRate, bool &result) = 0; + virtual ErrCode ReportAppProcessInfo(const std::string processInfo, const BackupRestoreScenario sennario) = 0; + virtual ErrCode StartExtTimer(bool &isExtStart) = 0; + virtual ErrCode StartFwkTimer(bool &isFwkStart) = 0; DECLARE_INTERFACE_DESCRIPTOR(u"OHOS.Filemanagement.Backup.IService") }; diff --git a/interfaces/inner_api/native/backup_kit_inner/impl/i_service_ipc_interface_code.h b/interfaces/inner_api/native/backup_kit_inner/impl/i_service_ipc_interface_code.h index 1de4b9c45934275547880b510fcdbaed86101a9b..dbb444b53e327218b8088ea3e15f888a94aec536 100644 --- a/interfaces/inner_api/native/backup_kit_inner/impl/i_service_ipc_interface_code.h +++ b/interfaces/inner_api/native/backup_kit_inner/impl/i_service_ipc_interface_code.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2022-2024 Huawei Device Co., Ltd. + * Copyright (c) 2024 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at @@ -28,8 +28,8 @@ enum class IServiceInterfaceCode { SERVICE_CMD_RESULT_REPORT, SERVICE_CMD_START, SERVICE_CMD_GET_FILE_NAME, + SERVICE_CMD_APPEND_BUNDLES_RESTORE_SESSION_DETAIL, SERVICE_CMD_APPEND_BUNDLES_RESTORE_SESSION, - SERVICE_CMD_APPEND_BUNDLES_RESTORE_SESSION_DETAILS, SERVICE_CMD_APPEND_BUNDLES_BACKUP_SESSION, SERVICE_CMD_APPEND_BUNDLES_BACKUP_SESSION_DETAILS, SERVICE_CMD_FINISH, @@ -45,8 +45,11 @@ enum class IServiceInterfaceCode { SERVICE_CMD_GET_INCREMENTAL_FILE_NAME, SERVICE_CMD_GET_BACKUP_INFO, SERVICE_CMD_UPDATE_TIMER, + SERVICE_CMD_START_EXT_TIMER, + SERVICE_CMD_START_FWK_TIMER, SERVICE_CMD_UPDATE_SENDRATE, SERVICE_CMD_GET_APP_LOCAL_LIST_AND_DO_INCREMENTAL_BACKUP, + SERVICE_CMD_REPORT_APP_PROCESS_INFO, }; } // namespace OHOS::FileManagement::Backup diff --git a/interfaces/inner_api/native/backup_kit_inner/impl/i_service_reverse.h b/interfaces/inner_api/native/backup_kit_inner/impl/i_service_reverse.h index 8791c26b2514a21e8ed21978ba1046ac8364d2d1..52311dde514d0a45fab11942877f2722f8c9cb1c 100644 --- a/interfaces/inner_api/native/backup_kit_inner/impl/i_service_reverse.h +++ b/interfaces/inner_api/native/backup_kit_inner/impl/i_service_reverse.h @@ -28,6 +28,7 @@ public: UNDEFINED, BACKUP, RESTORE, + CLEAN, }; public: @@ -37,6 +38,7 @@ public: virtual void BackupOnResultReport(std::string result, std::string bundleName) = 0; virtual void BackupOnBundleFinished(int32_t errCode, std::string bundleName) = 0; virtual void BackupOnAllBundlesFinished(int32_t errCode) = 0; + virtual void BackupOnProcessInfo(std::string bundleName, std::string processInfo) = 0; virtual void RestoreOnBundleStarted(int32_t errCode, std::string bundleName) = 0; virtual void RestoreOnFileReady(std::string bundleName, std::string fileName, int fd, int32_t errCode) = 0; @@ -44,6 +46,7 @@ public: ErrCode errCode = 0) = 0; virtual void RestoreOnBundleFinished(int32_t errCode, std::string bundleName) = 0; virtual void RestoreOnAllBundlesFinished(int32_t errCode) = 0; + virtual void RestoreOnProcessInfo(std::string bundleName, std::string processInfo) = 0; virtual void IncrementalBackupOnBundleStarted(int32_t errCode, std::string bundleName) = 0; virtual void IncrementalBackupOnFileReady(std::string bundleName, std::string fileName, int fd, int manifestFd, @@ -51,6 +54,7 @@ public: virtual void IncrementalBackupOnResultReport(std::string result, std::string bundleName) = 0; virtual void IncrementalBackupOnBundleFinished(int32_t errCode, std::string bundleName) = 0; virtual void IncrementalBackupOnAllBundlesFinished(int32_t errCode) = 0; + virtual void IncrementalBackupOnProcessInfo(std::string bundleName, std::string processInfo) = 0; virtual void IncrementalRestoreOnBundleStarted(int32_t errCode, std::string bundleName) = 0; virtual void IncrementalRestoreOnFileReady(std::string bundleName, @@ -61,6 +65,7 @@ public: ErrCode errCode = 0) = 0; virtual void IncrementalRestoreOnBundleFinished(int32_t errCode, std::string bundleName) = 0; virtual void IncrementalRestoreOnAllBundlesFinished(int32_t errCode) = 0; + virtual void IncrementalRestoreOnProcessInfo(const std::string bundleName, const std::string processInfo) = 0; DECLARE_INTERFACE_DESCRIPTOR(u"OHOS.FileManagement.Backup.IServiceReverse") }; diff --git a/interfaces/inner_api/native/backup_kit_inner/impl/i_service_reverse_ipc_interface_code.h b/interfaces/inner_api/native/backup_kit_inner/impl/i_service_reverse_ipc_interface_code.h index a41ec673f0ede4d5870070b3873176113e109b5a..5d991d6fbd88212b1989695ad6fe100a586f0441 100644 --- a/interfaces/inner_api/native/backup_kit_inner/impl/i_service_reverse_ipc_interface_code.h +++ b/interfaces/inner_api/native/backup_kit_inner/impl/i_service_reverse_ipc_interface_code.h @@ -24,21 +24,25 @@ enum class IServiceReverseInterfaceCode { SERVICER_BACKUP_ON_SUB_TASK_FINISHED, SERVICER_BACKUP_ON_TASK_FINISHED, SERVICER_BACKUP_ON_RESULT_REPORT, + SERVICER_BACKUP_ON_PROCESS_INFO, SERVICER_RESTORE_ON_SUB_TASK_STARTED, SERVICER_RESTORE_ON_SUB_TASK_FINISHED, SERVICER_RESTORE_ON_TASK_FINISHED, SERVICER_RESTORE_ON_FILE_READY, SERVICER_RESTORE_ON_RESULT_REPORT, + SERVICER_RESTORE_ON_PROCESS_INFO, SERVICER_INCREMENTAL_BACKUP_ON_FILE_READY, SERVICER_INCREMENTAL_BACKUP_ON_SUB_TASK_STARTED, SERVICER_INCREMENTAL_BACKUP_ON_SUB_TASK_FINISHED, SERVICER_INCREMENTAL_BACKUP_ON_TASK_FINISHED, SERVICER_INCREMENTAL_BACKUP_ON_RESULT_REPORT, + SERVICER_INCREMENTAL_BACKUP_ON_PROCESS_INFO, SERVICER_INCREMENTAL_RESTORE_ON_SUB_TASK_STARTED, SERVICER_INCREMENTAL_RESTORE_ON_SUB_TASK_FINISHED, SERVICER_INCREMENTAL_RESTORE_ON_TASK_FINISHED, SERVICER_INCREMENTAL_RESTORE_ON_FILE_READY, SERVICER_INCREMENTAL_RESTORE_ON_RESULT_REPORT, + SERVICER_INCREMENTAL_RESTORE_ON_PROCESS_INFO, }; } // namespace OHOS::FileManagement::Backup diff --git a/interfaces/inner_api/native/backup_kit_inner/impl/service_proxy.h b/interfaces/inner_api/native/backup_kit_inner/impl/service_proxy.h index d0845087ee63d5148626174e238c488aafeb1f2b..21c676d85ffc5d35c95911bc877cc7bff311a926 100644 --- a/interfaces/inner_api/native/backup_kit_inner/impl/service_proxy.h +++ b/interfaces/inner_api/native/backup_kit_inner/impl/service_proxy.h @@ -66,8 +66,11 @@ public: ErrCode AppIncrementalDone(ErrCode errCode) override; ErrCode GetIncrementalFileHandle(const std::string &bundleName, const std::string &fileName) override; ErrCode GetBackupInfo(BundleName &bundleName, std::string &result) override; - ErrCode UpdateTimer(BundleName &bundleName, uint32_t timeOut, bool &result) override; + ErrCode UpdateTimer(BundleName &bundleName, uint32_t timeout, bool &result) override; ErrCode UpdateSendRate(std::string &bundleName, int32_t sendRate, bool &result) override; + ErrCode ReportAppProcessInfo(const std::string processInfo, const BackupRestoreScenario sennario) override; + ErrCode StartExtTimer(bool &isExtStart) override; + ErrCode StartFwkTimer(bool &isFwkStart) override; public: explicit ServiceProxy(const sptr &impl) : IRemoteProxy(impl) {} @@ -76,6 +79,7 @@ public: public: template bool WriteParcelableVector(const std::vector &parcelableVector, Parcel &data); + static sptr GetServiceProxyPointer(); static sptr GetInstance(); static void InvaildInstance(); diff --git a/interfaces/inner_api/native/backup_kit_inner/impl/svc_death_recipient.h b/interfaces/inner_api/native/backup_kit_inner/impl/svc_death_recipient.h index d7d9d294da68df2612f36fa3e6ca1ab675fb93e5..4f318b47471442c377e9ba14b4b794d5cac749e2 100644 --- a/interfaces/inner_api/native/backup_kit_inner/impl/svc_death_recipient.h +++ b/interfaces/inner_api/native/backup_kit_inner/impl/svc_death_recipient.h @@ -25,8 +25,8 @@ class SvcDeathRecipient : public IRemoteObject::DeathRecipient { public: void OnRemoteDied(const wptr &object) override { - object->RemoveDeathRecipient(this); functor_(object); + object->RemoveDeathRecipient(this); }; public: diff --git a/interfaces/innerkits/native/file_uri/include/file_uri.h b/interfaces/innerkits/native/file_uri/include/file_uri.h index 1f8f50410c7bbeebf2718b2df408b00983d10b69..8ae2f8a114b322a817a8ad53329be7b331e698d0 100644 --- a/interfaces/innerkits/native/file_uri/include/file_uri.h +++ b/interfaces/innerkits/native/file_uri/include/file_uri.h @@ -26,8 +26,8 @@ class FileUri { public: std::string GetName(); std::string GetPath(); - std::string GetRealPathBySA(const std::string &targetBundleName = ""); std::string GetRealPath(); + std::string GetRealPathBySA(const std::string &targetBundleName = ""); std::string ToString(); std::string GetFullDirectoryUri(); bool IsRemoteUri(); diff --git a/interfaces/kits/js/backup/general_callbacks.cpp b/interfaces/kits/js/backup/general_callbacks.cpp index 63170425fabd7de54062b103b31940121f2ea357..da856fa4a987a7a72610ba6ffd4121847117033c 100644 --- a/interfaces/kits/js/backup/general_callbacks.cpp +++ b/interfaces/kits/js/backup/general_callbacks.cpp @@ -22,6 +22,32 @@ namespace OHOS::FileManagement::Backup { using namespace std; +void GeneralCallbacks::RemoveCallbackRef() +{ + HILOGI("Called RemoveCallbackRef"); + onFileReady.CleanRef(); + onBundleBegin.CleanRef(); + onBundleEnd.CleanRef(); + onAllBundlesEnd.CleanRef(); + onBackupServiceDied.CleanRef(); + onResultReport.CleanRef(); + onProcess.CleanRef(); +} + +void BackupRestoreCallback::CleanRef() +{ + HILOGI("BackupRestoreCallback CleanRef"); + if (!ctx_) { + HILOGE("BackupRestoreCallback ctx is nullptr"); + return; + } + if (!bool(ctx_->cb_)) { + HILOGE("BackupRestoreCallback ref is nullptr"); + return; + } + ctx_->cb_.DeleteJsEnv(); +} + BackupRestoreCallback::BackupRestoreCallback(napi_env env, LibN::NVal thisPtr, LibN::NVal cb) : env_(env) { ctx_ = new LibN::NAsyncContextCallback(thisPtr, cb); @@ -29,7 +55,9 @@ BackupRestoreCallback::BackupRestoreCallback(napi_env env, LibN::NVal thisPtr, L BackupRestoreCallback::~BackupRestoreCallback() { + HILOGI("BackupRestoreCallback destruct start"); if (!ctx_) { + HILOGE("BackupRestoreCallback ctx is nullptr"); return; } @@ -53,6 +81,7 @@ BackupRestoreCallback::~BackupRestoreCallback() loop, work.get(), [](uv_work_t *work) {}, [](uv_work_t *work, int status) { LibN::NAsyncContextCallback *ctx = static_cast(work->data); + HILOGI("BackupRestoreCallback destruct delete ctx"); delete ctx; delete work; }); @@ -63,6 +92,7 @@ BackupRestoreCallback::~BackupRestoreCallback() ptr.release(); work.release(); ctx_ = nullptr; + HILOGI("BackupRestoreCallback destruct end"); } BackupRestoreCallback::operator bool() const @@ -96,6 +126,10 @@ static void DoCallJsMethod(napi_env env, void *data, InputArgsParser argParser) napi_value global = nullptr; napi_get_global(env, &global); napi_value callback = ctx->cb_.Deref(env).val_; + if (!bool(ctx->cb_)) { + HILOGE("Failed to get ref."); + return; + } napi_value result = nullptr; napi_status status = napi_call_function(env, global, callback, argv.size(), argv.data(), &result); if (status != napi_ok) { @@ -114,11 +148,7 @@ void BackupRestoreCallback::CallJsMethod(InputArgsParser argParser) HILOGE("failed to get uv event loop."); return; } - struct WorkArgs { - BackupRestoreCallback *ptr = nullptr; - InputArgsParser argParser; - }; - auto workArgs = make_unique(); + auto workArgs = make_shared(); auto work = make_unique(); if (workArgs == nullptr || work == nullptr) { HILOGE("failed to new workArgs or uv_work_t."); @@ -134,21 +164,25 @@ void BackupRestoreCallback::CallJsMethod(InputArgsParser argParser) auto workArgs = reinterpret_cast(work->data); do { if (workArgs == nullptr) { - HILOGE("failed to get CallJsParam."); + HILOGE("failed to get workArgs."); break; } DoCallJsMethod(workArgs->ptr->env_, workArgs->ptr->ctx_, workArgs->argParser); } while (false); - delete workArgs; + HILOGI("will notify current thread info"); + std::unique_lock lock(workArgs->callbackMutex); + workArgs->isReady.store(true); + workArgs->callbackCondition.notify_all(); delete work; }); if (ret != 0) { HILOGE("failed to exec uv_queue_work."); - workArgs.reset(); work.reset(); return; } - workArgs.release(); + std::unique_lock lock(workArgs->callbackMutex); + HILOGI("Wait execute callback method end"); + workArgs->callbackCondition.wait(lock, [workArgs]() { return workArgs->isReady.load(); }); work.release(); HILOGI("call BackupRestoreCallback CallJsMethod end."); } diff --git a/interfaces/kits/js/backup/general_callbacks.h b/interfaces/kits/js/backup/general_callbacks.h index 04956ac668675c339e731d5df5a1c92f88c68792..7f395fdfd8d96ffbb72196bc2d2527ed273c8ccb 100644 --- a/interfaces/kits/js/backup/general_callbacks.h +++ b/interfaces/kits/js/backup/general_callbacks.h @@ -30,11 +30,20 @@ public: ~BackupRestoreCallback(); void CallJsMethod(InputArgsParser argParser); explicit operator bool() const; + void CleanRef(); private: napi_env env_; LibN::NAsyncContextCallback *ctx_ = nullptr; }; +struct WorkArgs { + std::mutex callbackMutex; + std::condition_variable callbackCondition; + std::atomic isReady {false}; + BackupRestoreCallback *ptr = nullptr; + InputArgsParser argParser; +}; + class GeneralCallbacks { public: GeneralCallbacks(const napi_env &env, const LibN::NVal &thisPtr, const LibN::NVal &jsCallbacks) @@ -43,15 +52,18 @@ public: onBundleEnd(env, thisPtr, jsCallbacks.GetProp("onBundleEnd")), onAllBundlesEnd(env, thisPtr, jsCallbacks.GetProp("onAllBundlesEnd")), onBackupServiceDied(env, thisPtr, jsCallbacks.GetProp("onBackupServiceDied")), - onResultReport(env, thisPtr, jsCallbacks.GetProp("onResultReport")) {}; - + onResultReport(env, thisPtr, jsCallbacks.GetProp("onResultReport")), + onProcess(env, thisPtr, jsCallbacks.GetProp("onProcess")) {}; +public: + void RemoveCallbackRef(); public: LibN::NAsyncWorkCallback onFileReady; LibN::NAsyncWorkCallback onBundleBegin; LibN::NAsyncWorkCallback onBundleEnd; LibN::NAsyncWorkCallback onAllBundlesEnd; - LibN::NAsyncWorkCallback onBackupServiceDied; + BackupRestoreCallback onBackupServiceDied; BackupRestoreCallback onResultReport; + BackupRestoreCallback onProcess; }; } // namespace OHOS::FileManagement::Backup #endif // INTERFACES_KITS_JS_SRC_MOD_BACKUP_PROPERTIES_GENERAL_CALLBACKS_H \ No newline at end of file diff --git a/interfaces/kits/js/backup/prop_n_operation.cpp b/interfaces/kits/js/backup/prop_n_operation.cpp index d059dc95f201b774a0e0e800ce46a7ecca384723..1f6f5d7b01b88763fd0a050da24d930608f0a045 100644 --- a/interfaces/kits/js/backup/prop_n_operation.cpp +++ b/interfaces/kits/js/backup/prop_n_operation.cpp @@ -17,6 +17,7 @@ #include "b_error/b_error.h" #include "b_incremental_data.h" #include "b_resources/b_constants.h" +#include "b_sa/b_sa_utils.h" #include "filemgmt_libhilog.h" #include "filemgmt_libn.h" #include "incremental_backup_data.h" @@ -30,21 +31,6 @@ namespace OHOS::FileManagement::Backup { using namespace std; using namespace LibN; -const int32_t H_TO_MS = 3600 * 1000; - -static bool CheckPermission(const string &permission) -{ - Security::AccessToken::AccessTokenID tokenCaller = IPCSkeleton::GetCallingTokenID(); - return Security::AccessToken::AccessTokenKit::VerifyAccessToken(tokenCaller, permission) == - Security::AccessToken::PermissionState::PERMISSION_GRANTED; -} - -static bool IsSystemApp() -{ - uint64_t fullTokenId = OHOS::IPCSkeleton::GetCallingFullTokenID(); - return Security::AccessToken::TokenIdKit::IsSystemAppByFullTokenID(fullTokenId); -} - static napi_value AsyncCallback(napi_env env, const NFuncArg& funcArg) { HILOGD("called LocalCapabilities::AsyncCallback begin"); @@ -182,6 +168,16 @@ static napi_value AsyncDataList(napi_env env, const NFuncArg& funcArg) napi_value PropNOperation::Async(napi_env env, napi_callback_info info) { HILOGD("called LocalCapabilities::Async begin"); + if (!SAUtils::CheckBackupPermission()) { + HILOGE("Has not permission!"); + NError(E_PERMISSION).ThrowErr(env); + return nullptr; + } + if (!SAUtils::IsSystemApp()) { + HILOGE("System App check fail!"); + NError(E_PERMISSION_SYS).ThrowErr(env); + return nullptr; + } NFuncArg funcArg(env, info); if (!funcArg.InitArgs(NARG_CNT::ZERO, NARG_CNT::ONE)) { HILOGE("Number of arguments unmatched."); @@ -203,6 +199,16 @@ napi_value PropNOperation::Async(napi_env env, napi_callback_info info) napi_value PropNOperation::DoGetBackupInfo(napi_env env, napi_callback_info info) { HILOGD("called DoGetBackupInfo begin"); + if (!SAUtils::CheckBackupPermission()) { + HILOGE("Has not permission!"); + NError(E_PERMISSION).ThrowErr(env); + return nullptr; + } + if (!SAUtils::IsSystemApp()) { + HILOGE("System App check fail!"); + NError(E_PERMISSION_SYS).ThrowErr(env); + return nullptr; + } std::string result; NFuncArg funcArg(env, info); if (!funcArg.InitArgs(NARG_CNT::ONE, NARG_CNT::TWO)) { @@ -241,35 +247,35 @@ napi_value PropNOperation::DoGetBackupInfo(napi_env env, napi_callback_info info return nResult; } -bool PropNOperation::UpdateTimer(std::string &bundleName, uint32_t timeOut) +bool PropNOperation::UpdateSendRate(std::string &bundleName, int32_t sendRate) { bool result = false; ServiceProxy::InvaildInstance(); auto proxy = ServiceProxy::GetInstance(); if (!proxy) { - HILOGE("called DoUpdateTimer,failed to get proxy"); + HILOGE("called UpdateSendRate,failed to get proxy"); return result; } - ErrCode errcode = proxy->UpdateTimer(bundleName, timeOut, result); - if (errcode != 0) { - HILOGE("proxy->UpdateTimer faild."); + ErrCode errCode = proxy->UpdateSendRate(bundleName, sendRate, result); + if (errCode != 0) { + HILOGE("Proxy execute UpdateSendRate failed. errCode:%{public}d", errCode); return result; } return result; } -bool PropNOperation::UpdateSendRate(std::string &bundleName, int32_t sendRate) +bool PropNOperation::UpdateTimer(std::string &bundleName, uint32_t timeout) { bool result = false; ServiceProxy::InvaildInstance(); auto proxy = ServiceProxy::GetInstance(); if (!proxy) { - HILOGE("called UpdateSendRate,failed to get proxy"); + HILOGE("called DoUpdateTimer,failed to get proxy"); return result; } - ErrCode errCode = proxy->UpdateSendRate(bundleName, sendRate, result); - if (errCode != 0) { - HILOGE("Proxy execute UpdateSendRate failed. errCode:%{public}d", errCode); + ErrCode errcode = proxy->UpdateTimer(bundleName, timeout, result); + if (errcode != 0) { + HILOGE("proxy->UpdateTimer faild."); return result; } return result; @@ -278,12 +284,12 @@ bool PropNOperation::UpdateSendRate(std::string &bundleName, int32_t sendRate) napi_value PropNOperation::DoUpdateTimer(napi_env env, napi_callback_info info) { HILOGD("called DoUpdateTimer begin"); - if (!CheckPermission("ohos.permission.BACKUP")) { - HILOGE("has not permission!"); + if (!SAUtils::CheckBackupPermission()) { + HILOGE("Has not permission!"); NError(E_PERMISSION).ThrowErr(env); return nullptr; } - if (!IsSystemApp()) { + if (!SAUtils::IsSystemApp()) { HILOGE("System App check fail!"); NError(E_PERMISSION_SYS).ThrowErr(env); return nullptr; @@ -303,15 +309,15 @@ napi_value PropNOperation::DoUpdateTimer(napi_env env, napi_callback_info info) } NVal jsBundleInt(env, funcArg[NARG_POS::SECOND]); auto [succInt, time] = jsBundleInt.ToInt32(); - if (!succInt || time <= 0 || time > H_TO_MS) { + if (!succInt || time < 0 || time > static_cast(BConstants::MAX_UPDATE_TIMER)) { HILOGE("Second argument is not number."); NError(E_PARAMS).ThrowErr(env); return nullptr; } std::string bundleName = bundle.get(); - uint32_t timeOut = static_cast(time); - bool result = UpdateTimer(bundleName, timeOut); + uint32_t timeout = static_cast(time); + bool result = UpdateTimer(bundleName, timeout); napi_value nResult; napi_status status = napi_get_boolean(env, result, &nResult); @@ -326,12 +332,12 @@ napi_value PropNOperation::DoUpdateTimer(napi_env env, napi_callback_info info) napi_value PropNOperation::DoUpdateSendRate(napi_env env, napi_callback_info info) { HILOGD("called DoUpdateSendRate begin"); - if (!CheckPermission("ohos.permission.BACKUP")) { - HILOGE("has not permission!"); + if (!SAUtils::CheckBackupPermission()) { + HILOGE("Has not permission!"); NError(E_PERMISSION).ThrowErr(env); return nullptr; } - if (!IsSystemApp()) { + if (!SAUtils::IsSystemApp()) { HILOGE("System App check fail!"); NError(E_PERMISSION_SYS).ThrowErr(env); return nullptr; @@ -372,4 +378,4 @@ napi_value PropNOperation::DoUpdateSendRate(napi_env env, napi_callback_info inf HILOGI("DoUpdateSendRate success with result: %{public}d", result); return nResult; } -} // namespace OHOS::FileManagement::Backup \ No newline at end of file +} // namespace OHOS::FileManagement::Backup diff --git a/interfaces/kits/js/backup/prop_n_operation.h b/interfaces/kits/js/backup/prop_n_operation.h index b6d746f00db10c7db72408c4ea83f3bbffcf0fed..7137d8d14d7ac98fc9586306a4e0781752d61b04 100644 --- a/interfaces/kits/js/backup/prop_n_operation.h +++ b/interfaces/kits/js/backup/prop_n_operation.h @@ -26,7 +26,7 @@ public: static napi_value DoUpdateTimer(napi_env env, napi_callback_info info); static napi_value DoUpdateSendRate(napi_env env, napi_callback_info info); private: - static bool UpdateTimer(std::string &bundleName, uint32_t timeOut); + static bool UpdateTimer(std::string &bundleName, uint32_t timeout); static bool UpdateSendRate(std::string &bundleName, int32_t sendRate); }; diff --git a/interfaces/kits/js/backup/session_backup_n_exporter.cpp b/interfaces/kits/js/backup/session_backup_n_exporter.cpp index 0d84c030833a28891d5f0c1de5ca0ccd484ecd7f..fcb482f77fb11c8a4f9510eb210b252b68c05cd8 100644 --- a/interfaces/kits/js/backup/session_backup_n_exporter.cpp +++ b/interfaces/kits/js/backup/session_backup_n_exporter.cpp @@ -68,13 +68,20 @@ static void OnFileReady(weak_ptr pCallbacks, const BFileInfo & }; if (std::get<0>(errInfo) != 0) { obj = NVal {env, NError(errorParam).GetNapiErr(env)}; + napi_status status = napi_set_named_property(env, obj.val_, FILEIO_TAG_ERR_DATA.c_str(), + NVal::CreateUTF8String(env, bundleName).val_); + if (status != napi_ok) { + HILOGE("Failed to set data property, status %{public}d, bundleName %{public}s", + status, bundleName.c_str()); + } } else { obj = NVal::CreateObject(env); + obj.AddProp({ + NVal::DeclareNapiProperty(BConstants::BUNDLE_NAME.c_str(), + NVal::CreateUTF8String(env, bundleName).val_), + NVal::DeclareNapiProperty(BConstants::URI.c_str(), NVal::CreateUTF8String(env, fileName).val_), + NVal::DeclareNapiProperty(BConstants::FD.c_str(), NVal::CreateInt32(env, fd->Release()).val_)}); } - obj.AddProp({ - NVal::DeclareNapiProperty(BConstants::BUNDLE_NAME.c_str(), NVal::CreateUTF8String(env, bundleName).val_), - NVal::DeclareNapiProperty(BConstants::URI.c_str(), NVal::CreateUTF8String(env, fileName).val_), - NVal::DeclareNapiProperty(BConstants::FD.c_str(), NVal::CreateInt32(env, fd->Release()).val_)}); return {obj}; }; @@ -83,7 +90,7 @@ static void OnFileReady(weak_ptr pCallbacks, const BFileInfo & static void onBundleBegin(weak_ptr pCallbacks, ErrCode err, const BundleName name) { - HILOGI("Callback onBundleBegin, bundleName=%{public}s", name.c_str()); + HILOGI("Callback onBundleBegin, bundleName=%{public}s, errCode=%{public}d", name.c_str(), err); if (pCallbacks.expired()) { HILOGI("callbacks is unbound"); return; @@ -98,17 +105,23 @@ static void onBundleBegin(weak_ptr pCallbacks, ErrCode err, co return; } - auto cbCompl = [name {name}, errCode {err}](napi_env env, NError err) -> NVal { + ErrCode errCode = BError::GetBackupCodeByErrno(err); + std::string errMsg = BError::GetBackupMsgByErrno(errCode) + ", origin errno: " + to_string(err); + std::tuple errInfo = std::make_tuple(errCode, errMsg); + + auto cbCompl = [name {name}, errCode {err}, errInfo](napi_env env, NError err) -> NVal { NVal bundleName = NVal::CreateUTF8String(env, name); if (!err && errCode == 0) { return bundleName; } - + ErrParam errorParam = [ errInfo ]() { + return errInfo; + }; NVal res; if (err) { res = NVal {env, err.GetNapiErr(env)}; } else { - res = NVal {env, NError(errCode).GetNapiErr(env)}; + res = NVal {env, NError(errorParam).GetNapiErr(env)}; } napi_status status = napi_set_named_property(env, res.val_, FILEIO_TAG_ERR_DATA.c_str(), bundleName.val_); if (status != napi_ok) { @@ -123,7 +136,7 @@ static void onBundleBegin(weak_ptr pCallbacks, ErrCode err, co static void onBundleEnd(weak_ptr pCallbacks, ErrCode err, const BundleName name) { - HILOGI("Callback onBundleEnd, bundleName=%{public}s", name.c_str()); + HILOGI("Callback onBundleEnd, bundleName=%{public}s, errCode=%{public}d", name.c_str(), err); if (pCallbacks.expired()) { HILOGI("callbacks is unbound"); return; @@ -138,17 +151,23 @@ static void onBundleEnd(weak_ptr pCallbacks, ErrCode err, cons return; } - auto cbCompl = [name {name}, errCode {err}](napi_env env, NError err) -> NVal { + ErrCode errCode = BError::GetBackupCodeByErrno(err); + std::string errMsg = BError::GetBackupMsgByErrno(errCode) + ", origin errno: " + to_string(err); + std::tuple errInfo = std::make_tuple(errCode, errMsg); + + auto cbCompl = [name {name}, errCode {err}, errInfo](napi_env env, NError err) -> NVal { NVal bundleName = NVal::CreateUTF8String(env, name); if (!err && errCode == 0) { return bundleName; } - + ErrParam errorParam = [ errInfo ]() { + return errInfo; + }; NVal res; if (err) { res = NVal {env, err.GetNapiErr(env)}; } else { - res = NVal {env, NError(errCode).GetNapiErr(env)}; + res = NVal {env, NError(errorParam).GetNapiErr(env)}; } napi_status status = napi_set_named_property(env, res.val_, FILEIO_TAG_ERR_DATA.c_str(), bundleName.val_); if (status != napi_ok) { @@ -177,16 +196,22 @@ static void onAllBundlesEnd(weak_ptr pCallbacks, ErrCode err) return; } - auto cbCompl = [errCode {err}](napi_env env, NError err) -> NVal { + ErrCode errCode = BError::GetBackupCodeByErrno(err); + std::string errMsg = BError::GetBackupMsgByErrno(errCode) + ", origin errno: " + to_string(err); + std::tuple errInfo = std::make_tuple(errCode, errMsg); + + auto cbCompl = [errCode {err}, errInfo](napi_env env, NError err) -> NVal { if (!err && errCode == 0) { return NVal::CreateUndefined(env); } - + ErrParam errorParam = [ errInfo ]() { + return errInfo; + }; NVal res; if (err) { res = NVal {env, err.GetNapiErr(env)}; } else { - res = NVal {env, NError(errCode).GetNapiErr(env)}; + res = NVal {env, NError(errorParam).GetNapiErr(env)}; } return res; @@ -241,16 +266,77 @@ static void OnBackupServiceDied(weak_ptr pCallbacks) return; } - auto cbCompl = [](napi_env env, NError err) -> NVal { - return err ? NVal {env, err.GetNapiErr(env)} : NVal::CreateUndefined(env); + auto cbCompl = [](napi_env env, vector &argv) -> bool { + napi_value napi_res = nullptr; + napi_get_undefined(env, &napi_res); + argv.push_back(napi_res); + return true; }; + callbacks->onBackupServiceDied.CallJsMethod(cbCompl); +} - callbacks->onBackupServiceDied.ThreadSafeSchedule(cbCompl); +static void OnProcess(weak_ptr pCallbacks, const BundleName name, const std::string processInfo) +{ + HILOGI("Callback OnProcess, bundleName=%{public}s", name.c_str()); + if (pCallbacks.expired()) { + HILOGI("callbacks is unbound"); + return; + } + auto callbacks = pCallbacks.lock(); + if (!callbacks) { + HILOGI("callback function OnProcess has already been released"); + return; + } + if (!bool(callbacks->onProcess)) { + HILOGI("callback function OnProcess is undefined"); + return; + } + auto cbCompl = [bundleName {name}, process {processInfo}](napi_env env, vector &argv) -> bool { + napi_value napi_bName = nullptr; + napi_create_string_utf8(env, bundleName.c_str(), bundleName.size(), &napi_bName); + argv.push_back(napi_bName); + napi_value napi_process = nullptr; + napi_create_string_utf8(env, process.c_str(), process.size(), &napi_process); + argv.push_back(napi_process); + return true; + }; + callbacks->onProcess.CallJsMethod(cbCompl); +} + +static bool SetSessionBackupEntity(napi_env env, NFuncArg &funcArg, std::unique_ptr backupEntity) +{ + auto finalize = [](napi_env env, void *data, void *hint) { + std::unique_ptr entity = std::unique_ptr(static_cast(data)); + if (entity == nullptr) { + HILOGE("Entity is nullptr"); + return; + } + if (entity->callbacks == nullptr) { + HILOGE("Callbacks is nullptr"); + return; + } + entity->callbacks->RemoveCallbackRef(); + }; + if (napi_wrap(env, funcArg.GetThisVar(), backupEntity.release(), finalize, nullptr, nullptr) != napi_ok) { + HILOGE("Failed to set BackupEntity entity."); + return false; + } + return true; } napi_value SessionBackupNExporter::Constructor(napi_env env, napi_callback_info cbinfo) { HILOGD("called SessionBackup::Constructor begin"); + if (!SAUtils::CheckBackupPermission()) { + HILOGE("Has not permission!"); + NError(E_PERMISSION).ThrowErr(env); + return nullptr; + } + if (!SAUtils::IsSystemApp()) { + HILOGE("System App check fail!"); + NError(E_PERMISSION_SYS).ThrowErr(env); + return nullptr; + } NFuncArg funcArg(env, cbinfo); if (!funcArg.InitArgs(NARG_CNT::ONE)) { HILOGE("Number of arguments unmatched."); @@ -274,17 +360,16 @@ napi_value SessionBackupNExporter::Constructor(napi_env env, napi_callback_info .onBundleFinished = bind(onBundleEnd, backupEntity->callbacks, placeholders::_1, placeholders::_2), .onAllBundlesFinished = bind(onAllBundlesEnd, backupEntity->callbacks, placeholders::_1), .onResultReport = bind(OnResultReport, backupEntity->callbacks, placeholders::_1, placeholders::_2), - .onBackupServiceDied = bind(OnBackupServiceDied, backupEntity->callbacks)}); + .onBackupServiceDied = bind(OnBackupServiceDied, backupEntity->callbacks), + .onProcess = bind(OnProcess, backupEntity->callbacks, placeholders::_1, placeholders::_2)}); if (!backupEntity->session) { NError(BError(BError::Codes::SDK_INVAL_ARG, "Failed to init backup").GetCode()).ThrowErr(env); return nullptr; } - if (!NClass::SetEntityFor(env, funcArg.GetThisVar(), move(backupEntity))) { - HILOGE("Failed to set BackupEntity entity."); + if (!SetSessionBackupEntity(env, funcArg, std::move(backupEntity))) { NError(BError(BError::Codes::SDK_INVAL_ARG, "Failed to set BackupEntity entity").GetCode()).ThrowErr(env); return nullptr; } - HILOGD("called SessionBackup::Constructor end"); return funcArg.GetThisVar(); } @@ -326,6 +411,16 @@ static bool VerifyParamSuccess(NFuncArg &funcArg, std::vector &bund napi_value SessionBackupNExporter::AppendBundles(napi_env env, napi_callback_info cbinfo) { HILOGD("called SessionBackup::AppendBundles begin"); + if (!SAUtils::CheckBackupPermission()) { + HILOGE("Has not permission!"); + NError(E_PERMISSION).ThrowErr(env); + return nullptr; + } + if (!SAUtils::IsSystemApp()) { + HILOGE("System App check fail!"); + NError(E_PERMISSION_SYS).ThrowErr(env); + return nullptr; + } std::vector bundleNames; std::vector bundleInfos; NFuncArg funcArg(env, cbinfo); @@ -369,6 +464,16 @@ napi_value SessionBackupNExporter::AppendBundles(napi_env env, napi_callback_inf napi_value SessionBackupNExporter::Release(napi_env env, napi_callback_info cbinfo) { HILOGD("called SessionBackup::Release begin"); + if (!SAUtils::CheckBackupPermission()) { + HILOGE("Has not permission!"); + NError(E_PERMISSION).ThrowErr(env); + return nullptr; + } + if (!SAUtils::IsSystemApp()) { + HILOGE("System App check fail!"); + NError(E_PERMISSION_SYS).ThrowErr(env); + return nullptr; + } NFuncArg funcArg(env, cbinfo); if (!funcArg.InitArgs(NARG_CNT::ZERO)) { HILOGE("Number of arguments unmatched."); diff --git a/interfaces/kits/js/backup/session_incremental_backup_n_exporter.cpp b/interfaces/kits/js/backup/session_incremental_backup_n_exporter.cpp index 8d386e094d8806deb24bc1a724e6d76b531f0eb8..a983e927923a096f93bb048339ab818db5e6f100 100644 --- a/interfaces/kits/js/backup/session_incremental_backup_n_exporter.cpp +++ b/interfaces/kits/js/backup/session_incremental_backup_n_exporter.cpp @@ -22,6 +22,7 @@ #include "b_incremental_backup_session.h" #include "b_incremental_data.h" #include "b_resources/b_constants.h" +#include "b_sa/b_sa_utils.h" #include "backup_kit_inner.h" #include "directory_ex.h" #include "filemgmt_libhilog.h" @@ -72,15 +73,21 @@ static void OnFileReady(weak_ptr pCallbacks, const BFileInfo & }; if (std::get<0>(errInfo) != 0) { obj = NVal {env, NError(errorParam).GetNapiErr(env)}; + napi_status status = napi_set_named_property(env, obj.val_, FILEIO_TAG_ERR_DATA.c_str(), + NVal::CreateUTF8String(env, bundleName).val_); + if (status != napi_ok) { + HILOGE("Failed to set data, status %{public}d, bundleName %{public}s", status, bundleName.c_str()); + } } else { obj = NVal::CreateObject(env); + obj.AddProp({ + NVal::DeclareNapiProperty(BConstants::BUNDLE_NAME.c_str(), + NVal::CreateUTF8String(env, bundleName).val_), + NVal::DeclareNapiProperty(BConstants::URI.c_str(), NVal::CreateUTF8String(env, fileName).val_), + NVal::DeclareNapiProperty(BConstants::FD.c_str(), NVal::CreateInt32(env, fd->Release()).val_), + NVal::DeclareNapiProperty(BConstants::MANIFEST_FD.c_str(), + NVal::CreateInt32(env, manifestFd->Release()).val_)}); } - obj.AddProp({ - NVal::DeclareNapiProperty(BConstants::BUNDLE_NAME.c_str(), NVal::CreateUTF8String(env, bundleName).val_), - NVal::DeclareNapiProperty(BConstants::URI.c_str(), NVal::CreateUTF8String(env, fileName).val_), - NVal::DeclareNapiProperty(BConstants::FD.c_str(), NVal::CreateInt32(env, fd->Release()).val_), - NVal::DeclareNapiProperty(BConstants::MANIFEST_FD.c_str(), - NVal::CreateInt32(env, manifestFd->Release()).val_)}); return {obj}; }; @@ -89,7 +96,7 @@ static void OnFileReady(weak_ptr pCallbacks, const BFileInfo & static void onBundleBegin(weak_ptr pCallbacks, ErrCode err, const BundleName name) { - HILOGI("Callback onBundleBegin, bundleName=%{public}s", name.c_str()); + HILOGI("Callback onBundleBegin, bundleName=%{public}s, errCode=%{public}d", name.c_str(), err); if (pCallbacks.expired()) { HILOGI("callbacks is unbound"); return; @@ -104,17 +111,23 @@ static void onBundleBegin(weak_ptr pCallbacks, ErrCode err, co return; } - auto cbCompl = [name {name}, errCode {err}](napi_env env, NError err) -> NVal { + ErrCode errCode = BError::GetBackupCodeByErrno(err); + std::string errMsg = BError::GetBackupMsgByErrno(errCode) + ", origin errno: " + to_string(err); + std::tuple errInfo = std::make_tuple(errCode, errMsg); + + auto cbCompl = [name {name}, errCode {err}, errInfo](napi_env env, NError err) -> NVal { NVal bundleName = NVal::CreateUTF8String(env, name); if (!err && errCode == 0) { return bundleName; } - + ErrParam errorParam = [ errInfo ]() { + return errInfo; + }; NVal res; if (err) { res = NVal {env, err.GetNapiErr(env)}; } else { - res = NVal {env, NError(errCode).GetNapiErr(env)}; + res = NVal {env, NError(errorParam).GetNapiErr(env)}; } napi_status status = napi_set_named_property(env, res.val_, FILEIO_TAG_ERR_DATA.c_str(), bundleName.val_); if (status != napi_ok) { @@ -129,7 +142,7 @@ static void onBundleBegin(weak_ptr pCallbacks, ErrCode err, co static void onBundleEnd(weak_ptr pCallbacks, ErrCode err, const BundleName name) { - HILOGI("Callback onBundleEnd, bundleName=%{public}s", name.c_str()); + HILOGI("Callback onBundleEnd, bundleName=%{public}s, errCode=%{public}d", name.c_str(), err); if (pCallbacks.expired()) { HILOGI("callbacks is unbound"); return; @@ -144,17 +157,23 @@ static void onBundleEnd(weak_ptr pCallbacks, ErrCode err, cons return; } - auto cbCompl = [name {name}, errCode {err}](napi_env env, NError err) -> NVal { + ErrCode errCode = BError::GetBackupCodeByErrno(err); + std::string errMsg = BError::GetBackupMsgByErrno(errCode) + ", origin errno: " + to_string(err); + std::tuple errInfo = std::make_tuple(errCode, errMsg); + + auto cbCompl = [name {name}, errCode {err}, errInfo](napi_env env, NError err) -> NVal { NVal bundleName = NVal::CreateUTF8String(env, name); if (!err && errCode == 0) { return bundleName; } - + ErrParam errorParam = [ errInfo ]() { + return errInfo; + }; NVal res; if (err) { res = NVal {env, err.GetNapiErr(env)}; } else { - res = NVal {env, NError(errCode).GetNapiErr(env)}; + res = NVal {env, NError(errorParam).GetNapiErr(env)}; } napi_status status = napi_set_named_property(env, res.val_, FILEIO_TAG_ERR_DATA.c_str(), bundleName.val_); if (status != napi_ok) { @@ -183,16 +202,22 @@ static void onAllBundlesEnd(weak_ptr pCallbacks, ErrCode err) return; } - auto cbCompl = [errCode {err}](napi_env env, NError err) -> NVal { + ErrCode errCode = BError::GetBackupCodeByErrno(err); + std::string errMsg = BError::GetBackupMsgByErrno(errCode) + ", origin errno: " + to_string(err); + std::tuple errInfo = std::make_tuple(errCode, errMsg); + + auto cbCompl = [errCode {err}, errInfo](napi_env env, NError err) -> NVal { if (!err && errCode == 0) { return NVal::CreateUndefined(env); } - + ErrParam errorParam = [ errInfo ]() { + return errInfo; + }; NVal res; if (err) { res = NVal {env, err.GetNapiErr(env)}; } else { - res = NVal {env, NError(errCode).GetNapiErr(env)}; + res = NVal {env, NError(errorParam).GetNapiErr(env)}; } return res; @@ -247,16 +272,77 @@ static void OnBackupServiceDied(weak_ptr pCallbacks) return; } - auto cbCompl = [](napi_env env, NError err) -> NVal { - return err ? NVal {env, err.GetNapiErr(env)} : NVal::CreateUndefined(env); + auto cbCompl = [](napi_env env, vector &argv) -> bool { + napi_value napi_res = nullptr; + napi_get_undefined(env, &napi_res); + argv.push_back(napi_res); + return true; + }; + callbacks->onBackupServiceDied.CallJsMethod(cbCompl); +} + +static void OnProcess(weak_ptr pCallbacks, const BundleName name, const std::string processInfo) +{ + HILOGI("Callback OnProcess, bundleName=%{public}s", name.c_str()); + if (pCallbacks.expired()) { + HILOGI("callbacks is unbound"); + return; + } + auto callbacks = pCallbacks.lock(); + if (!callbacks) { + HILOGI("callback function OnProcess has already been released"); + return; + } + if (!bool(callbacks->onProcess)) { + HILOGI("callback function OnProcess is undefined"); + return; + } + auto cbCompl = [bundleName {name}, process {processInfo}](napi_env env, vector &argv) -> bool { + napi_value napi_bName = nullptr; + napi_create_string_utf8(env, bundleName.c_str(), bundleName.size(), &napi_bName); + argv.push_back(napi_bName); + napi_value napi_process = nullptr; + napi_create_string_utf8(env, process.c_str(), process.size(), &napi_process); + argv.push_back(napi_process); + return true; }; + callbacks->onProcess.CallJsMethod(cbCompl); +} - callbacks->onBackupServiceDied.ThreadSafeSchedule(cbCompl); +static bool SetIncrementalBackupEntity(napi_env env, NFuncArg &funcArg, std::unique_ptr backupEntity) +{ + auto finalize = [](napi_env env, void *data, void *hint) { + std::unique_ptr entity = std::unique_ptr(static_cast(data)); + if (entity == nullptr) { + HILOGE("Entity is nullptr"); + return; + } + if (entity->callbacks == nullptr) { + HILOGE("Callbacks is nullptr"); + return; + } + entity->callbacks->RemoveCallbackRef(); + }; + if (napi_wrap(env, funcArg.GetThisVar(), backupEntity.release(), finalize, nullptr, nullptr) != napi_ok) { + HILOGE("Failed to set BackupEntity entity."); + return false; + } + return true; } napi_value SessionIncrementalBackupNExporter::Constructor(napi_env env, napi_callback_info cbinfo) { HILOGD("called SessionIncrementalBackup::Constructor begin"); + if (!SAUtils::CheckBackupPermission()) { + HILOGE("Has not permission!"); + NError(E_PERMISSION).ThrowErr(env); + return nullptr; + } + if (!SAUtils::IsSystemApp()) { + HILOGE("System App check fail!"); + NError(E_PERMISSION_SYS).ThrowErr(env); + return nullptr; + } NFuncArg funcArg(env, cbinfo); if (!funcArg.InitArgs(NARG_CNT::ONE)) { HILOGE("Number of arguments unmatched"); @@ -281,17 +367,16 @@ napi_value SessionIncrementalBackupNExporter::Constructor(napi_env env, napi_cal .onBundleFinished = bind(onBundleEnd, backupEntity->callbacks, placeholders::_1, placeholders::_2), .onAllBundlesFinished = bind(onAllBundlesEnd, backupEntity->callbacks, placeholders::_1), .onResultReport = bind(OnResultReport, backupEntity->callbacks, placeholders::_1, placeholders::_2), - .onBackupServiceDied = bind(OnBackupServiceDied, backupEntity->callbacks)}); + .onBackupServiceDied = bind(OnBackupServiceDied, backupEntity->callbacks), + .onProcess = bind(OnProcess, backupEntity->callbacks, placeholders::_1, placeholders::_2)}); if (!backupEntity->session) { NError(BError(BError::Codes::SDK_INVAL_ARG, "Failed to init backup").GetCode()).ThrowErr(env); return nullptr; } - if (!NClass::SetEntityFor(env, funcArg.GetThisVar(), move(backupEntity))) { - HILOGE("Failed to set BackupEntity entity."); + if (!SetIncrementalBackupEntity(env, funcArg, std::move(backupEntity))) { NError(BError(BError::Codes::SDK_INVAL_ARG, "Failed to set BackupEntity entity.").GetCode()).ThrowErr(env); return nullptr; } - HILOGD("called SessionIncrementalBackup::Constructor end"); return funcArg.GetThisVar(); } @@ -391,6 +476,16 @@ static bool VerifyParamSuccess(NFuncArg &funcArg, std::vector napi_value SessionIncrementalBackupNExporter::AppendBundles(napi_env env, napi_callback_info cbinfo) { HILOGD("called SessionIncrementalBackup::AppendBundles begin"); + if (!SAUtils::CheckBackupPermission()) { + HILOGE("Has not permission!"); + NError(E_PERMISSION).ThrowErr(env); + return nullptr; + } + if (!SAUtils::IsSystemApp()) { + HILOGE("System App check fail!"); + NError(E_PERMISSION_SYS).ThrowErr(env); + return nullptr; + } std::vector backupBundles; std::vector bundleInfos; NFuncArg funcArg(env, cbinfo); @@ -431,6 +526,16 @@ napi_value SessionIncrementalBackupNExporter::AppendBundles(napi_env env, napi_c napi_value SessionIncrementalBackupNExporter::Release(napi_env env, napi_callback_info cbinfo) { HILOGD("called SessionIncrementalBackup::Release begin"); + if (!SAUtils::CheckBackupPermission()) { + HILOGE("Has not permission!"); + NError(E_PERMISSION).ThrowErr(env); + return nullptr; + } + if (!SAUtils::IsSystemApp()) { + HILOGE("System App check fail!"); + NError(E_PERMISSION_SYS).ThrowErr(env); + return nullptr; + } NFuncArg funcArg(env, cbinfo); if (!funcArg.InitArgs(NARG_CNT::ZERO)) { HILOGE("Number of arguments unmatched."); diff --git a/interfaces/kits/js/backup/session_restore_n_exporter.cpp b/interfaces/kits/js/backup/session_restore_n_exporter.cpp index 71d362b8d3c33947f8ddfebf01cec256f3bea86d..b39a7c264cbf4979f95acf6322f92bd58a0b825b 100644 --- a/interfaces/kits/js/backup/session_restore_n_exporter.cpp +++ b/interfaces/kits/js/backup/session_restore_n_exporter.cpp @@ -41,10 +41,8 @@ struct RestoreEntity { shared_ptr callbacks; }; -static void OnFileReadySheet(weak_ptr pCallbacks, - const BFileInfo &fileInfo, - UniqueFd fd, - UniqueFd manifestFd, int32_t sysErrno) +static void OnFileReadySheet(weak_ptr pCallbacks, const BFileInfo &fileInfo, + UniqueFd fd, UniqueFd manifestFd, int32_t sysErrno) { if (pCallbacks.expired()) { HILOGI("callbacks is unbound"); @@ -63,8 +61,7 @@ static void OnFileReadySheet(weak_ptr pCallbacks, std::string errMsg = "system errno: " + to_string(sysErrno); std::tuple errInfo = std::make_tuple(errCode, errMsg); - auto cbCompl = [bundleName {fileInfo.owner}, - fileName {fileInfo.fileName}, + auto cbCompl = [bundleName {fileInfo.owner}, fileName {fileInfo.fileName}, fd {make_shared(fd.Release())}, manifestFd {make_shared(manifestFd.Release())}, errInfo](napi_env env, NError err) -> NVal { @@ -78,15 +75,21 @@ static void OnFileReadySheet(weak_ptr pCallbacks, }; if (std::get<0>(errInfo) != 0) { obj = NVal {env, NError(errorParam).GetNapiErr(env)}; + napi_status status = napi_set_named_property(env, obj.val_, FILEIO_TAG_ERR_DATA.c_str(), + NVal::CreateUTF8String(env, bundleName).val_); + if (status != napi_ok) { + HILOGE("Failed to set data, status %{public}d, bundleName %{public}s", status, bundleName.c_str()); + } } else { obj = NVal::CreateObject(env); + obj.AddProp({ + NVal::DeclareNapiProperty(BConstants::BUNDLE_NAME.c_str(), + NVal::CreateUTF8String(env, bundleName).val_), + NVal::DeclareNapiProperty(BConstants::URI.c_str(), NVal::CreateUTF8String(env, fileName).val_), + NVal::DeclareNapiProperty(BConstants::FD.c_str(), NVal::CreateInt32(env, fd->Release()).val_), + NVal::DeclareNapiProperty(BConstants::MANIFEST_FD.c_str(), + NVal::CreateInt32(env, manifestFd->Release()).val_)}); } - obj.AddProp({ - NVal::DeclareNapiProperty(BConstants::BUNDLE_NAME.c_str(), NVal::CreateUTF8String(env, bundleName).val_), - NVal::DeclareNapiProperty(BConstants::URI.c_str(), NVal::CreateUTF8String(env, fileName).val_), - NVal::DeclareNapiProperty(BConstants::FD.c_str(), NVal::CreateInt32(env, fd->Release()).val_), - NVal::DeclareNapiProperty(BConstants::MANIFEST_FD.c_str(), - NVal::CreateInt32(env, manifestFd->Release()).val_)}); return {obj}; }; @@ -95,7 +98,7 @@ static void OnFileReadySheet(weak_ptr pCallbacks, static void onBundleBegin(weak_ptr pCallbacks, ErrCode err, const BundleName name) { - HILOGI("Callback onBundleBegin, bundleName=%{public}s", name.c_str()); + HILOGI("Callback onBundleBegin, bundleName=%{public}s, errCode=%{public}d", name.c_str(), err); if (pCallbacks.expired()) { HILOGI("callbacks is unbound"); return; @@ -110,17 +113,23 @@ static void onBundleBegin(weak_ptr pCallbacks, ErrCode err, co return; } - auto cbCompl = [name {name}, errCode {err}](napi_env env, NError err) -> NVal { + ErrCode errCode = BError::GetBackupCodeByErrno(err); + std::string errMsg = BError::GetBackupMsgByErrno(errCode) + ", origin errno: " + to_string(err); + std::tuple errInfo = std::make_tuple(errCode, errMsg); + + auto cbCompl = [name {name}, errCode {err}, errInfo](napi_env env, NError err) -> NVal { NVal bundleName = NVal::CreateUTF8String(env, name); if (!err && errCode == 0) { return bundleName; } - + ErrParam errorParam = [ errInfo ]() { + return errInfo; + }; NVal res; if (err) { res = NVal {env, err.GetNapiErr(env)}; } else { - res = NVal {env, NError(errCode).GetNapiErr(env)}; + res = NVal {env, NError(errorParam).GetNapiErr(env)}; } napi_status status = napi_set_named_property(env, res.val_, FILEIO_TAG_ERR_DATA.c_str(), bundleName.val_); if (status != napi_ok) { @@ -135,7 +144,7 @@ static void onBundleBegin(weak_ptr pCallbacks, ErrCode err, co static void onBundleEnd(weak_ptr pCallbacks, ErrCode err, const BundleName name) { - HILOGI("Callback onBundleEnd, bundleName=%{public}s", name.c_str()); + HILOGI("Callback onBundleEnd, bundleName=%{public}s, errCode=%{public}d", name.c_str(), err); if (pCallbacks.expired()) { HILOGI("callbacks is unbound"); return; @@ -150,17 +159,23 @@ static void onBundleEnd(weak_ptr pCallbacks, ErrCode err, cons return; } - auto cbCompl = [name {name}, errCode {err}](napi_env env, NError err) -> NVal { + ErrCode errCode = BError::GetBackupCodeByErrno(err); + std::string errMsg = BError::GetBackupMsgByErrno(errCode) + ", origin errno: " + to_string(err); + std::tuple errInfo = std::make_tuple(errCode, errMsg); + + auto cbCompl = [name {name}, errCode {err}, errInfo](napi_env env, NError err) -> NVal { NVal bundleName = NVal::CreateUTF8String(env, name); if (!err && errCode == 0) { return bundleName; } - + ErrParam errorParam = [ errInfo ]() { + return errInfo; + }; NVal res; if (err) { res = NVal {env, err.GetNapiErr(env)}; } else { - res = NVal {env, NError(errCode).GetNapiErr(env)}; + res = NVal {env, NError(errorParam).GetNapiErr(env)}; } napi_status status = napi_set_named_property(env, res.val_, FILEIO_TAG_ERR_DATA.c_str(), bundleName.val_); if (status != napi_ok) { @@ -189,16 +204,22 @@ static void onAllBundlesEnd(weak_ptr pCallbacks, ErrCode err) return; } - auto cbCompl = [errCode {err}](napi_env env, NError err) -> NVal { + ErrCode errCode = BError::GetBackupCodeByErrno(err); + std::string errMsg = BError::GetBackupMsgByErrno(errCode) + ", origin errno: " + to_string(err); + std::tuple errInfo = std::make_tuple(errCode, errMsg); + + auto cbCompl = [errCode {err}, errInfo](napi_env env, NError err) -> NVal { if (!err && errCode == 0) { return NVal::CreateUndefined(env); } - + ErrParam errorParam = [ errInfo ]() { + return errInfo; + }; NVal res; if (err) { res = NVal {env, err.GetNapiErr(env)}; } else { - res = NVal {env, NError(errCode).GetNapiErr(env)}; + res = NVal {env, NError(errorParam).GetNapiErr(env)}; } return res; @@ -224,11 +245,13 @@ static void OnBackupServiceDied(weak_ptr pCallbacks) return; } - auto cbCompl = [](napi_env env, NError err) -> NVal { - return err ? NVal {env, err.GetNapiErr(env)} : NVal::CreateUndefined(env); + auto cbCompl = [](napi_env env, vector &argv) -> bool { + napi_value napi_res = nullptr; + napi_get_undefined(env, &napi_res); + argv.push_back(napi_res); + return true; }; - - callbacks->onBackupServiceDied.ThreadSafeSchedule(cbCompl); + callbacks->onBackupServiceDied.CallJsMethod(cbCompl); } static void OnResultReport(weak_ptr pCallbacks, const std::string bundleName, @@ -260,6 +283,34 @@ static void OnResultReport(weak_ptr pCallbacks, const std::str callbacks->onResultReport.CallJsMethod(cbCompl); } +static void OnProcess(weak_ptr pCallbacks, const BundleName name, const std::string processInfo) +{ + HILOGI("Callback OnProcess, bundleName=%{public}s", name.c_str()); + if (pCallbacks.expired()) { + HILOGI("callbacks is unbound"); + return; + } + auto callbacks = pCallbacks.lock(); + if (!callbacks) { + HILOGI("callback function OnProcess has already been released"); + return; + } + if (!bool(callbacks->onProcess)) { + HILOGI("callback function OnProcess is undefined"); + return; + } + auto cbCompl = [bundleName {name}, process {processInfo}](napi_env env, vector &argv) -> bool { + napi_value napi_bName = nullptr; + napi_create_string_utf8(env, bundleName.c_str(), bundleName.size(), &napi_bName); + argv.push_back(napi_bName); + napi_value napi_process = nullptr; + napi_create_string_utf8(env, process.c_str(), process.size(), &napi_process); + argv.push_back(napi_process); + return true; + }; + callbacks->onProcess.CallJsMethod(cbCompl); +} + static bool VerifyAppendBundlesParam(NFuncArg &funcArg, int32_t &fd, std::vector &bundleNames, std::vector &bundleInfos, napi_env env) { @@ -358,6 +409,7 @@ static bool VerifyNapiObject(napi_env env, NFuncArg &funcArg) } return false; } + static bool VerifyNarg(napi_env env, NVal &callbacks) { if (!callbacks.TypeIs(napi_object)) { @@ -368,9 +420,40 @@ static bool VerifyNarg(napi_env env, NVal &callbacks) return false; } +static bool SetSessionRestoreEntity(napi_env env, NFuncArg &funcArg, std::unique_ptr restoreEntity) +{ + auto finalize = [](napi_env env, void *data, void *hint) { + std::unique_ptr entity = std::unique_ptr(static_cast(data)); + if (entity == nullptr) { + HILOGE("Entity is nullptr"); + return; + } + if (entity->callbacks == nullptr) { + HILOGE("Callbacks is nullptr"); + return; + } + entity->callbacks->RemoveCallbackRef(); + }; + if (napi_wrap(env, funcArg.GetThisVar(), restoreEntity.release(), finalize, nullptr, nullptr) != napi_ok) { + HILOGE("Failed to set restoreEntity entity."); + return false; + } + return true; +} + napi_value SessionRestoreNExporter::Constructor(napi_env env, napi_callback_info cbinfo) { HILOGI("called SessionRestore::Constructor begin"); + if (!SAUtils::CheckBackupPermission()) { + HILOGE("Has not permission!"); + NError(E_PERMISSION).ThrowErr(env); + return nullptr; + } + if (!SAUtils::IsSystemApp()) { + HILOGE("System App check fail!"); + NError(E_PERMISSION_SYS).ThrowErr(env); + return nullptr; + } NFuncArg funcArg(env, cbinfo); if (VerifyNapiObject(env, funcArg)) { return nullptr; @@ -391,37 +474,30 @@ napi_value SessionRestoreNExporter::Constructor(napi_env env, napi_callback_info .onBundleFinished = bind(onBundleEnd, restoreEntity->callbacks, placeholders::_1, placeholders::_2), .onAllBundlesFinished = bind(onAllBundlesEnd, restoreEntity->callbacks, placeholders::_1), .onResultReport = bind(OnResultReport, restoreEntity->callbacks, placeholders::_1, placeholders::_2), - .onBackupServiceDied = bind(OnBackupServiceDied, restoreEntity->callbacks)}); + .onBackupServiceDied = bind(OnBackupServiceDied, restoreEntity->callbacks), + .onProcess = bind(OnProcess, restoreEntity->callbacks, placeholders::_1, placeholders::_2)}); if (!restoreEntity->sessionSheet) { NError(BError(BError::Codes::SDK_INVAL_ARG, "Failed to init restore").GetCode()).ThrowErr(env); return nullptr; } - if (!NClass::SetEntityFor(env, funcArg.GetThisVar(), move(restoreEntity))) { + if (!SetSessionRestoreEntity(env, funcArg, std::move(restoreEntity))) { NError(BError(BError::Codes::SDK_INVAL_ARG, "Failed to set SessionRestore entity.").GetCode()).ThrowErr(env); return nullptr; } - HILOGI("called SessionRestore::Constructor end"); return funcArg.GetThisVar(); } -napi_value SessionRestoreNExporter::AppendBundles(napi_env env, napi_callback_info cbinfo) +static NContextCBExec GetAppendBundlesCBExec(napi_env env, NFuncArg &funcArg, const int32_t fdRestore, + const std::vector &bundleNames, const std::vector &bundleInfos) { - HILOGI("called SessionRestore::AppendBundles begin"); - int32_t fdRestore = BConstants::INVALID_FD_NUM; - std::vector bundleNames; - std::vector bundleInfos; - NFuncArg funcArg(env, cbinfo); - if (!VerifyAppendBundlesParam(funcArg, fdRestore, bundleNames, bundleInfos, env)) { - return nullptr; - } auto restoreEntity = NClass::GetEntityOf(env, funcArg.GetThisVar()); if (!(restoreEntity && (restoreEntity->sessionWhole || restoreEntity->sessionSheet))) { HILOGE("Failed to get RestoreSession entity."); NError(BError(BError::Codes::SDK_INVAL_ARG, "Failed to get RestoreSession entity.").GetCode()).ThrowErr(env); return nullptr; } - auto cbExec = [entity {restoreEntity}, fd {fdRestore}, bundles {bundleNames}, infos {bundleInfos}]() -> NError { + return [entity {restoreEntity}, fd {fdRestore}, bundles {bundleNames}, infos {bundleInfos}]() -> NError { if (!(entity && (entity->sessionWhole || entity->sessionSheet))) { return NError(BError(BError::Codes::SDK_INVAL_ARG, "restore session is nullptr").GetCode()); } @@ -440,10 +516,38 @@ napi_value SessionRestoreNExporter::AppendBundles(napi_env env, napi_callback_in } return NError(entity->sessionSheet->AppendBundles(UniqueFd(fd), bundles)); }; +} + +napi_value SessionRestoreNExporter::AppendBundles(napi_env env, napi_callback_info cbinfo) +{ + HILOGI("called SessionRestore::AppendBundles begin"); + if (!SAUtils::CheckBackupPermission()) { + HILOGE("Has not permission!"); + NError(E_PERMISSION).ThrowErr(env); + return nullptr; + } + if (!SAUtils::IsSystemApp()) { + HILOGE("System App check fail!"); + NError(E_PERMISSION_SYS).ThrowErr(env); + return nullptr; + } + int32_t fdRestore = BConstants::INVALID_FD_NUM; + std::vector bundleNames; + std::vector bundleInfos; + NFuncArg funcArg(env, cbinfo); + if (!VerifyAppendBundlesParam(funcArg, fdRestore, bundleNames, bundleInfos, env)) { + return nullptr; + } + auto cbExec = GetAppendBundlesCBExec(env, funcArg, fdRestore, bundleNames, bundleInfos); + if (cbExec == nullptr) { + HILOGE("GetAppendBundlesCBExec fail!"); + return nullptr; + } auto cbCompl = [](napi_env env, NError err) -> NVal { return err ? NVal {env, err.GetNapiErr(env)} : NVal::CreateUndefined(env); }; HILOGD("Called SessionRestore::AppendBundles end."); + NVal thisVar(env, funcArg.GetThisVar()); if (funcArg.GetArgc() == NARG_CNT::TWO) { return NAsyncWorkPromise(env, thisVar).Schedule(className, cbExec, cbCompl).val_; @@ -457,24 +561,16 @@ napi_value SessionRestoreNExporter::AppendBundles(napi_env env, napi_callback_in } } -napi_value SessionRestoreNExporter::PublishFile(napi_env env, napi_callback_info cbinfo) +static NContextCBExec GetPublishFileCBExec(napi_env env, NFuncArg &funcArg, const std::string &bundleName, + const std::string &fileName) { - HILOGD("called SessionRestore::PublishFile begin"); - std::string bundleName; - std::string fileName; - NFuncArg funcArg(env, cbinfo); - if (!VerifyPublishFileParam(funcArg, bundleName, fileName, env)) { - return nullptr; - } - auto restoreEntity = NClass::GetEntityOf(env, funcArg.GetThisVar()); if (!(restoreEntity && (restoreEntity->sessionWhole || restoreEntity->sessionSheet))) { HILOGE("Failed to get RestoreSession entity."); NError(BError(BError::Codes::SDK_INVAL_ARG, "Failed to get RestoreSession entity.").GetCode()).ThrowErr(env); return nullptr; } - - auto cbExec = [entity {restoreEntity}, bundleName {bundleName}, fileName {fileName}]() -> NError { + return [entity {restoreEntity}, bundleName {bundleName}, fileName {fileName}]() -> NError { if (!(entity && (entity->sessionWhole || entity->sessionSheet))) { return NError(BError(BError::Codes::SDK_INVAL_ARG, "restore session is nullptr").GetCode()); } @@ -485,17 +581,42 @@ napi_value SessionRestoreNExporter::PublishFile(napi_env env, napi_callback_info if (SAUtils::IsSABundleName(fileName)) { HILOGI("SA %{public}s pushlish file", bundleName.c_str()); if (fcntl(std::atoi(fileName.c_str()), F_GETFD) == -1) { - HILOGE("PublishFile fd is invalid."); - return NError(BError(BError::Codes::SDK_INVAL_ARG, "PublishFile fd is invalid.").GetCode()); - } + HILOGE("PublishFile fd is invalid."); + return NError(BError(BError::Codes::SDK_INVAL_ARG, "PublishFile fd is invalid.").GetCode()); + } return NError(entity->sessionSheet->PublishSAFile(fileInfo, UniqueFd(std::atoi(fileName.c_str())))); } return NError(entity->sessionSheet->PublishFile(fileInfo)); }; +} + +napi_value SessionRestoreNExporter::PublishFile(napi_env env, napi_callback_info cbinfo) +{ + HILOGD("called SessionRestore::PublishFile begin"); + if (!SAUtils::CheckBackupPermission()) { + HILOGE("Has not permission!"); + NError(E_PERMISSION).ThrowErr(env); + return nullptr; + } + if (!SAUtils::IsSystemApp()) { + HILOGE("System App check fail!"); + NError(E_PERMISSION_SYS).ThrowErr(env); + return nullptr; + } + std::string bundleName; + std::string fileName; + NFuncArg funcArg(env, cbinfo); + if (!VerifyPublishFileParam(funcArg, bundleName, fileName, env)) { + return nullptr; + } + auto cbExec = GetPublishFileCBExec(env, funcArg, bundleName, fileName); + if (cbExec == nullptr) { + HILOGE("GetPublishFileCBExec fail!"); + return nullptr; + } auto cbCompl = [](napi_env env, NError err) -> NVal { return err ? NVal {env, err.GetNapiErr(env)} : NVal::CreateUndefined(env); }; - HILOGD("Called SessionRestore::PublishFile end."); NVal thisVar(env, funcArg.GetThisVar()); @@ -507,9 +628,42 @@ napi_value SessionRestoreNExporter::PublishFile(napi_env env, napi_callback_info } } +static NContextCBExec GetFileHandleCBExec(napi_env env, NFuncArg &funcArg, std::unique_ptr bundleName, + std::unique_ptr fileName) +{ + auto restoreEntity = NClass::GetEntityOf(env, funcArg.GetThisVar()); + if (!(restoreEntity && (restoreEntity->sessionWhole || restoreEntity->sessionSheet))) { + HILOGE("Failed to get RestoreSession entity."); + NError(BError(BError::Codes::SDK_INVAL_ARG, "Failed to get RestoreSession entity.").GetCode()).ThrowErr(env); + return nullptr; + } + return [entity {restoreEntity}, bundleName {string(bundleName.get())}, + fileName {string(fileName.get())}]() -> NError { + if (!(entity && (entity->sessionWhole || entity->sessionSheet))) { + return NError(BError(BError::Codes::SDK_INVAL_ARG, "restore session is nullptr").GetCode()); + } + string bundle = bundleName; + string file = fileName; + if (entity->sessionWhole) { + return NError(entity->sessionWhole->GetFileHandle(bundle, file)); + } + return NError(entity->sessionSheet->GetFileHandle(bundle, file)); + }; +} + napi_value SessionRestoreNExporter::GetFileHandle(napi_env env, napi_callback_info cbinfo) { HILOGD("called SessionRestore::GetFileHandle begin"); + if (!SAUtils::CheckBackupPermission()) { + HILOGE("Has not permission!"); + NError(E_PERMISSION).ThrowErr(env); + return nullptr; + } + if (!SAUtils::IsSystemApp()) { + HILOGE("System App check fail!"); + NError(E_PERMISSION_SYS).ThrowErr(env); + return nullptr; + } NFuncArg funcArg(env, cbinfo); if (!funcArg.InitArgs(NARG_CNT::ONE, NARG_CNT::TWO)) { HILOGE("Number of arguments unmatched."); @@ -531,29 +685,14 @@ napi_value SessionRestoreNExporter::GetFileHandle(napi_env env, napi_callback_in return nullptr; } - auto restoreEntity = NClass::GetEntityOf(env, funcArg.GetThisVar()); - if (!(restoreEntity && (restoreEntity->sessionWhole || restoreEntity->sessionSheet))) { - HILOGE("Failed to get RestoreSession entity."); - NError(BError(BError::Codes::SDK_INVAL_ARG, "Failed to get RestoreSession entity.").GetCode()).ThrowErr(env); + auto cbExec = GetFileHandleCBExec(env, funcArg, move(bundleName), move(fileName)); + if (cbExec == nullptr) { + HILOGE("GetFileHandleCBExec fail!"); return nullptr; } - - auto cbExec = [entity {restoreEntity}, bundleName {string(bundleName.get())}, - fileName {string(fileName.get())}]() -> NError { - if (!(entity && (entity->sessionWhole || entity->sessionSheet))) { - return NError(BError(BError::Codes::SDK_INVAL_ARG, "restore session is nullptr").GetCode()); - } - string bundle = bundleName; - string file = fileName; - if (entity->sessionWhole) { - return NError(entity->sessionWhole->GetFileHandle(bundle, file)); - } - return NError(entity->sessionSheet->GetFileHandle(bundle, file)); - }; auto cbCompl = [](napi_env env, NError err) -> NVal { return err ? NVal {env, err.GetNapiErr(env)} : NVal::CreateUndefined(env); }; - HILOGD("Called SessionRestore::GetFileHandle end."); NVal thisVar(env, funcArg.GetThisVar()); @@ -568,6 +707,16 @@ napi_value SessionRestoreNExporter::GetFileHandle(napi_env env, napi_callback_in napi_value SessionRestoreNExporter::Release(napi_env env, napi_callback_info cbinfo) { HILOGI("called SessionRestore::Release begin"); + if (!SAUtils::CheckBackupPermission()) { + HILOGE("Has not permission!"); + NError(E_PERMISSION).ThrowErr(env); + return nullptr; + } + if (!SAUtils::IsSystemApp()) { + HILOGE("System App check fail!"); + NError(E_PERMISSION_SYS).ThrowErr(env); + return nullptr; + } NFuncArg funcArg(env, cbinfo); if (!funcArg.InitArgs(NARG_CNT::ZERO)) { HILOGE("Number of arguments unmatched."); @@ -594,7 +743,6 @@ napi_value SessionRestoreNExporter::Release(napi_env env, napi_callback_info cbi auto cbCompl = [](napi_env env, NError err) -> NVal { return err ? NVal {env, err.GetNapiErr(env)} : NVal::CreateUndefined(env); }; - HILOGI("Called SessionRestore::Release end."); NVal thisVar(env, funcArg.GetThisVar()); diff --git a/interfaces/kits/ndk/fileuri/include/oh_file_uri.h b/interfaces/kits/ndk/fileuri/include/oh_file_uri.h index b1e3177c836f0d865c1bf309445629e0bdf1032c..633f00817cd74f1d6e176fe75aa04ef044ad1534 100644 --- a/interfaces/kits/ndk/fileuri/include/oh_file_uri.h +++ b/interfaces/kits/ndk/fileuri/include/oh_file_uri.h @@ -77,6 +77,18 @@ FileManagement_ErrCode OH_FileUri_GetFullDirectoryUri(const char *uri, unsigned * @since 12 */ bool OH_FileUri_IsValidUri(const char *uri, unsigned int length); + +/** +* @brief Gets the fileName From uri. +* +* @param uri Input a pointer to the uri string. +* @param length The length of the input uri. +* @param result Output a pointer to a FileName string or FolderName string. Please use free() to clear the resource. +* @return Returns the status code of the execution. +* @syscap SystemCapability.FileManagement.AppFileService +* @since 13 + */ +FileManagement_ErrCode OH_FileUri_GetFileName(const char *uri, unsigned int length, char **result); #ifdef __cplusplus }; #endif diff --git a/interfaces/kits/ndk/fileuri/liboh_file_uir.ndk.json b/interfaces/kits/ndk/fileuri/liboh_file_uir.ndk.json index 776c160a844e043392cb6a6d33d84b72bccfcac1..d17efcd7a88cd6634ea7d1386c839c25529a977c 100644 --- a/interfaces/kits/ndk/fileuri/liboh_file_uir.ndk.json +++ b/interfaces/kits/ndk/fileuri/liboh_file_uir.ndk.json @@ -13,5 +13,9 @@ { "first_introduced": "12", "name":"OH_FileUri_IsValidUri" + }, + { + "first_introduced": "13", + "name":"OH_FileUri_GetFileName" } ] \ No newline at end of file diff --git a/interfaces/kits/ndk/fileuri/src/oh_file_uri.cpp b/interfaces/kits/ndk/fileuri/src/oh_file_uri.cpp index db175595eff1a8c27f5684fc99e3797c21da34b4..0686bb95df09f9a9ef3ba5d97b9ac888a67479d5 100644 --- a/interfaces/kits/ndk/fileuri/src/oh_file_uri.cpp +++ b/interfaces/kits/ndk/fileuri/src/oh_file_uri.cpp @@ -30,7 +30,7 @@ static FileManagement_ErrCode GetValue(std::string_view resultStr, char **result } if (count > OHOS::FileManagement::Backup::BConstants::PARAM_STARING_MAX_MEMORY) { LOGE("The param resultStr is too big"); - return ERR_UNKNOWN; + return ERR_PARAMS; } *result = static_cast(malloc(sizeof(char) * (count + 1))); if (*result == nullptr) { @@ -84,9 +84,24 @@ FileManagement_ErrCode OH_FileUri_GetFullDirectoryUri(const char *uri, unsigned bool OH_FileUri_IsValidUri(const char *uri, unsigned int length) { if (uri == nullptr || strlen(uri) != length) { - return ERR_PARAMS; + return false; } std::string uriStr(uri, length); OHOS::AppFileService::ModuleFileUri::FileUri fileUri(uriStr); return fileUri.CheckUriFormat(uriStr); -} \ No newline at end of file +} + +FileManagement_ErrCode OH_FileUri_GetFileName(const char *uri, unsigned int length, char **result) +{ + if (uri == nullptr || strlen(uri) != length || result == nullptr) { + return ERR_PARAMS; + } + std::string uriStr(uri, length); + OHOS::AppFileService::ModuleFileUri::FileUri fileUri(uriStr); + std::string resultStr = fileUri.GetName(); + size_t count = resultStr.length(); + if (count == 0) { + return ERR_PARAMS; + } + return GetValue(resultStr, result); +} diff --git a/services/5203.json b/services/5203.json index a38a55395fbb8eaa757307132fa566256b2f6476..e0662dff60da0e420b4b71176959bd2a92126282 100644 --- a/services/5203.json +++ b/services/5203.json @@ -5,12 +5,13 @@ "name": 5203, "libpath": "libbackup_sa.z.so", "run-on-create": false, + "auto-restart": true, "distributed": false, "dump_level": 1, "start-on-demand": { "commonevent": [ { - "name": "usual.event.BOOT_COMPLETED", + "name": "usual.event.USER_UNLOCKED", "conditions": [ { "eventId": "param", diff --git a/services/backup_sa/BUILD.gn b/services/backup_sa/BUILD.gn index 5bf8af4f0b7e9cbf0969c91096f98810ece90515..6425090912e4cfb837673e77f7e456e9abd16da7 100644 --- a/services/backup_sa/BUILD.gn +++ b/services/backup_sa/BUILD.gn @@ -36,6 +36,7 @@ ohos_shared_library("backup_sa") { "src/module_ipc/service_incremental_reverse_proxy.cpp", "src/module_ipc/service_reverse_proxy.cpp", "src/module_ipc/service_stub.cpp", + "src/module_ipc/sub_service.cpp", "src/module_ipc/svc_backup_connection.cpp", "src/module_ipc/svc_extension_incremental_proxy.cpp", "src/module_ipc/svc_extension_proxy.cpp", @@ -63,9 +64,9 @@ ohos_shared_library("backup_sa") { external_deps = [ "ability_base:want", - "ability_runtime:ability_connect_callback_stub", "ability_runtime:ability_manager", "access_token:libaccesstoken_sdk", + "access_token:libtokenid_sdk", "bundle_framework:appexecfwk_base", "bundle_framework:appexecfwk_core", "c_utils:utils", diff --git a/services/backup_sa/include/module_app_gallery/app_gallery_service_connection.h b/services/backup_sa/include/module_app_gallery/app_gallery_service_connection.h index 21a710a0e3e399ffc2bff8c20a80210b8e072b19..c5a06b7fc6f6c89d60e8ab65c85a19a7afbc42f9 100644 --- a/services/backup_sa/include/module_app_gallery/app_gallery_service_connection.h +++ b/services/backup_sa/include/module_app_gallery/app_gallery_service_connection.h @@ -60,7 +60,7 @@ template bool ConnectExtAbility() } auto appGalleryBundleName = BundleMgrAdapter::GetAppGalleryBundleName(); - if (!appGalleryBundleName.c_str()) { + if (appGalleryBundleName.empty()) { HILOGI("ConnectExtAbility GetAppGalleryBundleName failed"); return false; } diff --git a/services/backup_sa/include/module_external/bms_adapter.h b/services/backup_sa/include/module_external/bms_adapter.h index 5f106294c5aaaa772ef420eb703849c2eb79ca28..5f2dc4497e4aff076e5ab2c43a89c1f16a23dded 100644 --- a/services/backup_sa/include/module_external/bms_adapter.h +++ b/services/backup_sa/include/module_external/bms_adapter.h @@ -58,11 +58,22 @@ public: static std::vector GetBundleInfosForIncremental(int32_t userId, const std::vector &extraIncreData = {}); + static std::vector GetFullBundleInfos(int32_t userId); + static std::string GetExtName(string bundleName, int32_t userId); static std::vector GetBundleInfosForSA(); static void GetBundleInfoForSA(std::string bundleName, std::vector &bundleInfos); + + static bool IsUser0BundleName(std::string bundleName, int32_t userId); + + static std::vector GetBundleInfosForAppend( + const std::vector &incrementalDataList, int32_t userId); +private: + static bool GetCurBundleExtenionInfo(AppExecFwk::BundleInfo &installedBundle, const std::string &bundleName, + std::vector &extensionInfos, sptr bms, + int32_t userId); }; } // namespace OHOS::FileManagement::Backup #endif // OHOS_FILEMGMT_BACKUP_BUNDLE_MGR_ADAPTER_H diff --git a/services/backup_sa/include/module_ipc/service.h b/services/backup_sa/include/module_ipc/service.h index 7f81017326ff54077016134af12535c32b098248..2194834f4d3b4b226759075b2d0c5df47ef6b7d0 100644 --- a/services/backup_sa/include/module_ipc/service.h +++ b/services/backup_sa/include/module_ipc/service.h @@ -20,6 +20,7 @@ #include #include "b_jsonutil/b_jsonutil.h" +#include "b_json/b_json_clear_data_config.h" #include "b_json/b_json_entity_caps.h" #include "b_json/b_json_service_disposal_config.h" #include "i_service_reverse.h" @@ -31,6 +32,17 @@ #include "thread_pool.h" namespace OHOS::FileManagement::Backup { +struct ExtensionMutexInfo { + std::string bundleName; + std::mutex callbackMutex; + ExtensionMutexInfo(std::string bundleName_) : bundleName(bundleName_) {}; +}; + +struct BundleTaskInfo { + std::string reportTime; + ErrCode errCode; +}; + class Service : public SystemAbility, public ServiceStub, protected NoCopyable { DECLARE_SYSTEM_ABILITY(Service); @@ -75,8 +87,11 @@ public: ErrCode AppIncrementalDone(ErrCode errCode) override; ErrCode GetIncrementalFileHandle(const std::string &bundleName, const std::string &fileName) override; ErrCode GetBackupInfo(BundleName &bundleName, std::string &result) override; - ErrCode UpdateTimer(BundleName &bundleName, uint32_t timeOut, bool &result) override; + ErrCode UpdateTimer(BundleName &bundleName, uint32_t timeout, bool &result) override; ErrCode UpdateSendRate(std::string &bundleName, int32_t sendRate, bool &result) override; + ErrCode ReportAppProcessInfo(const std::string processInfo, const BackupRestoreScenario sennario) override; + ErrCode StartExtTimer(bool &isExtStart) override; + ErrCode StartFwkTimer(bool &isFwkStart) override; ErrCode SAResultReport(const std::string bundleName, const std::string resultInfo, const ErrCode errCode, const BackupRestoreScenario sennario); @@ -110,7 +125,7 @@ public: * * @param bundleName 应用名称 */ - void OnBackupExtensionDied(const std::string &&bundleName); + void OnBackupExtensionDied(const std::string &&bundleName, bool isSecondCalled = false); /** * @brief extension启动连接成功 @@ -168,11 +183,20 @@ public: */ void DeleteDisConfigFile(); + /** + * @brief 尝试清理处置 + * + * @param bundleName 应用名称 + * + */ + void TryToClearDispose(const BundleName &bundleName); + /** * @brief 结束会话删除session,卸载服务 * */ void SessionDeactive(); + /** * @brief 构造拉起应用所需的want * @@ -218,14 +242,73 @@ public: * @param bundleName 应用名称 * */ - std::function GetBackupInfoConnectDied(wptr obj, std::string &bundleName); + std::function GetBackupInfoConnectDied( + wptr obj, std::string &bundleName); + + /** + * @brief timeout callback + * + * @param ptr 当前对象 + * @param bundleName 应用名称 + */ + std::function TimeOutCallback(wptr ptr, std::string bundleName); + + /** + * @brief do timeout + * + * @param ptr 当前对象 + * @param bundleName 应用名称 + */ + void DoTimeout(wptr ptr, std::string bundleName); + + /** + * @brief 清理残留数据 + * + * @param bundleName 应用名称 + * + */ + ErrCode ClearResidualBundleData(const std::string &bundleName); + /** + * @brief 添加清理记录 + * + * @param bundleName 应用名称 + * + */ + void AddClearBundleRecord(const std::string &bundleName); + + /** + * @brief 删除清理记录 + * + * @param bundleName 应用名称 + * + */ + void DelClearBundleRecord(const std::vector &bundleNames); + + /** + * @brief 获取extension锁 + * + * @param bundleName 应用名称 + * + */ + std::shared_ptr GetExtensionMutex(const BundleName &bundleName); + + /** + * @brief 清理extension锁 + * + * @param bundleName 应用名称 + * + */ + void RemoveExtensionMutex(const BundleName &bundleName); + void StartRunningTimer(const std::string &bundleName); public: explicit Service(int32_t saID, bool runOnCreate = false) : SystemAbility(saID, runOnCreate) { threadPool_.Start(BConstants::EXTENSION_THREAD_POOL_COUNT); session_ = sptr(new SvcSessionManager(wptr(this))); disposal_ = make_shared(); + clearRecorder_ = make_shared(); + sched_ = sptr(new SchedScheduler(wptr(this), wptr(session_))); }; ~Service() override { @@ -311,12 +394,47 @@ private: * @param restoreBundleInfos 待恢复的应用 * @param restoreBundleNames 待恢复的应用包信息 * @param bundleNameDetailMap bundle和detail的对应关系 + * @param isClearDataFlags 清理数据标志集合 * @param restoreType 任务类型 */ void SetCurrentSessProperties(std::vector &restoreBundleInfos, std::vector &restoreBundleNames, std::map> &bundleNameDetailMap, - RestoreTypeEnum restoreType); + std::map &isClearDataFlags, RestoreTypeEnum restoreType); + + /** + * @brief set session info + * + * @param restoreBundleInfos: bundles to be restored + * @param restoreBundleNames: bundles info to be restored + * @param restoreType: retore type + */ + void SetCurrentSessProperties(std::vector &restoreBundleInfos, + std::vector &restoreBundleNames, RestoreTypeEnum restoreType); + + void SetCurrentSessProperties(BJsonEntityCaps::BundleInfo &info, std::map &isClearDataFlags, + const std::string &bundleNameIndexInfo); + + /** + * @brief add useridinfo to current backup session + * + * @param bundleNames: bundleNames list + * @param userId: userId + * @param backupBundleInfos: backupBundleInfos + * @param isIncBackup: isIncBackup + * + */ + void SetCurrentBackupSessProperties(const std::vector &bundleNames, int32_t userId, + std::vector &backupBundleInfos, bool isIncBackup); + + /** + * @brief send userid to app + * + * @param bundleName: bundleName + * @param userId: userId + * + */ + void SendUserIdToApp(std::string &bundleName, int32_t userId); /** * @brief 通知权限模块 @@ -324,7 +442,7 @@ private: * @param bundleName 包名称 * */ - void NotifyCloneBundleFinish(std::string bundleName); + void NotifyCloneBundleFinish(std::string bundleName, const BackupRestoreScenario sennario); /** * @brief SA 备份恢复结束 @@ -362,21 +480,99 @@ private: */ void NotifyCallerCurAppIncrementDone(ErrCode errCode, const std::string &callerName); + void SetWant(AAFwk::Want &want, const BundleName &bundleName, const BConstants::ExtensionAction &action); + + /** + * @brief GetBackupInfo 任务执行 + * + * @param bundleName 应用名称 + * @param result 业务结果出参 + * + */ + ErrCode GetBackupInfoCmdHandle(BundleName &bundleName, std::string &result); + + /** + * @brief 添加需要清理的Session + * + * @param bundleNames 需要清理的应用包信息 + * + */ + ErrCode AppendBundlesClearSession(const std::vector &bundleNames); + + void ReportOnExtConnectFailed(const IServiceReverse::Scenario scenario, + const std::string &bundleName, const ErrCode ret); + + void ReleaseOnException(); + + vector MakeDetailList(const vector &bundleNames); + + vector GetBundleNameByDetails(const std::vector &bundlesToBackup); + + void HandleCurGroupBackupInfos(vector &bundleInfos, + std::map> &bundleNameDetailMap, + std::map &isClearDataFlags); + + void HandleCurGroupIncBackupInfos(vector &bundleInfos, + std::map> &bundleNameDetailMap, + std::map &isClearDataFlags); + + void TimeoutRadarReport(IServiceReverse::Scenario scenario, std::string &bundleName); + + void CreateDirIfNotExist(const std::string &path); + + void OnBundleStarted(BError error, sptr session, const BundleName &bundleName); + + void HandleExceptionOnAppendBundles(sptr session, const vector &appendBundleNames, + const vector &restoreBundleNames); + + void BundleBeginRadarReport(const std::string &bundleName, const ErrCode errCode, + const IServiceReverse::Scenario scenario); + + void BundleEndRadarReport(const std::string &bundleName, const ErrCode errCode, + const IServiceReverse::Scenario scenario); + + void FileReadyRadarReport(const std::string &bundleName, const std::string &fileName, const ErrCode errCode, + const IServiceReverse::Scenario scenario); + + void ExtensionConnectFailRadarReport(const std::string &bundleName, const ErrCode errCode, + const IServiceReverse::Scenario scenario); + + void UpdateFailedBundles(const std::string &bundleName, BundleTaskInfo taskInfo); + + void ClearFailedBundles(); + std::vector GetSupportBackupBundleNames(vector &bundleInfos, + bool isIncBackup, const vector &srcBundleNames); + + void HandleNotSupportBundleNames(const std::vector &srcBundleNames, + std::vector &supportBundleNames, bool isIncBackup); + + void SetBundleIncDataInfo(const std::vector &bundlesToBackup, + std::vector &supportBundleNames); private: static sptr instance_; static std::mutex instanceLock_; - std::mutex getBackupInfoMutx_; + std::mutex getBackupInfoProcLock_; + std::mutex getBackupInfoSyncLock_; std::condition_variable getBackupInfoCondition_; static inline std::atomic seed {1}; std::atomic isConnectDied_ {false}; + std::atomic isCleanService_ {false}; sptr session_; sptr sched_; std::shared_ptr disposal_; - + std::shared_ptr clearRecorder_; + std::atomic isInRelease_ {false}; + std::atomic isRmConfigFile_ {true}; friend class ServiceTest; OHOS::ThreadPool threadPool_; + std::mutex extensionMutexLock_; + std::mutex failedBundlesLock_; +public: + std::map> backupExtMutexMap_; + std::map failedBundles_; + std::atomic successBundlesNum_ {0}; }; } // namespace OHOS::FileManagement::Backup diff --git a/services/backup_sa/include/module_ipc/service_reverse_proxy.h b/services/backup_sa/include/module_ipc/service_reverse_proxy.h index 43d4e13bb459722e5e5c129537270b5f245ccc40..3e6667d8d2164de1810494a428131faabc668b52 100644 --- a/services/backup_sa/include/module_ipc/service_reverse_proxy.h +++ b/services/backup_sa/include/module_ipc/service_reverse_proxy.h @@ -27,6 +27,7 @@ public: void BackupOnResultReport(std::string result, std::string bundleName) override; void BackupOnBundleFinished(int32_t errCode, std::string bundleName) override; void BackupOnAllBundlesFinished(int32_t errCode) override; + void BackupOnProcessInfo(std::string bundleName, std::string processInfo) override; void RestoreOnBundleStarted(int32_t errCode, std::string bundleName) override; void RestoreOnFileReady(std::string bundleName, std::string fileName, int fd, int32_t errCode) override; @@ -34,6 +35,7 @@ public: ErrCode errCode = 0) override; void RestoreOnBundleFinished(int32_t errCode, std::string bundleName) override; void RestoreOnAllBundlesFinished(int32_t errCode) override; + void RestoreOnProcessInfo(std::string bundleName, std::string processInfo) override; void IncrementalBackupOnBundleStarted(int32_t errCode, std::string bundleName) override; void IncrementalBackupOnFileReady(std::string bundleName, std::string fileName, int fd, int manifestFd, @@ -41,6 +43,7 @@ public: void IncrementalBackupOnResultReport(std::string result, std::string bundleName) override; void IncrementalBackupOnBundleFinished(int32_t errCode, std::string bundleName) override; void IncrementalBackupOnAllBundlesFinished(int32_t errCode) override; + void IncrementalBackupOnProcessInfo(std::string bundleName, std::string processInfo) override; void IncrementalRestoreOnBundleStarted(int32_t errCode, std::string bundleName) override; void IncrementalRestoreOnFileReady(std::string bundleName, std::string fileName, int fd, int manifestFd, @@ -49,6 +52,7 @@ public: ErrCode errCode = 0) override; void IncrementalRestoreOnBundleFinished(int32_t errCode, std::string bundleName) override; void IncrementalRestoreOnAllBundlesFinished(int32_t errCode) override; + void IncrementalRestoreOnProcessInfo(std::string bundleName, std::string processInfo) override; public: explicit ServiceReverseProxy(const sptr &impl) : IRemoteProxy(impl) {} diff --git a/services/backup_sa/include/module_ipc/service_stub.h b/services/backup_sa/include/module_ipc/service_stub.h index bd40fdd1ea400b1baa92db978454e426720eb89b..5aeba27525c9cade76a2d09643be1ae2e392825b 100644 --- a/services/backup_sa/include/module_ipc/service_stub.h +++ b/services/backup_sa/include/module_ipc/service_stub.h @@ -62,6 +62,9 @@ private: int32_t CmdGetBackupInfo(MessageParcel &data, MessageParcel &reply); int32_t CmdUpdateTimer(MessageParcel &data, MessageParcel &reply); int32_t CmdUpdateSendRate(MessageParcel &data, MessageParcel &reply); + int32_t CmdReportAppProcessInfo(MessageParcel &data, MessageParcel &reply); + int32_t CmdStartExtTimer(MessageParcel &data, MessageParcel &reply); + int32_t CmdStartFwkTimer(MessageParcel &data, MessageParcel &reply); void ServiceStubSupplement(); void ServiceStubSuppAppendBundles(); diff --git a/services/backup_sa/include/module_ipc/svc_backup_connection.h b/services/backup_sa/include/module_ipc/svc_backup_connection.h index 379721abd3dbbb7b6608f5ba3a51aeda5f1fb8d7..abff875c648e807e66e65c98c17ef2901f580052 100644 --- a/services/backup_sa/include/module_ipc/svc_backup_connection.h +++ b/services/backup_sa/include/module_ipc/svc_backup_connection.h @@ -76,31 +76,41 @@ public: * @param callConnected */ void SetCallback(std::function callConnected); - + /** * @brief Set the CallDied object * * @param callDied */ - void SetCallDied(std::function callDied); + void SetCallDied(std::function callDied); + + /** + * @brief wait disconnect done + */ + bool WaitDisconnectDone(); public: - SvcBackupConnection(std::function callDied, - std::function callConnected) - : callDied_(callDied), callConnected_(callConnected) + SvcBackupConnection(std::function callDied, + std::function callConnected, + std::string bundleNameIndexInfo) + : callDied_(callDied), callConnected_(callConnected), bundleNameIndexInfo_(bundleNameIndexInfo) { } ~SvcBackupConnection() override {}; private: std::mutex mutex_; + std::mutex waitMutex_; std::condition_variable condition_; + std::condition_variable waitCondition_; std::atomic isConnected_ = {false}; std::atomic isConnectedDone_ = {false}; + std::atomic isSecondOnDisCon_ = {false}; sptr backupProxy_; - std::function callDied_; + std::function callDied_; std::function callConnected_; + std::string bundleNameIndexInfo_; }; } // namespace OHOS::FileManagement::Backup diff --git a/services/backup_sa/include/module_ipc/svc_extension_proxy.h b/services/backup_sa/include/module_ipc/svc_extension_proxy.h index e817810ae7d36c609b20e2af954357235def8d2f..4e5b9932a424e392df16219593f29ec56ac91b66 100644 --- a/services/backup_sa/include/module_ipc/svc_extension_proxy.h +++ b/services/backup_sa/include/module_ipc/svc_extension_proxy.h @@ -25,16 +25,17 @@ class SvcExtensionProxy : public IRemoteProxy { public: UniqueFd GetFileHandle(const std::string &fileName, int32_t &errCode) override; ErrCode HandleClear() override; - ErrCode HandleBackup() override; + ErrCode HandleBackup(bool isClearData) override; ErrCode PublishFile(const std::string &fileName) override; - ErrCode HandleRestore() override; + ErrCode HandleRestore(bool isClearData) override; ErrCode GetIncrementalFileHandle(const std::string &fileName) override; ErrCode PublishIncrementalFile(const std::string &fileName) override; ErrCode HandleIncrementalBackup(UniqueFd incrementalFd, UniqueFd manifestFd) override; - ErrCode IncrementalOnBackup() override; + ErrCode IncrementalOnBackup(bool isClearData) override; std::tuple GetIncrementalBackupFileHandle() override; ErrCode GetBackupInfo(std::string &result) override; ErrCode UpdateFdSendRate(std::string &bundleName, int32_t sendRate) override; + ErrCode User0OnBackup() override; public: explicit SvcExtensionProxy(const sptr &remote) : IRemoteProxy(remote) {} diff --git a/services/backup_sa/include/module_ipc/svc_session_manager.h b/services/backup_sa/include/module_ipc/svc_session_manager.h index 737116a6c84041c2f5729054eb4e53b9c0204df7..eb6f9f5b3d257437d911727375ecaa8e47257f12 100644 --- a/services/backup_sa/include/module_ipc/svc_session_manager.h +++ b/services/backup_sa/include/module_ipc/svc_session_manager.h @@ -56,15 +56,22 @@ struct BackupExtInfo { /* Clone App: old device app versionCode */ std::string versionName; /* Ext Ability APP process time */ - uint32_t extTimerId; + uint32_t timerId; /* Timer Status: true is start & false is stop */ - bool timerStatus {false}; + bool extTimerStatus {false}; + bool fwkTimerStatus {false}; + uint32_t timeout = BConstants::TIMEOUT_INVALID; + uint32_t startTime; int64_t dataSize; int64_t lastIncrementalTime; int32_t manifestFd; std::string backupParameters; int32_t backupPriority; std::string extInfo; + int32_t appendNum {1}; + bool isClearData {true}; + bool isInPublishFile {false}; + bool isReadyLaunch {false}; }; class Service; @@ -102,7 +109,7 @@ public: * * @param impl 客户端信息 */ - ErrCode Active(Impl newImpl); + ErrCode Active(Impl newImpl, bool force = false); /** * @brief 关闭会话 @@ -382,51 +389,70 @@ public: void SetBundleDataSize(const std::string &bundleName, int64_t dataSize); /** - * @brief 启动应用扩展能力定时器 + * @brief 启动框架定时器 * * @param bundleName 应用名称 - * @return + * @param callback 超时回调 + * @return bool */ - void BundleExtTimerStart(const std::string &bundleName, const Utils::Timer::TimerCallback &callback); + bool StartFwkTimer(const std::string &bundleName, const Utils::Timer::TimerCallback &callback); /** - * @brief 重新设置定时器 + * @brief 停止框架定时器 * * @param bundleName 应用名称 - * @param timeOut 超时时间 - * @return true - * @return false + * @param callback 超时回调 + * @return bool */ - bool UpdateTimer(const std::string &bundleName, uint32_t timeOut, - const Utils::Timer::TimerCallback &callback); + bool StopFwkTimer(const std::string &bundleName); /** - * @brief 取消/暂停应用扩展能力定时器 + * @brief 启动extension定时器 * * @param bundleName 应用名称 - * @return + * @param callback 超时回调 + * @return bool */ - void BundleExtTimerStop(const std::string &bundleName); + bool StartExtTimer(const std::string &bundleName, const Utils::Timer::TimerCallback &callback); + + /** + * @brief 停止extension定时器 + * + * @param bundleName 应用名称 + * @return bool + */ + bool StopExtTimer(const std::string &bundleName); + + /** + * @brief 重新设置定时器 + * + * @param bundleName 应用名称 + * @param timeout 超时时间 + * @return true + * @return false + */ + bool UpdateTimer(const std::string &bundleName, uint32_t timeout, + const Utils::Timer::TimerCallback &callback); /** * @brief sessionCnt加计数 * * @param sessionCnt */ - void IncreaseSessionCnt(); + void IncreaseSessionCnt(const std::string funcName); /** * @brief sessionCnt加计数 * * @param sessionCnt */ - void DecreaseSessionCnt(); + void DecreaseSessionCnt(const std::string funcName); /** * @brief clear session data * */ - void ClearSessionData(); + ErrCode ClearSessionData(); /** * @brief Get the Is Incremental Backup object @@ -475,6 +501,18 @@ public: bool ValidRestoreDataType(RestoreTypeEnum restoreType); Impl GetImpl(); + int GetSessionCnt(); + + void SetClearDataFlag(const std::string &bundleName, bool isClearData); + bool GetClearDataFlag(const std::string &bundleName); + + bool CleanAndCheckIfNeedWait(ErrCode &ret, std::vector &bundleNameList); + + void SetPublishFlag(const std::string &bundleName); + + void SetImplRestoreType(const RestoreTypeEnum restoreType); + + void SetIsReadyLaunch(const std::string &bundleName); private: /** @@ -526,11 +564,11 @@ public: */ explicit SvcSessionManager(wptr reversePtr) : reversePtr_(reversePtr) { - extBundleTimer.Setup(); + timer_.Setup(); } ~SvcSessionManager() override { - extBundleTimer.Shutdown(); + timer_.Shutdown(); } private: @@ -539,7 +577,7 @@ private: sptr deathRecipient_; Impl impl_; uint32_t extConnectNum_ {0}; - Utils::Timer extBundleTimer {"backupBundleExtTimer"}; + Utils::Timer timer_ {"backupTimer"}; std::atomic sessionCnt_ {0}; int32_t memoryParaCurSize_ {BConstants::DEFAULT_VFS_CACHE_PRESSURE}; }; diff --git a/services/backup_sa/src/module_app_gallery/app_gallery_dispose_proxy.cpp b/services/backup_sa/src/module_app_gallery/app_gallery_dispose_proxy.cpp index 34f60aed333205220e16870eace44006c9b9af1a..e6817ebd96b9849a9298bf627dde230f210bd0b1 100644 --- a/services/backup_sa/src/module_app_gallery/app_gallery_dispose_proxy.cpp +++ b/services/backup_sa/src/module_app_gallery/app_gallery_dispose_proxy.cpp @@ -13,15 +13,17 @@ * limitations under the License. */ -#include "module_app_gallery/app_gallery_dispose_proxy.h" - #include +#include "b_radar/b_radar.h" +#include "b_sa/b_sa_utils.h" +#include "b_jsonutil/b_jsonutil.h" +#include "filemgmt_libhilog.h" #include "message_parcel.h" -#include "want.h" +#include "module_app_gallery/app_gallery_dispose_proxy.h" #include "module_app_gallery/app_gallery_service_connection.h" -#include "filemgmt_libhilog.h" +#include "want.h" namespace OHOS::FileManagement::Backup { using namespace std; @@ -64,61 +66,130 @@ sptr AppGalleryDisposeProxy::GetInstance() DisposeErr AppGalleryDisposeProxy::StartBackup(const std::string &bundleName) { HILOGI("StartBackup, app %{public}s", bundleName.c_str()); - return DoDispose(bundleName, DisposeOperation::START_BACKUP); + DisposeErr res = DoDispose(bundleName, DisposeOperation::START_BACKUP); + if (res != DisposeErr::REQUEST_FAIL) { + AppRadar::Info info(bundleName, "", ""); + AppRadar::GetInstance().RecordBackupFuncRes(info, "StartBackup", AppRadar::GetInstance().GetUserId(), + BizStageBackup::BIZ_STAGE_START_DISPOSE, static_cast(res)); + } + return res; } DisposeErr AppGalleryDisposeProxy::EndBackup(const std::string &bundleName) { HILOGI("EndBackup, app %{public}s", bundleName.c_str()); - return DoDispose(bundleName, DisposeOperation::END_BACKUP); + DisposeErr res = DoDispose(bundleName, DisposeOperation::END_BACKUP); + if (res != DisposeErr::REQUEST_FAIL) { + AppRadar::Info info(bundleName, "", ""); + AppRadar::GetInstance().RecordBackupFuncRes(info, "EndBackup", AppRadar::GetInstance().GetUserId(), + BizStageBackup::BIZ_STAGE_END_DISPOSE, static_cast(res)); + } + return res; } DisposeErr AppGalleryDisposeProxy::StartRestore(const std::string &bundleName) { + if (SAUtils::IsSABundleName(bundleName)) { + HILOGI("SA does not need to StartRestore"); + return DisposeErr::OK; + } HILOGI("StartRestore, app %{public}s", bundleName.c_str()); - return DoDispose(bundleName, DisposeOperation::START_RESTORE); + DisposeErr res = DoDispose(bundleName, DisposeOperation::START_RESTORE); + if (res != DisposeErr::REQUEST_FAIL) { + AppRadar::Info info(bundleName, "", ""); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "StartRestore", AppRadar::GetInstance().GetUserId(), + BizStageRestore::BIZ_STAGE_START_DISPOSE, static_cast(res)); + } + return res; } DisposeErr AppGalleryDisposeProxy::EndRestore(const std::string &bundleName) { + if (SAUtils::IsSABundleName(bundleName)) { + HILOGI("SA does not need to EndRestore"); + return DisposeErr::OK; + } HILOGI("EndRestore, app %{public}s", bundleName.c_str()); - return DoDispose(bundleName, DisposeOperation::END_RESTORE); + DisposeErr res = DoDispose(bundleName, DisposeOperation::END_RESTORE); + if (res != DisposeErr::REQUEST_FAIL) { + AppRadar::Info info(bundleName, "", ""); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "EndRestore", AppRadar::GetInstance().GetUserId(), + BizStageRestore::BIZ_STAGE_END_DISPOSE, static_cast(res)); + } + return res; } -DisposeErr AppGalleryDisposeProxy::DoDispose(const std::string &bundleName, DisposeOperation disposeOperation) +void RecordDoDisposeRes(const std::string &bundleName, + AppGalleryDisposeProxy::DisposeOperation disposeOperation, int32_t err) { - HILOGI("DoDispose, app %{public}s, operation %{public}d", bundleName.c_str(), disposeOperation); - if (!ConnectExtAbility() || appRemoteObj_ == nullptr) { - HILOGI("Can not connect to %{public}s", bundleName.c_str()); - return DisposeErr::CONN_FAIL; + AppRadar::Info info (bundleName, "", "REQUEST FAIL"); + switch (disposeOperation) { + case AppGalleryDisposeProxy::DisposeOperation::START_BACKUP: + AppRadar::GetInstance().RecordBackupFuncRes(info, "StartBackup", AppRadar::GetInstance().GetUserId(), + BizStageBackup::BIZ_STAGE_START_DISPOSE, err); + break; + case AppGalleryDisposeProxy::DisposeOperation::END_BACKUP: + AppRadar::GetInstance().RecordBackupFuncRes(info, "EndBackup", AppRadar::GetInstance().GetUserId(), + BizStageBackup::BIZ_STAGE_END_DISPOSE, err); + break; + case AppGalleryDisposeProxy::DisposeOperation::START_RESTORE: + AppRadar::GetInstance().RecordRestoreFuncRes(info, "StartRestore", AppRadar::GetInstance().GetUserId(), + BizStageRestore::BIZ_STAGE_START_DISPOSE, err); + break; + case AppGalleryDisposeProxy::DisposeOperation::END_RESTORE: + AppRadar::GetInstance().RecordRestoreFuncRes(info, "EndRestore", AppRadar::GetInstance().GetUserId(), + BizStageRestore::BIZ_STAGE_END_DISPOSE, err); + break; + default: + break; } +} - MessageParcel data; - if (!data.WriteString16(Str8ToStr16(bundleName))) { - HILOGI("write ownerInfo and bundleName failed"); - return DisposeErr::IPC_FAIL; - } +DisposeErr AppGalleryDisposeProxy::DoDispose(const std::string &bundleName, DisposeOperation disposeOperation) +{ + try { + HILOGI("DoDispose, app %{public}s, operation %{public}d", bundleName.c_str(), disposeOperation); + if (!ConnectExtAbility() || appRemoteObj_ == nullptr) { + HILOGE("Can not connect to %{public}s", bundleName.c_str()); + return DisposeErr::CONN_FAIL; + } - if (!data.WriteRemoteObject(this)) { - HILOGI("write RemoteObject failed"); + BJsonUtil::BundleDetailInfo bundleDetailInfo = BJsonUtil::ParseBundleNameIndexStr(bundleName); + MessageParcel data; + const auto interfaceToken = APP_FOUNDATION_SERVICE; + if (!data.WriteInterfaceToken(interfaceToken)) { + HILOGE("write WriteInterfaceToken failed"); + return DisposeErr::IPC_FAIL; + } + if (!data.WriteString16(Str8ToStr16(bundleDetailInfo.bundleName))) { + HILOGE("write bundleName failed"); + return DisposeErr::IPC_FAIL; + } + if (!data.WriteInt32(static_cast(bundleDetailInfo.bundleIndex))) { + HILOGE("write bundleIndex failed"); + return DisposeErr::IPC_FAIL; + } + + MessageParcel reply; + MessageOption option; + int32_t ret = appRemoteObj_->SendRequest(static_cast(disposeOperation), data, reply, option); + if (ret != ERR_NONE) { + HILOGE("SendRequest error, code=%{public}d, bundleName=%{public}s , appindex =%{public}d", + ret, bundleDetailInfo.bundleName.c_str(), bundleDetailInfo.bundleIndex); + RecordDoDisposeRes(bundleName, disposeOperation, ret); + return DisposeErr::REQUEST_FAIL; + } + + HILOGI("SendRequest success, dispose=%{public}d, bundleName=%{public}s, appindex =%{public}d", + disposeOperation, bundleDetailInfo.bundleName.c_str(), bundleDetailInfo.bundleIndex); + return DisposeErr::OK; + } catch (const BError &e) { + HILOGE("Catch exception, errCode = %{public}d", e.GetCode()); return DisposeErr::IPC_FAIL; - } - const auto interfaceToken = APP_FOUNDATION_SERVICE; - if (!data.WriteInterfaceToken(interfaceToken)) { - HILOGI("write WriteInterfaceToken failed"); + } catch (...) { + HILOGE("Unexpected exception"); return DisposeErr::IPC_FAIL; } - - MessageParcel reply; - MessageOption option(MessageOption::TF_ASYNC); - int32_t ret = appRemoteObj_->SendRequest(static_cast(disposeOperation), data, reply, option); - if (ret != ERR_NONE) { - HILOGI("SendRequest error, code=%{public}d, bundleName=%{public}s", ret, bundleName.c_str()); - return DisposeErr::REQUEST_FAIL; - } - - HILOGI("SendRequest success, dispose=%{public}d, bundleName=%{public}s", disposeOperation, bundleName.c_str()); - return DisposeErr::OK; } } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/services/backup_sa/src/module_external/bms_adapter.cpp b/services/backup_sa/src/module_external/bms_adapter.cpp index 87b1cfda47483c7014681a2048df70ddc83ef0ff..0738d24b56dabaf98020644408e66200f76727a6 100644 --- a/services/backup_sa/src/module_external/bms_adapter.cpp +++ b/services/backup_sa/src/module_external/bms_adapter.cpp @@ -22,6 +22,7 @@ #include "b_error/b_error.h" #include "b_file_info.h" +#include "b_jsonutil/b_jsonutil.h" #include "b_json/b_json_entity_extension_config.h" #include "b_resources/b_constants.h" #include "b_sa/b_sa_utils.h" @@ -47,7 +48,6 @@ const string LINUX_HAP_CODE_PATH = "2"; const string MEDIA_LIBRARY_HAP = "com.ohos.medialibrary.medialibrarydata"; const string EXTERNAL_FILE_HAP = "com.ohos.UserFile.ExternalFileManager"; const int E_ERR = -1; -const int SINGLE_BUNDLE_NUM = 1; const vector dataDir = {"app", "local", "distributed", "database", "cache"}; } // namespace @@ -95,7 +95,9 @@ static int64_t GetBundleStats(const string &bundleName, int32_t userId) } auto bms = GetBundleManager(); vector bundleStats; - bool res = bms->GetBundleStats(bundleName, userId, bundleStats); + BJsonUtil::BundleDetailInfo bundleDetailInfo = BJsonUtil::ParseBundleNameIndexStr(bundleName); + bool res = bms->GetBundleStats(bundleDetailInfo.bundleName, userId, bundleStats, bundleDetailInfo.bundleIndex, + AppExecFwk::Constants::NoGetBundleStatsFlag::GET_BUNDLE_WITHOUT_CACHE_SIZE); if (!res || bundleStats.size() != dataDir.size()) { HILOGE("An error occurred in querying bundle stats. name:%{public}s", bundleName.c_str()); return 0; @@ -117,30 +119,29 @@ vector BundleMgrAdapter::GetBundleInfos(const vecto HILOGI("Start, bundleNames size:%{public}zu", bundleNames.size()); for (auto const &bundleName : bundleNames) { HILOGI("Begin Get bundleName:%{public}s", bundleName.c_str()); + if (bundleName.empty()) { + HILOGE("BundleName is invalid"); + continue; + } if (SAUtils::IsSABundleName(bundleName)) { GetBundleInfoForSA(bundleName, bundleInfos); continue; } AppExecFwk::BundleInfo installedBundle; - if (!bms->GetBundleInfo(bundleName, AppExecFwk::GET_BUNDLE_WITH_EXTENSION_INFO, installedBundle, userId)) { - if (bundleNames.size() != SINGLE_BUNDLE_NUM) { - HILOGE("bundleName:%{public}s, current bundle info for backup/restore is empty", bundleName.c_str()); - continue; - } - throw BError(BError::Codes::SA_BUNDLE_INFO_EMPTY, "Failed to get bundle info"); - } - if (installedBundle.applicationInfo.codePath == HMOS_HAP_CODE_PATH || - installedBundle.applicationInfo.codePath == LINUX_HAP_CODE_PATH) { - HILOGI("Unsupported applications, name : %{public}s", installedBundle.name.data()); + std::vector extensionInfos; + bool getBundleSuccess = GetCurBundleExtenionInfo(installedBundle, bundleName, extensionInfos, bms, userId); + if (!getBundleSuccess) { + HILOGE("Get current extension failed"); continue; } auto [allToBackup, fullBackupOnly, extName, restoreDeps, supportScene, extraInfo] = - GetAllowAndExtName(installedBundle.extensionInfos); + GetAllowAndExtName(extensionInfos); int64_t dataSize = 0; if (allToBackup) { - dataSize = GetBundleStats(installedBundle.name, userId); + dataSize = GetBundleStats(bundleName, userId); } - bundleInfos.emplace_back(BJsonEntityCaps::BundleInfo {installedBundle.name, installedBundle.versionCode, + bundleInfos.emplace_back(BJsonEntityCaps::BundleInfo {installedBundle.name, installedBundle.appIndex, + installedBundle.versionCode, installedBundle.versionName, dataSize, 0, allToBackup, fullBackupOnly, extName, restoreDeps, supportScene, extraInfo}); @@ -195,11 +196,21 @@ static bool CreateIPCInteractionFiles(int32_t userId, const string &bundleName, const vector &includes, const vector &excludes) { // backup_sa bundle path - string backupSaBundleDir = BConstants::BACKUP_PATH_PREFIX + to_string(userId) + BConstants::BACKUP_PATH_SURFFIX + - bundleName + BConstants::FILE_SEPARATOR_CHAR; + BJsonUtil::BundleDetailInfo bundleDetail = BJsonUtil::ParseBundleNameIndexStr(bundleName); + string backupSaBundleDir; + if (bundleDetail.bundleIndex > 0) { + std::string bundleNameIndex = "+clone-" + std::to_string(bundleDetail.bundleIndex) + "+" + + bundleDetail.bundleName; + backupSaBundleDir = BConstants::BACKUP_PATH_PREFIX + to_string(userId) + BConstants::BACKUP_PATH_SURFFIX + + bundleNameIndex + BConstants::FILE_SEPARATOR_CHAR; + } else { + backupSaBundleDir = BConstants::BACKUP_PATH_PREFIX + to_string(userId) + BConstants::BACKUP_PATH_SURFFIX + + bundleDetail.bundleName + BConstants::FILE_SEPARATOR_CHAR; + } + HILOGI("bundleInteraction dir is:%{public}s", backupSaBundleDir.c_str()); if (access(backupSaBundleDir.data(), F_OK) != 0) { int32_t err = mkdir(backupSaBundleDir.data(), S_IRWXU | S_IRWXG); - if (err != 0) { + if (err != 0 && errno != EEXIST) { HILOGE("Failed to create folder in backup_sa bundleName:%{public}s, sys err:%{public}d", bundleName.c_str(), errno); return false; @@ -258,6 +269,7 @@ static bool GenerateBundleStatsIncrease(int32_t userId, const vector &bu std::string curBundleName = bundleInfos[i].name; HILOGD("BundleMgrAdapter name for %{public}s", curBundleName.c_str()); BJsonEntityCaps::BundleInfo newBundleInfo = {.name = curBundleName, + .appIndex = bundleInfos[i].appIndex, .versionCode = bundleInfos[i].versionCode, .versionName = bundleInfos[i].versionName, .spaceOccupied = pkgFileSizes[i], @@ -282,32 +294,37 @@ vector BundleMgrAdapter::GetBundleInfosForIncrement auto bms = GetBundleManager(); for (auto const &bundleNameTime : incrementalDataList) { auto bundleName = bundleNameTime.bundleName; - HILOGD("Begin get bundleName:%{private}s", bundleName.c_str()); AppExecFwk::BundleInfo installedBundle; - if (!bms->GetBundleInfo(bundleName, AppExecFwk::GET_BUNDLE_WITH_EXTENSION_INFO, installedBundle, userId)) { - throw BError(BError::Codes::SA_BROKEN_IPC, "Failed to get bundle info"); - } - if (installedBundle.applicationInfo.codePath == HMOS_HAP_CODE_PATH || - installedBundle.applicationInfo.codePath == LINUX_HAP_CODE_PATH) { - HILOGI("Unsupported applications, name : %{private}s", installedBundle.name.data()); + std::vector extensionInfos; + bool getBundleSuccess = GetCurBundleExtenionInfo(installedBundle, bundleName, extensionInfos, bms, userId); + if (!getBundleSuccess) { + HILOGE("Failed to get bundle info from bms, bundleName:%{public}s", bundleName.c_str()); continue; } struct BJsonEntityCaps::BundleBackupConfigPara backupPara; - if (!GetBackupExtConfig(installedBundle.extensionInfos, backupPara)) { - HILOGE("No backup extension ability found"); + if (!GetBackupExtConfig(extensionInfos, backupPara)) { + HILOGE("No backup extension ability found, bundleName:%{public}s", bundleName.c_str()); continue; } if (!CreateIPCInteractionFiles(userId, bundleName, bundleNameTime.lastIncrementalTime, backupPara.includes, backupPara.excludes)) { + HILOGE("Create bundleInteraction dir failed, bundleName:%{public}s", bundleName.c_str()); continue; } - bundleInfos.emplace_back(BJsonEntityCaps::BundleInfo {installedBundle.name, installedBundle.versionCode, + bundleInfos.emplace_back(BJsonEntityCaps::BundleInfo {installedBundle.name, installedBundle.appIndex, + installedBundle.versionCode, installedBundle.versionName, 0, 0, backupPara.allToBackup, backupPara.fullBackupOnly, backupPara.extensionName, backupPara.restoreDeps, backupPara.supportScene, backupPara.extraInfo}); - bundleNames.emplace_back(bundleName); + if (installedBundle.appIndex > 0) { + std::string bundleNameIndex = "+clone-" + std::to_string(installedBundle.appIndex) + "+" + + installedBundle.name; + bundleNames.emplace_back(bundleNameIndex); + } else { + bundleNames.emplace_back(bundleName); + } incrementalBackTimes.emplace_back(bundleNameTime.lastIncrementalTime); } vector newBundleInfos {}; @@ -315,7 +332,6 @@ vector BundleMgrAdapter::GetBundleInfosForIncrement HILOGE("Failed to get bundleStats result"); return {}; } - HILOGI("BundleMgrAdapter GetBundleInfosForIncremental end "); return newBundleInfos; } @@ -342,9 +358,9 @@ vector BundleMgrAdapter::GetBundleInfosForIncrement auto [allToBackup, fullBackupOnly, extName, restoreDeps, supportScene, extraInfo] = GetAllowAndExtName(installedBundle.extensionInfos); if (!allToBackup) { - bundleInfos.emplace_back(BJsonEntityCaps::BundleInfo {installedBundle.name, installedBundle.versionCode, - installedBundle.versionName, 0, 0, allToBackup, fullBackupOnly, extName, restoreDeps, supportScene, - extraInfo}); + bundleInfos.emplace_back(BJsonEntityCaps::BundleInfo {installedBundle.name, installedBundle.appIndex, + installedBundle.versionCode, installedBundle.versionName, 0, 0, allToBackup, fullBackupOnly, + extName, restoreDeps, supportScene, extraInfo}); continue; } auto it = std::find_if(extraIncreData.begin(), extraIncreData.end(), @@ -365,6 +381,48 @@ vector BundleMgrAdapter::GetBundleInfosForIncrement return bundleInfos; } +vector BundleMgrAdapter::GetFullBundleInfos(int32_t userId) +{ + vector installedBundles; + HILOGI("Begin GetFullBundleInfos"); + auto bms = GetBundleManager(); + if (!bms->GetBundleInfos(AppExecFwk::GET_BUNDLE_WITH_EXTENSION_INFO, installedBundles, userId)) { + throw BError(BError::Codes::SA_BROKEN_IPC, "Failed to get bundle infos"); + } + vector bundleNames; + vector bundleInfos; + for (auto const &installedBundle : installedBundles) { + HILOGI("Begin get bundle infos, bundleName = %{public}s", installedBundle.name.data()); + if (installedBundle.applicationInfo.codePath == HMOS_HAP_CODE_PATH || + installedBundle.applicationInfo.codePath == LINUX_HAP_CODE_PATH) { + HILOGI("Unsupported applications, name : %{public}s", installedBundle.name.data()); + continue; + } + if (installedBundle.appIndex > 0) { + std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(installedBundle.name, + installedBundle.appIndex); + bundleNames.emplace_back(bundleNameIndexInfo); + continue; + } + auto [allToBackup, fullBackupOnly, extName, restoreDeps, supportScene, extraInfo] = + GetAllowAndExtName(installedBundle.extensionInfos); + if (!allToBackup) { + HILOGI("Not allToBackup, bundleName = %{public}s", installedBundle.name.data()); + bundleInfos.emplace_back(BJsonEntityCaps::BundleInfo {installedBundle.name, installedBundle.appIndex, + installedBundle.versionCode, installedBundle.versionName, 0, 0, allToBackup, fullBackupOnly, extName, + restoreDeps, supportScene, extraInfo}); + continue; + } + bundleNames.emplace_back(installedBundle.name); + } + auto bundleInfosNew = BundleMgrAdapter::GetBundleInfos(bundleNames, userId); + auto bundleInfosSA = BundleMgrAdapter::GetBundleInfosForSA(); + copy(bundleInfosNew.begin(), bundleInfosNew.end(), back_inserter(bundleInfos)); + copy(bundleInfosSA.begin(), bundleInfosSA.end(), back_inserter(bundleInfos)); + HILOGI("End GetFullBundleInfos, bundleInfos size: %{public}zu", bundleInfos.size()); + return bundleInfos; +} + string BundleMgrAdapter::GetExtName(string bundleName, int32_t userId) { vector installedBundles; @@ -405,7 +463,7 @@ std::vector BundleMgrAdapter::GetBundleInfosForSA() int32_t ret = samgrProxy->GetExtensionSaIds(BConstants::EXTENSION_BACKUP, saIds); HILOGI("GetExtensionSaIds ret: %{public}d", ret); for (auto saId : saIds) { - saBundleInfos.emplace_back(BJsonEntityCaps::BundleInfo {std::to_string(saId), 0, "", 0, 0, true, false, + saBundleInfos.emplace_back(BJsonEntityCaps::BundleInfo {std::to_string(saId), 0, 0, "", 0, 0, true, false, "", "", "", ""}); } return saBundleInfos; @@ -435,7 +493,71 @@ void BundleMgrAdapter::GetBundleInfoForSA(std::string bundleName, std::vector &extensionInfos, + sptr bms, int32_t userId) +{ + BJsonUtil::BundleDetailInfo bundleDetailInfo = BJsonUtil::ParseBundleNameIndexStr(bundleName); + int32_t flags = static_cast(AppExecFwk::GetBundleInfoFlag::GET_BUNDLE_INFO_WITH_HAP_MODULE) | + static_cast(AppExecFwk::GetBundleInfoFlag::GET_BUNDLE_INFO_WITH_EXTENSION_ABILITY) | + static_cast(AppExecFwk::GetBundleInfoFlag::GET_BUNDLE_INFO_WITH_METADATA); + ErrCode ret = bms->GetCloneBundleInfo(bundleDetailInfo.bundleName, flags, bundleDetailInfo.bundleIndex, + installedBundle, userId); + if (ret != ERR_OK) { + HILOGE("bundleName:%{public}s, ret:%{public}d, current bundle info for backup/restore is empty", + bundleName.c_str(), ret); + return false; + } + if (installedBundle.applicationInfo.codePath == HMOS_HAP_CODE_PATH || + installedBundle.applicationInfo.codePath == LINUX_HAP_CODE_PATH) { + HILOGE("Unsupported applications, name : %{public}s", installedBundle.name.data()); + return false; + } + std::vector hapModuleInfos = installedBundle.hapModuleInfos; + for (auto &hapModuleInfo : hapModuleInfos) { + extensionInfos.insert(extensionInfos.end(), hapModuleInfo.extensionInfos.begin(), + hapModuleInfo.extensionInfos.end()); + } + HILOGI("bundleName:%{public}s, extensionInfos size:%{public}zu", bundleName.c_str(), extensionInfos.size()); + return true; +} + +bool BundleMgrAdapter::IsUser0BundleName(std::string bundleName, int32_t userId) +{ + auto bms = GetBundleManager(); + AppExecFwk::BundleInfo installedBundle; + BJsonUtil::BundleDetailInfo bundleDetailInfo = BJsonUtil::ParseBundleNameIndexStr(bundleName); + int32_t flags = static_cast(AppExecFwk::GetBundleInfoFlag::GET_BUNDLE_INFO_WITH_HAP_MODULE) | + static_cast(AppExecFwk::GetBundleInfoFlag::GET_BUNDLE_INFO_WITH_EXTENSION_ABILITY) | + static_cast(AppExecFwk::GetBundleInfoFlag::GET_BUNDLE_INFO_WITH_METADATA) | + static_cast(AppExecFwk::GetBundleInfoFlag::GET_BUNDLE_INFO_WITH_APPLICATION); + ErrCode ret = bms->GetCloneBundleInfo(bundleDetailInfo.bundleName, flags, bundleDetailInfo.bundleIndex, + installedBundle, userId); + if (ret != ERR_OK) { + HILOGE("bundleName:%{public}s, ret:%{public}d, GetBundle Failed from BMS", bundleName.c_str(), ret); + return false; + } + if (installedBundle.applicationInfo.singleton == true) { + HILOGI("bundleName:%{public}s is zero user bundle", bundleName.c_str()); + return true; + } + HILOGI("bundleName:%{public}s is not zero user bundle", bundleName.c_str()); + return false; +} + +vector BundleMgrAdapter::GetBundleInfosForAppend(const std::vector &list, + int32_t userId) +{ + auto bundleInfos = BundleMgrAdapter::GetBundleInfosForIncremental(list, userId); + for (auto const &info : list) { + if (SAUtils::IsSABundleName(info.bundleName)) { + GetBundleInfoForSA(info.bundleName, bundleInfos); + } + } + return bundleInfos; +} } // namespace OHOS::FileManagement::Backup diff --git a/services/backup_sa/src/module_ipc/sa_backup_connection.cpp b/services/backup_sa/src/module_ipc/sa_backup_connection.cpp index 3f4c84960b750d3a08bd2ffe871ea62a2612f2f8..13f2cb77954e280d76f1c7e9cb6e50d99dada539 100644 --- a/services/backup_sa/src/module_ipc/sa_backup_connection.cpp +++ b/services/backup_sa/src/module_ipc/sa_backup_connection.cpp @@ -128,11 +128,12 @@ ErrCode SABackupConnection::LoadBackupSAExtInner() [loadCallback]() { return loadCallback->isLoadSuccess_.load(); }); if (!waitStatus) { HILOGE("Load sa %{public}d timeout", saId_); + lock.unlock(); isConnected_.store(false); return LoadBackupSAExt(); } + lock.unlock(); isConnected_.store(true); - callConnected_(move(bundleName_)); return LoadBackupSAExt(); } diff --git a/services/backup_sa/src/module_ipc/service.cpp b/services/backup_sa/src/module_ipc/service.cpp index 952aeefa0aaf082835e66a5fa900ea53edd3703d..6f84ebb5b6364db97f86c870b27c62b379982643 100644 --- a/services/backup_sa/src/module_ipc/service.cpp +++ b/services/backup_sa/src/module_ipc/service.cpp @@ -47,13 +47,17 @@ #include "b_jsonutil/b_jsonutil.h" #include "b_ohos/startup/backup_para.h" #include "b_process/b_multiuser.h" +#include "b_radar/b_radar.h" #include "b_resources/b_constants.h" #include "b_sa/b_sa_utils.h" +#include "b_utils/b_time.h" #include "bundle_mgr_client.h" #include "filemgmt_libhilog.h" #include "hisysevent.h" #include "hitrace_meter.h" #include "ipc_skeleton.h" +#include "access_token.h" +#include "tokenid_kit.h" #include "module_app_gallery/app_gallery_dispose_proxy.h" #include "module_external/bms_adapter.h" #include "module_external/sms_adapter.h" @@ -73,6 +77,7 @@ namespace { constexpr int32_t DEBUG_ID = 100; constexpr int32_t INDEX = 3; constexpr int32_t MS_1000 = 1000; +constexpr int DEFAULT_FD_SEND_RATE = 60; const static string BROADCAST_TYPE = "broadcast"; const std::string FILE_BACKUP_EVENTS = "FILE_BACKUP_EVENTS"; const static string UNICAST_TYPE = "unicast"; @@ -80,6 +85,8 @@ const int32_t CONNECT_WAIT_TIME_S = 15; const std::string BACKUPSERVICE_WORK_STATUS_KEY = "persist.backupservice.workstatus"; const std::string BACKUPSERVICE_WORK_STATUS_ON = "true"; const std::string BACKUPSERVICE_WORK_STATUS_OFF = "false"; +const std::string BACKUP_PERMISSION = "ohos.permission.BACKUP"; +const int32_t MAX_TRY_CLEAR_DISPOSE_NUM = 3; } // namespace /* Shell/Xts user id equal to 0/1, we need set default 100 */ @@ -97,21 +104,147 @@ static inline int32_t GetUserIdDefault() return multiuser.userId; } +void OnStartResRadarReport(const std::vector &bundleNameList, int32_t stage) +{ + std::stringstream ss; + ss << "failedBundles:{"; + for (auto &bundleName : bundleNameList) { + ss << bundleName << ", "; + } + ss << "}"; + AppRadar::Info info("", "", ss.str()); + AppRadar::GetInstance().RecordDefaultFuncRes(info, "Service::OnStart", GetUserIdDefault(), + static_cast(stage), ERR_OK); +} + +void Service::ClearFailedBundles() +{ + std::lock_guard lock(failedBundlesLock_); + failedBundles_.clear(); +} + +void Service::UpdateFailedBundles(const std::string &bundleName, BundleTaskInfo taskInfo) +{ + std::lock_guard lock(failedBundlesLock_); + failedBundles_[bundleName] = taskInfo; +} + +void Service::BundleBeginRadarReport(const std::string &bundleName, const ErrCode errCode, + const IServiceReverse::Scenario scenario) +{ + if (errCode == ERR_OK || errCode == BError(BError::Codes::SA_BOOT_EXT_FAIL).GetCode()) { + return; + } + BundleTaskInfo taskInfo; + taskInfo.reportTime = TimeUtils::GetCurrentTime(); + taskInfo.errCode = errCode; + UpdateFailedBundles(bundleName, taskInfo); + AppRadar::Info info(bundleName, "", ""); + if (scenario == IServiceReverse::Scenario::RESTORE) { + AppRadar::GetInstance().RecordRestoreFuncRes(info, "Service::BundleBeginRadarReport", + GetUserIdDefault(), BizStageRestore::BIZ_STAGE_APPEND_BUNDLES_FAIL, errCode); + } else if (scenario == IServiceReverse::Scenario::BACKUP) { + AppRadar::GetInstance().RecordBackupFuncRes(info, "Service::BundleBeginRadarReport", + GetUserIdDefault(), BizStageBackup::BIZ_STAGE_APPEND_BUNDLES_FAIL, errCode); + } +} + +void Service::BundleEndRadarReport(const std::string &bundleName, const ErrCode errCode, + const IServiceReverse::Scenario scenario) +{ + if (errCode == ERR_OK) { + successBundlesNum_++; + return; + } + BundleTaskInfo taskInfo; + taskInfo.reportTime = TimeUtils::GetCurrentTime(); + taskInfo.errCode = errCode; + UpdateFailedBundles(bundleName, taskInfo); + AppRadar::Info info(bundleName, "", ""); + if (scenario == IServiceReverse::Scenario::RESTORE) { + AppRadar::GetInstance().RecordRestoreFuncRes(info, "Service::BundleEndRadarReport", + GetUserIdDefault(), BizStageRestore::BIZ_STAGE_EXECU_FAIL, errCode); + } else if (scenario == IServiceReverse::Scenario::BACKUP) { + AppRadar::GetInstance().RecordBackupFuncRes(info, "Service::BundleEndRadarReport", + GetUserIdDefault(), BizStageBackup::BIZ_STAGE_EXECU_FAIL, errCode); + } +} + +void Service::FileReadyRadarReport(const std::string &bundleName, const std::string &fileName, const ErrCode errCode, + const IServiceReverse::Scenario scenario) +{ + if (errCode == ERR_OK) { + return; + } + std::string fileNameReport = std::string("fileName:\"") + GetAnonyPath(fileName) + "\""; + AppRadar::Info info(bundleName, "", fileNameReport); + if (scenario == IServiceReverse::Scenario::RESTORE) { + AppRadar::GetInstance().RecordRestoreFuncRes(info, "Service::FileReadyRadarReport", + GetUserIdDefault(), BizStageRestore::BIZ_STAGE_GET_FILE_HANDLE_FAIL, errCode); + } else if (scenario == IServiceReverse::Scenario::BACKUP) { + AppRadar::GetInstance().RecordBackupFuncRes(info, "Service::FileReadyRadarReport", + GetUserIdDefault(), BizStageBackup::BIZ_STAGE_DO_BACKUP, errCode); + } +} + +void Service::ExtensionConnectFailRadarReport(const std::string &bundleName, const ErrCode errCode, + const IServiceReverse::Scenario scenario) +{ + std::stringstream ss; + ss << "errCode:" << errCode; + AppRadar::Info info(bundleName, "", ss.str()); + if (scenario == IServiceReverse::Scenario::RESTORE) { + AppRadar::GetInstance().RecordRestoreFuncRes(info, "Service::ExtensionConnectFailRadarReport", + GetUserIdDefault(), BizStageRestore::BIZ_STAGE_CONNECT_EXTENSION_FAIL, + BError(BError::Codes::SA_BOOT_EXT_FAIL).GetCode()); + } else if (scenario == IServiceReverse::Scenario::BACKUP) { + AppRadar::GetInstance().RecordBackupFuncRes(info, "Service::ExtensionConnectFailRadarReport", + GetUserIdDefault(), BizStageBackup::BIZ_STAGE_CONNECT_EXTENSION_FAIL, + BError(BError::Codes::SA_BOOT_EXT_FAIL).GetCode()); + } +} + void Service::OnStart() { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); HILOGI("SA OnStart Begin."); - ClearDisposalOnSaStart(); + std::vector bundleNameList; + if (disposal_ != nullptr) { + bundleNameList = disposal_->GetBundleNameFromConfigFile(); + } + std::vector residualBundleNameList; + if (clearRecorder_ != nullptr) { + residualBundleNameList = clearRecorder_->GetAllClearBundleRecords(); + } + if (!bundleNameList.empty() || !residualBundleNameList.empty()) { + if (!bundleNameList.empty()) { + OnStartResRadarReport(bundleNameList, + static_cast(BizStageBackup::BIZ_STAGE_ONSTART_DISPOSE)); + } + if (!residualBundleNameList.empty()) { + OnStartResRadarReport(residualBundleNameList, + static_cast(BizStageBackup::BIZ_STAGE_ONSTART_RESIDUAL)); + } + session_->Active( + { + .clientToken = IPCSkeleton::GetCallingTokenID(), + .scenario = IServiceReverse::Scenario::CLEAN, + .clientProxy = nullptr, + .userId = GetUserIdDefault(), + }, + true); + isCleanService_.store(true); + HILOGE("SA OnStart, cleaning up backup data"); + } bool res = SystemAbility::Publish(sptr(this)); - sched_ = sptr(new SchedScheduler(wptr(this), wptr(session_))); - sched_->StartTimer(); - string work_status = system::GetParameter(BACKUPSERVICE_WORK_STATUS_KEY, ""); - HILOGI("Param %{public}s value is %{public}s", BACKUPSERVICE_WORK_STATUS_KEY.c_str(), work_status.c_str()); - if (work_status.compare(BACKUPSERVICE_WORK_STATUS_ON) == 0) { - bool isSetSucc = system::SetParameter(BACKUPSERVICE_WORK_STATUS_KEY, BACKUPSERVICE_WORK_STATUS_OFF); - HILOGI("SetParameter %{public}s false end, result %{public}d.", BACKUPSERVICE_WORK_STATUS_KEY.c_str(), - isSetSucc); - sched_->TryUnloadService(); + if (sched_ != nullptr) { + sched_->StartTimer(); + } + ClearDisposalOnSaStart(); + auto ret = AppendBundlesClearSession(residualBundleNameList); + if (isCleanService_.load() && ret) { + isCleanService_.store(false); + StopAll(nullptr, true); } HILOGI("SA OnStart End, res = %{public}d", res); } @@ -125,13 +258,6 @@ void Service::OnStop() oldMemoryParaSize = session_->GetMemParaCurSize(); } StorageMgrAdapter::UpdateMemPara(oldMemoryParaSize); - string work_status = system::GetParameter(BACKUPSERVICE_WORK_STATUS_KEY, ""); - HILOGI("Param %{public}s value is %{public}s", BACKUPSERVICE_WORK_STATUS_KEY.c_str(), work_status.c_str()); - if (work_status.compare(BACKUPSERVICE_WORK_STATUS_ON) == 0) { - bool isSetSucc = system::SetParameter(BACKUPSERVICE_WORK_STATUS_KEY, BACKUPSERVICE_WORK_STATUS_OFF); - HILOGI("SetParameter %{public}s false end, result %{public}d.", BACKUPSERVICE_WORK_STATUS_KEY.c_str(), - isSetSucc); - } HILOGI("SA OnStop End."); } @@ -144,15 +270,21 @@ UniqueFd Service::GetLocalCapabilities() so there must be set init userId. */ HILOGI("Begin"); - session_->IncreaseSessionCnt(); + if (session_ == nullptr || isCleanService_.load()) { + HILOGE("GetLocalCapabilities error, session is empty."); + return UniqueFd(-EPERM); + } + session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); session_->SetSessionUserId(GetUserIdDefault()); VerifyCaller(); string path = BConstants::GetSaBundleBackupRootDir(session_->GetSessionUserId()); BExcepUltils::VerifyPath(path, false); + CreateDirIfNotExist(path); UniqueFd fd(open(path.data(), O_TMPFILE | O_RDWR, S_IRUSR | S_IWUSR)); if (fd < 0) { HILOGE("Failed to open config file = %{private}s, err = %{public}d", path.c_str(), errno); - return UniqueFd(-1); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); + return UniqueFd(-EPERM); } BJsonCachedEntity cachedEntity(std::move(fd)); @@ -160,22 +292,22 @@ UniqueFd Service::GetLocalCapabilities() cache.SetSystemFullName(GetOSFullName()); cache.SetDeviceType(GetDeviceType()); - auto bundleInfos = BundleMgrAdapter::GetBundleInfosForIncremental(session_->GetSessionUserId()); + auto bundleInfos = BundleMgrAdapter::GetFullBundleInfos(session_->GetSessionUserId()); cache.SetBundleInfos(bundleInfos); cachedEntity.Persist(); - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGI("End"); return move(cachedEntity.GetFd()); } catch (const BError &e) { - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGE("GetLocalCapabilities failed, errCode = %{public}d", e.GetCode()); return UniqueFd(-e.GetCode()); } catch (const exception &e) { - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGI("Catched an unexpected low-level exception %{public}s", e.what()); return UniqueFd(-EPERM); } catch (...) { - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGI("Unexpected exception"); return UniqueFd(-EPERM); } @@ -184,9 +316,42 @@ UniqueFd Service::GetLocalCapabilities() void Service::StopAll(const wptr &obj, bool force) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + std::lock_guard lock(failedBundlesLock_); + uint32_t fail_cnt = failedBundles_.size(); + uint32_t totalBundles = fail_cnt + successBundlesNum_.load(); + if (totalBundles != 0) { + int32_t result = 0; + if (fail_cnt != 0) { + result = BError::BackupErrorCode::E_TASKFAIL; + } + std::stringstream ss; + ss << "successBundleNum:" << successBundlesNum_ << "," << "failedBundleNum:" << + fail_cnt << "," << "failedBundles:{"; + for (auto &failBundle : failedBundles_) { + ss << "\"" << failBundle.first << "\":" << "{errCode:" << failBundle.second.errCode << "," + << "reportTime:" << failBundle.second.reportTime << "},"; + } + ss << "}"; + string resultInfo = ss.str(); + AppRadar::StatInfo statInfo("", resultInfo); + IServiceReverse::Scenario scenario = session_->GetScenario(); + AppRadar::GetInstance().RecordStatisticRes(statInfo, GetUserIdDefault(), scenario, + successBundlesNum_.load(), fail_cnt, result); + } + failedBundles_.clear(); + successBundlesNum_ = 0; session_->Deactive(obj, force); } +static inline void PermissionCheckFailRadar(const std::string &info, const std::string &func) +{ + std::string funcPos = "Service::"; + AppRadar::Info resInfo("", "", info); + AppRadar::GetInstance().RecordDefaultFuncRes(resInfo, funcPos.append(func), + GetUserIdDefault(), BizStageBackup::BIZ_STAGE_PERMISSION_CHECK_FAIL, + BError(BError::Codes::SA_REFUSED_ACT).GetCode()); +} + string Service::VerifyCallerAndGetCallerName() { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); @@ -195,13 +360,18 @@ string Service::VerifyCallerAndGetCallerName() if (tokenType == Security::AccessToken::ATokenTypeEnum::TOKEN_HAP) { Security::AccessToken::HapTokenInfo hapTokenInfo; if (Security::AccessToken::AccessTokenKit::GetHapTokenInfo(tokenCaller, hapTokenInfo) != 0) { + PermissionCheckFailRadar("Get hap token info failed", "VerifyCallerAndGetCallerName"); throw BError(BError::Codes::SA_INVAL_ARG, "Get hap token info failed"); } - session_->VerifyBundleName(hapTokenInfo.bundleName); - return hapTokenInfo.bundleName; + std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(hapTokenInfo.bundleName, + hapTokenInfo.instIndex); + session_->VerifyBundleName(bundleNameIndexInfo); + return bundleNameIndexInfo; } else { string str = to_string(tokenCaller); HILOGE("tokenID = %{private}s", GetAnonyString(str).c_str()); + std::string info = string("Invalid token type").append(to_string(tokenType)).append(string("\"}")); + PermissionCheckFailRadar(info, "VerifyCallerAndGetCallerName"); throw BError(BError::Codes::SA_INVAL_ARG, string("Invalid token type ").append(to_string(tokenType))); } } @@ -212,23 +382,44 @@ void Service::VerifyCaller() uint32_t tokenCaller = IPCSkeleton::GetCallingTokenID(); int tokenType = Security::AccessToken::AccessTokenKit::GetTokenType(tokenCaller); switch (tokenType) { - case Security::AccessToken::ATokenTypeEnum::TOKEN_NATIVE: /* Update Service */ + case Security::AccessToken::ATokenTypeEnum::TOKEN_NATIVE: { /* Update Service */ + if (Security::AccessToken::AccessTokenKit::VerifyAccessToken(tokenCaller, BACKUP_PERMISSION) != + Security::AccessToken::PermissionState::PERMISSION_GRANTED) { + std::string info = "Permission denied, token type is " + to_string(tokenType); + PermissionCheckFailRadar(info, "VerifyCaller"); + throw BError(BError::Codes::SA_REFUSED_ACT, + string("Permission denied, token type is ").append(to_string(tokenType))); + } + break; + } case Security::AccessToken::ATokenTypeEnum::TOKEN_HAP: { - const string permission = "ohos.permission.BACKUP"; - if (Security::AccessToken::AccessTokenKit::VerifyAccessToken(tokenCaller, permission) == - Security::AccessToken::TypePermissionState::PERMISSION_DENIED) { - throw BError(BError::Codes::SA_INVAL_ARG, - string("Permission denied, token type is ").append(to_string(tokenType))); + if (Security::AccessToken::AccessTokenKit::VerifyAccessToken(tokenCaller, BACKUP_PERMISSION) != + Security::AccessToken::PermissionState::PERMISSION_GRANTED) { + std::string info = "Permission denied, token type is " + to_string(tokenType); + PermissionCheckFailRadar(info, "VerifyCaller"); + throw BError(BError::Codes::SA_REFUSED_ACT, + string("Permission denied, token type is ").append(to_string(tokenType))); + } + uint64_t fullTokenId = OHOS::IPCSkeleton::GetCallingFullTokenID(); + if (!Security::AccessToken::TokenIdKit::IsSystemAppByFullTokenID(fullTokenId)) { + std::string info = "Permission denied, token type is " + to_string(tokenType); + PermissionCheckFailRadar(info, "VerifyCaller"); + throw BError(BError::Codes::SA_REFUSED_ACT, + string("Permission denied, token type is ").append(to_string(tokenType))); } break; } case Security::AccessToken::ATokenTypeEnum::TOKEN_SHELL: if (IPCSkeleton::GetCallingUid() != BConstants::SYSTEM_UID) { - throw BError(BError::Codes::SA_INVAL_ARG, "Calling uid is invalid"); + std::string info = "invalid calling uid"; + PermissionCheckFailRadar(info, "VerifyCaller"); + throw BError(BError::Codes::SA_REFUSED_ACT, "Calling uid is invalid"); } break; default: - throw BError(BError::Codes::SA_INVAL_ARG, string("Invalid token type ").append(to_string(tokenType))); + std::string info = "Permission denied, token type is " + to_string(tokenType); + PermissionCheckFailRadar(info, "VerifyCaller"); + throw BError(BError::Codes::SA_REFUSED_ACT, string("Invalid token type ").append(to_string(tokenType))); break; } } @@ -245,12 +436,17 @@ ErrCode Service::InitRestoreSession(sptr remote) HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); try { VerifyCaller(); - return session_->Active({ + ErrCode errCode = session_->Active({ .clientToken = IPCSkeleton::GetCallingTokenID(), .scenario = IServiceReverse::Scenario::RESTORE, .clientProxy = remote, .userId = GetUserIdDefault(), }); + if (errCode == 0) { + ClearFailedBundles(); + successBundlesNum_ = 0; + } + return errCode; } catch (const BError &e) { StopAll(nullptr, true); return e.GetCode(); @@ -271,25 +467,41 @@ ErrCode Service::InitBackupSession(sptr remote) int32_t oldSize = StorageMgrAdapter::UpdateMemPara(BConstants::BACKUP_VFS_CACHE_PRESSURE); HILOGE("InitBackupSession oldSize %{public}d", oldSize); session_->SetMemParaCurSize(oldSize); - return session_->Active({ + ErrCode errCode = session_->Active({ .clientToken = IPCSkeleton::GetCallingTokenID(), .scenario = IServiceReverse::Scenario::BACKUP, .clientProxy = remote, .userId = GetUserIdDefault(), }); + if (errCode == 0) { + ClearFailedBundles(); + successBundlesNum_ = 0; + } + return errCode; } catch (const BError &e) { StopAll(nullptr, true); return e.GetCode(); + } catch (const exception &e) { + HILOGI("Catched an unexpected low-level exception %{public}s", e.what()); + return EPERM; + } catch (...) { + HILOGI("Unexpected exception"); + return EPERM; } } ErrCode Service::Start() { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); - VerifyCaller(session_->GetScenario()); - session_->Start(); - OnStartSched(); - return BError(BError::Codes::OK); + try { + VerifyCaller(session_->GetScenario()); + session_->Start(); + OnStartSched(); + return BError(BError::Codes::OK); + } catch (const BError &e) { + HILOGE("Failde to Start"); + return e.GetCode(); + } } static bool SpecialVersion(const string &versionName) @@ -303,7 +515,7 @@ static bool SpecialVersion(const string &versionName) return false; } -static void OnBundleStarted(BError error, sptr session, const BundleName &bundleName) +void Service::OnBundleStarted(BError error, sptr session, const BundleName &bundleName) { IServiceReverse::Scenario scenario = session->GetScenario(); if (scenario == IServiceReverse::Scenario::RESTORE && BackupPara().GetBackupOverrideIncrementalRestore() && @@ -312,6 +524,7 @@ static void OnBundleStarted(BError error, sptr session, const } else if (scenario == IServiceReverse::Scenario::RESTORE) { session->GetServiceReverseProxy()->RestoreOnBundleStarted(error, bundleName); } + BundleBeginRadarReport(bundleName, error.GetCode(), scenario); } static vector GetRestoreBundleNames(UniqueFd fd, @@ -325,14 +538,13 @@ static vector GetRestoreBundleNames(UniqueFd fd, auto cache = cachedEntity.Structuralize(); auto bundleInfos = cache.GetBundleInfos(); if (!bundleInfos.size()) { - HILOGE("GetRestoreBundleNames bundleInfos is empty."); throw BError(BError::Codes::SA_INVAL_ARG, "Json entity caps is empty"); } - HILOGI("restoreInfos size is:%{public}zu", restoreInfos.size()); vector restoreBundleInfos {}; for (auto &restoreInfo : restoreInfos) { if (SAUtils::IsSABundleName(restoreInfo.name)) { BJsonEntityCaps::BundleInfo info = {.name = restoreInfo.name, + .appIndex = restoreInfo.appIndex, .versionCode = restoreInfo.versionCode, .versionName = restoreInfo.versionName, .spaceOccupied = restoreInfo.spaceOccupied, @@ -343,13 +555,15 @@ static vector GetRestoreBundleNames(UniqueFd fd, restoreBundleInfos.emplace_back(info); continue; } - auto it = find_if(bundleInfos.begin(), bundleInfos.end(), - [&restoreInfo](const auto &obj) { return obj.name == restoreInfo.name; }); + auto it = find_if(bundleInfos.begin(), bundleInfos.end(), [&restoreInfo](const auto &obj) { + return obj.name == restoreInfo.name && obj.appIndex == restoreInfo.appIndex; + }); if (it == bundleInfos.end()) { HILOGE("Bundle not need restore, bundleName is %{public}s.", restoreInfo.name.c_str()); continue; } BJsonEntityCaps::BundleInfo info = {.name = (*it).name, + .appIndex = (*it).appIndex, .versionCode = (*it).versionCode, .versionName = (*it).versionName, .spaceOccupied = (*it).spaceOccupied, @@ -359,21 +573,21 @@ static vector GetRestoreBundleNames(UniqueFd fd, .restoreDeps = restoreInfo.restoreDeps}; restoreBundleInfos.emplace_back(info); } - HILOGI("restoreBundleInfos size is:%{public}zu", restoreInfos.size()); return restoreBundleInfos; } -static void HandleExceptionOnAppendBundles(sptr session, +void Service::HandleExceptionOnAppendBundles(sptr session, const vector &appendBundleNames, const vector &restoreBundleNames) { if (appendBundleNames.size() != restoreBundleNames.size()) { - HILOGE("AppendBundleNames not equal restoreBundleNames."); + HILOGE("AppendBundleNames not equal restoreBundleNames, appendBundleNames size:%{public}zu," + "restoreBundleNames size:%{public}zu", appendBundleNames.size(), restoreBundleNames.size()); for (auto bundleName : appendBundleNames) { auto it = find_if(restoreBundleNames.begin(), restoreBundleNames.end(), [&bundleName](const auto &obj) { return obj == bundleName; }); if (it == restoreBundleNames.end()) { HILOGE("AppendBundles failed, bundleName = %{public}s.", bundleName.c_str()); - OnBundleStarted(BError(BError::Codes::SA_INVAL_ARG), session, bundleName); + OnBundleStarted(BError(BError::Codes::SA_BUNDLE_INFO_EMPTY), session, bundleName); } } } @@ -383,43 +597,86 @@ ErrCode Service::AppendBundlesRestoreSession(UniqueFd fd, const vector &bundleInfos, RestoreTypeEnum restoreType, int32_t userId) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); - HILOGI("Begin"); try { - session_->IncreaseSessionCnt(); + if (session_ == nullptr || isCleanService_.load()) { + HILOGE("AppendBundles restore session with infos error, session is empty"); + return BError(BError::Codes::SA_INVAL_ARG); + } + session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); + session_->SetImplRestoreType(restoreType); if (userId != DEFAULT_INVAL_VALUE) { /* multi user scenario */ session_->SetSessionUserId(userId); + } else { + session_->SetSessionUserId(GetUserIdDefault()); } VerifyCaller(IServiceReverse::Scenario::RESTORE); std::vector bundleNamesOnly; + std::map isClearDataFlags; std::map> bundleNameDetailMap = - BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly, userId); - auto restoreInfos = GetRestoreBundleNames(move(fd), session_, bundleNamesOnly); + BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly, + session_->GetSessionUserId(), isClearDataFlags); + auto restoreInfos = GetRestoreBundleNames(move(fd), session_, bundleNames); auto restoreBundleNames = SvcRestoreDepsManager::GetInstance().GetRestoreBundleNames(restoreInfos, restoreType); HandleExceptionOnAppendBundles(session_, bundleNames, restoreBundleNames); if (restoreBundleNames.empty()) { HILOGE("AppendBundlesRestoreSession failed, restoreBundleNames is empty."); - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return BError(BError::Codes::OK); } session_->AppendBundles(restoreBundleNames); - SetCurrentSessProperties(restoreInfos, restoreBundleNames, bundleNameDetailMap, restoreType); + SetCurrentSessProperties(restoreInfos, restoreBundleNames, bundleNameDetailMap, + isClearDataFlags, restoreType); OnStartSched(); - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGI("End"); return BError(BError::Codes::OK); } catch (const BError &e) { HILOGE("Catch exception"); HandleExceptionOnAppendBundles(session_, bundleNames, {}); - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return e.GetCode(); } catch (...) { HILOGE("Unexpected exception"); HandleExceptionOnAppendBundles(session_, bundleNames, {}); - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return EPERM; } } +void Service::SetCurrentSessProperties(std::vector &restoreBundleInfos, + std::vector &restoreBundleNames, RestoreTypeEnum restoreType) +{ + HILOGI("Start"); + for (auto restoreInfo : restoreBundleInfos) { + auto it = find_if(restoreBundleNames.begin(), restoreBundleNames.end(), [&restoreInfo](const auto &bundleName) { + std::string bundleNameIndex = BJsonUtil::BuildBundleNameIndexInfo(restoreInfo.name, restoreInfo.appIndex); + return bundleName == bundleNameIndex; + }); + if (it == restoreBundleNames.end()) { + throw BError(BError::Codes::SA_BUNDLE_INFO_EMPTY, "Can't find bundle name"); + } + HILOGI("bundleName: %{public}s, extensionName: %{public}s", restoreInfo.name.c_str(), + restoreInfo.extensionName.c_str()); + std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(restoreInfo.name, restoreInfo.appIndex); + if ((!restoreInfo.allToBackup && !SpecialVersion(restoreInfo.versionName)) || + (restoreInfo.extensionName.empty() && !SAUtils::IsSABundleName(restoreInfo.name))) { + OnBundleStarted(BError(BError::Codes::SA_FORBID_BACKUP_RESTORE), session_, bundleNameIndexInfo); + session_->RemoveExtInfo(bundleNameIndexInfo); + continue; + } + session_->SetBundleRestoreType(bundleNameIndexInfo, restoreType); + session_->SetBundleVersionCode(bundleNameIndexInfo, restoreInfo.versionCode); + session_->SetBundleVersionName(bundleNameIndexInfo, restoreInfo.versionName); + session_->SetBundleDataSize(bundleNameIndexInfo, restoreInfo.spaceOccupied); + if (BundleMgrAdapter::IsUser0BundleName(bundleNameIndexInfo, session_->GetSessionUserId())) { + SendUserIdToApp(bundleNameIndexInfo, session_->GetSessionUserId()); + } + session_->SetBackupExtName(bundleNameIndexInfo, restoreInfo.extensionName); + session_->SetIsReadyLaunch(bundleNameIndexInfo); + } + HILOGI("End"); +} + ErrCode Service::AppendBundlesRestoreSession(UniqueFd fd, const vector &bundleNames, RestoreTypeEnum restoreType, @@ -427,91 +684,94 @@ ErrCode Service::AppendBundlesRestoreSession(UniqueFd fd, { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); try { - session_->IncreaseSessionCnt(); + if (session_ == nullptr || isCleanService_.load()) { + HILOGE("AppendBundles restore session error, session is empty"); + return BError(BError::Codes::SA_INVAL_ARG); + } + session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); + session_->SetImplRestoreType(restoreType); if (userId != DEFAULT_INVAL_VALUE) { /* multi user scenario */ session_->SetSessionUserId(userId); + } else { + session_->SetSessionUserId(GetUserIdDefault()); } VerifyCaller(IServiceReverse::Scenario::RESTORE); auto restoreInfos = GetRestoreBundleNames(move(fd), session_, bundleNames); auto restoreBundleNames = SvcRestoreDepsManager::GetInstance().GetRestoreBundleNames(restoreInfos, restoreType); + HandleExceptionOnAppendBundles(session_, bundleNames, restoreBundleNames); if (restoreBundleNames.empty()) { - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGW("RestoreBundleNames is empty."); return BError(BError::Codes::OK); } session_->AppendBundles(restoreBundleNames); - for (auto restoreInfo : restoreInfos) { - auto it = find_if(restoreBundleNames.begin(), restoreBundleNames.end(), - [&restoreInfo](const auto &bundleName) { return bundleName == restoreInfo.name; }); - if (it == restoreBundleNames.end()) { - throw BError(BError::Codes::SA_BUNDLE_INFO_EMPTY, "Can't find bundle name"); - } - HILOGI("bundleName: %{public}s, extensionName: %{public}s", restoreInfo.name.c_str(), - restoreInfo.extensionName.c_str()); - if ((restoreInfo.allToBackup == false && !SpecialVersion(restoreInfo.versionName)) || - (restoreInfo.extensionName.empty() && !SAUtils::IsSABundleName(restoreInfo.name))) { - OnBundleStarted(BError(BError::Codes::SA_FORBID_BACKUP_RESTORE), session_, restoreInfo.name); - session_->RemoveExtInfo(restoreInfo.name); - continue; - } - session_->SetBundleRestoreType(restoreInfo.name, restoreType); - session_->SetBundleVersionCode(restoreInfo.name, restoreInfo.versionCode); - session_->SetBundleVersionName(restoreInfo.name, restoreInfo.versionName); - session_->SetBundleDataSize(restoreInfo.name, restoreInfo.spaceOccupied); - session_->SetBackupExtName(restoreInfo.name, restoreInfo.extensionName); - } + SetCurrentSessProperties(restoreInfos, restoreBundleNames, restoreType); OnStartSched(); - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return BError(BError::Codes::OK); } catch (const BError &e) { - session_->DecreaseSessionCnt(); + HILOGE("Catch exception"); + HandleExceptionOnAppendBundles(session_, bundleNames, {}); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return e.GetCode(); } catch (...) { - session_->DecreaseSessionCnt(); - HILOGI("Unexpected exception"); + HILOGE("Unexpected exception"); + HandleExceptionOnAppendBundles(session_, bundleNames, {}); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return EPERM; } } void Service::SetCurrentSessProperties(std::vector &restoreBundleInfos, std::vector &restoreBundleNames, - std::map> &bundleNameDetailMap, RestoreTypeEnum restoreType) + std::map> &bundleNameDetailMap, + std::map &isClearDataFlags, RestoreTypeEnum restoreType) { HILOGI("Start"); for (auto restoreInfo : restoreBundleInfos) { auto it = find_if(restoreBundleNames.begin(), restoreBundleNames.end(), - [&restoreInfo](const auto &bundleName) { return bundleName == restoreInfo.name; }); + [&restoreInfo](const auto &bundleName) { + std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(restoreInfo.name, + restoreInfo.appIndex); + return bundleName == bundleNameIndexInfo; + }); if (it == restoreBundleNames.end()) { throw BError(BError::Codes::SA_BUNDLE_INFO_EMPTY, "Can't find bundle name"); } HILOGD("bundleName: %{public}s, extensionName: %{public}s", restoreInfo.name.c_str(), restoreInfo.extensionName.c_str()); - if ((restoreInfo.allToBackup == false && !SpecialVersion(restoreInfo.versionName)) || + std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(restoreInfo.name, restoreInfo.appIndex); + if ((!restoreInfo.allToBackup && !SpecialVersion(restoreInfo.versionName)) || (restoreInfo.extensionName.empty() && !SAUtils::IsSABundleName(restoreInfo.name))) { - OnBundleStarted(BError(BError::Codes::SA_FORBID_BACKUP_RESTORE), session_, restoreInfo.name); - session_->RemoveExtInfo(restoreInfo.name); + OnBundleStarted(BError(BError::Codes::SA_FORBID_BACKUP_RESTORE), session_, bundleNameIndexInfo); + session_->RemoveExtInfo(bundleNameIndexInfo); continue; } - session_->SetBundleRestoreType(restoreInfo.name, restoreType); - session_->SetBundleVersionCode(restoreInfo.name, restoreInfo.versionCode); - session_->SetBundleVersionName(restoreInfo.name, restoreInfo.versionName); - session_->SetBundleDataSize(restoreInfo.name, restoreInfo.spaceOccupied); - session_->SetBackupExtName(restoreInfo.name, restoreInfo.extensionName); + session_->SetBundleRestoreType(bundleNameIndexInfo, restoreType); + session_->SetBundleVersionCode(bundleNameIndexInfo, restoreInfo.versionCode); + session_->SetBundleVersionName(bundleNameIndexInfo, restoreInfo.versionName); + session_->SetBundleDataSize(bundleNameIndexInfo, restoreInfo.spaceOccupied); + auto iter = isClearDataFlags.find(bundleNameIndexInfo); + if (iter != isClearDataFlags.end()) { + session_->SetClearDataFlag(bundleNameIndexInfo, iter->second); + } BJsonUtil::BundleDetailInfo broadCastInfo; BJsonUtil::BundleDetailInfo uniCastInfo; - bool broadCastRet = BJsonUtil::FindBundleInfoByName(bundleNameDetailMap, restoreInfo.name, BROADCAST_TYPE, + bool broadCastRet = BJsonUtil::FindBundleInfoByName(bundleNameDetailMap, bundleNameIndexInfo, BROADCAST_TYPE, broadCastInfo); if (broadCastRet) { bool notifyRet = DelayedSingleton::GetInstance()->NotifyBundleDetail(broadCastInfo); HILOGI("Publish event end, notify result is:%{public}d", notifyRet); } - bool uniCastRet = BJsonUtil::FindBundleInfoByName(bundleNameDetailMap, restoreInfo.name, UNICAST_TYPE, + bool uniCastRet = BJsonUtil::FindBundleInfoByName(bundleNameDetailMap, bundleNameIndexInfo, UNICAST_TYPE, uniCastInfo); if (uniCastRet) { HILOGI("current bundle, unicast info:%{public}s", GetAnonyString(uniCastInfo.detail).c_str()); - session_->SetBackupExtInfo(restoreInfo.name, uniCastInfo.detail); + session_->SetBackupExtInfo(bundleNameIndexInfo, uniCastInfo.detail); } + session_->SetBackupExtName(bundleNameIndexInfo, restoreInfo.extensionName); + session_->SetIsReadyLaunch(bundleNameIndexInfo); } HILOGI("End"); } @@ -520,208 +780,244 @@ ErrCode Service::AppendBundlesBackupSession(const vector &bundleName { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); try { - session_->IncreaseSessionCnt(); // BundleMgrAdapter::GetBundleInfos可能耗时 - VerifyCaller(IServiceReverse::Scenario::BACKUP); - auto backupInfos = BundleMgrAdapter::GetBundleInfos(bundleNames, session_->GetSessionUserId()); - session_->AppendBundles(bundleNames); - for (auto info : backupInfos) { - session_->SetBundleDataSize(info.name, info.spaceOccupied); - session_->SetBackupExtName(info.name, info.extensionName); - if (info.allToBackup == false) { - session_->GetServiceReverseProxy()->BackupOnBundleStarted( - BError(BError::Codes::SA_FORBID_BACKUP_RESTORE), info.name); - session_->RemoveExtInfo(info.name); - } + if (session_ == nullptr || isCleanService_.load()) { + HILOGE("AppendBundles backup session error, session is empty"); + return BError(BError::Codes::SA_INVAL_ARG); } + session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); // BundleMgrAdapter::GetBundleInfos可能耗时 + VerifyCaller(IServiceReverse::Scenario::BACKUP); + auto bundleDetails = MakeDetailList(bundleNames); + auto backupInfos = BundleMgrAdapter::GetBundleInfosForAppend(bundleDetails, session_->GetSessionUserId()); + std::vector supportBackupNames = GetSupportBackupBundleNames(backupInfos, false, bundleNames); + session_->AppendBundles(supportBackupNames); + SetCurrentBackupSessProperties(supportBackupNames, session_->GetSessionUserId(), backupInfos, false); OnStartSched(); - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return BError(BError::Codes::OK); } catch (const BError &e) { - session_->DecreaseSessionCnt(); HILOGE("Failed, errCode = %{public}d", e.GetCode()); + HandleExceptionOnAppendBundles(session_, bundleNames, {}); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return e.GetCode(); } catch (const exception &e) { - session_->DecreaseSessionCnt(); - HILOGI("Catched an unexpected low-level exception %{public}s", e.what()); + HILOGE("Catched an unexpected low-level exception %{public}s", e.what()); + HandleExceptionOnAppendBundles(session_, bundleNames, {}); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return EPERM; } catch (...) { - session_->DecreaseSessionCnt(); - HILOGI("Unexpected exception"); + HILOGE("Unexpected exception"); + HandleExceptionOnAppendBundles(session_, bundleNames, {}); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return EPERM; } } ErrCode Service::AppendBundlesDetailsBackupSession(const vector &bundleNames, - const vector &bundleInfos) + const vector &bundleInfos) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); try { - session_->IncreaseSessionCnt(); // BundleMgrAdapter::GetBundleInfos可能耗时 + if (session_ == nullptr || isCleanService_.load()) { + HILOGE("AppendBundles backup session with infos error, session is empty"); + return BError(BError::Codes::SA_INVAL_ARG); + } + session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); // BundleMgrAdapter::GetBundleInfos可能耗时 VerifyCaller(IServiceReverse::Scenario::BACKUP); std::vector bundleNamesOnly; + std::map isClearDataFlags; std::map> bundleNameDetailMap = - BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly, session_->GetSessionUserId()); - auto backupInfos = BundleMgrAdapter::GetBundleInfos(bundleNames, session_->GetSessionUserId()); - session_->AppendBundles(bundleNames); - for (auto info : backupInfos) { - session_->SetBundleDataSize(info.name, info.spaceOccupied); - session_->SetBackupExtName(info.name, info.extensionName); - if (info.allToBackup == false) { - session_->GetServiceReverseProxy()->BackupOnBundleStarted( - BError(BError::Codes::SA_FORBID_BACKUP_RESTORE), info.name); - session_->RemoveExtInfo(info.name); - } - BJsonUtil::BundleDetailInfo uniCastInfo; - bool uniCastRet = BJsonUtil::FindBundleInfoByName(bundleNameDetailMap, info.name, UNICAST_TYPE, - uniCastInfo); - if (uniCastRet) { - HILOGI("current bundle, unicast info:%{public}s", GetAnonyString(uniCastInfo.detail).c_str()); - session_->SetBackupExtInfo(info.name, uniCastInfo.detail); - } - } + BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly, + session_->GetSessionUserId(), isClearDataFlags); + auto bundleDetails = MakeDetailList(bundleNames); + auto backupInfos = BundleMgrAdapter::GetBundleInfosForAppend(bundleDetails, session_->GetSessionUserId()); + std::vector supportBackupNames = GetSupportBackupBundleNames(backupInfos, false, bundleNames); + session_->AppendBundles(supportBackupNames); + HandleCurGroupBackupInfos(backupInfos, bundleNameDetailMap, isClearDataFlags); OnStartSched(); - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return BError(BError::Codes::OK); } catch (const BError &e) { - session_->DecreaseSessionCnt(); HILOGE("Failed, errCode = %{public}d", e.GetCode()); + HandleExceptionOnAppendBundles(session_, bundleNames, {}); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return e.GetCode(); - } catch (const exception &e) { - session_->DecreaseSessionCnt(); - HILOGE("Catched an unexpected low-level exception %{public}s", e.what()); - return EPERM; } catch(...) { - session_->DecreaseSessionCnt(); HILOGE("Unexpected exception"); + HandleExceptionOnAppendBundles(session_, bundleNames, {}); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return EPERM; } } -ErrCode Service::Finish() +void Service::HandleCurGroupBackupInfos(std::vector &backupInfos, + std::map> &bundleNameDetailMap, + std::map &isClearDataFlags) { - HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); - VerifyCaller(session_->GetScenario()); - session_->Finish(); - OnAllBundlesFinished(BError(BError::Codes::OK)); - return BError(BError::Codes::OK); + for (auto &info : backupInfos) { + HILOGI("Current backupInfo bundleName:%{public}s, extName:%{public}s, appIndex:%{public}d", + info.name.c_str(), info.extensionName.c_str(), info.appIndex); + std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(info.name, info.appIndex); + SetCurrentSessProperties(info, isClearDataFlags, bundleNameIndexInfo); + BJsonUtil::BundleDetailInfo uniCastInfo; + if (BJsonUtil::FindBundleInfoByName(bundleNameDetailMap, bundleNameIndexInfo, UNICAST_TYPE, uniCastInfo)) { + HILOGI("current bundle:%{public}s, unicast info:%{public}s, unicast info size:%{public}zu", + bundleNameIndexInfo.c_str(), GetAnonyString(uniCastInfo.detail).c_str(), uniCastInfo.detail.size()); + session_->SetBackupExtInfo(bundleNameIndexInfo, uniCastInfo.detail); + } + session_->SetBackupExtName(bundleNameIndexInfo, info.extensionName); + session_->SetIsReadyLaunch(bundleNameIndexInfo); + } } -ErrCode Service::PublishFile(const BFileInfo &fileInfo) +ErrCode Service::ServiceResultReport(const std::string restoreRetInfo, + BackupRestoreScenario sennario, ErrCode errCode) { + string callerName = ""; HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); try { - VerifyCaller(IServiceReverse::Scenario::RESTORE); - if (!fileInfo.fileName.empty()) { - HILOGE("Forbit to use publishFile with fileName for App"); - return EPERM; - } - auto backUpConnection = session_->GetExtConnection(fileInfo.owner); - if (backUpConnection == nullptr) { - HILOGE("PublishFile error, backUpConnection is empty"); - return BError(BError::Codes::SA_INVAL_ARG); - } - auto proxy = backUpConnection->GetBackupExtProxy(); - if (!proxy) { - HILOGE("PublishFile error, Extension backup Proxy is empty"); - return BError(BError::Codes::SA_INVAL_ARG); - } - ErrCode res = proxy->PublishFile(fileInfo.fileName); - if (res) { - HILOGE("Failed to publish file for backup extension"); + callerName = VerifyCallerAndGetCallerName(); + SendEndAppGalleryNotify(callerName); + if (sennario == BackupRestoreScenario::FULL_RESTORE) { + session_->GetServiceReverseProxy()->RestoreOnResultReport(restoreRetInfo, callerName, errCode); + NotifyCloneBundleFinish(callerName, sennario); + } else if (sennario == BackupRestoreScenario::INCREMENTAL_RESTORE) { + session_->GetServiceReverseProxy()->IncrementalRestoreOnResultReport(restoreRetInfo, callerName, errCode); + NotifyCloneBundleFinish(callerName, sennario); + } else if (sennario == BackupRestoreScenario::FULL_BACKUP) { + session_->GetServiceReverseProxy()->BackupOnResultReport(restoreRetInfo, callerName); + } else if (sennario == BackupRestoreScenario::INCREMENTAL_BACKUP) { + session_->GetServiceReverseProxy()->IncrementalBackupOnResultReport(restoreRetInfo, callerName); } - - return res; + return BError(BError::Codes::OK); } catch (const BError &e) { - return e.GetCode(); + NotifyCloneBundleFinish(callerName, sennario); + return e.GetCode(); // 任意异常产生,终止监听该任务 } catch (const exception &e) { + NotifyCloneBundleFinish(callerName, sennario); HILOGI("Catched an unexpected low-level exception %{public}s", e.what()); return EPERM; } catch (...) { + NotifyCloneBundleFinish(callerName, sennario); HILOGI("Unexpected exception"); return EPERM; } } -ErrCode Service::AppFileReady(const string &fileName, UniqueFd fd, int32_t errCode) +ErrCode Service::SAResultReport(const std::string bundleName, const std::string restoreRetInfo, + const ErrCode errCode, const BackupRestoreScenario sennario) +{ + if (sennario == BackupRestoreScenario::FULL_RESTORE) { + session_->GetServiceReverseProxy()->RestoreOnResultReport(restoreRetInfo, bundleName); + } else if (sennario == BackupRestoreScenario::INCREMENTAL_RESTORE) { + session_->GetServiceReverseProxy()->IncrementalRestoreOnResultReport(restoreRetInfo, bundleName); + } else if (sennario == BackupRestoreScenario::FULL_BACKUP) { + session_->GetServiceReverseProxy()->BackupOnResultReport(restoreRetInfo, bundleName); + session_->GetServiceReverseProxy()->BackupOnBundleFinished(errCode, bundleName); + } else if (sennario == BackupRestoreScenario::INCREMENTAL_BACKUP) { + session_->GetServiceReverseProxy()->IncrementalBackupOnResultReport(restoreRetInfo, bundleName); + } + if (sennario == BackupRestoreScenario::FULL_RESTORE || sennario == BackupRestoreScenario::INCREMENTAL_RESTORE) { + BundleEndRadarReport(bundleName, errCode, IServiceReverse::Scenario::RESTORE); + } else if (sennario == BackupRestoreScenario::FULL_BACKUP || + sennario == BackupRestoreScenario::INCREMENTAL_BACKUP) { + BundleEndRadarReport(bundleName, errCode, IServiceReverse::Scenario::BACKUP); + } + return SADone(errCode, bundleName); +} + +void Service::NotifyCloneBundleFinish(std::string bundleName, const BackupRestoreScenario sennario) { - HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); try { - string callerName = VerifyCallerAndGetCallerName(); - HILOGD("Caller name is:%{public}s", callerName.c_str()); - if (fileName.find('/') != string::npos) { - throw BError(BError::Codes::SA_INVAL_ARG, "Filename is not valid"); - } - if (fileName == BConstants::EXT_BACKUP_MANAGE) { - fd = session_->OnBundleExtManageInfo(callerName, move(fd)); + if (sennario != BackupRestoreScenario::FULL_RESTORE && + sennario != BackupRestoreScenario::INCREMENTAL_RESTORE) { + return; } - - session_->GetServiceReverseProxy()->BackupOnFileReady(callerName, fileName, move(fd), errCode); - - if (session_->OnBundleFileReady(callerName, fileName)) { - auto backUpConnection = session_->GetExtConnection(callerName); + if (session_->OnBundleFileReady(bundleName)) { + std::shared_ptr mutexPtr = GetExtensionMutex(bundleName); + if (mutexPtr == nullptr) { + HILOGE("extension mutex ptr is nullptr"); + return; + } + std::lock_guard lock(mutexPtr->callbackMutex); + auto backUpConnection = session_->GetExtConnection(bundleName); if (backUpConnection == nullptr) { - HILOGE("AppFileReady error, backUpConnection is empty"); - return BError(BError::Codes::SA_INVAL_ARG); + throw BError(BError::Codes::SA_INVAL_ARG, "backUpConnection is empty"); } auto proxy = backUpConnection->GetBackupExtProxy(); if (!proxy) { - HILOGE("AppFileReady error, Extension backup Proxy is empty"); - return BError(BError::Codes::SA_INVAL_ARG); + throw BError(BError::Codes::SA_INVAL_ARG, "Extension backup Proxy is empty"); } - // 通知extension清空缓存 proxy->HandleClear(); - // 清除Timer - session_->BundleExtTimerStop(callerName); - // 通知TOOL 备份完成 - session_->GetServiceReverseProxy()->BackupOnBundleFinished(BError(BError::Codes::OK), callerName); - // 断开extension + session_->StopFwkTimer(bundleName); + session_->StopExtTimer(bundleName); backUpConnection->DisconnectBackupExtAbility(); - ClearSessionAndSchedInfo(callerName); + ClearSessionAndSchedInfo(bundleName); } + RemoveExtensionMutex(bundleName); OnAllBundlesFinished(BError(BError::Codes::OK)); - return BError(BError::Codes::OK); - } catch (const BError &e) { - return e.GetCode(); // 任意异常产生,终止监听该任务 - } catch (const exception &e) { - HILOGI("Catched an unexpected low-level exception %{public}s", e.what()); - return EPERM; } catch (...) { HILOGI("Unexpected exception"); - return EPERM; + ReleaseOnException(); } } -ErrCode Service::AppDone(ErrCode errCode) +ErrCode Service::LaunchBackupSAExtension(const BundleName &bundleName) +{ + string extInfo = session_->GetBackupExtInfo(bundleName); + IServiceReverse::Scenario scenario = session_->GetScenario(); + if (SAUtils::IsSABundleName(bundleName)) { + auto saBackUpConnection = session_->GetSAExtConnection(bundleName); + std::shared_ptr saConnection = saBackUpConnection.lock(); + if (saConnection == nullptr) { + HILOGE("lock sa connection ptr is nullptr"); + return BError(BError::Codes::SA_INVAL_ARG); + } + if (scenario == IServiceReverse::Scenario::BACKUP) { + return saConnection->ConnectBackupSAExt(bundleName, BConstants::EXTENSION_BACKUP, extInfo); + } else if (scenario == IServiceReverse::Scenario::RESTORE) { + return saConnection->ConnectBackupSAExt(bundleName, BConstants::EXTENSION_RESTORE, extInfo); + } + } + return BError(BError::Codes::OK); +} + +ErrCode Service::GetFileHandle(const string &bundleName, const string &fileName) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); try { - if (session_ == nullptr) { - HILOGE("App finish error, session info is empty"); - return BError(BError::Codes::SA_INVAL_ARG); + VerifyCaller(IServiceReverse::Scenario::RESTORE); + + bool updateRes = SvcRestoreDepsManager::GetInstance().UpdateToRestoreBundleMap(bundleName, fileName); + if (updateRes) { + return BError(BError::Codes::OK); } - string callerName = VerifyCallerAndGetCallerName(); - HILOGI("Begin, callerName is: %{public}s, errCode: %{public}d", callerName.c_str(), errCode); - if (session_->OnBundleFileReady(callerName) || errCode != BError(BError::Codes::OK)) { - auto backUpConnection = session_->GetExtConnection(callerName); + auto action = session_->GetServiceSchedAction(bundleName); + if (action == BConstants::ServiceSchedAction::RUNNING) { + auto backUpConnection = session_->GetExtConnection(bundleName); if (backUpConnection == nullptr) { - HILOGE("App finish error, backUpConnection is empty"); + HILOGE("GetFileHandle error, backUpConnection is empty"); return BError(BError::Codes::SA_INVAL_ARG); } auto proxy = backUpConnection->GetBackupExtProxy(); if (!proxy) { - throw BError(BError::Codes::SA_INVAL_ARG, "Extension backup Proxy is empty"); + HILOGE("GetFileHandle error, Extension backup Proxy is empty"); + return BError(BError::Codes::SA_INVAL_ARG); } - proxy->HandleClear(); - session_->BundleExtTimerStop(callerName); - NotifyCallerCurAppDone(errCode, callerName); - backUpConnection->DisconnectBackupExtAbility(); - ClearSessionAndSchedInfo(callerName); + int32_t errCode = 0; + UniqueFd fd = proxy->GetFileHandle(fileName, errCode); + if (errCode != ERR_OK) { + AppRadar::Info info (bundleName, "", ""); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "Service::GetFileHandle", GetUserIdDefault(), + BizStageRestore::BIZ_STAGE_GET_FILE_HANDLE_FAIL, errCode); + } + session_->GetServiceReverseProxy()->RestoreOnFileReady(bundleName, fileName, move(fd), errCode); + FileReadyRadarReport(bundleName, fileName, errCode, IServiceReverse::Scenario::RESTORE); + } else { + session_->SetExtFileNameRequest(bundleName, fileName); } - OnAllBundlesFinished(BError(BError::Codes::OK)); return BError(BError::Codes::OK); } catch (const BError &e) { - HILOGE("AppDone error, err code is: %{public}d", e.GetCode()); - return e.GetCode(); // 任意异常产生,终止监听该任务 + return e.GetCode(); } catch (const exception &e) { HILOGI("Catched an unexpected low-level exception %{public}s", e.what()); return EPERM; @@ -731,222 +1027,16 @@ ErrCode Service::AppDone(ErrCode errCode) } } -ErrCode Service::ServiceResultReport(const std::string restoreRetInfo, - BackupRestoreScenario sennario, ErrCode errCode) -{ - HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); - try { - string callerName = VerifyCallerAndGetCallerName(); - if (sennario == BackupRestoreScenario::FULL_RESTORE) { - session_->GetServiceReverseProxy()->RestoreOnResultReport(restoreRetInfo, callerName, errCode); - NotifyCloneBundleFinish(callerName); - } else if (sennario == BackupRestoreScenario::INCREMENTAL_RESTORE) { - session_->GetServiceReverseProxy()->IncrementalRestoreOnResultReport(restoreRetInfo, callerName, errCode); - NotifyCloneBundleFinish(callerName); - } else if (sennario == BackupRestoreScenario::FULL_BACKUP) { - session_->GetServiceReverseProxy()->BackupOnResultReport(restoreRetInfo, callerName); - } else if (sennario == BackupRestoreScenario::INCREMENTAL_BACKUP) { - session_->GetServiceReverseProxy()->IncrementalBackupOnResultReport(restoreRetInfo, callerName); - } - - return BError(BError::Codes::OK); - } catch (const BError &e) { - return e.GetCode(); // 任意异常产生,终止监听该任务 - } catch (const exception &e) { - HILOGI("Catched an unexpected low-level exception %{public}s", e.what()); - return EPERM; - } catch (...) { - HILOGI("Unexpected exception"); - return EPERM; - } -} - -ErrCode Service::SAResultReport(const std::string bundleName, const std::string restoreRetInfo, - const ErrCode errCode, const BackupRestoreScenario sennario) -{ - if (sennario == BackupRestoreScenario::FULL_RESTORE) { - session_->GetServiceReverseProxy()->RestoreOnResultReport(restoreRetInfo, bundleName); - } else if (sennario == BackupRestoreScenario::INCREMENTAL_RESTORE) { - session_->GetServiceReverseProxy()->IncrementalRestoreOnResultReport(restoreRetInfo, bundleName); - } else if (sennario == BackupRestoreScenario::FULL_BACKUP) { - session_->GetServiceReverseProxy()->BackupOnResultReport(restoreRetInfo, bundleName); - session_->GetServiceReverseProxy()->BackupOnBundleFinished(errCode, bundleName); - } else if (sennario == BackupRestoreScenario::INCREMENTAL_BACKUP) { - session_->GetServiceReverseProxy()->IncrementalBackupOnResultReport(restoreRetInfo, bundleName); - } - return SADone(errCode, bundleName); -} - -void Service::NotifyCloneBundleFinish(std::string bundleName) -{ - if (session_->OnBundleFileReady(bundleName)) { - auto backUpConnection = session_->GetExtConnection(bundleName); - if (backUpConnection == nullptr) { - throw BError(BError::Codes::SA_INVAL_ARG, "backUpConnection is empty"); - } - auto proxy = backUpConnection->GetBackupExtProxy(); - if (!proxy) { - throw BError(BError::Codes::SA_INVAL_ARG, "Extension backup Proxy is empty"); - } - proxy->HandleClear(); - session_->BundleExtTimerStop(bundleName); - backUpConnection->DisconnectBackupExtAbility(); - ClearSessionAndSchedInfo(bundleName); - } - SendEndAppGalleryNotify(bundleName); - OnAllBundlesFinished(BError(BError::Codes::OK)); -} - -ErrCode Service::LaunchBackupExtension(const BundleName &bundleName) -{ - HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); - try { - HILOGI("begin %{public}s", bundleName.data()); - IServiceReverse::Scenario scenario = session_->GetScenario(); - BConstants::ExtensionAction action; - if (scenario == IServiceReverse::Scenario::BACKUP) { - action = BConstants::ExtensionAction::BACKUP; - } else if (scenario == IServiceReverse::Scenario::RESTORE) { - action = BConstants::ExtensionAction::RESTORE; - } else { - throw BError(BError::Codes::SA_INVAL_ARG, "Failed to scenario"); - } - if (SAUtils::IsSABundleName(bundleName)) { - return LaunchBackupSAExtension(bundleName); - } - AAFwk::Want want; - string backupExtName = session_->GetBackupExtName(bundleName); /* new device app ext name */ - HILOGD("backupExtName: %{public}s, bundleName: %{public}s", backupExtName.data(), bundleName.data()); - string versionName = session_->GetBundleVersionName(bundleName); /* old device app version name */ - int64_t versionCode = session_->GetBundleVersionCode(bundleName); /* old device app version code */ - RestoreTypeEnum restoreType = session_->GetBundleRestoreType(bundleName); /* app restore type */ - string bundleExtInfo = session_->GetBackupExtInfo(bundleName); - HILOGI("bundleExtInfo is:%{public}s", GetAnonyString(bundleExtInfo).c_str()); - - want.SetElementName(bundleName, backupExtName); - want.SetParam(BConstants::EXTENSION_ACTION_PARA, static_cast(action)); - want.SetParam(BConstants::EXTENSION_VERSION_CODE_PARA, static_cast(versionCode)); - want.SetParam(BConstants::EXTENSION_RESTORE_TYPE_PARA, static_cast(restoreType)); - want.SetParam(BConstants::EXTENSION_VERSION_NAME_PARA, versionName); - want.SetParam(BConstants::EXTENSION_RESTORE_EXT_INFO_PARA, bundleExtInfo); - want.SetParam(BConstants::EXTENSION_BACKUP_EXT_INFO_PARA, bundleExtInfo); - - auto backUpConnection = session_->GetExtConnection(bundleName); - if (backUpConnection == nullptr) { - HILOGE("LaunchBackupExtension error, backUpConnection is empty"); - return BError(BError::Codes::SA_INVAL_ARG); - } - ErrCode ret = backUpConnection->ConnectBackupExtAbility(want, session_->GetSessionUserId()); - return ret; - } catch (const BError &e) { - return e.GetCode(); - } catch (const exception &e) { - HILOGI("Catched an unexpected low-level exception %{public}s", e.what()); - return EPERM; - } catch (...) { - HILOGI("Unexpected exception"); - return EPERM; - } -} - -ErrCode Service::LaunchBackupSAExtension(const BundleName &bundleName) -{ - string extInfo = session_->GetBackupExtInfo(bundleName); - IServiceReverse::Scenario scenario = session_->GetScenario(); - if (SAUtils::IsSABundleName(bundleName)) { - auto saBackUpConnection = session_->GetSAExtConnection(bundleName); - std::shared_ptr saConnection = saBackUpConnection.lock(); - if (saConnection == nullptr) { - HILOGE("lock sa connection ptr is nullptr"); - return BError(BError::Codes::SA_INVAL_ARG); - } - if (scenario == IServiceReverse::Scenario::BACKUP) { - return saConnection->ConnectBackupSAExt(bundleName, BConstants::EXTENSION_BACKUP, extInfo); - } else if (scenario == IServiceReverse::Scenario::RESTORE) { - return saConnection->ConnectBackupSAExt(bundleName, BConstants::EXTENSION_RESTORE, extInfo); - } - } - return BError(BError::Codes::OK); -} - -ErrCode Service::GetFileHandle(const string &bundleName, const string &fileName) -{ - HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); - try { - VerifyCaller(IServiceReverse::Scenario::RESTORE); - - bool updateRes = SvcRestoreDepsManager::GetInstance().UpdateToRestoreBundleMap(bundleName, fileName); - if (updateRes) { - return BError(BError::Codes::OK); - } - auto action = session_->GetServiceSchedAction(bundleName); - if (action == BConstants::ServiceSchedAction::RUNNING) { - auto backUpConnection = session_->GetExtConnection(bundleName); - if (backUpConnection == nullptr) { - HILOGE("GetFileHandle error, backUpConnection is empty"); - return BError(BError::Codes::SA_INVAL_ARG); - } - auto proxy = backUpConnection->GetBackupExtProxy(); - if (!proxy) { - HILOGE("GetFileHandle error, Extension backup Proxy is empty"); - return BError(BError::Codes::SA_INVAL_ARG); - } - int32_t errCode = 0; - UniqueFd fd = proxy->GetFileHandle(fileName, errCode); - session_->GetServiceReverseProxy()->RestoreOnFileReady(bundleName, fileName, move(fd), errCode); - } else { - session_->SetExtFileNameRequest(bundleName, fileName); - } - return BError(BError::Codes::OK); - } catch (const BError &e) { - return e.GetCode(); - } catch (const exception &e) { - HILOGI("Catched an unexpected low-level exception %{public}s", e.what()); - return EPERM; - } catch (...) { - HILOGI("Unexpected exception"); - return EPERM; - } -} - -void Service::OnBackupExtensionDied(const string &&bundleName) +void Service::OnBackupExtensionDied(const string &&bundleName, bool isSecondCalled) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); try { string callName = move(bundleName); HILOGE("Backup <%{public}s> Extension Process Died", callName.c_str()); session_->VerifyBundleName(callName); - string versionName = session_->GetBundleVersionName(bundleName); /* old device app version name */ - string versionNameFlag = - versionName.substr(0, versionName.find_first_of(BConstants::VERSION_NAME_SEPARATOR_CHAR)); - if (versionNameFlag == BConstants::DEFAULT_VERSION_NAME && - session_->ValidRestoreDataType(RestoreTypeEnum::RESTORE_DATA_READDY)) { - ExtConnectDied(bundleName); - return; - } // 重新连接清理缓存 - HILOGE("Clear backup extension data, bundleName: %{public}s", bundleName.data()); - auto backUpConnection = session_->GetExtConnection(bundleName); - auto callConnected = [ptr {wptr(this)}](const string &&bundleName) { - HILOGE("OnBackupExtensionDied callConnected <%{public}s>", bundleName.c_str()); - auto thisPtr = ptr.promote(); - if (!thisPtr) { - HILOGW("this pointer is null."); - return; - } - thisPtr->ExtConnectDied(bundleName); - }; - if (backUpConnection == nullptr) { - HILOGE("OnBackupExtensionDied error. backUpConnection is empty"); - ExtConnectDied(bundleName); - return; - } - backUpConnection->SetCallback(callConnected); - auto ret = LaunchBackupExtension(bundleName); - if (ret) { - ExtConnectDied(bundleName); - return; - } + HILOGI("Clear backup extension data, bundleName: %{public}s", callName.c_str()); + ExtConnectDied(callName); } catch (...) { HILOGE("Unexpected exception, bundleName: %{public}s", bundleName.c_str()); ExtConnectDied(bundleName); @@ -959,22 +1049,33 @@ void Service::ExtConnectDied(const string &callName) HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); try { HILOGI("Begin, bundleName: %{public}s", callName.c_str()); + std::shared_ptr mutexPtr = GetExtensionMutex(callName); + if (mutexPtr == nullptr) { + HILOGE("extension mutex ptr is nullptr"); + return; + } + std::lock_guard lock(mutexPtr->callbackMutex); /* Clear Timer */ - session_->BundleExtTimerStop(callName); + session_->StopFwkTimer(callName); + session_->StopExtTimer(callName); auto backUpConnection = session_->GetExtConnection(callName); if (backUpConnection != nullptr && backUpConnection->IsExtAbilityConnected()) { backUpConnection->DisconnectBackupExtAbility(); } - /* Clear Session before notice client finish event */ - ClearSessionAndSchedInfo(callName); + session_->SetServiceSchedAction(callName, BConstants::ServiceSchedAction::CLEAN); + auto ret = LaunchBackupExtension(callName); + if (ret) { + /* Clear Session before notice client finish event */ + ClearSessionAndSchedInfo(callName); + } /* Notice Client Ext Ability Process Died */ NoticeClientFinish(callName, BError(BError::Codes::EXT_ABILITY_DIED)); } catch (...) { HILOGE("Unexpected exception, bundleName: %{public}s", callName.c_str()); ClearSessionAndSchedInfo(callName); NoticeClientFinish(callName, BError(BError::Codes::EXT_ABILITY_DIED)); - return; } + RemoveExtensionMutex(callName); } void Service::ExtStart(const string &bundleName) @@ -998,32 +1099,34 @@ void Service::ExtStart(const string &bundleName) if (!proxy) { throw BError(BError::Codes::SA_INVAL_ARG, "ExtStart bundle task error, Extension backup Proxy is empty"); } + std::string name = bundleName; + proxy->UpdateFdSendRate(name, DEFAULT_FD_SEND_RATE); if (scenario == IServiceReverse::Scenario::BACKUP) { - auto ret = proxy->HandleBackup(); + auto ret = proxy->HandleBackup(session_->GetClearDataFlag(bundleName)); session_->GetServiceReverseProxy()->BackupOnBundleStarted(ret, bundleName); + BundleBeginRadarReport(bundleName, ret, scenario); if (ret) { ClearSessionAndSchedInfo(bundleName); NoticeClientFinish(bundleName, BError(BError::Codes::SA_INVAL_ARG)); } return; - } - if (scenario != IServiceReverse::Scenario::RESTORE) { + } else if (scenario != IServiceReverse::Scenario::RESTORE) { throw BError(BError::Codes::SA_INVAL_ARG, "Failed to scenario"); } - auto ret = proxy->HandleRestore(); + auto ret = proxy->HandleRestore(session_->GetClearDataFlag(bundleName)); session_->GetServiceReverseProxy()->RestoreOnBundleStarted(ret, bundleName); + BundleBeginRadarReport(bundleName, ret, scenario); auto fileNameVec = session_->GetExtFileNameRequest(bundleName); for (auto &fileName : fileNameVec) { int32_t errCode = 0; UniqueFd fd = proxy->GetFileHandle(fileName, errCode); session_->GetServiceReverseProxy()->RestoreOnFileReady(bundleName, fileName, move(fd), errCode); + FileReadyRadarReport(bundleName, fileName, errCode, scenario); } - return; } catch (...) { HILOGI("Unexpected exception, bundleName: %{public}s", bundleName.c_str()); ClearSessionAndSchedInfo(bundleName); NoticeClientFinish(bundleName, BError(BError::Codes::SA_INVAL_ARG)); - return; } } @@ -1038,31 +1141,48 @@ int Service::Dump(int fd, const vector &args) return 0; } -void Service::ExtConnectFailed(const string &bundleName, ErrCode ret) +void Service::ReportOnExtConnectFailed(const IServiceReverse::Scenario scenario, + const std::string &bundleName, const ErrCode ret) { - HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); try { - HILOGE("begin %{public}s", bundleName.data()); - IServiceReverse::Scenario scenario = session_->GetScenario(); + if (session_ == nullptr) { + HILOGE("Report extConnectfailed error, session info is empty"); + return; + } if (scenario == IServiceReverse::Scenario::BACKUP && session_->GetIsIncrementalBackup()) { session_->GetServiceReverseProxy()->IncrementalBackupOnBundleStarted(ret, bundleName); + BundleBeginRadarReport(bundleName, ret, scenario); } else if (scenario == IServiceReverse::Scenario::RESTORE && BackupPara().GetBackupOverrideIncrementalRestore() && session_->ValidRestoreDataType(RestoreTypeEnum::RESTORE_DATA_WAIT_SEND)) { session_->GetServiceReverseProxy()->IncrementalRestoreOnBundleStarted(ret, bundleName); - + BundleBeginRadarReport(bundleName, ret, scenario); DisposeErr disposeErr = AppGalleryDisposeProxy::GetInstance()->EndRestore(bundleName); HILOGI("ExtConnectFailed EndRestore, code=%{public}d, bundleName=%{public}s", disposeErr, bundleName.c_str()); } else if (scenario == IServiceReverse::Scenario::BACKUP) { session_->GetServiceReverseProxy()->BackupOnBundleStarted(ret, bundleName); + BundleBeginRadarReport(bundleName, ret, scenario); } else if (scenario == IServiceReverse::Scenario::RESTORE) { session_->GetServiceReverseProxy()->RestoreOnBundleStarted(ret, bundleName); - + BundleBeginRadarReport(bundleName, ret, scenario); DisposeErr disposeErr = AppGalleryDisposeProxy::GetInstance()->EndRestore(bundleName); HILOGI("ExtConnectFailed EndRestore, code=%{public}d, bundleName=%{public}s", disposeErr, bundleName.c_str()); } + } catch (...) { + HILOGE("Report extConnectfailed error"); + } +} + +void Service::ExtConnectFailed(const string &bundleName, ErrCode ret) +{ + HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + IServiceReverse::Scenario scenario = IServiceReverse::Scenario::UNDEFINED; + try { + HILOGE("begin %{public}s", bundleName.data()); + scenario = session_->GetScenario(); + ReportOnExtConnectFailed(scenario, bundleName, ret); ClearSessionAndSchedInfo(bundleName); NoticeClientFinish(bundleName, BError(BError::Codes::EXT_ABILITY_DIED)); return; @@ -1082,6 +1202,7 @@ void Service::NoticeClientFinish(const string &bundleName, ErrCode errCode) HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); HILOGI("begin %{public}s", bundleName.c_str()); try { + SendEndAppGalleryNotify(bundleName); auto scenario = session_->GetScenario(); if (scenario == IServiceReverse::Scenario::BACKUP && session_->GetIsIncrementalBackup()) { session_->GetServiceReverseProxy()->IncrementalBackupOnBundleFinished(errCode, bundleName); @@ -1094,56 +1215,47 @@ void Service::NoticeClientFinish(const string &bundleName, ErrCode errCode) } else if (scenario == IServiceReverse::Scenario::RESTORE) { session_->GetServiceReverseProxy()->RestoreOnBundleFinished(errCode, bundleName); }; + BundleEndRadarReport(bundleName, errCode, scenario); /* If all bundle ext process finish, notice client. */ OnAllBundlesFinished(BError(BError::Codes::OK)); + } catch(const BError &e) { + ReleaseOnException(); } catch (...) { + ReleaseOnException(); HILOGI("Unexpected exception"); return; } } +void Service::StartRunningTimer(const std::string &bundleName) +{ + auto timeoutCallback = TimeOutCallback(wptr(this), bundleName); + auto scenario = session_->GetScenario(); + if (scenario == IServiceReverse::Scenario::BACKUP) { + session_->StartExtTimer(bundleName, timeoutCallback); + } else if (scenario == IServiceReverse::Scenario::RESTORE) { + session_->StartFwkTimer(bundleName, timeoutCallback); + } +} + void Service::ExtConnectDone(string bundleName) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); - auto timeoutCallback = [ptr {wptr(this)}, bundleName]() { - HILOGI("begin timeoutCallback bundleName = %{public}s", bundleName.c_str()); - auto thisPtr = ptr.promote(); - if (!thisPtr) { - HILOGE("ServicePtr is nullptr."); - return; - } - auto sessionPtr = ptr->session_; - if (sessionPtr == nullptr) { - HILOGE("SessionPtr is nullptr."); + try { + HILOGE("begin %{public}s", bundleName.data()); + + BConstants::ServiceSchedAction curSchedAction = session_->GetServiceSchedAction(bundleName); + if (curSchedAction == BConstants::ServiceSchedAction::CLEAN) { + sched_->Sched(bundleName); return; } - try { - if (SAUtils::IsSABundleName(bundleName)) { - auto sessionConnection = sessionPtr->GetSAExtConnection(bundleName); - shared_ptr saConnection = sessionConnection.lock(); - if (saConnection == nullptr) { - HILOGE("lock sa connection ptr is nullptr"); - return; - } - sessionPtr->BundleExtTimerStop(bundleName); - saConnection->DisconnectBackupSAExt(); - } else { - auto sessionConnection = sessionPtr->GetExtConnection(bundleName); - sessionPtr->BundleExtTimerStop(bundleName); - sessionConnection->DisconnectBackupExtAbility(); - } - thisPtr->ClearSessionAndSchedInfo(bundleName); - thisPtr->NoticeClientFinish(bundleName, BError(BError::Codes::EXT_ABILITY_TIMEOUT)); - } catch (...) { - HILOGE("Unexpected exception, bundleName: %{public}s", bundleName.c_str()); - thisPtr->ClearSessionAndSchedInfo(bundleName); - thisPtr->NoticeClientFinish(bundleName, BError(BError::Codes::EXT_ABILITY_TIMEOUT)); + if (curSchedAction == BConstants::ServiceSchedAction::START && + clearRecorder_->FindClearBundleRecord(bundleName)) { + session_->SetServiceSchedAction(bundleName, BConstants::ServiceSchedAction::CLEAN); + } else { + session_->SetServiceSchedAction(bundleName, BConstants::ServiceSchedAction::RUNNING); + AddClearBundleRecord(bundleName); } - }; - try { - HILOGE("begin %{public}s", bundleName.data()); - session_->BundleExtTimerStart(bundleName, timeoutCallback); - session_->SetServiceSchedAction(bundleName, BConstants::ServiceSchedAction::RUNNING); sched_->Sched(bundleName); } catch (...) { HILOGE("Unexpected exception, bundleName: %{public}s", bundleName.c_str()); @@ -1161,6 +1273,12 @@ void Service::ClearSessionAndSchedInfo(const string &bundleName) session_->RemoveExtInfo(bundleName); sched_->RemoveExtConn(bundleName); HandleRestoreDepsBundle(bundleName); + DelClearBundleRecord({bundleName}); + if (isCleanService_.load() && session_->IsOnAllBundlesFinished()) { + isCleanService_.store(false); + StopAll(nullptr, true); + return; + } sched_->Sched(); } catch (const BError &e) { return; @@ -1219,6 +1337,9 @@ void Service::OnAllBundlesFinished(ErrCode errCode) HILOGI("called begin."); if (session_->IsOnAllBundlesFinished()) { IServiceReverse::Scenario scenario = session_->GetScenario(); + if (isInRelease_.load() && (scenario == IServiceReverse::Scenario::RESTORE)) { + SessionDeactive(); + } if (scenario == IServiceReverse::Scenario::BACKUP && session_->GetIsIncrementalBackup()) { session_->GetServiceReverseProxy()->IncrementalBackupOnAllBundlesFinished(errCode); } else if (scenario == IServiceReverse::Scenario::RESTORE && @@ -1250,20 +1371,17 @@ void Service::OnStartSched() void Service::SendStartAppGalleryNotify(const BundleName &bundleName) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + if (SAUtils::IsSABundleName(bundleName)) { + HILOGI("SA does not need to StartRestore"); + return; + } IServiceReverse::Scenario scenario = session_->GetScenario(); if (scenario != IServiceReverse::Scenario::RESTORE) { - return ; - } - string work_status = system::GetParameter(BACKUPSERVICE_WORK_STATUS_KEY, ""); - HILOGI("Param %{public}s value is %{public}s", BACKUPSERVICE_WORK_STATUS_KEY.c_str(), work_status.c_str()); - if (work_status.compare(BACKUPSERVICE_WORK_STATUS_OFF) == 0) { - bool isSetSucc = system::SetParameter(BACKUPSERVICE_WORK_STATUS_KEY, BACKUPSERVICE_WORK_STATUS_ON); - HILOGI("SetParameter %{public}s true end, result %{public}d.", BACKUPSERVICE_WORK_STATUS_KEY.c_str(), - isSetSucc); + return; } if (!disposal_->IfBundleNameInDisposalConfigFile(bundleName)) { HILOGE("WriteDisposalConfigFile Failed"); - return ; + return; } HILOGI("AppendIntoDisposalConfigFile OK, bundleName=%{public}s", bundleName.c_str()); DisposeErr disposeErr = AppGalleryDisposeProxy::GetInstance()->StartRestore(bundleName); @@ -1274,45 +1392,61 @@ void Service::SendStartAppGalleryNotify(const BundleName &bundleName) void Service::SendEndAppGalleryNotify(const BundleName &bundleName) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + if (SAUtils::IsSABundleName(bundleName)) { + HILOGI("SA does not need to EndRestore"); + return; + } IServiceReverse::Scenario scenario = session_->GetScenario(); if (scenario != IServiceReverse::Scenario::RESTORE) { - return ; + return; } DisposeErr disposeErr = AppGalleryDisposeProxy::GetInstance()->EndRestore(bundleName); HILOGI("EndRestore, code=%{public}d, bundleName=%{public}s", disposeErr, bundleName.c_str()); if (disposeErr != DisposeErr::OK) { - HILOGE("Error, disposal will be clear in the end"); - return ; + HILOGE("Error code=%{public}d, disposal will be clear in the end", disposeErr); + return; } if (!disposal_->DeleteFromDisposalConfigFile(bundleName)) { HILOGE("DeleteFromDisposalConfigFile Failed, bundleName=%{public}s", bundleName.c_str()); - return ; + return; } HILOGI("DeleteFromDisposalConfigFile OK, bundleName=%{public}s", bundleName.c_str()); } +void Service::TryToClearDispose(const BundleName &bundleName) +{ + int32_t maxAtt = MAX_TRY_CLEAR_DISPOSE_NUM; + int32_t att = 0; + while (att < maxAtt) { + DisposeErr disposeErr = AppGalleryDisposeProxy::GetInstance()->EndRestore(bundleName); + HILOGI("EndRestore, code=%{public}d, bundleName=%{public}s", disposeErr, bundleName.c_str()); + if (disposeErr == DisposeErr::OK) { + break; + } + ++att; + HILOGI("Try to clear dispose, num = %{public}d", att); + } + if (!disposal_->DeleteFromDisposalConfigFile(bundleName)) { + HILOGE("DeleteFromDisposalConfigFile Failed, bundleName=%{public}s", bundleName.c_str()); + } +} + void Service::SendErrAppGalleryNotify() { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); IServiceReverse::Scenario scenario = session_->GetScenario(); if (scenario != IServiceReverse::Scenario::RESTORE) { - return ; + return; } vector bundleNameList = disposal_->GetBundleNameFromConfigFile(); if (bundleNameList.empty()) { HILOGI("End, All disposal pasitions have been cleared"); - return ; + return; } for (vector::iterator it = bundleNameList.begin(); it != bundleNameList.end(); ++it) { string bundleName = *it; - DisposeErr disposeErr = AppGalleryDisposeProxy::GetInstance()->EndRestore(bundleName); - HILOGI("EndRestore, code=%{public}d, bundleName=%{public}s", disposeErr, - bundleName.c_str()); - if (disposeErr != DisposeErr::OK) { - HILOGE("Error,disposal will be clear in the end"); - return ; - } + TryToClearDispose(bundleName); } } @@ -1323,9 +1457,8 @@ void Service::ClearDisposalOnSaStart() if (!bundleNameList.empty()) { for (vector::iterator it = bundleNameList.begin(); it != bundleNameList.end(); ++it) { string bundleName = *it; - DisposeErr disposeErr = AppGalleryDisposeProxy::GetInstance()->EndRestore(bundleName); - HILOGI("EndRestore, code=%{public}d, bundleName=%{public}s", disposeErr, - bundleName.c_str()); + HILOGE("dispose has residual, clear now, bundelName =%{public}s", bundleName.c_str()); + TryToClearDispose(bundleName); } } HILOGI("SA start, All Errdisposal pasitions have been cleared"); @@ -1336,12 +1469,12 @@ void Service::DeleteDisConfigFile() HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); IServiceReverse::Scenario scenario = session_->GetScenario(); if (scenario != IServiceReverse::Scenario::RESTORE) { - return ; + return; } vector bundleNameList = disposal_->GetBundleNameFromConfigFile(); if (!bundleNameList.empty()) { HILOGE("DisposalConfigFile is not empty"); - return ; + return; } if (!disposal_->DeleteConfigFile()) { HILOGE("DeleteConfigFile failed"); @@ -1353,7 +1486,28 @@ void Service::SessionDeactive() HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); try { HILOGI("Begin"); + isInRelease_.store(true); //清理处置状态 + if (session_ == nullptr) { + HILOGE("Session deactive error, session is empty"); + return; + } + ErrCode ret = BError(BError::Codes::OK); + std::vector bundleNameList; + if (session_->GetScenario() == IServiceReverse::Scenario::RESTORE && + session_->CleanAndCheckIfNeedWait(ret, bundleNameList)) { + if (ret != ERR_OK) { + isRmConfigFile_.store(false); + } + if (!bundleNameList.empty()) { + DelClearBundleRecord(bundleNameList); + } + return; + } + isInRelease_.store(false); + if (!bundleNameList.empty()) { + DelClearBundleRecord(bundleNameList); + } SendErrAppGalleryNotify(); DeleteDisConfigFile(); // 结束定时器 @@ -1367,9 +1521,16 @@ void Service::SessionDeactive() HILOGE("Session deactive error, session is empty"); return; } - session_->ClearSessionData(); - // 卸载服务 - sched_->TryUnloadService(); + ret = session_->ClearSessionData(); + if (clearRecorder_ != nullptr && !ret && isRmConfigFile_.load()) { + clearRecorder_->DeleteConfigFile(); + } + // close session + StopAll(nullptr, true); + if (session_->GetSessionCnt() <= 0) { + HILOGI("do unload Service."); + sched_->TryUnloadService(); + } } catch (...) { HILOGE("Unexpected exception"); return; @@ -1389,9 +1550,10 @@ std::function Service::GetBackupInfoConnectDone(wptr }; } -std::function Service::GetBackupInfoConnectDied(wptr obj, std::string &bundleName) +std::function Service::GetBackupInfoConnectDied( + wptr obj, std::string &bundleName) { - return [obj](const string &&bundleName) { + return [obj](const string &&bundleName, bool isSecondCalled) { HILOGI("GetBackupInfoConnectDied, bundleName: %{public}s", bundleName.c_str()); auto thisPtr = obj.promote(); if (!thisPtr) { @@ -1403,94 +1565,219 @@ std::function Service::GetBackupInfoConnectDied(wptr }; } +ErrCode Service::ClearResidualBundleData(const std::string &bundleName) +{ + if (session_ == nullptr) { + return BError(BError::Codes::SA_INVAL_ARG); + } + auto backUpConnection = session_->GetExtConnection(bundleName); + if (backUpConnection == nullptr) { + throw BError(BError::Codes::SA_INVAL_ARG, "backUpConnection is empty"); + } + auto proxy = backUpConnection->GetBackupExtProxy(); + if (!proxy) { + throw BError(BError::Codes::SA_INVAL_ARG, "Extension backup Proxy is empty"); + } + // 通知ext清理 + ErrCode res = proxy->HandleClear(); + if (backUpConnection->IsExtAbilityConnected()) { + backUpConnection->DisconnectBackupExtAbility(); + } + ClearSessionAndSchedInfo(bundleName); + // 非清理任务,需要上报 + if (session_->GetScenario() != IServiceReverse::Scenario::CLEAN) { + OnAllBundlesFinished(BError(BError::Codes::OK)); + } + return res; +} + +ErrCode Service::GetBackupInfoCmdHandle(BundleName &bundleName, std::string &result) +{ + if (session_ == nullptr) { + HILOGE("Get BackupInfo error, session is empty."); + return BError(BError::Codes::SA_INVAL_ARG); + } + session_->SetSessionUserId(GetUserIdDefault()); + auto backupConnection = session_->CreateBackupConnection(bundleName); + if (backupConnection == nullptr) { + HILOGE("backupConnection is null. bundleName: %{public}s", bundleName.c_str()); + return BError(BError::Codes::SA_INVAL_ARG); + } + auto callConnected = GetBackupInfoConnectDone(wptr(this), bundleName); + auto callDied = GetBackupInfoConnectDied(wptr(this), bundleName); + backupConnection->SetCallback(callConnected); + backupConnection->SetCallDied(callDied); + AAFwk::Want want = CreateConnectWant(bundleName); + auto ret = backupConnection->ConnectBackupExtAbility(want, session_->GetSessionUserId()); + if (ret) { + HILOGE("ConnectBackupExtAbility faild, bundleName:%{public}s, ret:%{public}d", bundleName.c_str(), ret); + return BError(BError::Codes::SA_BOOT_EXT_FAIL); + } + std::unique_lock lock(getBackupInfoSyncLock_); + getBackupInfoCondition_.wait_for(lock, std::chrono::seconds(CONNECT_WAIT_TIME_S)); + if (isConnectDied_.load()) { + HILOGE("GetBackupInfoConnectDied, please check bundleName: %{public}s", bundleName.c_str()); + isConnectDied_.store(false); + return BError(BError::Codes::EXT_ABILITY_DIED); + } + auto proxy = backupConnection->GetBackupExtProxy(); + if (!proxy) { + HILOGE("Extension backup Proxy is empty."); + return BError(BError::Codes::SA_INVAL_ARG); + } + ret = proxy->GetBackupInfo(result); + backupConnection->DisconnectBackupExtAbility(); + if (ret != ERR_OK) { + HILOGE("Call Ext GetBackupInfo faild."); + AppRadar::Info info(bundleName, "", "Call Ext GetBackupInfo faild"); + Backup::AppRadar::GetInstance().RecordBackupFuncRes(info, "Service::GetBackupInfoCmdHandle", GetUserIdDefault(), + BizStageBackup::BIZ_STAGE_GET_BACKUP_INFO_FAIL, ret); + return BError(BError::Codes::SA_INVAL_ARG); + } + + return BError(BError::Codes::OK); +} + ErrCode Service::GetBackupInfo(BundleName &bundleName, std::string &result) { try { + std::lock_guard lock(getBackupInfoProcLock_); HILOGI("Service::GetBackupInfo begin."); - if (session_->GetImpl().clientToken) { - return BError(BError::Codes::SA_REFUSED_ACT, "Already have an active session"); - } - session_->IncreaseSessionCnt(); - session_->SetSessionUserId(GetUserIdDefault()); - auto backupConnection = session_->CreateBackupConnection(bundleName); - if (backupConnection == nullptr) { - HILOGE("backupConnection is null. bundleName: %{public}s", bundleName.c_str()); + if (session_ == nullptr || isCleanService_.load()) { + HILOGE("Get BackupInfo error, session is empty."); return BError(BError::Codes::SA_INVAL_ARG); } - auto callConnected = GetBackupInfoConnectDone(wptr(this), bundleName); - auto callDied = GetBackupInfoConnectDied(wptr(this), bundleName); - backupConnection->SetCallback(callConnected); - backupConnection->SetCallDied(callDied); - AAFwk::Want want = CreateConnectWant(bundleName); - auto ret = backupConnection->ConnectBackupExtAbility(want, session_->GetSessionUserId()); - if (ret) { - HILOGE("ConnectBackupExtAbility faild, please check bundleName: %{public}s", bundleName.c_str()); - return BError(BError::Codes::EXT_ABILITY_DIED); - } - std::unique_lock lock(getBackupInfoMutx_); - getBackupInfoCondition_.wait_for(lock, std::chrono::seconds(CONNECT_WAIT_TIME_S)); - if (isConnectDied_.load()) { - HILOGE("GetBackupInfoConnectDied, please check bundleName: %{public}s", bundleName.c_str()); - isConnectDied_.store(false); - return BError(BError::Codes::EXT_ABILITY_DIED); + if (session_->GetImpl().clientToken) { + return BError(BError::Codes::SA_REFUSED_ACT, "Already have an active session"); } - auto proxy = backupConnection->GetBackupExtProxy(); - if (!proxy) { - HILOGE("Extension backup Proxy is empty."); + session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); + auto ret = GetBackupInfoCmdHandle(bundleName, result); + HILOGI("Service::GetBackupInfo end. result: %{public}s", result.c_str()); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); + return ret; + } catch (...) { + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); + HILOGI("Unexpected exception"); + return EPERM; + } +} + +ErrCode Service::StartExtTimer(bool &isExtStart) +{ + try { + HILOGI("Service::StartExtTimer begin."); + if (session_ == nullptr) { + HILOGE("StartExtTimer error, session_ is nullptr."); + isExtStart = false; return BError(BError::Codes::SA_INVAL_ARG); } - ret = proxy->GetBackupInfo(result); - backupConnection->DisconnectBackupExtAbility(); - if (ret != ERR_OK) { - HILOGE("Call Ext GetBackupInfo faild."); + session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); + string bundleName = VerifyCallerAndGetCallerName(); + auto timeoutCallback = TimeOutCallback(wptr(this), bundleName); + session_->StopFwkTimer(bundleName); + isExtStart = session_->StartExtTimer(bundleName, timeoutCallback); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); + return BError(BError::Codes::OK); + } catch (...) { + isExtStart = false; + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); + HILOGI("Unexpected exception"); + return EPERM; + } +} + +ErrCode Service::StartFwkTimer(bool &isFwkStart) +{ + try { + HILOGI("Service::StartFwkTimer begin."); + if (session_ == nullptr) { + HILOGE("StartFwkTimer error, session_ is nullptr."); + isFwkStart = false; return BError(BError::Codes::SA_INVAL_ARG); } - HILOGI("Service::GetBackupInfo end. result: %s", result.c_str()); - session_->DecreaseSessionCnt(); + session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); + string bundleName = VerifyCallerAndGetCallerName(); + auto timeoutCallback = TimeOutCallback(wptr(this), bundleName); + session_->StopExtTimer(bundleName); + isFwkStart = session_->StartFwkTimer(bundleName, timeoutCallback); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return BError(BError::Codes::OK); } catch (...) { - session_->DecreaseSessionCnt(); + isFwkStart = false; + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGI("Unexpected exception"); return EPERM; } } -ErrCode Service::UpdateTimer(BundleName &bundleName, uint32_t timeOut, bool &result) +ErrCode Service::AppendBundlesClearSession(const std::vector &bundleNames) { - auto timeoutCallback = [ptr {wptr(this)}, bundleName]() { - HILOGE("Backup <%{public}s> Extension Process Timeout", bundleName.c_str()); - auto thisPtr = ptr.promote(); - if (!thisPtr) { - HILOGW("this pointer is null."); - return; + HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + try { + if (bundleNames.empty() || session_ == nullptr) { + HILOGE("AppendBundles clear session error, session is empty"); + return EPERM; } - auto sessionPtr = ptr->session_; - if (sessionPtr == nullptr) { - HILOGW("SessionPtr is null."); - return; + session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); // BundleMgrAdapter::GetBundleInfos可能耗时 + auto backupInfos = BundleMgrAdapter::GetBundleInfos(bundleNames, session_->GetSessionUserId()); + if (backupInfos.empty()) { + if (clearRecorder_ != nullptr) { + clearRecorder_->DeleteConfigFile(); + } + HILOGE("AppendBundles clear session error, backupInfos is empty"); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); + return EPERM; } - try { - auto sessionConnection = sessionPtr->GetExtConnection(bundleName); - sessionPtr->BundleExtTimerStop(bundleName); - sessionConnection->DisconnectBackupExtAbility(); - thisPtr->ClearSessionAndSchedInfo(bundleName); - thisPtr->NoticeClientFinish(bundleName, BError(BError::Codes::EXT_ABILITY_TIMEOUT)); - } catch (...) { - HILOGE("Unexpected exception, bundleName: %{public}s", bundleName.c_str()); - thisPtr->ClearSessionAndSchedInfo(bundleName); - thisPtr->NoticeClientFinish(bundleName, BError(BError::Codes::EXT_ABILITY_TIMEOUT)); + std::vector supportBundleNames; + for (auto info : backupInfos) { + std::string bundleNameIndexStr = BJsonUtil::BuildBundleNameIndexInfo(info.name, info.appIndex); + supportBundleNames.emplace_back(bundleNameIndexStr); } - }; + session_->AppendBundles(supportBundleNames); + for (auto info : backupInfos) { + std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(info.name, info.appIndex); + session_->SetBackupExtName(bundleNameIndexInfo, info.extensionName); + session_->SetIsReadyLaunch(bundleNameIndexInfo); + } + OnStartSched(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); + return BError(BError::Codes::OK); + } catch (const BError &e) { + HandleExceptionOnAppendBundles(session_, bundleNames, {}); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); + HILOGE("Failed, errCode = %{public}d", e.GetCode()); + return e.GetCode(); + } catch (const exception &e) { + HandleExceptionOnAppendBundles(session_, bundleNames, {}); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); + HILOGE("Catched an unexpected low-level exception %{public}s", e.what()); + return EPERM; + } catch (...) { + HandleExceptionOnAppendBundles(session_, bundleNames, {}); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); + HILOGE("Unexpected exception"); + return EPERM; + } +} + +ErrCode Service::UpdateTimer(BundleName &bundleName, uint32_t timeout, bool &result) +{ try { HILOGI("Service::UpdateTimer begin."); + if (session_ == nullptr || isCleanService_.load()) { + HILOGE("Update Timer error, session is empty."); + result = false; + return BError(BError::Codes::SA_INVAL_ARG); + } + session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); VerifyCaller(); - session_->IncreaseSessionCnt(); - result = session_->UpdateTimer(bundleName, timeOut, timeoutCallback); - session_->DecreaseSessionCnt(); + auto timeoutCallback = TimeOutCallback(wptr(this), bundleName); + result = session_->UpdateTimer(bundleName, timeout, timeoutCallback); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return BError(BError::Codes::OK); } catch (...) { result = false; - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGI("Unexpected exception"); return EPERM; } @@ -1498,25 +1785,42 @@ ErrCode Service::UpdateTimer(BundleName &bundleName, uint32_t timeOut, bool &res ErrCode Service::UpdateSendRate(std::string &bundleName, int32_t sendRate, bool &result) { - HILOGI("Begin, bundle name:%{public}s, sendRate is:%{public}d", bundleName.c_str(), sendRate); - VerifyCaller(); - IServiceReverse::Scenario scenario = session_ -> GetScenario(); - if (scenario != IServiceReverse::Scenario::BACKUP) { - HILOGE("This method is applicable to the backup scenario"); - return BError(BError::Codes::SA_INVAL_ARG); - } - auto backupConnection = session_->GetExtConnection(bundleName); - auto proxy = backupConnection->GetBackupExtProxy(); - if (!proxy) { - throw BError(BError::Codes::SA_INVAL_ARG, "Extension backup Proxy is empty"); - } - auto ret = proxy->UpdateFdSendRate(bundleName, sendRate); - if (ret != NO_ERROR) { + try { + HILOGI("Begin, bundle name:%{public}s, sendRate is:%{public}d", bundleName.c_str(), sendRate); + if (session_ == nullptr || isCleanService_.load()) { + HILOGE("Update Send Rate error, session is empty."); + result = false; + return BError(BError::Codes::SA_INVAL_ARG); + } + session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); + VerifyCaller(); + IServiceReverse::Scenario scenario = session_ -> GetScenario(); + if (scenario != IServiceReverse::Scenario::BACKUP) { + HILOGE("This method is applicable to the backup scenario"); + result = false; + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); + return BError(BError::Codes::SA_INVAL_ARG); + } + auto backupConnection = session_->GetExtConnection(bundleName); + auto proxy = backupConnection->GetBackupExtProxy(); + if (!proxy) { + throw BError(BError::Codes::SA_INVAL_ARG, "Extension backup Proxy is empty"); + } + auto ret = proxy->UpdateFdSendRate(bundleName, sendRate); + if (ret != NO_ERROR) { + result = false; + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); + return BError(BError::Codes::EXT_BROKEN_IPC); + } + result = true; + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); + return BError(BError::Codes::OK); + } catch (...) { result = false; - return BError(BError::Codes::EXT_BROKEN_IPC); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); + HILOGI("Unexpected exception"); + return EPERM; } - result = true; - return BError(BError::Codes::OK); } AAFwk::Want Service::CreateConnectWant (BundleName &bundleName) @@ -1542,6 +1846,7 @@ ErrCode Service::BackupSA(std::string bundleName) if (scenario == IServiceReverse::Scenario::BACKUP) { auto ret = saConnection->CallBackupSA(); session_->GetServiceReverseProxy()->BackupOnBundleStarted(ret, bundleName); + BundleBeginRadarReport(bundleName, ret, scenario); if (ret) { HILOGI("BackupSA ret is %{public}d", ret); ClearSessionAndSchedInfo(bundleName); @@ -1557,17 +1862,36 @@ ErrCode Service::BackupSA(std::string bundleName) void Service::OnSABackup(const std::string &bundleName, const int &fd, const std::string &result, const ErrCode &errCode) { - HILOGI("OnSABackup bundleName: %{public}s, fd: %{public}d, result: %{public}s, err: %{public}d", - bundleName.c_str(), fd, result.c_str(), errCode); - session_->GetServiceReverseProxy()->BackupOnFileReady(bundleName, "", move(fd), errCode); - SAResultReport(bundleName, result, errCode, BackupRestoreScenario::FULL_BACKUP); + auto task = [bundleName, fd, result, errCode, this]() { + HILOGI("OnSABackup bundleName: %{public}s, fd: %{public}d, result: %{public}s, err: %{public}d", + bundleName.c_str(), fd, result.c_str(), errCode); + session_->GetServiceReverseProxy()->BackupOnFileReady(bundleName, "", move(fd), errCode); + FileReadyRadarReport(bundleName, "", errCode, IServiceReverse::Scenario::BACKUP); + SAResultReport(bundleName, result, errCode, BackupRestoreScenario::FULL_BACKUP); + }; + threadPool_.AddTask([task]() { + try { + task(); + } catch (...) { + HILOGE("Failed to add task to thread pool"); + } + }); } void Service::OnSARestore(const std::string &bundleName, const std::string &result, const ErrCode &errCode) { - HILOGI("OnSARestore bundleName: %{public}s, result: %{public}s, err: %{public}d", - bundleName.c_str(), result.c_str(), errCode); - SAResultReport(bundleName, result, errCode, BackupRestoreScenario::INCREMENTAL_RESTORE); + auto task = [bundleName, result, errCode, this]() { + HILOGI("OnSARestore bundleName: %{public}s, result: %{public}s, err: %{public}d", + bundleName.c_str(), result.c_str(), errCode); + SAResultReport(bundleName, result, errCode, BackupRestoreScenario::INCREMENTAL_RESTORE); + }; + threadPool_.AddTask([task]() { + try { + task(); + } catch (...) { + HILOGE("Failed to add task to thread pool"); + } + }); } ErrCode Service::SADone(ErrCode errCode, std::string bundleName) @@ -1581,18 +1905,22 @@ ErrCode Service::SADone(ErrCode errCode, std::string bundleName) HILOGE("lock sa connection ptr is nullptr"); return BError(BError::Codes::SA_INVAL_ARG); } - session_->BundleExtTimerStop(bundleName); + session_->StopFwkTimer(bundleName); + session_->StopExtTimer(bundleName); saConnection->DisconnectBackupSAExt(); ClearSessionAndSchedInfo(bundleName); } OnAllBundlesFinished(BError(BError::Codes::OK)); return BError(BError::Codes::OK); } catch (const BError &e) { + ReleaseOnException(); return e.GetCode(); // 任意异常产生,终止监听该任务 } catch (const exception &e) { + ReleaseOnException(); HILOGE("Catched an unexpected low-level exception %{public}s", e.what()); return EPERM; } catch(...) { + ReleaseOnException(); HILOGE("Unexpected exception"); return EPERM; } @@ -1621,7 +1949,146 @@ void Service::NotifyCallerCurAppDone(ErrCode errCode, const std::string &callerN ); } else if (scenario == IServiceReverse::Scenario::RESTORE) { HILOGI("will notify clone data, scenario is Restore"); + SendEndAppGalleryNotify(callerName); session_->GetServiceReverseProxy()->RestoreOnBundleFinished(errCode, callerName); } + BundleEndRadarReport(callerName, errCode, scenario); +} + +ErrCode Service::ReportAppProcessInfo(const std::string processInfo, BackupRestoreScenario sennario) +{ + HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + try { + string bundleName = VerifyCallerAndGetCallerName(); + if (sennario == BackupRestoreScenario::FULL_RESTORE) { + session_->GetServiceReverseProxy()->RestoreOnProcessInfo(bundleName, processInfo); + } else if (sennario == BackupRestoreScenario::INCREMENTAL_RESTORE) { + session_->GetServiceReverseProxy()->IncrementalRestoreOnProcessInfo(bundleName, processInfo); + } else if (sennario == BackupRestoreScenario::FULL_BACKUP) { + session_->GetServiceReverseProxy()->BackupOnProcessInfo(bundleName, processInfo); + } else if (sennario == BackupRestoreScenario::INCREMENTAL_BACKUP) { + session_->GetServiceReverseProxy()->IncrementalBackupOnProcessInfo(bundleName, processInfo); + } + return BError(BError::Codes::OK); + } catch (const BError &e) { + return e.GetCode(); // 任意异常产生,终止监听该任务 + } catch (const exception &e) { + HILOGI("Catched an unexpected low-level exception %{public}s", e.what()); + return EPERM; + } +} + +std::function Service::TimeOutCallback(wptr ptr, std::string bundleName) +{ + return [ptr, bundleName, this]() { + HILOGI("begin timeoutCallback bundleName = %{public}s", bundleName.c_str()); + auto thisPtr = ptr.promote(); + if (!thisPtr) { + HILOGE("ServicePtr is nullptr."); + return; + } + try { + DoTimeout(thisPtr, bundleName); + } catch (...) { + HILOGE("Unexpected exception, bundleName: %{public}s", bundleName.c_str()); + thisPtr->ClearSessionAndSchedInfo(bundleName); + thisPtr->NoticeClientFinish(bundleName, BError(BError::Codes::EXT_ABILITY_TIMEOUT)); + } + }; +} + +void Service::TimeoutRadarReport(IServiceReverse::Scenario scenario, std::string &bundleName) +{ + int32_t errCode = BError(BError::Codes::EXT_ABILITY_TIMEOUT).GetCode(); + if (scenario == IServiceReverse::Scenario::BACKUP) { + AppRadar::Info info(bundleName, "", "on backup timeout"); + AppRadar::GetInstance().RecordBackupFuncRes(info, "Service::TimeOutCallback", GetUserIdDefault(), + BizStageBackup::BIZ_STAGE_ON_BACKUP, errCode); + } else if (scenario == IServiceReverse::Scenario::RESTORE) { + AppRadar::Info info(bundleName, "", "on restore timeout"); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "Service::TimeOutCallback", GetUserIdDefault(), + BizStageRestore::BIZ_STAGE_ON_RESTORE, errCode); + } +} + +void Service::DoTimeout(wptr ptr, std::string bundleName) +{ + auto thisPtr = ptr.promote(); + if (!thisPtr) { + HILOGE("ServicePtr is nullptr."); + return; + } + auto sessionPtr = thisPtr->session_; + if (sessionPtr == nullptr) { + HILOGE("SessionPtr is nullptr."); + return; + } + IServiceReverse::Scenario scenario = sessionPtr->GetScenario(); + TimeoutRadarReport(scenario, bundleName); + try { + std::shared_ptr mutexPtr = GetExtensionMutex(bundleName); + if (mutexPtr == nullptr) { + HILOGE("extension mutex ptr is nullptr"); + return; + } + std::lock_guard lock(mutexPtr->callbackMutex); + if (SAUtils::IsSABundleName(bundleName)) { + auto sessionConnection = sessionPtr->GetSAExtConnection(bundleName); + shared_ptr saConnection = sessionConnection.lock(); + if (saConnection == nullptr) { + HILOGE("lock sa connection ptr is nullptr"); + return; + } + saConnection->DisconnectBackupSAExt(); + } else { + auto sessionConnection = sessionPtr->GetExtConnection(bundleName); + sessionConnection->DisconnectBackupExtAbility(); + } + sessionPtr->StopFwkTimer(bundleName); + sessionPtr->StopExtTimer(bundleName); + thisPtr->ClearSessionAndSchedInfo(bundleName); + thisPtr->NoticeClientFinish(bundleName, BError(BError::Codes::EXT_ABILITY_TIMEOUT)); + } catch (...) { + HILOGE("Unexpected exception, bundleName: %{public}s", bundleName.c_str()); + thisPtr->ClearSessionAndSchedInfo(bundleName); + thisPtr->NoticeClientFinish(bundleName, BError(BError::Codes::EXT_ABILITY_TIMEOUT)); + } + RemoveExtensionMutex(bundleName); +} + +void Service::AddClearBundleRecord(const std::string &bundleName) +{ + // 添加清理记录 + if (!clearRecorder_->InsertClearBundleRecord(bundleName)) { + HILOGE("Failed to add clear bundle record, bundleName=%{public}s", bundleName.c_str()); + return; + } + HILOGI("Add clear bundle record OK, bundleName=%{public}s", bundleName.c_str()); +} + +void Service::DelClearBundleRecord(const std::vector &bundleNames) +{ + // 删除清理记录 + for (const auto &it : bundleNames) { + if (!clearRecorder_->DeleteClearBundleRecord(it)) { + HILOGE("Failed to delete clear bundle record, bundleName=%{public}s", it.c_str()); + continue; + } + HILOGI("Delete clear bundle record OK, bundleName=%{public}s", it.c_str()); + } +} + +void Service::ReleaseOnException() +{ + try { + if (session_->IsOnAllBundlesFinished()) { + IServiceReverse::Scenario scenario = session_->GetScenario(); + if (isInRelease_.load() && (scenario == IServiceReverse::Scenario::RESTORE)) { + SessionDeactive(); + } + } + } catch (...) { + HILOGE("Unexpected exception"); + } } } // namespace OHOS::FileManagement::Backup diff --git a/services/backup_sa/src/module_ipc/service_incremental.cpp b/services/backup_sa/src/module_ipc/service_incremental.cpp index 07c6f6f87fca4c4faf3a9a15925f0158964ead74..d3ddc141c68a221af7501e4796883ac33a73de34 100644 --- a/services/backup_sa/src/module_ipc/service_incremental.cpp +++ b/services/backup_sa/src/module_ipc/service_incremental.cpp @@ -38,6 +38,7 @@ #include "b_json/b_json_entity_caps.h" #include "b_ohos/startup/backup_para.h" #include "b_process/b_multiuser.h" +#include "b_radar/b_radar.h" #include "b_resources/b_constants.h" #include "b_sa/b_sa_utils.h" #include "filemgmt_libhilog.h" @@ -79,11 +80,56 @@ ErrCode Service::Release() { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); HILOGI("KILL"); - VerifyCaller(session_->GetScenario()); + IServiceReverse::Scenario scenario = session_->GetScenario(); + VerifyCaller(scenario); + AppRadar::Info info("", "", "call release"); + if (scenario == IServiceReverse::Scenario::RESTORE) { + AppRadar::GetInstance().RecordRestoreFuncRes(info, "Service::Release", session_->GetSessionUserId(), + BizStageRestore::BIZ_STAGE_RELEASE, ERR_OK); + } else if (scenario == IServiceReverse::Scenario::BACKUP) { + AppRadar::GetInstance().RecordBackupFuncRes(info, "Service::Release", session_->GetSessionUserId(), + BizStageBackup::BIZ_STAGE_RELEASE, ERR_OK); + } SessionDeactive(); return BError(BError::Codes::OK); } +std::shared_ptr Service::GetExtensionMutex(const BundleName &bundleName) +{ + std::unique_lock lock(extensionMutexLock_); + auto it = backupExtMutexMap_.find(bundleName); + if (it == backupExtMutexMap_.end()) { + HILOGI("BackupExtMutexMap not contain %{public}s", bundleName.c_str()); + backupExtMutexMap_[bundleName] = std::make_shared(bundleName); + return backupExtMutexMap_[bundleName]; + } + HILOGI("BackupExtMutexMap contain %{public}s", bundleName.c_str()); + return it->second; +} + +void Service::RemoveExtensionMutex(const BundleName &bundleName) +{ + std::unique_lock lock(extensionMutexLock_); + auto it = backupExtMutexMap_.find(bundleName); + if (it == backupExtMutexMap_.end()) { + HILOGI("BackupExtMutexMap not contain %{public}s", bundleName.c_str()); + return; + } + backupExtMutexMap_.erase(it); +} + +void Service::CreateDirIfNotExist(const std::string &path) +{ + if (access(path.c_str(), F_OK) != 0) { + bool created = ForceCreateDirectory(path.data()); + if (created) { + HILOGI("Create directory successfully."); + } else { + HILOGE("Failed to create directory, path = %{private}s, err = %{public}d", path.c_str(), errno); + } + } +} + UniqueFd Service::GetLocalCapabilitiesIncremental(const std::vector &bundleNames) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); @@ -93,19 +139,20 @@ UniqueFd Service::GetLocalCapabilitiesIncremental(const std::vectorIncreaseSessionCnt(); + session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); session_->SetSessionUserId(GetUserIdDefault()); VerifyCaller(); string path = BConstants::GetSaBundleBackupRootDir(session_->GetSessionUserId()); BExcepUltils::VerifyPath(path, false); + CreateDirIfNotExist(path); UniqueFd fd(open(path.data(), O_TMPFILE | O_RDWR, S_IRUSR | S_IWUSR)); if (fd < 0) { HILOGE("GetLocalCapabilitiesIncremental: open file failed, err = %{public}d", errno); - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return UniqueFd(-ENOENT); } BJsonCachedEntity cachedEntity(move(fd)); @@ -117,19 +164,19 @@ UniqueFd Service::GetLocalCapabilitiesIncremental(const std::vectorDecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGI("End, bundleInfos size:%{public}zu", bundleInfos.size()); return move(cachedEntity.GetFd()); } catch (const BError &e) { - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGE("GetLocalCapabilitiesIncremental failed, errCode = %{public}d", e.GetCode()); return UniqueFd(-e.GetCode()); } catch (const exception &e) { - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGI("Catched an unexpected low-level exception %{public}s", e.what()); return UniqueFd(-EPERM); } catch (...) { - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGI("Unexpected exception"); return UniqueFd(-EPERM); } @@ -154,6 +201,15 @@ void Service::StartGetFdTask(std::string bundleName, wptr ptr) if (!proxy) { throw BError(BError::Codes::SA_INVAL_ARG, "Extension backup Proxy is empty"); } + // distinguish whether it is 0 user + if (BundleMgrAdapter::IsUser0BundleName(bundleName, session_->GetSessionUserId())) { + auto ret = proxy->User0OnBackup(); + if (ret) { + thisPtr->ClearSessionAndSchedInfo(bundleName); + thisPtr->NoticeClientFinish(bundleName, BError(BError::Codes::EXT_ABILITY_DIED)); + } + return; + } int64_t lastTime = session->GetLastIncrementalTime(bundleName); std::vector bundleNames; bundleNames.emplace_back(BIncrementalData {bundleName, lastTime}); @@ -181,11 +237,11 @@ ErrCode Service::GetAppLocalListAndDoIncrementalBackup() { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); try { - if (session_ == nullptr) { + if (session_ == nullptr || isCleanService_.load()) { HILOGE("session is nullptr"); return BError(BError::Codes::SA_INVAL_ARG); } - session_->IncreaseSessionCnt(); + session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); session_->SetSessionUserId(GetUserIdDefault()); std::string bundleName = VerifyCallerAndGetCallerName(); auto task = [this, bundleName]() { @@ -202,18 +258,18 @@ ErrCode Service::GetAppLocalListAndDoIncrementalBackup() HILOGI("Unexpected exception"); } }); - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return BError(BError::Codes::OK); } catch (const BError &e) { - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGE("GetAppLocalListAndDoIncrementalBackup failed, errCode = %{public}d", e.GetCode()); return e.GetCode(); } catch (const exception &e) { - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGI("Catched an unexpected low-level exception %{public}s", e.what()); return EPERM; } catch (...) { - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGI("Unexpected exception"); return EPERM; } @@ -228,54 +284,57 @@ ErrCode Service::InitIncrementalBackupSession(sptr remote) HILOGE("Init Incremental backup session error, session is empty"); return BError(BError::Codes::SA_INVAL_ARG); } - return session_->Active({.clientToken = IPCSkeleton::GetCallingTokenID(), - .scenario = IServiceReverse::Scenario::BACKUP, - .clientProxy = remote, - .userId = GetUserIdDefault(), - .isIncrementalBackup = true}); + ErrCode errCode = session_->Active({.clientToken = IPCSkeleton::GetCallingTokenID(), + .scenario = IServiceReverse::Scenario::BACKUP, + .clientProxy = remote, + .userId = GetUserIdDefault(), + .isIncrementalBackup = true}); + if (errCode == 0) { + ClearFailedBundles(); + successBundlesNum_ = 0; + } + return errCode; } catch (const BError &e) { StopAll(nullptr, true); return e.GetCode(); } } +vector Service::GetBundleNameByDetails(const std::vector &bundlesToBackup) +{ + vector bundleNames {}; + for (auto bundle : bundlesToBackup) { + bundleNames.emplace_back(bundle.bundleName); + } + return bundleNames; +} + ErrCode Service::AppendBundlesIncrementalBackupSession(const std::vector &bundlesToBackup) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); try { - if (session_ == nullptr) { + if (session_ == nullptr || isCleanService_.load()) { HILOGE("Init Incremental backup session error, session is empty"); return BError(BError::Codes::SA_INVAL_ARG); } - session_->IncreaseSessionCnt(); // BundleMgrAdapter::GetBundleInfos可能耗时 + session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); // BundleMgrAdapter::GetBundleInfos可能耗时 VerifyCaller(IServiceReverse::Scenario::BACKUP); - vector bundleNames {}; - for (auto &bundle : bundlesToBackup) { - bundleNames.emplace_back(bundle.bundleName); - } - auto backupInfos = BundleMgrAdapter::GetBundleInfos(bundleNames, session_->GetSessionUserId()); - session_->AppendBundles(bundleNames); - for (auto info : backupInfos) { - session_->SetBundleDataSize(info.name, info.spaceOccupied); - session_->SetBackupExtName(info.name, info.extensionName); - if (info.allToBackup == false) { - session_->GetServiceReverseProxy()->IncrementalBackupOnBundleStarted( - BError(BError::Codes::SA_FORBID_BACKUP_RESTORE), info.name); - session_->RemoveExtInfo(info.name); - } - } - for (auto &bundleInfo : bundlesToBackup) { - session_->SetIncrementalData(bundleInfo); - } + vector bundleNames = GetBundleNameByDetails(bundlesToBackup); + auto backupInfos = BundleMgrAdapter::GetBundleInfosForAppend(bundlesToBackup, + session_->GetSessionUserId()); + std::vector supportBackupNames = GetSupportBackupBundleNames(backupInfos, true, bundleNames); + session_->AppendBundles(supportBackupNames); + SetBundleIncDataInfo(bundlesToBackup, supportBackupNames); + SetCurrentBackupSessProperties(supportBackupNames, session_->GetSessionUserId(), backupInfos, true); OnStartSched(); - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return BError(BError::Codes::OK); } catch (const BError &e) { - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGE("Failed, errCode = %{public}d", e.GetCode()); return e.GetCode(); } catch (...) { - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGI("Unexpected exception"); return EPERM; } @@ -286,50 +345,62 @@ ErrCode Service::AppendBundlesIncrementalBackupSession(const std::vectorIncreaseSessionCnt(); // BundleMgrAdapter::GetBundleInfos可能耗时 + if (session_ == nullptr || isCleanService_.load()) { + HILOGE("Init Incremental backup session error, session is empty"); + return BError(BError::Codes::SA_INVAL_ARG); + } + session_->IncreaseSessionCnt(__PRETTY_FUNCTION__); // BundleMgrAdapter::GetBundleInfos可能耗时 VerifyCaller(IServiceReverse::Scenario::BACKUP); vector bundleNames {}; for (auto &bundle : bundlesToBackup) { bundleNames.emplace_back(bundle.bundleName); } std::vector bundleNamesOnly; + std::map isClearDataFlags; std::map> bundleNameDetailMap = - BJsonUtil::BuildBundleInfos(bundleNames, infos, bundleNamesOnly, session_->GetSessionUserId()); - auto backupInfos = BundleMgrAdapter::GetBundleInfos(bundleNames, session_->GetSessionUserId()); - session_->AppendBundles(bundleNames); - for (auto info : backupInfos) { - session_->SetBundleDataSize(info.name, info.spaceOccupied); - session_->SetBackupExtName(info.name, info.extensionName); - if (info.allToBackup == false) { - session_->GetServiceReverseProxy()->IncrementalBackupOnBundleStarted( - BError(BError::Codes::SA_FORBID_BACKUP_RESTORE), info.name); - session_->RemoveExtInfo(info.name); - } - BJsonUtil::BundleDetailInfo uniCastInfo; - bool uniCastRet = BJsonUtil::FindBundleInfoByName(bundleNameDetailMap, info.name, UNICAST_TYPE, - uniCastInfo); - if (uniCastRet) { - HILOGI("current bundle, unicast info:%{public}s", GetAnonyString(uniCastInfo.detail).c_str()); - session_->SetBackupExtInfo(info.name, uniCastInfo.detail); - } - } - for (auto &bundleInfo : bundlesToBackup) { - session_->SetIncrementalData(bundleInfo); - } + BJsonUtil::BuildBundleInfos(bundleNames, infos, bundleNamesOnly, + session_->GetSessionUserId(), isClearDataFlags); + auto backupInfos = BundleMgrAdapter::GetBundleInfosForAppend(bundlesToBackup, + session_->GetSessionUserId()); + std::vector supportBackupNames = GetSupportBackupBundleNames(backupInfos, true, bundleNames); + session_->AppendBundles(supportBackupNames); + SetBundleIncDataInfo(bundlesToBackup, supportBackupNames); + HandleCurGroupIncBackupInfos(backupInfos, bundleNameDetailMap, isClearDataFlags); OnStartSched(); - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); return BError(BError::Codes::OK); } catch (const BError &e) { - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGE("Failed, errCode = %{public}d", e.GetCode()); return e.GetCode(); } catch (...) { - session_->DecreaseSessionCnt(); + session_->DecreaseSessionCnt(__PRETTY_FUNCTION__); HILOGI("Unexpected exception"); return EPERM; } } +void Service::HandleCurGroupIncBackupInfos(vector &backupInfos, + std::map> &bundleNameDetailMap, + std::map &isClearDataFlags) +{ + for (auto &info : backupInfos) { + HILOGI("Current backupInfo bundleName:%{public}s, index:%{public}d, extName:%{public}s", info.name.c_str(), + info.appIndex, info.extensionName.c_str()); + std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(info.name, info.appIndex); + SetCurrentSessProperties(info, isClearDataFlags, bundleNameIndexInfo); + session_->SetBundleDataSize(bundleNameIndexInfo, info.increSpaceOccupied); + BJsonUtil::BundleDetailInfo uniCastInfo; + if (BJsonUtil::FindBundleInfoByName(bundleNameDetailMap, bundleNameIndexInfo, UNICAST_TYPE, uniCastInfo)) { + HILOGI("current bundle:%{public}s, unicast info:%{public}s", bundleNameIndexInfo.c_str(), + GetAnonyString(uniCastInfo.detail).c_str()); + session_->SetBackupExtInfo(bundleNameIndexInfo, uniCastInfo.detail); + } + session_->SetBackupExtName(bundleNameIndexInfo, info.extensionName); + session_->SetIsReadyLaunch(bundleNameIndexInfo); + } +} + ErrCode Service::PublishIncrementalFile(const BFileInfo &fileInfo) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); @@ -340,6 +411,9 @@ ErrCode Service::PublishIncrementalFile(const BFileInfo &fileInfo) HILOGE("Forbit to use PublishIncrementalFile with fileName for App"); return EPERM; } + if (session_ != nullptr) { + session_->SetPublishFlag(fileInfo.owner); + } auto backUpConnection = session_->GetExtConnection(fileInfo.owner); if (backUpConnection == nullptr) { HILOGE("PublishIncrementalFile error, backUpConnection is empty"); @@ -391,6 +465,7 @@ ErrCode Service::AppIncrementalFileReady(const std::string &fileName, UniqueFd f if (session_->GetScenario() == IServiceReverse::Scenario::RESTORE) { session_->GetServiceReverseProxy()->IncrementalRestoreOnFileReady(callerName, fileName, move(fd), move(manifestFd), errCode); + FileReadyRadarReport(callerName, fileName, errCode, IServiceReverse::Scenario::RESTORE); return BError(BError::Codes::OK); } @@ -400,6 +475,7 @@ ErrCode Service::AppIncrementalFileReady(const std::string &fileName, UniqueFd f HILOGD("reverse: Will notify IncrementalBackupOnFileReady"); session_->GetServiceReverseProxy()->IncrementalBackupOnFileReady(callerName, fileName, move(fd), move(manifestFd), errCode); + FileReadyRadarReport(callerName, fileName, errCode, IServiceReverse::Scenario::BACKUP); if (session_->OnBundleFileReady(callerName, fileName)) { auto backUpConnection = session_->GetExtConnection(callerName); auto proxy = backUpConnection->GetBackupExtProxy(); @@ -409,11 +485,13 @@ ErrCode Service::AppIncrementalFileReady(const std::string &fileName, UniqueFd f // 通知extension清空缓存 proxy->HandleClear(); // 清除Timer - session_->BundleExtTimerStop(callerName); + session_->StopFwkTimer(callerName); + session_->StopExtTimer(callerName); // 通知TOOL 备份完成 HILOGI("reverse: Will notify IncrementalBackupOnBundleFinished"); session_->GetServiceReverseProxy()->IncrementalBackupOnBundleFinished(BError(BError::Codes::OK), callerName); + BundleEndRadarReport(callerName, BError(BError::Codes::OK), IServiceReverse::Scenario::BACKUP); // 断开extension backUpConnection->DisconnectBackupExtAbility(); ClearSessionAndSchedInfo(callerName); @@ -443,6 +521,12 @@ ErrCode Service::AppIncrementalDone(ErrCode errCode) HILOGI("Service AppIncrementalDone start, callerName is %{public}s, errCode is: %{public}d", callerName.c_str(), errCode); if (session_->OnBundleFileReady(callerName) || errCode != BError(BError::Codes::OK)) { + std::shared_ptr mutexPtr = GetExtensionMutex(callerName); + if (mutexPtr == nullptr) { + HILOGE("extension mutex ptr is nullptr"); + return BError(BError::Codes::SA_INVAL_ARG, "Extension mutex ptr is null."); + } + std::lock_guard lock(mutexPtr->callbackMutex); auto tempBackUpConnection = session_->GetExtConnection(callerName); auto backUpConnection = tempBackUpConnection.promote(); if (backUpConnection == nullptr) { @@ -453,17 +537,21 @@ ErrCode Service::AppIncrementalDone(ErrCode errCode) return BError(BError::Codes::SA_INVAL_ARG, "Extension backup Proxy is empty"); } proxy->HandleClear(); - session_->BundleExtTimerStop(callerName); - NotifyCallerCurAppIncrementDone(errCode, callerName); + session_->StopFwkTimer(callerName); + session_->StopExtTimer(callerName); backUpConnection->DisconnectBackupExtAbility(); ClearSessionAndSchedInfo(callerName); + NotifyCallerCurAppIncrementDone(errCode, callerName); } + RemoveExtensionMutex(callerName); OnAllBundlesFinished(BError(BError::Codes::OK)); return BError(BError::Codes::OK); } catch (const BError &e) { + ReleaseOnException(); HILOGE("AppIncrementalDone error, err code is:%{public}d", e.GetCode()); return e.GetCode(); // 任意异常产生,终止监听该任务 } catch (...) { + ReleaseOnException(); HILOGI("Unexpected exception"); return EPERM; } @@ -473,6 +561,7 @@ ErrCode Service::GetIncrementalFileHandle(const std::string &bundleName, const s { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); try { + HILOGI("Begin get incrementalFileHandle"); VerifyCaller(IServiceReverse::Scenario::RESTORE); auto action = session_->GetServiceSchedAction(bundleName); if (action == BConstants::ServiceSchedAction::RUNNING) { @@ -486,9 +575,12 @@ ErrCode Service::GetIncrementalFileHandle(const std::string &bundleName, const s HILOGE("GetIncrementalFileHandle error, Extension backup Proxy is empty"); return BError(BError::Codes::SA_INVAL_ARG); } - int res = proxy->GetIncrementalFileHandle(fileName); - if (res) { + ErrCode res = proxy->GetIncrementalFileHandle(fileName); + if (res != ERR_OK) { HILOGE("Failed to extension file handle"); + AppRadar::Info info (bundleName, "", ""); + AppRadar::GetInstance().RecordRestoreFuncRes(info, "Service::GetIncrementalFileHandle", + GetUserIdDefault(), BizStageRestore::BIZ_STAGE_GET_FILE_HANDLE_FAIL, res); } } else { SvcRestoreDepsManager::GetInstance().UpdateToRestoreBundleMap(bundleName, fileName); @@ -519,8 +611,9 @@ bool Service::IncrementalBackup(const string &bundleName) throw BError(BError::Codes::SA_INVAL_ARG, "Extension backup Proxy is empty"); } if (scenario == IServiceReverse::Scenario::BACKUP && session_->GetIsIncrementalBackup()) { - auto ret = proxy->IncrementalOnBackup(); + auto ret = proxy->IncrementalOnBackup(session_->GetClearDataFlag(bundleName)); session_->GetServiceReverseProxy()->IncrementalBackupOnBundleStarted(ret, bundleName); + BundleBeginRadarReport(bundleName, ret, IServiceReverse::Scenario::BACKUP); if (ret) { ClearSessionAndSchedInfo(bundleName); NoticeClientFinish(bundleName, BError(BError::Codes::EXT_ABILITY_DIED)); @@ -528,8 +621,9 @@ bool Service::IncrementalBackup(const string &bundleName) return true; } else if (scenario == IServiceReverse::Scenario::RESTORE && BackupPara().GetBackupOverrideIncrementalRestore() && session_->ValidRestoreDataType(RestoreTypeEnum::RESTORE_DATA_WAIT_SEND)) { - auto ret = proxy->HandleRestore(); + auto ret = proxy->HandleRestore(session_->GetClearDataFlag(bundleName)); session_->GetServiceReverseProxy()->IncrementalRestoreOnBundleStarted(ret, bundleName); + BundleBeginRadarReport(bundleName, ret, IServiceReverse::Scenario::RESTORE); auto fileNameVec = session_->GetExtFileNameRequest(bundleName); for (auto &fileName : fileNameVec) { ret = proxy->GetIncrementalFileHandle(fileName); @@ -548,6 +642,7 @@ void Service::NotifyCallerCurAppIncrementDone(ErrCode errCode, const std::string if (scenario == IServiceReverse::Scenario::BACKUP) { HILOGI("will notify clone data, scenario is incremental backup"); session_->GetServiceReverseProxy()->IncrementalBackupOnBundleFinished(errCode, callerName); + BundleEndRadarReport(callerName, errCode, scenario); auto now = std::chrono::system_clock::now(); auto time = std::chrono::system_clock::to_time_t(now); auto ms = std::chrono::duration_cast(now.time_since_epoch()); @@ -565,6 +660,71 @@ void Service::NotifyCallerCurAppIncrementDone(ErrCode errCode, const std::string HILOGI("will notify clone data, scenario is Restore"); SendEndAppGalleryNotify(callerName); session_->GetServiceReverseProxy()->IncrementalRestoreOnBundleFinished(errCode, callerName); + BundleEndRadarReport(callerName, errCode, scenario); + } +} + +void Service::SendUserIdToApp(string &bundleName, int32_t userId) +{ + if (session_ == nullptr) { + HILOGI("session_ is nullptr"); + return; + } + HILOGI("Begin, bundleName: %{public}s", bundleName.c_str()); + string detailInfo; + if (!BJsonUtil::BuildBundleInfoJson(userId, detailInfo)) { + HILOGE("BuildBundleInfoJson failed, bundleName : %{public}s", bundleName.c_str()); + return; + } + session_->SetBackupExtInfo(bundleName, detailInfo); + HILOGI("End, bundleName:%{public}s, unicast info:%{public}s", bundleName.c_str(), + GetAnonyString(detailInfo).c_str()); +} + +void Service::SetCurrentBackupSessProperties(const vector &bundleNames, int32_t userId, + vector &backupBundleInfos, bool isIncBackup) +{ + HILOGI("start SetCurrentBackupSessProperties"); + std::map bundleNameIndexBundleInfoMap; + for (auto &bundleInfo : backupBundleInfos) { + std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(bundleInfo.name, bundleInfo.appIndex); + bundleNameIndexBundleInfoMap[bundleNameIndexInfo] = bundleInfo; + } + for (auto item : bundleNames) { + std::string bundleName = item; + if (BundleMgrAdapter::IsUser0BundleName(bundleName, userId)) { + HILOGE("bundleName:%{public}s is zero user bundle", bundleName.c_str()); + SendUserIdToApp(bundleName, userId); + } + auto it = bundleNameIndexBundleInfoMap.find(bundleName); + if (it == bundleNameIndexBundleInfoMap.end()) { + HILOGE("Current bundleName can not find bundleInfo, bundleName:%{public}s", bundleName.c_str()); + session_->RemoveExtInfo(bundleName); + continue; + } + auto bundleInfo = it->second; + if (isIncBackup) { + session_->SetBundleDataSize(bundleName, bundleInfo.increSpaceOccupied); + } else { + session_->SetBundleDataSize(bundleName, bundleInfo.spaceOccupied); + } + session_->SetBackupExtName(bundleName, bundleInfo.extensionName); + session_->SetIsReadyLaunch(bundleName); + } + HILOGI("end SetCurrentBackupSessProperties"); +} + +void Service::SetBundleIncDataInfo(const std::vector& bundlesToBackup, + std::vector& supportBundleNames) +{ + for (auto &bundleInfo : bundlesToBackup) { + std::string bundleName = bundleInfo.bundleName; + auto it = std::find(supportBundleNames.begin(), supportBundleNames.end(), bundleName); + if (it == supportBundleNames.end()) { + HILOGE("Current bundle is not support to backup, bundleName:%{public}s", bundleName.c_str()); + continue; + } + session_->SetIncrementalData(bundleInfo); } } } // namespace OHOS::FileManagement::Backup diff --git a/services/backup_sa/src/module_ipc/service_incremental_reverse_proxy.cpp b/services/backup_sa/src/module_ipc/service_incremental_reverse_proxy.cpp index 6a9cd7560323e766662da0b26105a72ab2c3b006..39a5251735fa091aae44b67af2269334bac5f19a 100644 --- a/services/backup_sa/src/module_ipc/service_incremental_reverse_proxy.cpp +++ b/services/backup_sa/src/module_ipc/service_incremental_reverse_proxy.cpp @@ -121,6 +121,24 @@ void ServiceReverseProxy::IncrementalBackupOnAllBundlesFinished(int32_t errCode) } } +void ServiceReverseProxy::IncrementalBackupOnProcessInfo(std::string bundleName, std::string processInfo) +{ + BExcepUltils::BAssert(Remote(), BError::Codes::SDK_INVAL_ARG, "Remote is nullptr"); + MessageParcel data; + if (!data.WriteInterfaceToken(GetDescriptor()) || !data.WriteString(bundleName) || !data.WriteString(processInfo)) { + throw BError(BError::Codes::SA_BROKEN_IPC); + } + + MessageParcel reply; + MessageOption option; + if (int err = Remote()->SendRequest( + static_cast(IServiceReverseInterfaceCode::SERVICER_INCREMENTAL_BACKUP_ON_PROCESS_INFO), data, + reply, option); + err != ERR_OK) { + throw BError(BError::Codes::SA_BROKEN_IPC, to_string(err)); + } +} + void ServiceReverseProxy::IncrementalRestoreOnBundleStarted(int32_t errCode, string bundleName) { BExcepUltils::BAssert(Remote(), BError::Codes::SDK_INVAL_ARG, "Remote is nullptr"); @@ -217,4 +235,22 @@ void ServiceReverseProxy::IncrementalRestoreOnFileReady(string bundleName, strin throw BError(BError::Codes::SA_BROKEN_IPC, to_string(err)); } } + +void ServiceReverseProxy::IncrementalRestoreOnProcessInfo(std::string bundleName, std::string processInfo) +{ + BExcepUltils::BAssert(Remote(), BError::Codes::SDK_INVAL_ARG, "Remote is nullptr"); + MessageParcel data; + if (!data.WriteInterfaceToken(GetDescriptor()) || !data.WriteString(bundleName) || !data.WriteString(processInfo)) { + throw BError(BError::Codes::SA_BROKEN_IPC); + } + + MessageParcel reply; + MessageOption option; + if (int err = Remote()->SendRequest( + static_cast(IServiceReverseInterfaceCode::SERVICER_INCREMENTAL_RESTORE_ON_PROCESS_INFO), data, + reply, option); + err != ERR_OK) { + throw BError(BError::Codes::SA_BROKEN_IPC, to_string(err)); + } +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/services/backup_sa/src/module_ipc/service_reverse_proxy.cpp b/services/backup_sa/src/module_ipc/service_reverse_proxy.cpp index fdb44c962536785c4752db8cc966f103dfbbf6af..efe357b202253a3788f67a905d1f49d1a625108d 100644 --- a/services/backup_sa/src/module_ipc/service_reverse_proxy.cpp +++ b/services/backup_sa/src/module_ipc/service_reverse_proxy.cpp @@ -15,7 +15,6 @@ #include "module_ipc/service_reverse_proxy.h" -#include "module_app_gallery/app_gallery_dispose_proxy.h" #include "b_error/b_error.h" #include "b_error/b_excep_utils.h" #include "filemgmt_libhilog.h" @@ -113,6 +112,23 @@ void ServiceReverseProxy::BackupOnAllBundlesFinished(int32_t errCode) } } +void ServiceReverseProxy::BackupOnProcessInfo(std::string bundleName, std::string processInfo) +{ + BExcepUltils::BAssert(Remote(), BError::Codes::SDK_INVAL_ARG, "Remote is nullptr"); + MessageParcel data; + if (!data.WriteInterfaceToken(GetDescriptor()) || !data.WriteString(bundleName) || !data.WriteString(processInfo)) { + throw BError(BError::Codes::SA_BROKEN_IPC); + } + + MessageParcel reply; + MessageOption option; + if (int err = Remote()->SendRequest( + static_cast(IServiceReverseInterfaceCode::SERVICER_BACKUP_ON_PROCESS_INFO), data, reply, option); + err != ERR_OK) { + throw BError(BError::Codes::SA_BROKEN_IPC, to_string(err)); + } +} + void ServiceReverseProxy::RestoreOnBundleStarted(int32_t errCode, string bundleName) { BExcepUltils::BAssert(Remote(), BError::Codes::SDK_INVAL_ARG, "Remote is nullptr"); @@ -147,10 +163,6 @@ void ServiceReverseProxy::RestoreOnBundleFinished(int32_t errCode, string bundle err != ERR_OK) { throw BError(BError::Codes::SA_BROKEN_IPC, to_string(err)); } - - DisposeErr disposeErr = AppGalleryDisposeProxy::GetInstance()->EndRestore(bundleName); - HILOGI("RestoreOnBundleFinished EndRestore, code=%{public}d, bundleName=%{public}s", disposeErr, - bundleName.c_str()); } void ServiceReverseProxy::RestoreOnAllBundlesFinished(int32_t errCode) @@ -209,4 +221,21 @@ void ServiceReverseProxy::RestoreOnResultReport(string result, std::string bundl throw BError(BError::Codes::SA_BROKEN_IPC, to_string(err)); } } + +void ServiceReverseProxy::RestoreOnProcessInfo(std::string bundleName, std::string processInfo) +{ + BExcepUltils::BAssert(Remote(), BError::Codes::SDK_INVAL_ARG, "Remote is nullptr"); + MessageParcel data; + if (!data.WriteInterfaceToken(GetDescriptor()) || !data.WriteString(bundleName) || !data.WriteString(processInfo)) { + throw BError(BError::Codes::SA_BROKEN_IPC); + } + + MessageParcel reply; + MessageOption option; + if (int err = Remote()->SendRequest( + static_cast(IServiceReverseInterfaceCode::SERVICER_RESTORE_ON_PROCESS_INFO), data, reply, option); + err != ERR_OK) { + throw BError(BError::Codes::SA_BROKEN_IPC, to_string(err)); + } +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/services/backup_sa/src/module_ipc/service_stub.cpp b/services/backup_sa/src/module_ipc/service_stub.cpp index bd6d1be91a849d22d0c7c3cb718783bdaeb34bbf..20dedbbba63d611e3bba1ef1d20f69e42768cb8d 100644 --- a/services/backup_sa/src/module_ipc/service_stub.cpp +++ b/services/backup_sa/src/module_ipc/service_stub.cpp @@ -43,6 +43,13 @@ void ServiceStub::ServiceStubSupplement() opToInterfaceMap_[static_cast( IServiceInterfaceCode::SERVICE_CMD_GET_APP_LOCAL_LIST_AND_DO_INCREMENTAL_BACKUP)] = &ServiceStub::CmdGetAppLocalListAndDoIncrementalBackup; + opToInterfaceMap_[static_cast( + IServiceInterfaceCode::SERVICE_CMD_REPORT_APP_PROCESS_INFO)] = + &ServiceStub::CmdReportAppProcessInfo; + opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_START_EXT_TIMER)] = + &ServiceStub::CmdStartExtTimer; + opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_START_FWK_TIMER)] = + &ServiceStub::CmdStartFwkTimer; } void ServiceStub::ServiceStubSuppAppendBundles() @@ -75,8 +82,8 @@ ServiceStub::ServiceStub() &ServiceStub::CmdGetFileHandle; opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_APPEND_BUNDLES_RESTORE_SESSION)] = &ServiceStub::CmdAppendBundlesRestoreSession; - opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_APPEND_BUNDLES_RESTORE_SESSION_DETAILS)] - = &ServiceStub::CmdAppendBundlesDetailsRestoreSession; + opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_APPEND_BUNDLES_RESTORE_SESSION_DETAIL)] = + &ServiceStub::CmdAppendBundlesDetailsRestoreSession; opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_APPEND_BUNDLES_BACKUP_SESSION)] = &ServiceStub::CmdAppendBundlesBackupSession; opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_APPEND_BUNDLES_BACKUP_SESSION_DETAILS)] = @@ -407,12 +414,12 @@ int32_t ServiceStub::CmdUpdateTimer(MessageParcel &data, MessageParcel &reply) if (!data.ReadString(bundleName)) { return BError(BError::Codes::SA_BROKEN_IPC, string("Failed to recive bundleName")); } - uint32_t timeOut; - if (!data.ReadUint32(timeOut)) { - return BError(BError::Codes::SA_BROKEN_IPC, string("Failed to recive timeOut")); + uint32_t timeout; + if (!data.ReadUint32(timeout)) { + return BError(BError::Codes::SA_BROKEN_IPC, string("Failed to recive timeout")); } bool result; - ret = UpdateTimer(bundleName, timeOut, result); + ret = UpdateTimer(bundleName, timeout, result); if (ret != ERR_OK) { return BError(BError::Codes::SA_BROKEN_IPC, string("Failed to call UpdateTimer")); } @@ -447,6 +454,38 @@ int32_t ServiceStub::CmdUpdateSendRate(MessageParcel &data, MessageParcel &reply return BError(BError::Codes::OK); } +int32_t ServiceStub::CmdStartExtTimer(MessageParcel &data, MessageParcel &reply) +{ + HILOGI("ServiceStub::CmdStartExtTimer Begin."); + int ret = ERR_OK; + bool isExtStart; + ret = StartExtTimer(isExtStart); + if (ret != ERR_OK) { + return BError(BError::Codes::SA_BROKEN_IPC, string("Failed to call UpdateTimer")); + } + if (!reply.WriteBool(isExtStart)) { + return BError(BError::Codes::SA_BROKEN_IPC, string("Failed to write result")); + } + HILOGI("ServiceStub::CmdStartExtTimer end."); + return BError(BError::Codes::OK); +} + +int32_t ServiceStub::CmdStartFwkTimer(MessageParcel &data, MessageParcel &reply) +{ + HILOGI("ServiceStub::CmdStartFwkTimer Begin."); + int ret = ERR_OK; + bool isFwkStart; + ret = StartFwkTimer(isFwkStart); + if (ret != ERR_OK) { + return BError(BError::Codes::SA_BROKEN_IPC, string("Failed to call UpdateTimer")); + } + if (!reply.WriteBool(isFwkStart)) { + return BError(BError::Codes::SA_BROKEN_IPC, string("Failed to write result")); + } + HILOGI("ServiceStub::CmdStartFwkTimer end."); + return BError(BError::Codes::OK); +} + int32_t ServiceStub::CmdRelease(MessageParcel &data, MessageParcel &reply) { int res = Release(); @@ -622,6 +661,20 @@ int32_t ServiceStub::CmdGetIncrementalFileHandle(MessageParcel &data, MessagePar return GetIncrementalFileHandle(bundleName, fileName); } +int32_t ServiceStub::CmdReportAppProcessInfo(MessageParcel &data, MessageParcel &reply) +{ + string processInfo; + if (!data.ReadString(processInfo)) { + return BError(BError::Codes::SA_INVAL_ARG, "Failed to receive bundleName").GetCode(); + } + int32_t scenario; + if (!data.ReadInt32(scenario)) { + return BError(BError::Codes::SA_INVAL_ARG, "Failed to receive errCode"); + } + BackupRestoreScenario secenrioInfo = static_cast(scenario); + return ReportAppProcessInfo(processInfo, secenrioInfo); +} + template bool ServiceStub::ReadParcelableVector(std::vector &parcelableInfos, MessageParcel &data) { diff --git a/services/backup_sa/src/module_ipc/sub_service.cpp b/services/backup_sa/src/module_ipc/sub_service.cpp new file mode 100644 index 0000000000000000000000000000000000000000..7d3fc2387f16747f2d3c5fb6e71a5b013d56f8f4 --- /dev/null +++ b/services/backup_sa/src/module_ipc/sub_service.cpp @@ -0,0 +1,353 @@ +/* + * Copyright (c) 2022-2024 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "module_ipc/service.h" + +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include + +#include + +#include "ability_manager_client.h" +#include "accesstoken_kit.h" +#include "b_anony/b_anony.h" +#include "b_error/b_error.h" +#include "b_error/b_excep_utils.h" +#include "b_file_info.h" +#include "b_json/b_json_cached_entity.h" +#include "b_jsonutil/b_jsonutil.h" +#include "b_ohos/startup/backup_para.h" +#include "b_process/b_multiuser.h" +#include "b_radar/b_radar.h" +#include "b_resources/b_constants.h" +#include "b_sa/b_sa_utils.h" +#include "bundle_mgr_client.h" +#include "filemgmt_libhilog.h" +#include "hisysevent.h" +#include "hitrace_meter.h" +#include "ipc_skeleton.h" +#include "access_token.h" +#include "tokenid_kit.h" +#include "module_app_gallery/app_gallery_dispose_proxy.h" +#include "module_external/bms_adapter.h" +#include "module_external/sms_adapter.h" +#include "module_ipc/svc_backup_connection.h" +#include "module_ipc/svc_restore_deps_manager.h" +#include "module_notify/notify_work_service.h" +#include "parameter.h" +#include "parameters.h" +#include "system_ability_definition.h" + +namespace OHOS::FileManagement::Backup { +using namespace std; + +vector Service::MakeDetailList(const vector &bundleNames) +{ + vector bundleDetails {}; + for (auto bundleName : bundleNames) { + bundleDetails.emplace_back(BIncrementalData {bundleName, 0}); + } + return bundleDetails; +} + +ErrCode Service::Finish() +{ + HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + try { + VerifyCaller(session_->GetScenario()); + session_->Finish(); + OnAllBundlesFinished(BError(BError::Codes::OK)); + return BError(BError::Codes::OK); + } catch (const BError &e) { + ReleaseOnException(); + HILOGE("Failde to Finish"); + return e.GetCode(); + } +} + +ErrCode Service::PublishFile(const BFileInfo &fileInfo) +{ + HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + try { + VerifyCaller(IServiceReverse::Scenario::RESTORE); + if (!fileInfo.fileName.empty()) { + HILOGE("Forbit to use publishFile with fileName for App"); + return EPERM; + } + auto backUpConnection = session_->GetExtConnection(fileInfo.owner); + if (backUpConnection == nullptr) { + HILOGE("PublishFile error, backUpConnection is empty"); + return BError(BError::Codes::SA_INVAL_ARG); + } + auto proxy = backUpConnection->GetBackupExtProxy(); + if (!proxy) { + HILOGE("PublishFile error, Extension backup Proxy is empty"); + return BError(BError::Codes::SA_INVAL_ARG); + } + ErrCode res = proxy->PublishFile(fileInfo.fileName); + if (res) { + HILOGE("Failed to publish file for backup extension"); + } + return res; + } catch (const BError &e) { + return e.GetCode(); + } catch (const exception &e) { + HILOGI("Catched an unexpected low-level exception %{public}s", e.what()); + return EPERM; + } catch (...) { + HILOGI("Unexpected exception"); + return EPERM; + } +} + +ErrCode Service::AppFileReady(const string &fileName, UniqueFd fd, int32_t errCode) +{ + HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + try { + string callerName = VerifyCallerAndGetCallerName(); + if (fileName.find('/') != string::npos) { + throw BError(BError::Codes::SA_INVAL_ARG, "Filename is not valid"); + } + if (fileName == BConstants::EXT_BACKUP_MANAGE) { + fd = session_->OnBundleExtManageInfo(callerName, move(fd)); + } + session_->GetServiceReverseProxy()->BackupOnFileReady(callerName, fileName, move(fd), errCode); + FileReadyRadarReport(callerName, fileName, errCode, session_->GetScenario()); + if (session_->OnBundleFileReady(callerName, fileName)) { + auto backUpConnection = session_->GetExtConnection(callerName); + if (backUpConnection == nullptr) { + HILOGE("AppFileReady error, backUpConnection is empty"); + return BError(BError::Codes::SA_INVAL_ARG); + } + auto proxy = backUpConnection->GetBackupExtProxy(); + if (!proxy) { + HILOGE("AppFileReady error, Extension backup Proxy is empty"); + return BError(BError::Codes::SA_INVAL_ARG); + } + // 通知extension清空缓存 + proxy->HandleClear(); + // 清除Timer + session_->StopFwkTimer(callerName); + session_->StopExtTimer(callerName); + // 通知TOOL 备份完成 + session_->GetServiceReverseProxy()->BackupOnBundleFinished(BError(BError::Codes::OK), callerName); + BundleEndRadarReport(callerName, BError(BError::Codes::OK), session_->GetScenario()); + // 断开extension + backUpConnection->DisconnectBackupExtAbility(); + ClearSessionAndSchedInfo(callerName); + } + OnAllBundlesFinished(BError(BError::Codes::OK)); + return BError(BError::Codes::OK); + } catch (const BError &e) { + return e.GetCode(); // 任意异常产生,终止监听该任务 + } catch (const exception &e) { + HILOGI("Catched an unexpected low-level exception %{public}s", e.what()); + return EPERM; + } catch (...) { + HILOGI("Unexpected exception"); + return EPERM; + } +} + +ErrCode Service::AppDone(ErrCode errCode) +{ + HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + try { + if (session_ == nullptr) { + HILOGE("App finish error, session info is empty"); + return BError(BError::Codes::SA_INVAL_ARG); + } + string callerName = VerifyCallerAndGetCallerName(); + HILOGI("Begin, callerName is: %{public}s, errCode: %{public}d", callerName.c_str(), errCode); + if (session_->OnBundleFileReady(callerName) || errCode != BError(BError::Codes::OK)) { + std::shared_ptr mutexPtr = GetExtensionMutex(callerName); + if (mutexPtr == nullptr) { + HILOGE("extension mutex ptr is nullptr"); + return BError(BError::Codes::SA_INVAL_ARG); + } + std::lock_guard lock(mutexPtr->callbackMutex); + auto backUpConnection = session_->GetExtConnection(callerName); + if (backUpConnection == nullptr) { + HILOGE("App finish error, backUpConnection is empty"); + return BError(BError::Codes::SA_INVAL_ARG); + } + auto proxy = backUpConnection->GetBackupExtProxy(); + if (!proxy) { + throw BError(BError::Codes::SA_INVAL_ARG, "Extension backup Proxy is empty"); + } + proxy->HandleClear(); + session_->StopFwkTimer(callerName); + session_->StopExtTimer(callerName); + backUpConnection->DisconnectBackupExtAbility(); + ClearSessionAndSchedInfo(callerName); + NotifyCallerCurAppDone(errCode, callerName); + } + RemoveExtensionMutex(callerName); + OnAllBundlesFinished(BError(BError::Codes::OK)); + return BError(BError::Codes::OK); + } catch (const BError &e) { + ReleaseOnException(); + HILOGE("AppDone error, err code is: %{public}d", e.GetCode()); + return e.GetCode(); // 任意异常产生,终止监听该任务 + } catch (const exception &e) { + ReleaseOnException(); + HILOGI("Catched an unexpected low-level exception %{public}s", e.what()); + return EPERM; + } catch (...) { + HILOGI("Unexpected exception"); + return EPERM; + } +} + +ErrCode Service::LaunchBackupExtension(const BundleName &bundleName) +{ + HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + try { + HILOGI("begin %{public}s", bundleName.data()); + IServiceReverse::Scenario scenario = session_->GetScenario(); + BConstants::ExtensionAction action; + if (scenario == IServiceReverse::Scenario::BACKUP || scenario == IServiceReverse::Scenario::CLEAN) { + action = BConstants::ExtensionAction::BACKUP; + } else if (scenario == IServiceReverse::Scenario::RESTORE) { + action = BConstants::ExtensionAction::RESTORE; + } else { + throw BError(BError::Codes::SA_INVAL_ARG, "Failed to scenario"); + } + if (SAUtils::IsSABundleName(bundleName)) { + return LaunchBackupSAExtension(bundleName); + } + AAFwk::Want want; + SetWant(want, bundleName, action); + auto backUpConnection = session_->GetExtConnection(bundleName); + if (backUpConnection == nullptr) { + HILOGE("LaunchBackupExtension error, backUpConnection is empty"); + return BError(BError::Codes::SA_INVAL_ARG); + } + if (backUpConnection->IsExtAbilityConnected() && !backUpConnection->WaitDisconnectDone()) { + HILOGE("LaunchBackupExtension error, WaitDisconnectDone failed"); + return BError(BError::Codes::SA_INVAL_ARG); + } + ErrCode ret = backUpConnection->ConnectBackupExtAbility(want, session_->GetSessionUserId()); + if (ret) { + HILOGE("ConnectBackupExtAbility faild, bundleName:%{public}s, ret:%{public}d", bundleName.c_str(), ret); + ExtensionConnectFailRadarReport(bundleName, ret, scenario); + return BError(BError::Codes::SA_BOOT_EXT_FAIL); + } + return BError(BError::Codes::OK); + } catch (const BError &e) { + return e.GetCode(); + } catch (const exception &e) { + HILOGI("Catched an unexpected low-level exception %{public}s", e.what()); + return EPERM; + } catch (...) { + HILOGI("Unexpected exception"); + return EPERM; + } +} + +void Service::SetWant(AAFwk::Want &want, const BundleName &bundleName, const BConstants::ExtensionAction &action) +{ + BJsonUtil::BundleDetailInfo bundleDetail = BJsonUtil::ParseBundleNameIndexStr(bundleName); + string backupExtName = session_->GetBackupExtName(bundleName); /* new device app ext name */ + HILOGI("BackupExtName: %{public}s, bundleName: %{public}s", backupExtName.data(), bundleName.data()); + string versionName = session_->GetBundleVersionName(bundleName); /* old device app version name */ + int64_t versionCode = session_->GetBundleVersionCode(bundleName); /* old device app version code */ + RestoreTypeEnum restoreType = session_->GetBundleRestoreType(bundleName); /* app restore type */ + string bundleExtInfo = session_->GetBackupExtInfo(bundleName); + HILOGI("BundleExtInfo is:%{public}s", GetAnonyString(bundleExtInfo).c_str()); + want.SetElementName(bundleDetail.bundleName, backupExtName); + want.SetParam(BConstants::EXTENSION_ACTION_PARA, static_cast(action)); + want.SetParam(BConstants::EXTENSION_VERSION_CODE_PARA, static_cast(versionCode)); + want.SetParam(BConstants::EXTENSION_RESTORE_TYPE_PARA, static_cast(restoreType)); + want.SetParam(BConstants::EXTENSION_VERSION_NAME_PARA, versionName); + want.SetParam(BConstants::EXTENSION_RESTORE_EXT_INFO_PARA, bundleExtInfo); + want.SetParam(BConstants::EXTENSION_BACKUP_EXT_INFO_PARA, bundleExtInfo); + want.SetParam(BConstants::EXTENSION_APP_CLONE_INDEX_PARA, bundleDetail.bundleIndex); +} + +std::vector Service::GetSupportBackupBundleNames(vector &backupInfos, + bool isIncBackup, const std::vector &srcBundleNames) +{ + HILOGI("Begin"); + std::vector supportBackupNames; + for (auto info : backupInfos) { + HILOGI("Current backupInfo bundleName:%{public}s, index:%{public}d, extName:%{public}s", info.name.c_str(), + info.appIndex, info.extensionName.c_str()); + std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(info.name, info.appIndex); + if (!info.allToBackup) { + if (isIncBackup) { + session_->GetServiceReverseProxy()->IncrementalBackupOnBundleStarted( + BError(BError::Codes::SA_FORBID_BACKUP_RESTORE), bundleNameIndexInfo); + } else { + session_->GetServiceReverseProxy()->BackupOnBundleStarted( + BError(BError::Codes::SA_FORBID_BACKUP_RESTORE), bundleNameIndexInfo); + } + BundleBeginRadarReport(bundleNameIndexInfo, BError(BError::Codes::SA_FORBID_BACKUP_RESTORE).GetCode(), + IServiceReverse::Scenario::BACKUP); + continue; + } + supportBackupNames.emplace_back(bundleNameIndexInfo); + } + HandleNotSupportBundleNames(srcBundleNames, supportBackupNames, isIncBackup); + HILOGI("End"); + return supportBackupNames; +} + +void Service::SetCurrentSessProperties(BJsonEntityCaps::BundleInfo &info, + std::map &isClearDataFlags, const std::string &bundleNameIndexInfo) +{ + HILOGI("Begin"); + if (session_ == nullptr) { + HILOGE("Set currrent session properties error, session is empty"); + return; + } + session_->SetBundleDataSize(bundleNameIndexInfo, info.spaceOccupied); + auto iter = isClearDataFlags.find(bundleNameIndexInfo); + if (iter != isClearDataFlags.end()) { + session_->SetClearDataFlag(bundleNameIndexInfo, iter->second); + } + HILOGI("End"); +} + +void Service::HandleNotSupportBundleNames(const std::vector &srcBundleNames, + std::vector &supportBundleNames, bool isIncBackup) +{ + for (auto bundleName : srcBundleNames) { + auto it = std::find(supportBundleNames.begin(), supportBundleNames.end(), bundleName); + if (it != supportBundleNames.end()) { + continue; + } + HILOGE("bundleName:%{public}s, can not find from supportBundleNames", bundleName.c_str()); + if (isIncBackup) { + session_->GetServiceReverseProxy()->IncrementalBackupOnBundleStarted( + BError(BError::Codes::SA_BUNDLE_INFO_EMPTY), bundleName); + } else { + session_->GetServiceReverseProxy()->BackupOnBundleStarted( + BError(BError::Codes::SA_BUNDLE_INFO_EMPTY), bundleName); + } + } +} +} \ No newline at end of file diff --git a/services/backup_sa/src/module_ipc/svc_backup_connection.cpp b/services/backup_sa/src/module_ipc/svc_backup_connection.cpp index a44451272684c93085e4468067b75608543c35e3..8fc298baad2d4f88f65a5afeb56611aca122c5a5 100644 --- a/services/backup_sa/src/module_ipc/svc_backup_connection.cpp +++ b/services/backup_sa/src/module_ipc/svc_backup_connection.cpp @@ -47,7 +47,8 @@ void SvcBackupConnection::OnAbilityConnectDone(const AppExecFwk::ElementName &el } isConnected_.store(true); string bundleName = element.GetBundleName(); - HILOGI("%{public}s, OnAbilityConnectDone", bundleName.c_str()); + HILOGI("bundleName:%{public}s, OnAbilityConnectDone, bundleNameIndexInfo:%{public}s", bundleName.c_str(), + bundleNameIndexInfo_.c_str()); auto now = std::chrono::system_clock::now(); auto time = std::chrono::system_clock::to_time_t(now); auto ms = std::chrono::duration_cast(now.time_since_epoch()); @@ -63,6 +64,12 @@ void SvcBackupConnection::OnAbilityConnectDone(const AppExecFwk::ElementName &el "PID", getpid(), "TIME", strTime.str() ); + if (bundleNameIndexInfo_.find(bundleName) == string::npos) { + HILOGE("Current bundle name is wrong, bundleNameIndexInfo:%{public}s, bundleName:%{public}s", + bundleNameIndexInfo_.c_str(), bundleName.c_str()); + return; + } + bundleName = bundleNameIndexInfo_; callConnected_(move(bundleName)); HILOGI("called end"); } @@ -71,15 +78,30 @@ void SvcBackupConnection::OnAbilityDisconnectDone(const AppExecFwk::ElementName { HILOGI("called begin"); isConnected_.store(false); - backupProxy_ = nullptr; string bundleName = element.GetBundleName(); + HILOGI("bundleName:%{public}s, OnAbilityDisconnectDone, bundleNameIndexInfo:%{public}s", bundleName.c_str(), + bundleNameIndexInfo_.c_str()); + if (bundleNameIndexInfo_.find(bundleName) == string::npos) { + HILOGE("Current bundle name is wrong, bundleNameIndexInfo:%{public}s, bundleName:%{public}s", + bundleNameIndexInfo_.c_str(), bundleName.c_str()); + return; + } + bundleName = bundleNameIndexInfo_; + if (isSecondOnDisCon_ == false) { + isSecondOnDisCon_.store(true); + } else { + HILOGE("It's error that the backup extension second died before the backup sa. name : %{public}s", + bundleName.data()); + callDied_(move(bundleName), true); + } if (isConnectedDone_ == false) { isConnectedDone_.store(true); HILOGE("It's error that the backup extension dies before the backup sa. name : %{public}s", bundleName.data()); - callDied_(move(bundleName)); + callDied_(move(bundleName), false); } condition_.notify_all(); - HILOGI("called end, name: %{public}s", bundleName.c_str()); + waitCondition_.notify_all(); + HILOGI("called end, name: %{public}s", bundleNameIndexInfo_.c_str()); } ErrCode SvcBackupConnection::ConnectBackupExtAbility(AAFwk::Want &want, int32_t userId) @@ -103,7 +125,7 @@ ErrCode SvcBackupConnection::DisconnectBackupExtAbility() HILOGE("Dis connect failed"); return false; } - return extPtr->GetBackupExtProxy() == nullptr; + return extPtr->isConnected_.load() == false; }; if (condition_.wait_for(lock, std::chrono::seconds(WAIT_TIME), callback)) { HILOGI("Wait until the connection ends"); @@ -112,6 +134,17 @@ ErrCode SvcBackupConnection::DisconnectBackupExtAbility() return ret; } +bool SvcBackupConnection::WaitDisconnectDone() +{ + std::unique_lock lock(waitMutex_); + if (waitCondition_.wait_for(lock, std::chrono::seconds(WAIT_TIME), + [this]() { return isConnected_.load() == false; })) { + HILOGI("Wait disconnected done success"); + return true; + } + return false; +} + bool SvcBackupConnection::IsExtAbilityConnected() { return isConnected_.load(); @@ -127,7 +160,7 @@ void SvcBackupConnection::SetCallback(function callC callConnected_ = callConnected; } -void SvcBackupConnection::SetCallDied(function callDied) +void SvcBackupConnection::SetCallDied(function callDied) { callDied_ = callDied; } diff --git a/services/backup_sa/src/module_ipc/svc_extension_incremental_proxy.cpp b/services/backup_sa/src/module_ipc/svc_extension_incremental_proxy.cpp index c4355e6aa43a0cc28a328383abbd922a1ec295d8..03dbb4fe3133fdaf0f030579646aeaa0c6626272 100644 --- a/services/backup_sa/src/module_ipc/svc_extension_incremental_proxy.cpp +++ b/services/backup_sa/src/module_ipc/svc_extension_incremental_proxy.cpp @@ -101,13 +101,15 @@ ErrCode SvcExtensionProxy::HandleIncrementalBackup(UniqueFd incrementalFd, Uniqu return reply.ReadInt32(); } -ErrCode SvcExtensionProxy::IncrementalOnBackup() +ErrCode SvcExtensionProxy::IncrementalOnBackup(bool isClearData) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); HILOGD("Start"); BExcepUltils::BAssert(Remote(), BError::Codes::SDK_INVAL_ARG, "Remote is nullptr"); MessageParcel data; - data.WriteInterfaceToken(GetDescriptor()); + if (!data.WriteInterfaceToken(GetDescriptor()) || !data.WriteBool(isClearData)) { + return BError(BError::Codes::SDK_INVAL_ARG, "build param fail."); + } MessageParcel reply; MessageOption option; @@ -122,6 +124,27 @@ ErrCode SvcExtensionProxy::IncrementalOnBackup() return BError(BError::Codes::OK); } +ErrCode SvcExtensionProxy::User0OnBackup() +{ + HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); + HILOGD("Start"); + BExcepUltils::BAssert(Remote(), BError::Codes::SDK_INVAL_ARG, "Remote is nullptr"); + MessageParcel data; + data.WriteInterfaceToken(GetDescriptor()); + + MessageParcel reply; + MessageOption option; + int32_t ret = Remote()->SendRequest(static_cast(IExtensionInterfaceCode::CMD_HANDLE_USER_0_BACKUP), + data, reply, option); + if (ret != NO_ERROR) { + HILOGE("Received error %{public}d when doing IPC", ret); + return ErrCode(ret); + } + + HILOGD("Successful"); + return reply.ReadInt32(); +} + tuple SvcExtensionProxy::GetIncrementalBackupFileHandle() { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); diff --git a/services/backup_sa/src/module_ipc/svc_extension_proxy.cpp b/services/backup_sa/src/module_ipc/svc_extension_proxy.cpp index 57e126eb35275538bcb63f56b1928035df7e478a..ce2bfcc36b75865ade94bba5f7cac9cd889af247 100644 --- a/services/backup_sa/src/module_ipc/svc_extension_proxy.cpp +++ b/services/backup_sa/src/module_ipc/svc_extension_proxy.cpp @@ -79,13 +79,15 @@ ErrCode SvcExtensionProxy::HandleClear() return reply.ReadInt32(); } -ErrCode SvcExtensionProxy::HandleBackup() +ErrCode SvcExtensionProxy::HandleBackup(bool isClearData) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); HILOGI("Start"); BExcepUltils::BAssert(Remote(), BError::Codes::SDK_INVAL_ARG, "Remote is nullptr"); MessageParcel data; - data.WriteInterfaceToken(GetDescriptor()); + if (!data.WriteInterfaceToken(GetDescriptor()) || !data.WriteBool(isClearData)) { + return BError(BError::Codes::SDK_INVAL_ARG, "build param fail."); + } MessageParcel reply; MessageOption option; @@ -126,13 +128,15 @@ ErrCode SvcExtensionProxy::PublishFile(const string &fileName) return reply.ReadInt32(); } -ErrCode SvcExtensionProxy::HandleRestore() +ErrCode SvcExtensionProxy::HandleRestore(bool isClearData) { HITRACE_METER_NAME(HITRACE_TAG_FILEMANAGEMENT, __PRETTY_FUNCTION__); HILOGI("Start"); BExcepUltils::BAssert(Remote(), BError::Codes::SDK_INVAL_ARG, "Remote is nullptr"); MessageParcel data; - data.WriteInterfaceToken(GetDescriptor()); + if (!data.WriteInterfaceToken(GetDescriptor()) || !data.WriteBool(isClearData)) { + return BError(BError::Codes::SDK_INVAL_ARG, "build param fail."); + } MessageParcel reply; MessageOption option; diff --git a/services/backup_sa/src/module_ipc/svc_restore_deps_manager.cpp b/services/backup_sa/src/module_ipc/svc_restore_deps_manager.cpp index 115db71c495443b2d8149ecec32c30ac24481fba..682b0a2b4ecc6514ba7244c64fa014bf618c17cb 100644 --- a/services/backup_sa/src/module_ipc/svc_restore_deps_manager.cpp +++ b/services/backup_sa/src/module_ipc/svc_restore_deps_manager.cpp @@ -15,6 +15,7 @@ #include "module_ipc/svc_restore_deps_manager.h" +#include "b_jsonutil/b_jsonutil.h" #include "filemgmt_libhilog.h" namespace OHOS::FileManagement::Backup { @@ -28,23 +29,16 @@ vector SvcRestoreDepsManager::GetRestoreBundleNames(const vector &bundleInfos) { for (auto &bundleInfo : bundleInfos) { - if (depsMap_.find(bundleInfo.name) != depsMap_.end()) { + std::string bundleNameIndexInfo = BJsonUtil::BuildBundleNameIndexInfo(bundleInfo.name, bundleInfo.appIndex); + if (depsMap_.find(bundleNameIndexInfo) != depsMap_.end()) { continue; } allBundles_.emplace_back(bundleInfo); @@ -100,7 +95,7 @@ void SvcRestoreDepsManager::BuildDepsMap(const vector lock(lock_); if (impl_.scenario != scenario) { + HILOGE("Inconsistent scenario, impl scenario:%{public}d", impl_.scenario); + AppRadar::Info info("", "", "Inconsistent scenario"); + AppRadar::GetInstance().RecordDefaultFuncRes(info, "SvcSessionManager::VerifyCallerAndScenario", impl_.userId, + BizStageBackup::BIZ_STAGE_PERMISSION_CHECK_FAIL, + BError(BError::Codes::SDK_MIXED_SCENARIO).GetCode()); throw BError(BError::Codes::SDK_MIXED_SCENARIO); } if (impl_.clientToken != clientToken) { + AppRadar::Info info2("", "", "Caller mismatched"); + AppRadar::GetInstance().RecordDefaultFuncRes(info2, "SvcSessionManager::VerifyCallerAndScenario", impl_.userId, + BizStageBackup::BIZ_STAGE_PERMISSION_CHECK_FAIL, + BError(BError::Codes::SDK_MIXED_SCENARIO).GetCode()); throw BError(BError::Codes::SA_REFUSED_ACT, "Caller mismatched"); } HILOGD("Succeed to verify the caller"); @@ -53,7 +64,12 @@ SvcSessionManager::Impl SvcSessionManager::GetImpl() return impl_; } -ErrCode SvcSessionManager::Active(Impl newImpl) +int SvcSessionManager::GetSessionCnt() +{ + return sessionCnt_.load(); +} + +ErrCode SvcSessionManager::Active(Impl newImpl, bool force) { unique_lock lock(lock_); const Impl &oldImpl = impl_; @@ -62,37 +78,48 @@ ErrCode SvcSessionManager::Active(Impl newImpl) return BError(BError::Codes::SA_REFUSED_ACT); } - if (!newImpl.clientToken) { + if (!force && !newImpl.clientToken) { throw BError(BError::Codes::SA_INVAL_ARG, "No caller token was specified"); } - if (newImpl.scenario == IServiceReverse::Scenario::UNDEFINED) { + if (!force && newImpl.scenario == IServiceReverse::Scenario::UNDEFINED) { throw BError(BError::Codes::SA_INVAL_ARG, "No scenario was specified"); } - InitClient(newImpl); + if (!force) { + InitClient(newImpl); + } impl_ = newImpl; + IncreaseSessionCnt(__PRETTY_FUNCTION__); return BError(BError::Codes::OK); } void SvcSessionManager::Deactive(const wptr &remoteInAction, bool force) { unique_lock lock(lock_); - if (!impl_.clientToken || !impl_.clientProxy) { + if (!impl_.clientToken) { HILOGI("Empty session"); return; } if (!force && (!impl_.clientToken || !impl_.clientProxy)) { - throw BError(BError::Codes::SA_REFUSED_ACT, "Try to deactive an empty session"); + return; } - auto remoteHeldByProxy = impl_.clientProxy->AsObject(); - if (!force && (remoteInAction != remoteHeldByProxy)) { + if (!force && (remoteInAction != impl_.clientProxy->AsObject())) { throw BError(BError::Codes::SA_INVAL_ARG, "Only the client actived the session can deactive it"); } deathRecipient_ = nullptr; + AppRadar::Info info("", "", "deactive session success"); + if (impl_.scenario == IServiceReverse::Scenario::RESTORE) { + AppRadar::GetInstance().RecordRestoreFuncRes(info, "SvcSessionManager::Deactive", impl_.userId, + BizStageRestore::BIZ_STAGE_DEACTIVE_SESSION, ERR_OK); + } else if (impl_.scenario == IServiceReverse::Scenario::BACKUP) { + AppRadar::GetInstance().RecordBackupFuncRes(info, "SvcSessionManager::Deactive", impl_.userId, + BizStageBackup::BIZ_STAGE_DEACTIVE_SESSION, ERR_OK); + } HILOGI("Succeed to deactive a session"); impl_ = {}; extConnectNum_ = 0; + DecreaseSessionCnt(__PRETTY_FUNCTION__); } void SvcSessionManager::VerifyBundleName(string &bundleName) @@ -144,7 +171,7 @@ bool SvcSessionManager::OnBundleFileReady(const string &bundleName, const string if (!impl_.clientToken) { throw BError(BError::Codes::SA_INVAL_ARG, "No caller token was specified"); } - HILOGD("Begin, bundleName name is:%{public}s", bundleName.c_str()); + HILOGD("Begin, bundleName name is:%{private}s", bundleName.c_str()); auto it = impl_.backupExtNameMap.find(bundleName); if (it == impl_.backupExtNameMap.end()) { stringstream ss; @@ -171,7 +198,7 @@ bool SvcSessionManager::OnBundleFileReady(const string &bundleName, const string return true; } } - HILOGD("End, bundleName name is:%{public}s", bundleName.c_str()); + HILOGD("End, bundleName name is:%{private}s", bundleName.c_str()); return false; } @@ -205,12 +232,18 @@ void SvcSessionManager::RemoveExtInfo(const string &bundleName) unique_lock lock(lock_); auto it = impl_.backupExtNameMap.find(bundleName); if (it == impl_.backupExtNameMap.end()) { + HILOGI("BackupExtNameMap not contain %{public}s", bundleName.c_str()); return; } - impl_.backupExtNameMap.erase(it); if (extConnectNum_) { extConnectNum_--; } + int32_t &appendNum = impl_.backupExtNameMap[bundleName].appendNum; + if (--appendNum > 0) { + HILOGI("No need remove bundleName:%{public}s, appendNum=%{public}d", bundleName.c_str(), appendNum); + return; + } + impl_.backupExtNameMap.erase(it); } wptr SvcSessionManager::GetExtConnection(const BundleName &bundleName) @@ -247,14 +280,14 @@ std::weak_ptr SvcSessionManager::GetSAExtConnection(const Bu sptr SvcSessionManager::GetBackupAbilityExt(const string &bundleName) { - auto callDied = [revPtr {reversePtr_}](const string &&bundleName) { + auto callDied = [revPtr {reversePtr_}](const string &&bundleName, bool isSecondCalled = false) { auto revPtrStrong = revPtr.promote(); if (!revPtrStrong) { // 服务先于客户端死亡是一种异常场景,但该场景对本流程来说也没什么影响,所以只是简单记录一下 HILOGW("It's curious that the backup sa dies before the backup client"); return; } - revPtrStrong->OnBackupExtensionDied(move(bundleName)); + revPtrStrong->OnBackupExtensionDied(move(bundleName), isSecondCalled); }; auto callConnected = [revPtr {reversePtr_}](const string &&bundleName) { @@ -267,7 +300,7 @@ sptr SvcSessionManager::GetBackupAbilityExt(const string &b revPtrStrong->ExtConnectDone(move(bundleName)); }; - return sptr(new SvcBackupConnection(callDied, callConnected)); + return sptr(new SvcBackupConnection(callDied, callConnected, bundleName)); } std::shared_ptr SvcSessionManager::GetBackupSAExt(const std::string &bundleName) @@ -346,6 +379,14 @@ void SvcSessionManager::InitClient(Impl &newImpl) }; deathRecipient_ = sptr(new SvcDeathRecipient(callback)); remoteObj->AddDeathRecipient(deathRecipient_); + AppRadar::Info info("", "", "active session success"); + if (newImpl.scenario == IServiceReverse::Scenario::RESTORE) { + AppRadar::GetInstance().RecordRestoreFuncRes(info, "SvcSessionManager::InitClient", newImpl.userId, + BizStageRestore::BIZ_STAGE_ACTIVE_SESSION, ERR_OK); + } else if (newImpl.scenario == IServiceReverse::Scenario::BACKUP) { + AppRadar::GetInstance().RecordBackupFuncRes(info, "SvcSessionManager::InitClient", newImpl.userId, + BizStageBackup::BIZ_STAGE_ACTIVE_SESSION, ERR_OK); + } HILOGI("Succeed to active a session"); } @@ -397,6 +438,10 @@ bool SvcSessionManager::GetSchedBundleName(string &bundleName) for (auto &&it : impl_.backupExtNameMap) { if (it.second.schedAction == BConstants::ServiceSchedAction::WAIT) { bundleName = it.first; + if (!it.second.isReadyLaunch) { + HILOGE("Current bundle:%{public}s can not sched, baseInfo is not set done", bundleName.c_str()); + return false; + } it.second.schedAction = BConstants::ServiceSchedAction::START; extConnectNum_++; return true; @@ -483,6 +528,15 @@ void SvcSessionManager::AppendBundles(const vector &bundleNames) for (auto &&bundleName : bundleNames) { HILOGD("bundleName: %{public}s", bundleName.c_str()); BackupExtInfo info {}; + auto it = impl_.backupExtNameMap.find(bundleName); + if (it != impl_.backupExtNameMap.end()) { + HILOGI("BackupExtNameMap already contain %{public}s", bundleName.c_str()); + info.backUpConnection = impl_.backupExtNameMap[bundleName].backUpConnection; + info.saBackupConnection = impl_.backupExtNameMap[bundleName].saBackupConnection; + info.appendNum = impl_.backupExtNameMap[bundleName].appendNum + 1; + impl_.backupExtNameMap[bundleName] = info; + continue; + } if (SAUtils::IsSABundleName(bundleName)) { info.saBackupConnection = GetBackupSAExt(bundleName); } else { @@ -535,7 +589,6 @@ bool SvcSessionManager::IsOnAllBundlesFinished() bool SvcSessionManager::IsOnOnStartSched() { - HILOGI("Begin"); shared_lock lock(lock_); if (!impl_.clientToken) { throw BError(BError::Codes::SA_INVAL_ARG, "No caller token was specified"); @@ -543,7 +596,7 @@ bool SvcSessionManager::IsOnOnStartSched() if (impl_.isBackupStart && impl_.backupExtNameMap.size()) { return true; } - HILOGI("End"); + return false; } @@ -571,7 +624,6 @@ void SvcSessionManager::SetBundleRestoreType(const std::string &bundleName, Rest auto it = GetBackupExtNameMap(bundleName); it->second.restoreType = restoreType; - impl_.restoreDataType = restoreType; } RestoreTypeEnum SvcSessionManager::GetBundleRestoreType(const std::string &bundleName) @@ -661,107 +713,170 @@ uint32_t SvcSessionManager::CalAppProcessTime(const std::string &bundleName) } timeout = timeout < minTimeout ? minTimeout : timeout; resTimeoutMs = (uint32_t)(timeout * invertMillisecond % UINT_MAX); /* conver second to millisecond */ - HILOGI("Calculate App extension process run timeout=%{public}u(us), bundleName=%{public}s ", resTimeoutMs, + HILOGI("Calculate App extension process run timeout=%{public}u(ms), bundleName=%{public}s ", resTimeoutMs, bundleName.c_str()); return resTimeoutMs; } -void SvcSessionManager::BundleExtTimerStart(const std::string &bundleName, const Utils::Timer::TimerCallback &callback) +bool SvcSessionManager::StartFwkTimer(const std::string &bundleName, const Utils::Timer::TimerCallback &callback) { unique_lock lock(lock_); + HILOGI("StartFwkTimer begin bundleName %{public}s", bundleName.c_str()); if (!impl_.clientToken) { - throw BError(BError::Codes::SA_INVAL_ARG, "No caller token was specified"); + HILOGE("No caller token was specified"); + return false; + } + auto it = GetBackupExtNameMap(bundleName); + if (it->second.fwkTimerStatus == true) { + HILOGE("FwkTimer is registered, unregister first."); + return false; } uint32_t timeout = CalAppProcessTime(bundleName); + it->second.fwkTimerStatus = true; + it->second.timerId = timer_.Register(callback, timeout, true); + HILOGI("StartFwkTimer end bundleName %{public}s", bundleName.c_str()); + return true; +} + +bool SvcSessionManager::StopFwkTimer(const std::string &bundleName) +{ + unique_lock lock(lock_); + HILOGI("StopFwkTimer begin bundleName %{public}s", bundleName.c_str()); + if (!impl_.clientToken) { + HILOGE("No caller token was specified"); + return false; + } auto it = GetBackupExtNameMap(bundleName); - if (it->second.timerStatus == false) { - it->second.timerStatus = true; - it->second.extTimerId = extBundleTimer.Register(callback, timeout, true); + if (it->second.fwkTimerStatus == false) { + HILOGE("FwkTimer is unregistered, register first."); + return true; } + + it->second.fwkTimerStatus = false; + timer_.Unregister(it->second.timerId); + HILOGI("StopFwkTimer end bundleName %{public}s", bundleName.c_str()); + return true; } -bool SvcSessionManager::UpdateTimer(const std::string &bundleName, uint32_t timeOut, - const Utils::Timer::TimerCallback &callback) +bool SvcSessionManager::StartExtTimer(const std::string &bundleName, const Utils::Timer::TimerCallback &callback) { unique_lock lock(lock_); + HILOGI("StartExtTimer begin bundleName %{public}s", bundleName.c_str()); if (!impl_.clientToken) { - throw BError(BError::Codes::SA_INVAL_ARG, "No caller token was specified"); + HILOGE("No caller token was specified"); + return false; } + auto it = GetBackupExtNameMap(bundleName); + if (it->second.extTimerStatus == true) { + HILOGE("ExtTimer is registered, unregister first."); + return false; + } + uint32_t timeout = it->second.timeout; + timeout = (timeout != BConstants::TIMEOUT_INVALID) ? timeout : BConstants::DEFAULT_TIMEOUT; + it->second.extTimerStatus = true; + it->second.timerId = timer_.Register(callback, timeout, true); + HILOGI("StartExtTimer end, timeout %{public}u(ms), bundleName %{public}s", timeout, bundleName.c_str()); + return true; +} +bool SvcSessionManager::StopExtTimer(const std::string &bundleName) +{ + unique_lock lock(lock_); + HILOGI("StopExtTimer begin bundleName %{public}s", bundleName.c_str()); + if (!impl_.clientToken) { + HILOGE("No caller token was specified"); + return false; + } auto it = GetBackupExtNameMap(bundleName); - if (it->second.timerStatus == true) { - // 定时器已存在,则先销毁,再重新注册 - it->second.timerStatus = false; - extBundleTimer.Unregister(it->second.extTimerId); - HILOGI("UpdateTimer timeout=%{public}u(ms), bundleName=%{public}s ", - timeOut, bundleName.c_str()); - it->second.extTimerId = extBundleTimer.Register(callback, timeOut, true); - it->second.timerStatus = true; + if (it->second.extTimerStatus == false) { + HILOGE("ExtTimer is unregistered, register first."); return true; } - return false; + + it->second.extTimerStatus = false; + it->second.timeout = BConstants::TIMEOUT_INVALID; + timer_.Unregister(it->second.timerId); + HILOGI("StopExtTimer end bundleName %{public}s", bundleName.c_str()); + return true; } -void SvcSessionManager::BundleExtTimerStop(const std::string &bundleName) +bool SvcSessionManager::UpdateTimer(const std::string &bundleName, uint32_t timeout, + const Utils::Timer::TimerCallback &callback) { unique_lock lock(lock_); + HILOGI("UpdateTimer begin bundleName %{public}s", bundleName.c_str()); if (!impl_.clientToken) { - throw BError(BError::Codes::SA_INVAL_ARG, "No caller token was specified"); + HILOGE("No caller token was specified"); + return false; } - auto it = GetBackupExtNameMap(bundleName); - if (it->second.timerStatus == true) { - it->second.timerStatus = false; - extBundleTimer.Unregister(it->second.extTimerId); + it->second.timeout = timeout; + if (it->second.extTimerStatus == false) { + HILOGI("ExtTimer is unregistered, just store timeout %{public}u(ms)", timeout); + return true; } + + timer_.Unregister(it->second.timerId); + HILOGI("UpdateTimer timeout %{public}u(ms), bundleName %{public}s ", timeout, bundleName.c_str()); + it->second.timerId = timer_.Register(callback, timeout, true); + it->second.extTimerStatus = true; + HILOGI("UpdateTimer end bundleName %{public}s", bundleName.c_str()); + return true; } -void SvcSessionManager::IncreaseSessionCnt() +void SvcSessionManager::IncreaseSessionCnt(const std::string funcName) { sessionCnt_++; + HILOGI("func name:%{public}s, %{public}d.", funcName.c_str(), sessionCnt_.load()); } -void SvcSessionManager::DecreaseSessionCnt() +void SvcSessionManager::DecreaseSessionCnt(const std::string funcName) { - unique_lock lock(lock_); if (sessionCnt_.load() > 0) { sessionCnt_--; } else { HILOGE("Invalid sessionCount."); } + HILOGI("func name:%{public}s, %{public}d.", funcName.c_str(), sessionCnt_.load()); } -void SvcSessionManager::ClearSessionData() +ErrCode SvcSessionManager::ClearSessionData() { unique_lock lock(lock_); + ErrCode ret = BError(BError::Codes::OK); for (auto &&it : impl_.backupExtNameMap) { // clear timer - if (it.second.timerStatus == true) { - it.second.timerStatus = false; - extBundleTimer.Unregister(it.second.extTimerId); + if (it.second.fwkTimerStatus == true || it.second.extTimerStatus == true) { + it.second.fwkTimerStatus = false; + it.second.extTimerStatus = false; + timer_.Unregister(it.second.timerId); } // disconnect extension if (it.second.schedAction == BConstants::ServiceSchedAction::RUNNING) { auto backUpConnection = it.second.backUpConnection; if (backUpConnection == nullptr) { HILOGE("Clear session error, backUpConnection is empty"); - return; + return BError(BError::Codes::SA_INVAL_ARG); } auto proxy = backUpConnection->GetBackupExtProxy(); if (proxy == nullptr) { HILOGE("Clear session error, proxy is empty"); - return; + return BError(BError::Codes::EXT_INVAL_ARG); } if (impl_.restoreDataType != RestoreTypeEnum::RESTORE_DATA_READDY) { - proxy->HandleClear(); + ret = proxy->HandleClear(); } backUpConnection->DisconnectBackupExtAbility(); } + if (ret != BError(BError::Codes::OK)) { + return ret; + } // clear data it.second.schedAction = BConstants::ServiceSchedAction::FINISH; } impl_.backupExtNameMap.clear(); + return BError(BError::Codes::OK); } bool SvcSessionManager::GetIsIncrementalBackup() @@ -816,8 +931,106 @@ void SvcSessionManager::SetMemParaCurSize(int32_t size) memoryParaCurSize_ = size; } +void SvcSessionManager::SetClearDataFlag(const std::string &bundleName, bool isClearData) +{ + unique_lock lock(lock_); + if (!impl_.clientToken) { + throw BError(BError::Codes::SA_INVAL_ARG, "No caller token was specified"); + } + auto it = GetBackupExtNameMap(bundleName); + it->second.isClearData = isClearData; + HILOGI("bundleName:%{public}s, set clear data flag:%{public}d.", bundleName.c_str(), isClearData); +} +bool SvcSessionManager::GetClearDataFlag(const std::string &bundleName) +{ + unique_lock lock(lock_); + if (!impl_.clientToken) { + throw BError(BError::Codes::SA_INVAL_ARG, "No caller token was specified"); + } + auto it = GetBackupExtNameMap(bundleName); + return it->second.isClearData; +} + bool SvcSessionManager::ValidRestoreDataType(RestoreTypeEnum restoreDataType) { return impl_.restoreDataType == restoreDataType; } + +bool SvcSessionManager::CleanAndCheckIfNeedWait(ErrCode &ret, std::vector &bundleNameList) +{ + unique_lock lock(lock_); + for (auto it = impl_.backupExtNameMap.begin(); it != impl_.backupExtNameMap.end();) { + if (it->second.schedAction == BConstants::ServiceSchedAction::WAIT) { + it = impl_.backupExtNameMap.erase(it); + } else if (it->second.schedAction == BConstants::ServiceSchedAction::START || + (it->second.schedAction == BConstants::ServiceSchedAction::RUNNING && !it->second.isInPublishFile)) { + if (it->second.fwkTimerStatus == true || it->second.extTimerStatus == true) { + it->second.fwkTimerStatus = false; + it->second.extTimerStatus = false; + timer_.Unregister(it->second.timerId); + } + auto backUpConnection = it->second.backUpConnection; + if (backUpConnection == nullptr) { + HILOGE("Clear session error, backUpConnection is empty"); + it = impl_.backupExtNameMap.erase(it); + continue; + } + auto proxy = backUpConnection->GetBackupExtProxy(); + // start action + if (proxy == nullptr) { + HILOGE("Clear session error, backUpConnection is empty"); + backUpConnection->DisconnectBackupExtAbility(); + it = impl_.backupExtNameMap.erase(it); + continue; + } + // running action + ErrCode retTmp = ERR_OK; + if (impl_.restoreDataType != RestoreTypeEnum::RESTORE_DATA_READDY) { + retTmp = proxy->HandleClear(); + } + if (retTmp == ERR_OK) { + bundleNameList.push_back(it->first); + } else { + ret = retTmp; + } + backUpConnection->DisconnectBackupExtAbility(); + it = impl_.backupExtNameMap.erase(it); + } else { + ++it; + } + } + if (impl_.backupExtNameMap.empty()) { + HILOGI("Release normally, no need wait"); + return false; + } + HILOGI("Release abnormally, need wait for restore"); + return true; +} + +void SvcSessionManager::SetPublishFlag(const std::string &bundleName) +{ + unique_lock lock(lock_); + if (!impl_.clientToken) { + throw BError(BError::Codes::SA_INVAL_ARG, "No caller token was specified"); + } + auto it = GetBackupExtNameMap(bundleName); + it->second.isInPublishFile = true; + HILOGE("Set PublishFile success, bundleName = %{public}s", bundleName.c_str()); +} + +void SvcSessionManager::SetImplRestoreType(const RestoreTypeEnum restoreType) +{ + impl_.restoreDataType = restoreType; +} + +void SvcSessionManager::SetIsReadyLaunch(const std::string &bundleName) +{ + unique_lock lock(lock_); + if (!impl_.clientToken) { + throw BError(BError::Codes::SA_INVAL_ARG, "No caller token was specified"); + } + auto it = GetBackupExtNameMap(bundleName); + it->second.isReadyLaunch = true; + HILOGE("SetIsReadyLaunch success, bundleName = %{public}s", bundleName.c_str()); +} } // namespace OHOS::FileManagement::Backup diff --git a/services/backup_sa/src/module_notify/notify_work_service.cpp b/services/backup_sa/src/module_notify/notify_work_service.cpp index 093f06d208eedeb456f8407272eac836d986be28..f9e403a22aaab708a59611f62b04bd40ca429da3 100644 --- a/services/backup_sa/src/module_notify/notify_work_service.cpp +++ b/services/backup_sa/src/module_notify/notify_work_service.cpp @@ -25,9 +25,6 @@ #include "want_params.h" namespace OHOS::FileManagement::Backup { -namespace { - const static std::string EVENT_NAME = "COMMON_EVENT_RESTORE_START"; -} NotifyWorkService::NotifyWorkService() {} NotifyWorkService::~NotifyWorkService() {} @@ -43,7 +40,7 @@ bool NotifyWorkService::NotifyBundleDetail(BJsonUtil::BundleDetailInfo bundleDet want.SetParam("userId", bundleDetailInfo.userId); want.SetParam("index", bundleDetailInfo.bundleIndex); want.SetParam("detail", bundleDetail); - want.SetAction(EVENT_NAME); + want.SetAction(EventFwk::CommonEventSupport::COMMON_EVENT_RESTORE_START); EventFwk::CommonEventData commonData {want}; HILOGI("End publish event, bundleName is: %{public}s", bundleName.c_str()); return EventFwk::CommonEventManager::PublishCommonEvent(commonData); diff --git a/services/backup_sa/src/module_sched/sched_scheduler.cpp b/services/backup_sa/src/module_sched/sched_scheduler.cpp index 726c742d466df94cb84b64c6a2ba80cff02bdf2b..4510666123e4d68f077c8d150994828fa08a4947 100644 --- a/services/backup_sa/src/module_sched/sched_scheduler.cpp +++ b/services/backup_sa/src/module_sched/sched_scheduler.cpp @@ -29,6 +29,7 @@ #include "b_error/b_error.h" #include "b_ohos/startup/backup_para.h" +#include "b_radar/b_radar.h" #include "filemgmt_libhilog.h" #include "iservice_registry.h" #include "module_external/bms_adapter.h" @@ -39,6 +40,21 @@ namespace OHOS::FileManagement::Backup { using namespace std; +void ExtDiedClearFailRadarReport(const string& bundleName, IServiceReverse::Scenario scenario, ErrCode res) +{ + if (res == ERR_OK) { + return; + } + AppRadar::Info info(bundleName, "", ""); + if (scenario == IServiceReverse::Scenario::RESTORE) { + AppRadar::GetInstance().RecordRestoreFuncRes(info, "SchedScheduler::ExecutingQueueTasks", + AppRadar::GetInstance().GetUserId(), BizStageRestore::BIZ_STAGE_EXTENSION_ABNORMAL_EXIT_CLEAR_FAIL, res); + } else if (scenario == IServiceReverse::Scenario::BACKUP) { + AppRadar::GetInstance().RecordBackupFuncRes(info, "SchedScheduler::ExecutingQueueTasks", + AppRadar::GetInstance().GetUserId(), BizStageBackup::BIZ_STAGE_EXTENSION_ABNORMAL_EXIT_CLEAR_FAIL, res); + } +} + void SchedScheduler::Sched(string bundleName) { if (bundleName == "") { @@ -72,28 +88,30 @@ void SchedScheduler::Sched(string bundleName) void SchedScheduler::ExecutingQueueTasks(const string &bundleName) { - HILOGE("start"); if (sessionPtr_ == nullptr) { HILOGE("ExecutingQueueTasks bundle %{public}s error, sessionPtr is empty", bundleName.c_str()); return; } BConstants::ServiceSchedAction action = sessionPtr_->GetServiceSchedAction(bundleName); if (action == BConstants::ServiceSchedAction::START) { - // 注册启动定时器 + // register timer for connect extension auto callStart = [reversePtr {reversePtr_}, bundleName]() { HILOGE("Extension connect failed = %{public}s", bundleName.data()); auto ptr = reversePtr.promote(); if (ptr) { - ptr->ExtConnectFailed(bundleName, BError(BError::Codes::SA_BOOT_TIMEOUT)); + ptr->ExtConnectFailed(bundleName, BError(BError::Codes::SA_BOOT_EXT_TIMEOUT)); } }; auto iTime = extTime_.Register(callStart, BConstants::EXT_CONNECT_MAX_TIME, true); unique_lock lock(lock_); bundleTimeVec_.emplace_back(make_tuple(bundleName, iTime)); lock.unlock(); - // 启动extension + // launch extension if (reversePtr_ != nullptr) { - reversePtr_->LaunchBackupExtension(bundleName); + ErrCode errCode = reversePtr_->LaunchBackupExtension(bundleName); + if (errCode) { + reversePtr_->ExtConnectFailed(bundleName, errCode); + } } } else if (action == BConstants::ServiceSchedAction::RUNNING) { HILOGI("Current bundle %{public}s process is running", bundleName.data()); @@ -106,16 +124,20 @@ void SchedScheduler::ExecutingQueueTasks(const string &bundleName) throw BError(BError::Codes::SA_INVAL_ARG, "Failed to find timer"); } auto &[bName, iTime] = *iter; - // 移除启动定时器 当前逻辑无启动成功后的ext心跳检测 + // unregister timer extTime_.Unregister(iTime); lock.unlock(); - // 开始执行备份恢复流程 - HILOGI("Current bundle %{public}s extension start", bundleName.data()); - //通知应用市场设置处置 + //notify AppGallery to start restore if (reversePtr_ != nullptr) { + reversePtr_->StartRunningTimer(bundleName); reversePtr_->SendStartAppGalleryNotify(bundleName); reversePtr_->ExtStart(bundleName); } + } else if (action == BConstants::ServiceSchedAction::CLEAN) { + HILOGI("Current bundle %{public}s process is cleaning", bundleName.data()); + ErrCode res = reversePtr_->ClearResidualBundleData(bundleName); + IServiceReverse::Scenario scenario = sessionPtr_->GetScenario(); + ExtDiedClearFailRadarReport(bundleName, scenario, res); } } @@ -137,16 +159,14 @@ void SchedScheduler::RemoveExtConn(const string &bundleName) void SchedScheduler::StartTimer() { extTime_.Setup(); - if (!BackupPara().GetBackupOverrideBackupSARelease()) { - TryUnloadServiceTimer(); - } + TryUnloadServiceTimer(); } void SchedScheduler::TryUnloadServiceTimer(bool force) { auto tryUnload = [sessionPtr {sessionPtr_}]() { auto ptr = sessionPtr.promote(); - if (ptr && !ptr->NeedToUnloadService()) { + if (ptr && ptr->GetSessionCnt() > 0) { return; } HILOGI("Unload system ability"); diff --git a/services/backupservice.para b/services/backupservice.para index b2d857b67d47afa32f6c827f5811be12a6f6652d..f87a8b1a6a5f84f4c4d0f621d513b120577b9eb3 100644 --- a/services/backupservice.para +++ b/services/backupservice.para @@ -11,4 +11,4 @@ # See the License for the specific language governing permissions and # limitations under the License. -persist.backupservice.workstatus=false \ No newline at end of file +persist.backupservice.workstatus=true \ No newline at end of file diff --git a/test/fuzztest/backupext_fuzzer/BUILD.gn b/test/fuzztest/backupext_fuzzer/BUILD.gn index b406dbcd5abcaaecf629daaae384b75e6e03c970..5d32a6bd681a5347f6590ec3cf19485f855f612a 100644 --- a/test/fuzztest/backupext_fuzzer/BUILD.gn +++ b/test/fuzztest/backupext_fuzzer/BUILD.gn @@ -42,6 +42,7 @@ ohos_fuzztest("BackupExtFuzzTest") { "${path_backup}/frameworks/native/backup_ext/src/ext_backup_loader.cpp", "${path_backup}/frameworks/native/backup_ext/src/ext_extension.cpp", "${path_backup}/frameworks/native/backup_ext/src/ext_extension_stub.cpp", + "${path_backup}/frameworks/native/backup_ext/src/sub_ext_extension.cpp", "${path_backup}/frameworks/native/backup_ext/src/tar_file.cpp", "${path_backup}/frameworks/native/backup_ext/src/untar_file.cpp", "backupext_fuzzer.cpp", diff --git a/test/fuzztest/backupext_fuzzer/backupext_fuzzer.cpp b/test/fuzztest/backupext_fuzzer/backupext_fuzzer.cpp index 2528f0082b50f842a0afae2763c90b061983ce2b..d00abd06b85291998fde89fecb04c02d5267fd01 100644 --- a/test/fuzztest/backupext_fuzzer/backupext_fuzzer.cpp +++ b/test/fuzztest/backupext_fuzzer/backupext_fuzzer.cpp @@ -273,7 +273,7 @@ extern "C" int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) { /* Run your code on data */ auto extBackup = std::make_shared(); - auto extension = std::make_shared(extBackup); + auto extension = std::make_shared(extBackup, ""); OHOS::OnRemoteRequestFuzzTest(extension, data, size); OHOS::InitFuzzTest(extBackup, data, size); diff --git a/test/fuzztest/backupservicestub_fuzzer/backupservicestub_fuzzer.cpp b/test/fuzztest/backupservicestub_fuzzer/backupservicestub_fuzzer.cpp index 854692d2cacdcf8b82c861016d8d9f75590ced0c..b3c714e657930d70deb33921cba61a1f83e6e395 100644 --- a/test/fuzztest/backupservicestub_fuzzer/backupservicestub_fuzzer.cpp +++ b/test/fuzztest/backupservicestub_fuzzer/backupservicestub_fuzzer.cpp @@ -574,9 +574,9 @@ bool CmdUpdateTimerFuzzTest(sptr service, const uint8_t *data, size_t s try { int pos = 0; - int32_t timeOut = TypeCast(data, &pos); + int32_t timeout = TypeCast(data, &pos); msg.WriteString(string(reinterpret_cast(data + pos), size - pos)); - msg.WriteInt32(timeOut); + msg.WriteInt32(timeout); service->CmdUpdateTimer(msg, reply); } catch (OHOS::FileManagement::Backup::BError &err) { // Only filter BError errors, Other results are not expected. diff --git a/test/unittest/file_share_native/file_share_test.cpp b/test/unittest/file_share_native/file_share_test.cpp index dea3a408a889cb8fa84c0f756442c9f605cc9ea4..2cd55d06f1b89b62f0aeac7ebe47076cce8be7ad 100644 --- a/test/unittest/file_share_native/file_share_test.cpp +++ b/test/unittest/file_share_native/file_share_test.cpp @@ -25,7 +25,6 @@ #include "access_token_error.h" #include "accesstoken_kit.h" -#include "file_permission.h" #include "file_share.h" #include "ipc_skeleton.h" #include "log.h" diff --git a/test/unittest/file_uri_ndk_test/file_uri_ndk_test.cpp b/test/unittest/file_uri_ndk_test/file_uri_ndk_test.cpp index 307dfb9f7127aea1c8c1c382686238355bd29106..d34f45de82877f48d6d839a23e158989317aa5f1 100644 --- a/test/unittest/file_uri_ndk_test/file_uri_ndk_test.cpp +++ b/test/unittest/file_uri_ndk_test/file_uri_ndk_test.cpp @@ -319,4 +319,91 @@ HWTEST_F(NDKFileUriTest, is_valid_uri_test_002, TestSize.Level1) GTEST_LOG_(INFO) << "is_valid_uri_test_002"; } +/** + * @tc.number: get_filename_test_001 + * @tc.name: Test function of OH_FileUri_GetFileName() interface for unknown path + * @tc.desc: Set uri and get filename + * @tc.type: FUNC + */ +HWTEST_F(NDKFileUriTest, get_fileUri_filename_test_001, TestSize.Level1) +{ + GTEST_LOG_(INFO) << "get_fileUri_filename_test_001 start"; + const char fileUri[] = "file://docs/storage/Users/currentUser/Documents/GetFullDirectoryUri001.txt"; + const char resultUri[] = "GetFullDirectoryUri001.txt"; + char *result = nullptr; + unsigned int length = strlen(fileUri); + FileManagement_ErrCode ret = OH_FileUri_GetFileName(fileUri, length, &result); + EXPECT_EQ(ret, ERR_OK); + if (result != nullptr) { + GTEST_LOG_(INFO) << result; + EXPECT_EQ(strcmp(result, resultUri), 0); + } + FreeResult(&result); + GTEST_LOG_(INFO) << "get_fileUri_filename_test_001 end"; +} + +/** + * @tc.number: get_filename_test_002 + * @tc.name: Test function of OH_FileUri_GetFileName() interface for unknown path + * @tc.desc: Set uri and get filename + * @tc.type: FUNC + */ +HWTEST_F(NDKFileUriTest, get_fileUri_filename_test_002, TestSize.Level1) +{ + GTEST_LOG_(INFO) << "get_fileUri_filename_test_002 start"; + const char fileUri[] = "file://docs/storage/Users/currentUser/Documents/dirName"; + const char resultUri[] = "dirName"; + char *result = nullptr; + unsigned int length = strlen(fileUri); + FileManagement_ErrCode ret = OH_FileUri_GetFileName(fileUri, length, &result); + EXPECT_EQ(ret, ERR_OK); + if (result != nullptr) { + GTEST_LOG_(INFO) << result; + EXPECT_EQ(strcmp(result, resultUri), 0); + } + FreeResult(&result); + GTEST_LOG_(INFO) << "get_fileUri_filename_test_002 end"; +} + +/** + * @tc.number: get_filename_test_003 + * @tc.name: Test function of OH_FileUri_GetFileName() interface for unknown path + * @tc.desc: Set uri and get filename + * @tc.type: FUNC + */ +HWTEST_F(NDKFileUriTest, get_fileUri_filename_test_003, TestSize.Level1) +{ + GTEST_LOG_(INFO) << "get_fileUri_filename_test_003 start"; + const char fileUri[] = "file://com.example.filesharea/data/test/file_uri_test.txt"; + char *result = nullptr; + unsigned int length = strlen(fileUri); + FileManagement_ErrCode ret = OH_FileUri_GetFileName(nullptr, length, &result); + EXPECT_EQ(ret, ERR_PARAMS); + + ret = OH_FileUri_GetFileName(fileUri, length - 1, &result); + EXPECT_EQ(ret, ERR_PARAMS); + + ret = OH_FileUri_GetFileName(fileUri, length, nullptr); + EXPECT_EQ(ret, ERR_PARAMS); + FreeResult(&result); + GTEST_LOG_(INFO) << "get_fileUri_filename_test_003 end"; +} + +/** + * @tc.number: get_filename_test_004 + * @tc.name: Test function of OH_FileUri_GetFileName() interface for unknown path + * @tc.desc: Set uri and get filename + * @tc.type: FUNC + */ +HWTEST_F(NDKFileUriTest, get_fileUri_filename_test_004, TestSize.Level1) +{ + GTEST_LOG_(INFO) << "get_fileUri_filename_test_004 start"; + const char fileUri[] = "file://docs/storage/Users/currentUser/Documents/dirName/"; + char *result = nullptr; + unsigned int length = strlen(fileUri); + FileManagement_ErrCode ret = OH_FileUri_GetFileName(fileUri, length, &result); + EXPECT_EQ(ret, ERR_PARAMS); + GTEST_LOG_(INFO) << "get_fileUri_filename_test_004 end"; +} + } // namespace OHOS::AppFileService::ModuleFileUri \ No newline at end of file diff --git a/tests/mock/accesstoken/accesstoken_kit_mock.cpp b/tests/mock/accesstoken/accesstoken_kit_mock.cpp index 1531837704a37124fc2d4f1f7bb08ae806b07081..f2c5795cc147ff1ce70e97cd0ba0b5561a790999 100644 --- a/tests/mock/accesstoken/accesstoken_kit_mock.cpp +++ b/tests/mock/accesstoken/accesstoken_kit_mock.cpp @@ -14,6 +14,7 @@ */ #include "accesstoken_kit.h" +#include "tokenid_kit.h" namespace OHOS::Security::AccessToken { ATokenTypeEnum AccessTokenKit::GetTokenType(AccessTokenID tokenID) @@ -31,4 +32,9 @@ int AccessTokenKit::VerifyAccessToken(AccessTokenID tokenID, const std::string & { return 0; } + +bool TokenIdKit::IsSystemAppByFullTokenID(uint64_t tokenId) +{ + return true; +} } // namespace OHOS::Security::AccessToken diff --git a/tests/mock/backup_ext/include/ext_backup_mock.h b/tests/mock/backup_ext/include/ext_backup_mock.h index 1ef89adfe95ac3212e63660902a568f9ba722e15..76826057ba1cb173b13d8003330277e47cf5959b 100644 --- a/tests/mock/backup_ext/include/ext_backup_mock.h +++ b/tests/mock/backup_ext/include/ext_backup_mock.h @@ -51,6 +51,7 @@ public: virtual BConstants::ExtensionAction VerifyAndGetAction(const AAFwk::Want &, std::shared_ptr) = 0; virtual ErrCode GetParament(const AAFwk::Want &) = 0; + virtual ErrCode OnProcess(std::function callback) = 0; public: virtual std::unique_ptr LoadSystemModuleByEngine(napi_env, const std::string&, const napi_value*, size_t) = 0; @@ -86,6 +87,7 @@ public: std::function)); MOCK_METHOD(ErrCode, OnRestore, (std::function)); MOCK_METHOD(ErrCode, GetBackupInfo, (std::function)); + MOCK_METHOD(ErrCode, OnProcess, (std::function)); MOCK_METHOD(bool, WasFromSpecialVersion, ()); MOCK_METHOD(bool, SpecialVersionForCloneAndCloud, ()); MOCK_METHOD(bool, RestoreDataReady, ()); diff --git a/tests/mock/backup_ext/src/ext_backup_mock.cpp b/tests/mock/backup_ext/src/ext_backup_mock.cpp index 457d01de6da96a0d05717a47936c62931de0b116..16d6f55b5f87d21699d7fc81342b68ce95755ff5 100644 --- a/tests/mock/backup_ext/src/ext_backup_mock.cpp +++ b/tests/mock/backup_ext/src/ext_backup_mock.cpp @@ -133,4 +133,9 @@ ErrCode ExtBackup::InvokeAppExtMethod(ErrCode errCode, const std::string result) { return BExtBackup::extBackup->InvokeAppExtMethod(errCode, result); } + +ErrCode ExtBackup::OnProcess(function callback) +{ + return BExtBackup::extBackup->OnProcess(callback); +} } // namespace OHOS::FileManagement::Backup diff --git a/tests/mock/backup_kit_inner/b_session_restore_async_mock.cpp b/tests/mock/backup_kit_inner/b_session_restore_async_mock.cpp index dd71f134c5a737fb93400b6073b8aa5b7b292854..9e680cd346eea84a7c7045bf1e2af753ae7ca7a8 100644 --- a/tests/mock/backup_kit_inner/b_session_restore_async_mock.cpp +++ b/tests/mock/backup_kit_inner/b_session_restore_async_mock.cpp @@ -80,7 +80,6 @@ ErrCode BSessionRestoreAsync::AppendBundles(UniqueFd remoteCap, vector &bundleNames, - const vector &detailInfos, RestoreTypeEnum restoreType, int32_t userId) +ErrCode ServiceProxy::AppendBundlesRestoreSession(UniqueFd fd, + const vector &bundleNames, + RestoreTypeEnum restoreType, + int32_t userId) { return BError(BError::Codes::OK); } ErrCode ServiceProxy::AppendBundlesRestoreSession(UniqueFd fd, const vector &bundleNames, + const vector &detailInfos, RestoreTypeEnum restoreType, int32_t userId) { @@ -177,7 +180,16 @@ ErrCode ServiceProxy::GetBackupInfo(std::string &bundleName, std::string &result return BError(BError::Codes::OK); } -ErrCode ServiceProxy::UpdateTimer(BundleName &bundleName, uint32_t timeOut, bool &result) +ErrCode ServiceProxy::UpdateTimer(BundleName &bundleName, uint32_t timeout, bool &result) +{ + return BError(BError::Codes::OK); +} + +ErrCode ServiceProxy::StartExtTimer(bool &isExtStart) +{ + return BError(BError::Codes::OK); +} +ErrCode ServiceProxy::StartFwkTimer(bool &isFwkStart) { return BError(BError::Codes::OK); } @@ -187,6 +199,16 @@ ErrCode ServiceProxy::UpdateSendRate(std::string &bundleName, int32_t sendRate, return BError(BError::Codes::OK); } +ErrCode ServiceProxy::ReportAppProcessInfo(const std::string processInfo, const BackupRestoreScenario sennario) +{ + return BError(BError::Codes::OK); +} + +sptr ServiceProxy::GetServiceProxyPointer() +{ + return serviceProxy_; +} + sptr ServiceProxy::GetInstance() { if (!GetMockGetInstance()) { diff --git a/tests/mock/cJson/include/cJsonMock.h b/tests/mock/cJson/include/cJsonMock.h index 6d47050cd8f046f0a327eae5b9be8bfc7719545b..5f39b5bf1a5b73641166f35579485123cf72f5b6 100644 --- a/tests/mock/cJson/include/cJsonMock.h +++ b/tests/mock/cJson/include/cJsonMock.h @@ -33,8 +33,11 @@ public: virtual void cJSON_Delete(cJSON *item) = 0; virtual cJSON_bool cJSON_AddItemToObject(cJSON *object, const char *string, cJSON *item) = 0; virtual int cJSON_GetArraySize(const cJSON *array) = 0; - virtual cJSON_bool cJSON_AddItemToArray(cJSON *array, cJSON *item); - virtual cJSON *cJSON_AddStringToObject(cJSON *const object, const char *const name, const char *const string); + virtual cJSON* cJSON_GetArrayItem(const cJSON* array, int index) = 0; + virtual void cJSON_free(void* object) = 0; + virtual cJSON_bool cJSON_AddItemToArray(cJSON *array, cJSON *item) = 0; + virtual cJSON *cJSON_AddStringToObject(cJSON *const object, const char *const name, const char *const string) = 0; + virtual cJSON_bool cJSON_IsArray(const cJSON * const item) = 0; public: static inline std::shared_ptr cJsonPtr = nullptr; @@ -50,9 +53,12 @@ public: MOCK_METHOD1(cJSON_Parse, cJSON *(const char *value)); MOCK_METHOD2(cJSON_GetObjectItem, cJSON *(const cJSON *const object, const char *const string)); MOCK_METHOD1(cJSON_GetArraySize, int(const cJSON *array)); + MOCK_METHOD2(cJSON_GetArrayItem, cJSON *(const cJSON* array, int index)); MOCK_METHOD2(cJSON_AddItemToArray, cJSON_bool(cJSON *array, cJSON *item)); MOCK_METHOD3(cJSON_AddStringToObject, cJSON *(cJSON *const object, const char *const name, const char *const string)); + MOCK_METHOD1(cJSON_free, void(void* object)); + MOCK_METHOD1(cJSON_IsArray, cJSON_bool(const cJSON * const item)); }; } // namespace OHOS::FileManagement::Backup #endif \ No newline at end of file diff --git a/tests/mock/cJson/src/cJsonMock.cpp b/tests/mock/cJson/src/cJsonMock.cpp index 8aa2427dd9bb1a7b0be9618bc5f35dbd5c78662e..04e1985b634fc36f0739436d04fa96eee39364a4 100644 --- a/tests/mock/cJson/src/cJsonMock.cpp +++ b/tests/mock/cJson/src/cJsonMock.cpp @@ -18,6 +18,82 @@ using namespace OHOS::FileManagement::Backup; +static int CaseInsensitiveStrcmp(const unsigned char *string1, const unsigned char *string2) +{ + if ((string1 == NULL) || (string2 == NULL)) { + return 1; + } + + if (string1 == string2) { + return 0; + } + + for (; tolower(*string1) == tolower(*string2); (void)string1++, string2++) { + if (*string1 == '\0') { + return 0; + } + } + + return tolower(*string1) - tolower(*string2); +} + +static cJSON *GetObjectItem(const cJSON * const object, const char * const name, const cJSON_bool caseSensitive) +{ + cJSON *current_element = NULL; + + if ((object == NULL) || (name == NULL)) { + return NULL; + } + + current_element = object->child; + if (caseSensitive) { + while ((current_element != NULL) && (current_element->string != NULL) && + (strcmp(name, current_element->string) != 0)) { + current_element = current_element->next; + } + } else { + while ((current_element != NULL) && + (CaseInsensitiveStrcmp((const unsigned char*)name, (const unsigned char*)(current_element->string)) != 0)) { + current_element = current_element->next; + } + } + + if ((current_element == NULL) || (current_element->string == NULL)) { + return NULL; + } + + return current_element; +} + +CJSON_PUBLIC(void) CJSONDelete(cJSON *item) +{ + cJSON *next = NULL; + while (item != NULL) + { + next = item->next; + if (!(item->type & cJSON_IsReference) && (item->child != NULL)) + { + CJSONDelete(item->child); + } + if (!(item->type & cJSON_IsReference) && (item->valuestring != NULL)) + { + free(item->valuestring); + item->valuestring = NULL; + } + if (!(item->type & cJSON_StringIsConst) && (item->string != NULL)) + { + free(item->string); + item->string = NULL; + } + if (next == item) + { + break; + } + free(item); + item = next; + } +} + CJSON_PUBLIC(cJSON *) cJSON_CreateArray(void) { return CJson::cJsonPtr->cJSON_CreateArray(); @@ -35,17 +111,18 @@ CJSON_PUBLIC(char *) cJSON_Print(const cJSON *item) CJSON_PUBLIC(cJSON *) cJSON_Parse(const char *value) { - return CJson::cJsonPtr->cJSON_Parse(value); + return (CJson::cJsonPtr == nullptr) ? cJSON_ParseWithOpts(value, 0, 0) : CJson::cJsonPtr->cJSON_Parse(value); } CJSON_PUBLIC(cJSON *) cJSON_GetObjectItem(const cJSON *const object, const char *const string) { - return CJson::cJsonPtr->cJSON_GetObjectItem(object, string); + return (CJson::cJsonPtr == nullptr) ? GetObjectItem(object, string, false) : + CJson::cJsonPtr->cJSON_GetObjectItem(object, string); } CJSON_PUBLIC(void) cJSON_Delete(cJSON *item) { - return CJson::cJsonPtr->cJSON_Delete(item); + return (CJson::cJsonPtr == nullptr) ? CJSONDelete(item) : CJson::cJsonPtr->cJSON_Delete(item); } CJSON_PUBLIC(cJSON_bool) cJSON_AddItemToObject(cJSON *object, const char *string, cJSON *item) @@ -66,4 +143,23 @@ CJSON_PUBLIC(cJSON_bool) cJSON_AddItemToArray(cJSON *array, cJSON *item) CJSON_PUBLIC(cJSON*) cJSON_AddStringToObject(cJSON * const object, const char * const name, const char * const string) { return CJson::cJsonPtr->cJSON_AddStringToObject(object, name, string); +} + +static CJSON_PUBLIC(cJSON_bool) IsArray(const cJSON * const item) +{ + if (item == NULL) { + return false; + } + + return (item->type & 0xFF) == cJSON_Array; +} + +CJSON_PUBLIC(cJSON_bool) cJSON_IsArray(const cJSON * const item) +{ + return (CJson::cJsonPtr == nullptr) ? IsArray(item) : CJson::cJsonPtr->cJSON_IsArray(item); +} + +CJSON_PUBLIC(void) cJSON_free(void *object) +{ + return (CJson::cJsonPtr == nullptr) ? free(object) : CJson::cJsonPtr->cJSON_free(object); } \ No newline at end of file diff --git a/tests/mock/file_permission_native_mock/include/file_permission_mock.h b/tests/mock/file_permission_native_mock/include/file_permission_mock.h new file mode 100644 index 0000000000000000000000000000000000000000..19942181585f0a66f16005f1d8c938068170715b --- /dev/null +++ b/tests/mock/file_permission_native_mock/include/file_permission_mock.h @@ -0,0 +1,55 @@ +/* + * Copyright (c) 2024 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef FILEMANAGEMENT_FILE_PERMISSION_MOCK_MOCK_H +#define FILEMANAGEMENT_FILE_PERMISSION_MOCK_MOCK_H +#include + +#include "file_permission.h" +namespace OHOS { +namespace AppFileService { +class IFilePermissionMock { +public: + virtual ~IFilePermissionMock() = default; + virtual int32_t PersistPermission(const vector &uriPolicies, + deque &errorResults) = 0; + virtual int32_t RevokePermission(const vector &uriPolicies, + deque &errorResults) = 0; + virtual int32_t ActivatePermission(const vector &uriPolicies, + deque &errorResults) = 0; + virtual int32_t DeactivatePermission(const vector &uriPolicies, + deque &errorResults) = 0; + virtual int32_t CheckPersistentPermission(const vector &uriPolicies, + vector &errorResults) = 0; +public: + static inline std::shared_ptr filePermissionMock = nullptr; +}; + +class FilePermissionMock : public IFilePermissionMock { +public: + MOCK_METHOD2(PersistPermission, + int32_t(const vector &uriPolicies, deque &errorResults)); + MOCK_METHOD2(RevokePermission, int32_t(const vector &uriPolicies, + deque &errorResults)); + MOCK_METHOD2(ActivatePermission, int32_t(const vector &uriPolicies, + deque &errorResults)); + MOCK_METHOD2(DeactivatePermission, int32_t(const vector &uriPolicies, + deque &errorResults)); + MOCK_METHOD2(CheckPersistentPermission, int32_t(const vector &uriPolicies, + vector &errorResults)); +}; +} +} +#endif diff --git a/tests/mock/file_permission_native_mock/src/file_permission_mock.cpp b/tests/mock/file_permission_native_mock/src/file_permission_mock.cpp new file mode 100644 index 0000000000000000000000000000000000000000..f46fb424383137acf99e3c50dc3d8a0c60cf4b7d --- /dev/null +++ b/tests/mock/file_permission_native_mock/src/file_permission_mock.cpp @@ -0,0 +1,65 @@ +/* + * Copyright (c) 2024 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +#include "file_permission_mock.h" + +namespace OHOS { +using namespace AppFileService; +int32_t FilePermission::PersistPermission(const vector &uriPolicies, + deque &errorResults) +{ + if (IFilePermissionMock::filePermissionMock == nullptr) { + return 0; + } + + return IFilePermissionMock::filePermissionMock->PersistPermission(uriPolicies, errorResults); +} + +int32_t FilePermission::RevokePermission(const vector &uriPolicies, + deque &errorResults) +{ + if (IFilePermissionMock::filePermissionMock == nullptr) { + return 0; + } + + return IFilePermissionMock::filePermissionMock->RevokePermission(uriPolicies, errorResults); +} + +int32_t FilePermission::ActivatePermission(const vector &uriPolicies, + deque &errorResults) +{ + if (IFilePermissionMock::filePermissionMock == nullptr) { + return 0; + } + + return IFilePermissionMock::filePermissionMock->ActivatePermission(uriPolicies, errorResults); +} +int32_t FilePermission::DeactivatePermission(const vector &uriPolicies, + deque &errorResults) +{ + if (IFilePermissionMock::filePermissionMock == nullptr) { + return 0; + } + + return IFilePermissionMock::filePermissionMock->DeactivatePermission(uriPolicies, errorResults); +} +int32_t FilePermission::CheckPersistentPermission(const vector &uriPolicies, vector &errorResults) +{ + if (IFilePermissionMock::filePermissionMock == nullptr) { + return 0; + } + + return IFilePermissionMock::filePermissionMock->CheckPersistentPermission(uriPolicies, errorResults); +} +} \ No newline at end of file diff --git a/tests/mock/library_func_mock/library_func_mock.cpp b/tests/mock/library_func_mock/library_func_mock.cpp new file mode 100644 index 0000000000000000000000000000000000000000..5ff83cc4637f9d0047eda7d092856f2cba7c3c50 --- /dev/null +++ b/tests/mock/library_func_mock/library_func_mock.cpp @@ -0,0 +1,49 @@ +/* +* Copyright (c) 2024 Huawei Device Co., Ltd. +* Licensed under the Apache License, Version 2.0 (the "License"); +* you may not use this file except in compliance with the License. +* You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. + */ + +#include "library_func_mock.h" + +using namespace OHOS::AppFileService; +int fseeko(FILE *stream, off_t offset, int whence) +{ + if (LibraryFunc::libraryFunc_ == nullptr) { + return -1; + } + return LibraryFunc::libraryFunc_->fseeko(stream, offset, whence); +} + +off_t ftello(FILE *stream) +{ + if (LibraryFunc::libraryFunc_ == nullptr) { + return -1; + } + return LibraryFunc::libraryFunc_->ftello(stream); +} + +int access(const char *pathname, int mode) +{ + if (LibraryFunc::libraryFunc_ == nullptr) { + return -1; + } + return LibraryFunc::libraryFunc_->access(pathname, mode); +} + +int mkdir(const char *pathname, mode_t mode) +{ + if (LibraryFunc::libraryFunc_ == nullptr) { + return -1; + } + return LibraryFunc::libraryFunc_->mkdir(pathname, mode); +} \ No newline at end of file diff --git a/tests/mock/library_func_mock/library_func_mock.h b/tests/mock/library_func_mock/library_func_mock.h new file mode 100644 index 0000000000000000000000000000000000000000..a6cc5a1e2f2e4d552dab537a2980c43e639a7fd8 --- /dev/null +++ b/tests/mock/library_func_mock/library_func_mock.h @@ -0,0 +1,50 @@ +/* +* Copyright (c) 2024 Huawei Device Co., Ltd. +* Licensed under the Apache License, Version 2.0 (the "License"); +* you may not use this file except in compliance with the License. +* You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + +#ifndef FILEMANAGEMENT_APP_FILE_SERVICE_LIBRARY_FUNC_MOCK_H +#define FILEMANAGEMENT_APP_FILE_SERVICE_LIBRARY_FUNC_MOCK_H + +#include + +#include +#include +#include +#include +#include + +namespace OHOS { +namespace AppFileService { +class LibraryFunc { +public: + virtual ~LibraryFunc() = default; + virtual int fseeko(FILE *stream, off_t offset, int whence) = 0; + virtual off_t ftello(FILE *stream) = 0; + virtual int access(const char *pathname, int mode) = 0; + virtual int mkdir(const char *pathname, mode_t mode) = 0; +public: + static inline std::shared_ptr libraryFunc_ = nullptr; +}; + +class LibraryFuncMock : public LibraryFunc { +public: + MOCK_METHOD3(fseeko, int(FILE *stream, off_t offset, int whence)); + MOCK_METHOD1(ftello, off_t(FILE *stream)); + MOCK_METHOD2(access, int(const char *pathname, int mode)); + MOCK_METHOD2(mkdir, int(const char *pathname, mode_t mode)); +}; +} // namespace AppFileService +} // namespace OHOS + +#endif // FILEMANAGEMENT_APP_FILE_SERVICE_LIBRARY_FUNC_MOCK_H diff --git a/tests/mock/module_external/bms_adapter_mock.cpp b/tests/mock/module_external/bms_adapter_mock.cpp index cef59d5f1921af0494ce638b98d1fe311cb02154..08ca46bf806fe8f43a2d7d85b8b5f3e224c9a1e2 100644 --- a/tests/mock/module_external/bms_adapter_mock.cpp +++ b/tests/mock/module_external/bms_adapter_mock.cpp @@ -32,7 +32,8 @@ vector BundleMgrAdapter::GetBundleInfos(const vecto { vector bundleInfos; bundleInfos.emplace_back( - BJsonEntityCaps::BundleInfo {"com.example.app2backup", {}, {}, 0, 0, true, false, "com.example.app2backup"}); + BJsonEntityCaps::BundleInfo {"com.example.app2backup", 0, 0, "", 0, 0, true, false, + "", "", "", ""}); return bundleInfos; } @@ -46,7 +47,8 @@ vector BundleMgrAdapter::GetBundleInfosForIncrement { vector bundleInfos; bundleInfos.emplace_back( - BJsonEntityCaps::BundleInfo {"com.example.app2backup", {}, {}, 0, 0, true, false, "com.example.app2backup"}); + BJsonEntityCaps::BundleInfo {"com.example.app2backup", 0, 0, "", 0, 0, true, false, + "", "", "", ""}); return bundleInfos; } @@ -55,7 +57,18 @@ vector BundleMgrAdapter::GetBundleInfosForIncrement { vector bundleInfos; bundleInfos.emplace_back( - BJsonEntityCaps::BundleInfo {"com.example.app2backup", {}, {}, 0, 0, true, false, "com.example.app2backup"}); + BJsonEntityCaps::BundleInfo {"com.example.app2backup", 0, 0, "", 0, 0, true, false, + "", "", "", ""}); + return bundleInfos; +} + + +vector BundleMgrAdapter::GetFullBundleInfos(int32_t userId) +{ + vector bundleInfos; + bundleInfos.emplace_back( + BJsonEntityCaps::BundleInfo {"com.example.app2backup", 0, 0, "", 0, 0, true, false, + "", "", "", ""}); return bundleInfos; } @@ -63,4 +76,19 @@ string BundleMgrAdapter::GetExtName(string bundleName, int32_t userId) { return "BackupExtensionAbility"; } + +bool BundleMgrAdapter::IsUser0BundleName(std::string bundleName, int32_t userId) +{ + return true; +} + +vector BundleMgrAdapter::GetBundleInfosForAppend( + const vector &incrementalDataList, int32_t userId) +{ + vector bundleInfos; + bundleInfos.emplace_back( + BJsonEntityCaps::BundleInfo {"com.example.app2backup", 0, 0, "", 0, 0, true, false, + "", "", "", ""}); + return bundleInfos; +} } // namespace OHOS::FileManagement::Backup diff --git a/tests/mock/module_ipc/service_mock.cpp b/tests/mock/module_ipc/service_mock.cpp index c058c5e8365192df93ca1661178718dc278033a4..4d81c6bf820990c971d0e9e3c8bd360db1c79e38 100644 --- a/tests/mock/module_ipc/service_mock.cpp +++ b/tests/mock/module_ipc/service_mock.cpp @@ -123,7 +123,7 @@ ErrCode Service::GetFileHandle(const string &bundleName, const string &fileName) return BError(BError::Codes::OK); } -void Service::OnBackupExtensionDied(const string &&bundleName) {} +void Service::OnBackupExtensionDied(const string &&bundleName, bool isSecondCalled) {} void Service::ExtConnectDied(const string &callName) {} @@ -216,7 +216,17 @@ ErrCode Service::GetBackupInfo(BundleName &bundleName, std::string &result) return BError(BError::Codes::OK); } -ErrCode Service::UpdateTimer(BundleName &bundleName, uint32_t timeOut, bool &result) +ErrCode Service::StartExtTimer(bool &isExtStart) +{ + return BError(BError::Codes::OK); +} + +ErrCode Service::StartFwkTimer(bool &isFwkStart) +{ + return BError(BError::Codes::OK); +} + +ErrCode Service::UpdateTimer(BundleName &bundleName, uint32_t timeout, bool &result) { return BError(BError::Codes::OK); } @@ -226,6 +236,11 @@ ErrCode Service::UpdateSendRate(std::string &bundleName, int32_t sendRate, bool return BError(BError::Codes::OK); } +ErrCode Service::ReportAppProcessInfo(const std::string processInfo, const BackupRestoreScenario sennario) +{ + return BError(BError::Codes::OK); +} + void Service::OnSABackup(const std::string &bundleName, const int &fd, const std::string &result, @@ -234,4 +249,55 @@ void Service::OnSABackup(const std::string &bundleName, } void Service::OnSARestore(const std::string &bundleName, const std::string &result, const ErrCode &errCode) {} + +ErrCode Service::ClearResidualBundleData(const std::string &bundleName) +{ + return BError(BError::Codes::OK); +} + +std::shared_ptr Service::GetExtensionMutex(const BundleName &bundleName) +{ + return nullptr; +} + +void Service::RemoveExtensionMutex(const BundleName &bundleName) +{ +} + +void Service::CreateDirIfNotExist(const std::string &path) +{ +} + +void Service::OnBundleStarted(BError error, sptr session, const BundleName &bundleName) {} + +void Service::HandleExceptionOnAppendBundles(sptr session, + const vector &appendBundleNames, const vector &restoreBundleNames) {} + +void Service::BundleBeginRadarReport(const std::string &bundleName, const ErrCode errCode, + const IServiceReverse::Scenario scenario) {} + +void Service::BundleEndRadarReport(const std::string &bundleName, const ErrCode errCode, + const IServiceReverse::Scenario scenario) {} + +void Service::FileReadyRadarReport(const std::string &bundleName, const std::string &fileName, const ErrCode errCode, + const IServiceReverse::Scenario scenario) {} + +void Service::ExtensionConnectFailRadarReport(const std::string &bundleName, const ErrCode errCode, + const IServiceReverse::Scenario scenario) {} + +void Service::UpdateFailedBundles(const std::string &bundleName, BundleTaskInfo taskInfo) {} + +void Service::ClearFailedBundles() {} + +std::vector Service::GetSupportBackupBundleNames(vector&, bool, + const vector&) +{ + return {}; +} + +void Service::StartRunningTimer(const std::string &bundleName) {} + +void Service::HandleNotSupportBundleNames(const vector&, vector&, bool) {} + +void Service::SetBundleIncDataInfo(const std::vector&, std::vector&) {} } // namespace OHOS::FileManagement::Backup diff --git a/tests/mock/module_ipc/service_reverse_proxy_mock.cpp b/tests/mock/module_ipc/service_reverse_proxy_mock.cpp index 1d7b598d4ce821942ecae41db23bb2ea2126d414..1b224076d31f04363b8035c384aa14f4a4214132 100644 --- a/tests/mock/module_ipc/service_reverse_proxy_mock.cpp +++ b/tests/mock/module_ipc/service_reverse_proxy_mock.cpp @@ -30,6 +30,8 @@ void ServiceReverseProxy::BackupOnBundleFinished(int32_t errCode, string bundleN void ServiceReverseProxy::BackupOnAllBundlesFinished(int32_t errCode) {} +void ServiceReverseProxy::BackupOnProcessInfo(std::string bundleName, std::string processInfo) {} + void ServiceReverseProxy::RestoreOnBundleStarted(int32_t errCode, string bundleName) {} void ServiceReverseProxy::RestoreOnBundleFinished(int32_t errCode, string bundleName) {} @@ -40,6 +42,8 @@ void ServiceReverseProxy::RestoreOnFileReady(string bundleName, string fileName, void ServiceReverseProxy::RestoreOnResultReport(string result, string bundleName, ErrCode errCode) {} +void ServiceReverseProxy::RestoreOnProcessInfo(std::string bundleName, std::string processInfo) {} + void ServiceReverseProxy::IncrementalBackupOnFileReady(string bundleName, string fileName, int fd, int manifestFd, int32_t errCode) {} @@ -51,6 +55,8 @@ void ServiceReverseProxy::IncrementalBackupOnBundleFinished(int32_t errCode, str void ServiceReverseProxy::IncrementalBackupOnAllBundlesFinished(int32_t errCode) {} +void ServiceReverseProxy::IncrementalBackupOnProcessInfo(std::string bundleName, std::string processInfo) {} + void ServiceReverseProxy::IncrementalRestoreOnBundleStarted(int32_t errCode, string bundleName) {} void ServiceReverseProxy::IncrementalRestoreOnBundleFinished(int32_t errCode, string bundleName) {} @@ -61,4 +67,6 @@ void ServiceReverseProxy::IncrementalRestoreOnFileReady(string bundleName, strin int32_t errCode) {} void ServiceReverseProxy::IncrementalRestoreOnResultReport(string result, string bundleName, ErrCode errCode) {} + +void ServiceReverseProxy::IncrementalRestoreOnProcessInfo(std::string bundleName, std::string processInfo) {} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/mock/module_ipc/service_stub_mock.cpp b/tests/mock/module_ipc/service_stub_mock.cpp index 9d4b055697a1c411c87b79d51e27bf7fbd47fd5d..07ae3a29230ab8d379044438aa57746c3d351ab1 100644 --- a/tests/mock/module_ipc/service_stub_mock.cpp +++ b/tests/mock/module_ipc/service_stub_mock.cpp @@ -40,15 +40,13 @@ ServiceStub::ServiceStub() opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_PUBLISH_FILE)] = &ServiceStub::CmdPublishFile; opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_APP_DONE)] = &ServiceStub::CmdAppDone; - opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_RESULT_REPORT)] = - &ServiceStub::CmdResultReport; opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_START)] = &ServiceStub::CmdStart; opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_GET_FILE_NAME)] = &ServiceStub::CmdGetFileHandle; opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_APPEND_BUNDLES_RESTORE_SESSION)] = &ServiceStub::CmdAppendBundlesRestoreSession; - opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_APPEND_BUNDLES_RESTORE_SESSION_DETAILS)] - = &ServiceStub::CmdAppendBundlesDetailsRestoreSession; + opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_APPEND_BUNDLES_RESTORE_SESSION_DETAIL)] = + &ServiceStub::CmdAppendBundlesDetailsRestoreSession; opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_APPEND_BUNDLES_BACKUP_SESSION)] = &ServiceStub::CmdAppendBundlesBackupSession; opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_GET_LOCAL_CAPABILITIES_INCREMENTAL)] = @@ -81,6 +79,8 @@ void ServiceStub::ServiceStubSupplement() &ServiceStub::CmdUpdateTimer; opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_UPDATE_SENDRATE)] = &ServiceStub::CmdUpdateSendRate; + opToInterfaceMap_[static_cast(IServiceInterfaceCode::SERVICE_CMD_REPORT_APP_PROCESS_INFO)] = + &ServiceStub::CmdReportAppProcessInfo; } int32_t ServiceStub::OnRemoteRequest(uint32_t code, MessageParcel &data, MessageParcel &reply, MessageOption &option) @@ -188,6 +188,7 @@ int32_t ServiceStub::CmdAppendBundlesRestoreSession(MessageParcel &data, Message UniqueFd fd(data.ReadFileDescriptor()); std::vector bundleNames; data.ReadStringVector(&bundleNames); + int res = AppendBundlesRestoreSession(move(fd), bundleNames); reply.WriteInt32(res); return BError(BError::Codes::OK); @@ -209,6 +210,7 @@ int32_t ServiceStub::CmdAppendBundlesBackupSession(MessageParcel &data, MessageP { std::vector bundleNames; data.ReadStringVector(&bundleNames); + int res = AppendBundlesBackupSession(bundleNames); reply.WriteInt32(res); return BError(BError::Codes::OK); @@ -240,12 +242,12 @@ int32_t ServiceStub::CmdUpdateTimer(MessageParcel &data, MessageParcel &reply) if (!data.ReadString(bundleName)) { return BError(BError::Codes::SA_BROKEN_IPC, string("Failed to recive bundleName")); } - uint32_t timeOut; - if (!data.ReadUint32(timeOut)) { - return BError(BError::Codes::SA_BROKEN_IPC, string("Failed to recive timeOut")); + uint32_t timeout; + if (!data.ReadUint32(timeout)) { + return BError(BError::Codes::SA_BROKEN_IPC, string("Failed to recive timeout")); } bool result; - ret = UpdateTimer(bundleName, timeOut, result); + ret = UpdateTimer(bundleName, timeout, result); return BError(BError::Codes::OK); } @@ -311,4 +313,9 @@ int32_t ServiceStub::CmdGetIncrementalFileHandle(MessageParcel &data, MessagePar { return BError(BError::Codes::OK); } + +int32_t ServiceStub::CmdReportAppProcessInfo(MessageParcel &data, MessageParcel &reply) +{ + return BError(BError::Codes::OK); +} } // namespace OHOS::FileManagement::Backup diff --git a/tests/mock/module_ipc/svc_backup_connection_mock.cpp b/tests/mock/module_ipc/svc_backup_connection_mock.cpp index 1d007fa7c4cb0baad931ed09c09b08a3a9a8d477..8e06902e2280daaf0dd9ed9e522f5d3cdba6bbc3 100644 --- a/tests/mock/module_ipc/svc_backup_connection_mock.cpp +++ b/tests/mock/module_ipc/svc_backup_connection_mock.cpp @@ -42,7 +42,7 @@ void SvcBackupConnection::OnAbilityDisconnectDone(const AppExecFwk::ElementName backupProxy_ = nullptr; isConnected_.store(false); string bundleName = ""; - callDied_(move(bundleName)); + callDied_(move(bundleName), false); } ErrCode SvcBackupConnection::ConnectBackupExtAbility(AAFwk::Want &want, int32_t userId) @@ -55,6 +55,11 @@ ErrCode SvcBackupConnection::DisconnectBackupExtAbility() return 0; } +bool SvcBackupConnection::WaitDisconnectDone() +{ + return true; +} + bool SvcBackupConnection::IsExtAbilityConnected() { bool bFlag = g_bExtAbilityConnected; @@ -67,7 +72,7 @@ void SvcBackupConnection::SetCallback(function callC callConnected_ = callConnected; } -void SvcBackupConnection::SetCallDied(function callDied) +void SvcBackupConnection::SetCallDied(function callDied) { callDied_ = callDied; } diff --git a/tests/mock/module_ipc/svc_extension_proxy_mock.cpp b/tests/mock/module_ipc/svc_extension_proxy_mock.cpp index bd20c461fc5470db4ea6772b7349e89a44991845..bb000e0900a90ffe5f8b665150286f646df861f2 100644 --- a/tests/mock/module_ipc/svc_extension_proxy_mock.cpp +++ b/tests/mock/module_ipc/svc_extension_proxy_mock.cpp @@ -28,7 +28,7 @@ ErrCode SvcExtensionProxy::HandleClear() return 0; } -ErrCode SvcExtensionProxy::HandleBackup() +ErrCode SvcExtensionProxy::HandleBackup(bool isClearData) { return 0; } @@ -38,7 +38,7 @@ ErrCode SvcExtensionProxy::PublishFile(const string &fileName) return 0; } -ErrCode SvcExtensionProxy::HandleRestore() +ErrCode SvcExtensionProxy::HandleRestore(bool isClearData) { return 0; } @@ -63,7 +63,7 @@ ErrCode SvcExtensionProxy::HandleIncrementalBackup(UniqueFd incrementalFd, Uniqu return 0; } -ErrCode SvcExtensionProxy::IncrementalOnBackup() +ErrCode SvcExtensionProxy::IncrementalOnBackup(bool isClearData) { return 0; } @@ -73,6 +73,11 @@ ErrCode SvcExtensionProxy::UpdateFdSendRate(std::string &bundleName, int32_t sen return 0; } +ErrCode SvcExtensionProxy::User0OnBackup() +{ + return 0; +} + tuple SvcExtensionProxy::GetIncrementalBackupFileHandle() { return {UniqueFd(-1), UniqueFd(-1)}; diff --git a/tests/mock/module_ipc/svc_session_manager_mock.cpp b/tests/mock/module_ipc/svc_session_manager_mock.cpp index 320bdd66cd0b298fe6873337d3f87cbc6899116f..ba5f6a5c68bee389077383c7c55de7641241815a 100644 --- a/tests/mock/module_ipc/svc_session_manager_mock.cpp +++ b/tests/mock/module_ipc/svc_session_manager_mock.cpp @@ -41,7 +41,7 @@ void SvcSessionManager::VerifyCallerAndScenario(uint32_t clientToken, IServiceRe GTEST_LOG_(INFO) << "VerifyCallerAndScenario"; } -ErrCode SvcSessionManager::Active(Impl newImpl) +ErrCode SvcSessionManager::Active(Impl newImpl, bool force) { GTEST_LOG_(INFO) << "Active"; extConnectNum_ = 0; @@ -102,9 +102,10 @@ wptr SvcSessionManager::GetExtConnection(const BundleName & return nullptr; } if (!it->second.backUpConnection) { - auto callDied = [](const string &&bundleName) {}; + auto callDied = [](const string &&bundleName, bool isSecondCalled = false) {}; auto callConnected = [](const string &&bundleName) {}; - it->second.backUpConnection = sptr(new SvcBackupConnection(callDied, callConnected)); + it->second.backUpConnection = sptr(new SvcBackupConnection(callDied, callConnected, + bundleName)); sptr mock = sptr(new BackupExtExtensionMock()); it->second.backUpConnection->OnAbilityConnectDone({}, mock->AsObject(), 0); } @@ -114,7 +115,7 @@ wptr SvcSessionManager::GetExtConnection(const BundleName & sptr SvcSessionManager::GetBackupAbilityExt(const string &bundleName) { GTEST_LOG_(INFO) << "GetBackupAbilityExt"; - return sptr(new SvcBackupConnection(nullptr, nullptr)); + return sptr(new SvcBackupConnection(nullptr, nullptr, bundleName)); } void SvcSessionManager::DumpInfo(const int fd, const std::vector &args) @@ -353,21 +354,35 @@ void SvcSessionManager::SetBundleDataSize(const std::string &bundleName, int64_t it->second.dataSize = dataSize; } -void SvcSessionManager::BundleExtTimerStart(const std::string &bundleName, const Utils::Timer::TimerCallback &callback) +bool SvcSessionManager::StartFwkTimer(const std::string &bundleName, const Utils::Timer::TimerCallback &callback) { + return true; } -bool SvcSessionManager::UpdateTimer(const std::string &bundleName, uint32_t timeOut, - const Utils::Timer::TimerCallback &callback) +bool SvcSessionManager::StopFwkTimer(const std::string &bundleName) { return true; } -void SvcSessionManager::BundleExtTimerStop(const std::string &bundleName) {} +bool SvcSessionManager::StartExtTimer(const std::string &bundleName, const Utils::Timer::TimerCallback &callback) +{ + return true; +} -void SvcSessionManager::IncreaseSessionCnt() {} +bool SvcSessionManager::StopExtTimer(const std::string &bundleName) +{ + return true; +} -void SvcSessionManager::DecreaseSessionCnt() {} +bool SvcSessionManager::UpdateTimer(const std::string &bundleName, uint32_t timeout, + const Utils::Timer::TimerCallback &callback) +{ + return true; +} + +void SvcSessionManager::IncreaseSessionCnt(const std::string funcName) {} + +void SvcSessionManager::DecreaseSessionCnt(const std::string funcName) {} int32_t SvcSessionManager::GetMemParaCurSize() { @@ -376,7 +391,10 @@ int32_t SvcSessionManager::GetMemParaCurSize() void SvcSessionManager::SetMemParaCurSize(int32_t size) {} -void SvcSessionManager::ClearSessionData() {} +ErrCode SvcSessionManager::ClearSessionData() +{ + return 0; +} bool SvcSessionManager::GetIsIncrementalBackup() { @@ -393,6 +411,18 @@ SvcSessionManager::Impl SvcSessionManager::GetImpl() return impl_; } +int SvcSessionManager::GetSessionCnt() +{ + return sessionCnt_.load(); +} + +void SvcSessionManager::SetClearDataFlag(const std::string &bundleName, bool isNotClear) {} + +bool SvcSessionManager::GetClearDataFlag(const std::string &bundleName) +{ + return true; +} + void SvcSessionManager::SetIncrementalData(const BIncrementalData &incrementalData) {} int32_t SvcSessionManager::GetIncrementalManifestFd(const string &bundleName) @@ -404,4 +434,15 @@ int64_t SvcSessionManager::GetLastIncrementalTime(const string &bundleName) { return 0; } + +bool SvcSessionManager::CleanAndCheckIfNeedWait(ErrCode &ret, std::vector &bundleNameList) +{ + return false; +} + +void SvcSessionManager::SetPublishFlag(const std::string &bundleName) {} + +void SvcSessionManager::SetImplRestoreType(const RestoreTypeEnum restoreType) {} + +void SvcSessionManager::SetIsReadyLaunch(const std::string &bundleName) {} } // namespace OHOS::FileManagement::Backup diff --git a/tests/mock/module_ipc/svc_session_manager_throw_mock.cpp b/tests/mock/module_ipc/svc_session_manager_throw_mock.cpp index 9ba4687b8fa3a87246f3cb89c89a259c7f5dab32..8a0b29390d8c1c10d91c8847f9ae5db9059b1ebf 100644 --- a/tests/mock/module_ipc/svc_session_manager_throw_mock.cpp +++ b/tests/mock/module_ipc/svc_session_manager_throw_mock.cpp @@ -24,7 +24,7 @@ void SvcSessionManager::VerifyCallerAndScenario(uint32_t clientToken, IServiceRe BackupSvcSessionManager::session->VerifyCallerAndScenario(clientToken, scenario); } -ErrCode SvcSessionManager::Active(Impl newImpl) +ErrCode SvcSessionManager::Active(Impl newImpl, bool force) { return BackupSvcSessionManager::session->Active(newImpl); } @@ -219,30 +219,40 @@ void SvcSessionManager::SetBundleDataSize(const std::string &bundleName, int64_t BackupSvcSessionManager::session->SetBundleDataSize(bundleName, dataSize); } -void SvcSessionManager::BundleExtTimerStart(const std::string &bundleName, const Utils::Timer::TimerCallback &callback) +bool SvcSessionManager::StartFwkTimer(const std::string &bundleName, const Utils::Timer::TimerCallback &callback) { - BackupSvcSessionManager::session->BundleExtTimerStart(bundleName, callback); + return BackupSvcSessionManager::session->StartFwkTimer(bundleName, callback); } -bool SvcSessionManager::UpdateTimer(const std::string &bundleName, uint32_t timeOut, - const Utils::Timer::TimerCallback &callback) +bool SvcSessionManager::StopFwkTimer(const std::string &bundleName) +{ + return BackupSvcSessionManager::session->StopFwkTimer(bundleName); +} + +bool SvcSessionManager::StartExtTimer(const std::string &bundleName, const Utils::Timer::TimerCallback &callback) +{ + return BackupSvcSessionManager::session->StartExtTimer(bundleName, callback); +} + +bool SvcSessionManager::StopExtTimer(const std::string &bundleName) { - return BackupSvcSessionManager::session->UpdateTimer(bundleName, timeOut, callback); + return BackupSvcSessionManager::session->StopExtTimer(bundleName); } -void SvcSessionManager::BundleExtTimerStop(const std::string &bundleName) +bool SvcSessionManager::UpdateTimer(const std::string &bundleName, uint32_t timeout, + const Utils::Timer::TimerCallback &callback) { - BackupSvcSessionManager::session->BundleExtTimerStop(bundleName); + return BackupSvcSessionManager::session->UpdateTimer(bundleName, timeout, callback); } -void SvcSessionManager::IncreaseSessionCnt() +void SvcSessionManager::IncreaseSessionCnt(const std::string funcName) { - BackupSvcSessionManager::session->IncreaseSessionCnt(); + BackupSvcSessionManager::session->IncreaseSessionCnt(funcName); } -void SvcSessionManager::DecreaseSessionCnt() +void SvcSessionManager::DecreaseSessionCnt(const std::string funcName) { - BackupSvcSessionManager::session->DecreaseSessionCnt(); + BackupSvcSessionManager::session->DecreaseSessionCnt(funcName); } int32_t SvcSessionManager::GetMemParaCurSize() @@ -255,9 +265,9 @@ void SvcSessionManager::SetMemParaCurSize(int32_t size) BackupSvcSessionManager::session->SetMemParaCurSize(size); } -void SvcSessionManager::ClearSessionData() +ErrCode SvcSessionManager::ClearSessionData() { - BackupSvcSessionManager::session->ClearSessionData(); + return BackupSvcSessionManager::session->ClearSessionData(); } bool SvcSessionManager::GetIsIncrementalBackup() @@ -275,6 +285,21 @@ SvcSessionManager::Impl SvcSessionManager::GetImpl() return BackupSvcSessionManager::session->GetImpl(); } +int SvcSessionManager::GetSessionCnt() +{ + return BackupSvcSessionManager::session->GetSessionCnt(); +} + +void SvcSessionManager::SetClearDataFlag(const std::string &bundleName, bool isNotClear) +{ + BackupSvcSessionManager::session->SetClearDataFlag(bundleName, isNotClear); +} + +bool SvcSessionManager::GetClearDataFlag(const std::string &bundleName) +{ + return BackupSvcSessionManager::session->GetClearDataFlag(bundleName); +} + void SvcSessionManager::SetIncrementalData(const BIncrementalData &incrementalData) { BackupSvcSessionManager::session->SetIncrementalData(incrementalData); @@ -289,4 +314,15 @@ int64_t SvcSessionManager::GetLastIncrementalTime(const string &bundleName) { return BackupSvcSessionManager::session->GetLastIncrementalTime(bundleName); } + +bool SvcSessionManager::CleanAndCheckIfNeedWait(ErrCode &ret, std::vector &bundleNameList) +{ + return false; +} + +void SvcSessionManager::SetPublishFlag(const std::string &bundleName) {} + +void SvcSessionManager::SetImplRestoreType(const RestoreTypeEnum restoreType) {} + +void SvcSessionManager::SetIsReadyLaunch(const std::string &bundleName) {} } // namespace OHOS::FileManagement::Backup diff --git a/tests/mock/module_ipc/svc_session_manager_throw_mock.h b/tests/mock/module_ipc/svc_session_manager_throw_mock.h index 670bef53b5a5f69288fc3c03c021f0c6e0b716a3..cb9904f7329a83785fa12f0decf9cf32b2871715 100644 --- a/tests/mock/module_ipc/svc_session_manager_throw_mock.h +++ b/tests/mock/module_ipc/svc_session_manager_throw_mock.h @@ -67,20 +67,29 @@ public: virtual void SetBundleVersionName(const std::string &, std::string) = 0; virtual std::string GetBundleVersionName(const std::string &) = 0; virtual void SetBundleDataSize(const std::string &, int64_t) = 0; - virtual void BundleExtTimerStart(const std::string &, const Utils::Timer::TimerCallback &) = 0; + virtual bool StartFwkTimer(const std::string &, const Utils::Timer::TimerCallback &) = 0; + virtual bool StopFwkTimer(const std::string &) = 0; + virtual bool StartExtTimer(const std::string &, const Utils::Timer::TimerCallback &) = 0; + virtual bool StopExtTimer(const std::string &) = 0; virtual bool UpdateTimer(const std::string &, uint32_t, const Utils::Timer::TimerCallback &) = 0; - virtual void BundleExtTimerStop(const std::string &) = 0; - virtual void IncreaseSessionCnt() = 0; - virtual void DecreaseSessionCnt() = 0; + virtual void IncreaseSessionCnt(const std::string) = 0; + virtual void DecreaseSessionCnt(const std::string) = 0; virtual int32_t GetMemParaCurSize() = 0; virtual void SetMemParaCurSize(int32_t) = 0; - virtual void ClearSessionData() = 0; + virtual ErrCode ClearSessionData() = 0; virtual bool GetIsIncrementalBackup() = 0; virtual bool ValidRestoreDataType(RestoreTypeEnum) = 0; virtual SvcSessionManager::Impl GetImpl() = 0; + virtual int GetSessionCnt() = 0; + virtual void SetClearDataFlag(const std::string &bundleName, bool isNotClear) = 0; + virtual bool GetClearDataFlag(const std::string &bundleName) = 0; virtual void SetIncrementalData(const BIncrementalData &) = 0; virtual int32_t GetIncrementalManifestFd(const std::string &) = 0; virtual int64_t GetLastIncrementalTime(const std::string &) = 0; + virtual bool CleanAndCheckIfNeedWait(ErrCode &ret, std::vector &bundleNameList) = 0; + virtual void SetPublishFlag(const std::string &bundleName) = 0; + virtual void SetImplRestoreType(const RestoreTypeEnum restoreType) = 0; + virtual void SetIsReadyLaunch(const std::string &bundleName) = 0; public: static inline std::shared_ptr session = nullptr; }; @@ -127,20 +136,29 @@ public: MOCK_METHOD(void, SetBundleVersionName, (const std::string &, std::string)); MOCK_METHOD(std::string, GetBundleVersionName, (const std::string &)); MOCK_METHOD(void, SetBundleDataSize, (const std::string &, int64_t)); - MOCK_METHOD(void, BundleExtTimerStart, (const std::string &, const Utils::Timer::TimerCallback &)); + MOCK_METHOD(bool, StartFwkTimer, (const std::string &, const Utils::Timer::TimerCallback &)); + MOCK_METHOD(bool, StopFwkTimer, (const std::string &)); + MOCK_METHOD(bool, StartExtTimer, (const std::string &, const Utils::Timer::TimerCallback &)); + MOCK_METHOD(bool, StopExtTimer, (const std::string &)); MOCK_METHOD(bool, UpdateTimer, (const std::string &, uint32_t, const Utils::Timer::TimerCallback &)); - MOCK_METHOD(void, BundleExtTimerStop, (const std::string &)); - MOCK_METHOD(void, IncreaseSessionCnt, ()); - MOCK_METHOD(void, DecreaseSessionCnt, ()); + MOCK_METHOD(void, IncreaseSessionCnt, (const std::string)); + MOCK_METHOD(void, DecreaseSessionCnt, (const std::string)); MOCK_METHOD(int32_t, GetMemParaCurSize, ()); MOCK_METHOD(void, SetMemParaCurSize, (int32_t)); - MOCK_METHOD(void, ClearSessionData, ()); + MOCK_METHOD(ErrCode, ClearSessionData, ()); MOCK_METHOD(bool, GetIsIncrementalBackup, ()); MOCK_METHOD(bool, ValidRestoreDataType, (RestoreTypeEnum)); MOCK_METHOD(SvcSessionManager::Impl, GetImpl, ()); + MOCK_METHOD(int, GetSessionCnt, ()); + MOCK_METHOD(void, SetClearDataFlag, (const std::string &, bool)); + MOCK_METHOD(bool, GetClearDataFlag, (const std::string &)); MOCK_METHOD(void, SetIncrementalData, (const BIncrementalData &)); MOCK_METHOD(int32_t, GetIncrementalManifestFd, (const std::string &)); MOCK_METHOD(int64_t, GetLastIncrementalTime, (const std::string &)); + MOCK_METHOD(bool, CleanAndCheckIfNeedWait, (ErrCode &, std::vector &)); + MOCK_METHOD(void, SetPublishFlag, (const std::string &)); + MOCK_METHOD(void, SetImplRestoreType, (const RestoreTypeEnum restoreType)); + MOCK_METHOD(void, SetIsReadyLaunch, (const std::string &)); }; } // namespace OHOS::FileManagement::Backup diff --git a/tests/mock/napi/include/napi_mock.h b/tests/mock/napi/include/napi_mock.h index bc699b791d8ba1548bcf6abc11f318245c9546d1..5f70f4f022c00af96c55e54410330bc2f22a0541 100644 --- a/tests/mock/napi/include/napi_mock.h +++ b/tests/mock/napi/include/napi_mock.h @@ -60,6 +60,7 @@ public: virtual napi_status napi_create_function(napi_env, const char*, size_t, napi_callback, void*, napi_value*) = 0; virtual napi_status napi_open_handle_scope(napi_env, napi_handle_scope*) = 0; virtual napi_status napi_close_handle_scope(napi_env, napi_handle_scope) = 0; + virtual napi_status napi_is_exception_pending(napi_env, bool*) = 0; public: static inline std::shared_ptr napi = nullptr; }; @@ -96,6 +97,7 @@ public: MOCK_METHOD6(napi_create_function, napi_status(napi_env, const char*, size_t, napi_callback, void*, napi_value*)); MOCK_METHOD2(napi_open_handle_scope, napi_status(napi_env, napi_handle_scope*)); MOCK_METHOD2(napi_close_handle_scope, napi_status(napi_env, napi_handle_scope)); + MOCK_METHOD2(napi_is_exception_pending, napi_status(napi_env, bool*)); }; } // namespace OHOS::FileManagement::Backup #endif // TEST_UNITTEST_MOCK_NAPI_H \ No newline at end of file diff --git a/tests/mock/napi/src/napi_mock.cpp b/tests/mock/napi/src/napi_mock.cpp index 0310429d36660f0c13e192b167aa541ec70dd138..5b672ce665a256f232ce8cfa4b2bb3360c68aa84 100644 --- a/tests/mock/napi/src/napi_mock.cpp +++ b/tests/mock/napi/src/napi_mock.cpp @@ -18,12 +18,6 @@ int uv_queue_work(uv_loop_t* loop, uv_work_t* req, uv_work_cb work_cb, uv_after_work_cb after_work_cb) { - if (work_cb) { - work_cb(req); - } - if (after_work_cb) { - after_work_cb(req, 0); - } return OHOS::FileManagement::Backup::Napi::napi->uv_queue_work(loop, req, work_cb, after_work_cb); } @@ -163,4 +157,9 @@ NAPI_EXTERN napi_status napi_open_handle_scope(napi_env env, napi_handle_scope* NAPI_EXTERN napi_status napi_close_handle_scope(napi_env env, napi_handle_scope scope) { return OHOS::FileManagement::Backup::Napi::napi->napi_close_handle_scope(env, scope); +} + +napi_status napi_is_exception_pending(napi_env env, bool* result) +{ + return OHOS::FileManagement::Backup::Napi::napi->napi_is_exception_pending(env, result); } \ No newline at end of file diff --git a/tests/mock/parameter_mock/include/parameter_mock.h b/tests/mock/parameter_mock/include/parameter_mock.h new file mode 100644 index 0000000000000000000000000000000000000000..76136ae9aad7c03d9ec10561c3875c6d690732ab --- /dev/null +++ b/tests/mock/parameter_mock/include/parameter_mock.h @@ -0,0 +1,39 @@ +/* + * Copyright (c) 2022-2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef MOCK_OHOS_MOCK_PARAMETER_H +#define MOCK_OHOS_MOCK_PARAMETER_H + +#include +#include + +namespace OHOS { +namespace AppFileService { +class IParamMoc { +public: + virtual ~IParamMoc() = default; +public: + virtual int GetParameter(const char *key, const char *def, char *value, uint32_t len) = 0; +public: + static inline std::shared_ptr paramMoc = nullptr; +}; + +class ParamMoc : public IParamMoc { +public: + MOCK_METHOD4(GetParameter, int(const char *key, const char *def, char *value, uint32_t len)); +}; +} +} +#endif \ No newline at end of file diff --git a/tests/mock/parameter_mock/src/parameter_mock.cpp b/tests/mock/parameter_mock/src/parameter_mock.cpp new file mode 100644 index 0000000000000000000000000000000000000000..106ce53d8c2f0a0ea52a627967039167a6930562 --- /dev/null +++ b/tests/mock/parameter_mock/src/parameter_mock.cpp @@ -0,0 +1,27 @@ +/* + * Copyright (c) 2022-2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "parameter_mock.h" + +#include "parameter.h" + +using namespace OHOS::AppFileService; +int GetParameter(const char *key, const char *def, char *value, uint32_t len) +{ + if (IParamMoc::paramMoc == nullptr) { + return -1; + } + return IParamMoc::paramMoc->GetParameter(key, def, value, len); +} \ No newline at end of file diff --git a/tests/moduletests/backup_kit_inner/BUILD.gn b/tests/moduletests/backup_kit_inner/BUILD.gn index 9d97e78341cadf84aad1969755b474194bb2976e..c3fc260eee40865512d9d714ed0bf6303853f5fd 100644 --- a/tests/moduletests/backup_kit_inner/BUILD.gn +++ b/tests/moduletests/backup_kit_inner/BUILD.gn @@ -44,12 +44,6 @@ ohos_unittest("b_session_test") { "${path_backup}/utils:backup_utils", ] - cflags = [ "--coverage" ] - - ldflags = [ "--coverage" ] - - cflags_cc = [ "--coverage" ] - external_deps = [ "c_utils:utils", "hilog:libhilog", diff --git a/tests/moduletests/backup_kit_inner/b_session_backup_test.cpp b/tests/moduletests/backup_kit_inner/b_session_backup_test.cpp index 814cd7b549850e6c0d59128f90f3cdb1000e4da4..10b69da7dc9cb7718e5a4f56dfd924e50c0cb955 100644 --- a/tests/moduletests/backup_kit_inner/b_session_backup_test.cpp +++ b/tests/moduletests/backup_kit_inner/b_session_backup_test.cpp @@ -309,4 +309,70 @@ HWTEST_F(BSessionBackupTest, SUB_backup_b_session_backup_0700, testing::ext::Tes } GTEST_LOG_(INFO) << "BSessionBackupTest-end SUB_backup_b_session_backup_0700"; } + +/** + * @tc.number: SUB_backup_b_session_backup_0800 + * @tc.name: SUB_backup_b_session_backup_0800 + * @tc.desc: 测试AppendBundles接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(BSessionBackupTest, SUB_backup_b_session_backup_0800, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "BSessionBackupTest-AppendBundles SUB_backup_b_session_backup_0800"; + try { + if (backupPtr_ == nullptr) { + GTEST_LOG_(INFO) << "SUB_backup_b_session_backup_0800 backupPtr_ == nullptr"; + return; + } + vector bundleNames; + vector detailInfos; + GTEST_LOG_(INFO) << "GetInstance is true"; + SetMockGetInstance(true); + auto ret = backupPtr_->AppendBundles(bundleNames, detailInfos); + EXPECT_EQ(ret, ErrCode(BError::Codes::OK)); + GTEST_LOG_(INFO) << "GetInstance is false"; + SetMockGetInstance(false); + ret = backupPtr_->AppendBundles(bundleNames, detailInfos); + EXPECT_NE(ret, ErrCode(BError::Codes::OK)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BSessionBackupTest-an exception occurred by AppendBundles."; + } + GTEST_LOG_(INFO) << "BSessionBackupTest-end SUB_backup_b_session_backup_0800"; +} + +/** + * @tc.number: SUB_backup_b_session_backup_0900 + * @tc.name: SUB_backup_b_session_backup_0900 + * @tc.desc: 测试AppendBundles接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(BSessionBackupTest, SUB_backup_b_session_backup_0900, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "BSessionBackupTest-Release SUB_backup_b_session_backup_0900"; + try { + if (backupPtr_ == nullptr) { + GTEST_LOG_(INFO) << "SUB_backup_b_session_backup_0900 backupPtr_ == nullptr"; + return; + } + GTEST_LOG_(INFO) << "GetInstance is true"; + SetMockGetInstance(true); + auto ret = backupPtr_->Release(); + EXPECT_EQ(ret, ErrCode(BError::Codes::OK)); + GTEST_LOG_(INFO) << "GetInstance is false"; + SetMockGetInstance(false); + ret = backupPtr_->Release(); + EXPECT_NE(ret, ErrCode(BError::Codes::OK)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BSessionBackupTest-an exception occurred by Release."; + } + GTEST_LOG_(INFO) << "BSessionBackupTest-end SUB_backup_b_session_backup_0900"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/moduletests/backup_kit_inner/b_session_restore_async_test.cpp b/tests/moduletests/backup_kit_inner/b_session_restore_async_test.cpp index a25d4c1b3eea64a3abd221cea390f9f1dbc02e9e..9d6d8e81a51a55e1d61c372e44072d41bc5dd907 100644 --- a/tests/moduletests/backup_kit_inner/b_session_restore_async_test.cpp +++ b/tests/moduletests/backup_kit_inner/b_session_restore_async_test.cpp @@ -54,11 +54,6 @@ static void OnBackupServiceDied() GTEST_LOG_(INFO) << "BSessionRestoreAsyncTest OnBackupServiceDied OK"; } -static void OnResultReport(std::string bundleName, std::string result) -{ - GTEST_LOG_(INFO) << "BSessionRestoreAsyncTest OnResultReport OK"; -} - class BSessionRestoreAsyncTest : public testing::Test { public: static void SetUpTestCase(void) {}; @@ -92,7 +87,6 @@ void BSessionRestoreAsyncTest::Init() callbacks_.onBundleFinished = OnBundleFinished; callbacks_.onAllBundlesFinished = OnAllBundlesFinished; callbacks_.onBackupServiceDied = OnBackupServiceDied; - callbacks_.onResultReport = OnResultReport; } /** @@ -115,7 +109,6 @@ HWTEST_F(BSessionRestoreAsyncTest, SUB_backup_b_session_restore_async_0100, test callbacks_.onBundleFinished(ErrCode(BError::Codes::OK), ""); callbacks_.onAllBundlesFinished(ErrCode(BError::Codes::OK)); callbacks_.onBackupServiceDied(); - callbacks_.onResultReport("", ""); } catch (...) { EXPECT_TRUE(false); GTEST_LOG_(INFO) << "BSessionRestoreAsyncTest-an exception occurred by Callbacks."; @@ -236,6 +229,9 @@ HWTEST_F(BSessionRestoreAsyncTest, SUB_backup_b_session_restore_async_0500, test EXPECT_EQ(ret, ErrCode(BError::Codes::OK)); ret = restorePtr_->AppendBundles(UniqueFd(-1), bundleNames); EXPECT_EQ(ret, ErrCode(BError::Codes::OK)); + SetMockGetInstance(false); + ret = restorePtr_->AppendBundles(UniqueFd(-1), bundleNames); + EXPECT_NE(ret, ErrCode(BError::Codes::OK)); restorePtr_ = nullptr; } catch (...) { EXPECT_TRUE(false); @@ -269,6 +265,9 @@ HWTEST_F(BSessionRestoreAsyncTest, SUB_backup_b_session_restore_async_0501, test EXPECT_EQ(ret, ErrCode(BError::Codes::OK)); ret = restorePtr_->AppendBundles(UniqueFd(-1), bundleNames, detailInfos); EXPECT_EQ(ret, ErrCode(BError::Codes::OK)); + SetMockGetInstance(false); + ret = restorePtr_->AppendBundles(UniqueFd(-1), bundleNames, detailInfos); + EXPECT_NE(ret, ErrCode(BError::Codes::OK)); restorePtr_ = nullptr; } catch (...) { EXPECT_TRUE(false); @@ -300,10 +299,43 @@ HWTEST_F(BSessionRestoreAsyncTest, SUB_backup_b_session_restore_async_0600, test GTEST_LOG_(INFO) << "GetInstance is true but not equal to parameter"; SetMockGetInstance(true); restorePtr_->RegisterBackupServiceDied(nullptr); + Init(); + SetMockGetInstance(true); + restorePtr_->RegisterBackupServiceDied(callbacks_.onBackupServiceDied); } catch (...) { EXPECT_TRUE(false); GTEST_LOG_(INFO) << "BSessionRestoreAsyncTest-an exception occurred by RegisterBackupServiceDied."; } GTEST_LOG_(INFO) << "BSessionRestoreAsyncTest-end SUB_backup_b_session_restore_async_0600"; } + +/** + * @tc.number: SUB_backup_b_session_restore_async_0700 + * @tc.name: SUB_backup_b_session_restore_async_0700 + * @tc.desc: 测试Release接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I7L7A6 + */ +HWTEST_F(BSessionRestoreAsyncTest, SUB_backup_b_session_restore_async_0700, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "BSessionRestoreAsyncTest-begin SUB_backup_b_session_restore_async_0700"; + try { + if (restorePtr_ == nullptr) { + GTEST_LOG_(INFO) << "SUB_backup_b_session_restore_async_0700 restorePtr_ == nullptr"; + return; + } + SetMockGetInstance(false); + ErrCode ret = restorePtr_->Release(); + EXPECT_NE(ret, ErrCode(BError::Codes::OK)); + SetMockGetInstance(true); + ret = restorePtr_->Release(); + EXPECT_EQ(ret, ErrCode(BError::Codes::OK)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BSessionRestoreAsyncTest-an exception occurred by ~BSessionRestoreAsync."; + } + GTEST_LOG_(INFO) << "BSessionRestoreAsyncTest-end SUB_backup_b_session_restore_async_0700"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/moduletests/backup_kit_inner/b_session_restore_test.cpp b/tests/moduletests/backup_kit_inner/b_session_restore_test.cpp index 1694f91d51558970f970a4f70c94df94aed84db7..b8dc3716305e7225d989b978a40df64b682a9b4b 100644 --- a/tests/moduletests/backup_kit_inner/b_session_restore_test.cpp +++ b/tests/moduletests/backup_kit_inner/b_session_restore_test.cpp @@ -55,11 +55,6 @@ static void OnBackupServiceDied() GTEST_LOG_(INFO) << "BSessionRestoreTest OnBackupServiceDied OK"; } -static void OnResultReport(std::string bundleName, const std::string result) -{ - GTEST_LOG_(INFO) << "BSessionRestoreAsyncTest OnResultReport OK"; -} - class BSessionRestoreTest : public testing::Test { public: static void SetUpTestCase(void) {}; @@ -93,7 +88,6 @@ void BSessionRestoreTest::Init() callbacks_.onBundleFinished = OnBundleFinished; callbacks_.onAllBundlesFinished = OnAllBundlesFinished; callbacks_.onBackupServiceDied = OnBackupServiceDied; - callbacks_.onResultReport = OnResultReport; } /** diff --git a/tests/unittests/backup_api/backup_impl/include/ext_extension_mock.h b/tests/unittests/backup_api/backup_impl/include/ext_extension_mock.h index 7484d1b8c64bf208e376adaf37dc8998a8fc84fc..b5070b41f53fc228b3471e56955304860c2de76a 100644 --- a/tests/unittests/backup_api/backup_impl/include/ext_extension_mock.h +++ b/tests/unittests/backup_api/backup_impl/include/ext_extension_mock.h @@ -79,7 +79,7 @@ public: return BError(BError::Codes::OK); }; - ErrCode HandleBackup() override + ErrCode HandleBackup(bool isClearData) override { GTEST_LOG_(INFO) << "HandleBackup"; if (nHandleBackupNum_ == 1) { @@ -99,7 +99,7 @@ public: return BError(BError::Codes::OK); }; - ErrCode HandleRestore() override + ErrCode HandleRestore(bool isClearData) override { return BError(BError::Codes::OK); }; @@ -119,7 +119,7 @@ public: return BError(BError::Codes::OK); }; - ErrCode IncrementalOnBackup() override + ErrCode IncrementalOnBackup(bool isClearData) override { return BError(BError::Codes::OK); }; @@ -139,6 +139,11 @@ public: return BError(BError::Codes::OK); }; + ErrCode User0OnBackup() override + { + return BError(BError::Codes::OK); + }; + private: int32_t nHandleBackupNum_ = 0; }; diff --git a/tests/unittests/backup_api/backup_impl/include/i_service_mock.h b/tests/unittests/backup_api/backup_impl/include/i_service_mock.h index 0a0ffa7e8217f72fd5116723bb041dc0093140a3..a0da61edc9fc132789a051c9f64d6a9cb84218a6 100644 --- a/tests/unittests/backup_api/backup_impl/include/i_service_mock.h +++ b/tests/unittests/backup_api/backup_impl/include/i_service_mock.h @@ -102,6 +102,7 @@ public: ErrCode AppendBundlesRestoreSession(UniqueFd fd, const std::vector &bundleNames, + const std::vector &detailInfos, RestoreTypeEnum restoreType, int32_t userId) override { @@ -110,7 +111,6 @@ public: ErrCode AppendBundlesRestoreSession(UniqueFd fd, const std::vector &bundleNames, - const std::vector &detailInfos, RestoreTypeEnum restoreType, int32_t userId) override { @@ -138,7 +138,17 @@ public: return BError(BError::Codes::OK); } - ErrCode UpdateTimer(BundleName &bundleName, uint32_t timeOut, bool &result) override + ErrCode UpdateTimer(BundleName &bundleName, uint32_t timeout, bool &result) override + { + return BError(BError::Codes::OK); + } + + ErrCode StartExtTimer(bool &isExtStart) override + { + return BError(BError::Codes::OK); + } + + ErrCode StartFwkTimer(bool &isFwkStart) override { return BError(BError::Codes::OK); } @@ -203,6 +213,11 @@ public: { return BError(BError::Codes::OK); } + + ErrCode ReportAppProcessInfo(const std::string processInfo, const BackupRestoreScenario sennario) + { + return BError(BError::Codes::OK); + } }; } // namespace OHOS::FileManagement::Backup #endif // MOCK_I_SERVICE_MOCK_H \ No newline at end of file diff --git a/tests/unittests/backup_api/backup_impl/include/service_reverse_mock.h b/tests/unittests/backup_api/backup_impl/include/service_reverse_mock.h index 4ea6262fdc045a4bc65ec2d45105c5eef2572145..7b1bf2f9b96749795245ae35d3dbf962146f7f45 100644 --- a/tests/unittests/backup_api/backup_impl/include/service_reverse_mock.h +++ b/tests/unittests/backup_api/backup_impl/include/service_reverse_mock.h @@ -41,12 +41,14 @@ public: void BackupOnResultReport(std::string result, std::string bundleName) override {}; void BackupOnBundleFinished(int32_t errCode, std::string bundleName) override {} void BackupOnAllBundlesFinished(int32_t errCode) override {} + void BackupOnProcessInfo(std::string bundleName, std::string processInfo) override {} void RestoreOnBundleStarted(int32_t errCode, std::string bundleName) override {} void RestoreOnBundleFinished(int32_t errCode, std::string bundleName) override {} void RestoreOnAllBundlesFinished(int32_t errCode) override {} void RestoreOnFileReady(std::string bundleName, std::string fileName, int fd, int32_t errCode) override {} void RestoreOnResultReport(std::string result, std::string bundleName, ErrCode errCode) override {} + void RestoreOnProcessInfo(std::string bundleName, std::string processInfo) override {} void IncrementalBackupOnFileReady(std::string bundleName, std::string fileName, int fd, int manifestFd, int32_t errCode) override {} @@ -54,6 +56,7 @@ public: void IncrementalBackupOnResultReport(std::string result, std::string bundleName) override {} void IncrementalBackupOnBundleFinished(int32_t errCode, std::string bundleName) override {} void IncrementalBackupOnAllBundlesFinished(int32_t errCode) override {} + void IncrementalBackupOnProcessInfo(std::string bundleName, std::string processInfo) override {} void IncrementalRestoreOnBundleStarted(int32_t errCode, std::string bundleName) override {} void IncrementalRestoreOnBundleFinished(int32_t errCode, std::string bundleName) override {} @@ -61,6 +64,7 @@ public: void IncrementalRestoreOnFileReady(std::string bundleName, std::string fileName, int fd, int manifestFd, int32_t errCode) override {} void IncrementalRestoreOnResultReport(std::string result, std::string bundleName, ErrCode errCode) override {}; + void IncrementalRestoreOnProcessInfo(std::string bundleName, std::string processInfo) override {} }; } // namespace OHOS::FileManagement::Backup #endif // MOCK_SERVICE_REVERSE_MOCK_H \ No newline at end of file diff --git a/tests/unittests/backup_api/backup_impl/service_proxy_test.cpp b/tests/unittests/backup_api/backup_impl/service_proxy_test.cpp index f95584e61d204e60609cb74b85bad115a9010f73..0f273c977650a05e2616fbf0663cb778b1285b50 100644 --- a/tests/unittests/backup_api/backup_impl/service_proxy_test.cpp +++ b/tests/unittests/backup_api/backup_impl/service_proxy_test.cpp @@ -32,7 +32,6 @@ using namespace std; using namespace testing; namespace { -const string BUNDLE_NAME = "com.example.app2backup"; const string FILE_NAME = "1.tar"; constexpr int32_t SERVICE_ID = 5203; } // namespace @@ -271,6 +270,36 @@ HWTEST_F(ServiceProxyTest, SUB_Service_proxy_AppDone_0100, testing::ext::TestSiz GTEST_LOG_(INFO) << "ServiceProxyTest-end SUB_Service_proxy_AppDone_0100"; } +/** + * @tc.number: SUB_Service_proxy_ServiceResultReport_0100 + * @tc.name: SUB_Service_proxy_ServiceResultReport_0100 + * @tc.desc: 测试 ServiceResultReport + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ServiceProxyTest, SUB_Service_proxy_ServiceResultReport_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceProxyTest-begin SUB_Service_proxy_ServiceResultReport_0100"; + if (proxy_ == nullptr) { + GTEST_LOG_(INFO) << "SUB_Service_proxy_ServiceResultReport_0100 proxy_ == nullptr"; + return; + } + EXPECT_CALL(*mock_, SendRequest(_, _, _, _)) + .Times(2) + .WillOnce(Invoke(mock_.GetRefPtr(), &IServiceMock::InvokeSendRequest)) + .WillOnce(Return(EPERM)); + std::string restoreRetInfo = "test_restoreRetInfo"; + BackupRestoreScenario scenario = FULL_BACKUP; + int32_t result = proxy_->ServiceResultReport(restoreRetInfo, scenario, BError(BError::Codes::OK)); + EXPECT_EQ(result, BError(BError::Codes::OK)); + + result = proxy_->ServiceResultReport(restoreRetInfo, scenario, BError(BError::Codes::OK)); + EXPECT_NE(result, BError(BError::Codes::OK)); + GTEST_LOG_(INFO) << "ServiceProxyTest-end SUB_Service_proxy_ServiceResultReport_0100"; +} + /** * @tc.number: SUB_Service_proxy_GetFileHandle_0100 * @tc.name: SUB_Service_proxy_GetFileHandle_0100 @@ -394,6 +423,38 @@ HWTEST_F(ServiceProxyTest, SUB_Service_proxy_AppendBundlesBackupSession_0100, te GTEST_LOG_(INFO) << "ServiceProxyTest-end SUB_Service_proxy_AppendBundlesBackupSession_0100"; } +/** + * @tc.number: SUB_Service_proxy_AppendBundlesDetailsBackupSession_0100 + * @tc.name: SUB_Service_proxy_AppendBundlesDetailsBackupSession_0100 + * @tc.desc: 测试 AppendBundlesDetailsBackupSession + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6URNZ + */ +HWTEST_F(ServiceProxyTest, SUB_Service_proxy_AppendBundlesDetailsBackupSession_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceProxyTest-begin SUB_Service_proxy_AppendBundlesDetailsBackupSession_0100"; + if (proxy_ == nullptr) { + GTEST_LOG_(INFO) << "SUB_Service_proxy_AppendBundlesDetailsBackupSession_0100 proxy_ == nullptr"; + return; + } + EXPECT_CALL(*mock_, SendRequest(_, _, _, _)) + .Times(2) + .WillOnce(Invoke(mock_.GetRefPtr(), &IServiceMock::InvokeSendRequest)) + .WillOnce(Return(EPERM)); + + std::vector bundleNames; + std::vector detailInfos; + + int32_t result = proxy_->AppendBundlesDetailsBackupSession(bundleNames, detailInfos); + EXPECT_EQ(result, BError(BError::Codes::OK)); + + result = proxy_->AppendBundlesDetailsBackupSession(bundleNames, detailInfos); + EXPECT_NE(result, BError(BError::Codes::OK)); + GTEST_LOG_(INFO) << "ServiceProxyTest-end SUB_Service_proxy_AppendBundlesDetailsBackupSession_0100"; +} + /** * @tc.number: SUB_Service_proxy_Finish_0100 * @tc.name: SUB_Service_proxy_Finish_0100 @@ -604,6 +665,43 @@ HWTEST_F(ServiceProxyTest, SUB_Service_proxy_PublishIncrementalFile_0100, testin GTEST_LOG_(INFO) << "ServiceProxyTest-end SUB_Service_proxy_PublishIncrementalFile_0100"; } +/** + * @tc.number: SUB_Service_proxy_PublishSAIncrementalFile_0100 + * @tc.name: SUB_Service_proxy_PublishSAIncrementalFile_0100 + * @tc.desc: 测试 PublishSAIncrementalFile 接口调用成功和失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I90ZV5 + */ +HWTEST_F(ServiceProxyTest, SUB_Service_proxy_PublishSAIncrementalFile_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceProxyTest-begin SUB_Service_proxy_PublishSAIncrementalFile_0100"; + if (proxy_ == nullptr) { + GTEST_LOG_(INFO) << "SUB_Service_proxy_PublishSAIncrementalFile_0100 proxy_ == nullptr"; + return; + } + EXPECT_CALL(*mock_, SendRequest(_, _, _, _)) + .Times(2) + .WillOnce(Invoke(mock_.GetRefPtr(), &IServiceMock::InvokeSendRequest)) + .WillOnce(Return(EPERM)); + + string bundleName = "com.example.app2backup"; + string fileName = ""; + BFileInfo fileInfo(bundleName, fileName, -1); + TestManager tm("AppIncrementalFileReady_GetFd_0100"); + std::string filePath = tm.GetRootDirCurTest().append(FILE_NAME); + UniqueFd fd(open(filePath.data(), O_RDONLY | O_CREAT, S_IRUSR | S_IWUSR)); + ErrCode ret = proxy_->PublishSAIncrementalFile(fileInfo, move(fd)); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + + TestManager tmErr("AppIncrementalFileReady_GetFd_0200"); + UniqueFd fdErr(open(tmErr.GetRootDirCurTest().append(FILE_NAME).data(), O_RDONLY | O_CREAT, S_IRUSR | S_IWUSR)); + ret = proxy_->PublishSAIncrementalFile(fileInfo, move(fdErr)); + EXPECT_NE(ret, BError(BError::Codes::OK)); + GTEST_LOG_(INFO) << "ServiceProxyTest-end SUB_Service_proxy_PublishSAIncrementalFile_0100"; +} + /** * @tc.number: SUB_Service_proxy_AppIncrementalFileReady_0100 * @tc.name: SUB_Service_proxy_AppIncrementalFileReady_0100 @@ -643,6 +741,41 @@ HWTEST_F(ServiceProxyTest, SUB_Service_proxy_AppIncrementalFileReady_0100, testi GTEST_LOG_(INFO) << "ServiceProxyTest-end SUB_Service_proxy_AppIncrementalFileReady_0100"; } +/** + * @tc.number: SUB_Service_proxy_AppIncrementalFileReady_0200 + * @tc.name: SUB_Service_proxy_AppIncrementalFileReady_0200 + * @tc.desc: 测试 AppIncrementalFileReady 接口成功和失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I90ZV5 + */ +HWTEST_F(ServiceProxyTest, SUB_Service_proxy_AppIncrementalFileReady_0200, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceProxyTest-begin SUB_Service_proxy_AppIncrementalFileReady_0200"; + if (proxy_ == nullptr) { + GTEST_LOG_(INFO) << "SUB_Service_proxy_AppIncrementalFileReady_0200 proxy_ == nullptr"; + return; + } + EXPECT_CALL(*mock_, SendRequest(_, _, _, _)) + .Times(2) + .WillOnce(Return(0)) + .WillOnce(Return(0)); + + string bundleName = "com.example.app2backup"; + TestManager tm("AppIncrementalFileReady_0200"); + std::string filePath = tm.GetRootDirCurTest().append(FILE_NAME); + UniqueFd fd(open(filePath.data(), O_RDONLY | O_CREAT, S_IRUSR | S_IWUSR)); + UniqueFd manifestFd(open(filePath.data(), O_RDONLY | O_CREAT, S_IRUSR | S_IWUSR)); + + int32_t result = proxy_->AppIncrementalFileReady(bundleName, UniqueFd(-1), move(manifestFd), 0); + EXPECT_EQ(result, BError(BError::Codes::OK)); + + result = proxy_->AppIncrementalFileReady(bundleName, move(fd), UniqueFd(-1), 0); + EXPECT_EQ(result, BError(BError::Codes::OK)); + GTEST_LOG_(INFO) << "ServiceProxyTest-end SUB_Service_proxy_AppIncrementalFileReady_0200"; +} + /** * @tc.number: SUB_Service_proxy_AppIncrementalDone_0100 * @tc.name: SUB_Service_proxy_AppIncrementalDone_0100 @@ -896,8 +1029,8 @@ HWTEST_F(ServiceProxyTest, SUB_Service_proxy_UpdateTimer_0100, testing::ext::Tes .WillOnce(Invoke(mock_.GetRefPtr(), &IServiceMock::InvokeSendRequest)); bool result; std::string bundleName = "com.example.app2backup"; - uint32_t timeOut = 30000; - int32_t ret = proxy_->UpdateTimer(bundleName, timeOut, result); + uint32_t timeout = 30000; + int32_t ret = proxy_->UpdateTimer(bundleName, timeout, result); EXPECT_EQ(ret, BError(BError::Codes::OK)); GTEST_LOG_(INFO) << "ServiceProxyTest-end SUB_Service_proxy_UpdateTimer_0100"; } diff --git a/tests/unittests/backup_api/backup_impl/service_reverse_stub_test.cpp b/tests/unittests/backup_api/backup_impl/service_reverse_stub_test.cpp index b69f91d463fcc9657d6242d96f30b46e1a373b7c..d5c75557cd2fa4b3e2140081a7e65b87be28b14b 100644 --- a/tests/unittests/backup_api/backup_impl/service_reverse_stub_test.cpp +++ b/tests/unittests/backup_api/backup_impl/service_reverse_stub_test.cpp @@ -45,23 +45,27 @@ public: MOCK_METHOD2(BackupOnResultReport, void(string result, std::string bundleName)); MOCK_METHOD2(BackupOnBundleFinished, void(int32_t errCode, string bundleName)); MOCK_METHOD1(BackupOnAllBundlesFinished, void(int32_t errCode)); + MOCK_METHOD2(BackupOnProcessInfo, void(std::string bundleName, std::string processInfo)); MOCK_METHOD2(RestoreOnBundleStarted, void(int32_t errCode, std::string bundleName)); MOCK_METHOD2(RestoreOnBundleFinished, void(int32_t errCode, string bundleName)); MOCK_METHOD1(RestoreOnAllBundlesFinished, void(int32_t errCode)); MOCK_METHOD4(RestoreOnFileReady, void(string bundleName, string fileName, int fd, int32_t errCode)); MOCK_METHOD3(RestoreOnResultReport, void(string result, string bundleName, ErrCode errCode)); + MOCK_METHOD2(RestoreOnProcessInfo, void(std::string bundleName, std::string processInfo)); MOCK_METHOD5(IncrementalBackupOnFileReady, void(string bundleName, string fileName, int fd, int manifestFd, int32_t errCode)); MOCK_METHOD2(IncrementalBackupOnBundleStarted, void(int32_t errCode, string bundleName)); MOCK_METHOD2(IncrementalBackupOnResultReport, void(string result, std::string bundleName)); MOCK_METHOD2(IncrementalBackupOnBundleFinished, void(int32_t errCode, string bundleName)); MOCK_METHOD1(IncrementalBackupOnAllBundlesFinished, void(int32_t errCode)); + MOCK_METHOD2(IncrementalBackupOnProcessInfo, void(std::string bundleName, std::string processInfo)); MOCK_METHOD2(IncrementalRestoreOnBundleStarted, void(int32_t errCode, std::string bundleName)); MOCK_METHOD2(IncrementalRestoreOnBundleFinished, void(int32_t errCode, string bundleName)); MOCK_METHOD1(IncrementalRestoreOnAllBundlesFinished, void(int32_t errCode)); MOCK_METHOD5(IncrementalRestoreOnFileReady, void(string bundleName, string fileName, int fd, int manifestFd, int32_t errCode)); MOCK_METHOD3(IncrementalRestoreOnResultReport, void(string result, string bundleName, ErrCode errCode)); + MOCK_METHOD2(IncrementalRestoreOnProcessInfo, void(std::string bundleName, std::string processInfo)); }; class ServiceReverseStubTest : public testing::Test { diff --git a/tests/unittests/backup_ext/BUILD.gn b/tests/unittests/backup_ext/BUILD.gn index 7ab377141aaaf2f03300b45dd6d8184fb8552e5b..849943f247ed548a33f3bb94ee35e90ac2cec557 100644 --- a/tests/unittests/backup_ext/BUILD.gn +++ b/tests/unittests/backup_ext/BUILD.gn @@ -139,6 +139,7 @@ ohos_unittest("tar_file_test") { "${path_backup}/frameworks/native/backup_ext/src/ext_backup_loader.cpp", "${path_backup}/frameworks/native/backup_ext/src/ext_extension.cpp", "${path_backup}/frameworks/native/backup_ext/src/ext_extension_stub.cpp", + "${path_backup}/frameworks/native/backup_ext/src/sub_ext_extension.cpp", "${path_backup}/frameworks/native/backup_ext/src/tar_file.cpp", "${path_backup}/frameworks/native/backup_ext/src/untar_file.cpp", "tar_file_test.cpp", @@ -192,6 +193,82 @@ ohos_unittest("tar_file_test") { use_exceptions = true } +ohos_unittest("untar_file_sup_test") { + branch_protector_ret = "pac_ret" + sanitize = { + integer_overflow = true + cfi = true + cfi_cross_dso = true + debug = false + blocklist = "${path_backup}/cfi_blocklist.txt" + } + + module_out_path = path_module_out_tests + + sources = [ + "${path_backup}/frameworks/native/backup_ext/src/ext_backup.cpp", + "${path_backup}/frameworks/native/backup_ext/src/ext_backup_context.cpp", + "${path_backup}/frameworks/native/backup_ext/src/ext_backup_context_js.cpp", + "${path_backup}/frameworks/native/backup_ext/src/ext_backup_js.cpp", + "${path_backup}/frameworks/native/backup_ext/src/ext_backup_loader.cpp", + "${path_backup}/frameworks/native/backup_ext/src/ext_extension.cpp", + "${path_backup}/frameworks/native/backup_ext/src/ext_extension_stub.cpp", + "${path_backup}/frameworks/native/backup_ext/src/sub_ext_extension.cpp", + "${path_backup}/frameworks/native/backup_ext/src/tar_file.cpp", + "${path_backup}/tests/mock/library_func_mock/library_func_mock.cpp", + "untar_file_sup_test.cpp", + ] + sources += backup_mock_proxy_src + + include_dirs = [ + "${path_ability_runtime}/services/common/include", + "${path_ability_runtime}/interfaces/kits/napi/aafwk/inner/napi_common", + "${path_ability_runtime}/interfaces/kits/native/appkit/ability_runtime", + "${path_backup}/frameworks/native/backup_ext/include", + "${path_backup}/frameworks/native/backup_ext/src", + "${path_backup}/interfaces/inner_api/native/backup_kit_inner/", + "${path_backup}/interfaces/inner_api/native/backup_kit_inner/impl", + "${path_backup}/frameworks/native/backup_kit_inner/include", + "${path_backup}/tests/mock/library_func_mock", + "${path_backup}/utils/include", + "${path_napi}/native_engine", + ] + include_dirs += backup_mock_utils_include + + deps = [ + "${path_backup}/interfaces/inner_api/native/backup_kit_inner:backup_kit_inner", + "${path_backup}/interfaces/innerkits/native:sandbox_helper_native", + "${path_backup}/tests/utils:backup_test_utils", + "${path_backup}/utils:backup_utils", + "${path_googletest}:gmock_main", + "${path_jsoncpp}:jsoncpp", + ] + + cflags = [ "--coverage" ] + ldflags = [ "--coverage" ] + cflags_cc = [ "--coverage" ] + + external_deps = [ + "ability_base:want", + "ability_runtime:ability_context_native", + "ability_runtime:abilitykit_native", + "ability_runtime:app_context", + "ability_runtime:appkit_native", + "ability_runtime:runtime", + "access_token:libaccesstoken_sdk", + "bundle_framework:appexecfwk_core", + "c_utils:utils", + "hitrace:hitrace_meter", + "ipc:ipc_core", + "napi:ace_napi", + "samgr:samgr_proxy", + ] + + defines = [ "private=public" ] + + use_exceptions = true +} + ohos_unittest("untar_file_test") { branch_protector_ret = "pac_ret" sanitize = { @@ -211,6 +288,7 @@ ohos_unittest("untar_file_test") { "${path_backup}/frameworks/native/backup_ext/src/ext_backup_loader.cpp", "${path_backup}/frameworks/native/backup_ext/src/ext_extension.cpp", "${path_backup}/frameworks/native/backup_ext/src/ext_extension_stub.cpp", + "${path_backup}/frameworks/native/backup_ext/src/sub_ext_extension.cpp", "${path_backup}/frameworks/native/backup_ext/src/tar_file.cpp", "${path_backup}/frameworks/native/backup_ext/src/untar_file.cpp", "untar_file_test.cpp", @@ -325,12 +403,14 @@ ohos_unittest("ext_backup_js_test") { group("backup_ext_test") { testonly = true - - deps = [ - ":ext_backup_js_test", - ":ext_extension_stub_test", - ":ext_extension_test", - ":tar_file_test", - ":untar_file_test", - ] + if (!use_libfuzzer) { + deps = [ + ":ext_backup_js_test", + ":ext_extension_stub_test", + ":ext_extension_test", + ":tar_file_test", + ":untar_file_sup_test", + ":untar_file_test", + ] + } } diff --git a/tests/unittests/backup_ext/ext_backup_js_test.cpp b/tests/unittests/backup_ext/ext_backup_js_test.cpp index 4e23ad233323ae150ed7387390ff2538d3fb61ef..0ea80082b073a2acbf14a4fbfdcc5e9df1968680 100644 --- a/tests/unittests/backup_ext/ext_backup_js_test.cpp +++ b/tests/unittests/backup_ext/ext_backup_js_test.cpp @@ -1,5 +1,5 @@ /* - * Copyright (c) 2024 Huawei Device Co., Ltd. + * Copyright (c) 2024-2025 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at @@ -38,6 +38,7 @@ namespace OHOS::FileManagement::Backup { using namespace std; using namespace testing; +const int ARG_INDEX_FIRST = 1; const int ARG_INDEX_SECOND = 2; const int ARG_INDEX_FOURTH = 4; const int ARG_INDEX_FIFTH = 5; @@ -194,18 +195,19 @@ HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_DealNapiException_0100, testing::ext try { napi_env env = nullptr; string exceptionInfo = ""; + napi_value exception; EXPECT_CALL(*napiMock, napi_get_and_clear_last_exception(_, _)).WillOnce(Return(napi_invalid_arg)); - auto ret = DealNapiException(env, exceptionInfo); + auto ret = DealNapiException(env, exception, exceptionInfo); EXPECT_EQ(ret, napi_invalid_arg); EXPECT_CALL(*napiMock, napi_get_and_clear_last_exception(_, _)).WillOnce(Return(napi_ok)); EXPECT_CALL(*napiMock, napi_get_value_string_utf8(_, _, _, _, _)).WillOnce(Return(napi_invalid_arg)); - ret = DealNapiException(env, exceptionInfo); + ret = DealNapiException(env, exception, exceptionInfo); EXPECT_EQ(ret, napi_invalid_arg); EXPECT_CALL(*napiMock, napi_get_and_clear_last_exception(_, _)).WillOnce(Return(napi_ok)); EXPECT_CALL(*napiMock, napi_get_value_string_utf8(_, _, _, _, _)).WillOnce(Return(napi_ok)); - ret = DealNapiException(env, exceptionInfo); + ret = DealNapiException(env, exception, exceptionInfo); EXPECT_EQ(ret, napi_ok); } catch (...) { EXPECT_TRUE(false); @@ -782,11 +784,18 @@ HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_ExportJsContext_0100, testing::ext:: extBackupJs->ExportJsContext(); EXPECT_TRUE(extBackupJs->jsObj_ == nullptr); + extBackupJs->jsObj_ = make_unique(); + auto refMock = static_cast(extBackupJs->jsObj_.get()); EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); - extBackupJs->jsObj_ = unique_ptr(); + EXPECT_CALL(*refMock, GetNapiValue()).WillOnce(Return(nullptr)); extBackupJs->ExportJsContext(); - EXPECT_TRUE(true); - extBackupJs->jsObj_ = nullptr; + EXPECT_TRUE(extBackupJs->jsObj_ != nullptr); + + int value = 0; + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*refMock, GetNapiValue()).WillOnce(Return(reinterpret_cast(&value))); + extBackupJs->ExportJsContext(); + EXPECT_TRUE(extBackupJs->jsObj_ != nullptr); } catch (...) { EXPECT_TRUE(false); GTEST_LOG_(INFO) << "ExtBackupJsTest-an exception occurred by ExportJsContext."; @@ -812,16 +821,18 @@ HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_CallJsMethod_0100, testing::ext::Tes auto ret = extBackupJs->CallJsMethod("", *jsRuntime, nullptr, nullptr, nullptr); EXPECT_EQ(ret, EINVAL); - EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)).WillOnce(Return(nullptr)); + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(Return(1)); - EXPECT_CALL(*napiMock, napi_open_handle_scope(_, _)).WillOnce(Return(napi_ok)); ret = extBackupJs->CallJsMethod("", *jsRuntime, nullptr, nullptr, nullptr); EXPECT_EQ(ret, EINVAL); EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)).WillOnce(Return(nullptr)); EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); - EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(Return(0)); + EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(DoAll(WithArgs<1, 3>(Invoke( + [](uv_work_t* req, uv_after_work_cb after_work_cb) { + after_work_cb(req, 0); + })), Return(0))); EXPECT_CALL(*napiMock, napi_open_handle_scope(_, _)).WillOnce(Return(napi_ok)); ret = extBackupJs->CallJsMethod("", *jsRuntime, nullptr, nullptr, nullptr); EXPECT_EQ(ret, ERR_OK); @@ -831,4 +842,654 @@ HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_CallJsMethod_0100, testing::ext::Tes } GTEST_LOG_(INFO) << "ExtBackupJsTest-end SUB_backup_ext_js_CallJsMethod_0100"; } + +/** + * @tc.number: SUB_backup_ext_js_DoCallJsMethod_0100 + * @tc.name: SUB_backup_ext_js_DoCallJsMethod_0100 + * @tc.desc: 测试 DoCallJsMethod 各个分支成功与失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesIAFBOS + */ +HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_DoCallJsMethod_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ExtBackupJsTest-begin SUB_backup_ext_js_DoCallJsMethod_0100"; + try { + string funcName = ""; + InputArgsParser argParserIn = {}; + ResultValueParser retParserIn = {}; + auto param = make_shared(funcName, nullptr, nullptr, argParserIn, retParserIn); + auto ret = DoCallJsMethod(param.get()); + EXPECT_EQ(ret, EINVAL); + + param->jsRuntime = jsRuntime.get(); + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_open_handle_scope(_, _)).WillOnce(Return(napi_ok)); + ret = DoCallJsMethod(param.get()); + EXPECT_EQ(ret, EINVAL); + + int scope = 0; + param->argParser = [](napi_env, std::vector &){ return false; }; + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_open_handle_scope(_, _)).WillOnce( + DoAll(SetArgPointee(reinterpret_cast(&scope)), Return(napi_ok))); + EXPECT_CALL(*napiMock, napi_close_handle_scope(_, _)).WillOnce(Return(napi_ok)); + ret = DoCallJsMethod(param.get()); + EXPECT_EQ(ret, EINVAL); + + auto ref = make_shared(); + param->argParser = [](napi_env, std::vector &){ return true; }; + param->jsObj = ref.get(); + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_open_handle_scope(_, _)).WillOnce( + DoAll(SetArgPointee(reinterpret_cast(&scope)), Return(napi_ok))); + EXPECT_CALL(*ref, GetNapiValue()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_close_handle_scope(_, _)).WillOnce(Return(napi_ok)); + ret = DoCallJsMethod(param.get()); + EXPECT_EQ(ret, EINVAL); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ExtBackupJsTest-an exception occurred by DoCallJsMethod."; + } + GTEST_LOG_(INFO) << "ExtBackupJsTest-end SUB_backup_ext_js_DoCallJsMethod_0100"; +} + +/** + * @tc.number: SUB_backup_ext_js_DoCallJsMethod_0200 + * @tc.name: SUB_backup_ext_js_DoCallJsMethod_0200 + * @tc.desc: 测试 DoCallJsMethod 各个分支成功与失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesIAFBOS + */ +HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_DoCallJsMethod_0200, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ExtBackupJsTest-begin SUB_backup_ext_js_DoCallJsMethod_0200"; + try { + string funcName = ""; + InputArgsParser argParserIn = {}; + ResultValueParser retParserIn = {}; + auto param = make_shared(funcName, nullptr, nullptr, argParserIn, retParserIn); + auto ref = make_shared(); + param->argParser = nullptr; + param->retParser = nullptr; + param->jsObj = ref.get(); + + int scope = 0; + napi_value value = nullptr; + param->jsRuntime = jsRuntime.get(); + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_open_handle_scope(_, _)).WillOnce( + DoAll(SetArgPointee(reinterpret_cast(&scope)), Return(napi_ok))); + EXPECT_CALL(*ref, GetNapiValue()).WillOnce(Return(reinterpret_cast(&value))); + EXPECT_CALL(*napiMock, napi_get_named_property(_, _, _, _)).WillOnce(Return(napi_invalid_arg)); + EXPECT_CALL(*napiMock, napi_close_handle_scope(_, _)).WillOnce(Return(napi_ok)); + auto ret = DoCallJsMethod(param.get()); + EXPECT_EQ(ret, EINVAL); + + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_open_handle_scope(_, _)).WillOnce( + DoAll(SetArgPointee(reinterpret_cast(&scope)), Return(napi_ok))); + EXPECT_CALL(*ref, GetNapiValue()).WillOnce(Return(reinterpret_cast(&value))); + EXPECT_CALL(*napiMock, napi_get_named_property(_, _, _, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_close_handle_scope(_, _)).WillOnce(Return(napi_ok)); + ret = DoCallJsMethod(param.get()); + EXPECT_EQ(ret, EINVAL); + + param->retParser = [](napi_env, napi_value){ return false; }; + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_open_handle_scope(_, _)).WillOnce( + DoAll(SetArgPointee(reinterpret_cast(&scope)), Return(napi_ok))); + EXPECT_CALL(*ref, GetNapiValue()).WillOnce(Return(reinterpret_cast(&value))); + EXPECT_CALL(*napiMock, napi_get_named_property(_, _, _, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_call_function(_, _, _, _, _, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_escape_handle(_, _, _, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_close_handle_scope(_, _)).WillOnce(Return(napi_ok)); + ret = DoCallJsMethod(param.get()); + EXPECT_EQ(ret, EINVAL); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ExtBackupJsTest-an exception occurred by DoCallJsMethod."; + } + GTEST_LOG_(INFO) << "ExtBackupJsTest-end SUB_backup_ext_js_DoCallJsMethod_0200"; +} + +/** + * @tc.number: SUB_backup_ext_js_DoCallJsMethod_0300 + * @tc.name: SUB_backup_ext_js_DoCallJsMethod_0300 + * @tc.desc: 测试 DoCallJsMethod 各个分支成功与失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesIAFBOS + */ +HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_DoCallJsMethod_0300, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ExtBackupJsTest-begin SUB_backup_ext_js_DoCallJsMethod_0300"; + try { + string funcName = ""; + InputArgsParser argParserIn = {}; + ResultValueParser retParserIn = {}; + auto param = make_shared(funcName, nullptr, nullptr, argParserIn, retParserIn); + auto ref = make_shared(); + param->argParser = nullptr; + param->retParser = nullptr; + param->jsObj = ref.get(); + + int scope = 0; + napi_value value = nullptr; + param->jsRuntime = jsRuntime.get(); + param->retParser = [](napi_env, napi_value){ return true; }; + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_open_handle_scope(_, _)).WillOnce( + DoAll(SetArgPointee(reinterpret_cast(&scope)), Return(napi_ok))); + EXPECT_CALL(*ref, GetNapiValue()).WillOnce(Return(reinterpret_cast(&value))); + EXPECT_CALL(*napiMock, napi_get_named_property(_, _, _, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_call_function(_, _, _, _, _, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_escape_handle(_, _, _, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_close_handle_scope(_, _)).WillOnce(Return(napi_ok)); + auto ret = DoCallJsMethod(param.get()); + EXPECT_EQ(ret, ERR_OK); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ExtBackupJsTest-an exception occurred by DoCallJsMethod."; + } + GTEST_LOG_(INFO) << "ExtBackupJsTest-end SUB_backup_ext_js_DoCallJsMethod_0300"; +} + +/** + * @tc.number: SUB_backup_ext_js_InvokeAppExtMethod_0100 + * @tc.name: SUB_backup_ext_js_InvokeAppExtMethod_0100 + * @tc.desc: 测试 InvokeAppExtMethod 各个分支成功与失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesIAFBOS + */ +HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_InvokeAppExtMethod_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ExtBackupJsTest-begin SUB_backup_ext_js_InvokeAppExtMethod_0100"; + try { + ErrCode errCode = BError(BError::Codes::OK); + string result = ""; + auto ret = extBackupJs->InvokeAppExtMethod(errCode, result); + EXPECT_EQ(ret, ERR_OK); + + result = "test"; + ret = extBackupJs->InvokeAppExtMethod(errCode, result); + EXPECT_EQ(ret, ERR_OK); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ExtBackupJsTest-an exception occurred by InvokeAppExtMethod."; + } + GTEST_LOG_(INFO) << "ExtBackupJsTest-end SUB_backup_ext_js_InvokeAppExtMethod_0100"; +} + +/** + * @tc.number: SUB_backup_ext_js_CallJsOnBackupEx_0100 + * @tc.name: SUB_backup_ext_js_CallJsOnBackupEx_0100 + * @tc.desc: 测试 CallJsOnBackupEx 各个分支成功与失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesIAFBOS + */ +HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_CallJsOnBackupEx_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ExtBackupJsTest-begin SUB_backup_ext_js_CallJsOnBackupEx_0100"; + try { + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_invalid_arg)); + auto ret = extBackupJs->CallJsOnBackupEx(); + EXPECT_EQ(ret, EINVAL); + + extBackupJs->callbackInfoEx_ = std::make_shared([](ErrCode, std::string){}); + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_is_exception_pending(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_get_value_string_utf8(_, _, _, _, _)).WillOnce(Return(napi_invalid_arg)); + EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(WithArgs<1>(Invoke([](uv_work_t* work) { + CallJsParam *param = reinterpret_cast(work->data); + param->retParser(nullptr, nullptr); + return -1; + }))); + ret = extBackupJs->CallJsOnBackupEx(); + EXPECT_EQ(ret, EINVAL); + + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_is_exception_pending(_, _)) + .WillOnce(DoAll(SetArgPointee(true), Return(napi_ok))); + EXPECT_CALL(*napiMock, napi_get_and_clear_last_exception(_, _)).WillOnce(Return(napi_invalid_arg)); + EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(WithArgs<1>(Invoke([](uv_work_t* work) { + CallJsParam *param = reinterpret_cast(work->data); + param->retParser(nullptr, nullptr); + return -1; + }))); + ret = extBackupJs->CallJsOnBackupEx(); + EXPECT_EQ(ret, EINVAL); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ExtBackupJsTest-an exception occurred by CallJsOnBackupEx."; + } + GTEST_LOG_(INFO) << "ExtBackupJsTest-end SUB_backup_ext_js_CallJsOnBackupEx_0100"; +} + +/** + * @tc.number: SUB_backup_ext_js_CallJsOnBackupEx_0200 + * @tc.name: SUB_backup_ext_js_CallJsOnBackupEx_0200 + * @tc.desc: 测试 CallJsOnBackupEx 各个分支成功与失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesIAFBOS + */ +HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_CallJsOnBackupEx_0200, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ExtBackupJsTest-begin SUB_backup_ext_js_CallJsOnBackupEx_0200"; + try { + extBackupJs->callbackInfoEx_ = std::make_shared([](ErrCode, std::string){}); + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_is_promise(_, _, _)) + .WillOnce(DoAll(SetArgPointee(true), Return(napi_ok))); + EXPECT_CALL(*napiMock, napi_open_handle_scope(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_close_handle_scope(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_get_named_property(_, _, _, _)).WillOnce(Return(napi_invalid_arg)); + EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(WithArgs<1>(Invoke([](uv_work_t* work) { + int value = 0; + CallJsParam *param = reinterpret_cast(work->data); + param->retParser(nullptr, reinterpret_cast(&value)); + return -1; + }))); + auto ret = extBackupJs->CallJsOnBackupEx(); + EXPECT_EQ(ret, EINVAL); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ExtBackupJsTest-an exception occurred by CallJsOnBackupEx."; + } + GTEST_LOG_(INFO) << "ExtBackupJsTest-end SUB_backup_ext_js_CallJsOnBackupEx_0200"; +} + +/** + * @tc.number: SUB_backup_ext_js_CallJsOnBackup_0100 + * @tc.name: SUB_backup_ext_js_CallJsOnBackup_0100 + * @tc.desc: 测试 CallJsOnBackup 各个分支成功与失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesIAFBOS + */ +HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_CallJsOnBackup_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ExtBackupJsTest-begin SUB_backup_ext_js_CallJsOnBackup_0100"; + try { + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_invalid_arg)); + auto ret = extBackupJs->CallJsOnBackup(); + EXPECT_EQ(ret, EINVAL); + + extBackupJs->callbackInfo_ = std::make_shared([](ErrCode, std::string){}); + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_is_exception_pending(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(WithArgs<1>(Invoke([](uv_work_t* work) { + CallJsParam *param = reinterpret_cast(work->data); + param->retParser(nullptr, nullptr); + return -1; + }))); + ret = extBackupJs->CallJsOnBackup(); + EXPECT_EQ(ret, EINVAL); + + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_is_exception_pending(_, _)) + .WillOnce(DoAll(SetArgPointee(true), Return(napi_ok))); + EXPECT_CALL(*napiMock, napi_get_and_clear_last_exception(_, _)).WillOnce(Return(napi_invalid_arg)); + EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(WithArgs<1>(Invoke([](uv_work_t* work) { + CallJsParam *param = reinterpret_cast(work->data); + param->retParser(nullptr, nullptr); + return -1; + }))); + ret = extBackupJs->CallJsOnBackup(); + EXPECT_EQ(ret, EINVAL); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ExtBackupJsTest-an exception occurred by CallJsOnBackup."; + } + GTEST_LOG_(INFO) << "ExtBackupJsTest-end SUB_backup_ext_js_CallJsOnBackup_0100"; +} + +/** + * @tc.number: SUB_backup_ext_js_CallJsOnBackup_0200 + * @tc.name: SUB_backup_ext_js_CallJsOnBackup_0200 + * @tc.desc: 测试 CallJsOnBackup 各个分支成功与失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesIAFBOS + */ +HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_CallJsOnBackup_0200, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ExtBackupJsTest-begin SUB_backup_ext_js_CallJsOnBackup_0200"; + try { + extBackupJs->callbackInfo_ = std::make_shared([](ErrCode, std::string){}); + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_is_promise(_, _, _)) + .WillOnce(DoAll(SetArgPointee(true), Return(napi_ok))); + EXPECT_CALL(*napiMock, napi_open_handle_scope(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_close_handle_scope(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_get_named_property(_, _, _, _)).WillOnce(Return(napi_invalid_arg)); + EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(WithArgs<1>(Invoke([](uv_work_t* work) { + int value = 0; + CallJsParam *param = reinterpret_cast(work->data); + param->retParser(nullptr, reinterpret_cast(&value)); + return -1; + }))); + auto ret = extBackupJs->CallJsOnBackup(); + EXPECT_EQ(ret, EINVAL); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ExtBackupJsTest-an exception occurred by CallJsOnBackup."; + } + GTEST_LOG_(INFO) << "ExtBackupJsTest-end SUB_backup_ext_js_CallJsOnBackup_0200"; +} + +/** + * @tc.number: SUB_backup_ext_js_CallJSRestoreEx_0100 + * @tc.name: SUB_backup_ext_js_CallJSRestoreEx_0100 + * @tc.desc: 测试 CallJSRestoreEx 各个分支成功与失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesIAFBOS + */ +HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_CallJSRestoreEx_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ExtBackupJsTest-begin SUB_backup_ext_js_CallJSRestoreEx_0100"; + try { + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_invalid_arg)); + auto ret = extBackupJs->CallJSRestoreEx(); + EXPECT_EQ(ret, EINVAL); + + extBackupJs->callbackInfoEx_ = std::make_shared([](ErrCode, std::string){}); + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_is_exception_pending(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_get_value_string_utf8(_, _, _, _, _)).WillOnce(Return(napi_invalid_arg)); + EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(WithArgs<1>(Invoke([](uv_work_t* work) { + CallJsParam *param = reinterpret_cast(work->data); + param->retParser(nullptr, nullptr); + return -1; + }))); + ret = extBackupJs->CallJSRestoreEx(); + EXPECT_EQ(ret, EINVAL); + + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_is_exception_pending(_, _)) + .WillOnce(DoAll(SetArgPointee(true), Return(napi_ok))); + EXPECT_CALL(*napiMock, napi_get_and_clear_last_exception(_, _)).WillOnce(Return(napi_invalid_arg)); + EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(WithArgs<1>(Invoke([](uv_work_t* work) { + CallJsParam *param = reinterpret_cast(work->data); + param->retParser(nullptr, nullptr); + return -1; + }))); + ret = extBackupJs->CallJSRestoreEx(); + EXPECT_EQ(ret, EINVAL); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ExtBackupJsTest-an exception occurred by CallJSRestoreEx."; + } + GTEST_LOG_(INFO) << "ExtBackupJsTest-end SUB_backup_ext_js_CallJSRestoreEx_0100"; +} + +/** + * @tc.number: SUB_backup_ext_js_CallJSRestoreEx_0200 + * @tc.name: SUB_backup_ext_js_CallJSRestoreEx_0200 + * @tc.desc: 测试 CallJSRestoreEx 各个分支成功与失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesIAFBOS + */ +HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_CallJSRestoreEx_0200, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ExtBackupJsTest-begin SUB_backup_ext_js_CallJSRestoreEx_0200"; + try { + extBackupJs->callbackInfoEx_ = std::make_shared([](ErrCode, std::string){}); + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_is_promise(_, _, _)) + .WillOnce(DoAll(SetArgPointee(true), Return(napi_ok))); + EXPECT_CALL(*napiMock, napi_open_handle_scope(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_close_handle_scope(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_get_named_property(_, _, _, _)).WillOnce(Return(napi_invalid_arg)); + EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(WithArgs<1>(Invoke([](uv_work_t* work) { + int value = 0; + CallJsParam *param = reinterpret_cast(work->data); + param->retParser(nullptr, reinterpret_cast(&value)); + return -1; + }))); + auto ret = extBackupJs->CallJSRestoreEx(); + EXPECT_EQ(ret, EINVAL); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ExtBackupJsTest-an exception occurred by CallJSRestoreEx."; + } + GTEST_LOG_(INFO) << "ExtBackupJsTest-end SUB_backup_ext_js_CallJSRestoreEx_0200"; +} + +/** + * @tc.number: SUB_backup_ext_js_CallJSRestore_0100 + * @tc.name: SUB_backup_ext_js_CallJSRestore_0100 + * @tc.desc: 测试 CallJSRestore 各个分支成功与失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesIAFBOS + */ +HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_CallJSRestore_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ExtBackupJsTest-begin SUB_backup_ext_js_CallJSRestore_0100"; + try { + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_invalid_arg)); + auto ret = extBackupJs->CallJSRestore(); + EXPECT_EQ(ret, EINVAL); + + extBackupJs->callbackInfo_ = std::make_shared([](ErrCode, std::string){}); + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_is_exception_pending(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(WithArgs<1>(Invoke([](uv_work_t* work) { + CallJsParam *param = reinterpret_cast(work->data); + param->retParser(nullptr, nullptr); + return -1; + }))); + ret = extBackupJs->CallJSRestore(); + EXPECT_EQ(ret, EINVAL); + + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_is_exception_pending(_, _)) + .WillOnce(DoAll(SetArgPointee(true), Return(napi_ok))); + EXPECT_CALL(*napiMock, napi_get_and_clear_last_exception(_, _)).WillOnce(Return(napi_invalid_arg)); + EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(WithArgs<1>(Invoke([](uv_work_t* work) { + CallJsParam *param = reinterpret_cast(work->data); + param->retParser(nullptr, nullptr); + return -1; + }))); + ret = extBackupJs->CallJSRestore(); + EXPECT_EQ(ret, EINVAL); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ExtBackupJsTest-an exception occurred by CallJSRestore."; + } + GTEST_LOG_(INFO) << "ExtBackupJsTest-end SUB_backup_ext_js_CallJSRestore_0100"; +} + +/** + * @tc.number: SUB_backup_ext_js_CallJSRestore_0200 + * @tc.name: SUB_backup_ext_js_CallJSRestore_0200 + * @tc.desc: 测试 CallJSRestore 各个分支成功与失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesIAFBOS + */ +HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_CallJSRestore_0200, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ExtBackupJsTest-begin SUB_backup_ext_js_CallJSRestore_0200"; + try { + extBackupJs->callbackInfo_ = std::make_shared([](ErrCode, std::string){}); + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_is_promise(_, _, _)) + .WillOnce(DoAll(SetArgPointee(true), Return(napi_ok))); + EXPECT_CALL(*napiMock, napi_open_handle_scope(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_close_handle_scope(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_get_named_property(_, _, _, _)).WillOnce(Return(napi_invalid_arg)); + EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(WithArgs<1>(Invoke([](uv_work_t* work) { + int value = 0; + CallJsParam *param = reinterpret_cast(work->data); + param->retParser(nullptr, reinterpret_cast(&value)); + return -1; + }))); + auto ret = extBackupJs->CallJSRestore(); + EXPECT_EQ(ret, EINVAL); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ExtBackupJsTest-an exception occurred by CallJSRestore."; + } + GTEST_LOG_(INFO) << "ExtBackupJsTest-end SUB_backup_ext_js_CallJSRestore_0200"; +} + +/** + * @tc.number: SUB_backup_ext_js_GetBackupInfo_0100 + * @tc.name: SUB_backup_ext_js_GetBackupInfo_0100 + * @tc.desc: 测试 GetBackupInfo 各个分支成功与失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesIAFBOS + */ +HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_GetBackupInfo_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ExtBackupJsTest-begin SUB_backup_ext_js_GetBackupInfo_0100"; + try { + extBackupJs->jsObj_ = make_unique(); + EXPECT_CALL(*napiMock, napi_is_exception_pending(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_invalid_arg)); + auto ret = extBackupJs->GetBackupInfo([](ErrCode, std::string){}); + EXPECT_EQ(ret, EINVAL); + + EXPECT_CALL(*napiMock, napi_is_exception_pending(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_get_value_string_utf8(_, _, _, _, _)).WillOnce(Return(napi_invalid_arg)); + EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(WithArgs<1>(Invoke([](uv_work_t* work) { + CallJsParam *param = reinterpret_cast(work->data); + param->retParser(nullptr, nullptr); + return -1; + }))); + ret = extBackupJs->GetBackupInfo([](ErrCode, std::string){}); + EXPECT_EQ(ret, EINVAL); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ExtBackupJsTest-an exception occurred by GetBackupInfo."; + } + GTEST_LOG_(INFO) << "ExtBackupJsTest-end SUB_backup_ext_js_GetBackupInfo_0100"; +} + +/** + * @tc.number: SUB_backup_ext_js_GetBackupInfo_0200 + * @tc.name: SUB_backup_ext_js_GetBackupInfo_0200 + * @tc.desc: 测试 GetBackupInfo 各个分支成功与失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesIAFBOS + */ +HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_GetBackupInfo_0200, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ExtBackupJsTest-begin SUB_backup_ext_js_GetBackupInfo_0200"; + try { + extBackupJs->jsObj_ = make_unique(); + EXPECT_CALL(*napiMock, napi_is_exception_pending(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_get_value_string_utf8(_, _, _, _, _)).WillOnce(Return(napi_ok)) + .WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(WithArgs<1>(Invoke([](uv_work_t* work) { + CallJsParam *param = reinterpret_cast(work->data); + param->retParser(nullptr, nullptr); + return -1; + }))); + auto ret = extBackupJs->GetBackupInfo([](ErrCode, std::string){}); + EXPECT_EQ(ret, EINVAL); + + EXPECT_CALL(*napiMock, napi_is_exception_pending(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*extBackupMock, GetNapiEnv()).WillOnce(Return(nullptr)).WillOnce(Return(nullptr)); + EXPECT_CALL(*napiMock, napi_get_uv_event_loop(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_is_promise(_, _, _)) + .WillOnce(DoAll(SetArgPointee(true), Return(napi_ok))); + EXPECT_CALL(*napiMock, napi_open_handle_scope(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_close_handle_scope(_, _)).WillOnce(Return(napi_ok)); + EXPECT_CALL(*napiMock, napi_get_named_property(_, _, _, _)).WillOnce(Return(napi_invalid_arg)); + EXPECT_CALL(*napiMock, uv_queue_work(_, _, _, _)).WillOnce(WithArgs<1>(Invoke([](uv_work_t* work) { + int value = 0; + CallJsParam *param = reinterpret_cast(work->data); + param->retParser(nullptr, reinterpret_cast(&value)); + return -1; + }))); + ret = extBackupJs->GetBackupInfo([](ErrCode, std::string){}); + EXPECT_EQ(ret, EINVAL); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ExtBackupJsTest-an exception occurred by GetBackupInfo."; + } + GTEST_LOG_(INFO) << "ExtBackupJsTest-end SUB_backup_ext_js_GetBackupInfo_0200"; +} + +/** + * @tc.number: SUB_backup_ext_js_InitTempPath_0100 + * @tc.name: SUB_backup_ext_js_InitTempPath_0100 + * @tc.desc: 测试 InitTempPath 各个分支成功与失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesIAFBOS + */ +HWTEST_F(ExtBackupJsTest, SUB_backup_ext_js_InitTempPath_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ExtBackupJsTest-begin SUB_backup_ext_js_InitTempPath_0100"; + try { + std::string el2BackupDir(BConstants::PATH_BUNDLE_BACKUP_HOME); + int ret = access(el2BackupDir.c_str(), F_OK); + EXPECT_TRUE(ret != F_OK); + std::string el1BackupDir(BConstants::PATH_BUNDLE_BACKUP_HOME_EL1); + ret = access(el1BackupDir.c_str(), F_OK); + EXPECT_TRUE(ret != F_OK); + std::string bundleName = "testBundleName"; + extBackupJs->InitTempPath(bundleName); + ret = access(el2BackupDir.c_str(), F_OK); + EXPECT_EQ(ret, F_OK); + ret = access(el1BackupDir.c_str(), F_OK); + EXPECT_EQ(ret, F_OK); + std::string el2RootPath = BConstants::BACKUP_DIR_PRE + BConstants::CONTEXT_ELS[0]; // 0: {"el1", "el2"}中的el1 + std::string el1RootPath = BConstants::BACKUP_DIR_PRE + BConstants::CONTEXT_ELS[1]; // 1: {"el1", "el2"}中的el2 + ForceRemoveDirectoryBMS(el2RootPath); + ForceRemoveDirectoryBMS(el1RootPath); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ExtBackupJsTest-an exception occurred by OnProcess."; + } + GTEST_LOG_(INFO) << "ExtBackupJsTest-end SUB_backup_ext_js_InitTempPath_0100"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_ext/ext_extension_stub_test.cpp b/tests/unittests/backup_ext/ext_extension_stub_test.cpp index 413212265d6d6ff246ebc15e8eb3b9e4c1ee673a..8755506fc2e192586689373755a52d2f0f756586 100644 --- a/tests/unittests/backup_ext/ext_extension_stub_test.cpp +++ b/tests/unittests/backup_ext/ext_extension_stub_test.cpp @@ -28,16 +28,17 @@ class ExtExtensionStubMock : public ExtExtensionStub { public: MOCK_METHOD(UniqueFd, GetFileHandle, (const std::string &fileName, int32_t &errCode)); MOCK_METHOD(ErrCode, HandleClear, ()); - MOCK_METHOD(ErrCode, HandleBackup, ()); + MOCK_METHOD(ErrCode, HandleBackup, (bool isClearData)); MOCK_METHOD(ErrCode, PublishFile, (const std::string &fileName)); - MOCK_METHOD(ErrCode, HandleRestore, ()); + MOCK_METHOD(ErrCode, HandleRestore, (bool isClearData)); MOCK_METHOD(ErrCode, GetIncrementalFileHandle, (const std::string &fileName)); MOCK_METHOD(ErrCode, PublishIncrementalFile, (const std::string &fileName)); MOCK_METHOD(ErrCode, HandleIncrementalBackup, (UniqueFd incrementalFd, UniqueFd manifestFd)); - MOCK_METHOD(ErrCode, IncrementalOnBackup, ()); + MOCK_METHOD(ErrCode, IncrementalOnBackup, (bool isClearData)); MOCK_METHOD((std::tuple), GetIncrementalBackupFileHandle, ()); MOCK_METHOD(ErrCode, GetBackupInfo, (std::string &result)); MOCK_METHOD(ErrCode, UpdateFdSendRate, (std::string &bundleName, int32_t sendRate)); + MOCK_METHOD(ErrCode, User0OnBackup, ()); }; class ExtExtensionStubTest : public testing::Test { @@ -201,13 +202,13 @@ HWTEST_F(ExtExtensionStubTest, SUB_backup_ext_ExtExtensionStub_CmdHandleBackup_0 try { MessageParcel data; MessageParcel reply; - EXPECT_CALL(*stub, HandleBackup()).WillOnce(Return(0)); + EXPECT_CALL(*stub, HandleBackup(_)).WillOnce(Return(0)); EXPECT_CALL(*messageParcelMock, WriteInt32(_)).WillOnce(Return(false)); EXPECT_TRUE(stub != nullptr); auto err = stub->CmdHandleBackup(data, reply); EXPECT_EQ(err, BError(BError::Codes::EXT_BROKEN_IPC)); - EXPECT_CALL(*stub, HandleBackup()).WillOnce(Return(0)); + EXPECT_CALL(*stub, HandleBackup(_)).WillOnce(Return(0)); EXPECT_CALL(*messageParcelMock, WriteInt32(_)).WillOnce(Return(true)); err = stub->CmdHandleBackup(data, reply); EXPECT_EQ(err, BError(BError::Codes::OK)); @@ -271,13 +272,13 @@ HWTEST_F(ExtExtensionStubTest, SUB_backup_ext_ExtExtensionStub_CmdHandleRestore_ try { MessageParcel data; MessageParcel reply; - EXPECT_CALL(*stub, HandleRestore()).WillOnce(Return(0)); + EXPECT_CALL(*stub, HandleRestore(_)).WillOnce(Return(0)); EXPECT_CALL(*messageParcelMock, WriteInt32(_)).WillOnce(Return(false)); EXPECT_TRUE(stub != nullptr); auto err = stub->CmdHandleRestore(data, reply); EXPECT_EQ(err, BError(BError::Codes::EXT_BROKEN_IPC)); - EXPECT_CALL(*stub, HandleRestore()).WillOnce(Return(0)); + EXPECT_CALL(*stub, HandleRestore(_)).WillOnce(Return(0)); EXPECT_CALL(*messageParcelMock, WriteInt32(_)).WillOnce(Return(true)); err = stub->CmdHandleRestore(data, reply); EXPECT_EQ(err, BError(BError::Codes::OK)); @@ -417,13 +418,13 @@ HWTEST_F(ExtExtensionStubTest, SUB_backup_ext_ExtExtensionStub_CmdIncrementalOnB try { MessageParcel data; MessageParcel reply; - EXPECT_CALL(*stub, IncrementalOnBackup()).WillOnce(Return(0)); + EXPECT_CALL(*stub, IncrementalOnBackup(_)).WillOnce(Return(0)); EXPECT_CALL(*messageParcelMock, WriteInt32(_)).WillOnce(Return(false)); EXPECT_TRUE(stub != nullptr); auto err = stub->CmdIncrementalOnBackup(data, reply); EXPECT_EQ(err, BError(BError::Codes::EXT_BROKEN_IPC)); - EXPECT_CALL(*stub, IncrementalOnBackup()).WillOnce(Return(0)); + EXPECT_CALL(*stub, IncrementalOnBackup(_)).WillOnce(Return(0)); EXPECT_CALL(*messageParcelMock, WriteInt32(_)).WillOnce(Return(true)); err = stub->CmdIncrementalOnBackup(data, reply); EXPECT_EQ(err, BError(BError::Codes::OK)); @@ -560,4 +561,36 @@ HWTEST_F(ExtExtensionStubTest, SUB_backup_ext_ExtExtensionStub_CmdUpdateSendRate } GTEST_LOG_(INFO) << "ExtExtensionStubTest-end SUB_backup_ext_ExtExtensionStub_CmdUpdateSendRate_0100"; } + +/** + * @tc.number: SUB_backup_ext_ExtExtensionStub_CmdUser0_0100 + * @tc.name: SUB_backup_ext_ExtExtensionStub_CmdUser0_0100 + * @tc.desc: 测试 CmdHandleUser0Backup 各个分支成功与失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issues + */ +HWTEST_F(ExtExtensionStubTest, SUB_backup_ext_ExtExtensionStub_CmdUser0_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ExtExtensionStubTest-begin SUB_backup_ext_ExtExtensionStub_CmdUser0_0100"; + try { + MessageParcel data; + MessageParcel reply; + EXPECT_CALL(*stub, User0OnBackup()).WillOnce(Return(0)); + EXPECT_CALL(*messageParcelMock, WriteInt32(_)).WillOnce(Return(false)); + EXPECT_TRUE(stub != nullptr); + auto err = stub->CmdHandleUser0Backup(data, reply); + EXPECT_EQ(err, BError(BError::Codes::EXT_BROKEN_IPC)); + + EXPECT_CALL(*stub, User0OnBackup()).WillOnce(Return(0)); + EXPECT_CALL(*messageParcelMock, WriteInt32(_)).WillOnce(Return(true)); + err = stub->CmdHandleUser0Backup(data, reply); + EXPECT_EQ(err, BError(BError::Codes::OK)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ExtExtensionStubTest-an exception occurred by CmdHandleClear."; + } + GTEST_LOG_(INFO) << "ExtExtensionStubTest-end SUB_backup_ext_ExtExtensionStub_CmdUser0_0100"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_ext/ext_extension_test.cpp b/tests/unittests/backup_ext/ext_extension_test.cpp index 7022e5e1da5aab3bdfc3eb206fba65b49058e361..993b7173dfc7ebf038346188b82265d558c98cc5 100644 --- a/tests/unittests/backup_ext/ext_extension_test.cpp +++ b/tests/unittests/backup_ext/ext_extension_test.cpp @@ -27,6 +27,7 @@ #include "b_error/b_error.h" #include "b_error/b_excep_utils.h" #include "ext_extension.cpp" +#include "sub_ext_extension.cpp" namespace OHOS::FileManagement::Backup { using namespace std; @@ -153,8 +154,10 @@ HWTEST_F(ExtExtensionTest, Ext_Extension_Test_0300, testing::ext::TestSize.Level try { string tarFile = " "; vector extManageInfo; - bool ret = IsUserTar(tarFile, extManageInfo); + off_t tarFileSize = 0; + bool ret = IsUserTar(tarFile, extManageInfo, tarFileSize); EXPECT_FALSE(ret); + EXPECT_TRUE(tarFileSize == 0); } catch (...) { EXPECT_TRUE(false); GTEST_LOG_(INFO) << "ExtExtensionTest-an exception occurred by construction."; @@ -177,8 +180,10 @@ HWTEST_F(ExtExtensionTest, Ext_Extension_Test_0301, testing::ext::TestSize.Level try { string tarFile = TAR_FILE; vector extManageInfo; - bool ret = IsUserTar(tarFile, extManageInfo); + off_t tarFileSize = 0; + bool ret = IsUserTar(tarFile, extManageInfo, tarFileSize); EXPECT_FALSE(ret); + EXPECT_TRUE(tarFileSize == 0); } catch (...) { EXPECT_TRUE(false); GTEST_LOG_(INFO) << "ExtExtensionTest-an exception occurred by construction."; @@ -204,9 +209,12 @@ HWTEST_F(ExtExtensionTest, Ext_Extension_Test_0302, testing::ext::TestSize.Level ExtManageInfo info; info.hashName = TAR_FILE; info.isUserTar = true; + info.sta.st_size = 1; // 1: test number; extManageInfo.push_back(info); - bool ret = IsUserTar(tarFile, extManageInfo); + off_t tarFileSize = 0; + bool ret = IsUserTar(tarFile, extManageInfo, tarFileSize); EXPECT_TRUE(ret); + EXPECT_TRUE(tarFileSize == 1); } catch (...) { EXPECT_TRUE(false); GTEST_LOG_(INFO) << "ExtExtensionTest-an exception occurred by construction."; diff --git a/tests/unittests/backup_ext/tar_file_test.cpp b/tests/unittests/backup_ext/tar_file_test.cpp index 5e8b37785a8742121528012e60a2a9bed153cb9d..b1848785f77403d2691fd5dad90003d807218327 100644 --- a/tests/unittests/backup_ext/tar_file_test.cpp +++ b/tests/unittests/backup_ext/tar_file_test.cpp @@ -101,7 +101,17 @@ HWTEST_F(TarFileTest, SUB_Tar_File_Packet_0100, testing::ext::TestSize.Level1) string tarFileName = ""; string pkPath = ""; TarMap tarMap; - bool ret = TarFile::GetInstance().Packet(srcFiles, tarFileName, pkPath, tarMap); + auto reportCb = [](std::string path, int err) { + return; + }; + bool ret = TarFile::GetInstance().Packet(srcFiles, tarFileName, pkPath, tarMap, reportCb); + EXPECT_TRUE(tarMap.empty()); + EXPECT_FALSE(ret); + + TestManager tm("SUB_Tar_File_Packet_0100"); + string root = tm.GetRootDirCurTest(); + pkPath = root; + ret = TarFile::GetInstance().Packet(srcFiles, tarFileName, pkPath, tarMap, reportCb); EXPECT_TRUE(tarMap.empty()); EXPECT_FALSE(ret); } catch (...) { @@ -136,7 +146,10 @@ HWTEST_F(TarFileTest, SUB_Tar_File_Packet_0200, testing::ext::TestSize.Level1) TarMap tarMap; string tarFileName = "part"; string pkPath = root; - bool ret = TarFile::GetInstance().Packet(srcFiles, tarFileName, pkPath, tarMap); + auto reportCb = [](std::string path, int err) { + return; + }; + bool ret = TarFile::GetInstance().Packet(srcFiles, tarFileName, pkPath, tarMap, reportCb); EXPECT_TRUE(ret); EXPECT_EQ(tarMap.size(), 1); ClearCache(); @@ -172,7 +185,10 @@ HWTEST_F(TarFileTest, SUB_Tar_File_Packet_0300, testing::ext::TestSize.Level1) string pkPath = root; string tarFileName = "part"; TarMap tarMap; - bool ret = TarFile::GetInstance().Packet(srcFiles, tarFileName, pkPath, tarMap); + auto reportCb = [](std::string path, int err) { + return; + }; + bool ret = TarFile::GetInstance().Packet(srcFiles, tarFileName, pkPath, tarMap, reportCb); EXPECT_TRUE(ret); EXPECT_EQ(tarMap.size(), 1); ClearCache(); @@ -200,7 +216,10 @@ HWTEST_F(TarFileTest, SUB_Tar_File_Packet_0400, testing::ext::TestSize.Level1) string tarFileName = "part"; string pkPath = "/data/storage/el2/backup/backup"; TarMap tarMap; - bool ret = TarFile::GetInstance().Packet(srcFiles, tarFileName, pkPath, tarMap); + auto reportCb = [](std::string path, int err) { + return; + }; + bool ret = TarFile::GetInstance().Packet(srcFiles, tarFileName, pkPath, tarMap, reportCb); EXPECT_FALSE(ret); EXPECT_TRUE(tarMap.empty()); } catch (...) { @@ -241,7 +260,10 @@ HWTEST_F(TarFileTest, SUB_Tar_File_Packet_0500, testing::ext::TestSize.Level1) string tarFileName = "part"; string pkPath = root; TarMap tarMap; - bool ret = TarFile::GetInstance().Packet(srcFiles, tarFileName, pkPath, tarMap); + auto reportCb = [](std::string path, int err) { + return; + }; + bool ret = TarFile::GetInstance().Packet(srcFiles, tarFileName, pkPath, tarMap, reportCb); EXPECT_TRUE(ret); EXPECT_EQ(tarMap.size(), 1); ClearCache(); @@ -284,7 +306,10 @@ HWTEST_F(TarFileTest, SUB_Tar_File_Packet_0600, testing::ext::TestSize.Level1) TarMap tarMap; string tarFileName = "part"; string pkPath = root; - bool ret = TarFile::GetInstance().Packet(srcFiles, tarFileName, pkPath, tarMap); + auto reportCb = [](std::string path, int err) { + return; + }; + bool ret = TarFile::GetInstance().Packet(srcFiles, tarFileName, pkPath, tarMap, reportCb); EXPECT_TRUE(ret); EXPECT_EQ(tarMap.size(), 2); ClearCache(); @@ -332,7 +357,10 @@ HWTEST_F(TarFileTest, SUB_Tar_File_Packet_0700, testing::ext::TestSize.Level1) string tarFileName = "part"; string pkPath = root; TarMap tarMap; - bool ret = TarFile::GetInstance().Packet(srcFiles, tarFileName, pkPath, tarMap); + auto reportCb = [](std::string path, int err) { + return; + }; + bool ret = TarFile::GetInstance().Packet(srcFiles, tarFileName, pkPath, tarMap, reportCb); EXPECT_TRUE(ret); EXPECT_EQ(tarMap.size(), 2); ClearCache(); diff --git a/tests/unittests/backup_ext/untar_file_sup_test.cpp b/tests/unittests/backup_ext/untar_file_sup_test.cpp new file mode 100644 index 0000000000000000000000000000000000000000..7f3ad347156fffd55167a1f79064bd5af7a19c1c --- /dev/null +++ b/tests/unittests/backup_ext/untar_file_sup_test.cpp @@ -0,0 +1,269 @@ +/* + * Copyright (c) 2024 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include +#include + +#include "b_error/b_error.h" +#include "file_ex.h" +#include "library_func_mock.h" +#include "test_manager.h" +#include "untar_file.cpp" + + +namespace OHOS::FileManagement::Backup { +using namespace std; +using namespace testing; +using namespace OHOS::AppFileService; +class UntarFileSupTest : public testing::Test { +public: + static void SetUpTestCase(void); + static void TearDownTestCase(); + void SetUp() override {}; + void TearDown() override {}; + static inline shared_ptr funcMock = nullptr; +}; + +static void ClearCache() +{ + UntarFile::GetInstance().rootPath_.clear(); + UntarFile::GetInstance().tarFileSize_ = 0; + UntarFile::GetInstance().tarFileBlockCnt_ = 0; + UntarFile::GetInstance().pos_ = 0; + UntarFile::GetInstance().readCnt_ = 0; + if (UntarFile::GetInstance().tarFilePtr_ != nullptr) { + fclose(UntarFile::GetInstance().tarFilePtr_); + UntarFile::GetInstance().tarFilePtr_ = nullptr; + } + TarFile::GetInstance().fileCount_ = 0; + TarFile::GetInstance().tarMap_.clear(); + TarFile::GetInstance().rootPath_.clear(); + TarFile::GetInstance().packagePath_.clear(); + TarFile::GetInstance().baseTarName_.clear(); + TarFile::GetInstance().tarFileName_.clear(); + TarFile::GetInstance().ioBuffer_.clear(); + TarFile::GetInstance().currentTarName_.clear(); + TarFile::GetInstance().currentTarFileSize_ = 0; + TarFile::GetInstance().tarFileCount_ = 0; + TarFile::GetInstance().currentFileName_.clear(); + if (TarFile::GetInstance().currentTarFile_ != nullptr) { + fclose(TarFile::GetInstance().currentTarFile_); + TarFile::GetInstance().currentTarFile_ = nullptr; + } +} + +void UntarFileSupTest::SetUpTestCase(void) +{ + GTEST_LOG_(INFO) << "SetUpTestCase enter"; + funcMock = make_shared(); + LibraryFuncMock::libraryFunc_ = funcMock; +} + +void UntarFileSupTest::TearDownTestCase() +{ + GTEST_LOG_(INFO) << "TearDownTestCase enter"; + LibraryFuncMock::libraryFunc_ = nullptr; + funcMock = nullptr; + ClearCache(); +} + +/** + * @tc.number: SUB_Untar_File_IsEmptyBlock_0100 + * @tc.name: SUB_Untar_File_IsEmptyBlock_0100 + * @tc.desc: 测试 IsEmptyBlock + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(UntarFileSupTest, SUB_Untar_File_IsEmptyBlock_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "UntarFileSupTest-begin SUB_Untar_File_IsEmptyBlock_0100"; + try { + EXPECT_EQ(IsEmptyBlock(nullptr), true); + char buff[BLOCK_SIZE] = {0}; + EXPECT_EQ(IsEmptyBlock(buff), true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "UntarFileSupTest-an exception occurred by IsEmptyBlock."; + } + GTEST_LOG_(INFO) << "UntarFileSupTest-end SUB_Untar_File_IsEmptyBlock_0100"; +} + +/** + * @tc.number: SUB_Untar_File_ParseOctalStr_0100 + * @tc.name: SUB_Untar_File_ParseOctalStr_0100 + * @tc.desc: 测试 ParseOctalStr 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(UntarFileSupTest, SUB_Untar_File_ParseOctalStr_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "UntarFileSupTest-begin SUB_Untar_File_ParseOctalStr_0100"; + EXPECT_EQ(ParseOctalStr("0", 0), 0); + EXPECT_EQ(ParseOctalStr("1234", 0), 0); + EXPECT_EQ(ParseOctalStr("()-891234", 10), 668); + GTEST_LOG_(INFO) << "UntarFileSupTest-end SUB_Untar_File_ParseOctalStr_0100"; +} + +/** + * @tc.number: SUB_Untar_File_GenRealPath_0100 + * @tc.name: SUB_Untar_File_GenRealPath_0100 + * @tc.desc: 测试 GenRealPath 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(UntarFileSupTest, SUB_Untar_File_GenRealPath_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "UntarFileSupTest-begin SUB_Untar_File_GenRealPath_0100"; + string rootPath = ""; + string realName = ""; + EXPECT_EQ(UntarFile::GetInstance().GenRealPath(rootPath, realName), ""); + + rootPath = "rootPath"; + EXPECT_EQ(UntarFile::GetInstance().GenRealPath(rootPath, realName), ""); + + realName = "realName"; + EXPECT_EQ(UntarFile::GetInstance().GenRealPath(rootPath, realName), "rootPath/realName"); + + rootPath = "/rootPath/"; + realName = "/realName"; + EXPECT_EQ(UntarFile::GetInstance().GenRealPath(rootPath, realName), "rootPath/realName"); + GTEST_LOG_(INFO) << "UntarFileSupTest-end SUB_Untar_File_GenRealPath_0100"; +} + +/** + * @tc.number: SUB_Untar_File_ForceCreateDirectoryWithMode_0100 + * @tc.name: SUB_Untar_File_ForceCreateDirectoryWithMode_0100 + * @tc.desc: 测试 ForceCreateDirectoryWithMode 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(UntarFileSupTest, SUB_Untar_File_ForceCreateDirectoryWithMode_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "UntarFileSupTest-begin SUB_Untar_File_ForceCreateDirectoryWithMode_0100"; + string rootPath = "rootPath/realName"; + EXPECT_CALL(*funcMock, access(_, _)).WillOnce(Return(1)); + EXPECT_CALL(*funcMock, mkdir(_, _)).WillOnce(Return(1)); + EXPECT_EQ(ForceCreateDirectoryWithMode(rootPath, S_IRWXU), false); + + EXPECT_CALL(*funcMock, access(_, _)).WillOnce(Return(0)).WillOnce(Return(1)).WillOnce(Return(0)); + EXPECT_CALL(*funcMock, mkdir(_, _)).WillOnce(Return(0)); + EXPECT_EQ(ForceCreateDirectoryWithMode(rootPath, S_IRWXU), true); + + EXPECT_CALL(*funcMock, access(_, _)).WillOnce(Return(0)).WillOnce(Return(1)).WillOnce(Return(1)); + EXPECT_CALL(*funcMock, mkdir(_, _)).WillOnce(Return(0)); + EXPECT_EQ(ForceCreateDirectoryWithMode(rootPath, S_IRWXU), false); + GTEST_LOG_(INFO) << "UntarFileSupTest-end SUB_Untar_File_ParseOctalStr_0100"; +} + +/** + * @tc.number: SUB_Untar_File_CreateDir_0100 + * @tc.name: SUB_Untar_File_CreateDir_0100 + * @tc.desc: 测试 CreateDir 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(UntarFileSupTest, SUB_Untar_File_CreateDir_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "UntarFileSupTest-begin SUB_Untar_File_CreateDir_0100"; + string rootPath = ""; + try { + UntarFile::GetInstance().CreateDir(rootPath, S_IRWXU); + rootPath = "rootPath/realName"; + EXPECT_CALL(*funcMock, access(_, _)).WillOnce(Return(0)); + UntarFile::GetInstance().CreateDir(rootPath, S_IRWXU); + + rootPath = "rootPath/realName"; + EXPECT_CALL(*funcMock, access(_, _)).WillOnce(Return(1)).WillOnce(Return(0)) + .WillOnce(Return(1)).WillOnce(Return(0)); + EXPECT_CALL(*funcMock, mkdir(_, _)).WillOnce(Return(0)); + UntarFile::GetInstance().CreateDir(rootPath, S_IRWXU); + + EXPECT_CALL(*funcMock, access(_, _)).WillOnce(Return(1)).WillOnce(Return(0)) + .WillOnce(Return(1)).WillOnce(Return(1)); + EXPECT_CALL(*funcMock, mkdir(_, _)).WillOnce(Return(0)); + UntarFile::GetInstance().CreateDir(rootPath, S_IRWXU); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "UntarFileSupTest-an exception occurred by CreateDir."; + } + GTEST_LOG_(INFO) << "UntarFileSupTest-end SUB_Untar_File_CreateDir_0100"; +} + +/** + * @tc.number: SUB_Untar_File_ParseFileByTypeFlag_0100 + * @tc.name: SUB_Untar_File_ParseFileByTypeFlag_0100 + * @tc.desc: 测试 ParseFileByTypeFlag 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(UntarFileSupTest, SUB_Untar_File_ParseFileByTypeFlag_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "UntarFileSupTest-begin SUB_Untar_File_CreateDir_0100"; + FileStatInfo info; + info.fullPath = "realName"; + UntarFile::GetInstance().rootPath_ = "rootPath"; + try { + UntarFile::GetInstance().ParseFileByTypeFlag(SYMTYPE, info); + + EXPECT_CALL(*funcMock, access(_, _)).WillOnce(Return(1)).WillOnce(Return(0)) + .WillOnce(Return(1)).WillOnce(Return(0)); + EXPECT_CALL(*funcMock, mkdir(_, _)).WillOnce(Return(0)); + UntarFile::GetInstance().ParseFileByTypeFlag(DIRTYPE, info); + EXPECT_EQ(info.fullPath, "rootPath/realName"); + + EXPECT_CALL(*funcMock, fseeko(_, _, _)).WillOnce(Return(0)); + UntarFile::GetInstance().ParseFileByTypeFlag('6', info); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "UntarFileSupTest-an exception occurred by ParseFileByTypeFlag."; + } + GTEST_LOG_(INFO) << "UntarFileSupTest-end SUB_Untar_File_CreateDir_0100"; +} + +/** + * @tc.number: SUB_Untar_File_IsValidTarBlock_0100 + * @tc.name: SUB_Untar_File_IsValidTarBlock_0100 + * @tc.desc: 测试 IsValidTarBlock 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(UntarFileSupTest, SUB_Untar_File_IsValidTarBlock_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "UntarFileSupTest-begin SUB_Untar_File_IsValidTarBlock_0100"; + TarHeader header { .magic = "test" }; + try { + EXPECT_EQ(UntarFile::GetInstance().IsValidTarBlock(header), false); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "UntarFileSupTest-an exception occurred by IsValidTarBlock."; + } + GTEST_LOG_(INFO) << "UntarFileSupTest-end SUB_Untar_File_IsValidTarBlock_0100"; +} +} // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_ext/untar_file_test.cpp b/tests/unittests/backup_ext/untar_file_test.cpp index 9d79edb4336287416495fbf9d409c6976fc1ffe8..f67ba503d2e56d996fa801bc22cf0c5cd57abc2e 100644 --- a/tests/unittests/backup_ext/untar_file_test.cpp +++ b/tests/unittests/backup_ext/untar_file_test.cpp @@ -108,7 +108,7 @@ HWTEST_F(UntarFileTest, SUB_Untar_File_UnPacket_0100, testing::ext::TestSize.Lev try { string tarFile(""); string rootPath(""); - int ret = UntarFile::GetInstance().UnPacket(tarFile, rootPath); + auto [ret, fileInfos, errFileInfos] = UntarFile::GetInstance().UnPacket(tarFile, rootPath); EXPECT_EQ(ret, ENOENT); ClearCache(); } catch (...) { @@ -151,7 +151,7 @@ HWTEST_F(UntarFileTest, SUB_Untar_File_UnPacket_0200, testing::ext::TestSize.Lev GTEST_LOG_(INFO) << " execute tar failure, errno :" << errno; throw BError(errno); } - int ret = UntarFile::GetInstance().UnPacket(tarFile, rootPath); + auto [ret, fileInfos, errFileInfos] = UntarFile::GetInstance().UnPacket(tarFile, rootPath); EXPECT_EQ(ret, 0); ClearCache(); } catch (...) { @@ -186,7 +186,7 @@ HWTEST_F(UntarFileTest, SUB_Untar_File_UnPacket_0300, testing::ext::TestSize.Lev SaveStringToFile(aFile, "hello"); string rootPath(root); - int ret = UntarFile::GetInstance().UnPacket(aFile, rootPath); + auto [ret, fileInfos, errFileInfos] = UntarFile::GetInstance().UnPacket(aFile, rootPath); EXPECT_EQ(ret, 0); ClearCache(); } catch (...) { @@ -225,7 +225,7 @@ HWTEST_F(UntarFileTest, SUB_Untar_File_UnPacket_0400, testing::ext::TestSize.Lev } string rootPath(root); - int ret = UntarFile::GetInstance().UnPacket(tarFile, rootPath); + auto [ret, fileInfos, errFileInfos] = UntarFile::GetInstance().UnPacket(tarFile, rootPath); EXPECT_EQ(ret, 0); ClearCache(); } catch (...) { @@ -273,10 +273,13 @@ HWTEST_F(UntarFileTest, SUB_Untar_File_UnPacket_0500, testing::ext::TestSize.Lev vector smallFiles; smallFiles.emplace_back(aFile); smallFiles.emplace_back(bFile); - TarFile::GetInstance().Packet(smallFiles, "test", root, tarMap); + auto reportCb = [](std::string msg, int err) { + return; + }; + TarFile::GetInstance().Packet(smallFiles, "test", root, tarMap, reportCb); string rootPath(root); - int ret = UntarFile::GetInstance().UnPacket(tarFile, rootPath); + auto [ret, fileInfos, errFileInfos] = UntarFile::GetInstance().UnPacket(tarFile, rootPath); EXPECT_EQ(ret, 0); ClearCache(); } catch (...) { @@ -323,12 +326,16 @@ HWTEST_F(UntarFileTest, SUB_Untar_File_IncrementalUnPacket_0100, testing::ext::T vector smallFiles; smallFiles.emplace_back(aFile); smallFiles.emplace_back(bFile); - TarFile::GetInstance().Packet(smallFiles, "test", root, tarMap); + auto reportCb = [](std::string msg, int err) { + return; + }; + TarFile::GetInstance().Packet(smallFiles, "test", root, tarMap, reportCb); string tarFile = root + "/test.0.tar"; string rootPath(root); unordered_map cloudFiles; - int ret = UntarFile::GetInstance().IncrementalUnPacket(tarFile, rootPath, cloudFiles); + auto [ret, fileInfos, errFileInfos] = + UntarFile::GetInstance().IncrementalUnPacket(tarFile, rootPath, cloudFiles); EXPECT_EQ(ret, 0); ClearCache(); } catch (...) { @@ -358,7 +365,8 @@ HWTEST_F(UntarFileTest, SUB_Untar_File_IncrementalUnPacket_0200, testing::ext::T string tarFile = root + "/empty.0.tar"; string rootPath(root); unordered_map cloudFiles; - int ret = UntarFile::GetInstance().IncrementalUnPacket(tarFile, rootPath, cloudFiles); + auto [ret, fileInfos, errFileInfos] = + UntarFile::GetInstance().IncrementalUnPacket(tarFile, rootPath, cloudFiles); EXPECT_EQ(ret, 2); // 错误码2表示找不到文件或路径 ClearCache(); } catch (...) { @@ -395,7 +403,10 @@ HWTEST_F(UntarFileTest, SUB_Untar_File_IncrementalUnPacket_0300, testing::ext::T TarMap tarMap {}; vector smallFiles; smallFiles.emplace_back(aFile); - TarFile::GetInstance().Packet(smallFiles, "test", root, tarMap); + auto reportCb = [](std::string msg, int err) { + return; + }; + TarFile::GetInstance().Packet(smallFiles, "test", root, tarMap, reportCb); string tarFile = root + "/test.0.tar"; string rootPath(root); @@ -404,7 +415,8 @@ HWTEST_F(UntarFileTest, SUB_Untar_File_IncrementalUnPacket_0300, testing::ext::T FILE *currentTarFile = fopen(tarFile.c_str(), "wb+"); fwrite("\0", sizeof(uint8_t), 1, currentTarFile); fclose(currentTarFile); - int ret = UntarFile::GetInstance().IncrementalUnPacket(tarFile, rootPath, cloudFiles); + auto [ret, fileInfos, errFileInfos] = + UntarFile::GetInstance().IncrementalUnPacket(tarFile, rootPath, cloudFiles); EXPECT_EQ(ret, 0); ClearCache(); } catch (...) { @@ -451,7 +463,10 @@ HWTEST_F(UntarFileTest, SUB_Untar_File_IncrementalUnPacket_0400, testing::ext::T vector smallFiles; smallFiles.emplace_back(aFile); smallFiles.emplace_back(bFile); - TarFile::GetInstance().Packet(smallFiles, "test", root, tarMap); + auto reportCb = [](std::string msg, int err) { + return; + }; + TarFile::GetInstance().Packet(smallFiles, "test", root, tarMap, reportCb); string tarFile = root + "/test.0.tar"; string rootPath(root); @@ -461,7 +476,8 @@ HWTEST_F(UntarFileTest, SUB_Untar_File_IncrementalUnPacket_0400, testing::ext::T fseeko(currentTarFile, 1L, SEEK_SET); fwrite("\0", sizeof(uint8_t), 1, currentTarFile); fclose(currentTarFile); - int ret = UntarFile::GetInstance().IncrementalUnPacket(tarFile, rootPath, cloudFiles); + auto [ret, fileInfos, errFileInfos] = + UntarFile::GetInstance().IncrementalUnPacket(tarFile, rootPath, cloudFiles); EXPECT_EQ(ret, 0); ClearCache(); } catch (...) { diff --git a/tests/unittests/backup_sa/module_ipc/BUILD.gn b/tests/unittests/backup_sa/module_ipc/BUILD.gn index 6a395d44a106d07b304d71aa687d4dc5d9ea41b3..8077a607e72880e69c0b7c9d5a74964aa5fbd4cc 100644 --- a/tests/unittests/backup_sa/module_ipc/BUILD.gn +++ b/tests/unittests/backup_sa/module_ipc/BUILD.gn @@ -12,6 +12,7 @@ # limitations under the License. import("//build/test.gni") +import("//foundation/filemanagement/app_file_service/app_file_service.gni") import("//foundation/filemanagement/app_file_service/backup.gni") ohos_unittest("module_ipc_test") { @@ -68,6 +69,7 @@ ohos_unittest("module_ipc_test") { ] sanitize = { + integer_overflow = true cfi = true cfi_cross_dso = true debug = false @@ -93,7 +95,6 @@ ohos_unittest("backup_service_test") { "${path_backup_mock}/module_ipc/app_gallery_dispose_proxy_mock.cpp", "${path_backup_mock}/timer/timer_mock.cpp", "${path_backup}/services/backup_sa/src/module_ipc/sa_backup_connection.cpp", - "${path_backup}/services/backup_sa/src/module_ipc/service.cpp", "${path_backup}/services/backup_sa/src/module_ipc/service_incremental.cpp", "${path_backup}/services/backup_sa/src/module_ipc/svc_restore_deps_manager.cpp", "${path_backup}/services/backup_sa/src/module_notify/notify_work_service.cpp", @@ -107,6 +108,7 @@ ohos_unittest("backup_service_test") { include_dirs = [ "${path_backup}/services/backup_sa/include", "${path_backup}/interfaces/inner_api/native/backup_kit_inner/impl", + "${path_backup}/services/backup_sa/src/module_ipc", "${path_backup}/tests/unittests/backup_api/backup_impl/include", "${path_access_token}/interfaces/innerkits/accesstoken/include", "${path_backup_mock}/b_process/", @@ -137,13 +139,24 @@ ohos_unittest("backup_service_test") { ] sanitize = { + integer_overflow = true cfi = true cfi_cross_dso = true debug = false blocklist = "${path_backup}/cfi_blocklist.txt" } + defines = [ "private=public" ] use_exceptions = true + + cflags = [ + "-g", + "-O0", + "-Wno-unused-variable", + "-fno-omit-frame-pointer", + "-Dprivate=public", + "-Dprotected=public", + ] } ohos_unittest("backup_service_throw_test") { @@ -159,6 +172,7 @@ ohos_unittest("backup_service_throw_test") { "${path_backup}/services/backup_sa/src/module_ipc/sa_backup_connection.cpp", "${path_backup}/services/backup_sa/src/module_ipc/service.cpp", "${path_backup}/services/backup_sa/src/module_ipc/service_incremental.cpp", + "${path_backup}/services/backup_sa/src/module_ipc/sub_service.cpp", "${path_backup}/services/backup_sa/src/module_ipc/svc_restore_deps_manager.cpp", "${path_backup}/services/backup_sa/src/module_notify/notify_work_service.cpp", "service_throw_test.cpp", @@ -244,6 +258,7 @@ ohos_unittest("backup_service_session_test") { ] deps = [ + "${app_file_service_path}/services/backup_sa:backup_sa", "${path_backup}/interfaces/inner_api/native/backup_kit_inner:backup_kit_inner", "${path_backup}/tests/utils:backup_test_utils", "${path_backup}/utils:backup_utils", @@ -317,6 +332,7 @@ ohos_unittest("backup_service_scheduler_test") { ] sanitize = { + integer_overflow = true cfi = true cfi_cross_dso = true debug = false @@ -342,6 +358,7 @@ ohos_unittest("backup_restore_deps_manager_test") { "${path_backup}/services/backup_sa/src/module_ipc/sa_backup_connection.cpp", "${path_backup}/services/backup_sa/src/module_ipc/service.cpp", "${path_backup}/services/backup_sa/src/module_ipc/service_incremental.cpp", + "${path_backup}/services/backup_sa/src/module_ipc/sub_service.cpp", "${path_backup}/services/backup_sa/src/module_ipc/svc_restore_deps_manager.cpp", "${path_backup}/services/backup_sa/src/module_notify/notify_work_service.cpp", "svc_restore_deps_manager_test.cpp", diff --git a/tests/unittests/backup_sa/module_ipc/sched_scheduler_test.cpp b/tests/unittests/backup_sa/module_ipc/sched_scheduler_test.cpp index 27273d9cfef5c3472d0dde6fee4d1afbe4b04af2..505e0eb577076c7510f55349b957c7e1164d4034 100644 --- a/tests/unittests/backup_sa/module_ipc/sched_scheduler_test.cpp +++ b/tests/unittests/backup_sa/module_ipc/sched_scheduler_test.cpp @@ -121,6 +121,30 @@ HWTEST_F(SchedSchedulerTest, SUB_Service_Sched_0100, testing::ext::TestSize.Leve GTEST_LOG_(INFO) << "SchedSchedulerTest-end SUB_Service_Sched_0100"; } +/** + * @tc.number: SUB_Service_Sched_0200 + * @tc.name: SUB_Service_Sched_0200 + * @tc.desc: 测试 Sched接口,sessionPtr_为空场景 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(SchedSchedulerTest, SUB_Service_Sched_0200, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "SchedSchedulerTest-begin SUB_Service_Sched_0200"; + try { + sptr schedPtrNull = sptr(new SchedScheduler(wptr(servicePtr_), nullptr)); + schedPtrNull->Sched(); + schedPtrNull->ExecutingQueueTasks("test"); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "SchedSchedulerTest-an exception occurred by Sched."; + } + GTEST_LOG_(INFO) << "SchedSchedulerTest-end SUB_Service_Sched_0200"; +} + /** * @tc.number: SUB_Service_ExecutingQueueTasks_0100 * @tc.name: SUB_Service_ExecutingQueueTasks_0100 @@ -168,4 +192,49 @@ HWTEST_F(SchedSchedulerTest, SUB_Service_RemoveExtConn_0100, testing::ext::TestS } GTEST_LOG_(INFO) << "SchedSchedulerTest-end SUB_Service_RemoveExtConn_0100"; } + +/** + * @tc.number: SUB_Service_TryUnloadServiceTimer_0100 + * @tc.name: SUB_Service_TryUnloadServiceTimer_0100 + * @tc.desc: 测试 TryUnloadServiceTimer 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(SchedSchedulerTest, SUB_Service_TryUnloadServiceTimer_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "SchedSchedulerTest-begin SUB_Service_TryUnloadServiceTimer_0100"; + try { + EXPECT_TRUE(schedPtr_ != nullptr); + schedPtr_->TryUnloadServiceTimer(true); + schedPtr_->TryUnloadServiceTimer(false); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "SchedSchedulerTest-an exception occurred by TryUnloadServiceTimer."; + } + GTEST_LOG_(INFO) << "SchedSchedulerTest-end SUB_Service_TryUnloadServiceTimer_0100"; +} + +/** + * @tc.number: SUB_Service_TryUnloadService_0100 + * @tc.name: SUB_Service_TryUnloadServicer_0100 + * @tc.desc: 测试 TryUnloadService 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(SchedSchedulerTest, SUB_Service_TryUnloadService_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "SchedSchedulerTest-begin SUB_Service_TryUnloadService_0100"; + try { + EXPECT_TRUE(schedPtr_ != nullptr); + schedPtr_->TryUnloadService(); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "SchedSchedulerTest-an exception occurred by TryUnloadService."; + } + GTEST_LOG_(INFO) << "SchedSchedulerTest-end SUB_Service_TryUnloadService_0100"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_sa/module_ipc/service_reverse_proxy_test.cpp b/tests/unittests/backup_sa/module_ipc/service_reverse_proxy_test.cpp index 5cf98223801b041f630b4822a20e0ad63f5b8767..2dbda93dfa72d8563f147c3e0ce9fb66bd9558be 100644 --- a/tests/unittests/backup_sa/module_ipc/service_reverse_proxy_test.cpp +++ b/tests/unittests/backup_sa/module_ipc/service_reverse_proxy_test.cpp @@ -2080,4 +2080,92 @@ HWTEST_F(ServiceReverseProxyTest, SUB_ServiceReverse_proxy_IncrementalRestoreOnR } GTEST_LOG_(INFO) << "ServiceReverseProxyTest-end SUB_ServiceReverse_proxy_IncrementalRestoreOnResultReport_0101"; } + +/** + * @tc.number: SUB_ServiceReverse_proxy_IncrementalBackupOnResultReport_0100 + * @tc.name: SUB_ServiceReverse_proxy_IncrementalBackupOnResultReport_0100 + * @tc.desc: Test function of IncrementalBackupOnResultReport interface for FAILURE. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I9OVHB + */ +HWTEST_F(ServiceReverseProxyTest, SUB_ServiceReverse_proxy_IncrementalBackupOnResultReport_0100, + testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceReverseProxyTest-begin SUB_ServiceReverse_proxy_IncrementalBackupOnResultReport_0100"; + try { + std::string bundleName = "app01"; + try { + EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(false)); + EXPECT_TRUE(proxy_ != nullptr); + proxy_->IncrementalBackupOnResultReport(RESULT_REPORT, bundleName); + EXPECT_TRUE(false); + } catch (BError &err) { + EXPECT_EQ(err.GetRawCode(), BError::Codes::SA_BROKEN_IPC); + } + + try { + EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteString(_)).WillOnce(Return(false)); + proxy_->IncrementalBackupOnResultReport(RESULT_REPORT, bundleName); + EXPECT_TRUE(false); + } catch (BError &err) { + EXPECT_EQ(err.GetRawCode(), BError::Codes::SA_BROKEN_IPC); + } + + try { + EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteString(_)).WillOnce(Return(true)).WillOnce(Return(false)); + proxy_->IncrementalBackupOnResultReport(RESULT_REPORT, bundleName); + EXPECT_TRUE(false); + } catch (BError &err) { + EXPECT_EQ(err.GetRawCode(), BError::Codes::SA_BROKEN_IPC); + } + + try { + EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteString(_)).WillOnce(Return(true)).WillOnce(Return(true)); + EXPECT_CALL(*mock_, SendRequest(_, _, _, _)).WillOnce(Return(-1)); + proxy_->IncrementalBackupOnResultReport(RESULT_REPORT, bundleName); + EXPECT_TRUE(false); + } catch (BError &err) { + EXPECT_EQ(err.GetRawCode(), BError::Codes::SA_BROKEN_IPC); + } + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceReverseProxyTest-an exception occurred by IncrementalBackupOnResultReport."; + } + GTEST_LOG_(INFO) << "ServiceReverseProxyTest-end SUB_ServiceReverse_proxy_IncrementalBackupOnResultReport_0100"; +} + +/** + * @tc.number: SUB_ServiceReverse_proxy_IncrementalBackupOnResultReport_0101 + * @tc.name: SUB_ServiceReverse_proxy_IncrementalBackupOnResultReport_0101 + * @tc.desc: Test function of IncrementalBackupOnResultReport interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ServiceReverseProxyTest, SUB_ServiceReverse_proxy_IncrementalBackupOnResultReport_0101, + testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceReverseProxyTest-begin SUB_ServiceReverse_proxy_IncrementalBackupOnResultReport_0101"; + try { + EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteString(_)).WillOnce(Return(true)).WillOnce(Return(true)); + EXPECT_CALL(*mock_, SendRequest(_, _, _, _)) + .Times(1) + .WillOnce(Invoke(mock_.GetRefPtr(), &ServiceReverseMock::InvokeSendRequest)); + std::string bundleName = "app01"; + EXPECT_TRUE(proxy_ != nullptr); + proxy_->IncrementalBackupOnResultReport(RESULT_REPORT, bundleName); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceReverseProxyTest-an exception occurred by RestoreOnResultReport."; + } + GTEST_LOG_(INFO) << "ServiceReverseProxyTest-end SUB_ServiceReverse_proxy_IncrementalBackupOnResultReport_0101"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_sa/module_ipc/service_stub_test.cpp b/tests/unittests/backup_sa/module_ipc/service_stub_test.cpp index 9b9947fcbdd92014cd1c73cc32bd0e429cd56b8b..c5e07a900bf941bd36019d18b469bafd944e67bd 100644 --- a/tests/unittests/backup_sa/module_ipc/service_stub_test.cpp +++ b/tests/unittests/backup_sa/module_ipc/service_stub_test.cpp @@ -53,10 +53,8 @@ public: MOCK_METHOD3(ServiceResultReport, ErrCode(const string restoreRetInfo, BackupRestoreScenario scenario, ErrCode errCode)); MOCK_METHOD2(GetFileHandle, ErrCode(const string &bundleName, const string &fileName)); - MOCK_METHOD5( - AppendBundlesRestoreSession, - ErrCode(UniqueFd fd, const std::vector &bundleNames, const std::vector &detailInfos, - RestoreTypeEnum restoreType, int32_t userId)); + MOCK_METHOD5(AppendBundlesRestoreSession, ErrCode(UniqueFd fd, const std::vector &bundleNames, + const std::vector &detailInfos, RestoreTypeEnum restoreType, int32_t userId)); MOCK_METHOD4( AppendBundlesRestoreSession, ErrCode(UniqueFd fd, const std::vector &bundleNames, RestoreTypeEnum restoreType, int32_t userId)); @@ -79,8 +77,11 @@ public: MOCK_METHOD1(AppIncrementalDone, ErrCode(ErrCode errCode)); MOCK_METHOD2(GetIncrementalFileHandle, ErrCode(const std::string &bundleName, const std::string &fileName)); MOCK_METHOD2(GetBackupInfo, ErrCode(string &bundleName, string &result)); - MOCK_METHOD3(UpdateTimer, ErrCode(BundleName &bundleName, uint32_t timeOut, bool &result)); + MOCK_METHOD3(UpdateTimer, ErrCode(BundleName &bundleName, uint32_t timeout, bool &result)); + MOCK_METHOD1(StartExtTimer, ErrCode(bool &isExtStart)); + MOCK_METHOD1(StartFwkTimer, ErrCode(bool &isFwkStart)); MOCK_METHOD3(UpdateSendRate, ErrCode(std::string &bundleName, int32_t sendRate, bool &result)); + MOCK_METHOD2(ReportAppProcessInfo, ErrCode(const std::string processInfo, BackupRestoreScenario sennario)); }; class ServiceStubTest : public testing::Test { @@ -1331,4 +1332,160 @@ HWTEST_F(ServiceStubTest, SUB_backup_sa_ServiceStub_GetIncrementalFileHandle_010 } GTEST_LOG_(INFO) << "ServiceStubTest-end SUB_backup_sa_ServiceStub_GetIncrementalFileHandle_0100"; } + +/** + * @tc.number: SUB_backup_sa_ServiceStub_CmdResultReport_0100 + * @tc.name: SUB_backup_sa_ServiceStub_CmdResultReport_0100 + * @tc.desc: Test function of CmdResultReport interface for FAILURE. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ServiceStubTest, SUB_backup_sa_ServiceStub_CmdResultReport_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceStubTest-begin SUB_backup_sa_ServiceStub_CmdResultReport_0100"; + try { + MessageParcel data; + MessageParcel reply; + EXPECT_CALL(*messageParcelMock, ReadString(_)).WillOnce(Return(false)); + EXPECT_TRUE(service != nullptr); + auto err = service->CmdResultReport(data, reply); + EXPECT_EQ(err, BError(BError::Codes::SA_INVAL_ARG)); + + EXPECT_CALL(*messageParcelMock, ReadString(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock, ReadInt32(_)).WillOnce(Return(false)); + err = service->CmdResultReport(data, reply); + EXPECT_EQ(err, BError(BError::Codes::SA_INVAL_ARG)); + + EXPECT_CALL(*messageParcelMock, ReadString(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock, ReadInt32(_)).WillOnce(Return(true)).WillOnce(Return(false)); + err = service->CmdResultReport(data, reply); + EXPECT_EQ(err, BError(BError::Codes::SA_INVAL_ARG)); + + EXPECT_CALL(*messageParcelMock, ReadString(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock, ReadInt32(_)).WillOnce(Return(true)).WillOnce(Return(true)); + EXPECT_CALL(*service, ServiceResultReport(_, _, _)).WillOnce(Return(BError(BError::Codes::OK))); + EXPECT_CALL(*messageParcelMock, WriteInt32(_)).WillOnce(Return(false)); + err = service->CmdResultReport(data, reply); + EXPECT_EQ(err, BError(BError::Codes::SA_BROKEN_IPC)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceStubTest-an exception occurred by CmdResultReport."; + } + GTEST_LOG_(INFO) << "ServiceStubTest-end SUB_backup_sa_ServiceStub_CmdResultReport_0100"; +} + +/** + * @tc.number: SUB_backup_sa_ServiceStub_CmdResultReport_0200 + * @tc.name: SUB_backup_sa_ServiceStub_CmdResultReport_0200 + * @tc.desc: Test function of GetIncrementalFileHandle interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ServiceStubTest, SUB_backup_sa_ServiceStub_CmdResultReport_0200, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceStubTest-begin SUB_backup_sa_ServiceStub_CmdResultReport_0200"; + try { + MessageParcel data; + MessageParcel reply; + EXPECT_TRUE(service != nullptr); + EXPECT_CALL(*messageParcelMock, ReadString(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock, ReadInt32(_)).WillOnce(Return(true)).WillOnce(Return(true)); + EXPECT_CALL(*service, ServiceResultReport(_, _, _)).WillOnce(Return(BError(BError::Codes::OK))); + EXPECT_CALL(*messageParcelMock, WriteInt32(_)).WillOnce(Return(true)); + auto ret = service->CmdResultReport(data, reply); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceStubTest-an exception occurred by CmdResultReport."; + } + GTEST_LOG_(INFO) << "ServiceStubTest-end SUB_backup_sa_ServiceStub_CmdResultReport_0200"; +} + +/** + * @tc.number: SUB_backup_sa_ServiceStub_CmdUpdateSendRate_0100 + * @tc.name: SUB_backup_sa_ServiceStub_CmdUpdateSendRate_0100 + * @tc.desc: Test function of CmdUpdateSendRate interface for FAILURE. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ServiceStubTest, SUB_backup_sa_ServiceStub_CmdUpdateSendRate_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceStubTest-begin SUB_backup_sa_ServiceStub_CmdUpdateSendRate_0100"; + try { + MessageParcel data; + MessageParcel reply; + EXPECT_CALL(*messageParcelMock, ReadString(_)).WillOnce(Return(false)); + EXPECT_TRUE(service != nullptr); + auto err = service->CmdUpdateSendRate(data, reply); + EXPECT_EQ(err, BError(BError::Codes::SA_BROKEN_IPC)); + + EXPECT_CALL(*messageParcelMock, ReadString(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock, ReadInt32(_)).WillOnce(Return(false)); + err = service->CmdUpdateSendRate(data, reply); + EXPECT_EQ(err, BError(BError::Codes::SA_BROKEN_IPC)); + + EXPECT_CALL(*messageParcelMock, ReadString(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock, ReadInt32(_)).WillOnce(Return(true)); + EXPECT_CALL(*service, UpdateSendRate(_, _, _)).WillOnce(Return(BError(BError::Codes::SA_INVAL_ARG))); + err = service->CmdUpdateSendRate(data, reply); + EXPECT_EQ(err, BError(BError::Codes::SA_BROKEN_IPC)); + + EXPECT_CALL(*messageParcelMock, ReadString(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock, ReadInt32(_)).WillOnce(Return(true)); + EXPECT_CALL(*service, UpdateSendRate(_, _, _)).WillOnce(Return(BError(BError::Codes::OK))); + EXPECT_CALL(*messageParcelMock, WriteBool(_)).WillOnce(Return(false)); + err = service->CmdUpdateSendRate(data, reply); + EXPECT_EQ(err, BError(BError::Codes::SA_BROKEN_IPC)); + + EXPECT_CALL(*messageParcelMock, ReadString(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock, ReadInt32(_)).WillOnce(Return(true)); + EXPECT_CALL(*service, UpdateSendRate(_, _, _)).WillOnce(Return(BError(BError::Codes::OK))); + EXPECT_CALL(*messageParcelMock, WriteBool(_)).WillOnce(Return(true)); + err = service->CmdUpdateSendRate(data, reply); + EXPECT_EQ(err, BError(BError::Codes::OK)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceStubTest-an exception occurred by CmdUpdateSendRate."; + } + GTEST_LOG_(INFO) << "ServiceStubTest-end SUB_backup_sa_ServiceStub_CmdUpdateSendRate_0100"; +} + +/** + * @tc.number: SUB_backup_sa_ServiceStub_CmdGetAppLocalListAndDoIncrementalBackup_0100 + * @tc.name: SUB_backup_sa_ServiceStub_CmdGetAppLocalListAndDoIncrementalBackup_0100 + * @tc.desc: Test function of CmdGetAppLocalListAndDoIncrementalBackup interface for FAILURE. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ServiceStubTest, SUB_backup_sa_ServiceStub_CmdGetAppLocalListAndDoIncrementalBackup_0100, + testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceStubTest-begin SUB_backup_sa_ServiceStub_CmdGetAppLocalListAndDoIncrementalBackup_0100"; + try { + MessageParcel data; + MessageParcel reply; + EXPECT_TRUE(service != nullptr); + EXPECT_CALL(*service, GetAppLocalListAndDoIncrementalBackup()).WillOnce(Return(BError(BError::Codes::OK))); + EXPECT_CALL(*messageParcelMock, WriteInt32(_)).WillOnce(Return(false)); + auto err = service->CmdGetAppLocalListAndDoIncrementalBackup(data, reply); + EXPECT_EQ(err, BError(BError::Codes::SA_BROKEN_IPC)); + + EXPECT_CALL(*service, GetAppLocalListAndDoIncrementalBackup()).WillOnce(Return(BError(BError::Codes::OK))); + EXPECT_CALL(*messageParcelMock, WriteInt32(_)).WillOnce(Return(true)); + err = service->CmdGetAppLocalListAndDoIncrementalBackup(data, reply); + EXPECT_EQ(err, BError(BError::Codes::OK)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceStubTest-an exception occurred by CmdGetAppLocalListAndDoIncrementalBackup."; + } + GTEST_LOG_(INFO) << "ServiceStubTest-end SUB_backup_sa_ServiceStub_CmdGetAppLocalListAndDoIncrementalBackup_0100"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_sa/module_ipc/service_test.cpp b/tests/unittests/backup_sa/module_ipc/service_test.cpp index f2e6511c836431e60978f9761538af5bdf55046a..9065de6caf3f39b991638d0ab6cb783db6fc4a94 100644 --- a/tests/unittests/backup_sa/module_ipc/service_test.cpp +++ b/tests/unittests/backup_sa/module_ipc/service_test.cpp @@ -20,7 +20,9 @@ #include #include "module_ipc/service.h" +#include "service.cpp" #include "service_reverse_mock.h" +#include "sub_service.cpp" #include "test_manager.h" namespace OHOS::FileManagement::Backup { @@ -441,6 +443,43 @@ HWTEST_F(ServiceTest, SUB_Service_AppDone_0102, testing::ext::TestSize.Level1) GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_AppDone_0102"; } +/** + * @tc.number: SUB_Service_ServiceResultReport_0000 + * @tc.name: SUB_Service_ServiceResultReport_0000 + * @tc.desc: 测试 ServiceResultReport 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ServiceTest, SUB_Service_ServiceResultReport_0000, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_ServiceResultReport_0000"; + try { + GTEST_LOG_(INFO) << "SUB_Service_ServiceResultReport Branches Start"; + string bundleName = ""; + EXPECT_TRUE(servicePtr_ != nullptr); + auto ret = servicePtr_->ServiceResultReport("test", BackupRestoreScenario::FULL_RESTORE, 0); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + + ret = servicePtr_->ServiceResultReport("test", BackupRestoreScenario::INCREMENTAL_RESTORE, 0); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + + ret = servicePtr_->ServiceResultReport("test", BackupRestoreScenario::FULL_BACKUP, 0); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + + ret = servicePtr_->ServiceResultReport("test", BackupRestoreScenario::INCREMENTAL_BACKUP, 0); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + + ret = servicePtr_->ServiceResultReport("test", static_cast(1000), 0); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by ServiceResultReport."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_ServiceResultReport_0000"; +} + /** * @tc.number: SUB_Service_LaunchBackupExtension_0100 * @tc.name: SUB_Service_LaunchBackupExtension_0100 @@ -523,6 +562,40 @@ HWTEST_F(ServiceTest, SUB_Service_GetFileHandle_0100, testing::ext::TestSize.Lev GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_GetFileHandle_0100"; } +/** + * @tc.number: SUB_Service_GetFileHandle_0101 + * @tc.name: SUB_Service_GetFileHandle_0101 + * @tc.desc: 测试 GetFileHandle 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ServiceTest, SUB_Service_GetFileHandle_0101, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_GetFileHandle_0101"; + try { + ErrCode ret = Init(IServiceReverse::Scenario::RESTORE); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + + SvcSessionManager::Impl impl_; + impl_.clientToken = 1; + BackupExtInfo extInfo {}; + auto callDied = [](const string &&bundleName, bool isSecondCalled) {}; + auto callConnected = [](const string &&bundleName) {}; + extInfo.backUpConnection = sptr(new SvcBackupConnection(callDied, callConnected, BUNDLE_NAME)); + extInfo.schedAction = BConstants::ServiceSchedAction::RUNNING; + impl_.backupExtNameMap[BUNDLE_NAME] = extInfo; + EXPECT_TRUE(servicePtr_ != nullptr); + ret = servicePtr_->GetFileHandle(BUNDLE_NAME, FILE_NAME); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by GetFileHandle."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_GetFileHandle_0101"; +} + /** * @tc.number: SUB_Service_OnBackupExtensionDied_0100 * @tc.name: SUB_Service_OnBackupExtensionDied_0100 @@ -554,6 +627,48 @@ HWTEST_F(ServiceTest, SUB_Service_OnBackupExtensionDied_0100, testing::ext::Test GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_OnBackupExtensionDied_0100"; } +/** + * @tc.number: SUB_Service_OnBackupExtensionDied_0101 + * @tc.name: SUB_Service_OnBackupExtensionDied_0101 + * @tc.desc: 测试 OnBackupExtensionDied 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ServiceTest, SUB_Service_OnBackupExtensionDied_0101, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_OnBackupExtensionDied_0101"; + try { + GTEST_LOG_(INFO) << "SUB_Service_OnBackupExtensionDied_0101 RESTORE"; + ErrCode ret = Init(IServiceReverse::Scenario::RESTORE); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + string bundleName = BUNDLE_NAME; + SvcSessionManager::Impl impl_; + impl_.clientToken = 1; + BackupExtInfo extInfo {}; + extInfo.backUpConnection = nullptr; + extInfo.versionName = "0.0.0.0-0.0.0.0"; + impl_.restoreDataType = RESTORE_DATA_WAIT_SEND; + impl_.backupExtNameMap[BUNDLE_NAME] = extInfo; + impl_.scenario = IServiceReverse::Scenario::RESTORE; + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->OnBackupExtensionDied(move(bundleName)); + GTEST_LOG_(INFO) << "SUB_Service_OnBackupExtensionDied_0101 BACKUP"; + + ret = Init(IServiceReverse::Scenario::BACKUP); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + impl_.restoreDataType = RESTORE_DATA_READDY; + bundleName = "123456789"; + impl_.backupExtNameMap[bundleName] = extInfo; + servicePtr_->OnBackupExtensionDied(move(bundleName)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by GetFileHandle."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_OnBackupExtensionDied_0101"; +} + /** * @tc.number: SUB_Service_ExtStart_0100 * @tc.name: SUB_Service_ExtStart_0100 @@ -584,6 +699,54 @@ HWTEST_F(ServiceTest, SUB_Service_ExtStart_0100, testing::ext::TestSize.Level1) GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_ExtStart_0100"; } +/** + * @tc.number: SUB_Service_ExtStart_0101 + * @tc.name: SUB_Service_ExtStart_0101 + * @tc.desc: 测试 ExtStart 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ServiceTest, SUB_Service_ExtStart_0101, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_ExtStart_0101"; + try { + GTEST_LOG_(INFO) << "SUB_Service_ExtStart_0101 BACKUP"; + std::string bundleName = "123456"; + ErrCode ret = Init(IServiceReverse::Scenario::BACKUP); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->ExtStart(bundleName); + + GTEST_LOG_(INFO) << "SUB_Service_ExtStart_0101 RESTORE"; + SvcSessionManager::Impl impl_; + impl_.clientToken = 1; + BackupExtInfo extInfo {}; + auto callDied = [](const string &&bundleName, bool isSecondCalled) {}; + auto callConnected = [](const string &&bundleName) {}; + extInfo.backUpConnection = sptr(new SvcBackupConnection(callDied, callConnected, BUNDLE_NAME)); + extInfo.backUpConnection->backupProxy_ = nullptr; + impl_.backupExtNameMap[BUNDLE_NAME] = extInfo; + impl_.scenario = IServiceReverse::Scenario::UNDEFINED; + ret = Init(IServiceReverse::Scenario::UNDEFINED); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + servicePtr_->ExtStart(BUNDLE_NAME); + + ret = Init(IServiceReverse::Scenario::RESTORE); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + servicePtr_->ExtStart(BUNDLE_NAME); + + ret = Init(IServiceReverse::Scenario::UNDEFINED); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + servicePtr_->ExtStart(BUNDLE_NAME); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by ExtStart."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_ExtStart_0101"; +} + /** * @tc.number: SUB_Service_Dump_0100 * @tc.name: SUB_Service_Dump_0100 @@ -678,6 +841,13 @@ HWTEST_F(ServiceTest, SUB_Service_ExtConnectFailed_0100, testing::ext::TestSize. ret = Init(IServiceReverse::Scenario::BACKUP); EXPECT_EQ(ret, BError(BError::Codes::OK)); servicePtr_->ExtConnectFailed(BUNDLE_NAME, BError(BError::Codes::OK)); + + SvcSessionManager::Impl impl_; + impl_.clientToken = 1; + impl_.restoreDataType = RESTORE_DATA_READDY; + ret = Init(IServiceReverse::Scenario::RESTORE); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + servicePtr_->ExtConnectFailed(BUNDLE_NAME, BError(BError::Codes::OK)); } catch (...) { EXPECT_TRUE(false); GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by ExtConnectFailed."; @@ -873,6 +1043,30 @@ HWTEST_F(ServiceTest, SUB_Service_SendStartAppGalleryNotify_0100, testing::ext:: GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_SendStartAppGalleryNotify_0100"; } +/** + * @tc.number: SUB_Service_SendStartAppGalleryNotify_0101 + * @tc.name: SUB_Service_SendStartAppGalleryNotify_0101 + * @tc.desc: 测试 SendStartAppGalleryNotify 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_SendStartAppGalleryNotify_0101, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_SendStartAppGalleryNotify_0101"; + try { + ErrCode ret = Init(IServiceReverse::Scenario::RESTORE); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->SendStartAppGalleryNotify(BUNDLE_NAME); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by SendStartAppGalleryNotify."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_SendStartAppGalleryNotify_0101"; +} + /** * @tc.number: SUB_Service_SessionDeactive_0100 * @tc.name: SUB_Service_SessionDeactive_0100 @@ -921,6 +1115,40 @@ HWTEST_F(ServiceTest, SUB_Service_GetBackupInfo_0100, testing::ext::TestSize.Lev GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_GetBackupInfo_0100"; } +/** + * @tc.number: SUB_Service_GetBackupInfo_0101 + * @tc.name: SUB_Service_GetBackupInfo_0101 + * @tc.desc: 测试 SessionDeactive 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_GetBackupInfo_0101, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_GetBackupInfo_0101"; + try { + std::string bundleName = "com.example.app2backup"; + std::string result = "ok"; + auto ret = Init(IServiceReverse::Scenario::BACKUP); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->session_ = nullptr; + SvcSessionManager::Impl impl_; + impl_.clientToken = 1; + ret = servicePtr_->GetBackupInfo(bundleName, result); + EXPECT_NE(ret, BError(BError::Codes::OK)); + + impl_.clientToken = 0; + ret = servicePtr_->GetBackupInfo(bundleName, result); + EXPECT_NE(ret, BError(BError::Codes::OK)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by GetBackupInfo."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_GetBackupInfo_0101"; +} + /** * @tc.number: SUB_Service_UpdateTimer_0100 * @tc.name: SUB_Service_UpdateTimer_0100 @@ -936,13 +1164,621 @@ HWTEST_F(ServiceTest, SUB_Service_UpdateTimer_0100, testing::ext::TestSize.Level try { std::string bundleName = "com.example.app2backup"; bool result = true; - uint32_t timeOut = 30000; + uint32_t timeout = 30000; EXPECT_TRUE(servicePtr_ != nullptr); - servicePtr_->UpdateTimer(bundleName, timeOut, result); + servicePtr_->UpdateTimer(bundleName, timeout, result); } catch (...) { EXPECT_TRUE(false); GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by UpdateTimer."; } GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_UpdateTimer_0100"; } + +/** + * @tc.number: SUB_Service_UpdateTimer_0101 + * @tc.name: SUB_Service_UpdateTimer_0101 + * @tc.desc: 测试 UpdateTimer 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_UpdateTimer_0101, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_UpdateTimer_0101"; + try { + std::string bundleName = "com.example.app2backup"; + bool result = true; + uint32_t timeout = 30000; + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->session_ = nullptr; + servicePtr_->UpdateTimer(bundleName, timeout, result); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by UpdateTimer."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_UpdateTimer_0101"; +} + +/** + * @tc.number: SUB_Service_GetBackupInfoCmdHandle_0100 + * @tc.name: SUB_Service_GetBackupInfoCmdHandle_0100 + * @tc.desc: 测试 GetBackupInfoCmdHandle 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_GetBackupInfoCmdHandle_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_GetBackupInfoCmdHandle_0100"; + try { + std::string bundleName = "com.example.app2backup"; + std::string result; + EXPECT_TRUE(servicePtr_ != nullptr); + auto ret = servicePtr_->GetBackupInfoCmdHandle(bundleName, result); + EXPECT_TRUE(ret == BError::BackupErrorCode::E_INVAL); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by GetBackupInfoCmdHandle."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_GetBackupInfoCmdHandle_0100"; +} + +/** + * @tc.number: SUB_Service_SpecialVersion_0100 + * @tc.name: SUB_Service_SpecialVersion_0100 + * @tc.desc: 测试 SpecialVersion 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_SpecialVersion_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_SpecialVersion_0100"; + try { + std::string versionName = "0.0.0.0-0.0.0.0"; + EXPECT_TRUE(servicePtr_ != nullptr); + bool ret = SpecialVersion(versionName); + EXPECT_EQ(ret, true); + versionName = "1.1.1.1-1.1.1.1"; + ret = SpecialVersion(versionName); + EXPECT_EQ(ret, false); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by SpecialVersion."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_SpecialVersion_0100"; +} + +/** + * @tc.number: SUB_Service_OnBundleStarted_0100 + * @tc.name: SUB_Service_OnBundleStarted_0100 + * @tc.desc: 测试 OnBundleStarted 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_OnBundleStarted_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_OnBundleStarted_0100"; + try { + int32_t saID = 2503; + wptr reversePtr(new Service(saID)); + sptr session(new SvcSessionManager(reversePtr)); + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->OnBundleStarted(BError(BError::Codes::SA_INVAL_ARG), session, BUNDLE_NAME); + SvcSessionManager::Impl impl_; + impl_.clientToken = 1; + impl_.scenario = IServiceReverse::Scenario::RESTORE; + servicePtr_->OnBundleStarted(BError(BError::Codes::SA_INVAL_ARG), session, BUNDLE_NAME); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by OnBundleStarted."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_OnBundleStarted_0100"; +} + +/** + * @tc.number: SUB_Service_HandleExceptionOnAppendBundles_0100 + * @tc.name: SUB_Service_HandleExceptionOnAppendBundles_0100 + * @tc.desc: 测试 HandleExceptionOnAppendBundles 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_HandleExceptionOnAppendBundles_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_HandleExceptionOnAppendBundles_0100"; + try { + int32_t saID = 4801; + wptr reversePtr(new Service(saID)); + sptr session(new SvcSessionManager(reversePtr)); + vector appendBundleNames {"123456"}; + vector restoreBundleNames {"abcdef"}; + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->HandleExceptionOnAppendBundles(session, appendBundleNames, restoreBundleNames); + + appendBundleNames.push_back("789"); + servicePtr_->HandleExceptionOnAppendBundles(session, appendBundleNames, restoreBundleNames); + + restoreBundleNames.push_back("123456"); + restoreBundleNames.push_back("123"); + servicePtr_->HandleExceptionOnAppendBundles(session, appendBundleNames, restoreBundleNames); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by HandleExceptionOnAppendBundles."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_HandleExceptionOnAppendBundles_0100"; +} + +/** + * @tc.number: SUB_Service_SetCurrentSessProperties_0100 + * @tc.name: SUB_Service_SetCurrentSessProperties_0100 + * @tc.desc: 测试 SetCurrentSessProperties 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_SetCurrentSessProperties_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_SetCurrentSessProperties_0100"; + try { + BJsonEntityCaps::BundleInfo aInfo {}; + aInfo.name = "123456"; + aInfo.extensionName = "abcdef"; + aInfo.allToBackup = true; + std::vector restoreBundleInfos {aInfo}; + std::vector restoreBundleNames {"12345678"}; + RestoreTypeEnum restoreType = RESTORE_DATA_READDY; + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->session_ = sptr(new SvcSessionManager(servicePtr_)); + servicePtr_->SetCurrentSessProperties(restoreBundleInfos, restoreBundleNames, restoreType); + + restoreBundleNames.push_back("123456"); + servicePtr_->SetCurrentSessProperties(restoreBundleInfos, restoreBundleNames, restoreType); + + restoreBundleInfos.clear(); + aInfo.allToBackup = true; + aInfo.versionName = "0.0.0.0-0.0.0.0"; + aInfo.extensionName = ""; + restoreBundleInfos.push_back(aInfo); + servicePtr_->SetCurrentSessProperties(restoreBundleInfos, restoreBundleNames, restoreType); + + restoreBundleInfos.clear(); + aInfo.name = "123456a"; + restoreBundleInfos.push_back(aInfo); + restoreBundleNames.push_back("123456a"); + servicePtr_->SetCurrentSessProperties(restoreBundleInfos, restoreBundleNames, restoreType); + + restoreBundleInfos.clear(); + aInfo.allToBackup = false; + aInfo.extensionName = ""; + restoreBundleInfos.push_back(aInfo); + servicePtr_->SetCurrentSessProperties(restoreBundleInfos, restoreBundleNames, restoreType); + + restoreBundleInfos.clear(); + aInfo.allToBackup = false; + aInfo.extensionName = ""; + restoreBundleInfos.push_back(aInfo); + servicePtr_->SetCurrentSessProperties(restoreBundleInfos, restoreBundleNames, restoreType); + } catch (...) { + EXPECT_TRUE(true); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by SetCurrentSessProperties."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_SetCurrentSessProperties_0100"; +} + +/** + * @tc.number: SUB_Service_SetCurrentSessProperties_0101 + * @tc.name: SUB_Service_SetCurrentSessProperties_0101 + * @tc.desc: 测试 SetCurrentSessProperties 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_SetCurrentSessProperties_0101, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_SetCurrentSessProperties_0101"; + try { + BJsonEntityCaps::BundleInfo aInfo {}; + aInfo.name = "123456"; + aInfo.versionName = "0.0.0.0-0.0.0.0"; + aInfo.extensionName = "abcdef"; + aInfo.allToBackup = false; + std::vector restoreBundleInfos {aInfo}; + std::vector restoreBundleNames {"123456"}; + RestoreTypeEnum restoreType = RESTORE_DATA_READDY; + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->session_ = sptr(new SvcSessionManager(servicePtr_)); + servicePtr_->SetCurrentSessProperties(restoreBundleInfos, restoreBundleNames, restoreType); + + restoreBundleInfos.clear(); + aInfo.extensionName = ""; + restoreBundleInfos.push_back(aInfo); + servicePtr_->SetCurrentSessProperties(restoreBundleInfos, restoreBundleNames, restoreType); + + restoreBundleInfos.clear(); + aInfo.name = "123456a"; + restoreBundleInfos.push_back(aInfo); + restoreBundleNames.push_back("123456a"); + servicePtr_->SetCurrentSessProperties(restoreBundleInfos, restoreBundleNames, restoreType); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by SetCurrentSessProperties."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_SetCurrentSessProperties_0101"; +} + +/** + * @tc.number: SUB_Service_SetCurrentSessProperties_0102 + * @tc.name: SUB_Service_SetCurrentSessProperties_0102 + * @tc.desc: 测试 SetCurrentSessProperties 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_SetCurrentSessProperties_0102, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_SetCurrentSessProperties_0102"; + try { + BJsonEntityCaps::BundleInfo aInfo {}; + aInfo.name = "123456"; + aInfo.versionName = "0.0.0.0-0.0.0.0"; + aInfo.extensionName = "abcdef"; + aInfo.allToBackup = false; + std::vector restoreBundleInfos {aInfo}; + std::vector restoreBundleNames {"123456"}; + RestoreTypeEnum restoreType = RESTORE_DATA_READDY; + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->SetCurrentSessProperties(restoreBundleInfos, restoreBundleNames, restoreType); + + restoreBundleInfos.clear(); + aInfo.versionName = "1.1.1.1-1.1.1.1"; + aInfo.extensionName = ""; + aInfo.name = "123456"; + restoreBundleInfos.push_back(aInfo); + servicePtr_->SetCurrentSessProperties(restoreBundleInfos, restoreBundleNames, restoreType); + + restoreBundleInfos.clear(); + aInfo.name = "123456a"; + restoreBundleInfos.push_back(aInfo); + servicePtr_->SetCurrentSessProperties(restoreBundleInfos, restoreBundleNames, restoreType); + + restoreBundleInfos.clear(); + aInfo.extensionName = "abcdef"; + restoreBundleInfos.push_back(aInfo); + servicePtr_->SetCurrentSessProperties(restoreBundleInfos, restoreBundleNames, restoreType); + + restoreBundleInfos.clear(); + aInfo.name = "123456"; + restoreBundleInfos.push_back(aInfo); + servicePtr_->SetCurrentSessProperties(restoreBundleInfos, restoreBundleNames, restoreType); + } catch (...) { + EXPECT_TRUE(true); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by SetCurrentSessProperties."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_SetCurrentSessProperties_0102"; +} + +/** + * @tc.number: SUB_Service_AppendBundlesRestoreSession_0100 + * @tc.name: SUB_Service_AppendBundlesRestoreSession_0100 + * @tc.desc: 测试 AppendBundlesRestoreSession 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_AppendBundlesRestoreSession_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_AppendBundlesRestoreSession_0100"; + try { + UniqueFd fd = servicePtr_->GetLocalCapabilities(); + EXPECT_GE(fd, BError(BError::Codes::OK)); + vector bundleNames {}; + RestoreTypeEnum restoreType = RESTORE_DATA_READDY; + int32_t userId = 1; + EXPECT_TRUE(servicePtr_ != nullptr); + auto ret = servicePtr_->AppendBundlesRestoreSession(move(fd), bundleNames, restoreType, userId); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by AppendBundlesRestoreSession."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_AppendBundlesRestoreSession_0100"; +} + +/** + * @tc.number: SUB_Service_NotifyCloneBundleFinish_0100 + * @tc.name: SUB_Service_NotifyCloneBundleFinish_0100 + * @tc.desc: 测试 NotifyCloneBundleFinish 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_NotifyCloneBundleFinish_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_NotifyCloneBundleFinish_0100"; + try { + SvcSessionManager::Impl impl_; + impl_.clientToken = 1; + BackupExtInfo extInfo {}; + extInfo.backUpConnection = nullptr; + impl_.backupExtNameMap[BUNDLE_NAME] = extInfo; + impl_.scenario = IServiceReverse::Scenario::RESTORE; + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->NotifyCloneBundleFinish(BUNDLE_NAME, BackupRestoreScenario::FULL_RESTORE); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by NotifyCloneBundleFinish."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_NotifyCloneBundleFinish_0100"; +} + +/** + * @tc.number: SUB_Service_LaunchBackupSAExtension_0100 + * @tc.name: SUB_Service_LaunchBackupSAExtension_0100 + * @tc.desc: 测试 LaunchBackupSAExtension 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_LaunchBackupSAExtension_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_LaunchBackupSAExtension_0100"; + try { + std::string bundleName = "123456"; + ErrCode ret = Init(IServiceReverse::Scenario::RESTORE); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + EXPECT_TRUE(servicePtr_ != nullptr); + ret = servicePtr_->LaunchBackupSAExtension(BUNDLE_NAME); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + + SvcSessionManager::Impl impl_; + impl_.clientToken = 1; + BackupExtInfo extInfo {}; + extInfo.backUpConnection = nullptr; + + auto callDied = [](const string &&bundleName) {}; + auto callConnected = [](const string &&bundleName) {}; + auto callBackup = [](const std::string &&bundleName, const int &&fd, const std::string &&result, + const ErrCode &&errCode) {}; + auto callRestore = [](const std::string &&bundleName, const std::string &&result, const ErrCode &&errCode) {}; + extInfo.saBackupConnection = + std::make_shared(callDied, callConnected, callBackup, callRestore); + + impl_.backupExtNameMap[BUNDLE_NAME] = extInfo; + ret = servicePtr_->LaunchBackupSAExtension(bundleName); + EXPECT_NE(ret, BError(BError::Codes::OK)); + + ret = Init(IServiceReverse::Scenario::BACKUP); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + ret = servicePtr_->LaunchBackupSAExtension(bundleName); + EXPECT_NE(ret, BError(BError::Codes::OK)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by LaunchBackupSAExtension."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_LaunchBackupSAExtension_0100"; +} + +/** + * @tc.number: SUB_Service_ExtConnectDied_0100 + * @tc.name: SUB_Service_ExtConnectDied_0100 + * @tc.desc: 测试 ExtConnectDied 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_ExtConnectDied_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_ExtConnectDied_0100"; + try { + std::string callName = "123456"; + ErrCode ret = Init(IServiceReverse::Scenario::RESTORE); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + SvcSessionManager::Impl impl_; + impl_.clientToken = 1; + BackupExtInfo extInfo {}; + auto callDied = [](const string &&bundleName, bool isSecondCalled) {}; + auto callConnected = [](const string &&bundleName) {}; + extInfo.backUpConnection = sptr(new SvcBackupConnection(callDied, callConnected, BUNDLE_NAME)); + impl_.backupExtNameMap[BUNDLE_NAME] = extInfo; + impl_.scenario = IServiceReverse::Scenario::RESTORE; + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->ExtConnectDied(callName); + extInfo.backUpConnection->isConnected_.store(true); + servicePtr_->ExtConnectDied(callName); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by ExtConnectDied."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_ExtConnectDied_0100"; +} + +/** + * @tc.number: SUB_Service_NoticeClientFinish_0100 + * @tc.name: SUB_Service_NoticeClientFinish_0100 + * @tc.desc: 测试 NoticeClientFinish 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_NoticeClientFinish_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_NoticeClientFinish_0100"; + try { + ErrCode ret = Init(IServiceReverse::Scenario::RESTORE); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->NoticeClientFinish(BUNDLE_NAME, BError(BError::Codes::OK)); + GTEST_LOG_(INFO) << "SUB_Service_NoticeClientFinish_0100 BACKUP"; + ret = Init(IServiceReverse::Scenario::BACKUP); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + servicePtr_->NoticeClientFinish(BUNDLE_NAME, BError(BError::Codes::OK)); + + SvcSessionManager::Impl impl_; + impl_.clientToken = 1; + impl_.restoreDataType = RESTORE_DATA_READDY; + ret = Init(IServiceReverse::Scenario::RESTORE); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + servicePtr_->NoticeClientFinish(BUNDLE_NAME, BError(BError::Codes::OK)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by NoticeClientFinish."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_NoticeClientFinish_0100"; +} + +/** + * @tc.number: SUB_Service_OnAllBundlesFinished_0100 + * @tc.name: SUB_Service_OnAllBundlesFinished_0100 + * @tc.desc: 测试 OnAllBundlesFinished 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ServiceTest, SUB_Service_OnAllBundlesFinished_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_OnAllBundlesFinished_0100"; + try { + ErrCode ret = Init(IServiceReverse::Scenario::BACKUP); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->session_ = sptr(new SvcSessionManager(servicePtr_)); + servicePtr_->OnAllBundlesFinished(BError(BError::Codes::OK)); + + ret = Init(IServiceReverse::Scenario::RESTORE); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + servicePtr_->OnAllBundlesFinished(BError(BError::Codes::OK)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by OnAllBundlesFinished."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_OnAllBundlesFinished_0100"; +} + +/** + * @tc.number: SUB_Service_SendEndAppGalleryNotify_0100 + * @tc.name: SUB_Service_SendEndAppGalleryNotify_0100 + * @tc.desc: 测试 SendEndAppGalleryNotify 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_SendEndAppGalleryNotify_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_SendEndAppGalleryNotify_0100"; + try { + ErrCode ret = Init(IServiceReverse::Scenario::BACKUP); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->SendEndAppGalleryNotify(BUNDLE_NAME); + + ret = Init(IServiceReverse::Scenario::RESTORE); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + servicePtr_->SendEndAppGalleryNotify(BUNDLE_NAME); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by SendEndAppGalleryNotify."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_SendEndAppGalleryNotify_0100"; +} + +/** + * @tc.number: SUB_Service_SendErrAppGalleryNotify_0100 + * @tc.name: SUB_Service_SendErrAppGalleryNotify_0100 + * @tc.desc: 测试 SendErrAppGalleryNotify 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_SendErrAppGalleryNotify_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_SendErrAppGalleryNotify_0100"; + try { + ErrCode ret = Init(IServiceReverse::Scenario::BACKUP); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->SendErrAppGalleryNotify(); + + ret = Init(IServiceReverse::Scenario::RESTORE); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + servicePtr_->SendErrAppGalleryNotify(); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by SendErrAppGalleryNotify."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_SendErrAppGalleryNotify_0100"; +} + +/** + * @tc.number: SUB_Service_ClearDisposalOnSaStart_0100 + * @tc.name: SUB_Service_ClearDisposalOnSaStart_0100 + * @tc.desc: 测试 ClearDisposalOnSaStart 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_ClearDisposalOnSaStart_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_ClearDisposalOnSaStart_0100"; + try { + ErrCode ret = Init(IServiceReverse::Scenario::BACKUP); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->ClearDisposalOnSaStart(); + + ret = Init(IServiceReverse::Scenario::RESTORE); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + servicePtr_->ClearDisposalOnSaStart(); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by ClearDisposalOnSaStart."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_ClearDisposalOnSaStart_0100"; +} + +/** + * @tc.number: SUB_Service_DeleteDisConfigFile_0100 + * @tc.name: SUB_Service_DeleteDisConfigFile_0100 + * @tc.desc: 测试 DeleteDisConfigFile 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I8ZIMJ + */ +HWTEST_F(ServiceTest, SUB_Service_DeleteDisConfigFile_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ServiceTest-begin SUB_Service_DeleteDisConfigFile_0100"; + try { + ErrCode ret = Init(IServiceReverse::Scenario::BACKUP); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + EXPECT_TRUE(servicePtr_ != nullptr); + servicePtr_->DeleteDisConfigFile(); + + ret = Init(IServiceReverse::Scenario::RESTORE); + EXPECT_EQ(ret, BError(BError::Codes::OK)); + servicePtr_->DeleteDisConfigFile(); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ServiceTest-an exception occurred by DeleteDisConfigFile."; + } + GTEST_LOG_(INFO) << "ServiceTest-end SUB_Service_DeleteDisConfigFile_0100"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_sa/module_ipc/service_throw_test.cpp b/tests/unittests/backup_sa/module_ipc/service_throw_test.cpp index 06dc18af33722d59bdebe3c3a1c0a98a8bd7613b..9286bc29d9bfe64952e164de64dbdd1dbc1971e4 100644 --- a/tests/unittests/backup_sa/module_ipc/service_throw_test.cpp +++ b/tests/unittests/backup_sa/module_ipc/service_throw_test.cpp @@ -67,24 +67,24 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_GetLocalCapabilities_0100, testing: GTEST_LOG_(INFO) << "ServiceThrowTest-begin SUB_Service_throw_GetLocalCapabilities_0100"; try { EXPECT_NE(service, nullptr); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw BError(BError::Codes::EXT_THROW_EXCEPTION); })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); auto ret = service->GetLocalCapabilities(); EXPECT_EQ(-ret, BError(BError::Codes::EXT_THROW_EXCEPTION).GetCode()); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw runtime_error("运行时错误"); })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); ret = service->GetLocalCapabilities(); EXPECT_EQ(-ret, EPERM); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw "未知错误"; })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); ret = service->GetLocalCapabilities(); EXPECT_EQ(-ret, EPERM); } catch (...) { @@ -177,17 +177,17 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_AppendBundlesRestoreSession_0100, t GTEST_LOG_(INFO) << "ServiceThrowTest-begin SUB_Service_throw_AppendBundlesRestoreSession_0100"; try { EXPECT_NE(service, nullptr); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw BError(BError::Codes::EXT_THROW_EXCEPTION); })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); auto ret = service->AppendBundlesRestoreSession(UniqueFd(-1), {}, {}, RESTORE_DATA_WAIT_SEND, 0); EXPECT_EQ(ret, BError(BError::Codes::EXT_THROW_EXCEPTION).GetCode()); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw "未知错误"; })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); ret = service->AppendBundlesRestoreSession(UniqueFd(-1), {}, {}, RESTORE_DATA_WAIT_SEND, 0); EXPECT_EQ(ret, EPERM); } catch (...) { @@ -211,17 +211,17 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_AppendBundlesRestoreSession_0200, t GTEST_LOG_(INFO) << "ServiceThrowTest-begin SUB_Service_throw_AppendBundlesRestoreSession_0200"; try { EXPECT_NE(service, nullptr); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw BError(BError::Codes::EXT_THROW_EXCEPTION); })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); auto ret = service->AppendBundlesRestoreSession(UniqueFd(-1), {}, RESTORE_DATA_WAIT_SEND, 0); EXPECT_EQ(ret, BError(BError::Codes::EXT_THROW_EXCEPTION).GetCode()); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw "未知错误"; })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); ret = service->AppendBundlesRestoreSession(UniqueFd(-1), {}, RESTORE_DATA_WAIT_SEND, 0); EXPECT_EQ(ret, EPERM); } catch (...) { @@ -245,24 +245,24 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_AppendBundlesBackupSession_0100, te GTEST_LOG_(INFO) << "ServiceThrowTest-begin SUB_Service_throw_AppendBundlesBackupSession_0100"; try { EXPECT_NE(service, nullptr); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw BError(BError::Codes::EXT_THROW_EXCEPTION); })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); auto ret = service->AppendBundlesBackupSession({}); EXPECT_EQ(ret, BError(BError::Codes::EXT_THROW_EXCEPTION).GetCode()); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw runtime_error("运行时错误"); })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); ret = service->AppendBundlesBackupSession({}); EXPECT_EQ(ret, EPERM); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw "未知错误"; })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); ret = service->AppendBundlesBackupSession({}); EXPECT_EQ(ret, EPERM); } catch (...) { @@ -286,24 +286,24 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_AppendBundlesDetailsBackupSession_0 GTEST_LOG_(INFO) << "ServiceThrowTest-begin SUB_Service_throw_AppendBundlesDetailsBackupSession_0100"; try { EXPECT_NE(service, nullptr); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw BError(BError::Codes::EXT_THROW_EXCEPTION); })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); auto ret = service->AppendBundlesDetailsBackupSession({}, {}); EXPECT_EQ(ret, BError(BError::Codes::EXT_THROW_EXCEPTION).GetCode()); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw runtime_error("运行时错误"); })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); ret = service->AppendBundlesDetailsBackupSession({}, {}); EXPECT_EQ(ret, EPERM); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw "未知错误"; })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); ret = service->AppendBundlesDetailsBackupSession({}, {}); EXPECT_EQ(ret, EPERM); } catch (...) { @@ -526,19 +526,23 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_OnBackupExtensionDied_0100, testing try { EXPECT_NE(service, nullptr); string bundleName; + EXPECT_CALL(*sessionMock, GetScenario()).WillOnce(Return(IServiceReverse::Scenario::UNDEFINED)) + .WillOnce(Return(IServiceReverse::Scenario::UNDEFINED)) + .WillOnce(Invoke([]() { + throw "未知错误"; + return IServiceReverse::Scenario::UNDEFINED; + })); EXPECT_CALL(*sessionMock, VerifyBundleName(_)).WillOnce(Invoke([]() { throw BError(BError::Codes::EXT_THROW_EXCEPTION); })); - EXPECT_CALL(*sessionMock, BundleExtTimerStop(_)).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, StopFwkTimer(_)).WillOnce(Invoke([]() { throw BError(BError::Codes::EXT_THROW_EXCEPTION); + return true; })); EXPECT_CALL(*sessionMock, RemoveExtInfo(_)).WillOnce(Invoke([]() { throw BError(BError::Codes::EXT_THROW_EXCEPTION); })); - EXPECT_CALL(*sessionMock, GetScenario()).WillOnce(Invoke([]() { - throw BError(BError::Codes::EXT_THROW_EXCEPTION); - return IServiceReverse::Scenario::UNDEFINED; - })); + EXPECT_CALL(*sessionMock, IsOnAllBundlesFinished()).WillOnce(Return(false)); service->OnBackupExtensionDied("bundleName"); EXPECT_TRUE(true); } catch (...) { @@ -548,40 +552,6 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_OnBackupExtensionDied_0100, testing GTEST_LOG_(INFO) << "ServiceThrowTest-end SUB_Service_throw_OnBackupExtensionDied_0100"; } -/** - * @tc.number: SUB_Service_throw_ExtConnectDied_0100 - * @tc.name: SUB_Service_throw_ExtConnectDied_0100 - * @tc.desc: 测试 ExtConnectDied 接口的 catch 分支 - * @tc.size: MEDIUM - * @tc.type: FUNC - * @tc.level Level 1 - * @tc.require: issuesIAC04T - */ -HWTEST_F(ServiceThrowTest, SUB_Service_throw_ExtConnectDied_0100, testing::ext::TestSize.Level1) -{ - GTEST_LOG_(INFO) << "ServiceThrowTest-begin SUB_Service_throw_ExtConnectDied_0100"; - try { - EXPECT_NE(service, nullptr); - string callName; - EXPECT_CALL(*sessionMock, BundleExtTimerStop(_)).WillOnce(Invoke([]() { - throw BError(BError::Codes::EXT_THROW_EXCEPTION); - })); - EXPECT_CALL(*sessionMock, RemoveExtInfo(_)).WillOnce(Invoke([]() { - throw BError(BError::Codes::EXT_THROW_EXCEPTION); - })); - EXPECT_CALL(*sessionMock, GetScenario()).WillOnce(Invoke([]() { - throw BError(BError::Codes::EXT_THROW_EXCEPTION); - return IServiceReverse::Scenario::UNDEFINED; - })); - service->ExtConnectDied(callName); - EXPECT_TRUE(true); - } catch (...) { - EXPECT_TRUE(false); - GTEST_LOG_(INFO) << "ServiceThrowTest-an exception occurred by ExtConnectDied."; - } - GTEST_LOG_(INFO) << "ServiceThrowTest-end SUB_Service_throw_ExtConnectDied_0100"; -} - /** * @tc.number: SUB_Service_throw_ExtStart_0100 * @tc.name: SUB_Service_throw_ExtStart_0100 @@ -607,6 +577,7 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_ExtStart_0100, testing::ext::TestSi EXPECT_CALL(*sessionMock, RemoveExtInfo(_)).WillOnce(Invoke([]() { throw BError(BError::Codes::EXT_THROW_EXCEPTION); })); + EXPECT_CALL(*sessionMock, IsOnAllBundlesFinished()).WillOnce(Return(false)); service->ExtStart(bundleName); EXPECT_TRUE(true); } catch (...) { @@ -634,6 +605,9 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_ExtConnectFailed_0100, testing::ext EXPECT_CALL(*sessionMock, GetScenario()).WillOnce(Invoke([]() { throw BError(BError::Codes::EXT_THROW_EXCEPTION); return IServiceReverse::Scenario::UNDEFINED; + })).WillOnce(Invoke([]() { + throw BError(BError::Codes::EXT_THROW_EXCEPTION); + return IServiceReverse::Scenario::UNDEFINED; })); service->ExtConnectFailed(bundleName, 0); EXPECT_TRUE(true); @@ -641,6 +615,9 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_ExtConnectFailed_0100, testing::ext EXPECT_CALL(*sessionMock, GetScenario()).WillOnce(Invoke([]() { throw runtime_error("运行时错误"); return IServiceReverse::Scenario::UNDEFINED; + })).WillOnce(Invoke([]() { + throw runtime_error("运行时错误"); + return IServiceReverse::Scenario::UNDEFINED; })); service->ExtConnectFailed(bundleName, 0); EXPECT_TRUE(true); @@ -648,6 +625,9 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_ExtConnectFailed_0100, testing::ext EXPECT_CALL(*sessionMock, GetScenario()).WillOnce(Invoke([]() { throw "未知错误"; return IServiceReverse::Scenario::UNDEFINED; + })).WillOnce(Invoke([]() { + throw "未知错误"; + return IServiceReverse::Scenario::UNDEFINED; })); service->ExtConnectFailed(bundleName, 0); EXPECT_TRUE(true); @@ -678,6 +658,7 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_NoticeClientFinish_0100, testing::e throw BError(BError::Codes::EXT_THROW_EXCEPTION); return IServiceReverse::Scenario::UNDEFINED; })); + EXPECT_CALL(*sessionMock, IsOnAllBundlesFinished()).WillOnce(Return(false)); service->NoticeClientFinish(bundleName, errCode); EXPECT_TRUE(true); } catch (...) { @@ -687,40 +668,6 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_NoticeClientFinish_0100, testing::e GTEST_LOG_(INFO) << "ServiceThrowTest-end SUB_Service_throw_NoticeClientFinish_0100"; } -/** - * @tc.number: SUB_Service_throw_ExtConnectDone_0100 - * @tc.name: SUB_Service_throw_ExtConnectDone_0100 - * @tc.desc: 测试 ExtConnectDone 接口的 catch 分支 - * @tc.size: MEDIUM - * @tc.type: FUNC - * @tc.level Level 1 - * @tc.require: issuesIAC04T - */ -HWTEST_F(ServiceThrowTest, SUB_Service_throw_ExtConnectDone_0100, testing::ext::TestSize.Level1) -{ - GTEST_LOG_(INFO) << "ServiceThrowTest-begin SUB_Service_throw_ExtConnectDone_0100"; - try { - EXPECT_NE(service, nullptr); - string bundleName; - EXPECT_CALL(*sessionMock, BundleExtTimerStart(_, _)).WillOnce(Invoke([]() { - throw BError(BError::Codes::EXT_THROW_EXCEPTION); - })); - EXPECT_CALL(*sessionMock, RemoveExtInfo(_)).WillOnce(Invoke([]() { - throw BError(BError::Codes::EXT_THROW_EXCEPTION); - })); - EXPECT_CALL(*sessionMock, GetScenario()).WillOnce(Invoke([]() { - throw BError(BError::Codes::EXT_THROW_EXCEPTION); - return IServiceReverse::Scenario::UNDEFINED; - })); - service->ExtConnectDone(bundleName); - EXPECT_TRUE(true); - } catch (...) { - EXPECT_TRUE(false); - GTEST_LOG_(INFO) << "ServiceThrowTest-an exception occurred by ExtConnectDone."; - } - GTEST_LOG_(INFO) << "ServiceThrowTest-end SUB_Service_throw_ExtConnectDone_0100"; -} - /** * @tc.number: SUB_Service_throw_ClearSessionAndSchedInfo_0100 * @tc.name: SUB_Service_throw_ClearSessionAndSchedInfo_0100 @@ -776,10 +723,10 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_GetBackupInfo_0100, testing::ext::T EXPECT_NE(service, nullptr); BundleName bundleName; string result; - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw "未知错误"; })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); auto ret = service->GetBackupInfo(bundleName, result); EXPECT_EQ(ret, EPERM); } catch (...) { @@ -805,10 +752,10 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_UpdateTimer_0100, testing::ext::Tes EXPECT_NE(service, nullptr); BundleName bundleName; bool result = false; - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw "未知错误"; })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); auto ret = service->UpdateTimer(bundleName, 0, result); EXPECT_EQ(ret, EPERM); } catch (...) { @@ -838,6 +785,7 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_SADone_0100, testing::ext::TestSize throw BError(BError::Codes::EXT_THROW_EXCEPTION); return false; })); + EXPECT_CALL(*sessionMock, IsOnAllBundlesFinished()).WillOnce(Return(false)); auto ret = service->SADone(errCode, bundleName); EXPECT_EQ(ret, BError(BError::Codes::EXT_THROW_EXCEPTION).GetCode()); @@ -845,6 +793,7 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_SADone_0100, testing::ext::TestSize throw runtime_error("运行时错误"); return false; })); + EXPECT_CALL(*sessionMock, IsOnAllBundlesFinished()).WillOnce(Return(false)); ret = service->SADone(errCode, bundleName); EXPECT_EQ(ret, EPERM); @@ -852,6 +801,7 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_SADone_0100, testing::ext::TestSize throw "未知错误"; return false; })); + EXPECT_CALL(*sessionMock, IsOnAllBundlesFinished()).WillOnce(Return(false)); ret = service->SADone(errCode, bundleName); EXPECT_EQ(ret, EPERM); } catch (...) { @@ -876,24 +826,24 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_GetLocalCapabilitiesIncremental_010 try { EXPECT_NE(service, nullptr); vector bundleNames; - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw BError(BError::Codes::EXT_THROW_EXCEPTION); })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); auto ret = service->GetLocalCapabilitiesIncremental(bundleNames); EXPECT_EQ(-ret, BError(BError::Codes::EXT_THROW_EXCEPTION).GetCode()); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw runtime_error("运行时错误"); })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); ret = service->GetLocalCapabilitiesIncremental(bundleNames); EXPECT_EQ(-ret, EPERM); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw "未知错误"; })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); ret = service->GetLocalCapabilitiesIncremental(bundleNames); EXPECT_EQ(-ret, EPERM); } catch (...) { @@ -917,24 +867,24 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_GetAppLocalListAndDoIncrementalBack GTEST_LOG_(INFO) << "ServiceThrowTest-begin SUB_Service_throw_GetAppLocalListAndDoIncrementalBackup_0100"; try { EXPECT_NE(service, nullptr); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw BError(BError::Codes::EXT_THROW_EXCEPTION); })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); auto ret = service->GetAppLocalListAndDoIncrementalBackup(); EXPECT_EQ(ret, BError(BError::Codes::EXT_THROW_EXCEPTION).GetCode()); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw runtime_error("运行时错误"); })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); ret = service->GetAppLocalListAndDoIncrementalBackup(); EXPECT_EQ(ret, EPERM); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw "未知错误"; })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); ret = service->GetAppLocalListAndDoIncrementalBackup(); EXPECT_EQ(ret, EPERM); } catch (...) { @@ -963,6 +913,7 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_InitIncrementalBackupSession_0100, return 0; })); EXPECT_CALL(*sessionMock, Deactive(_, _)).WillOnce(Return()); + EXPECT_CALL(*sessionMock, GetScenario()).WillOnce(Return(IServiceReverse::Scenario::UNDEFINED)); auto ret = service->InitIncrementalBackupSession(nullptr); EXPECT_EQ(ret, BError(BError::Codes::EXT_THROW_EXCEPTION).GetCode()); } catch (...) { @@ -987,17 +938,17 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_AppendBundlesIncrementalBackupSessi try { EXPECT_NE(service, nullptr); vector bundlesToBackup; - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw BError(BError::Codes::EXT_THROW_EXCEPTION); })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); auto ret = service->AppendBundlesIncrementalBackupSession(bundlesToBackup); EXPECT_EQ(ret, BError(BError::Codes::EXT_THROW_EXCEPTION).GetCode()); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw "未知错误"; })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); ret = service->AppendBundlesIncrementalBackupSession(bundlesToBackup); EXPECT_EQ(ret, EPERM); } catch (...) { @@ -1023,17 +974,17 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_AppendBundlesIncrementalBackupSessi EXPECT_NE(service, nullptr); vector bundlesToBackup; vector infos; - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw BError(BError::Codes::EXT_THROW_EXCEPTION); })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); auto ret = service->AppendBundlesIncrementalBackupSession(bundlesToBackup, infos); EXPECT_EQ(ret, BError(BError::Codes::EXT_THROW_EXCEPTION).GetCode()); - EXPECT_CALL(*sessionMock, IncreaseSessionCnt()).WillOnce(Invoke([]() { + EXPECT_CALL(*sessionMock, IncreaseSessionCnt(_)).WillOnce(Invoke([]() { throw "未知错误"; })); - EXPECT_CALL(*sessionMock, DecreaseSessionCnt()).WillOnce(Return()); + EXPECT_CALL(*sessionMock, DecreaseSessionCnt(_)).WillOnce(Return()); ret = service->AppendBundlesIncrementalBackupSession(bundlesToBackup, infos); EXPECT_EQ(ret, EPERM); } catch (...) { @@ -1138,12 +1089,14 @@ HWTEST_F(ServiceThrowTest, SUB_Service_throw_AppIncrementalDone_0100, testing::e EXPECT_CALL(*sessionMock, VerifyBundleName(_)).WillOnce(Invoke([]() { throw BError(BError::Codes::EXT_THROW_EXCEPTION); })); + EXPECT_CALL(*sessionMock, IsOnAllBundlesFinished()).WillOnce(Return(false)); auto ret = service->AppIncrementalDone(0); EXPECT_EQ(ret, BError(BError::Codes::EXT_THROW_EXCEPTION).GetCode()); EXPECT_CALL(*sessionMock, VerifyBundleName(_)).WillOnce(Invoke([]() { throw "未知错误"; })); + EXPECT_CALL(*sessionMock, IsOnAllBundlesFinished()).WillOnce(Return(false)); ret = service->AppIncrementalDone(0); EXPECT_EQ(ret, EPERM); } catch (...) { diff --git a/tests/unittests/backup_sa/module_ipc/svc_backup_connection_test.cpp b/tests/unittests/backup_sa/module_ipc/svc_backup_connection_test.cpp index cfdfacc4c82a08e4edf864075401808661d4821b..886618eb67d31114ae2007c89e6234c87eeac685 100644 --- a/tests/unittests/backup_sa/module_ipc/svc_backup_connection_test.cpp +++ b/tests/unittests/backup_sa/module_ipc/svc_backup_connection_test.cpp @@ -41,7 +41,7 @@ public: static inline shared_ptr castMock = nullptr; }; -static void CallDied(const std::string &&name) +static void CallDied(const std::string &&name, bool isSecondCalled) { GTEST_LOG_(INFO) << "ServiceReverseProxyTest-CallDied SUCCESS"; } @@ -53,7 +53,7 @@ static void CallDone(const std::string &&name) void SvcBackupConnectionTest::SetUpTestCase() { - backupCon_ = sptr(new SvcBackupConnection(CallDied, CallDone)); + backupCon_ = sptr(new SvcBackupConnection(CallDied, CallDone, "com.example.app")); castMock = std::make_shared(); IfaceCastMock::cast = castMock; } diff --git a/tests/unittests/backup_sa/module_ipc/svc_extension_proxy_test.cpp b/tests/unittests/backup_sa/module_ipc/svc_extension_proxy_test.cpp index 0e54994bfe2084ae4db8eb254a31798a8b67ac9f..aa55e0dc00e928c014643a46ec7b341a0a453fa4 100644 --- a/tests/unittests/backup_sa/module_ipc/svc_extension_proxy_test.cpp +++ b/tests/unittests/backup_sa/module_ipc/svc_extension_proxy_test.cpp @@ -148,15 +148,17 @@ HWTEST_F(SvcExtensionProxyTest, SUB_Ext_Extension_proxy_HandleBackup_0100, testi GTEST_LOG_(INFO) << "SvcExtensionProxyTest-begin SUB_Ext_Extension_proxy_HandleBackup_0100"; try { EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteBool(_)).WillOnce(Return(true)); EXPECT_CALL(*mock_, SendRequest(_, _, _, _)).WillOnce(Return(EPERM)); EXPECT_TRUE(proxy_ != nullptr); - ErrCode ret = proxy_->HandleBackup(); + ErrCode ret = proxy_->HandleBackup(true); EXPECT_EQ(EPERM, ret); EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteBool(_)).WillOnce(Return(true)); EXPECT_CALL(*mock_, SendRequest(_, _, _, _)).WillOnce(Return(0)); EXPECT_CALL(*messageParcelMock_, ReadInt32()).WillOnce(Return(0)); - ret = proxy_->HandleBackup(); + ret = proxy_->HandleBackup(true); EXPECT_EQ(BError(BError::Codes::OK), ret); } catch (...) { EXPECT_TRUE(false); @@ -218,15 +220,17 @@ HWTEST_F(SvcExtensionProxyTest, SUB_Ext_Extension_proxy_HandleRestore_0100, test GTEST_LOG_(INFO) << "SvcExtensionProxyTest-begin SUB_Ext_Extension_proxy_HandleRestore_0100"; try { EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteBool(_)).WillOnce(Return(true)); EXPECT_CALL(*mock_, SendRequest(_, _, _, _)).WillOnce(Return(EPERM)); EXPECT_TRUE(proxy_ != nullptr); - ErrCode ret = proxy_->HandleRestore(); + ErrCode ret = proxy_->HandleRestore(true); EXPECT_EQ(EPERM, ret); EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteBool(_)).WillOnce(Return(true)); EXPECT_CALL(*mock_, SendRequest(_, _, _, _)).WillOnce(Return(0)); EXPECT_CALL(*messageParcelMock_, ReadInt32()).WillOnce(Return(0)); - ret = proxy_->HandleRestore(); + ret = proxy_->HandleRestore(true); EXPECT_EQ(BError(BError::Codes::OK), ret); } catch (...) { EXPECT_TRUE(false); @@ -287,6 +291,66 @@ HWTEST_F(SvcExtensionProxyTest, SUB_Ext_Extension_proxy_GetBackupInfo_0100, test GTEST_LOG_(INFO) << "SvcExtensionProxyTest-end SUB_Ext_Extension_proxy_GetBackupInfo_0100"; } +/** + * @tc.number: SUB_Ext_Extension_proxy_UpdateFdSendRate_0100 + * @tc.name: SUB_Ext_Extension_proxy_UpdateFdSendRate_0100 + * @tc.desc: 测试 HandleRestore 接口调用成功和失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(SvcExtensionProxyTest, SUB_Service_GetBackupInfoCmdHandle_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "SvcExtensionProxyTest-begin SUB_Ext_Extension_proxy_UpdateFdSendRate_0100"; + try { + std::string bundleName = "bundleName"; + int32_t sendRate = 0; + EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteString(_)).WillOnce(Return(false)); + EXPECT_TRUE(proxy_ != nullptr); + ErrCode ret = proxy_->UpdateFdSendRate(bundleName, sendRate); + EXPECT_EQ(EPERM, ret); + + EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteString(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteInt32(_)).WillOnce(Return(false)); + EXPECT_TRUE(proxy_ != nullptr); + ret = proxy_->UpdateFdSendRate(bundleName, sendRate); + EXPECT_EQ(EPERM, ret); + + EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteString(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteInt32(_)).WillOnce(Return(true)); + EXPECT_CALL(*mock_, SendRequest(_, _, _, _)).WillOnce(Return(EPERM)); + EXPECT_TRUE(proxy_ != nullptr); + ret = proxy_->UpdateFdSendRate(bundleName, sendRate); + EXPECT_EQ(EPERM, ret); + + EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteString(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteInt32(_)).WillOnce(Return(true)); + EXPECT_CALL(*mock_, SendRequest(_, _, _, _)).WillOnce(Return(NO_ERROR)); + EXPECT_CALL(*messageParcelMock_, ReadInt32(_)).WillOnce(Return(false)); + EXPECT_TRUE(proxy_ != nullptr); + ret = proxy_->UpdateFdSendRate(bundleName, sendRate); + EXPECT_EQ(BError(BError::Codes::OK), ret); + + EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteString(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteInt32(_)).WillOnce(Return(true)); + EXPECT_CALL(*mock_, SendRequest(_, _, _, _)).WillOnce(Return(NO_ERROR)); + EXPECT_CALL(*messageParcelMock_, ReadInt32(_)).WillOnce(Return(true)); + EXPECT_TRUE(proxy_ != nullptr); + ret = proxy_->UpdateFdSendRate(bundleName, sendRate); + EXPECT_EQ(BError(BError::Codes::OK), ret); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "SvcExtensionProxyTest-an exception occurred by UpdateFdSendRate."; + } + GTEST_LOG_(INFO) << "SvcExtensionProxyTest-end SUB_Ext_Extension_proxy_UpdateFdSendRate_0100"; +} + /** * @tc.number: SUB_Ext_Extension_proxy_GetIncrementalFileHandle_0100 * @tc.name: SUB_Ext_Extension_proxy_GetIncrementalFileHandle_0100 @@ -398,6 +462,51 @@ HWTEST_F(SvcExtensionProxyTest, SUB_Ext_Extension_proxy_HandleIncrementalBackup_ GTEST_LOG_(INFO) << "SvcExtensionProxyTest-end SUB_Ext_Extension_proxy_HandleIncrementalBackup_0100"; } +/** + * @tc.number: SUB_Ext_Extension_proxy_IncrementalOnBackup_0100 + * @tc.name: SUB_Ext_Extension_proxy_IncrementalOnBackup_0100 + * @tc.desc: 测试 IncrementalOnBackup 接口调用成功和失败 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(SvcExtensionProxyTest, SUB_Ext_Extension_proxy_IncrementalOnBackup_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "SvcExtensionProxyTest-begin SUB_Ext_Extension_proxy_IncrementalOnBackup_0100"; + try { + EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(false)); + EXPECT_CALL(*messageParcelMock_, WriteBool(_)).WillOnce(Return(true)); + EXPECT_TRUE(proxy_ != nullptr); + ErrCode ret = proxy_->IncrementalOnBackup(true); + EXPECT_NE(ret, ErrCode(BError::Codes::OK)); + + EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteBool(_)).WillOnce(Return(false)); + EXPECT_TRUE(proxy_ != nullptr); + ret = proxy_->IncrementalOnBackup(true); + EXPECT_NE(ret, ErrCode(BError::Codes::OK)); + + EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteBool(_)).WillOnce(Return(true)); + EXPECT_CALL(*mock_, SendRequest(_, _, _, _)).WillOnce(Return(EPERM)); + EXPECT_TRUE(proxy_ != nullptr); + ret = proxy_->IncrementalOnBackup(true); + EXPECT_EQ(ret, ErrCode(EPERM)); + + EXPECT_CALL(*messageParcelMock_, WriteInterfaceToken(_)).WillOnce(Return(true)); + EXPECT_CALL(*messageParcelMock_, WriteBool(_)).WillOnce(Return(true)); + EXPECT_CALL(*mock_, SendRequest(_, _, _, _)).WillOnce(Return(NO_ERROR)); + EXPECT_TRUE(proxy_ != nullptr); + ret = proxy_->IncrementalOnBackup(true); + EXPECT_EQ(ret, ErrCode(BError::Codes::OK)); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "SvcExtensionProxyTest-an exception occurred by IncrementalOnBackup."; + } + GTEST_LOG_(INFO) << "SvcExtensionProxyTest-end SUB_Ext_Extension_proxy_IncrementalOnBackup_0100"; +} + /** * @tc.number: SUB_Ext_Extension_proxy_GetIncrementalBackupFileHandle_0100 * @tc.name: SUB_Ext_Extension_proxy_GetIncrementalBackupFileHandle_0100 diff --git a/tests/unittests/backup_sa/module_ipc/svc_restore_deps_manager_test.cpp b/tests/unittests/backup_sa/module_ipc/svc_restore_deps_manager_test.cpp index 6668c0246e9ec39a457cfdc117a7b0f74d440bf8..3cb2a0082767bfbc57f06253ecaec7921afef187 100644 --- a/tests/unittests/backup_sa/module_ipc/svc_restore_deps_manager_test.cpp +++ b/tests/unittests/backup_sa/module_ipc/svc_restore_deps_manager_test.cpp @@ -107,8 +107,8 @@ HWTEST_F(SvcRestoreDepsManagerTest, SUB_SvcRestoreDepsManager_GetRestoreBundleNa vector bundleInfos {info1, info2}; RestoreTypeEnum restoreType = RESTORE_DATA_WAIT_SEND; auto bundleNames = SvcRestoreDepsManager::GetInstance().GetRestoreBundleNames(bundleInfos, restoreType); - EXPECT_EQ(bundleNames.size(), 1); - EXPECT_FALSE(SvcRestoreDepsManager::GetInstance().IsAllBundlesRestored()); + EXPECT_EQ(bundleNames.size(), 2); + EXPECT_TRUE(SvcRestoreDepsManager::GetInstance().IsAllBundlesRestored()); ClearCache(); GTEST_LOG_(INFO) << "SvcRestoreDepsManagerTest-end SUB_SvcRestoreDepsManager_GetRestoreBundleNames_0200"; } diff --git a/tests/unittests/backup_sa/module_ipc/svc_session_manager_ex_test.cpp b/tests/unittests/backup_sa/module_ipc/svc_session_manager_ex_test.cpp new file mode 100644 index 0000000000000000000000000000000000000000..cdd655b42ba803240768ca0c1c7114bacc65d328 --- /dev/null +++ b/tests/unittests/backup_sa/module_ipc/svc_session_manager_ex_test.cpp @@ -0,0 +1,149 @@ +/* + * Copyright (c) 2024 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @tc.number: SUB_backup_sa_session_GetLastIncrementalTime_0100 + * @tc.name: SUB_backup_sa_session_GetLastIncrementalTime_0100 + * @tc.desc: 测试 GetLastIncrementalTime + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_GetLastIncrementalTime_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "SvcSessionManagerTest-begin SUB_backup_sa_session_GetLastIncrementalTime_0100"; + try { + try { + EXPECT_TRUE(sessionManagerPtr_ != nullptr); + sessionManagerPtr_->impl_.clientToken = 0; + sessionManagerPtr_->GetLastIncrementalTime(BUNDLE_NAME); + EXPECT_TRUE(false); + } catch (BError &err) { + EXPECT_EQ(err.GetRawCode(), BError::Codes::SA_INVAL_ARG); + } + + sessionManagerPtr_->impl_.clientToken = CLIENT_TOKEN_ID; + sessionManagerPtr_->impl_.backupExtNameMap.clear(); + sessionManagerPtr_->impl_.backupExtNameMap[BUNDLE_NAME] = {}; + sessionManagerPtr_->GetLastIncrementalTime(BUNDLE_NAME); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "SvcSessionManagerTest-an exception occurred by GetLastIncrementalTime."; + } + GTEST_LOG_(INFO) << "SvcSessionManagerTest-end SUB_backup_sa_session_GetLastIncrementalTime_0100"; +} + +/** + * @tc.number: SUB_backup_sa_session_DecreaseSessionCnt_0100 + * @tc.name: SUB_backup_sa_session_DecreaseSessionCnt_0100 + * @tc.desc: 测试 DecreaseSessionCnt + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_DecreaseSessionCnt_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "SvcSessionManagerTest-begin SUB_backup_sa_session_DecreaseSessionCnt_0100"; + try { + sessionManagerPtr_->DecreaseSessionCnt(__PRETTY_FUNCTION__); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "SvcSessionManagerTest-an exception occurred by DecreaseSessionCnt."; + } + GTEST_LOG_(INFO) << "SvcSessionManagerTest-end SUB_backup_sa_session_DecreaseSessionCnt_0100"; +} + +/** + * @tc.number: SUB_backup_sa_session_DecreaseSessionCnt_0101 + * @tc.name: SUB_backup_sa_session_DecreaseSessionCnt_0101 + * @tc.desc: 测试 DecreaseSessionCnt + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_DecreaseSessionCnt_0101, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "SvcSessionManagerTest-begin SUB_backup_sa_session_DecreaseSessionCnt_0101"; + try { + sessionManagerPtr_->IncreaseSessionCnt(__PRETTY_FUNCTION__); + sessionManagerPtr_->DecreaseSessionCnt(__PRETTY_FUNCTION__); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "SvcSessionManagerTest-an exception occurred by DecreaseSessionCnt."; + } + GTEST_LOG_(INFO) << "SvcSessionManagerTest-end SUB_backup_sa_session_DecreaseSessionCnt_0101"; +} + +/** + * @tc.number: SUB_backup_sa_session_GetServiceSchedAction_0104 + * @tc.name: SUB_backup_sa_session_GetServiceSchedAction_0104 + * @tc.desc: 测试 GetServiceSchedAction 获取状态 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_GetServiceSchedAction_0104, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "SvcSessionManagerTest-begin SUB_backup_sa_session_GetServiceSchedAction_0104"; + try { + try { + EXPECT_TRUE(sessionManagerPtr_ != nullptr); + sessionManagerPtr_->impl_.clientToken = 0; + sessionManagerPtr_->GetServiceSchedAction(BUNDLE_NAME); + EXPECT_TRUE(true); + } catch (BError &err) { + EXPECT_EQ(err.GetRawCode(), BError::Codes::SA_INVAL_ARG); + } + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "SvcSessionManagerTest-an exception occurred by GetServiceSchedAction."; + } + GTEST_LOG_(INFO) << "SvcSessionManagerTest-end SUB_backup_sa_session_GetServiceSchedAction_0104"; +} + +/** + * @tc.number: SUB_backup_sa_session_GetServiceSchedAction_0105 + * @tc.name: SUB_backup_sa_session_GetServiceSchedAction_0105 + * @tc.desc: 测试 GetServiceSchedAction 获取状态 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_GetServiceSchedAction_0105, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "SvcSessionManagerTest-begin SUB_backup_sa_session_GetServiceSchedAction_0105"; + try { + try { + EXPECT_TRUE(sessionManagerPtr_ != nullptr); + sessionManagerPtr_->impl_.clientToken = 0; + sessionManagerPtr_->SetServiceSchedAction(BUNDLE_NAME, BConstants::ServiceSchedAction::RUNNING); + EXPECT_TRUE(true); + } catch (BError &err) { + EXPECT_EQ(err.GetRawCode(), BError::Codes::SA_INVAL_ARG); + } + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "SvcSessionManagerTest-an exception occurred by GetServiceSchedAction."; + } + GTEST_LOG_(INFO) << "SvcSessionManagerTest-end SUB_backup_sa_session_GetServiceSchedAction_0105"; +} \ No newline at end of file diff --git a/tests/unittests/backup_sa/module_ipc/svc_session_manager_test.cpp b/tests/unittests/backup_sa/module_ipc/svc_session_manager_test.cpp index a60ac156d26b7ba0f3b9153cb248b7d331808718..b74452b8c50d164c63c37023cc0e770b1203c837 100644 --- a/tests/unittests/backup_sa/module_ipc/svc_session_manager_test.cpp +++ b/tests/unittests/backup_sa/module_ipc/svc_session_manager_test.cpp @@ -507,13 +507,13 @@ HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_GetBackupAbilityExt_0100, EXPECT_TRUE(sessionManagerPtr_ != nullptr); sessionManagerPtr_->reversePtr_ = nullptr; auto ret = sessionManagerPtr_->GetBackupAbilityExt(BUNDLE_NAME); - ret->callDied_(""); + ret->callDied_("", false); ret->callConnected_(""); EXPECT_TRUE(true); sessionManagerPtr_->reversePtr_ = servicePtr_; ret = sessionManagerPtr_->GetBackupAbilityExt(BUNDLE_NAME); - ret->callDied_(""); + ret->callDied_("", false); ret->callConnected_(""); EXPECT_TRUE(true); } catch (...) { @@ -627,6 +627,92 @@ HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_GetExtFileNameRequest_0100 GTEST_LOG_(INFO) << "SvcSessionManagerTest-end SUB_backup_sa_session_GetExtFileNameRequest_0100"; } +/** + * @tc.number: SUB_backup_sa_session_GetExtFileNameRequest_0101 + * @tc.name: SUB_backup_sa_session_GetExtFileNameRequest_0101 + * @tc.desc: 测试 GetExtFileNameRequest 获取暂存真实文件请求 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_GetExtFileNameRequest_0101, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "SvcSessionManagerTest-begin SUB_backup_sa_session_GetExtFileNameRequest_0101"; + try { + try { + EXPECT_TRUE(sessionManagerPtr_ != nullptr); + sessionManagerPtr_->impl_.clientToken = 0; + sessionManagerPtr_->GetExtFileNameRequest(BUNDLE_NAME); + EXPECT_TRUE(true); + } catch (BError &err) { + EXPECT_EQ(err.GetRawCode(), BError::Codes::SA_INVAL_ARG); + } + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "SvcSessionManagerTest-an exception occurred by GetExtFileNameRequest."; + } + GTEST_LOG_(INFO) << "SvcSessionManagerTest-end SUB_backup_sa_session_GetExtFileNameRequest_0101"; +} + +/** + * @tc.number: SUB_backup_sa_session_GetExtFileNameRequest_0102 + * @tc.name: SUB_backup_sa_session_GetExtFileNameRequest_0102 + * @tc.desc: 测试 GetExtFileNameRequest 获取暂存真实文件请求 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_GetExtFileNameRequest_0102, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "SvcSessionManagerTest-begin SUB_backup_sa_session_GetExtFileNameRequest_0102"; + try { + try { + EXPECT_TRUE(sessionManagerPtr_ != nullptr); + sessionManagerPtr_->impl_.clientToken = CLIENT_TOKEN_ID; + sessionManagerPtr_->impl_.scenario = IServiceReverse::Scenario::UNDEFINED; + sessionManagerPtr_->GetExtFileNameRequest(BUNDLE_NAME); + EXPECT_TRUE(true); + } catch (BError &err) { + EXPECT_EQ(err.GetRawCode(), BError::Codes::SA_INVAL_ARG); + } + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "SvcSessionManagerTest-an exception occurred by GetExtFileNameRequest."; + } + GTEST_LOG_(INFO) << "SvcSessionManagerTest-end SUB_backup_sa_session_GetExtFileNameRequest_0102"; +} + +/** + * @tc.number: SUB_backup_sa_session_GetExtFileNameRequest_0103 + * @tc.name: SUB_backup_sa_session_GetExtFileNameRequest_0103 + * @tc.desc: 测试 GetExtFileNameRequest 获取暂存真实文件请求 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_GetExtFileNameRequest_0103, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "SvcSessionManagerTest-begin SUB_backup_sa_session_GetExtFileNameRequest_0103"; + try { + try { + EXPECT_TRUE(sessionManagerPtr_ != nullptr); + sessionManagerPtr_->impl_.clientToken = CLIENT_TOKEN_ID; + sessionManagerPtr_->impl_.scenario = IServiceReverse::Scenario::RESTORE; + sessionManagerPtr_->GetExtFileNameRequest(BUNDLE_NAME); + EXPECT_TRUE(true); + } catch (BError &err) { + EXPECT_EQ(err.GetRawCode(), BError::Codes::SA_INVAL_ARG); + } + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "SvcSessionManagerTest-an exception occurred by GetExtFileNameRequest."; + } + GTEST_LOG_(INFO) << "SvcSessionManagerTest-end SUB_backup_sa_session_GetExtFileNameRequest_0103"; +} + /** * @tc.number: SUB_backup_sa_session_GetExtConnection_0100 * @tc.name: SUB_backup_sa_session_GetExtConnection_0100 @@ -668,7 +754,7 @@ HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_GetExtConnection_0100, tes } BackupExtInfo info; - info.backUpConnection = sptr(new SvcBackupConnection(nullptr, nullptr)); + info.backUpConnection = sptr(new SvcBackupConnection(nullptr, nullptr, BUNDLE_NAME)); sessionManagerPtr_->impl_.clientToken = CLIENT_TOKEN_ID; sessionManagerPtr_->impl_.backupExtNameMap[BUNDLE_NAME] = info; auto ret = sessionManagerPtr_->GetExtConnection(BUNDLE_NAME); @@ -774,6 +860,7 @@ HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_GetSchedBundleName_0100, t try { string bundleName; EXPECT_TRUE(sessionManagerPtr_ != nullptr); + sessionManagerPtr_->SetIsReadyLaunch(BUNDLE_NAME); bool condition = sessionManagerPtr_->GetSchedBundleName(bundleName); EXPECT_EQ(bundleName, BUNDLE_NAME); EXPECT_TRUE(condition); @@ -1259,7 +1346,7 @@ HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_SetBundleRestoreType_0100, sessionManagerPtr_->impl_.backupExtNameMap.clear(); sessionManagerPtr_->impl_.backupExtNameMap[BUNDLE_NAME] = {}; sessionManagerPtr_->SetBundleRestoreType(BUNDLE_NAME, RESTORE_DATA_READDY); - EXPECT_EQ(sessionManagerPtr_->impl_.restoreDataType, RESTORE_DATA_READDY); + EXPECT_EQ(sessionManagerPtr_->impl_.backupExtNameMap[BUNDLE_NAME].restoreType, RESTORE_DATA_READDY); } catch (...) { EXPECT_TRUE(false); GTEST_LOG_(INFO) << "SvcSessionManagerTest-an exception occurred by SetBundleRestoreType."; @@ -1618,47 +1705,47 @@ HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_SetBundleDataSize_0100, te } /** - * @tc.number: SUB_backup_sa_session_BundleExtTimerStart_0100 - * @tc.name: SUB_backup_sa_session_BundleExtTimerStart_0100 - * @tc.desc: 测试 BundleExtTimerStart + * @tc.number: SUB_backup_sa_session_StartFwkTimer_0100 + * @tc.name: SUB_backup_sa_session_StartFwkTimer_0100 + * @tc.desc: 测试 StartFwkTimer * @tc.size: MEDIUM * @tc.type: FUNC * @tc.level Level 1 * @tc.require: I6F3GV */ -HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_BundleExtTimerStart_0100, testing::ext::TestSize.Level1) +HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_StartFwkTimer_0100, testing::ext::TestSize.Level1) { - GTEST_LOG_(INFO) << "SvcSessionManagerTest-begin SUB_backup_sa_session_BundleExtTimerStart_0100"; + GTEST_LOG_(INFO) << "SvcSessionManagerTest-begin SUB_backup_sa_session_StartFwkTimer_0100"; try { auto callback = []() -> void {}; - try { - EXPECT_TRUE(sessionManagerPtr_ != nullptr); - sessionManagerPtr_->impl_.clientToken = 0; - sessionManagerPtr_->BundleExtTimerStart(BUNDLE_NAME, callback); - EXPECT_TRUE(false); - } catch (BError &err) { - EXPECT_EQ(err.GetRawCode(), BError::Codes::SA_INVAL_ARG); - } + EXPECT_TRUE(sessionManagerPtr_ != nullptr); + sessionManagerPtr_->impl_.clientToken = 0; + auto ret = sessionManagerPtr_->StartFwkTimer(BUNDLE_NAME, callback); + EXPECT_FALSE(ret); BackupExtInfo info; - info.timerStatus = false; + info.fwkTimerStatus = false; sessionManagerPtr_->impl_.clientToken = CLIENT_TOKEN_ID; sessionManagerPtr_->impl_.backupExtNameMap.clear(); sessionManagerPtr_->impl_.backupExtNameMap[BUNDLE_NAME] = info; - sessionManagerPtr_->BundleExtTimerStart(BUNDLE_NAME, callback); - EXPECT_TRUE(true); + ret = sessionManagerPtr_->StartFwkTimer(BUNDLE_NAME, callback); + EXPECT_TRUE(ret); + ret = sessionManagerPtr_->StopFwkTimer(BUNDLE_NAME); + EXPECT_TRUE(ret); - info.timerStatus = true; + info.fwkTimerStatus = true; sessionManagerPtr_->impl_.clientToken = CLIENT_TOKEN_ID; sessionManagerPtr_->impl_.backupExtNameMap.clear(); sessionManagerPtr_->impl_.backupExtNameMap[BUNDLE_NAME] = info; - sessionManagerPtr_->BundleExtTimerStart(BUNDLE_NAME, callback); - EXPECT_TRUE(true); + ret = sessionManagerPtr_->StartFwkTimer(BUNDLE_NAME, callback); + EXPECT_FALSE(ret); + ret = sessionManagerPtr_->StopFwkTimer(BUNDLE_NAME); + EXPECT_TRUE(ret); } catch (...) { EXPECT_TRUE(false); - GTEST_LOG_(INFO) << "SvcSessionManagerTest-an exception occurred by BundleExtTimerStart."; + GTEST_LOG_(INFO) << "SvcSessionManagerTest-an exception occurred by StartFwkTimer."; } - GTEST_LOG_(INFO) << "SvcSessionManagerTest-end SUB_backup_sa_session_BundleExtTimerStart_0100"; + GTEST_LOG_(INFO) << "SvcSessionManagerTest-end SUB_backup_sa_session_StartFwkTimer_0100"; } /** @@ -1675,28 +1762,26 @@ HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_UpdateTimer_0100, testing: GTEST_LOG_(INFO) << "SvcSessionManagerTest-begin SUB_backup_sa_session_UpdateTimer_0100"; try { auto callback = []() -> void {}; - try { - EXPECT_TRUE(sessionManagerPtr_ != nullptr); - sessionManagerPtr_->impl_.clientToken = 0; - sessionManagerPtr_->UpdateTimer(BUNDLE_NAME, 30, callback); - EXPECT_TRUE(false); - } catch (BError &err) { - EXPECT_EQ(err.GetRawCode(), BError::Codes::SA_INVAL_ARG); - } + EXPECT_TRUE(sessionManagerPtr_ != nullptr); + sessionManagerPtr_->impl_.clientToken = 0; + auto ret = sessionManagerPtr_->UpdateTimer(BUNDLE_NAME, BConstants::DEFAULT_TIMEOUT, callback); + EXPECT_FALSE(ret); - BackupExtInfo info; - info.timerStatus = false; sessionManagerPtr_->impl_.clientToken = CLIENT_TOKEN_ID; sessionManagerPtr_->impl_.backupExtNameMap.clear(); + EXPECT_THROW(sessionManagerPtr_->UpdateTimer(BUNDLE_NAME, BConstants::TIMEOUT_INVALID, callback), BError); + + BackupExtInfo info; + info.extTimerStatus = false; + sessionManagerPtr_->impl_.backupExtNameMap.clear(); sessionManagerPtr_->impl_.backupExtNameMap[BUNDLE_NAME] = info; - auto ret = sessionManagerPtr_->UpdateTimer(BUNDLE_NAME, 30, callback); - EXPECT_FALSE(ret); + ret = sessionManagerPtr_->UpdateTimer(BUNDLE_NAME, BConstants::DEFAULT_TIMEOUT, callback); + EXPECT_TRUE(ret); - info.timerStatus = true; - sessionManagerPtr_->impl_.clientToken = CLIENT_TOKEN_ID; + info.extTimerStatus = true; sessionManagerPtr_->impl_.backupExtNameMap.clear(); sessionManagerPtr_->impl_.backupExtNameMap[BUNDLE_NAME] = info; - ret = sessionManagerPtr_->UpdateTimer(BUNDLE_NAME, 30, callback); + ret = sessionManagerPtr_->UpdateTimer(BUNDLE_NAME, BConstants::DEFAULT_TIMEOUT, callback); EXPECT_TRUE(ret); } catch (...) { EXPECT_TRUE(false); @@ -1706,46 +1791,42 @@ HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_UpdateTimer_0100, testing: } /** - * @tc.number: SUB_backup_sa_session_BundleExtTimerStop_0100 - * @tc.name: SUB_backup_sa_session_BundleExtTimerStop_0100 - * @tc.desc: 测试 BundleExtTimerStop + * @tc.number: SUB_backup_sa_session_StopFwkTimer_0100 + * @tc.name: SUB_backup_sa_session_StopFwkTimer_0100 + * @tc.desc: 测试 StopFwkTimer * @tc.size: MEDIUM * @tc.type: FUNC * @tc.level Level 1 * @tc.require: I6F3GV */ -HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_BundleExtTimerStop_0100, testing::ext::TestSize.Level1) +HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_StopFwkTimer_0100, testing::ext::TestSize.Level1) { - GTEST_LOG_(INFO) << "SvcSessionManagerTest-begin SUB_backup_sa_session_BundleExtTimerStop_0100"; + GTEST_LOG_(INFO) << "SvcSessionManagerTest-begin SUB_backup_sa_session_StopFwkTimer_0100"; try { - try { - EXPECT_TRUE(sessionManagerPtr_ != nullptr); - sessionManagerPtr_->impl_.clientToken = 0; - sessionManagerPtr_->BundleExtTimerStop(BUNDLE_NAME); - EXPECT_TRUE(false); - } catch (BError &err) { - EXPECT_EQ(err.GetRawCode(), BError::Codes::SA_INVAL_ARG); - } + EXPECT_TRUE(sessionManagerPtr_ != nullptr); + sessionManagerPtr_->impl_.clientToken = 0; + auto ret = sessionManagerPtr_->StopFwkTimer(BUNDLE_NAME); + EXPECT_FALSE(ret); BackupExtInfo info; - info.timerStatus = false; + info.fwkTimerStatus = false; sessionManagerPtr_->impl_.clientToken = CLIENT_TOKEN_ID; sessionManagerPtr_->impl_.backupExtNameMap.clear(); sessionManagerPtr_->impl_.backupExtNameMap[BUNDLE_NAME] = info; - sessionManagerPtr_->BundleExtTimerStop(BUNDLE_NAME); - EXPECT_TRUE(true); + ret = sessionManagerPtr_->StopFwkTimer(BUNDLE_NAME); + EXPECT_TRUE(ret); - info.timerStatus = true; + info.fwkTimerStatus = true; sessionManagerPtr_->impl_.clientToken = CLIENT_TOKEN_ID; sessionManagerPtr_->impl_.backupExtNameMap.clear(); sessionManagerPtr_->impl_.backupExtNameMap[BUNDLE_NAME] = info; - sessionManagerPtr_->BundleExtTimerStop(BUNDLE_NAME); - EXPECT_TRUE(true); + ret = sessionManagerPtr_->StopFwkTimer(BUNDLE_NAME); + EXPECT_TRUE(ret); } catch (...) { EXPECT_TRUE(false); - GTEST_LOG_(INFO) << "SvcSessionManagerTest-an exception occurred by BundleExtTimerStop."; + GTEST_LOG_(INFO) << "SvcSessionManagerTest-an exception occurred by StopFwkTimer."; } - GTEST_LOG_(INFO) << "SvcSessionManagerTest-end SUB_backup_sa_session_BundleExtTimerStop_0100"; + GTEST_LOG_(INFO) << "SvcSessionManagerTest-end SUB_backup_sa_session_StopFwkTimer_0100"; } /** @@ -1762,16 +1843,16 @@ HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_ClearSessionData_0100, tes GTEST_LOG_(INFO) << "SvcSessionManagerTest-begin SUB_backup_sa_session_ClearSessionData_0100"; try { BackupExtInfo info; - info.timerStatus = true; + info.fwkTimerStatus = true; info.schedAction = BConstants::ServiceSchedAction::RUNNING; - info.backUpConnection = sptr(new SvcBackupConnection(nullptr, nullptr)); + info.backUpConnection = sptr(new SvcBackupConnection(nullptr, nullptr, BUNDLE_NAME)); EXPECT_TRUE(sessionManagerPtr_ != nullptr); sessionManagerPtr_->impl_.backupExtNameMap.clear(); sessionManagerPtr_->impl_.backupExtNameMap[BUNDLE_NAME] = info; sessionManagerPtr_->ClearSessionData(); EXPECT_TRUE(true); - info.timerStatus = false; + info.fwkTimerStatus = false; info.schedAction = BConstants::ServiceSchedAction::WAIT; sessionManagerPtr_->impl_.backupExtNameMap.clear(); sessionManagerPtr_->impl_.backupExtNameMap[BUNDLE_NAME] = info; @@ -1886,37 +1967,5 @@ HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_GetIncrementalManifestFd_0 GTEST_LOG_(INFO) << "SvcSessionManagerTest-end SUB_backup_sa_session_GetIncrementalManifestFd_0100"; } -/** - * @tc.number: SUB_backup_sa_session_GetLastIncrementalTime_0100 - * @tc.name: SUB_backup_sa_session_GetLastIncrementalTime_0100 - * @tc.desc: 测试 GetLastIncrementalTime - * @tc.size: MEDIUM - * @tc.type: FUNC - * @tc.level Level 1 - * @tc.require: I6F3GV - */ -HWTEST_F(SvcSessionManagerTest, SUB_backup_sa_session_GetLastIncrementalTime_0100, testing::ext::TestSize.Level1) -{ - GTEST_LOG_(INFO) << "SvcSessionManagerTest-begin SUB_backup_sa_session_GetLastIncrementalTime_0100"; - try { - try { - EXPECT_TRUE(sessionManagerPtr_ != nullptr); - sessionManagerPtr_->impl_.clientToken = 0; - sessionManagerPtr_->GetLastIncrementalTime(BUNDLE_NAME); - EXPECT_TRUE(false); - } catch (BError &err) { - EXPECT_EQ(err.GetRawCode(), BError::Codes::SA_INVAL_ARG); - } - - sessionManagerPtr_->impl_.clientToken = CLIENT_TOKEN_ID; - sessionManagerPtr_->impl_.backupExtNameMap.clear(); - sessionManagerPtr_->impl_.backupExtNameMap[BUNDLE_NAME] = {}; - sessionManagerPtr_->GetLastIncrementalTime(BUNDLE_NAME); - EXPECT_TRUE(true); - } catch (...) { - EXPECT_TRUE(false); - GTEST_LOG_(INFO) << "SvcSessionManagerTest-an exception occurred by GetLastIncrementalTime."; - } - GTEST_LOG_(INFO) << "SvcSessionManagerTest-end SUB_backup_sa_session_GetLastIncrementalTime_0100"; -} +#include "svc_session_manager_ex_test.cpp" } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_sa/session/b_incremental_session_test.cpp b/tests/unittests/backup_sa/session/b_incremental_session_test.cpp index 9adae7f71358b619f254981808f50a8508eb923b..54d192c5f1d87149eb1fb413255d28630e0aca9b 100644 --- a/tests/unittests/backup_sa/session/b_incremental_session_test.cpp +++ b/tests/unittests/backup_sa/session/b_incremental_session_test.cpp @@ -643,4 +643,34 @@ HWTEST_F(IncrementalSessionTest, SUB_b_incremental_session_test_1900, testing::e GTEST_LOG_(INFO) << "IncrementalSessionTest-end SUB_b_incremental_session_test_1900"; } +/** + * @tc.number: SUB_b_incremental_session_test_2000 + * @tc.name: SUB_b_incremental_session_test_2000 + * @tc.desc: 测试 PublishSAFile 接口 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesI9KPRL + */ +HWTEST_F(IncrementalSessionTest, SUB_b_incremental_session_test_2000, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "IncrementalSessionTest-begin SUB_b_incremental_session_test_2000"; + try { + ServiceProxy::serviceProxy_ = nullptr; + BFileInfo fileInfo; + UniqueFd fd; + EXPECT_TRUE(restoreSession != nullptr); + auto err = restoreSession->PublishSAFile(fileInfo, move(fd)); + EXPECT_EQ(err, BError(BError::Codes::SDK_BROKEN_IPC).GetCode()); + + EXPECT_CALL(*proxy, PublishIncrementalFile(_)).WillOnce(Return(0)); + ServiceProxy::serviceProxy_ = proxy; + err = restoreSession->PublishSAFile(fileInfo, move(fd)); + EXPECT_EQ(err, BError(BError::Codes::OK).GetCode()); + } catch (...) { + EXPECT_TRUE(true); + GTEST_LOG_(INFO) << "IncrementalSessionTest-an exception occurred by RemoveExtConn."; + } + GTEST_LOG_(INFO) << "IncrementalSessionTest-end SUB_b_incremental_session_test_2000"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_sa/session/service_proxy_mock.cpp b/tests/unittests/backup_sa/session/service_proxy_mock.cpp index 7220842562c3aafab49350bf5e33da678c37ed05..ebcf680de3908d865e9a8acc87deccb01a729d56 100644 --- a/tests/unittests/backup_sa/session/service_proxy_mock.cpp +++ b/tests/unittests/backup_sa/session/service_proxy_mock.cpp @@ -157,7 +157,17 @@ ErrCode ServiceProxy::GetBackupInfo(std::string &bundleName, std::string &result return BError(BError::Codes::OK); } -ErrCode ServiceProxy::UpdateTimer(BundleName &bundleName, uint32_t timeOut, bool &result) +ErrCode ServiceProxy::UpdateTimer(BundleName &bundleName, uint32_t timeout, bool &result) +{ + return BError(BError::Codes::OK); +} + +ErrCode ServiceProxy::StartExtTimer(bool &isExtStart) +{ + return BError(BError::Codes::OK); +} + +ErrCode ServiceProxy::StartFwkTimer(bool &isFwkStart) { return BError(BError::Codes::OK); } @@ -167,6 +177,16 @@ ErrCode ServiceProxy::UpdateSendRate(std::string &bundleName, int32_t sendRate, return BError(BError::Codes::OK); } +ErrCode ServiceProxy::ReportAppProcessInfo(const std::string processInfo, const BackupRestoreScenario sennario) +{ + return BError(BError::Codes::OK); +} + +sptr ServiceProxy::GetServiceProxyPointer() +{ + return serviceProxy_; +} + sptr ServiceProxy::GetInstance() { return serviceProxy_; diff --git a/tests/unittests/backup_sa/session/service_proxy_mock.h b/tests/unittests/backup_sa/session/service_proxy_mock.h index 9bbf0ba3c8cea709822c58e8b7f197487fba5bee..946043b332eb1876807cefb6740d47cd8863682b 100644 --- a/tests/unittests/backup_sa/session/service_proxy_mock.h +++ b/tests/unittests/backup_sa/session/service_proxy_mock.h @@ -57,7 +57,7 @@ public: MOCK_METHOD1(AppIncrementalDone, ErrCode(ErrCode errCode)); MOCK_METHOD2(GetIncrementalFileHandle, ErrCode(const std::string &bundleName, const std::string &fileName)); MOCK_METHOD2(GetBackupInfo, ErrCode(BundleName &bundleName, std::string &result)); - MOCK_METHOD3(UpdateTimer, ErrCode(BundleName &bundleName, uint32_t timeOut, bool &result)); + MOCK_METHOD3(UpdateTimer, ErrCode(BundleName &bundleName, uint32_t timeout, bool &result)); MOCK_METHOD0(GetAppLocalListAndDoIncrementalBackup, ErrCode()); }; } // End of namespace OHOS::FileManagement::Backup diff --git a/tests/unittests/backup_tools/BUILD.gn b/tests/unittests/backup_tools/BUILD.gn index 15fa2bced395cb897c616f5070d24ed26d312362..0a0c1d50a5090e3fa56cf0a24ab54176d2790ff6 100644 --- a/tests/unittests/backup_tools/BUILD.gn +++ b/tests/unittests/backup_tools/BUILD.gn @@ -1,4 +1,4 @@ -# Copyright (c) 2022-2023 Huawei Device Co., Ltd. +# Copyright (c) 2022-2024 Huawei Device Co., Ltd. # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. # You may obtain a copy of the License at @@ -21,12 +21,16 @@ ohos_unittest("backup_tool_test") { sources = [ "${path_backup_mock}/b_filesystem/b_file_mock.cpp", + "${path_backup}/frameworks/native/backup_kit_inner/src/b_incremental_backup_session.cpp", + "${path_backup}/frameworks/native/backup_kit_inner/src/b_incremental_data.cpp", + "${path_backup}/frameworks/native/backup_kit_inner/src/service_incremental_reverse.cpp", + "${path_backup}/frameworks/native/backup_kit_inner/src/service_reverse.cpp", + "${path_backup}/frameworks/native/backup_kit_inner/src/service_reverse_stub.cpp", "${path_backup}/tests/mock/backup_kit_inner/b_session_backup_mock.cpp", "${path_backup}/tools/backup_tool/src/tools_op.cpp", "${path_backup}/tools/backup_tool/src/tools_op_backup.cpp", "${path_backup}/tools/backup_tool/src/tools_op_check_sa.cpp", "${path_backup}/tools/backup_tool/src/tools_op_help.cpp", - "${path_backup}/tools/backup_tool/src/tools_op_incremental_backup.cpp", "backup_tool/tools_op_backup_test.cpp", "backup_tool/tools_op_check_sa_test.cpp", "backup_tool/tools_op_help_test.cpp", @@ -37,9 +41,11 @@ ohos_unittest("backup_tool_test") { include_dirs = [ "${path_base}/include", + "${path_backup}/frameworks/native/backup_kit_inner/include", "${path_backup}/interfaces/inner_api/native/backup_kit_inner/impl", "${path_backup}/interfaces/inner_api/native/backup_kit_inner", "${path_backup}/tools/backup_tool/include", + "${path_backup}/tools/backup_tool/src", ] include_dirs += backup_mock_utils_include @@ -81,10 +87,14 @@ ohos_unittest("backup_tool_restore_test") { sources = [ "${path_backup_mock}/b_filesystem/b_file_mock.cpp", + "${path_backup}/frameworks/native/backup_kit_inner/src/b_incremental_data.cpp", + "${path_backup}/frameworks/native/backup_kit_inner/src/b_incremental_restore_session.cpp", + "${path_backup}/frameworks/native/backup_kit_inner/src/service_incremental_reverse.cpp", + "${path_backup}/frameworks/native/backup_kit_inner/src/service_reverse.cpp", + "${path_backup}/frameworks/native/backup_kit_inner/src/service_reverse_stub.cpp", "${path_backup}/tests/mock/backup_kit_inner/b_session_restore_async_mock.cpp", "${path_backup}/tests/mock/backup_kit_inner/b_session_restore_mock.cpp", "${path_backup}/tools/backup_tool/src/tools_op.cpp", - "${path_backup}/tools/backup_tool/src/tools_op_incremental_restore.cpp", "backup_tool/tools_op_incremental_restore_test.cpp", "backup_tool/tools_op_restore_async_test.cpp", "backup_tool/tools_op_restore_test.cpp", @@ -93,6 +103,7 @@ ohos_unittest("backup_tool_restore_test") { include_dirs = [ "${path_base}/include", + "${path_backup}/frameworks/native/backup_kit_inner/include", "${path_backup}/interfaces/inner_api/native/backup_kit_inner/impl", "${path_backup}/interfaces/inner_api/native/backup_kit_inner", "${path_backup}/tools/backup_tool/include", diff --git a/tests/unittests/backup_tools/backup_tool/tools_op_incremental_backup_test.cpp b/tests/unittests/backup_tools/backup_tool/tools_op_incremental_backup_test.cpp index a4b7542221e8ebbcbdb4634a1cf2cbfcf28be507..75727088e95476c6f2bb5dbe73e53302a028311d 100644 --- a/tests/unittests/backup_tools/backup_tool/tools_op_incremental_backup_test.cpp +++ b/tests/unittests/backup_tools/backup_tool/tools_op_incremental_backup_test.cpp @@ -1,5 +1,5 @@ /* - * Copyright (c) 2022-2023 Huawei Device Co., Ltd. + * Copyright (c) 2022-2024 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at @@ -21,7 +21,7 @@ #include "b_resources/b_constants.h" #include "tools_op.h" -#include "tools_op_incremental_backup.h" +#include "tools_op_incremental_backup.cpp" #include "utils_mock_global_variable.h" namespace OHOS::FileManagement::Backup { @@ -178,4 +178,397 @@ HWTEST_F(ToolsOpIncrementalBackupTest, SUB_backup_tools_op_incremental_backup_03 } GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-end SUB_backup_tools_op_backup_0300"; } + +/** + * @tc.number: SUB_backup_tools_op_incremental_backup_0400 + * @tc.name: SUB_backup_tools_op_incremental_backup_0400 + * @tc.desc: 测试OnFileReady分支 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalBackupTest, SUB_backup_tools_op_incremental_restore_0400, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-begin SUB_backup_tools_op_incremental_restore_0400"; + try { + auto ctx = make_shared(); + BFileInfo fileInfo; + fileInfo.owner = "test"; + fileInfo.fileName = "/manage.json"; + fileInfo.sn = 1; + UniqueFd fd(open("textFile", O_RDONLY)); + UniqueFd manifestFd(open("textManifest", O_RDONLY)); + OnFileReady(ctx, fileInfo, move(fd), move(manifestFd)); + } catch (BError &e) { + EXPECT_EQ(e.GetCode(), BError(BError::Codes::TOOL_INVAL_ARG).GetCode()); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-end SUB_backup_tools_op_incremental_restore_0400"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_backup_0500 + * @tc.name: SUB_backup_tools_op_incremental_backup_0500 + * @tc.desc: 测试OnBundleStarted分支 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalBackupTest, SUB_backup_tools_op_incremental_backup_0500, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-begin SUB_backup_tools_op_incremental_backup_0500"; + try { + auto ctx = make_shared(); + ErrCode err = 0; + BundleName name = "bundle"; + OnBundleStarted(ctx, err, name); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-end SUB_backup_tools_op_incremental_backup_0500"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_backup_0501 + * @tc.name: SUB_backup_tools_op_incremental_backup_0501 + * @tc.desc: 测试OnBundleStarted分支 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalBackupTest, SUB_backup_tools_op_incremental_backup_0501, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-begin SUB_backup_tools_op_incremental_backup_0501"; + try { + auto ctx = make_shared(); + ctx->SetBundleFinishedCount(1); + ErrCode err = -1; + BundleName name = "bundle"; + OnBundleStarted(ctx, err, name); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-end SUB_backup_tools_op_incremental_backup_0501"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_backup_0600 + * @tc.name: SUB_backup_tools_op_incremental_backup_0600 + * @tc.desc: 测试OnBundleFinished分支 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalBackupTest, SUB_backup_tools_op_incremental_backup_0600, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-begin SUB_backup_tools_op_incremental_backup_0600"; + try { + auto ctx = make_shared(); + ctx->SetBundleFinishedCount(1); + ErrCode err = 0; + BundleName name = "bundle"; + OnBundleFinished(ctx, err, name); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-end SUB_backup_tools_op_incremental_backup_0600"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_backup_0700 + * @tc.name: SUB_backup_tools_op_incremental_backup_0700 + * @tc.desc: 测试OnAllBundlesFinished分支 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalBackupTest, SUB_backup_tools_op_incremental_backup_0700, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-begin SUB_backup_tools_op_incremental_backup_0700"; + try { + auto ctx = make_shared(); + ErrCode err = 0; + OnAllBundlesFinished(ctx, err); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-end SUB_backup_tools_op_incremental_backup_0700"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_backup_0701 + * @tc.name: SUB_backup_tools_op_incremental_backup_0701 + * @tc.desc: 测试OnAllBundlesFinished分支 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalBackupTest, SUB_backup_tools_op_incremental_backup_0701, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-begin SUB_backup_tools_op_incremental_backup_0701"; + try { + auto ctx = make_shared(); + ErrCode err = -1; + OnAllBundlesFinished(ctx, err); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-end SUB_backup_tools_op_incremental_backup_0701"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_backup_0800 + * @tc.name: SUB_backup_tools_op_incremental_backup_0800 + * @tc.desc: 测试OnBackupServiceDied分支 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalBackupTest, SUB_backup_tools_op_incremental_backup_0800, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-begin SUB_backup_tools_op_incremental_backup_0800"; + try { + auto ctx = make_shared(); + OnBackupServiceDied(ctx); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-end SUB_backup_tools_op_incremental_backup_0800"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_backup_0900 + * @tc.name: SUB_backup_tools_op_incremental_backup_0900 + * @tc.desc: 测试BackupToolDirSoftlinkToBackupDir分支 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalBackupTest, SUB_backup_tools_op_incremental_backup_0900, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-begin SUB_backup_tools_op_incremental_backup_0900"; + try { + BackupToolDirSoftlinkToBackupDir(); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-end SUB_backup_tools_op_incremental_backup_0900"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_backup_1000 + * @tc.name: SUB_backup_tools_op_incremental_backup_1000 + * @tc.desc: 测试GetLocalCapabilitiesIncremental分支 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalBackupTest, SUB_backup_tools_op_incremental_backup_1000, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-begin SUB_backup_tools_op_incremental_backup_1000"; + try { + auto ctx = make_shared(); + string pathCapFile = ""; + vector bundleNames; + bundleNames.push_back("bundle1"); + bundleNames.push_back("bundle2"); + vector times = {"100"}; + int32_t ret = GetLocalCapabilitiesIncremental(ctx, pathCapFile, bundleNames, times); + EXPECT_EQ(-EPERM, ret); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-end SUB_backup_tools_op_incremental_backup_1000"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_backup_1001 + * @tc.name: SUB_backup_tools_op_incremental_backup_1001 + * @tc.desc: 测试GetLocalCapabilitiesIncremental分支 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalBackupTest, SUB_backup_tools_op_incremental_backup_1001, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-begin SUB_backup_tools_op_incremental_backup_1001"; + try { + auto ctx = make_shared(); + string pathCapFile = "/data/backup"; + vector bundleNames; + bundleNames.push_back("bundle1"); + bundleNames.push_back("bundle2"); + vector times; + times.push_back("100"); + times.push_back("200"); + int32_t ret = GetLocalCapabilitiesIncremental(ctx, pathCapFile, bundleNames, times); + EXPECT_EQ(-EPERM, ret); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-end SUB_backup_tools_op_incremental_backup_1001"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_backup_1100 + * @tc.name: SUB_backup_tools_op_incremental_backup_1100 + * @tc.desc: 测试Init分支 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalBackupTest, SUB_backup_tools_op_incremental_backup_1100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-begin SUB_backup_tools_op_incremental_backup_1100"; + try { + string pathCapFile = "/data/backup"; + vector bundleNames; + bundleNames.push_back("bundle1"); + bundleNames.push_back("bundle2"); + vector times; + times.push_back("100"); + times.push_back("200"); + int32_t ret = Init(pathCapFile, bundleNames, times); + EXPECT_EQ(-EPERM, ret); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-end SUB_backup_tools_op_incremental_backup_1100"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_backup_1200 + * @tc.name: SUB_backup_tools_op_incremental_backup_1200 + * @tc.desc: 测试Exec分支 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalBackupTest, SUB_backup_tools_op_incremental_backup_1200, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-begin SUB_backup_tools_op_incremental_backup_1200"; + try { + map> mapArgToVal = { + {"pathCapFile", {"path"}}, + {"bundles", {"bundle1", "bundle2"}}, + {"incrementalTime", {"time"}} + }; + int ret = g_exec(mapArgToVal); + EXPECT_LT(ret, 0); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-end SUB_backup_tools_op_incremental_backup_1200"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_backup_1201 + * @tc.name: SUB_backup_tools_op_incremental_backup_1201 + * @tc.desc: 测试Exec分支 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalBackupTest, SUB_backup_tools_op_incremental_backup_1201, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-begin SUB_backup_tools_op_incremental_backup_1201"; + try { + map> mapArgToVal = { + {"bundles", {"bundle1"}}, + {"incrementalTime", {"time"}} + }; + int ret = g_exec(mapArgToVal); + EXPECT_LT(ret, 0); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-end SUB_backup_tools_op_incremental_backup_1201"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_backup_1202 + * @tc.name: SUB_backup_tools_op_incremental_backup_1202 + * @tc.desc: 测试Exec分支 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalBackupTest, SUB_backup_tools_op_incremental_backup_1202, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-begin SUB_backup_tools_op_incremental_backup_1202"; + try { + map> mapArgToVal = { + {"pathCapFile", {"path"}}, + {"incrementalTime", {"time"}} + }; + int ret = g_exec(mapArgToVal); + EXPECT_LT(ret, 0); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-end SUB_backup_tools_op_incremental_backup_1202"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_backup_1203 + * @tc.name: SUB_backup_tools_op_incremental_backup_1203 + * @tc.desc: 测试Exec分支 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalBackupTest, SUB_backup_tools_op_incremental_backup_1203, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-begin SUB_backup_tools_op_incremental_backup_1203"; + try { + map> mapArgToVal = { + {"pathCapFile", {"path"}}, + {"bundles", {"bundle1"}} + }; + int ret = g_exec(mapArgToVal); + EXPECT_LT(ret, 0); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalBackupTest-end SUB_backup_tools_op_incremental_backup_1203"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_tools/backup_tool/tools_op_incremental_restore_test.cpp b/tests/unittests/backup_tools/backup_tool/tools_op_incremental_restore_test.cpp index a5f8038a86e12ef98b2aca2acec51a54f144b8e0..94de5082106d9c699c1b2a846b27812cf913bb5a 100644 --- a/tests/unittests/backup_tools/backup_tool/tools_op_incremental_restore_test.cpp +++ b/tests/unittests/backup_tools/backup_tool/tools_op_incremental_restore_test.cpp @@ -1,5 +1,5 @@ /* - * Copyright (c) 2022-2023 Huawei Device Co., Ltd. + * Copyright (c) 2022-2024 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at @@ -21,7 +21,7 @@ #include "b_resources/b_constants.h" #include "tools_op.h" -#include "tools_op_incremental_restore.h" +#include "tools_op_incremental_restore.cpp" namespace OHOS::FileManagement::Backup { using namespace std; @@ -195,4 +195,655 @@ HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_ } GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_restore_0300"; } + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_0400 + * @tc.name: SUB_backup_tools_op_incremental_restore_0400 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_0400, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_0400"; + try { + auto ctx = make_shared(); + BFileInfo fileInfo; + fileInfo.owner = "test"; + fileInfo.fileName = "/manage.json"; + fileInfo.sn = 1; + UniqueFd fd(open("textFile", O_RDONLY)); + UniqueFd manifestFd(open("textManifest", O_RDONLY)); + OnFileReady(ctx, fileInfo, move(fd), move(manifestFd), 0); + } catch (BError &e) { + EXPECT_EQ(e.GetCode(), BError(BError::Codes::TOOL_INVAL_ARG).GetCode()); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_0400"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_0500 + * @tc.name: SUB_backup_tools_op_incremental_restore_0500 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_0500, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_0500"; + try { + auto ctx = make_shared(); + vector bundleNames; + bundleNames.push_back("bundle1"); + bundleNames.push_back("bundle2"); + vector times = {"100"}; + int32_t ret = InitRestoreSession(ctx, bundleNames, times); + EXPECT_EQ(-EPERM, ret); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_0500"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_0501 + * @tc.name: SUB_backup_tools_op_incremental_restore_0501 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_0501, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_0501"; + try { + auto ctx = make_shared(); + vector bundleNames; + bundleNames.push_back("bundle1"); + bundleNames.push_back("bundle2"); + vector times; + times.push_back("100"); + times.push_back("200"); + int32_t ret = InitRestoreSession(nullptr, bundleNames, times); + EXPECT_EQ(-EPERM, ret); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_0501"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_0502 + * @tc.name: SUB_backup_tools_op_incremental_restore_0502 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_0502, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_0502"; + try { + auto ctx = make_shared(); + vector bundleNames; + bundleNames.push_back("bundle1"); + bundleNames.push_back("bundle2"); + vector times; + times.push_back("10"); + times.push_back("20"); + int32_t ret = InitRestoreSession(ctx, bundleNames, times); + EXPECT_EQ(0, ret); + + BFileInfo fileInfo; + fileInfo.owner = "test"; + fileInfo.fileName = "manage.json"; + fileInfo.sn = 1; + UniqueFd fd(open("textFile", O_RDONLY)); + UniqueFd manifestFd(open("textManifest", O_RDONLY)); + OnFileReady(ctx, fileInfo, move(fd), move(manifestFd), 0); + } catch (BError &e) { + EXPECT_EQ(e.GetCode(), BError(BError::Codes::TOOL_INVAL_ARG).GetCode()); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_0502"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_0600 + * @tc.name: SUB_backup_tools_op_incremental_restore_0600 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_0600, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_0600"; + try { + auto ctx = make_shared(); + ErrCode err = 0; + BundleName name = "bundle"; + OnBundleStarted(ctx, err, name); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_0600"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_0601 + * @tc.name: SUB_backup_tools_op_incremental_restore_0601 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_0601, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_0601"; + try { + auto ctx = make_shared(); + ctx->cnt_ = 1; + ErrCode err = -1; + BundleName name = "bundle"; + OnBundleStarted(ctx, err, name); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_0601"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_0700 + * @tc.name: SUB_backup_tools_op_incremental_restore_0700 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_0700, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_0700"; + try { + auto ctx = make_shared(); + ctx->cnt_ = 1; + ErrCode err = 0; + BundleName name = "bundle"; + OnBundleFinished(ctx, err, name); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_0700"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_0701 + * @tc.name: SUB_backup_tools_op_incremental_restore_0701 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_0701, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_0701"; + try { + auto ctx = make_shared(); + ctx->cnt_ = 1; + ErrCode err = -1; + BundleName name = "bundle"; + OnBundleFinished(ctx, err, name); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_0701"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_0800 + * @tc.name: SUB_backup_tools_op_incremental_restore_0800 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_0800, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_0800"; + try { + auto ctx = make_shared(); + ErrCode err = 0; + OnAllBundlesFinished(ctx, err); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_0800"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_0801 + * @tc.name: SUB_backup_tools_op_incremental_restore_0801 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_0801, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_0801"; + try { + auto ctx = make_shared(); + ErrCode err = -1; + OnAllBundlesFinished(ctx, err); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_0801"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_0900 + * @tc.name: SUB_backup_tools_op_incremental_restore_0900 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_0900, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_0900"; + try { + auto ctx = make_shared(); + OnBackupServiceDied(ctx); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_0900"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_1000 + * @tc.name: SUB_backup_tools_op_incremental_restore_1000 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_1000, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_1000"; + try { + shared_ptr restore = nullptr; + RestoreApp(restore); + } catch (BError &e) { + EXPECT_EQ(e.GetCode(), BError(BError::Codes::TOOL_INVAL_ARG).GetCode()); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_1000"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_1001 + * @tc.name: SUB_backup_tools_op_incremental_restore_1001 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_1001, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_1001"; + try { + shared_ptr restore = make_shared(); + restore->session_ = nullptr; + RestoreApp(restore); + } catch (BError &e) { + EXPECT_EQ(e.GetCode(), BError(BError::Codes::TOOL_INVAL_ARG).GetCode()); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_1001"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_1002 + * @tc.name: SUB_backup_tools_op_incremental_restore_1002 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_1002, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_1002"; + try { + shared_ptr restore = make_shared(); + restore->session_ = {}; + BIncrementalData data("text", 1); + restore->lastIncrementalData = {data}; + RestoreApp(restore); + EXPECT_TRUE(true); + } catch (BError &e) { + EXPECT_EQ(e.GetCode(), BError(BError::Codes::TOOL_INVAL_ARG).GetCode()); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_1002"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_1003 + * @tc.name: SUB_backup_tools_op_incremental_restore_1003 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_1003, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_1003"; + try { + auto ctx = make_shared(); + vector bundleNames; + bundleNames.push_back("bundle1"); + bundleNames.push_back("bundle2"); + vector times; + times.push_back("10"); + times.push_back("20"); + int32_t ret = InitRestoreSession(ctx, bundleNames, times); + EXPECT_EQ(0, ret); + + RestoreApp(ctx); + EXPECT_TRUE(ctx); + } catch (BError &e) { + EXPECT_EQ(e.GetCode(), BError(BError::Codes::TOOL_INVAL_ARG).GetCode()); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_1003"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_1100 + * @tc.name: SUB_backup_tools_op_incremental_restore_1100 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_1100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_1100"; + try { + string pathCapFile = ""; + vector bundleNames = {"com.example.app2backup/"}; + bool depMode = true; + vector times = {"10"}; + int32_t ret = Init(pathCapFile, bundleNames, depMode, times); + EXPECT_LT(ret, 0); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_1100"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_1101 + * @tc.name: SUB_backup_tools_op_incremental_restore_1101 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_1101, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_1101"; + try { + string pathCapFile = "/data/backup"; + vector bundleNames = {"com.example.app2backup/"}; + bool depMode = true; + vector times = {"1"}; + int32_t ret = Init(pathCapFile, bundleNames, depMode, times); + EXPECT_LT(ret, 0); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_1101"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_1102 + * @tc.name: SUB_backup_tools_op_incremental_restore_1102 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_1102, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_1102"; + try { + string pathCapFile = ""; + vector bundleNames = {"com.example.app2backup/"}; + bool depMode = false; + vector times = {"10"}; + int32_t ret = Init(pathCapFile, bundleNames, depMode, times); + EXPECT_LT(ret, 0); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_1102"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_1200 + * @tc.name: SUB_backup_tools_op_incremental_restore_1200 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_1200, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_1200"; + try { + map> mapArgToVal; + mapArgToVal["depMode"] = {"false"}; + g_exec(mapArgToVal); + EXPECT_EQ(mapArgToVal["depMode"][0], "false"); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_1200"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_1201 + * @tc.name: SUB_backup_tools_op_incremental_restore_1201 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_1201, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_1201"; + try { + map> mapArgToVal = { + {"pathCapFile", {"path"}}, + {"bundles", {"bundle1"}}, + {"incrementalTime", {"time"}} + }; + int ret = g_exec(mapArgToVal); + EXPECT_LT(ret, 0); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_1201"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_1202 + * @tc.name: SUB_backup_tools_op_incremental_restore_1202 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_1202, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_1202"; + try { + map> mapArgToVal = { + {"bundles", {"bundle1"}}, + {"incrementalTime", {"time"}} + }; + int ret = g_exec(mapArgToVal); + EXPECT_LT(ret, 0); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_1202"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_1203 + * @tc.name: SUB_backup_tools_op_incremental_restore_1203 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_1203, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_1203"; + try { + map> mapArgToVal = { + {"pathCapFile", {"path"}}, + {"bundles", {"bundle1"}}, + {"incrementalTime", {"time"}}, + {"depMode", {"true"}} + }; + int ret = g_exec(mapArgToVal); + EXPECT_LT(ret, 0); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_1203"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_1204 + * @tc.name: SUB_backup_tools_op_incremental_restore_1204 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_1204, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_1204"; + try { + map> mapArgToVal = { + {"pathCapFile", {"path"}}, + {"incrementalTime", {"time"}} + }; + int ret = g_exec(mapArgToVal); + EXPECT_LT(ret, 0); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_1204"; +} + +/** + * @tc.number: SUB_backup_tools_op_incremental_restore_1205 + * @tc.name: SUB_backup_tools_op_incremental_restore_1205 + * @tc.desc: 测试 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(ToolsOpIncrementalRestoreTest, SUB_backup_tools_op_incremental_restore_1205, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-begin SUB_backup_tools_op_incremental_restore_1205"; + try { + map> mapArgToVal = { + {"pathCapFile", {"path"}}, + {"bundles", {"bundle1"}} + }; + int ret = g_exec(mapArgToVal); + EXPECT_LT(ret, 0); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpIncrementalRestoreTest-end SUB_backup_tools_op_incremental_restore_1205"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_tools/backup_tool/tools_op_restore_async_test.cpp b/tests/unittests/backup_tools/backup_tool/tools_op_restore_async_test.cpp index c7f7a7b9e6e3d66e676b36c9e284cf5c0a9a4a32..cc797c548c9475a7a4664552ec0d23784e5331e4 100644 --- a/tests/unittests/backup_tools/backup_tool/tools_op_restore_async_test.cpp +++ b/tests/unittests/backup_tools/backup_tool/tools_op_restore_async_test.cpp @@ -1,5 +1,5 @@ /* - * Copyright (c) 2023 Huawei Device Co., Ltd. + * Copyright (c) 2023-2024 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at @@ -293,6 +293,32 @@ HWTEST_F(ToolsOpRestoreAsyncTest, tools_op_restore_async_0400, testing::ext::Tes GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-end tools_op_restore_async_0400"; } +/** + * @tc.number: SUB_backup_tools_op_restore_async_0401 + * @tc.name: tools_op_restore_async_0401 + * @tc.desc: test func + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I9JNFM + */ +HWTEST_F(ToolsOpRestoreAsyncTest, tools_op_restore_async_0401, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-begin tools_op_restore_async_0401"; + try { + auto ctx = make_shared(); + ctx->cnt_ = 1; + ErrCode err = -1; + BundleName name = "testBundle"; + OnBundleStarted(ctx, err, name); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-end tools_op_restore_async_0401"; +} + /** * @tc.number: SUB_backup_tools_op_restore_async_0500 * @tc.name: tools_op_restore_async_0500 @@ -318,6 +344,32 @@ HWTEST_F(ToolsOpRestoreAsyncTest, tools_op_restore_async_0500, testing::ext::Tes GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-end tools_op_restore_async_0500"; } +/** + * @tc.number: SUB_backup_tools_op_restore_async_0501 + * @tc.name: tools_op_restore_async_0501 + * @tc.desc: 测试OnBundleFinished方法 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I9JNFM + */ +HWTEST_F(ToolsOpRestoreAsyncTest, tools_op_restore_async_0501, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-begin tools_op_restore_async_0501"; + try { + auto ctx = make_shared(); + ctx->cnt_ = 1; + ErrCode err = -1; + BundleName name = "testBundle"; + OnBundleFinished(ctx, err, name); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-end tools_op_restore_async_0501"; +} + /** * @tc.number: SUB_backup_tools_op_restore_async_0600 * @tc.name: tools_op_restore_async_0600 @@ -452,8 +504,9 @@ HWTEST_F(ToolsOpRestoreAsyncTest, tools_op_restore_async_1001, testing::ext::Tes GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-begin tools_op_restore_async_1001"; try { vector bundleNames; - bundleNames.push_back("bundle/name");\ + bundleNames.push_back("bundle/name"); shared_ptr restore = make_shared(); + restore->session_ = {}; RestoreApp(restore, bundleNames); } catch (BError &e) { EXPECT_EQ(e.GetCode(), BError(BError::Codes::TOOL_INVAL_ARG).GetCode()); @@ -479,8 +532,9 @@ HWTEST_F(ToolsOpRestoreAsyncTest, tools_op_restore_async_1002, testing::ext::Tes GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-begin tools_op_restore_async_1002"; try { vector bundleNames; - bundleNames.push_back("bundlename");\ + bundleNames.push_back("bundlename"); shared_ptr restore = make_shared(); + restore->session_ = {}; RestoreApp(restore, bundleNames); } catch (BError &e) { EXPECT_EQ(e.GetCode(), BError(BError::Codes::TOOL_INVAL_ARG).GetCode()); @@ -508,7 +562,7 @@ HWTEST_F(ToolsOpRestoreAsyncTest, tools_op_restore_async_1100, testing::ext::Tes string pathCapFile = "/data/user/0/test/files/bundleInfo.json"; vector bundleNames = {"bundlenames"}; string type = "false"; - int32_t ret =ChangeBundleInfo(pathCapFile, bundleNames, type); + int32_t ret = ChangeBundleInfo(pathCapFile, bundleNames, type); EXPECT_LT(ret, 0); } catch (...) { EXPECT_TRUE(false); @@ -533,7 +587,7 @@ HWTEST_F(ToolsOpRestoreAsyncTest, tools_op_restore_async_1101, testing::ext::Tes string pathCapFile = " "; vector bundleNames = {"bundlenames"}; string type = "false"; - int32_t ret =ChangeBundleInfo(pathCapFile, bundleNames, type); + int32_t ret = ChangeBundleInfo(pathCapFile, bundleNames, type); EXPECT_LT(ret, 0); } catch (...) { EXPECT_TRUE(false); @@ -558,7 +612,7 @@ HWTEST_F(ToolsOpRestoreAsyncTest, tools_op_restore_async_1102, testing::ext::Tes string pathCapFile = "/data/user/0/test/files/bundleInfo.json"; vector bundleNames = {}; string type = "true"; - int32_t ret =ChangeBundleInfo(pathCapFile, bundleNames, type); + int32_t ret = ChangeBundleInfo(pathCapFile, bundleNames, type); EXPECT_LT(ret, 0); } catch (...) { EXPECT_TRUE(false); @@ -768,7 +822,6 @@ HWTEST_F(ToolsOpRestoreAsyncTest, tools_op_restore_async_1401, testing::ext::Tes { GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-begin tools_op_restore_async_1401"; try { - map> mapArgToVal; int ret = Exec(mapArgToVal); EXPECT_EQ(ret, -EPERM); @@ -778,4 +831,97 @@ HWTEST_F(ToolsOpRestoreAsyncTest, tools_op_restore_async_1401, testing::ext::Tes } GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-end tools_op_restore_async_1401"; } + +/** + * @tc.number: SUB_backup_tools_op_restore_async_1500 + * @tc.name: tools_op_restore_async_1500 + * @tc.desc: test func + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I9NOPD + */ +HWTEST_F(ToolsOpRestoreAsyncTest, tools_op_restore_async_1500, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-begin tools_op_restore_async_1500"; + try { + std::string path = "/data/backup/receive"; + std::vector pkgInfo; + ExtManageInfo info; + info.hashName = "hashName"; + info.fileName = "fileName"; + info.isBigFile = false; + info.isUserTar = false; + pkgInfo.push_back(info); + + auto result = ReadyExtManage(path, pkgInfo); + EXPECT_EQ(result.size(), 1); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-end tools_op_restore_async_1500"; +} + +/** + * @tc.number: SUB_backup_tools_op_restore_async_1501 + * @tc.name: tools_op_restore_async_1501 + * @tc.desc: test func + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I9NOPD + */ +HWTEST_F(ToolsOpRestoreAsyncTest, tools_op_restore_async_1501, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-begin tools_op_restore_async_1501"; + try { + std::string path = "/data/backup/receive"; + std::vector pkgInfo; + ExtManageInfo info; + info.hashName = ""; + info.fileName = ""; + info.isBigFile = false; + info.isUserTar = false; + pkgInfo.push_back(info); + + auto result = ReadyExtManage(path, pkgInfo); + EXPECT_EQ(result.size(), 0); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-end tools_op_restore_async_1501"; +} + +/** + * @tc.number: SUB_backup_tools_op_restore_async_1502 + * @tc.name: tools_op_restore_async_1502 + * @tc.desc: test func + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I9NOPD + */ +HWTEST_F(ToolsOpRestoreAsyncTest, tools_op_restore_async_1502, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-begin tools_op_restore_async_1502"; + try { + std::string path = "/data/backup/receive"; + std::vector pkgInfo; + ExtManageInfo info; + info.hashName = "hashName"; + info.fileName = "fileName"; + info.isBigFile = true; + info.isUserTar = true; + pkgInfo.push_back(info); + + auto result = ReadyExtManage(path, pkgInfo); + EXPECT_EQ(result.size(), 1); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpRestoreAsyncTest-end tools_op_restore_async_1502"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_tools/backup_tool/tools_op_restore_test.cpp b/tests/unittests/backup_tools/backup_tool/tools_op_restore_test.cpp index 3d7220db85a358fa0c4f93d12d617b5967018527..6244fabf5afb683e65d7ff5473b68541320186a1 100644 --- a/tests/unittests/backup_tools/backup_tool/tools_op_restore_test.cpp +++ b/tests/unittests/backup_tools/backup_tool/tools_op_restore_test.cpp @@ -1,5 +1,5 @@ /* - * Copyright (c) 2022-2023 Huawei Device Co., Ltd. + * Copyright (c) 2022-2024 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at @@ -432,6 +432,129 @@ HWTEST_F(ToolsOpRestoreTest, tools_op_restore_OnBundleStarted_0601, testing::ext GTEST_LOG_(INFO) << "ToolsOpRestoreTest-end tools_op_restore_OnBundleStarted_0601"; } +/** + * @tc.number: SUB_backup_tools_op_restore_0700 + * @tc.name: tools_op_restore_OnBundleFinished_0700 + * @tc.desc: test func + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I9NOPD + */ +HWTEST_F(ToolsOpRestoreTest, tools_op_restore_OnBundleFinished_0700, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-begin tools_op_restore_OnBundleFinished_0700"; + try { + auto ctx = make_shared(); + ctx->cnt_ = 1; + ErrCode err = 0; + BundleName name = BUNDLE_NAME; + OnBundleFinished(ctx, err, name); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-end tools_op_restore_OnBundleFinished_0700"; +} + +/** + * @tc.number: SUB_backup_tools_op_restore_0701 + * @tc.name: tools_op_restore_OnBundleFinished_0701 + * @tc.desc: test func + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I9NOPD + */ +HWTEST_F(ToolsOpRestoreTest, tools_op_restore_OnBundleFinished_0701, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-begin tools_op_restore_OnBundleFinished_0701"; + try { + auto ctx = make_shared(); + ctx->cnt_ = 1; + ErrCode err = -1; + BundleName name = BUNDLE_NAME; + OnBundleFinished(ctx, err, name); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-end tools_op_restore_OnBundleFinished_0701"; +} + +/** + * @tc.number: SUB_backup_tools_op_restore_0702 + * @tc.name: tools_op_restore_OnBundleFinished_0702 + * @tc.desc: test func + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I9NOPD + */ +HWTEST_F(ToolsOpRestoreTest, tools_op_restore_OnBundleFinished_0702, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-begin tools_op_restore_OnBundleFinished_0702"; + try { + auto ctx = make_shared(); + ErrCode err = 0; + OnAllBundlesFinished(ctx, err); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-end tools_op_restore_OnBundleFinished_0702"; +} + +/** + * @tc.number: SUB_backup_tools_op_restore_0703 + * @tc.name: tools_op_restore_OnBundleFinished_0703 + * @tc.desc: test func + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I9NOPD + */ +HWTEST_F(ToolsOpRestoreTest, tools_op_restore_OnBundleFinished_0703, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-begin tools_op_restore_OnBundleFinished_0703"; + try { + auto ctx = make_shared(); + ErrCode err = -1; + OnAllBundlesFinished(ctx, err); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-end tools_op_restore_OnBundleFinished_0703"; +} + +/** + * @tc.number: SUB_backup_tools_op_restore_0704 + * @tc.name: tools_op_restore_OnBundleFinished_0704 + * @tc.desc: test func + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I9NOPD + */ +HWTEST_F(ToolsOpRestoreTest, tools_op_restore_OnBundleFinished_0704, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-begin tools_op_restore_OnBundleFinished_0704"; + try { + auto ctx = make_shared(); + OnBackupServiceDied(ctx); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-end tools_op_restore_OnBundleFinished_0704"; +} + /** * @tc.number: SUB_backup_tools_op_restore_0800 * @tc.name: tools_op_restore_OnResultReport_0800 @@ -639,6 +762,31 @@ HWTEST_F(ToolsOpRestoreTest, tools_op_restore_InitRestoreSession_1100, testing:: GTEST_LOG_(INFO) << "ToolsOpRestoreTest-end tools_op_restore_GInitRestoreSession_1100"; } +/** + * @tc.number: SUB_backup_tools_op_restore_1101 + * @tc.name: tools_op_restore_InitRestoreSession_1101 + * @tc.desc: 测试当ctx + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I9NOPD + */ +HWTEST_F(ToolsOpRestoreTest, tools_op_restore_InitRestoreSession_1101, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-begin tools_op_restore_InitRestoreSession_1101"; + try { + shared_ptr ctx = make_shared(); + InitRestoreSession(ctx); + } catch (BError &e) { + EXPECT_EQ(e.GetCode(), BError(BError::Codes::TOOL_INVAL_ARG).GetCode()); + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-end tools_op_restore_InitRestoreSession_1101"; +} + /** * @tc.number: SUB_backup_tools_op_restore_1200 * @tc.name: tools_op_restore_InitPathCapFile_1200 @@ -664,6 +812,60 @@ HWTEST_F(ToolsOpRestoreTest, tools_op_restore_InitPathCapFile_1200, testing::ext GTEST_LOG_(INFO) << "ToolsOpRestoreTest-end tools_op_restore_InitPathCapFile_1200"; } +/** + * @tc.number: SUB_backup_tools_op_restore_1201 + * @tc.name: tools_op_restore_InitPathCapFile_1201 + * @tc.desc: test func + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I9NOPD + */ +HWTEST_F(ToolsOpRestoreTest, tools_op_restore_InitPathCapFile_1201, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-begin tools_op_restore_InitPathCapFile_1201"; + try { + string pathCapFile = "/data/backup/tmp"; + vector bundleNames = {"com.example.app2backup/"}; + bool depMode = true; + int32_t ret = InitPathCapFile(pathCapFile, bundleNames, depMode); + EXPECT_LT(ret, 0); + } catch (BError &e) { + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-end tools_op_restore_InitPathCapFile_1201"; +} + +/** + * @tc.number: SUB_backup_tools_op_restore_1202 + * @tc.name: tools_op_restore_InitPathCapFile_1202 + * @tc.desc: test func + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I9NOPD + */ +HWTEST_F(ToolsOpRestoreTest, tools_op_restore_InitPathCapFile_1202, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-begin tools_op_restore_InitPathCapFile_1202"; + try { + string pathCapFile = "/data/backup/tmp"; + vector bundleNames = {"com.example.app2backup/"}; + bool depMode = false; + int32_t ret = InitPathCapFile(pathCapFile, bundleNames, depMode); + EXPECT_LT(ret, 0); + } catch (BError &e) { + EXPECT_TRUE(true); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-end tools_op_restore_InitPathCapFile_1202"; +} + /** * @tc.number: SUB_backup_tools_op_restore_1300 * @tc.name: tools_op_restore_Exec_1300 @@ -767,4 +969,29 @@ HWTEST_F(ToolsOpRestoreTest, tools_op_restore_Exec_1303, testing::ext::TestSize. } GTEST_LOG_(INFO) << "ToolsOpRestoreTest-end tools_op_restore_Exec_1303"; } + +/** + * @tc.number: SUB_backup_tools_op_restore_1304 + * @tc.name: tools_op_restore_Exec_1304 + * @tc.desc: test func + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I9NOPD + */ +HWTEST_F(ToolsOpRestoreTest, tools_op_restore_Exec_1304, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-begin tools_op_restore_Exec_1304"; + try { + map> mapArgToVal; + mapArgToVal["pathCapFile"] = {"/data/backup/recived/com.example.app2backup/"}; + mapArgToVal["bundles"] = {"com.example.app2backup/"}; + int ret = Exec(mapArgToVal); + EXPECT_LT(ret, 0); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-an exception occurred by construction."; + } + GTEST_LOG_(INFO) << "ToolsOpRestoreTest-end tools_op_restore_Exec_1304"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_utils/BUILD.gn b/tests/unittests/backup_utils/BUILD.gn index 40476eb1bc07c723cb250aff488ce0299725b90a..47be52ea6dd1446c0188c4ae061912a00918e737 100644 --- a/tests/unittests/backup_utils/BUILD.gn +++ b/tests/unittests/backup_utils/BUILD.gn @@ -54,6 +54,8 @@ ohos_unittest("b_file_test") { "b_filesystem/b_file_test.cpp", ] + include_dirs = [ "${path_backup}/utils/src/b_filesystem" ] + deps = [ "${path_backup}/tests/utils:backup_test_utils", "${path_backup}/utils/:backup_utils", @@ -293,6 +295,7 @@ group("backup_test") { ":b_file_test", ":b_json_other_test", ":b_json_test", + ":b_jsonutil_test", ":b_process_test", ":b_tarball_cmdline_test", ":b_tarball_factory_test", diff --git a/tests/unittests/backup_utils/b_error/b_error_test.cpp b/tests/unittests/backup_utils/b_error/b_error_test.cpp index d48c401d7f3cfe0a1db5e3bb6ca29dcaecad66a0..7a77a179154d1e6106eaa751f56f869cc9035bea 100644 --- a/tests/unittests/backup_utils/b_error/b_error_test.cpp +++ b/tests/unittests/backup_utils/b_error/b_error_test.cpp @@ -1,5 +1,5 @@ /* - * Copyright (c) 2022-2023 Huawei Device Co., Ltd. + * Copyright (c) 2022-2024 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at @@ -452,4 +452,58 @@ HWTEST_F(BErrorTest, b_error_int_0100, testing::ext::TestSize.Level0) EXPECT_EQ(result, 0); GTEST_LOG_(INFO) << "BErrorTest-end b_error_int_0100"; } + +/** + * @tc.number: SUB_backup_b_error_GetCodeByErrno_0100 + * @tc.name: b_error_GetCodeByErrno_0100 + * @tc.desc: Test function of int interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BErrorTest, b_error_GetCodeByErrno_0100, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BErrorTest-begin b_error_GetCodeByErrno_0100"; + int32_t errnoSys = 0; + int result = BError::GetCodeByErrno(errnoSys); + EXPECT_EQ(result, 0); + GTEST_LOG_(INFO) << "BErrorTest-end b_error_GetCodeByErrno_0100"; +} + +/** + * @tc.number: SUB_backup_b_error_GetCodeByErrno_0200 + * @tc.name: b_error_GetCodeByErrno_0200 + * @tc.desc: Test function of int interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BErrorTest, b_error_GetCodeByErrno_0200, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BErrorTest-begin b_error_GetCodeByErrno_0200"; + int32_t errnoSys = EPERM; + int result = BError::GetCodeByErrno(errnoSys); + EXPECT_EQ(result, BError::BackupErrorCode::E_PERM); + GTEST_LOG_(INFO) << "BErrorTest-end b_error_GetCodeByErrno_0200"; +} + +/** + * @tc.number: SUB_backup_b_error_GetCodeByErrno_0300 + * @tc.name: b_error_GetCodeByErrno_0300 + * @tc.desc: Test function of int interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BErrorTest, b_error_GetCodeByErrno_0300, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BErrorTest-begin b_error_GetCodeByErrno_0300"; + int32_t errnoSys = -EPERM; + int result = BError::GetCodeByErrno(errnoSys); + EXPECT_EQ(result, BError::BackupErrorCode::E_UKERR); + GTEST_LOG_(INFO) << "BErrorTest-end b_error_GetCodeByErrno_0300"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_utils/b_filesystem/b_dir_test.cpp b/tests/unittests/backup_utils/b_filesystem/b_dir_test.cpp index fc93f542ff066a40012f593fdd5117bbdf1e2f1e..531a634068daea86216edfda91281b66399674f2 100644 --- a/tests/unittests/backup_utils/b_filesystem/b_dir_test.cpp +++ b/tests/unittests/backup_utils/b_filesystem/b_dir_test.cpp @@ -24,6 +24,7 @@ #include #include "b_filesystem/b_dir.h" +#include "b_dir.cpp" #include "b_process/b_process.h" #include "test_manager.h" @@ -318,4 +319,28 @@ HWTEST_F(BDirTest, b_dir_GetDirs_0100, testing::ext::TestSize.Level1) GTEST_LOG_(INFO) << "BDirTest-end b_dir_GetDirs_0100"; } +/** + * @tc.number: SUB_backup_b_dir_GetFile_0100 + * @tc.name: b_dir_GetFile_0100 + * @tc.desc: Test function of GetFile interface for SUCCESS + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: I6F3GV + */ +HWTEST_F(BDirTest, b_dir_GetFile_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "BDirTest-begin b_dir_GetFile_0100"; + try { + string path = "/"; + auto [errCode, subFiles, subSmallFiles] = GetFile(path); + string pathData = "/data"; + auto [errCode1, subFiles1, subSmallFiles1] = GetFile(pathData, PATH_MAX_LEN); + auto [errCode2, subFiles2, subSmallFiles2] = GetFile(pathData); + EXPECT_EQ(errCode, 0); + } catch (...) { + GTEST_LOG_(INFO) << "BDirTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BDirTest-end b_dir_GetFile_0100"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_utils/b_filesystem/b_file_hash_test.cpp b/tests/unittests/backup_utils/b_filesystem/b_file_hash_test.cpp index a0f8621a8dc4d1c4ec672f0cdd7c6376339f5b66..bedfa2e60bd566005d67345090e3cd916e1a411a 100644 --- a/tests/unittests/backup_utils/b_filesystem/b_file_hash_test.cpp +++ b/tests/unittests/backup_utils/b_filesystem/b_file_hash_test.cpp @@ -74,4 +74,26 @@ HWTEST_F(BFileHashTest, b_file_hash_HashWithSHA256_0100, testing::ext::TestSize. } GTEST_LOG_(INFO) << "BFileHashTest-end b_file_hash_HashWithSHA256_0100"; } + +/** + * @tc.number: SUB_backup_b_file_hash_HashWithSHA256_0101 + * @tc.name: b_file_hash_HashWithSHA256_0100 + * @tc.desc: Test function of HashWithSHA256 interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + */ +HWTEST_F(BFileHashTest, b_file_hash_HashWithSHA256_0101, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BFileHashTest-begin b_file_hash_HashWithSHA256_0101"; + try { + std::string filePath = "/errPath"; + auto [res, fileHash] = BackupFileHash::HashWithSHA256(filePath); + EXPECT_NE(res, 0); + } catch (const exception &e) { + GTEST_LOG_(INFO) << "BFileHashTest-an exception occurred by HashWithSHA256."; + e.what(); + } + GTEST_LOG_(INFO) << "BFileHashTest-end b_file_hash_HashWithSHA256_0101"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_utils/b_json/b_json_entity_ext_manage_test.cpp b/tests/unittests/backup_utils/b_json/b_json_entity_ext_manage_test.cpp index a09c55ebcb4078fde2d0f056290d2126acc82c6c..239a274bd5d832f0ff427e16b675148c0f5a7598 100644 --- a/tests/unittests/backup_utils/b_json/b_json_entity_ext_manage_test.cpp +++ b/tests/unittests/backup_utils/b_json/b_json_entity_ext_manage_test.cpp @@ -526,6 +526,31 @@ HWTEST_F(BJsonEntityExtManageTest, b_json_entity_ext_manage_0803, testing::ext:: GTEST_LOG_(INFO) << "BJsonEntityExtManageTest-end b_json_entity_ext_manage_0803"; } +/** + * @tc.number: SUB_backup_b_json_entity_ext_manage_0804 + * @tc.name: b_json_entity_ext_manage_0804 + * @tc.desc: 测试GetExtManageInfo + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BJsonEntityExtManageTest, b_json_entity_ext_manage_0804, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BJsonEntityExtManageTest-begin b_json_entity_ext_manage_0804"; + try { + string_view sv = R"([{"isBigFile":false}, {"fileName":"test"}])"; + BJsonCachedEntity cachedEntity(sv); + auto cache = cachedEntity.Structuralize(); + auto mp = cache.GetExtManageInfo(); + EXPECT_TRUE(mp.empty()); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BJsonEntityExtManageTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BJsonEntityExtManageTest-end b_json_entity_ext_manage_0804"; +} + /** * @tc.number: SUB_backup_b_json_entity_ext_manage_0900 * @tc.name: b_json_entity_ext_manage_0900 @@ -674,4 +699,32 @@ HWTEST_F(BJsonEntityExtManageTest, b_json_entity_ext_manage_0903, testing::ext:: } GTEST_LOG_(INFO) << "BJsonEntityExtManageTest-end b_json_entity_ext_manage_0903"; } + +/** + * @tc.number: SUB_backup_b_json_entity_ext_manage_0904 + * @tc.name: b_json_entity_ext_manage_0904 + * @tc.desc: 测试CheckOwnPackTar各种异常分支 + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + * @tc.require: issuesI9JXNH + */ +HWTEST_F(BJsonEntityExtManageTest, b_json_entity_ext_manage_0904, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "BJsonEntityExtManageTest-begin b_json_entity_ext_manage_0904"; + try { + string fileName = "/home/user/test.tar"; + auto ret = CheckOwnPackTar(fileName); + EXPECT_FALSE(ret); + + fileName = string(BConstants::PATH_BUNDLE_BACKUP_HOME) + .append(BConstants::SA_BUNDLE_BACKUP_BACKUP).append("/part1.tar"); + ret = CheckOwnPackTar(fileName); + EXPECT_TRUE(ret); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BJsonEntityExtManageTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BJsonEntityExtManageTest-end b_json_entity_ext_manage_0904"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_utils/b_json/b_report_entity_test.cpp b/tests/unittests/backup_utils/b_json/b_report_entity_test.cpp index 3e51ac25818a0f48ff46284217bc782764ccb5bf..cbdba7332b544426885262d980bc04c16559f53b 100644 --- a/tests/unittests/backup_utils/b_json/b_report_entity_test.cpp +++ b/tests/unittests/backup_utils/b_json/b_report_entity_test.cpp @@ -227,4 +227,124 @@ HWTEST_F(BReportEntityTest, b_report_entity_DealLine_0100, testing::ext::TestSiz GTEST_LOG_(INFO) << "BReportEntityTest-end b_report_entity_DealLine_0100"; } +/** + * @tc.number: SUB_backup_b_report_entity_DealLine_0101 + * @tc.name: b_report_entity_DealLine_0101 + * @tc.desc: Test function of DealLine interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + */ +HWTEST_F(BReportEntityTest, b_report_entity_DealLine_0101, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "BReportEntityTest-begin b_report_entity_DealLine_0101"; + try { + unordered_map keys; + int num = 1; + string line = ""; + unordered_map infos; + DealLine(keys, num, line, infos); + EXPECT_EQ(infos.size(), 0); + } catch (const exception &e) { + GTEST_LOG_(INFO) << "BReportEntityTest-an exception occurred by DealLine. " << e.what(); + EXPECT_TRUE(false); + } + GTEST_LOG_(INFO) << "BReportEntityTest-end b_report_entity_DealLine_0101"; +} + +/** + * @tc.number: SUB_backup_b_report_entity_StorageDealLine_0100 + * @tc.name: b_report_entity_StorageDealLine_0100 + * @tc.desc: Test function of DealLine interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + */ +HWTEST_F(BReportEntityTest, b_report_entity_StorageDealLine_0100, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "BReportEntityTest-begin b_report_entity_StorageDealLine_0100"; + try { + unordered_map keys; + int num = 1; + string line = ""; + StorageDealLine(keys, num, line); + EXPECT_TRUE(true); + } catch (const exception &e) { + GTEST_LOG_(INFO) << "BReportEntityTest-an exception occurred by DealLine. " << e.what(); + EXPECT_TRUE(false); + } + GTEST_LOG_(INFO) << "BReportEntityTest-end b_report_entity_StorageDealLine_0100"; +} + +/** + * @tc.number: SUB_backup_b_report_entity_StorageDealLine_0101 + * @tc.name: b_report_entity_StorageDealLine_0101 + * @tc.desc: Test function of DealLine interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + */ +HWTEST_F(BReportEntityTest, b_report_entity_StorageDealLine_0101, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "BReportEntityTest-begin b_report_entity_StorageDealLine_0101"; + try { + unordered_map keys; + int num = 0; + string line = "test\r"; + StorageDealLine(keys, num, line); + EXPECT_TRUE(true); + } catch (const exception &e) { + GTEST_LOG_(INFO) << "BReportEntityTest-an exception occurred by DealLine. " << e.what(); + EXPECT_TRUE(false); + } + GTEST_LOG_(INFO) << "BReportEntityTest-end b_report_entity_StorageDealLine_0101"; +} + +/** + * @tc.number: SUB_backup_b_report_entity_StorageDealLine_0102 + * @tc.name: b_report_entity_StorageDealLine_0102 + * @tc.desc: Test function of DealLine interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + */ +HWTEST_F(BReportEntityTest, b_report_entity_StorageDealLine_0102, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "BReportEntityTest-begin b_report_entity_StorageDealLine_0102"; + try { + unordered_map keys; + int num = 1; + string line = "key1;key2;key3"; + StorageDealLine(keys, num, line); + EXPECT_TRUE(true); + } catch (const exception &e) { + GTEST_LOG_(INFO) << "BReportEntityTest-an exception occurred by DealLine. " << e.what(); + EXPECT_TRUE(false); + } + GTEST_LOG_(INFO) << "BReportEntityTest-end b_report_entity_StorageDealLine_0102"; +} + +/** + * @tc.number: SUB_backup_b_report_entity_StorageDealLine_0103 + * @tc.name: b_report_entity_StorageDealLine_0103 + * @tc.desc: Test function of DealLine interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 1 + */ +HWTEST_F(BReportEntityTest, b_report_entity_StorageDealLine_0103, testing::ext::TestSize.Level1) +{ + GTEST_LOG_(INFO) << "BReportEntityTest-begin b_report_entity_StorageDealLine_0103"; + try { + unordered_map keys; + int num = INFO_ALIGN_NUM; + string line = "key1;key2;key3"; + StorageDealLine(keys, num, line); + EXPECT_TRUE(true); + } catch (const exception &e) { + GTEST_LOG_(INFO) << "BReportEntityTest-an exception occurred by DealLine. " << e.what(); + EXPECT_TRUE(false); + } + GTEST_LOG_(INFO) << "BReportEntityTest-end b_report_entity_StorageDealLine_0103"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/tests/unittests/backup_utils/b_jsonutil/b_jsonutil_test.cpp b/tests/unittests/backup_utils/b_jsonutil/b_jsonutil_test.cpp index e21b944df14a0dca02301b77c6246491a6e061e1..09d7926d0e53fcaefec063acedfb99c574b338f5 100644 --- a/tests/unittests/backup_utils/b_jsonutil/b_jsonutil_test.cpp +++ b/tests/unittests/backup_utils/b_jsonutil/b_jsonutil_test.cpp @@ -30,6 +30,10 @@ namespace OHOS::FileManagement::Backup { using namespace std; +namespace { +constexpr uint32_t TEST_USER_ID = 100; +} // namespace + class BJsonUtilTest : public testing::Test { public: static void SetUpTestCase(void) {}; @@ -52,8 +56,7 @@ HWTEST_F(BJsonUtilTest, b_jsonutil_ParseBundleNameIndexStr_0100, testing::ext::T GTEST_LOG_(INFO) << "BJsonUtilTest-begin b_dir_GetDirFiles_0100"; try { std::string bundleName = "com.hos.app01:1"; - std::string pattern = ":"; - BJsonUtil::BundleDetailInfo detailInfo = BJsonUtil::ParseBundleNameIndexStr(bundleName, pattern); + BJsonUtil::BundleDetailInfo detailInfo = BJsonUtil::ParseBundleNameIndexStr(bundleName); EXPECT_EQ("com.hos.app01", detailInfo.bundleName); } catch (...) { EXPECT_TRUE(false); @@ -62,6 +65,29 @@ HWTEST_F(BJsonUtilTest, b_jsonutil_ParseBundleNameIndexStr_0100, testing::ext::T GTEST_LOG_(INFO) << "BDirTest-end b_dir_GetDirFiles_0100"; } +/** + * @tc.number: b_jsonutil_ParseBundleNameIndexStr_0200 + * @tc.name: b_jsonutil_ParseBundleNameIndexStr_0200 + * @tc.desc: Test function of ParseBundleNameIndexStr interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BJsonUtilTest, b_jsonutil_ParseBundleNameIndexStr_0200, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BJsonUtilTest-begin ParseBundleNameIndexStr_0200"; + try { + std::string bundleName = "com.hos.app01"; + BJsonUtil::BundleDetailInfo detailInfo = BJsonUtil::ParseBundleNameIndexStr(bundleName); + EXPECT_EQ("com.hos.app01", detailInfo.bundleName); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BDirTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BDirTest-end ParseBundleNameIndexStr_0200"; +} + /** * @tc.number: b_jsonutil_BuildBundleInfos_0100 * @tc.name: b_jsonutil_BuildBundleInfos_0100 @@ -77,31 +103,474 @@ HWTEST_F(BJsonUtilTest, b_jsonutil_BuildBundleInfos_0100, testing::ext::TestSize try { std::vector bundleNames; std::string bundleName = "com.hos.app01:1"; - std::string bundleName1 = "com.hos.app02"; bundleNames.push_back(bundleName); - bundleNames.push_back(bundleName1); - std::string pattern = ":"; - std::vector detailInfos; - std::string detail01 = "{ - "infos" : [ { - "details" : [ { - "detail" : [ { "source" : "com.ohos.app01", "target" : "com.hos.app01" } ], - "type" : "app_mapping_relation" } ], - "type" : "broadcast" } ] - }"; - detailInfos.push_back(detail01); - detailInfos.push_back(""); - int32_t userId = 100; - std::vector realBundleNames; - std::map> bundleNameDetailMap = - BJsonUtil::BuildBundleInfos(bundleNames, detailInfos, realBundleNames, userId); - std::string key = "com.hos.app01"; - EXPECT_EQ("com.hos.app01", bundleNameDetailMap[key].bundleName[0]); + std::vector bundleInfos; + std::string bundleInfo = "info1"; + std::string bundleInfo2 = "info2"; + bundleInfos.push_back(bundleInfo); + bundleInfos.push_back(bundleInfo2); + int32_t userId = TEST_USER_ID; + std::vector bundleNamesOnly; + std::map isClearDataFlags; + auto result = BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly, + userId, isClearDataFlags); + EXPECT_TRUE(result.empty()); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BJsonUtilTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BJsonUtilTest-end BuildBundleInfos_0100"; +} + +/** + * @tc.number: b_jsonutil_BuildBundleInfos_0200 + * @tc.name: b_jsonutil_BuildBundleInfos_0200 + * @tc.desc: Test function of BuildBundleInfos interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BJsonUtilTest, b_jsonutil_BuildBundleInfos_0200, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BJsonUtilTest-begin BuildBundleInfos_0200"; + try { + std::vector bundleNames; + std::string bundleName = "bundle"; + bundleNames.push_back(bundleName); + std::vector bundleInfos; + std::string bundleInfo = "{\"infos\":\"infos\"}"; + bundleInfos.push_back(bundleInfo); + int32_t userId = TEST_USER_ID; + std::vector bundleNamesOnly; + std::map isClearDataFlags; + auto result = BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly, + userId, isClearDataFlags); + EXPECT_FALSE(result.empty()); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BJsonUtilTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BJsonUtilTest-end BuildBundleInfos_0200"; +} + +/** + * @tc.number: b_jsonutil_BuildBundleInfos_0300 + * @tc.name: b_jsonutil_BuildBundleInfos_0300 + * @tc.desc: Test function of BuildBundleInfos interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BJsonUtilTest, b_jsonutil_BuildBundleInfos_0300, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BJsonUtilTest-begin BuildBundleInfos_0300"; + try { + std::vector bundleNames; + std::string bundleName = "bundle1:"; + bundleNames.push_back(bundleName); + std::vector bundleInfos; + std::string bundleInfo = "info1"; + bundleInfos.push_back(bundleInfo); + int32_t userId = TEST_USER_ID; + std::vector bundleNamesOnly; + std::map isClearDataFlags; + auto result = BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly, + userId, isClearDataFlags); + EXPECT_TRUE(result.empty()); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BJsonUtilTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BJsonUtilTest-end BuildBundleInfos_0300"; +} + +/** + * @tc.number: b_jsonutil_BuildBundleInfos_0301 + * @tc.name: b_jsonutil_BuildBundleInfos_0301 + * @tc.desc: Test function of BuildBundleInfos interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BJsonUtilTest, b_jsonutil_BuildBundleInfos_0301, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BJsonUtilTest-begin BuildBundleInfos_0301"; + try { + std::vector bundleNames; + std::string bundleName = ":bundle1"; + bundleNames.push_back(bundleName); + std::vector bundleInfos; + std::string bundleInfo = "info1"; + bundleInfos.push_back(bundleInfo); + int32_t userId = TEST_USER_ID; + std::vector bundleNamesOnly; + std::map isClearDataFlags; + auto result = BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly, + userId, isClearDataFlags); + EXPECT_TRUE(result.empty()); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BJsonUtilTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BJsonUtilTest-end BuildBundleInfos_0301"; +} + +/** + * @tc.number: b_jsonutil_BuildBundleInfos_0400 + * @tc.name: b_jsonutil_BuildBundleInfos_0400 + * @tc.desc: Test function of BuildBundleInfos interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BJsonUtilTest, b_jsonutil_BuildBundleInfos_0400, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BJsonUtilTest-begin BuildBundleInfos_0400"; + try { + std::vector bundleNames; + std::string bundleName = "bundle1"; + bundleNames.push_back(bundleName); + std::vector bundleInfos; + std::string bundleInfo = { + "{\"infos\":[{\"type\":\"type1\",\"details\":\"details1\"}],\"clearBackupData\": \"false\"}" + }; + bundleInfos.push_back(bundleInfo); + int32_t userId = TEST_USER_ID; + std::vector bundleNamesOnly; + std::map isClearDataFlags; + auto result = BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly, + userId, isClearDataFlags); + EXPECT_EQ(isClearDataFlags[bundleName], false); + EXPECT_FALSE(result.empty()); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BJsonUtilTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BJsonUtilTest-end BuildBundleInfos_0400"; +} + +/** + * @tc.number: b_jsonutil_BuildBundleInfos_0500 + * @tc.name: b_jsonutil_BuildBundleInfos_0500 + * @tc.desc: Test function of BuildBundleInfos interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BJsonUtilTest, b_jsonutil_BuildBundleInfos_0500, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BJsonUtilTest-begin BuildBundleInfos_0500"; + try { + std::vector bundleNames; + std::string bundleName = "bundle"; + bundleNames.push_back(bundleName); + std::vector bundleInfos; + std::string bundleInfo = {"{\"infos\":[{\"type\":null}]}"}; + bundleInfos.push_back(bundleInfo); + int32_t userId = TEST_USER_ID; + std::vector bundleNamesOnly; + std::map isClearDataFlags; + + auto result = BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly, + userId, isClearDataFlags); + EXPECT_EQ(isClearDataFlags[bundleName], true); + EXPECT_FALSE(result.empty()); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BJsonUtilTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BJsonUtilTest-end BuildBundleInfos_0500"; +} + +/** + * @tc.number: b_jsonutil_BuildBundleInfos_0600 + * @tc.name: b_jsonutil_BuildBundleInfos_0600 + * @tc.desc: Test function of BuildBundleInfos interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BJsonUtilTest, b_jsonutil_BuildBundleInfos_0600, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BJsonUtilTest-begin BuildBundleInfos_0600"; + try { + std::vector bundleNames; + std::string bundleName = "bundle"; + bundleNames.push_back(bundleName); + std::vector bundleInfos; + std::string bundleInfo = {"{\"infos\":[{\"type\":123}],\"clearBackupData\": \"true\"}"}; + bundleInfos.push_back(bundleInfo); + int32_t userId = TEST_USER_ID; + std::vector bundleNamesOnly; + std::map isClearDataFlags; + + auto result = BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly, + userId, isClearDataFlags); + EXPECT_EQ(isClearDataFlags[bundleName], true); + EXPECT_FALSE(result.empty()); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BJsonUtilTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BJsonUtilTest-end BuildBundleInfos_0600"; +} + +/** + * @tc.number: b_jsonutil_BuildBundleInfos_0700 + * @tc.name: b_jsonutil_BuildBundleInfos_0700 + * @tc.desc: Test function of BuildBundleInfos interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BJsonUtilTest, b_jsonutil_BuildBundleInfos_0700, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BJsonUtilTest-begin BuildBundleInfos_0700"; + try { + std::vector bundleNames; + std::string bundleName = "bundle"; + bundleNames.push_back(bundleName); + std::vector bundleInfos; + std::string bundleInfo = {"{\"infos\":[{\"type\":\"testType\",\"details\":null}]}"}; + bundleInfos.push_back(bundleInfo); + int32_t userId = TEST_USER_ID; + std::vector bundleNamesOnly; + std::map isClearDataFlags; + + auto result = BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly, + userId, isClearDataFlags); + EXPECT_FALSE(result.empty()); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BJsonUtilTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BJsonUtilTest-end BuildBundleInfos_0700"; +} + +/** + * @tc.number: b_jsonutil_BuildBundleInfos_0800 + * @tc.name: b_jsonutil_BuildBundleInfos_0800 + * @tc.desc: Test function of BuildBundleInfos interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BJsonUtilTest, b_jsonutil_BuildBundleInfos_0800, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BJsonUtilTest-begin BuildBundleInfos_0800"; + try { + std::vector bundleNames; + std::string bundleName = "bundle"; + bundleNames.push_back(bundleName); + std::vector bundleInfos; + std::string bundleInfo = {"{\"infos\":[{\"type\":\"testType\",\"details\":[]}]}"}; + bundleInfos.push_back(bundleInfo); + int32_t userId = TEST_USER_ID; + std::vector bundleNamesOnly; + std::map isClearDataFlags; + + auto result = BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly, + userId, isClearDataFlags); + EXPECT_FALSE(result.empty()); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BJsonUtilTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BJsonUtilTest-end BuildBundleInfos_0800"; +} + +/** + * @tc.number: b_jsonutil_BuildBundleInfos_0900 + * @tc.name: b_jsonutil_BuildBundleInfos_0900 + * @tc.desc: Test function of BuildBundleInfos interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BJsonUtilTest, b_jsonutil_BuildBundleInfos_0900, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BJsonUtilTest-begin BuildBundleInfos_0900"; + try { + std::vector bundleNames; + std::string bundleName = "bundle"; + bundleNames.push_back(bundleName); + std::vector bundleInfos; + std::string bundleInfo = {"{\"infos\":[{\"type\":\"testType\",\"details\":[\"detail\"]}]}"}; + bundleInfos.push_back(bundleInfo); + int32_t userId = TEST_USER_ID; + std::vector bundleNamesOnly; + std::map isClearDataFlags; + + auto result = BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly, + userId, isClearDataFlags); + EXPECT_FALSE(result.empty()); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BJsonUtilTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BJsonUtilTest-end BuildBundleInfos_0900"; +} + +/** + * @tc.number: b_jsonutil_BuildBundleInfos_1000 + * @tc.name: b_jsonutil_BuildBundleInfos_1000 + * @tc.desc: Test function of BuildBundleInfos interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BJsonUtilTest, b_jsonutil_BuildBundleInfos_1000, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BJsonUtilTest-begin BuildBundleInfos_1000"; + try { + std::vector bundleNames; + std::string bundleName = "bundle"; + bundleNames.push_back(bundleName); + std::vector bundleInfos; + std::string bundleInfo = {"{\"infos\":[\"infos\"]}"}; + bundleInfos.push_back(bundleInfo); + int32_t userId = TEST_USER_ID; + std::vector bundleNamesOnly; + std::map isClearDataFlags; + + auto result = BJsonUtil::BuildBundleInfos(bundleNames, bundleInfos, bundleNamesOnly, + userId, isClearDataFlags); + EXPECT_FALSE(result.empty()); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BJsonUtilTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BJsonUtilTest-end BuildBundleInfos_1000"; +} + +/** + * @tc.number: b_jsonutil_FindBundleInfoByName_0100 + * @tc.name: b_jsonutil_FindBundleInfoByName_0100 + * @tc.desc: Test function of FindBundleInfoByName interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BJsonUtilTest, b_jsonutil_FindBundleInfoByName_0100, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BJsonUtilTest-begin FindBundleInfoByName_0100"; + try { + std::map> bundleNameDetailsMap; + std::string bundleName = "bundle1"; + std::string jobType = "type"; + BJsonUtil::BundleDetailInfo bundleDetail; + + bool result = BJsonUtil::FindBundleInfoByName(bundleNameDetailsMap, bundleName, jobType, bundleDetail); + EXPECT_EQ(false, result); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BJsonUtilTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BJsonUtilTest-end FindBundleInfoByName_0100"; +} + +/** + * @tc.number: b_jsonutil_FindBundleInfoByName_0200 + * @tc.name: b_jsonutil_FindBundleInfoByName_0200 + * @tc.desc: Test function of FindBundleInfoByName interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BJsonUtilTest, b_jsonutil_FindBundleInfoByName_0200, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BJsonUtilTest-begin FindBundleInfoByName_0200"; + try { + std::map> bundleNameDetailsMap; + std::string bundleName = "bundle1"; + std::string jobType = "type"; + BJsonUtil::BundleDetailInfo detailInfo; + detailInfo.bundleName = bundleName; + detailInfo.type = jobType; + bundleNameDetailsMap[bundleName] = {detailInfo}; + BJsonUtil::BundleDetailInfo bundleDetail; + + bool result = BJsonUtil::FindBundleInfoByName(bundleNameDetailsMap, bundleName, jobType, bundleDetail); + EXPECT_EQ(true, result); + EXPECT_EQ(bundleDetail.type, detailInfo.type); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BJsonUtilTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BJsonUtilTest-end FindBundleInfoByName_0200"; +} + +/** + * @tc.number: b_jsonutil_FindBundleInfoByName_0300 + * @tc.name: b_jsonutil_FindBundleInfoByName_0300 + * @tc.desc: Test function of FindBundleInfoByName interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BJsonUtilTest, b_jsonutil_FindBundleInfoByName_0300, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BJsonUtilTest-begin FindBundleInfoByName_0300"; + try { + std::map> bundleNameDetailsMap; + std::string bundleName = "bundle1"; + std::string jobType = "type"; + std::string jobType1 = "type1"; + BJsonUtil::BundleDetailInfo detailInfo; + detailInfo.bundleName = bundleName; + detailInfo.type = jobType; + bundleNameDetailsMap[bundleName] = {detailInfo}; + BJsonUtil::BundleDetailInfo bundleDetail; + + bool result = BJsonUtil::FindBundleInfoByName(bundleNameDetailsMap, bundleName, jobType1, bundleDetail); + EXPECT_EQ(false, result); + } catch (...) { + EXPECT_TRUE(false); + GTEST_LOG_(INFO) << "BJsonUtilTest-an exception occurred."; + } + GTEST_LOG_(INFO) << "BJsonUtilTest-end FindBundleInfoByName_0300"; +} + +/** + * @tc.number: b_jsonutil_BuildExtensionErrInfo_0100 + * @tc.name: b_jsonutil_BuildExtensionErrInfo_0100 + * @tc.desc: Test function of BuildExtensionErrInfo interface for SUCCESS. + * @tc.size: MEDIUM + * @tc.type: FUNC + * @tc.level Level 0 + * @tc.require: I6F3GV + */ +HWTEST_F(BJsonUtilTest, b_jsonutil_BuildExtensionErrInfo_0100, testing::ext::TestSize.Level0) +{ + GTEST_LOG_(INFO) << "BJsonUtilTest-begin BuildExtensionErrInfo_0100"; + try { + std::string jsonStr; + int errCode = 1; + std::string errMsg = "error"; + + bool result = BJsonUtil::BuildExtensionErrInfo(jsonStr, errCode, errMsg); + EXPECT_EQ(true, result); + EXPECT_NE(jsonStr.find("errorCode"), std::string::npos); + EXPECT_NE(jsonStr.find("errorInfo"), std::string::npos); + EXPECT_NE(jsonStr.find("type"), std::string::npos); } catch (...) { EXPECT_TRUE(false); GTEST_LOG_(INFO) << "BJsonUtilTest-an exception occurred."; } - GTEST_LOG_(INFO) << "BJsonUtilTest-end b_dir_BuildBundleInfos_0100"; + GTEST_LOG_(INFO) << "BJsonUtilTest-end BuildExtensionErrInfo_0100"; } /* * @@ -127,8 +596,10 @@ HWTEST_F(BJsonUtilTest, b_jsonutil_BuildBundleInfos_0101, testing::ext::TestSize detailInfos.push_back(""); int32_t userId = 100; std::vector realBundleNames; + std::map isClearDataFlags; std::map> bundleNameDetailMap = - BJsonUtil::BuildBundleInfos(bundleNames, detailInfos, realBundleNames, userId); + BJsonUtil::BuildBundleInfos(bundleNames, detailInfos, realBundleNames, + userId, isClearDataFlags); EXPECT_EQ(0, bundleNameDetailMap.size()); } catch (...) { EXPECT_TRUE(false); diff --git a/tools/backup_tool/src/tools_op_backup.cpp b/tools/backup_tool/src/tools_op_backup.cpp index fcf892a4b20ff9e9d17e5dbf09020e5ff751ad0b..966827301d66a03fbb68745f6eaad4e02eab9e3a 100644 --- a/tools/backup_tool/src/tools_op_backup.cpp +++ b/tools/backup_tool/src/tools_op_backup.cpp @@ -189,6 +189,11 @@ static void OnBackupServiceDied(shared_ptr ctx) ctx->TryNotify(true); } +static void OnProcess(shared_ptr ctx, const std::string bundleName, const std::string processInfo) +{ + printf("OnProcess bundleName = %s, result = %s\n", bundleName.c_str(), processInfo.c_str()); +} + static void BackupToolDirSoftlinkToBackupDir() { // 判断BConstants::BACKUP_TOOL_LINK_DIR 是否是软链接 @@ -249,7 +254,8 @@ static int32_t InitPathCapFile(const string &pathCapFile, vector bundleN .onBundleFinished = bind(OnBundleFinished, ctx, placeholders::_1, placeholders::_2), .onAllBundlesFinished = bind(OnAllBundlesFinished, ctx, placeholders::_1), .onResultReport = bind(OnResultReport, ctx, placeholders::_1, placeholders::_2), - .onBackupServiceDied = bind(OnBackupServiceDied, ctx)}); + .onBackupServiceDied = bind(OnBackupServiceDied, ctx), + .onProcess = bind(OnProcess, ctx, placeholders::_1, placeholders::_2)}); if (ctx->session_ == nullptr) { printf("Failed to init backup\n"); FinishTrace(HITRACE_TAG_FILEMANAGEMENT); diff --git a/tools/backup_tool/src/tools_op_incremental_backup.cpp b/tools/backup_tool/src/tools_op_incremental_backup.cpp index 2be218c800ada8a4224c0b62cb7dfe62708eb175..32312082d56d756ab334699b9936f45e5d6b0269 100644 --- a/tools/backup_tool/src/tools_op_incremental_backup.cpp +++ b/tools/backup_tool/src/tools_op_incremental_backup.cpp @@ -224,6 +224,11 @@ static void OnBackupServiceDied(shared_ptr ctx) ctx->TryNotify(true); } +static void OnProcess(shared_ptr ctx, const std::string &bundleName, const std::string &processInfo) +{ + printf("OnProcess bundleName = %s, processInfo = %s\n", bundleName.c_str(), processInfo.c_str()); +} + static void BackupToolDirSoftlinkToBackupDir() { // 判断BConstants::BACKUP_TOOL_LINK_DIR 是否是软链接 @@ -308,7 +313,8 @@ static int32_t Init(const string &pathCapFile, const vector& bundleNames .onBundleFinished = bind(OnBundleFinished, ctx, placeholders::_1, placeholders::_2), .onAllBundlesFinished = bind(OnAllBundlesFinished, ctx, placeholders::_1), .onResultReport = bind(OnResultReport, ctx, placeholders::_1, placeholders::_2), - .onBackupServiceDied = bind(OnBackupServiceDied, ctx)}); + .onBackupServiceDied = bind(OnBackupServiceDied, ctx), + .onProcess = bind(OnProcess, ctx, placeholders::_1, placeholders::_2)}); if (ctx->session_ == nullptr) { printf("Failed to init backup\n"); FinishTrace(HITRACE_TAG_FILEMANAGEMENT); diff --git a/tools/backup_tool/src/tools_op_incremental_restore.cpp b/tools/backup_tool/src/tools_op_incremental_restore.cpp index a713c36424df282d5aa18b0fb886f271e0606250..64619efc9d26fd8ffd7e154a0257ec6e916d6a6b 100644 --- a/tools/backup_tool/src/tools_op_incremental_restore.cpp +++ b/tools/backup_tool/src/tools_op_incremental_restore.cpp @@ -219,6 +219,11 @@ static void OnResultReport(shared_ptr ctx, const std::string &bu printf("OnResultReport bundleName = %s, resultInfo = %s\n", bundleName.c_str(), resultInfo.c_str()); } +static void OnProcess(shared_ptr ctx, const std::string bundleName, const std::string processInfo) +{ + printf("OnProcess bundleName = %s, processInfo = %s\n", bundleName.c_str(), processInfo.c_str()); +} + static void RestoreApp(shared_ptr restore) { StartTrace(HITRACE_TAG_FILEMANAGEMENT, "RestoreApp"); @@ -272,7 +277,8 @@ static int32_t InitRestoreSession(shared_ptr ctx, .onBundleFinished = bind(OnBundleFinished, ctx, placeholders::_1, placeholders::_2), .onAllBundlesFinished = bind(OnAllBundlesFinished, ctx, placeholders::_1), .onResultReport = bind(OnResultReport, ctx, placeholders::_1, placeholders::_2), - .onBackupServiceDied = bind(OnBackupServiceDied, ctx)}); + .onBackupServiceDied = bind(OnBackupServiceDied, ctx), + .onProcess = bind(OnProcess, ctx, placeholders::_1, placeholders::_2)}); if (ctx->session_ == nullptr) { printf("Failed to init restore\n"); FinishTrace(HITRACE_TAG_FILEMANAGEMENT); diff --git a/tools/backup_tool/src/tools_op_incremental_restore_async.cpp b/tools/backup_tool/src/tools_op_incremental_restore_async.cpp index a2ff6d7d1b0b1335957a0e0677d0ff4946e83ba6..f39f53196a7688e059dbbf7cb48401246304a2e0 100644 --- a/tools/backup_tool/src/tools_op_incremental_restore_async.cpp +++ b/tools/backup_tool/src/tools_op_incremental_restore_async.cpp @@ -246,6 +246,11 @@ static void OnResultReport(shared_ptr ctx, const std::st printf("OnResultReport bundleName = %s, resultInfo = %s\n", bundleName.c_str(), resultInfo.c_str()); } +static void OnProcess(shared_ptr ctx, const std::string bundleName, const std::string processInfo) +{ + printf("OnProcess bundleName = %s, processInfo = %s\n", bundleName.c_str(), processInfo.c_str()); +} + static void RestoreApp(shared_ptr restore, vector &bundleNames) { StartTrace(HITRACE_TAG_FILEMANAGEMENT, "RestoreApp"); @@ -402,7 +407,8 @@ static int32_t InitArg(const string &pathCapFile, .onBundleFinished = bind(OnBundleFinished, ctx, placeholders::_1, placeholders::_2), .onAllBundlesFinished = bind(OnAllBundlesFinished, ctx, placeholders::_1), .onResultReport = bind(OnResultReport, ctx, placeholders::_1, placeholders::_2), - .onBackupServiceDied = bind(OnBackupServiceDied, ctx)}); + .onBackupServiceDied = bind(OnBackupServiceDied, ctx), + .onProcess = bind(OnProcess, ctx, placeholders::_1, placeholders::_2)}); if (ctx->session_ == nullptr) { printf("Failed to init restore\n"); FinishTrace(HITRACE_TAG_FILEMANAGEMENT); diff --git a/tools/backup_tool/src/tools_op_restore.cpp b/tools/backup_tool/src/tools_op_restore.cpp index e9c172426397c364c216df94fb40f2e90cbb1b24..bcf4075e88a7e7272cb22a2c1cb5a7cda860bb4e 100644 --- a/tools/backup_tool/src/tools_op_restore.cpp +++ b/tools/backup_tool/src/tools_op_restore.cpp @@ -197,6 +197,11 @@ static void OnBackupServiceDied(shared_ptr ctx) ctx->TryNotify(true); } +static void OnProcess(shared_ptr ctx, const std::string bundleName, const std::string processInfo) +{ + printf("OnProcess bundleName = %s, processInfo = %s\n", bundleName.c_str(), processInfo.c_str()); +} + static void RestoreApp(shared_ptr restore, vector &bundleNames, bool updateSendFiles) { StartTrace(HITRACE_TAG_FILEMANAGEMENT, "RestoreApp"); @@ -257,7 +262,8 @@ static int32_t InitRestoreSession(shared_ptr ctx) .onBundleFinished = bind(OnBundleFinished, ctx, placeholders::_1, placeholders::_2), .onAllBundlesFinished = bind(OnAllBundlesFinished, ctx, placeholders::_1), .onResultReport = bind(OnResultReport, ctx, placeholders::_1, placeholders::_2), - .onBackupServiceDied = bind(OnBackupServiceDied, ctx)}); + .onBackupServiceDied = bind(OnBackupServiceDied, ctx), + .onProcess = bind(OnProcess, ctx, placeholders::_1, placeholders::_2)}); if (ctx->session_ == nullptr) { printf("Failed to init restore\n"); FinishTrace(HITRACE_TAG_FILEMANAGEMENT); diff --git a/tools/backup_tool/src/tools_op_restore_async.cpp b/tools/backup_tool/src/tools_op_restore_async.cpp index a12a600f08e399b2d46b5b5a481742fe9f1d12ba..c87462f695277adc87d3b820a687ed80956946de 100644 --- a/tools/backup_tool/src/tools_op_restore_async.cpp +++ b/tools/backup_tool/src/tools_op_restore_async.cpp @@ -170,6 +170,11 @@ static void OnBackupServiceDied(shared_ptr ctx) ctx->TryNotify(true); } +static void OnProcess(shared_ptr ctx, const std::string bundleName, const std::string processInfo) +{ + printf("OnProcess bundleName = %s, processInfo = %s\n", bundleName.c_str(), processInfo.c_str()); +} + static map> ReadyExtManage(const string &path, std::vector& pkgInfo) { @@ -385,7 +390,8 @@ static int32_t InitArg(const string &pathCapFile, .onBundleFinished = bind(OnBundleFinished, ctx, placeholders::_1, placeholders::_2), .onAllBundlesFinished = bind(OnAllBundlesFinished, ctx, placeholders::_1), .onResultReport = bind(OnResultReport, ctx, placeholders::_1, placeholders::_2), - .onBackupServiceDied = bind(OnBackupServiceDied, ctx)}); + .onBackupServiceDied = bind(OnBackupServiceDied, ctx), + .onProcess = bind(OnProcess, ctx, placeholders::_1, placeholders::_2)}); if (ctx->session_ == nullptr) { printf("Failed to init restore\n"); FinishTrace(HITRACE_TAG_FILEMANAGEMENT); diff --git a/utils/BUILD.gn b/utils/BUILD.gn index 632b98ae19d07e3f5b0b2cba10d0607a7e2cd9fd..bb735177f50a48d20285bcf95305d35d7abc34a3 100644 --- a/utils/BUILD.gn +++ b/utils/BUILD.gn @@ -65,6 +65,7 @@ ohos_shared_library("backup_utils") { "src/b_filesystem/b_dir.cpp", "src/b_filesystem/b_file.cpp", "src/b_filesystem/b_file_hash.cpp", + "src/b_json/b_json_clear_data_config.cpp", "src/b_json/b_json_entity_ext_manage.cpp", "src/b_json/b_json_entity_extension_config.cpp", "src/b_json/b_json_service_disposal_config.cpp", @@ -74,26 +75,33 @@ ohos_shared_library("backup_utils") { "src/b_process/b_guard_cwd.cpp", "src/b_process/b_guard_signal.cpp", "src/b_process/b_process.cpp", + "src/b_radar/b_radar.cpp", "src/b_sa/b_sa_utils.cpp", "src/b_tarball/b_tarball_cmdline.cpp", "src/b_tarball/b_tarball_factory.cpp", + "src/b_utils/b_time.cpp", ] configs = [ ":utils_private_config" ] public_configs = [ ":utils_public_config" ] external_deps = [ + "access_token:libaccesstoken_sdk", + "access_token:libtokenid_sdk", "cJSON:cjson", "c_utils:utils", "faultloggerd:libdfx_dumpcatcher", "hilog:libhilog", + "hisysevent:libhisysevent", "hitrace:hitrace_meter", "init:libbegetutil", + "ipc:ipc_core", ] include_dirs = [ "${path_init}/interfaces/innerkits/include/syspara", "${path_backup}/interfaces/inner_api/native/backup_kit_inner/impl", + "${path_backup}/utils/include", ] deps = [ diff --git a/utils/include/b_error/b_error.h b/utils/include/b_error/b_error.h index 02bd0440ef0a0fee58fc295e28e33e799135a652..6de44f35f40698b19f2bc0ec86860e3865c9057d 100644 --- a/utils/include/b_error/b_error.h +++ b/utils/include/b_error/b_error.h @@ -70,8 +70,9 @@ public: SA_REFUSED_ACT = 0x3002, SA_BROKEN_ROOT_DIR = 0x3003, SA_FORBID_BACKUP_RESTORE = 0x3004, - SA_BOOT_TIMEOUT = 0x3005, + SA_BOOT_EXT_TIMEOUT = 0x3005, SA_BUNDLE_INFO_EMPTY = 0x3006, + SA_BOOT_EXT_FAIL = 0x3007, // 0x4000~0x4999 backup_SDK错误 SDK_INVAL_ARG = 0x4000, @@ -89,6 +90,9 @@ public: EXT_BACKUP_PACKET_ERROR = 0x5007, EXT_METHOD_NOT_EXIST = 0x5008, EXT_THROW_EXCEPTION = 0x5009, + EXT_BACKUP_UNPACKET_ERROR = 0x5010, + EXT_TIMER_ERROR = 0x5011, + EXT_CREATE_DIR_ERROR = 0x5012, // 0x6000~0x6999 sa_ext错误 SA_EXT_ERR_CALL = 0x6000, @@ -112,6 +116,9 @@ public: E_EMPTY = 13500005, E_PACKET = 13500006, E_EXCEPTION = 13500007, + E_UNPACKET = 13500008, + E_BEF = 13500009, + E_TASKFAIL = 13500010, }; public: @@ -149,6 +156,19 @@ public: return msg_.c_str(); } + /** + * @brief 归一返回备份恢复错误码 + * + * @return ErrCode 备份恢复错误码 + */ + static ErrCode GetBackupCodeByErrno(ErrCode err); + + /** + * @brief 归一返回备份恢复错误信息 + * + * @return string 备份恢复错误信息 + */ + static std::string GetBackupMsgByErrno(ErrCode err); public: /** * @brief 重载bool操作符,判断当前错误是否是错误 @@ -227,8 +247,9 @@ private: {Codes::SA_REFUSED_ACT, "SA refuse to act"}, {Codes::SA_BROKEN_ROOT_DIR, "SA failed to operate on the given root dir"}, {Codes::SA_FORBID_BACKUP_RESTORE, "SA forbid backup or restore"}, - {Codes::SA_BOOT_TIMEOUT, "SA boot application extension time out"}, + {Codes::SA_BOOT_EXT_TIMEOUT, "SA boot application extension time out"}, {Codes::SA_BUNDLE_INFO_EMPTY, "SA the bundle info for backup/restore is empty"}, + {Codes::SA_BOOT_EXT_FAIL, "SA failed to boot application extension"}, {Codes::SDK_INVAL_ARG, "SDK received invalid arguments"}, {Codes::SDK_BROKEN_IPC, "SDK failed to do IPC"}, {Codes::SDK_MIXED_SCENARIO, "SDK involed backup/restore when doing the contrary"}, @@ -240,7 +261,12 @@ private: {Codes::EXT_ABILITY_DIED, "Extension process died"}, {Codes::EXT_FORBID_BACKUP_RESTORE, "forbid backup or restore"}, {Codes::EXT_BACKUP_PACKET_ERROR, "Backup packet error"}, + {Codes::EXT_METHOD_NOT_EXIST, "Extension method not exist"}, {Codes::EXT_THROW_EXCEPTION, "Extension throw exception"}, + {Codes::EXT_BACKUP_UNPACKET_ERROR, "Backup unpacket error"}, + {Codes::SA_EXT_ERR_CALL, "SA Extension received invalid arguments"}, + {Codes::SA_EXT_ERR_SAMGR, "SA Extension get samgr failed"}, + {Codes::SA_EXT_RELOAD_FAIL, "SA Extension reload failed"}, }; static inline const std::map errCodeTable_ { @@ -256,8 +282,9 @@ private: {static_cast(Codes::SA_REFUSED_ACT), BackupErrorCode::E_PERM}, {static_cast(Codes::SA_BROKEN_ROOT_DIR), BackupErrorCode::E_UKERR}, {static_cast(Codes::SA_FORBID_BACKUP_RESTORE), BackupErrorCode::E_FORBID}, - {static_cast(Codes::SA_BOOT_TIMEOUT), BackupErrorCode::E_BTO}, + {static_cast(Codes::SA_BOOT_EXT_TIMEOUT), BackupErrorCode::E_BTO}, {static_cast(Codes::SA_BUNDLE_INFO_EMPTY), BackupErrorCode::E_EMPTY}, + {static_cast(Codes::SA_BOOT_EXT_FAIL), BackupErrorCode::E_BEF}, {static_cast(Codes::SDK_INVAL_ARG), BackupErrorCode::E_INVAL}, {static_cast(Codes::SDK_BROKEN_IPC), BackupErrorCode::E_IPCSS}, {static_cast(Codes::SDK_MIXED_SCENARIO), BackupErrorCode::E_INVAL}, @@ -269,7 +296,12 @@ private: {static_cast(Codes::EXT_ABILITY_TIMEOUT), BackupErrorCode::E_ETO}, {static_cast(Codes::EXT_FORBID_BACKUP_RESTORE), BackupErrorCode::E_FORBID}, {static_cast(Codes::EXT_BACKUP_PACKET_ERROR), BackupErrorCode::E_PACKET}, + {static_cast(Codes::EXT_METHOD_NOT_EXIST), BackupErrorCode::E_INVAL}, {static_cast(Codes::EXT_THROW_EXCEPTION), BackupErrorCode::E_EXCEPTION}, + {static_cast(Codes::EXT_BACKUP_UNPACKET_ERROR), BackupErrorCode::E_UNPACKET}, + {static_cast(Codes::SA_EXT_ERR_CALL), BackupErrorCode::E_INVAL}, + {static_cast(Codes::SA_EXT_ERR_SAMGR), BackupErrorCode::E_IPCSS}, + {static_cast(Codes::SA_EXT_RELOAD_FAIL), BackupErrorCode::E_BEF}, {BackupErrorCode::E_IPCSS, BackupErrorCode::E_IPCSS}, {BackupErrorCode::E_INVAL, BackupErrorCode::E_INVAL}, {BackupErrorCode::E_NOTEXIST, BackupErrorCode::E_NOTEXIST}, @@ -285,10 +317,12 @@ private: {BackupErrorCode::E_EMPTY, BackupErrorCode::E_EMPTY}, {BackupErrorCode::E_PACKET, BackupErrorCode::E_PACKET}, {BackupErrorCode::E_EXCEPTION, BackupErrorCode::E_EXCEPTION}, + {BackupErrorCode::E_UNPACKET, BackupErrorCode::E_UNPACKET}, + {BackupErrorCode::E_BEF, BackupErrorCode::E_BEF}, }; static inline const std::map sysErrnoCodeTable_ { - {EPERM, BackupErrorCode::E_IPCSS}, + {EPERM, BackupErrorCode::E_PERM}, {EIO, BackupErrorCode::E_IO}, {EBADF, BackupErrorCode::E_IO}, {EACCES, BackupErrorCode::E_IO}, @@ -302,6 +336,26 @@ private: {ENOSPC, BackupErrorCode::E_NOSPC}, }; + static inline const std::map backupErrorMsgTable_ { + {BackupErrorCode::E_IPCSS, "IPC error"}, + {BackupErrorCode::E_INVAL, "Invalid argument"}, + {BackupErrorCode::E_NOTEXIST, "Method not exist"}, + {BackupErrorCode::E_UKERR, "Unknown error"}, + {BackupErrorCode::E_PERM, "Operation not permitted"}, + {BackupErrorCode::E_NOMEM, "Out of memory"}, + {BackupErrorCode::E_NOSPC, "No space left on device"}, + {BackupErrorCode::E_IO, "I/O error"}, + {BackupErrorCode::E_FORBID, "Not support backup/restore"}, + {BackupErrorCode::E_BTO, "SA boot extension timeout"}, + {BackupErrorCode::E_ETO, "Extension process timeout"}, + {BackupErrorCode::E_DIED, "Extension process died"}, + {BackupErrorCode::E_EMPTY, "SA the bundle info for backup/restore is empty"}, + {BackupErrorCode::E_PACKET, "Tar failed"}, + {BackupErrorCode::E_EXCEPTION, "Extension throw exception"}, + {BackupErrorCode::E_UNPACKET, "Untar failed"}, + {BackupErrorCode::E_BEF, "SA failed to boot application extension"}, + }; + private: Codes code_ {Codes::OK}; std::string msg_; diff --git a/utils/include/b_filesystem/b_dir.h b/utils/include/b_filesystem/b_dir.h index 753529cb63e2eb48567c061412314a7ceb966072..5f4670a67ba95b989cd86bce353cc55692c73e26 100644 --- a/utils/include/b_filesystem/b_dir.h +++ b/utils/include/b_filesystem/b_dir.h @@ -26,6 +26,7 @@ #include #include +#include "b_json/b_report_entity.h" #include "errors.h" namespace OHOS::FileManagement::Backup { @@ -46,7 +47,7 @@ public: * @param excludes 需要排除的文件及目录集合 * @return 错误码、大文件名集合 */ - static std::tuple, std::vector> GetBigFiles( + static std::tuple, std::map> GetBigFiles( const std::vector &includes, const std::vector &excludes); /** @@ -56,6 +57,40 @@ public: * @return std::vector 目录集合 */ static std::vector GetDirs(const std::vector &paths); + + /** + * @brief 从给定的includes和excludes目录中获取所有的大文件和小文件 + * + * @param includes 需要包含的文件及目录集合 + * @param excludes 需要排除的文件及目录集合 + * @return 大文件和小文件的集合 + */ + static std::tuple, std::vector> GetBackupList( + const std::vector &includes, const std::vector &excludes); + + /** + * @brief 获取bigfile和smaillfile的文件信息并生成清单 + * + * @param bigFile 需要包含的文件及目录集合 + * @param smallFile 需要排除的文件及目录集合 + * @param allFiles 生成的所有文件信息清单 + * @param smallFiles 生成的小文件信息清单 + * @param bigFiles 生成的大文件信息清单 + * @return + */ + static void GetUser0FileStat(std::vector bigFile, + std::vector smallFile, + std::vector &allFiles, + std::vector &smallFiles, + std::vector &bigFiles); + + /** + * @brief 核实文件是否为异常无效路径 + * + * @param filePath 待核实的路径 + * @return 是否是异常无效路径 + */ + static bool CheckFilePathInvalid(const std::string &filePath); }; } // namespace OHOS::FileManagement::Backup diff --git a/utils/include/b_filesystem/b_file.h b/utils/include/b_filesystem/b_file.h index 2d69e75fdf09cf070018f38bef7c84d6ee6fd9f7..c2cc3c8af2f59f3b8e04cde0c92bc8675fe93d94 100644 --- a/utils/include/b_filesystem/b_file.h +++ b/utils/include/b_filesystem/b_file.h @@ -82,6 +82,16 @@ public: * @return false some error occur */ static bool GetRealPath(const string &path, string &realPath); + + /** + * @brief check if string is endswith suffix + * + * @param str str + * @param suffix suffix str + * @return true str is endswith suffix + * @return false str is not endswith suffix + */ + static bool EndsWith(const string &str, const string &suffix); private: }; } // namespace OHOS::FileManagement::Backup diff --git a/utils/include/b_json/b_json_clear_data_config.h b/utils/include/b_json/b_json_clear_data_config.h new file mode 100644 index 0000000000000000000000000000000000000000..1f60863fcc3e2be9d8f3fad8c485cdb9d67c2fde --- /dev/null +++ b/utils/include/b_json/b_json_clear_data_config.h @@ -0,0 +1,86 @@ +/* + * Copyright (c) 2024 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef OHOS_FILEMGMT_BACKUP_B_JSON_CLEAR_DATA_CONFIG_H +#define OHOS_FILEMGMT_BACKUP_B_JSON_CLEAR_DATA_CONFIG_H + +#include +#include +#include + +namespace OHOS::FileManagement::Backup { +class BJsonClearDataConfig { +public: + /** + * @brief 判断配置文件中是否有记录 + * + */ + bool HasClearBundleRecord(); + + /** + * @brief 判断配置文件中是否存在bundleName记录 + * + * @param bundlename + */ + bool FindClearBundleRecord(const std::string& bundleName); + + /** + * @brief 配置文件中插入bundleName记录 + * + * @param bundlename + */ + bool InsertClearBundleRecord(const std::string& bundleName); + + /** + * @brief 配置文件中删除bundleName记录 + * + * @param bundlename + */ + bool DeleteClearBundleRecord(const std::string& bundleName); + + /** + * @brief 配置文件中获取bundlename + * + */ + std::vector GetAllClearBundleRecords(); + + /** + * @brief 删除配置文件 + * + * + */ + bool DeleteConfigFile(); + +public: + /** + * @brief 构造方法 + * + * + */ + BJsonClearDataConfig(); +private: + /** + * @brief 配置文件中删除bundleName记录 + * + * @param bundlename + */ + bool WriteClearBundleRecord(const std::string& bundleName); + +private: + std::mutex fileMutex_; +}; + +} // namespace OHOS::FileManagement::Backup +#endif // OHOS_FILEMGMT_BACKUP_B_JSON_CLEAR_DATA_CONFIG_H \ No newline at end of file diff --git a/utils/include/b_json/b_json_entity_caps.h b/utils/include/b_json/b_json_entity_caps.h index 548beef14028f335b4138673c18544a286212624..74d092864e9b6f7f3356106cf9db82701ee4678d 100644 --- a/utils/include/b_json/b_json_entity_caps.h +++ b/utils/include/b_json/b_json_entity_caps.h @@ -24,6 +24,7 @@ class BJsonEntityCaps : public BJsonEntity { public: struct BundleInfo { std::string name; + int appIndex; int64_t versionCode; std::string versionName; int64_t spaceOccupied; @@ -74,6 +75,7 @@ public: for (const auto &item : bundleInfos) { Json::Value arrObj; arrObj["name"] = item.name; + arrObj["appIndex"] = item.appIndex; arrObj["versionCode"] = item.versionCode; arrObj["versionName"] = item.versionName; arrObj["spaceOccupied"] = item.spaceOccupied; @@ -146,7 +148,7 @@ public: return obj_["extraInfo"]; } - bool CheckBundlePropertiesIsValid(const Json::Value &bundleInfo) + bool CheckBundlePropertiesValid(const Json::Value &bundleInfo) { if (!bundleInfo) { HILOGE("Failed Check bundleInfo"); @@ -187,7 +189,7 @@ public: } std::vector bundleInfos; for (const auto &item : obj_["bundleInfos"]) { - if (!CheckBundlePropertiesIsValid(item)) { + if (!CheckBundlePropertiesValid(item)) { return {}; } string restoreDeps(""); @@ -202,18 +204,21 @@ public: if (item.isMember("extraInfo") && item["extraInfo"].isObject()) { extraInfo = item["extraInfo"]; } - int64_t increSpaceOccupied = 0; - if (item.isMember("increSpaceOccupied") && item["increSpaceOccupied"].isInt64()) { - increSpaceOccupied = item["increSpaceOccupied"].asInt64(); - } bool fullBackupOnly = false; if (item.isMember("fullBackupOnly") && item["fullBackupOnly"].isBool()) { fullBackupOnly = item["fullBackupOnly"].asBool(); } - bundleInfos.emplace_back(BundleInfo {item["name"].asString(), item["versionCode"].asInt64(), + int appIndex = 0; + if (item.isMember("appIndex") && item["appIndex"].isInt()) { + appIndex = item["appIndex"].asInt(); + } + int64_t increSpaceOccupied = 0; + if (item.isMember("increSpaceOccupied") && item["increSpaceOccupied"].isInt64()) { + increSpaceOccupied = item["increSpaceOccupied"].asInt64(); + } + bundleInfos.emplace_back(BundleInfo {item["name"].asString(), appIndex, item["versionCode"].asInt64(), item["versionName"].asString(), item["spaceOccupied"].asInt64(), - increSpaceOccupied, - item["allToBackup"].asBool(), fullBackupOnly, + increSpaceOccupied, item["allToBackup"].asBool(), fullBackupOnly, item["extensionName"].asString(), restoreDeps, supportScene, extraInfo}); } diff --git a/utils/include/b_jsonutil/b_jsonutil.h b/utils/include/b_jsonutil/b_jsonutil.h index 9efa19376a7aefef8919af267bb726b03d044de9..37c050a31f1ff8ad7429d2a0c358d5420244d324 100644 --- a/utils/include/b_jsonutil/b_jsonutil.h +++ b/utils/include/b_jsonutil/b_jsonutil.h @@ -34,11 +34,10 @@ public: * @brief 带有拼接字符的bundleName按照拼接字符进行分割 * * @param bundleNameStr bundleName拼接index的字符串 - * @param patternInfo 拼接字符串 * * @return 分割好的结果赋值给结构体 */ - static BundleDetailInfo ParseBundleNameIndexStr (const std::string &bundleNameStr, const std::string &patternInfo); + static BundleDetailInfo ParseBundleNameIndexStr (const std::string &bundleNameStr); /** * @brief 将传进来的bundleNames的集合进行按照拼接字符分割处理 @@ -48,26 +47,28 @@ public: * @param patternInfo 拼接的字符 * @param realBundleNames 分割后真正的bundleNames * @param userId userId + * @param isClearDataFlags 框架是否清理标志集合 * * @return 包名和解析结果的对应关系集合 * */ static std::map> BuildBundleInfos( const std::vector &bundleNames, const std::vector &details, - std::vector &realBundleNames, int32_t userId); + std::vector &realBundleNames, int32_t userId, + std::map &isClearDataFlags); /** * @brief 解析单个bundle对应的json串 * - * @param bundleDetailInfo json串 - * @param bundleDetail 结构体对象 - * @param bundleNameOnly bundle名称 - * @param bundleIndex bundle对应的索引 + * @param bundleInfo json串 + * @param bundleDetails 结构体对象 + * @param bundleDetailInfo bundle信息 + * @param isClearData 框架是否清理标志 * @param userId userId * */ static void ParseBundleInfoJson(const std::string &bundleInfo, std::vector &bundleDetails, - std::string &bundleNameOnly, int bundleIndex, int32_t userId); + BJsonUtil::BundleDetailInfo bundleDetailInfo, bool &isClearData, int32_t userId); /** * @brief 根据业务类型和bundleName确定唯一的bundleInfo @@ -93,7 +94,70 @@ public: * @return 是否组建成功 * */ - static bool BuildRestoreErrInfo(std::string &jsonStr, int errCode, std::string errMsg); + static bool BuildExtensionErrInfo(std::string &jsonStr, int errCode, std::string errMsg); + + /* * + * @brief 组建恢复文件错误信息的json + * + * @param jsonStr 组建结果 + * @param errCode 错误码 + * + * @return 是否组建成功 + * + */ + static bool BuildExtensionErrInfo(std::string &jsonStr, std::map> errFileInfo); + + /* * + * @brief 组建App进度返回的信息 + * @param jsonStr 组建结果 + * @param onProcessRet onProcess接口返回值 + * + * @return 是否组建成功 + * + */ + static bool BuildOnProcessRetInfo(std::string &jsonStr, std::string onProcessRet); + + /* * + * @brief 拼接包名和分身对应的索引 + * + * @param bundleName 包名 + * @param bundleIndex 索引 + * + * @return 拼接结果 + */ + static std::string BuildBundleNameIndexInfo(const std::string &bundleName, int bundleIndex); + /** + * @brief 组建App进度返回的信息 + * + * @param reportInfo 组建结果 + * @param path 报错文件 + * @param err 错误码 + * + * @return 是否组建成功 + * + */ + static bool BuildOnProcessErrInfo(std::string &reportInfo, std::string path, int err); + + /** + * @brief 构建包含userId的detailInfo + * + * @param userId userId + * @param detailInfo 包含userId的detailInfo + * + * @return 是否组建成功 + * + */ + static bool BuildBundleInfoJson(int32_t userId, std::string &detailInfo); + + /** + * @brief 判断传入的bundleinfo中是否包含unicast字段 + * + * @param bundleinfo json串 + * + * @return 是否包含unicast字段 + * + */ + static bool HasUnicastInfo(std::string &bundleInfo); }; } // namespace OHOS::FileManagement::Backup diff --git a/utils/include/b_ohos/startup/backup_para.h b/utils/include/b_ohos/startup/backup_para.h index 1cdf807375b263ddc4b262b44a85454eb9fb2f1b..c5c6ef481e2a6898dedc4200ef6a0c4dc99319ad 100644 --- a/utils/include/b_ohos/startup/backup_para.h +++ b/utils/include/b_ohos/startup/backup_para.h @@ -49,6 +49,13 @@ public: * @return 获取的配置项backup.overrideIncrementalRestore的值为true时则返回true,否则返回false */ bool GetBackupOverrideIncrementalRestore(); + + /** + * @brief 获取backup.para配置项backupDebugState的值 + * + * @return 获取的配置项backup.backupDebugState的值为true时则返回true,否则返回false + */ + static bool GetBackupDebugState(); }; } // namespace OHOS::FileManagement::Backup diff --git a/utils/include/b_radar/b_radar.h b/utils/include/b_radar/b_radar.h new file mode 100644 index 0000000000000000000000000000000000000000..2ec80872ed849717674d7aa70fc536c7e16f95d6 --- /dev/null +++ b/utils/include/b_radar/b_radar.h @@ -0,0 +1,133 @@ +/* + * Copyright (c) 2024 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef OHOS_FILEMGMT_BACKUP_B_RADAR_H +#define OHOS_FILEMGMT_BACKUP_B_RADAR_H +#include +#include +#include "i_service_reverse.h" + +namespace OHOS::FileManagement::Backup { +enum class BizStageBackup : int32_t { + BIZ_STAGE_DEFAULT = 0, + BIZ_STAGE_BOOT_BACKUP_SA_FAIL, + BIZ_STAGE_GET_LOCAL_CAPABILITIES_FAIL, + BIZ_STAGE_CREATE_BACKUP_SESSION_FAIL, + BIZ_STAGE_APPEND_BUNDLES_FAIL, + BIZ_STAGE_CONNECT_EXTENSION_FAIL, + BIZ_STAGE_START_DISPOSE, + BIZ_STAGE_EXTENSION_ABNORMAL_EXIT_CLEAR_FAIL, + BIZ_STAGE_GET_BACKUP_INFO_FAIL, + BIZ_STAGE_ON_BACKUP, + BIZ_STAGE_DO_BACKUP, + BIZ_STAGE_CHECK_DATA_FAIL, + BIZ_STAGE_END_DISPOSE, + BIZ_STAGE_PERMISSION_CHECK_FAIL, + BIZ_STAGE_EXECU_FAIL, + BIZ_STAGE_ACTIVE_SESSION, + BIZ_STAGE_DEACTIVE_SESSION, + BIZ_STAGE_RELEASE, + BIZ_STAGE_ONSTART_DISPOSE, + BIZ_STAGE_ONSTART_RESIDUAL +}; + +enum class BizStageRestore : int32_t { + BIZ_STAGE_DEFAULT = 0, + BIZ_STAGE_BOOT_BACKUP_SA_FAIL, + BIZ_STAGE_GET_LOCAL_CAPABILITIES_FAIL, + BIZ_STAGE_CREATE_RESTORE_SESSION_FAIL, + BIZ_STAGE_APPEND_BUNDLES_FAIL, + BIZ_STAGE_CONNECT_EXTENSION_FAIL, + BIZ_STAGE_START_DISPOSE, + BIZ_STAGE_EXTENSION_ABNORMAL_EXIT_CLEAR_FAIL, + BIZ_STAGE_GET_FILE_HANDLE_FAIL, + BIZ_STAGE_DO_RESTORE, + BIZ_STAGE_CHECK_DATA_FAIL, + BIZ_STAGE_ON_RESTORE, + BIZ_STAGE_END_DISPOSE, + BIZ_STAGE_PERMISSION_CHECK_FAIL, + BIZ_STAGE_EXECU_FAIL, + BIZ_STAGE_ACTIVE_SESSION, + BIZ_STAGE_DEACTIVE_SESSION, + BIZ_STAGE_RELEASE, + BIZ_STAGE_ONSTART_DISPOSE, + BIZ_STAGE_ONSTART_RESIDUAL +}; + +class AppRadar { +public: + static AppRadar &GetInstance() + { + static AppRadar instance; + return instance; + } + +public: + struct Info { + std::string bundleName; + std::string status; + std::string resInfo; + + Info(const std::string &bundleName, const std::string &status, const std::string &resInfo) + : bundleName(bundleName), status(status), resInfo(resInfo) {} + }; + + struct DoRestoreInfo { + uint32_t bigFileNum; + uint64_t bigFileSize; + int64_t bigFileSpendTime; + uint32_t tarFileNum; + uint64_t tarFileSize; + int64_t tarFileSpendTime; + int64_t totalFileSpendTime; + }; + + struct DoBackupInfo { + int64_t cost; + uint32_t allFileNum; + uint32_t smallFileNum; + uint32_t tarFileNum; + uint32_t includeNum; + uint32_t excludeNum; + }; + + struct StatInfo { + std::string callerName; + std::string resInfo; + + StatInfo(const std::string &callerName, const std::string &resInfo) + : callerName(callerName), resInfo(resInfo) {} + }; + +public: + int32_t GetUserId(); + void RecordDefaultFuncRes(Info &info, const std::string &func, int32_t userId, + enum BizStageBackup bizStage, int32_t resultCode); + void RecordBackupFuncRes(Info &info, const std::string &func, int32_t userId, + enum BizStageBackup bizStage, int32_t resultCode); + void RecordRestoreFuncRes(Info &info, const std::string &func, int32_t userId, + enum BizStageRestore bizStage, int32_t resultCode); + void RecordStatisticRes(StatInfo &statInfo, int32_t userId, enum IServiceReverse::Scenario scenario, + int32_t succ_cnt, int32_t fail_cnt, int32_t resultCode); +private: + AppRadar() = default; + ~AppRadar() = default; + AppRadar(const AppRadar &) = delete; + AppRadar &operator=(const AppRadar &) = delete; + AppRadar(AppRadar &&) = delete; + AppRadar &operator=(AppRadar &&) = delete; +}; +} // namespace OHOS::FileManagement::AppRadar +#endif // OHOS_FILEMGMT_BACKUP_B_RADAR_H diff --git a/utils/include/b_resources/b_constants.h b/utils/include/b_resources/b_constants.h index 512526b5caba6b5f2a9c5910abd550148247f969..fe7934006af567336cd85b49f86762f2645b64ec 100644 --- a/utils/include/b_resources/b_constants.h +++ b/utils/include/b_resources/b_constants.h @@ -30,6 +30,7 @@ static inline const char *EXTENSION_VERSION_CODE_PARA = "versionCode"; static inline const char *EXTENSION_VERSION_NAME_PARA = "versionName"; static inline const char *EXTENSION_RESTORE_EXT_INFO_PARA = "restoreExtInfo"; static inline const char *EXTENSION_BACKUP_EXT_INFO_PARA = "backupExtInfo"; +static inline const char *EXTENSION_APP_CLONE_INDEX_PARA = "ohos.extra.param.key.appCloneIndex"; enum class ExtensionAction { INVALID = 0, @@ -42,6 +43,7 @@ enum ServiceSchedAction { START = 1, RUNNING = 2, FINISH = 3, + CLEAN = 4, }; constexpr int SPAN_USERID_UID = 200000; @@ -50,7 +52,7 @@ constexpr int XTS_UID = 1; constexpr int DEFAULT_USER_ID = 100; constexpr int BACKUP_UID = 1089; constexpr int EXTENSION_THREAD_POOL_COUNT = 1; -constexpr int BACKUP_LOADSA_TIMEOUT_MS = 4000; +constexpr int BACKUP_LOADSA_TIMEOUT_MS = 5000; constexpr int DECIMAL_BASE = 10; // 十进制基数 @@ -67,6 +69,11 @@ constexpr int IPC_MAX_WAIT_TIME = 3000; // IPC通讯最大等待时间(s) constexpr int MAX_PARCELABLE_VECTOR_NUM = 10000; constexpr char FILE_SEPARATOR_CHAR = '/'; +// 分片打包常量 +const uint64_t DEFAULT_SLICE_SIZE = 100 * 1024 * 1024; // 分片文件大小为100M +const uint32_t MAX_FILE_COUNT = 6000; // 单个tar包最多包含6000个文件 +const int FILE_AND_MANIFEST_FD_COUNT = 2; // 每组文件和简报数量统计 + constexpr int DEFAULT_VFS_CACHE_PRESSURE = 100; // 默认内存回收参数 constexpr int BACKUP_VFS_CACHE_PRESSURE = 10000; // 备份过程修改参数 @@ -76,9 +83,19 @@ constexpr int MAX_FD_SEND_RATE = 800; // 允许应用申请的最大FD数量 constexpr int MIN_FD_SEND_RATE = 0; // 允许应用申请的最小FD数量 constexpr int DEFAULT_FD_SEND_RATE = 60; // 框架默认的FD数量 constexpr int32_t PARAM_STARING_MAX_MEMORY = 2 * 1024 * 1024; +constexpr uint32_t H2MS = 60 * 60 * 1000; +constexpr uint32_t MAX_UPDATE_TIMER = 4 * H2MS; +constexpr uint32_t DEFAULT_TIMEOUT = 15 * 60 * 1000; +constexpr uint32_t TIMEOUT_INVALID = UINT32_MAX; + +constexpr int CALL_APP_ON_PROCESS_TIME_INTERVAL = 5; // 框架每隔5s去调用应用的onProcess +constexpr int APP_ON_PROCESS_MAX_TIMEOUT = 1000; // 应用的onProcess接口最大超时时间为1秒 +constexpr int FIRST_CALL_APP_ON_PROCESS_MAX_TIMEOUT = 15000; // 首次调用应用的onProcess接口最大超时时间为15秒 +constexpr int APP_ON_PROCESS_TIMEOUT_MAX_COUNT = 3; // 应用的onProcess接口超时的上限次数 // backup.para内配置项的名称,该配置项值为true时可在不更新hap包的情况下,可以读取包管理元数据配置文件的内容 static inline std::string BACKUP_DEBUG_OVERRIDE_EXTENSION_CONFIG_KEY = "backup.debug.overrideExtensionConfig"; +static const bool BACKUP_DEBUG_OVERRIDE_EXTENSION_CONFIG_DEFAULT_VALUE = false; // backup.para内配置项的名称,该配置项AccountConfig为true时存在时,可以按照配置的AccountNumber备份恢复 static inline std::string BACKUP_DEBUG_OVERRIDE_ACCOUNT_CONFIG_KEY = "backup.debug.overrideAccountConfig"; @@ -94,9 +111,11 @@ static const std::string BACKUP_EXCLUDE = "EXCLUDES"; // backup.para内配置项的名称,该配置项为true时备份恢复支持Release接口调用 static inline std::string BACKUP_OVERRIDE_BACKUP_SA_RELEASE_KEY = "backup.overrideBackupSARelease"; +static const bool BACKUP_DEBUG_OVERRIDE_BACKUP_SA_RELEASE_DEFAULT_VALUE = true; // backup.para内配置项的名称,该配置项为true时备份恢复支持增量恢复 static inline std::string BACKUP_OVERRIDE_INCREMENTAL_KEY = "backup.overrideIncrementalRestore"; +static const bool BACKUP_DEBUG_OVERRIDE_INCREMENTAL_DEFAULT_VALUE = true; // 应用备份数据暂存路径 static inline std::string_view SA_BUNDLE_BACKUP_BACKUP = "/backup/"; @@ -105,6 +124,8 @@ static inline std::string_view SA_BUNDLE_BACKUP_TMP_DIR = "/tmp/"; static inline std::string_view BACKUP_TOOL_RECEIVE_DIR = "/data/backup/received/"; static inline std::string_view PATH_BUNDLE_BACKUP_HOME_EL1 = "/data/storage/el1/base/.backup"; static inline std::string_view PATH_BUNDLE_BACKUP_HOME = "/data/storage/el2/base/.backup"; +static inline std::string_view PATH_FILEMANAGE_BACKUP_HOME = "/storage/Users/currentUser/.backup"; +static inline std::string_view PATH_MEDIALDATA_BACKUP_HOME = "/storage/media/local/files/.backup"; static inline std::string_view BACKUP_TOOL_LINK_DIR = "/data/backup"; static inline std::string_view BACKUP_TOOL_INCREMENTAL_RECEIVE_DIR = "/data/backup/incrementalreceived/"; static inline std::string_view BACKUP_TOOL_MANIFEST = "/manifest"; @@ -112,6 +133,16 @@ static inline std::string_view BACKUP_TOOL_INCREMENTAL = "/incremental"; static inline std::string BACKUP_DIR_PRE = "/data/storage/"; static inline std::string CONTEXT_ELS[] = {"el1", "el2"}; static inline std::string BACKUP_DIR_END = "/base/.backup/"; +static inline std::string BUNDLE_BASE_DIR = "/data/storage/el2/base"; +static inline std::string PATH_PUBLIC_HOME = "/storage/Users/currentUser/"; +static inline std::string PATH_APP_DATA = "appdata"; + +// 文管bundleName +static inline std::string BUNDLE_FILE_MANAGER = "hmos.filemanager"; +// 文管bundleNameSize +constexpr size_t FM_LEN = 27; +// 媒体库数据bundleName +static inline std::string BUNDLE_MEDIAL_DATA = "com.ohos.medialibrary.medialibrarydata"; // SA Ext constexpr int BACKUP_DEFAULT_SA_ID = -1; constexpr int BACKUP_SA_RELOAD_MAX = 2; @@ -194,6 +225,17 @@ static inline std::string MANIFEST_FD = "manifestFd"; static inline std::string LAST_INCREMENTAL_TIME = "lastIncrementalTime"; static inline std::string PARAMETERS = "parameters"; static inline std::string PRIORITY = "priority"; + +// unicast +const std::string UNICAST_TYPE = "unicast"; + +// 雷达打点引用到的常量 +constexpr int32_t MS_1000 = 1000; +constexpr int32_t MAX_TIME_COST = 900000; +constexpr int32_t MAX_INEXCLUDE_SIZE = 25; +constexpr uint8_t INDEX = 3; +static inline std::string FILE_BACKUP_RESTORE_EVENTS = "FILE_BACKUP_RESTORE_EVENTS"; +static inline std::string FILE_BACKUP_RESTORE_STATISTIC = "FILE_BACKUP_RESTORE_STATISTIC"; } // namespace OHOS::FileManagement::Backup::BConstants #endif // OHOS_FILEMGMT_BACKUP_B_CONSTANTS_H diff --git a/utils/include/b_sa/b_sa_utils.h b/utils/include/b_sa/b_sa_utils.h index 1548fed1e68e7450da4138c4eb273a70e8e1eb21..b8d3edf4cb048d937f4a5b73fd27ad6ce7fcea33 100644 --- a/utils/include/b_sa/b_sa_utils.h +++ b/utils/include/b_sa/b_sa_utils.h @@ -21,6 +21,9 @@ namespace OHOS::FileManagement::Backup { class SAUtils { public: static bool IsSABundleName(std::string bundleName); + static bool CheckBackupPermission(); + static bool CheckPermission(const std::string &permission); + static bool IsSystemApp(); }; -} // namespace OHOS::FileManagement::Backup::BEncryption +} // namespace OHOS::FileManagement::Backup::SAUtils #endif // OHOS_FILEMGMT_BACKUP_B_SA_H \ No newline at end of file diff --git a/utils/include/b_utils/b_time.h b/utils/include/b_utils/b_time.h new file mode 100644 index 0000000000000000000000000000000000000000..840e5e5b7254686b3a850069f91692e5041d4611 --- /dev/null +++ b/utils/include/b_utils/b_time.h @@ -0,0 +1,29 @@ +/* + * Copyright (c) 2024 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef OHOS_FILEMGMT_BACKUP_B_TIME_H +#define OHOS_FILEMGMT_BACKUP_B_TIME_H +#include + +namespace OHOS::FileManagement::Backup { +class TimeUtils { +public: + static int64_t GetTimeS(); + static int64_t GetTimeMS(); + static int64_t GetTimeUS(); + static std::string GetCurrentTime(); +}; +} // namespace OHOS::FileManagement::TimeUtils +#endif // OHOS_FILEMGMT_BACKUP_B_TIME_H \ No newline at end of file diff --git a/utils/src/b_error/b_error.cpp b/utils/src/b_error/b_error.cpp index d99d3e62e83b2a882b9cf10ca0a3de5a7374cb64..7026b6a9e560e2416ae28ce4de74e7b41fd80ad2 100644 --- a/utils/src/b_error/b_error.cpp +++ b/utils/src/b_error/b_error.cpp @@ -52,6 +52,7 @@ string BError::WrapMessageWithExtraInfos(const char *fileName, (void)HILOG_IMPL(LOG_CORE, LOG_DEBUG, LOG_DOMAIN, LOG_TAG, "%{public}s", res.c_str()); return res; } + int BError::GetCode() const { int code = static_cast(GetRawCode()); @@ -73,4 +74,23 @@ int BError::GetCodeByErrno(int32_t errnoSys) } return BackupErrorCode::E_UKERR; } + +ErrCode BError::GetBackupCodeByErrno(ErrCode err) +{ + if (err == 0) { + return 0; + } + if (errCodeTable_.find(err) != errCodeTable_.end()) { + return errCodeTable_.at(err); + } + return BackupErrorCode::E_UKERR; +} + +string BError::GetBackupMsgByErrno(ErrCode err) +{ + if (backupErrorMsgTable_.find(err) != backupErrorMsgTable_.end()) { + return backupErrorMsgTable_.at(err); + } + return backupErrorMsgTable_.at(BackupErrorCode::E_UKERR); +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/utils/src/b_filesystem/b_dir.cpp b/utils/src/b_filesystem/b_dir.cpp index f8c70da1be67c17dba8c26707d7512478710d751..88f5c4e6ac1d6cd1a66673c9c2ece54c658f1cc6 100644 --- a/utils/src/b_filesystem/b_dir.cpp +++ b/utils/src/b_filesystem/b_dir.cpp @@ -19,6 +19,7 @@ #include #include #include +#include #include #include #include @@ -27,6 +28,7 @@ #include #include "b_error/b_error.h" +#include "b_filesystem/b_file_hash.h" #include "b_resources/b_constants.h" #include "directory_ex.h" #include "errors.h" @@ -35,11 +37,14 @@ namespace OHOS::FileManagement::Backup { using namespace std; const int32_t PATH_MAX_LEN = 4096; +const std::string APP_DATA_DIR = BConstants::PATH_PUBLIC_HOME + + BConstants::PATH_APP_DATA + BConstants::FILE_SEPARATOR_CHAR; static bool IsEmptyDirectory(const string &path) { DIR *dir = opendir(path.c_str()); if (dir == nullptr) { + HILOGE("Opendir failed, errno:%{public}d", errno); return false; } bool isEmpty = true; @@ -54,19 +59,20 @@ static bool IsEmptyDirectory(const string &path) return isEmpty; } -static tuple, vector> GetFile(const string &path, off_t size = -1) +static tuple, map> GetFile(const string &path, off_t size = -1) { map files; - vector smallFiles; + map smallFiles; struct stat sta = {}; if (stat(path.data(), &sta) == -1) { - return {BError(errno).GetCode(), files, smallFiles}; + HILOGE("File not exist, errno:%{public}d, fileName:%{private}s.", errno, path.c_str()); + return {BError(BError::Codes::OK).GetCode(), files, smallFiles}; } if (path == "/") { return {BError(BError::Codes::OK).GetCode(), files, smallFiles}; } if (sta.st_size <= size) { - smallFiles.emplace_back(path); + smallFiles.insert(make_pair(path, sta.st_size)); } else { files.try_emplace(path, sta); } @@ -77,26 +83,26 @@ static uint32_t CheckOverLongPath(const string &path) { uint32_t len = path.length(); if (len >= PATH_MAX_LEN) { - size_t found = path.find_last_of('/'); + size_t found = path.find_last_of(BConstants::FILE_SEPARATOR_CHAR); string sub = path.substr(found + 1); HILOGE("Path over long, length:%{public}d, fileName:%{public}s.", len, sub.c_str()); } return len; } -static tuple, vector> GetDirFilesDetail(const string &path, - bool recursion, - off_t size = -1) +static tuple, map> GetDirFilesDetail(const string &path, + bool recursion, + off_t size = -1) { map files; - vector smallFiles; + map smallFiles; if (IsEmptyDirectory(path)) { string newPath = path; - if (path.at(path.size()-1) != '/') { - newPath += '/'; + if (path.at(path.size()-1) != BConstants::FILE_SEPARATOR_CHAR) { + newPath += BConstants::FILE_SEPARATOR_CHAR; } - smallFiles.emplace_back(newPath); + smallFiles.insert(make_pair(newPath, 0)); return {ERR_OK, files, smallFiles}; } @@ -110,32 +116,34 @@ static tuple, vector> GetDirFilesDetai // current dir OR parent dir if ((strcmp(ptr->d_name, ".") == 0) || (strcmp(ptr->d_name, "..") == 0)) { continue; - } else if (ptr->d_type == DT_DIR) { - if (!recursion) { - continue; - } - auto [errCode, subFiles, subSmallFiles] = - GetDirFilesDetail(IncludeTrailingPathDelimiter(path) + string(ptr->d_name), recursion, size); - if (errCode != 0) { - return {errCode, files, smallFiles}; - } - files.merge(subFiles); - smallFiles.insert(smallFiles.end(), subSmallFiles.begin(), subSmallFiles.end()); - } else if (ptr->d_type == DT_LNK) { - continue; - } else { + } else if (ptr->d_type == DT_REG) { struct stat sta = {}; string fileName = IncludeTrailingPathDelimiter(path) + string(ptr->d_name); if (CheckOverLongPath(fileName) >= PATH_MAX_LEN || stat(fileName.data(), &sta) == -1) { continue; } if (sta.st_size <= size) { - smallFiles.emplace_back(fileName); + smallFiles.insert(make_pair(fileName, sta.st_size)); continue; } files.try_emplace(fileName, sta); + continue; + } else if (ptr->d_type != DT_DIR) { + HILOGE("Not support file type"); + continue; + } + // DT_DIR type + if (!recursion) { + continue; } + auto [errCode, subFiles, subSmallFiles] = + GetDirFilesDetail(IncludeTrailingPathDelimiter(path) + string(ptr->d_name), recursion, size); + if (errCode != 0) { + return {errCode, files, smallFiles}; + } + files.merge(subFiles); + smallFiles.insert(subSmallFiles.begin(), subSmallFiles.end()); } return {ERR_OK, files, smallFiles}; } @@ -164,6 +172,57 @@ tuple> BDir::GetDirFiles(const string &path) return {ERR_OK, files}; } +static std::set GetSubDir(const std::string &path) +{ + if (path.empty()) { + return {}; + } + std::set result; + unique_ptr> dir = {opendir(path.c_str()), closedir}; + if (!dir) { + HILOGE("Invalid directory path: %{private}s", path.c_str()); + return {}; + } + + struct dirent *ptr = nullptr; + while (!!(ptr = readdir(dir.get()))) { + // current dir OR parent dir + if ((strcmp(ptr->d_name, ".") == 0) || (strcmp(ptr->d_name, "..") == 0)) { + continue; + } else if (ptr->d_type == DT_DIR) { + std::string tmpPath = IncludeTrailingPathDelimiter(path) + + string(ptr->d_name) + BConstants::FILE_SEPARATOR_CHAR; + if (tmpPath == APP_DATA_DIR) { + HILOGI("Filter appdata successfully"); + continue; + } + result.emplace(tmpPath); + } else { + result.emplace(IncludeTrailingPathDelimiter(path) + string(ptr->d_name)); + } + } + return result; +} + +static void RmForceExcludePath(set &expandPath) +{ + set addPaths; + for (auto it = expandPath.begin(); it != expandPath.end();) { + if (*it == BConstants::PATH_PUBLIC_HOME) { + addPaths = GetSubDir(*it); + } + if ((*it).find(APP_DATA_DIR) == 0) { + it = expandPath.erase(it); + continue; + } + ++it; + } + if (!addPaths.empty()) { + expandPath.erase(BConstants::PATH_PUBLIC_HOME); + expandPath.merge(addPaths); + } +} + static set ExpandPathWildcard(const vector &vec, bool onlyPath) { unique_ptr> gl {new glob_t, [](glob_t *ptr) { globfree(ptr); }}; @@ -179,12 +238,17 @@ static set ExpandPathWildcard(const vector &vec, bool onlyPath) set expandPath, filteredPath; for (size_t i = 0; i < gl->gl_pathc; ++i) { - expandPath.emplace(gl->gl_pathv[i]); + std::string tmpPath = gl->gl_pathv[i]; + auto pos = tmpPath.find(BConstants::FILE_SEPARATOR_CHAR); + if (pos != 0 && pos != std::string::npos) { + tmpPath = BConstants::FILE_SEPARATOR_CHAR + tmpPath; + } + expandPath.emplace(tmpPath); } - + RmForceExcludePath(expandPath); for (auto it = expandPath.begin(); it != expandPath.end(); ++it) { filteredPath.insert(*it); - if (onlyPath && *it->rbegin() != '/') { + if (onlyPath && *it->rbegin() != BConstants::FILE_SEPARATOR_CHAR) { continue; } auto jt = it; @@ -197,20 +261,20 @@ static set ExpandPathWildcard(const vector &vec, bool onlyPath) return filteredPath; } -tuple, vector> BDir::GetBigFiles(const vector &includes, - const vector &excludes) +tuple, map> BDir::GetBigFiles(const vector &includes, + const vector &excludes) { - set inc = ExpandPathWildcard(includes, false); + set inc = ExpandPathWildcard(includes, true); map incFiles; - vector incSmallFiles; + map incSmallFiles; for (const auto &item : inc) { + HILOGW("GetBigFiles, path = %{public}s", item.c_str()); auto [errCode, files, smallFiles] = GetDirFilesDetail(item, true, BConstants::BIG_FILE_BOUNDARY); if (errCode == 0) { - int32_t num = static_cast(files.size()); incFiles.merge(move(files)); - HILOGI("big files: %{public}d; small files: %{public}d", num, static_cast(smallFiles.size())); - incSmallFiles.insert(incSmallFiles.end(), smallFiles.begin(), smallFiles.end()); + HILOGW("big files: %{public}zu; small files: %{public}zu", files.size(), smallFiles.size()); + incSmallFiles.insert(smallFiles.begin(), smallFiles.end()); } } @@ -223,7 +287,7 @@ tuple, vector> BDir::GetBigFiles(const continue; } string excludeItem = item; - if (excludeItem.at(item.size() - 1) == '/') { + if (excludeItem.at(item.size() - 1) == BConstants::FILE_SEPARATOR_CHAR) { excludeItem += "*"; } if (fnmatch(excludeItem.data(), str.data(), FNM_LEADING_DIR) == 0) { @@ -233,10 +297,10 @@ tuple, vector> BDir::GetBigFiles(const return false; }; - vector resSmallFiles; + map resSmallFiles; for (const auto &item : incSmallFiles) { - if (!isMatch(excludes, item)) { - resSmallFiles.emplace_back(item); + if (!isMatch(excludes, item.first)) { + resSmallFiles.insert(make_pair(item.first, item.second)); } } @@ -246,11 +310,186 @@ tuple, vector> BDir::GetBigFiles(const bigFiles[item.first] = item.second; } } - HILOGI("total number of big files is %{public}d", static_cast(bigFiles.size())); - HILOGI("total number of small files is %{public}d", static_cast(resSmallFiles.size())); + HILOGW("total number of big files is %{public}zu", bigFiles.size()); + HILOGW("total number of small files is %{public}zu", resSmallFiles.size()); return {ERR_OK, move(bigFiles), move(resSmallFiles)}; } +void BDir::GetUser0FileStat(vector bigFile, + vector smallFile, + vector &allFiles, + vector &smallFiles, + vector &bigFiles) +{ + for (const auto &item : smallFile) { + struct ReportFileInfo storageFiles; + storageFiles.filePath = item; + if (filesystem::is_directory(item)) { + storageFiles.isDir = 1; + storageFiles.userTar = 0; + } else { + storageFiles.isDir = 0; + auto [res, fileHash] = BackupFileHash::HashWithSHA256(item); + if (fileHash.empty()) { + continue; + } + storageFiles.hash = fileHash; + storageFiles.userTar = 1; + } + struct stat sta = {}; + if (stat(item.c_str(), &sta) != 0) { + throw BError(BError::Codes::EXT_INVAL_ARG, "Get file stat failed"); + } + storageFiles.size = sta.st_size; + storageFiles.mode = to_string(static_cast(sta.st_mode)); + int64_t lastUpdateTime = static_cast(sta.st_mtime); + storageFiles.mtime = lastUpdateTime; + allFiles.push_back(storageFiles); + smallFiles.push_back(storageFiles); + } + for (const auto &item : bigFile) { + struct ReportFileInfo storageFiles; + storageFiles.filePath = item; + auto [res, fileHash] = BackupFileHash::HashWithSHA256(item); + if (fileHash.empty()) { + continue; + } + storageFiles.hash = fileHash; + struct stat sta = {}; + if (stat(item.c_str(), &sta) != 0) { + throw BError(BError::Codes::EXT_INVAL_ARG, "Get file stat failed"); + } + storageFiles.size = sta.st_size; + storageFiles.mode = to_string(static_cast(sta.st_mode)); + int64_t lastUpdateTime = static_cast(sta.st_mtime); + storageFiles.mtime = lastUpdateTime; + storageFiles.userTar = 1; + allFiles.push_back(storageFiles); + bigFiles.push_back(storageFiles); + } + HILOGI("get FileStat end, bigfiles = %{public}zu, smallFiles = %{public}zu, allFiles = %{public}zu,", + bigFiles.size(), smallFiles.size(), allFiles.size()); +} + +static tuple, vector> IsNotPath(const string &path, vector &bigFiles, + vector &smallFiles, off_t size) +{ + struct stat sta = {}; + if (CheckOverLongPath(path) >= PATH_MAX_LEN || stat(path.data(), &sta) == -1) { + return {}; + } + if (sta.st_size <= size) { + smallFiles.push_back(path); + HILOGI("bigfiles = %{public}zu, smallfiles = %{public}zu", bigFiles.size(), smallFiles.size()); + return {bigFiles, smallFiles}; + } + bigFiles.push_back(path); + HILOGI("bigfiles = %{public}zu, smallfiles = %{public}zu", bigFiles.size(), smallFiles.size()); + return {bigFiles, smallFiles}; +} + +static tuple, vector> GetUser0DirFilesDetail(const string &path, off_t size = -1) +{ + vector bigFiles; + vector smallFiles; + if (IsEmptyDirectory(path)) { + string newPath = path; + if (path.at(path.size()-1) != BConstants::FILE_SEPARATOR_CHAR) { + newPath += BConstants::FILE_SEPARATOR_CHAR; + } + smallFiles.push_back(newPath); + return {bigFiles, smallFiles}; + } + if (filesystem::is_regular_file(path)) { + return IsNotPath(path, bigFiles, smallFiles, size); + } + unique_ptr> dir = {opendir(path.c_str()), closedir}; + if (!dir) { + HILOGE("Invalid directory path: %{private}s", path.c_str()); + return {}; + } + struct dirent *ptr = nullptr; + while (!!(ptr = readdir(dir.get()))) { + // current dir OR parent dir + if ((strcmp(ptr->d_name, ".") == 0) || (strcmp(ptr->d_name, "..") == 0)) { + continue; + } else if (ptr->d_type == DT_REG) { + struct stat sta = {}; + string fileName = IncludeTrailingPathDelimiter(path) + string(ptr->d_name); + if (CheckOverLongPath(fileName) >= PATH_MAX_LEN || stat(fileName.data(), &sta) == -1) { + continue; + } + if (sta.st_size <= size) { + smallFiles.push_back(fileName); + continue; + } + + bigFiles.push_back(fileName); + continue; + } else if (ptr->d_type != DT_DIR) { + HILOGE("Not support file type"); + continue; + } + // DT_DIR type + auto [subBigFiles, subSmallFiles] = + GetUser0DirFilesDetail(IncludeTrailingPathDelimiter(path) + string(ptr->d_name), size); + bigFiles.insert(bigFiles.end(), subBigFiles.begin(), subBigFiles.end()); + smallFiles.insert(smallFiles.end(), subSmallFiles.begin(), subSmallFiles.end()); + } + HILOGI("bigfiles = %{public}zu, smallfiles = %{public}zu", bigFiles.size(), smallFiles.size()); + return {bigFiles, smallFiles}; +} + +tuple, vector> BDir::GetBackupList(const vector &includes, + const vector &excludes) +{ + HILOGI("start get bigfiles and smallfiles"); + set inc = ExpandPathWildcard(includes, true); + vector bigFiles; + vector smallFiles; + for (const auto &item : inc) { + auto [bigFile, smallFile] = GetUser0DirFilesDetail(item, BConstants::BIG_FILE_BOUNDARY); + bigFiles.insert(bigFiles.end(), bigFile.begin(), bigFile.end()); + smallFiles.insert(smallFiles.end(), smallFile.begin(), smallFile.end()); + } + HILOGI("end bigfiles = %{public}zu, smallfiles = %{public}zu", bigFiles.size(), smallFiles.size()); + auto isMatch = [](const vector &s, const string &str) -> bool { + if (str.empty()) { + return false; + } + for (const string &item : s) { + if (item.empty()) { + continue; + } + string excludeItem = item; + if (excludeItem.at(item.size() - 1) == BConstants::FILE_SEPARATOR_CHAR) { + excludeItem += "*"; + } + if (fnmatch(excludeItem.data(), str.data(), FNM_LEADING_DIR) == 0) { + return true; + } + } + return false; + }; + + for (auto item = bigFiles.begin(); item != bigFiles.end();) { + if (isMatch(excludes, *item)) { + item = bigFiles.erase(item); + } else { + ++item; + } + } + for (auto item = smallFiles.begin(); item != smallFiles.end();) { + if (isMatch(excludes, *item)) { + item = smallFiles.erase(item); + } else { + ++item; + } + } + HILOGI("End compare bigfiles = %{public}zu, smallfiles = %{public}zu", bigFiles.size(), smallFiles.size()); + return {bigFiles, smallFiles}; +} + vector BDir::GetDirs(const vector &paths) { vector wildcardPath(paths.begin(), paths.end()); @@ -259,4 +498,11 @@ vector BDir::GetDirs(const vector &paths) return dirs; } +bool BDir::CheckFilePathInvalid(const std::string &filePath) +{ + if (filePath.find("../") != std::string::npos) { + return true; + } + return false; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/utils/src/b_filesystem/b_file.cpp b/utils/src/b_filesystem/b_file.cpp index f5828df41e84daca1131cc0b3cf2c4b9487a225a..27b91007816ab6efdd72c8b1000bfbd5c4d37eb1 100644 --- a/utils/src/b_filesystem/b_file.cpp +++ b/utils/src/b_filesystem/b_file.cpp @@ -186,10 +186,19 @@ bool BFile::MoveFile(const string &from, const string &to) throw BError(errno); } newPath.append("/").append(basename(name.get())); - if (rename(oldPath.c_str(), newPath.c_str())) { - HILOGE("failed to rename path, oldPath:%{public}s ,newPath: %{public}s", - GetAnonyPath(oldPath).c_str(), GetAnonyPath(newPath).c_str()); - throw BError(errno); + if (rename(oldPath.c_str(), newPath.c_str()) != 0) { + HILOGI("rename err,try copy errno: %{public}d", errno); + UniqueFd fdFrom(open(oldPath.data(), O_RDONLY)); + if (fdFrom == -1) { // -1: fd error code + HILOGE("failed to open the file %{public}s", GetAnonyPath(from).c_str()); + throw BError(errno); + } + UniqueFd fdTo(open(newPath.data(), O_RDWR | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR)); + if (fdTo == -1) { // -1: fd error code + HILOGE("failed to open the file %{public}s", GetAnonyPath(to).c_str()); + throw BError(errno); + } + SendFile(fdTo, fdFrom); } return true; } catch (const BError &e) { @@ -201,4 +210,12 @@ bool BFile::MoveFile(const string &from, const string &to) } return false; } + +bool BFile::EndsWith(const string &str, const string &suffix) +{ + if (suffix.length() > str.length()) { + return false; + } + return (str.rfind(suffix) == (str.length() - suffix.length())); +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/utils/src/b_json/b_json_clear_data_config.cpp b/utils/src/b_json/b_json_clear_data_config.cpp new file mode 100644 index 0000000000000000000000000000000000000000..9d823170f0fb16635e64b7a73e6f21710a50fb1a --- /dev/null +++ b/utils/src/b_json/b_json_clear_data_config.cpp @@ -0,0 +1,356 @@ +/* + * Copyright (c) 2024 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "b_json/b_json_clear_data_config.h" + +#include +#include +#include +#include +#include "unique_fd.h" +#include "filemgmt_libhilog.h" + +#include "cJSON.h" + +namespace OHOS::FileManagement::Backup { +using namespace std; + +namespace { + const string PATH_BUNDLE_BACKUP_HOME = "/data/service/el2/100/backup/"; + const string CONFIG_NAME = "ClearDataConfig.json"; +} + +BJsonClearDataConfig::BJsonClearDataConfig() +{ + string filePath = PATH_BUNDLE_BACKUP_HOME + CONFIG_NAME; + if (access(filePath.c_str(), F_OK) == 0) { + HILOGI("file exist filePath:%{public}s", filePath.c_str()); + return; + } + HILOGI("Failed to access filePath :%{public}s", filePath.c_str()); + UniqueFd fd(open(filePath.c_str(), O_RDWR | O_CREAT, S_IRUSR | S_IWUSR)); + if (fd < 0) { + HILOGE("Failed to creat filePath :%{public}s", filePath.c_str()); + return; + } + cJSON *jsonObjectDis = cJSON_CreateObject(); + if (jsonObjectDis == nullptr) { + HILOGE("Creat json failed"); + return; + } + cJSON *jsonArray = cJSON_CreateArray(); + if (jsonArray == nullptr) { + HILOGE("Creat json failed"); + cJSON_Delete(jsonObjectDis); + return; + } + cJSON_AddItemToObject(jsonObjectDis, "ClearDataConfigFile", jsonArray); + + char *newStr = cJSON_Print(jsonObjectDis); + if (newStr == nullptr) { + HILOGE("cJSON_Print json failed"); + cJSON_Delete(jsonObjectDis); + return; + } + ofstream outFile(filePath); + if (!outFile.is_open()) { + HILOGE("open json failed"); + cJSON_free(newStr); + cJSON_Delete(jsonObjectDis); + return; + } + outFile << newStr; + outFile.close(); + cJSON_free(newStr); + cJSON_Delete(jsonObjectDis); + HILOGI("Creat filePath ok :%{public}s", filePath.c_str()); +} + +bool BJsonClearDataConfig::HasClearBundleRecord() +{ + lock_guard autoLock(fileMutex_); + string filePath = PATH_BUNDLE_BACKUP_HOME + CONFIG_NAME; + ifstream inFile(filePath); + if (!inFile.is_open()) { + HILOGE("open json failed"); + return false; + } + + string jsonString((istreambuf_iterator(inFile)), istreambuf_iterator()); + inFile.close(); + + cJSON *jsonObjectDis = cJSON_Parse(jsonString.c_str()); + if (jsonObjectDis == nullptr) { + HILOGE("parse json failed"); + return false; + } + + cJSON *configArray = cJSON_GetObjectItem(jsonObjectDis, "ClearDataConfigFile"); + if (configArray == nullptr) { + HILOGE("parse json failed"); + cJSON_Delete(jsonObjectDis); + return false; + } + + int recordSize = cJSON_GetArraySize(configArray); + cJSON_Delete(jsonObjectDis); + return recordSize > 0; +} + +bool BJsonClearDataConfig::FindClearBundleRecord(const string& bundleName) +{ + lock_guard autoLock(fileMutex_); + string filePath = PATH_BUNDLE_BACKUP_HOME + CONFIG_NAME; + ifstream inFile(filePath); + if (!inFile.is_open()) { + HILOGE("open json failed"); + return false; + } + + string jsonString((istreambuf_iterator(inFile)), istreambuf_iterator()); + inFile.close(); + + cJSON *jsonObjectDis = cJSON_Parse(jsonString.c_str()); + if (jsonObjectDis == nullptr) { + HILOGE("parse json failed"); + return false; + } + + cJSON *configArray = cJSON_GetObjectItem(jsonObjectDis, "ClearDataConfigFile"); + if (configArray == nullptr) { + HILOGE("parse json failed"); + cJSON_Delete(jsonObjectDis); + return false; + } + bool ifBundlename = false; + for (int i = 0; i < cJSON_GetArraySize(configArray); ++i) { + cJSON *item = cJSON_GetArrayItem(configArray, i); + if (item != nullptr && cJSON_GetObjectItem(item, "bundleName") != nullptr && + cJSON_GetObjectItem(item, "bundleName")->type == cJSON_String && + cJSON_GetObjectItem(item, "bundleName")->valuestring == bundleName) { + ifBundlename = true; + } + } + + cJSON_Delete(jsonObjectDis); + return ifBundlename; +} + +bool BJsonClearDataConfig::InsertClearBundleRecord(const string& bundleName) +{ + lock_guard autoLock(fileMutex_); + string filePath = PATH_BUNDLE_BACKUP_HOME + CONFIG_NAME; + ifstream inFile(filePath); + if (!inFile.is_open()) { + HILOGE("open json failed"); + return false; + } + + string jsonString((istreambuf_iterator(inFile)), istreambuf_iterator()); + inFile.close(); + + cJSON *jsonObjectDis = cJSON_Parse(jsonString.c_str()); + if (jsonObjectDis == nullptr) { + HILOGE("parse json failed"); + return false; + } + + cJSON *configArray = cJSON_GetObjectItem(jsonObjectDis, "ClearDataConfigFile"); + if (configArray == nullptr) { + HILOGE("parse json failed"); + cJSON_Delete(jsonObjectDis); + return false; + } + + for (int i = 0; i < cJSON_GetArraySize(configArray); ++i) { + cJSON *item = cJSON_GetArrayItem(configArray, i); + if (item != nullptr && cJSON_GetObjectItem(item, "bundleName") != nullptr && + cJSON_GetObjectItem(item, "bundleName")->type == cJSON_String && + cJSON_GetObjectItem(item, "bundleName")->valuestring == bundleName) { + HILOGI("record already exist, bundleName=%{public}s", bundleName.c_str()); + cJSON_Delete(jsonObjectDis); + return true; + } + } + + if (!WriteClearBundleRecord(bundleName)) { + HILOGE("InsertClearBundleRecord Failed"); + cJSON_Delete(jsonObjectDis); + return false; + } + + HILOGI("InsertClearBundleRecord Ok"); + cJSON_Delete(jsonObjectDis); + return true; +} + +bool BJsonClearDataConfig::DeleteClearBundleRecord(const string& bundleName) +{ + lock_guard autoLock(fileMutex_); + string filePath = PATH_BUNDLE_BACKUP_HOME + CONFIG_NAME; + ifstream input(filePath); + if (!input.is_open()) { + HILOGE("open json failed"); + return false; + } + + string jsonString((istreambuf_iterator(input)), istreambuf_iterator()); + input.close(); + + cJSON *jsonObjectDis = cJSON_Parse(jsonString.c_str()); + if (jsonObjectDis == nullptr) { + HILOGE("parse json failed"); + return false; + } + + cJSON *configArray = cJSON_GetObjectItem(jsonObjectDis, "ClearDataConfigFile"); + if (configArray == nullptr) { + cJSON_Delete(jsonObjectDis); + return false; + } + for (int i = 0; i < cJSON_GetArraySize(configArray); ++i) { + cJSON *item = cJSON_GetArrayItem(configArray, i); + if (item != nullptr && cJSON_GetObjectItem(item, "bundleName") != nullptr && + cJSON_GetObjectItem(item, "bundleName")->type == cJSON_String && + cJSON_GetObjectItem(item, "bundleName")->valuestring == bundleName) { + cJSON_DeleteItemFromArray(configArray, i); + break; + } + } + char *newStr = cJSON_Print(jsonObjectDis); + if (newStr == nullptr) { + HILOGE("cJSON_Print json failed"); + cJSON_Delete(jsonObjectDis); + return false; + } + ofstream output(filePath); + if (!output.is_open()) { + HILOGE("open json failed"); + cJSON_free(newStr); + cJSON_Delete(jsonObjectDis); + return false; + } + output << newStr; + output.close(); + + cJSON_free(newStr); + cJSON_Delete(jsonObjectDis); + return true; +} + +vector BJsonClearDataConfig::GetAllClearBundleRecords() +{ + lock_guard autoLock(fileMutex_); + string filePath = PATH_BUNDLE_BACKUP_HOME + CONFIG_NAME; + vector bundleNameList; + ifstream inFile(filePath); + if (!inFile.is_open()) { + HILOGE("open json failed"); + return {}; + } + string jsonString((istreambuf_iterator(inFile)), istreambuf_iterator()); + inFile.close(); + + cJSON *jsonObjectDis = cJSON_Parse(jsonString.c_str()); + if (jsonObjectDis == nullptr) { + HILOGE("parse json failed"); + return {}; + } + + cJSON *configArray = cJSON_GetObjectItem(jsonObjectDis, "ClearDataConfigFile"); + if (configArray == nullptr) { + HILOGE("parse json failed"); + cJSON_Delete(jsonObjectDis); + return {}; + } + for (int i = 0; i < cJSON_GetArraySize(configArray); ++i) { + cJSON *item = cJSON_GetArrayItem(configArray, i); + if (item != nullptr && cJSON_GetObjectItem(item, "bundleName") != nullptr && + cJSON_GetObjectItem(item, "bundleName")->type == cJSON_String) { + bundleNameList.push_back(cJSON_GetObjectItem(item, "bundleName")->valuestring); + } + } + cJSON_Delete(jsonObjectDis); + return bundleNameList; +} + +bool BJsonClearDataConfig::DeleteConfigFile() +{ + string filePath = PATH_BUNDLE_BACKUP_HOME + CONFIG_NAME; + if (access(filePath.c_str(), F_OK) != 0) { + HILOGE("File is not exist"); + return false; + } + if (remove(filePath.c_str()) != 0) { + HILOGE("Delete ClearDataConfigFile failed"); + return false; + } + HILOGI("All Restore Finished, Delete ClearDataConfigFile OK"); + return true; +} + +bool BJsonClearDataConfig::WriteClearBundleRecord(const string& bundleName) +{ + string filePath = PATH_BUNDLE_BACKUP_HOME + CONFIG_NAME; + ifstream inFile(filePath); + if (!inFile.is_open()) { + HILOGE("open json failed"); + return false; + } + string jsonString((istreambuf_iterator(inFile)), istreambuf_iterator()); + inFile.close(); + + cJSON *jsonObjectDis = cJSON_Parse(jsonString.c_str()); + if (jsonObjectDis == nullptr) { + HILOGE("parse json failed"); + return false; + } + + cJSON *configArray = cJSON_GetObjectItem(jsonObjectDis, "ClearDataConfigFile"); + if (configArray == nullptr) { + HILOGE("parse json failed"); + cJSON_Delete(jsonObjectDis); + return false; + } + cJSON *newItem = cJSON_CreateObject(); + if (configArray == nullptr || newItem == nullptr) { + HILOGE("parse json failed"); + cJSON_Delete(jsonObjectDis); + return false; + } + + cJSON_AddStringToObject(newItem, "bundleName", bundleName.c_str()); + cJSON_AddItemToArray(configArray, newItem); + char *newStr = cJSON_Print(jsonObjectDis); + if (newStr == nullptr) { + HILOGE("cJSON_Print json failed"); + cJSON_Delete(jsonObjectDis); + return false; + } + ofstream outFile(filePath); + if (!outFile.is_open()) { + HILOGE("open json failed"); + cJSON_free(newStr); + cJSON_Delete(jsonObjectDis); + return false; + } + outFile << newStr; + outFile.close(); + + cJSON_free(newStr); + cJSON_Delete(jsonObjectDis); + return true; +} +} // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/utils/src/b_json/b_json_entity_extension_config.cpp b/utils/src/b_json/b_json_entity_extension_config.cpp index 0d93a72fe89af3ab4d50bb3e2d4cbc5835bdd6ff..915ece4cabfc699b5d3f145ded71782f07d4fdb6 100644 --- a/utils/src/b_json/b_json_entity_extension_config.cpp +++ b/utils/src/b_json/b_json_entity_extension_config.cpp @@ -37,7 +37,7 @@ vector BJsonEntityExtensionConfig::GetIncludes() const return {BConstants::PATHES_TO_BACKUP.begin(), BConstants::PATHES_TO_BACKUP.end()}; } if (!obj_.isMember("includes")) { - HILOGD("'includes' field not found"); + HILOGE("'includes' field not found"); return {BConstants::PATHES_TO_BACKUP.begin(), BConstants::PATHES_TO_BACKUP.end()}; } if (!obj_["includes"].isArray()) { diff --git a/utils/src/b_json/b_json_service_disposal_config.cpp b/utils/src/b_json/b_json_service_disposal_config.cpp index ca94e2112e32f880c6ddf073061c50918a7e043f..22dd89a43db28bb7b1ce73c5b104472fa6dc788d 100644 --- a/utils/src/b_json/b_json_service_disposal_config.cpp +++ b/utils/src/b_json/b_json_service_disposal_config.cpp @@ -34,24 +34,24 @@ BJsonDisposalConfig::BJsonDisposalConfig() string filePath = PATH_BUNDLE_BACKUP_HOME + CONFIG_NAME; if (access(filePath.c_str(), F_OK) == 0) { HILOGI("file exist filePath:%{public}s", filePath.c_str()); - return ; + return; } HILOGI("Failed to access filePath :%{public}s", filePath.c_str()); UniqueFd fd(open(filePath.c_str(), O_RDWR | O_CREAT, S_IRUSR | S_IWUSR)); if (fd < 0) { HILOGE("Failed to creat filePath :%{public}s", filePath.c_str()); - return ; + return; } cJSON *jsonObjectDis = cJSON_CreateObject(); if (jsonObjectDis == nullptr) { HILOGE("Creat json failed"); - return ; + return; } cJSON *jsonArray = cJSON_CreateArray(); if (jsonArray == nullptr) { HILOGE("Creat json failed"); cJSON_Delete(jsonObjectDis); - return ; + return; } cJSON_AddItemToObject(jsonObjectDis, "DispoasalConfigFile", jsonArray); @@ -59,14 +59,14 @@ BJsonDisposalConfig::BJsonDisposalConfig() if (newStr == nullptr) { HILOGE("cJSON_Print json failed"); cJSON_Delete(jsonObjectDis); - return ; + return; } ofstream outFile(filePath); if (!outFile.is_open()) { HILOGE("open json failed"); free(newStr); cJSON_Delete(jsonObjectDis); - return ; + return; } outFile << newStr; outFile.close(); @@ -93,13 +93,13 @@ bool BJsonDisposalConfig::AppendIntoDisposalConfigFile(const string& bundleName) } cJSON *configArray = cJSON_GetObjectItem(jsonObjectDis, "DispoasalConfigFile"); - if (configArray == nullptr) { + if (configArray == nullptr || !cJSON_IsArray(configArray)) { HILOGE("parse json failed"); cJSON_Delete(jsonObjectDis); return false; } cJSON *newItem = cJSON_CreateObject(); - if (configArray == nullptr || newItem == nullptr) { + if (newItem == nullptr) { HILOGE("parse json failed"); cJSON_Delete(jsonObjectDis); return false; @@ -148,7 +148,7 @@ bool BJsonDisposalConfig::DeleteFromDisposalConfigFile(const string& bundleName) } cJSON *configArray = cJSON_GetObjectItem(jsonObjectDis, "DispoasalConfigFile"); - if (configArray == nullptr) { + if (configArray == nullptr || !cJSON_IsArray(configArray)) { cJSON_Delete(jsonObjectDis); return false; } @@ -202,7 +202,7 @@ bool BJsonDisposalConfig::IfBundleNameInDisposalConfigFile(const string& bundleN } cJSON *configArray = cJSON_GetObjectItem(jsonObjectDis, "DispoasalConfigFile"); - if (configArray == nullptr) { + if (configArray == nullptr || !cJSON_IsArray(configArray)) { HILOGE("parse json failed"); cJSON_Delete(jsonObjectDis); return false; @@ -246,7 +246,7 @@ vector BJsonDisposalConfig::GetBundleNameFromConfigFile() } cJSON *configArray = cJSON_GetObjectItem(jsonObjectDis, "DispoasalConfigFile"); - if (configArray == nullptr) { + if (configArray == nullptr || !cJSON_IsArray(configArray)) { HILOGE("parse json failed"); cJSON_Delete(jsonObjectDis); return {}; diff --git a/utils/src/b_json/b_report_entity.cpp b/utils/src/b_json/b_report_entity.cpp index 7acdd932a631921c8f1eafb71272caae7d6c5b5b..fb5d342c1838aa648f3d5a8af73e7ffcdc84cf3a 100644 --- a/utils/src/b_json/b_report_entity.cpp +++ b/utils/src/b_json/b_report_entity.cpp @@ -257,7 +257,8 @@ void BReportEntity::CheckAndUpdateIfReportLineEncoded(std::string &path) } unordered_map infos = GetReportInfos(); - if (infos.size() == 1) { + constexpr int BIG_FILE_REPORT_INFO_NUM = 1; + if (infos.size() == BIG_FILE_REPORT_INFO_NUM) { auto info = infos.begin(); path = info->first; } else { diff --git a/utils/src/b_jsonutil/b_jsonutil.cpp b/utils/src/b_jsonutil/b_jsonutil.cpp index 578be2fd88434d25ac0cc544aed426a17ade112f..c420dc13668233a51a4e7e08196d3c36f5e9fab5 100644 --- a/utils/src/b_jsonutil/b_jsonutil.cpp +++ b/utils/src/b_jsonutil/b_jsonutil.cpp @@ -16,10 +16,15 @@ #include "b_jsonutil/b_jsonutil.h" #include +#include +#include +#include #include "cJSON.h" #include "b_error/b_error.h" +#include "b_resources/b_constants.h" #include "filemgmt_libhilog.h" +#include "b_utils/b_time.h" namespace OHOS::FileManagement::Backup { using namespace std; @@ -28,11 +33,10 @@ namespace { const static std::string BUNDLE_INDEX_SPLICE = ":"; } -BJsonUtil::BundleDetailInfo BJsonUtil::ParseBundleNameIndexStr(const std::string &bundleNameStr, - const std::string &patternInfo) +BJsonUtil::BundleDetailInfo BJsonUtil::ParseBundleNameIndexStr(const std::string &bundleNameStr) { HILOGI("Start parse bundle name and index"); - size_t hasPos = bundleNameStr.find(patternInfo); + size_t hasPos = bundleNameStr.find(BUNDLE_INDEX_SPLICE); BundleDetailInfo bundleDetailInfo; if (hasPos == std::string::npos) { bundleDetailInfo.bundleName = bundleNameStr; @@ -40,17 +44,23 @@ BJsonUtil::BundleDetailInfo BJsonUtil::ParseBundleNameIndexStr(const std::string return bundleDetailInfo; } std::string bundleName = bundleNameStr.substr(0, hasPos); - std::string indexStr = bundleNameStr.substr(hasPos + 1); - int index = std::stoi(indexStr); + std::string indexStr = ""; + if (to_string(bundleNameStr.back()) != BUNDLE_INDEX_SPLICE) { + indexStr = bundleNameStr.substr(hasPos + 1); + int index = std::stoi(indexStr); + bundleDetailInfo.bundleIndex = index; + } else { + bundleDetailInfo.bundleIndex = BUNDLE_INDEX_DEFAULT_VAL; + } bundleDetailInfo.bundleName = bundleName; - bundleDetailInfo.bundleIndex = index; HILOGI("End parse bundle name and index"); return bundleDetailInfo; } std::map> BJsonUtil::BuildBundleInfos( const std::vector &bundleNames, const std::vector &bundleInfos, - std::vector &bundleNamesOnly, int32_t userId) + std::vector &bundleNamesOnly, int32_t userId, + std::map &isClearDataFlags) { std::map> bundleNameDetailMap; if (bundleNames.size() != bundleInfos.size()) { @@ -60,6 +70,10 @@ std::map> BJsonUtil::Build HILOGI("Start BuildBundleInfos"); for (size_t i = 0; i < bundleNames.size(); i++) { std::string bundleName = bundleNames[i]; + if (bundleName.empty()) { + HILOGE("BundleName is invalid"); + continue; + } std::vector bundleDetailInfos; size_t pos = bundleName.find(BUNDLE_INDEX_SPLICE); if (pos == 0 || pos == (bundleName.size() - 1)) { @@ -74,64 +88,176 @@ std::map> BJsonUtil::Build bundleNamesOnly.emplace_back(bundleName); } else { std::string bundleNameSplit = bundleName.substr(0, pos); - std::string indexSplit = bundleName.substr(pos, bundleName.size() - 1); - int index = std::stoi(indexSplit); + if (to_string(bundleName.back()) != BUNDLE_INDEX_SPLICE) { + std::string indexSplit = bundleName.substr(pos + 1); + int index = std::atoi(indexSplit.c_str()); + bundleIndex = index; + } else { + bundleIndex = BUNDLE_INDEX_DEFAULT_VAL; + } bundleNameOnly = bundleNameSplit; - bundleIndex = index; bundleNamesOnly.emplace_back(bundleNameSplit); } std::string bundleInfo = bundleInfos[i]; - ParseBundleInfoJson(bundleInfo, bundleDetailInfos, bundleNameOnly, bundleIndex, userId); - bundleNameDetailMap[bundleNameOnly] = bundleDetailInfos; + bool isClearData = true; + BJsonUtil::BundleDetailInfo bundleDetailInfo; + bundleDetailInfo.bundleName = bundleNameOnly; + bundleDetailInfo.bundleIndex = bundleIndex; + bundleDetailInfo.userId = userId; + ParseBundleInfoJson(bundleInfo, bundleDetailInfos, bundleDetailInfo, isClearData, userId); + isClearDataFlags[bundleName] = isClearData; + bundleNameDetailMap[bundleName] = bundleDetailInfos; } HILOGI("End BuildBundleInfos"); return bundleNameDetailMap; } -void BJsonUtil::ParseBundleInfoJson(const std::string &bundleInfo, std::vector &bundleDetails, - std::string &bundleNameOnly, int bundleIndex, int32_t userId) +// 传递的bundleinfo不包含unicast字段时 需要拼接unicast字段 +static bool AddUnicastInfo(std::string &bundleInfo) { cJSON *root = cJSON_Parse(bundleInfo.c_str()); if (root == nullptr) { HILOGE("Parse json error,root is null"); - return; + return false; + } + cJSON *info = cJSON_CreateObject(); + if (info == nullptr) { + cJSON_Delete(root); + return false; + } + cJSON_AddStringToObject(info, "type", "unicast"); + cJSON *details = cJSON_CreateArray(); + if (details == nullptr) { + cJSON_Delete(root); + cJSON_Delete(info); + return false; + } + cJSON_AddItemToArray(details, {}); + cJSON_AddItemToObject(info, "details", details); + cJSON *infos = cJSON_GetObjectItem(root, "infos"); + if (infos == nullptr || !cJSON_IsArray(infos)) { + cJSON_Delete(root); + cJSON_Delete(info); + return false; + } + cJSON_AddItemToArray(infos, info); + char *jsonStr = cJSON_Print(root); + if (jsonStr == nullptr) { + cJSON_Delete(root); + return false; + } + bundleInfo = string(jsonStr); + cJSON_Delete(root); + free(jsonStr); + return true; +} + +bool BJsonUtil::HasUnicastInfo(std::string &bundleInfo) +{ + cJSON *root = cJSON_Parse(bundleInfo.c_str()); + if (root == nullptr) { + HILOGE("Parse json error,root is null"); + return false; } cJSON *infos = cJSON_GetObjectItem(root, "infos"); if (infos == nullptr || !cJSON_IsArray(infos) || cJSON_GetArraySize(infos) == 0) { HILOGE("Parse json error, infos is not array"); cJSON_Delete(root); - return; + return false; } int infosCount = cJSON_GetArraySize(infos); for (int i = 0; i < infosCount; i++) { - BJsonUtil::BundleDetailInfo bundleDetailInfo; - bundleDetailInfo.bundleName = bundleNameOnly; - bundleDetailInfo.bundleIndex = bundleIndex; - bundleDetailInfo.userId = userId; cJSON *infoItem = cJSON_GetArrayItem(infos, i); if (!cJSON_IsObject(infoItem)) { HILOGE("Parse json error, info item is not an object"); + continue; + } + cJSON *type = cJSON_GetObjectItem(infoItem, "type"); + if (type == nullptr || !cJSON_IsString(type) || (type->valuestring == nullptr)) { + HILOGE("Parse json type element error"); + continue; + } + if (string(type->valuestring).compare(BConstants::UNICAST_TYPE) == 0) { cJSON_Delete(root); + return true; + } + } + cJSON_Delete(root); + return false; +} + +static void InsertBundleDetailInfo(cJSON *infos, int infosCount, + std::vector &bundleDetails, + BJsonUtil::BundleDetailInfo bundleDetailInfo, + int32_t userId) +{ + for (int i = 0; i < infosCount; i++) { + cJSON *infoItem = cJSON_GetArrayItem(infos, i); + if (!cJSON_IsObject(infoItem)) { + HILOGE("Parse json error, info item is not an object"); return; } cJSON *type = cJSON_GetObjectItem(infoItem, "type"); if (type == nullptr || !cJSON_IsString(type) || (type->valuestring == nullptr)) { HILOGE("Parse json type element error"); - cJSON_Delete(root); return; } bundleDetailInfo.type = type->valuestring; cJSON *details = cJSON_GetObjectItem(infoItem, "details"); if (details == nullptr || !cJSON_IsArray(details)) { HILOGE("Parse json details element error"); - cJSON_Delete(root); return; } + if (bundleDetailInfo.type.compare(BConstants::UNICAST_TYPE) == 0) { + cJSON *detail = cJSON_CreateObject(); + if (detail == nullptr) { + HILOGE("creat json error"); + return; + } + string userIdstr = to_string(userId); + const char *const zeroUserId = userIdstr.c_str(); + cJSON_AddStringToObject(detail, "type", "userId"); + cJSON_AddStringToObject(detail, "detail", zeroUserId); + cJSON_AddItemToArray(details, detail); + } char *detailInfos = cJSON_Print(details); bundleDetailInfo.detail = std::string(detailInfos); bundleDetails.emplace_back(bundleDetailInfo); cJSON_free(detailInfos); } +} + +void BJsonUtil::ParseBundleInfoJson(const std::string &bundleInfo, std::vector &bundleDetails, + BJsonUtil::BundleDetailInfo bundleDetailInfo, bool &isClearData, int32_t userId) +{ + string bundleInfoCopy = move(bundleInfo); + if (!HasUnicastInfo(bundleInfoCopy)) { + if (!AddUnicastInfo(bundleInfoCopy)) { + HILOGE("AddUnicastInfo failed"); + return; + } + } + cJSON *root = cJSON_Parse(bundleInfoCopy.c_str()); + if (root == nullptr) { + HILOGE("Parse json error,root is null"); + return; + } + cJSON *clearBackupData = cJSON_GetObjectItem(root, "clearBackupData"); + if (clearBackupData == nullptr || !cJSON_IsString(clearBackupData) || (clearBackupData->valuestring == nullptr)) { + HILOGE("Parse json error."); + } else { + std::string value = clearBackupData->valuestring; + isClearData = value.compare("false") != 0; + HILOGI("bundleName:%{public}s clear data falg:%{public}d", bundleDetailInfo.bundleName.c_str(), isClearData); + } + cJSON *infos = cJSON_GetObjectItem(root, "infos"); + if (infos == nullptr || !cJSON_IsArray(infos) || cJSON_GetArraySize(infos) == 0) { + HILOGE("Parse json error, infos is not array"); + cJSON_Delete(root); + return; + } + int infosCount = cJSON_GetArraySize(infos); + InsertBundleDetailInfo(infos, infosCount, bundleDetails, bundleDetailInfo, userId); cJSON_Delete(root); } @@ -152,7 +278,7 @@ bool BJsonUtil::FindBundleInfoByName(std::map> errFileInfo) +{ + cJSON *errJson = cJSON_CreateObject(); + if (errJson == nullptr) { + HILOGE("Creat json failed"); + return false; + } + cJSON *arrJson = cJSON_CreateArray(); + if (arrJson == nullptr) { + cJSON_Delete(errJson); + return false; + } + for (const auto &it : errFileInfo) { + for (const auto &codeIt : it.second) { + cJSON *eleJson = cJSON_CreateObject(); + if (eleJson == nullptr) { + HILOGE("Creat eleJson failed"); + continue; + } + cJSON_AddStringToObject(eleJson, "type", "ErrorInfo"); + cJSON_AddStringToObject(eleJson, "errorInfo", it.first.c_str()); + cJSON_AddNumberToObject(eleJson, "errorCode", codeIt); + cJSON_AddItemToArray(arrJson, eleJson); + } + } + cJSON_AddItemToObject(errJson, "resultInfo", arrJson); + char *data = cJSON_Print(errJson); + if (data == nullptr) { + cJSON_Delete(errJson); + return false; + } + jsonStr = std::string(data); + cJSON_Delete(errJson); + cJSON_free(data); + return true; +} + +bool OHOS::FileManagement::Backup::BJsonUtil::BuildOnProcessRetInfo(std::string &jsonStr, std::string onProcessRet) +{ + cJSON *info = cJSON_CreateObject(); + if (info == nullptr) { + return false; + } + cJSON *processInfo = cJSON_CreateObject(); + if (processInfo == nullptr) { + cJSON_Delete(info); + return false; + } + std::string timeInfo = std::to_string(TimeUtils::GetTimeS()); + cJSON_AddStringToObject(processInfo, "timeInfo", timeInfo.c_str()); + cJSON_AddStringToObject(processInfo, "resultInfo", onProcessRet.c_str()); + cJSON_AddItemToObject(info, "processResult", processInfo); + char *data = cJSON_Print(info); + if (data == nullptr) { + cJSON_Delete(info); + return false; + } + jsonStr = std::string(data); + cJSON_Delete(info); + cJSON_free(data); + return true; +} + +std::string BJsonUtil::BuildBundleNameIndexInfo(const std::string &bundleName, int appIndex) +{ + std::string result = bundleName; + if (appIndex == BUNDLE_INDEX_DEFAULT_VAL) { + return result; + } + result += BUNDLE_INDEX_SPLICE; + result += std::to_string(appIndex); + return result; +} + +bool OHOS::FileManagement::Backup::BJsonUtil::BuildOnProcessErrInfo(std::string &reportInfo, std::string path, int err) +{ + cJSON *info = cJSON_CreateObject(); + if (info == nullptr) { + return false; + } + cJSON *item = cJSON_CreateObject(); + if (item == nullptr) { + cJSON_Delete(info); + return false; + } + cJSON *errInfoJs = cJSON_CreateObject(); + if (errInfoJs == nullptr) { + cJSON_Delete(info); + cJSON_Delete(item); + return false; + } + std::string errStr = std::to_string(err); + std::string timeInfo = std::to_string(TimeUtils::GetTimeS()); + cJSON_AddStringToObject(errInfoJs, "errorCode", errStr.c_str()); + cJSON_AddStringToObject(errInfoJs, "errorMessage", path.c_str()); + cJSON_AddStringToObject(item, "timeInfo", timeInfo.c_str()); + cJSON_AddItemToObject(item, "errorInfo", errInfoJs); + cJSON_AddItemToObject(info, "processResult", item); + char *data = cJSON_Print(info); + if (data == nullptr) { + cJSON_Delete(info); + return false; + } + reportInfo = std::string(data); + cJSON_Delete(info); + cJSON_free(data); + return true; +} + +bool BJsonUtil::BuildBundleInfoJson(int32_t userId, string &detailInfo) +{ + cJSON *infos = cJSON_CreateArray(); + if (infos == nullptr) { + return false; + } + cJSON *info = cJSON_CreateObject(); + if (info == nullptr) { + cJSON_Delete(infos); + return false; + } + string userIdstr = to_string(userId); + const char *const zeroUserId = userIdstr.c_str(); + cJSON_AddStringToObject(info, "type", "userId"); + cJSON_AddStringToObject(info, "detail", zeroUserId); + cJSON_AddItemToArray(infos, info); + char *jsonStr = cJSON_Print(infos); + if (jsonStr == nullptr) { + cJSON_Delete(infos); + return false; + } + detailInfo = string(jsonStr); + cJSON_Delete(infos); + free(jsonStr); + return true; +} +} diff --git a/utils/src/b_ohos/startup/backup_para.cpp b/utils/src/b_ohos/startup/backup_para.cpp index c5f9c1d9dc4fa4c3a5681681e837b769aebab22b..147544c7ce7895d0328b39a38d20d94029996a31 100644 --- a/utils/src/b_ohos/startup/backup_para.cpp +++ b/utils/src/b_ohos/startup/backup_para.cpp @@ -27,7 +27,7 @@ namespace OHOS::FileManagement::Backup { using namespace std; - +const char* BACKUP_DEBUG_STATE = "sys.backup.check.enable"; /** * @brief 获取配置参数的值 * @@ -37,25 +37,13 @@ using namespace std; */ static tuple GetConfigParameterValue(const string &key, uint32_t len) { - int handle = static_cast(FindParameter(key.c_str())); - HILOGI("start get config param value."); - if (handle == -1) { - HILOGI("Fail to find parameter."); - return {false, ""}; - } - try { - unique_ptr buffer = make_unique(len + 1); - int res = GetParameterValue(handle, buffer.get(), len + 1); - if (res < 0) { - HILOGI("Fail to get parameter value."); - return {false, ""}; - } - HILOGI("end get config param value."); - return {true, buffer.get()}; - } catch (const bad_alloc &e) { - HILOGE("Fail to get parameter value: %{public}s.", e.what()); + char configParam[] = "false"; + int length = GetParameter(key.c_str(), "", configParam, len + 1); + if (length <= 0) { + HILOGE("Fail to GetParameter name = %{public}s, length = %{public}d", key.c_str(), length); return {false, ""}; } + return {true, configParam}; } bool BackupPara::GetBackupDebugOverrideExtensionConfig() @@ -63,7 +51,8 @@ bool BackupPara::GetBackupDebugOverrideExtensionConfig() auto [getCfgParaValSucc, value] = GetConfigParameterValue(BConstants::BACKUP_DEBUG_OVERRIDE_EXTENSION_CONFIG_KEY, BConstants::BACKUP_PARA_VALUE_MAX); if (!getCfgParaValSucc) { - throw BError(BError::Codes::SA_INVAL_ARG, "Fail to get configuration parameter value of backup.para"); + HILOGE("Fail to get configuration parameter value of backup.para, return default value"); + return BConstants::BACKUP_DEBUG_OVERRIDE_EXTENSION_CONFIG_DEFAULT_VALUE; } return value == "true"; } @@ -73,7 +62,8 @@ bool BackupPara::GetBackupOverrideBackupSARelease() auto [getCfgParaValSucc, value] = GetConfigParameterValue(BConstants::BACKUP_OVERRIDE_BACKUP_SA_RELEASE_KEY, BConstants::BACKUP_PARA_VALUE_MAX); if (!getCfgParaValSucc) { - throw BError(BError::Codes::SA_INVAL_ARG, "Fail to get configuration parameter value of backup.para"); + HILOGE("Fail to get configuration parameter value of backup.para, return default value"); + return BConstants::BACKUP_DEBUG_OVERRIDE_BACKUP_SA_RELEASE_DEFAULT_VALUE; } return value == "true"; } @@ -83,7 +73,8 @@ bool BackupPara::GetBackupOverrideIncrementalRestore() auto [getCfgParaValSucc, value] = GetConfigParameterValue(BConstants::BACKUP_OVERRIDE_INCREMENTAL_KEY, BConstants::BACKUP_PARA_VALUE_MAX); if (!getCfgParaValSucc) { - throw BError(BError::Codes::SA_INVAL_ARG, "Fail to get configuration parameter value of backup.para"); + HILOGE("Fail to get configuration parameter value of backup.para, return default value"); + return BConstants::BACKUP_DEBUG_OVERRIDE_INCREMENTAL_DEFAULT_VALUE; } HILOGI("Get Parse IncrementalRestore result, value: %{public}s", value.c_str()); return value == "true"; @@ -106,4 +97,16 @@ tuple BackupPara::GetBackupDebugOverrideAccount() } return {false, 0}; } + +bool BackupPara::GetBackupDebugState() +{ + char paraValue[30] = {0}; // 30: for system paramter + auto res = GetParameter(BACKUP_DEBUG_STATE, "-1", paraValue, sizeof(paraValue)); + if (res <= 0) { + HILOGE("GetParameter fail, key:%{public}s res:%{public}d", BACKUP_DEBUG_STATE, res); + return false; + } + std::string result(paraValue); + return result == "true"; +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/utils/src/b_radar/b_radar.cpp b/utils/src/b_radar/b_radar.cpp new file mode 100644 index 0000000000000000000000000000000000000000..1c7f7ac8450ded0c0756ae40d4f69b87ef234dc3 --- /dev/null +++ b/utils/src/b_radar/b_radar.cpp @@ -0,0 +1,120 @@ +/* + * Copyright (c) 2024 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include +#include +#include +#include + +#include "b_process/b_multiuser.h" +#include "b_radar/b_radar.h" +#include "b_resources/b_constants.h" +#include "b_utils/b_time.h" +#include "hisysevent.h" +#include "i_service_reverse.h" + +namespace OHOS::FileManagement::Backup { +int32_t AppRadar::GetUserId() +{ + auto multiuser = BMultiuser::ParseUid(getuid()); + if ((multiuser.userId == BConstants::SYSTEM_UID) || (multiuser.userId == BConstants::XTS_UID)) { + return BConstants::DEFAULT_USER_ID; + } + return multiuser.userId; +} + +void AppRadar::RecordDefaultFuncRes(Info &info, const std::string &func, int32_t userId, + enum BizStageBackup bizStage, int32_t resultCode) +{ + std::stringstream ss; + ss << R"("result_info": {)" << info.resInfo << "}}"; + HiSysEventWrite( + OHOS::HiviewDFX::HiSysEvent::Domain::FILEMANAGEMENT, + BConstants::FILE_BACKUP_RESTORE_EVENTS, + OHOS::HiviewDFX::HiSysEvent::EventType::BEHAVIOR, + "BUNDLE_NAME", info.bundleName, + "USER_ID", userId, + "PID", getpid(), + "FUNC", func, + "TIME", TimeUtils::GetCurrentTime(), + "BIZ_SCENE", static_cast(IServiceReverse::Scenario::UNDEFINED), + "BIZ_STAGE", static_cast(bizStage), + "EXEC_STATUS", info.status, + "RESULT_CODE", resultCode, + "RESULT_INFO", ss.str()); +} + +void AppRadar::RecordBackupFuncRes(Info &info, const std::string &func, int32_t userId, + enum BizStageBackup bizStage, int32_t resultCode) +{ + std::stringstream ss; + ss << R"("result_info": {)" << info.resInfo << "}}"; + HiSysEventWrite( + OHOS::HiviewDFX::HiSysEvent::Domain::FILEMANAGEMENT, + BConstants::FILE_BACKUP_RESTORE_EVENTS, + OHOS::HiviewDFX::HiSysEvent::EventType::BEHAVIOR, + "BUNDLE_NAME", info.bundleName, + "USER_ID", userId, + "PID", getpid(), + "FUNC", func, + "TIME", TimeUtils::GetCurrentTime(), + "BIZ_SCENE", static_cast(IServiceReverse::Scenario::BACKUP), + "BIZ_STAGE", static_cast(bizStage), + "EXEC_STATUS", info.status, + "RESULT_CODE", resultCode, + "RESULT_INFO", ss.str()); +} + +void AppRadar::RecordRestoreFuncRes(Info &info, const std::string &func, int32_t userId, + enum BizStageRestore bizStage, int32_t resultCode) +{ + std::stringstream ss; + ss << R"("result_info": {)" << info.resInfo << "}}"; + HiSysEventWrite( + OHOS::HiviewDFX::HiSysEvent::Domain::FILEMANAGEMENT, + BConstants::FILE_BACKUP_RESTORE_EVENTS, + OHOS::HiviewDFX::HiSysEvent::EventType::BEHAVIOR, + "BUNDLE_NAME", info.bundleName, + "USER_ID", userId, + "PID", getpid(), + "FUNC", func, + "TIME", TimeUtils::GetCurrentTime(), + "BIZ_SCENE", static_cast(IServiceReverse::Scenario::RESTORE), + "BIZ_STAGE", static_cast(bizStage), + "EXEC_STATUS", info.status, + "RESULT_CODE", resultCode, + "RESULT_INFO", ss.str()); +} + +void AppRadar::RecordStatisticRes(StatInfo &statInfo, int32_t userId, enum IServiceReverse::Scenario scenario, + int32_t succ_cnt, int32_t fail_cnt, int32_t resultCode) +{ + std::stringstream ss; + ss << R"("result_info": {)" << statInfo.resInfo << "}}"; + HiSysEventWrite( + OHOS::HiviewDFX::HiSysEvent::Domain::FILEMANAGEMENT, + BConstants::FILE_BACKUP_RESTORE_STATISTIC, + OHOS::HiviewDFX::HiSysEvent::EventType::STATISTIC, + "CALLER_NAME", statInfo.callerName, + "USER_ID", userId, + "PID", getpid(), + "TIME", TimeUtils::GetCurrentTime(), + "BIZ_SCENE", static_cast(scenario), + "SUCC_CNT", succ_cnt, + "FAIL_CNT", fail_cnt, + "RESULT_CODE", resultCode, + "RESULT_INFO", ss.str()); +} +} // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/utils/src/b_sa/b_sa_utils.cpp b/utils/src/b_sa/b_sa_utils.cpp index 05d090e81c1edb26c4ab53827ecf582ef9ebdc71..399cb10269a26f1a124ea9d4957ea154737e1b20 100644 --- a/utils/src/b_sa/b_sa_utils.cpp +++ b/utils/src/b_sa/b_sa_utils.cpp @@ -14,9 +14,17 @@ */ #include "b_sa/b_sa_utils.h" +#include "access_token.h" +#include "accesstoken_kit.h" +#include "ipc_skeleton.h" +#include "tokenid_kit.h" namespace OHOS::FileManagement::Backup { +namespace { + const std::string BACKUP_PERMISSION = "ohos.permission.BACKUP"; +} + bool SAUtils::IsSABundleName(std::string bundleName) { if (bundleName.empty()) { @@ -29,4 +37,24 @@ bool SAUtils::IsSABundleName(std::string bundleName) } return true; } + +bool SAUtils::CheckBackupPermission() +{ + Security::AccessToken::AccessTokenID tokenCaller = IPCSkeleton::GetCallingTokenID(); + return Security::AccessToken::AccessTokenKit::VerifyAccessToken(tokenCaller, BACKUP_PERMISSION) == + Security::AccessToken::PermissionState::PERMISSION_GRANTED; +} + +bool SAUtils::CheckPermission(const std::string &permission) +{ + Security::AccessToken::AccessTokenID tokenCaller = IPCSkeleton::GetCallingTokenID(); + return Security::AccessToken::AccessTokenKit::VerifyAccessToken(tokenCaller, permission) == + Security::AccessToken::PermissionState::PERMISSION_GRANTED; +} + +bool SAUtils::IsSystemApp() +{ + uint64_t fullTokenId = OHOS::IPCSkeleton::GetCallingFullTokenID(); + return Security::AccessToken::TokenIdKit::IsSystemAppByFullTokenID(fullTokenId); +} } // namespace OHOS::FileManagement::Backup \ No newline at end of file diff --git a/utils/src/b_utils/b_time.cpp b/utils/src/b_utils/b_time.cpp new file mode 100644 index 0000000000000000000000000000000000000000..9729a5130ec7b5b35398c37eb906b76385b1a221 --- /dev/null +++ b/utils/src/b_utils/b_time.cpp @@ -0,0 +1,53 @@ +/* + * Copyright (c) 2024 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "b_resources/b_constants.h" +#include "b_utils/b_time.h" +#include +#include +#include +#include + +namespace OHOS::FileManagement::Backup { +int64_t TimeUtils::GetTimeS() +{ + std::chrono::seconds nowS = std::chrono::duration_cast( + std::chrono::system_clock::now().time_since_epoch()); + return nowS.count(); +} +int64_t TimeUtils::GetTimeMS() +{ + std::chrono::milliseconds nowMs = std::chrono::duration_cast( + std::chrono::system_clock::now().time_since_epoch()); + return nowMs.count(); +} +int64_t TimeUtils::GetTimeUS() +{ + std::chrono::microseconds nowUs = std::chrono::duration_cast( + std::chrono::system_clock::now().time_since_epoch()); + return nowUs.count(); +} + +std::string TimeUtils::GetCurrentTime() +{ + auto now = std::chrono::system_clock::now(); + auto time = std::chrono::system_clock::to_time_t(now); + auto ms = std::chrono::duration_cast(now.time_since_epoch()); + std::stringstream strTime; + strTime << (std::put_time(std::localtime(&time), "%Y-%m-%d %H:%M:%S:")) << (std::setfill('0')) + << (std::setw(BConstants::INDEX)) << (ms.count() % BConstants::MS_1000); + return strTime.str(); +} +} // namespace OHOS::FileManagement::Backup \ No newline at end of file