From b97bfc41f8c96d81377de55366192631176ea405 Mon Sep 17 00:00:00 2001 From: yang-jingbo1985 Date: Thu, 28 Dec 2023 14:28:08 +0800 Subject: [PATCH] =?UTF-8?q?backup=5Fsa=E4=BE=A7=E5=A2=9E=E9=87=8F=E6=96=87?= =?UTF-8?q?=E4=BB=B6=E8=AF=86=E5=88=AB=E9=80=BB=E8=BE=91=20Signed-off-by:?= =?UTF-8?q?=20yangjingbo10=20?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Change-Id: I6a69baaa5dcf351045a8c134262b7773d159c0ad --- .../src/b_incremental_data.cpp | 65 +++++++++++ .../impl/b_incremental_data.h | 47 ++++++++ .../include/module_external/bms_adapter.h | 12 +++ .../include/module_external/sms_adapter.h | 16 ++- .../src/module_external/bms_adapter.cpp | 102 +++++++++++++++++- .../src/module_external/sms_adapter.cpp | 11 ++ utils/include/b_resources/b_constants.h | 9 ++ 7 files changed, 259 insertions(+), 3 deletions(-) create mode 100644 frameworks/native/backup_kit_inner/src/b_incremental_data.cpp create mode 100644 interfaces/inner_api/native/backup_kit_inner/impl/b_incremental_data.h diff --git a/frameworks/native/backup_kit_inner/src/b_incremental_data.cpp b/frameworks/native/backup_kit_inner/src/b_incremental_data.cpp new file mode 100644 index 000000000..bb8e8dbba --- /dev/null +++ b/frameworks/native/backup_kit_inner/src/b_incremental_data.cpp @@ -0,0 +1,65 @@ +/* + * Copyright (c) 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 "b_incremental_data.h" + +#include "filemgmt_libhilog.h" +#include "message_parcel.h" + +namespace OHOS { +namespace FileManagement { +namespace Backup { +using namespace std; + +bool BIncrementalData::Marshalling(Parcel &parcel) const +{ + if (!parcel.WriteString(bundleName) || !parcel.WriteInt64(lastIncrementalTime) || + !parcel.WriteString(backupParameters) || !parcel.WriteString(backupPriority)) { + HILOGE("Failed"); + return false; + } + auto msgParcel = static_cast(&parcel); + msgParcel->WriteFileDescriptor(manifestFd); + return true; +} + +bool BIncrementalData::ReadFromParcel(Parcel &parcel) +{ + if (!parcel.ReadString(bundleName) || !parcel.ReadInt64(lastIncrementalTime) || + !parcel.ReadString(backupParameters) || !parcel.ReadString(backupPriority)) { + HILOGE("Failed"); + return false; + } + auto msgParcel = static_cast(&parcel); + manifestFd = msgParcel->ReadFileDescriptor(); + return true; +} + +BIncrementalData *BIncrementalData::Unmarshalling(Parcel &parcel) +{ + try { + auto result = make_unique(); + if (!result->ReadFromParcel(parcel)) { + return nullptr; + } + return result.release(); + } catch (const bad_alloc &e) { + HILOGE("Failed to unmarshall BIncrementalData because of %{public}s", e.what()); + } + return nullptr; +} +} // namespace Backup +} // namespace FileManagement +} // namespace OHOS \ No newline at end of file diff --git a/interfaces/inner_api/native/backup_kit_inner/impl/b_incremental_data.h b/interfaces/inner_api/native/backup_kit_inner/impl/b_incremental_data.h new file mode 100644 index 000000000..0052e61f4 --- /dev/null +++ b/interfaces/inner_api/native/backup_kit_inner/impl/b_incremental_data.h @@ -0,0 +1,47 @@ +/* + * Copyright (c) 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 OHOS_FILEMGMT_BACKUP_B_INCREMENTAL_DATA_H +#define OHOS_FILEMGMT_BACKUP_B_INCREMENTAL_DATA_H + +#include +#include + +#include "parcel.h" +#include "unique_fd.h" + +namespace OHOS::FileManagement::Backup { +struct BIncrementalData : public Parcelable { + std::string bundleName; + int64_t lastIncrementalTime; + int32_t manifestFd; + std::string backupParameters; + std::string backupPriority; + + BIncrementalData() = default; + BIncrementalData(std::string name, int64_t nTime, int fd, std::string parameters = "", std::string priority = "") + : bundleName(name), lastIncrementalTime(nTime), manifestFd(fd), backupParameters(parameters), + backupPriority(priority) + { + } + ~BIncrementalData() override = default; + + bool ReadFromParcel(Parcel &parcel); + bool Marshalling(Parcel &parcel) const override; + static BIncrementalData *Unmarshalling(Parcel &parcel); +}; +} // namespace OHOS::FileManagement::Backup + +#endif // OHOS_FILEMGMT_BACKUP_B_INCREMENTAL_DATA_H diff --git a/services/backup_sa/include/module_external/bms_adapter.h b/services/backup_sa/include/module_external/bms_adapter.h index 7af9bedff..7297a5fe6 100644 --- a/services/backup_sa/include/module_external/bms_adapter.h +++ b/services/backup_sa/include/module_external/bms_adapter.h @@ -21,6 +21,8 @@ #include "b_json/b_json_entity_caps.h" #include "bundlemgr/bundle_mgr_interface.h" +#include "b_incremental_data.h" +#include "istorage_manager.h" namespace OHOS::FileManagement::Backup { class InnerReceiverImpl; @@ -49,6 +51,16 @@ public: * @brief Get app gallery bundle name */ static std::string GetAppGalleryBundleName(); + + /** + * @brief Get the bundle infos object for incremental backup + * + * @param incrementalDataList bundle Name and time list + * @param userId User ID + * @return std::vector + */ + static std::vector GetBundleInfosForIncremental(const std::vector &incrementalDataList, + int32_t userId); }; } // namespace OHOS::FileManagement::Backup #endif // OHOS_FILEMGMT_BACKUP_BUNDLE_MGR_ADAPTER_H diff --git a/services/backup_sa/include/module_external/sms_adapter.h b/services/backup_sa/include/module_external/sms_adapter.h index 5dd16545b..d1aa7ff20 100644 --- a/services/backup_sa/include/module_external/sms_adapter.h +++ b/services/backup_sa/include/module_external/sms_adapter.h @@ -17,7 +17,8 @@ #define OHOS_FILEMGMT_BACKUP_STORAGE_MGR_ADAPTER_H #include - +#include +#include #include "istorage_manager.h" namespace OHOS::FileManagement::Backup { @@ -37,6 +38,19 @@ public: * @param userId user id */ static int64_t GetUserStorageStats(const std::string &bundleName, int32_t userId); + + /** + * @brief Get the user storage stats object + * + * @param userId user id + * @param bundleNames + * @param incrementalBackTimes + * @param pkgFileSizes bundle backup file size + * @param pkgStatPaths stat file path + */ + static int32_t GetBundleStatsForIncrease(uint32_t userId, const std::vector &bundleNames, + const std::vector &incrementalBackTimes, std::vector &pkgFileSizes, + std::vector &pkgStatPaths); }; } // namespace OHOS::FileManagement::Backup #endif // OHOS_FILEMGMT_BACKUP_STORAGE_MGR_ADAPTER_H \ 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 fbc7e4526..d068dffdd 100644 --- a/services/backup_sa/src/module_external/bms_adapter.cpp +++ b/services/backup_sa/src/module_external/bms_adapter.cpp @@ -14,7 +14,10 @@ */ #include "module_external/bms_adapter.h" +#include "module_external/sms_adapter.h" +#include +#include #include #include "b_error/b_error.h" @@ -99,8 +102,8 @@ static int64_t GetBundleStats(const string &bundleName, int32_t userId) bundleStats[i] = 0; } } - int64_t dataSize_ = bundleStats[LOCAL] + bundleStats[DISTRIBUTED] + bundleStats[DATABASE]; - return dataSize_; + int64_t dataSize = bundleStats[LOCAL] + bundleStats[DISTRIBUTED] + bundleStats[DATABASE]; + return dataSize; } vector BundleMgrAdapter::GetBundleInfos(int32_t userId) @@ -163,4 +166,99 @@ string BundleMgrAdapter::GetAppGalleryBundleName() } return bundleName; } + +static tuple, vector> GetBackupExtConfig( + const vector &extensionInfos) +{ + for (auto &&ext : extensionInfos) { + if (ext.type != AppExecFwk::ExtensionAbilityType::BACKUP) { + continue; + } + vector out; + AppExecFwk::BundleMgrClient client; + if (!client.GetResConfigFile(ext, "ohos.extension.backup", out) || out.size() == 0) { + throw BError(BError::Codes::SA_INVAL_ARG, "Failed to get resconfigfile of bundle " + ext.bundleName); + } + BJsonCachedEntity cachedEntity(out[0], ext.bundleName); + auto cache = cachedEntity.Structuralize(); + return {cache.GetAllowToBackupRestore(), ext.name, cache.GetRestoreDeps(), cache.GetSupportScene(), + cache.GetIncludes(), cache.GetExcludes()}; + } + HILOGI("No backup extension ability found"); + return {false, "", "", "", {}, {}}; +} + +static bool CreateIPCInteractionFiles(int32_t userId, const string &bundleName, int64_t lastIncrementalTime, + const vector &includes, const vector &excludes) +{ + // backup_sa bundle path + string backupSaBundleDir = BConstants::BACKUP_PATH_PREFIX + to_string(userId) + BConstants::BACKUP_PATH_SURFFIX + + bundleName + to_string(BConstants::FILE_SEPARATOR_CHAR); + if (access(backupSaBundleDir.data(), F_OK) != 0 && mkdir(backupSaBundleDir.data(), S_IRWXU | S_IRWXG) != 0) { + HILOGE("Failed to create folder in backup_sa"); + return false; + } + // backup_sa include/exclude + string incExFilePath = backupSaBundleDir + BConstants::BACKUP_INCEXC_SYMBOL + to_string(lastIncrementalTime); + std::ofstream incExcFile; + incExcFile.open(incExFilePath.data(), std::ios::out | std::ios::trunc); + if (!incExcFile.is_open()) { + HILOGE("Cannot create file"); + return false; + } + incExcFile << BConstants::BACKUP_INCLUDE << std::endl; + for (auto &include : includes) { + incExcFile << include << std::endl; + } + incExcFile << BConstants::BACKUP_EXCLUDE << std::endl; + for (auto &exclude : excludes) { + incExcFile << exclude << std::endl; + } + return true; +} + +std::vector GetBundleInfosForIncremental( + const std::vector &incrementalDataList, int32_t userId) +{ + std::vector bundleNames; + std::vector incrementalBackTimes; + vector bundleInfos; + auto bms = GetBundleManager(); + for (auto const &bundleNameTime : incrementalDataList) { + auto bundleName = bundleNameTime.bundleName; + HILOGI("Begin Get bundleName:%{public}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 : %{public}s", installedBundle.name.data()); + continue; + } + auto [allToBackup, extName, restoreDeps, supportScene, includes, excludes] = + GetBackupExtConfig(installedBundle.extensionInfos); + bundleInfos.emplace_back(BJsonEntityCaps::BundleInfo {installedBundle.name, installedBundle.versionCode, + installedBundle.versionName, 0, allToBackup, + extName, restoreDeps, supportScene}); + if (!CreateIPCInteractionFiles(userId, bundleName, bundleNameTime.lastIncrementalTime, includes, excludes)) { + HILOGE("Failed to write include/exclude files, name : %{public}s", installedBundle.name.data()); + continue; + } + bundleNames.emplace_back(bundleName); + incrementalBackTimes.emplace_back(bundleNameTime.lastIncrementalTime); + } + + std::vector pkgFileSizes; + std::vector pkgStatPaths; + StorageMgrAdapter::GetBundleStatsForIncrease(userId, bundleNames , incrementalBackTimes, pkgFileSizes, pkgStatPaths); + + std::vector newBundleInfos; + for (size_t i = 0; bundleInfos.size(); i++) { + BJsonEntityCaps::BundleInfo newBundleInfo = bundleInfos[i]; + newBundleInfo.spaceOccupied = pkgFileSizes[i]; + newBundleInfos.emplace_back(newBundleInfo); + } + return newBundleInfos; +} } // namespace OHOS::FileManagement::Backup diff --git a/services/backup_sa/src/module_external/sms_adapter.cpp b/services/backup_sa/src/module_external/sms_adapter.cpp index e6613ed2c..679842ee7 100644 --- a/services/backup_sa/src/module_external/sms_adapter.cpp +++ b/services/backup_sa/src/module_external/sms_adapter.cpp @@ -69,4 +69,15 @@ int64_t StorageMgrAdapter::GetUserStorageStats(const std::string &bundleName, in } return 0; } + +int32_t StorageMgrAdapter::GetBundleStatsForIncrease(uint32_t userId, const std::vector &bundleNames, + const std::vector &incrementalBackTimes, std::vector &pkgFileSizes, + std::vector &pkgStatPaths) +{ + auto storageMgr = GetStorageManager(); + if (storageMgr->GetBundleStatsForIncrease(userId, bundleNames, incrementalBackTimes, pkgFileSizes, pkgStatPaths)) { + throw BError(BError::Codes::SA_BROKEN_IPC, "Failed to get user storage stats"); + } + return 0; +} } // namespace OHOS::FileManagement::Backup diff --git a/utils/include/b_resources/b_constants.h b/utils/include/b_resources/b_constants.h index 9f4ae877b..679b623d2 100644 --- a/utils/include/b_resources/b_constants.h +++ b/utils/include/b_resources/b_constants.h @@ -70,6 +70,15 @@ static inline std::string BACKUP_DEBUG_OVERRIDE_EXTENSION_CONFIG_KEY = "backup.d static inline std::string BACKUP_DEBUG_OVERRIDE_ACCOUNT_CONFIG_KEY = "backup.debug.overrideAccountConfig"; static inline std::string BACKUP_DEBUG_OVERRIDE_ACCOUNT_NUMBER_KEY = "backup.debug.overrideAccountNumber"; +// 增量备份相关处理目录 +constexpr char FILE_SEPARATOR_CHAR = '/'; +static const std::string BACKUP_PATH_PREFIX = "/data/service/el2/"; +static const std::string BACKUP_PATH_SURFFIX = "/backup/backup_sa/"; +static const std::string BACKUP_INCEXC_SYMBOL = "incExc_"; +static const std::string BACKUP_STAT_SYMBOL = "stat_"; +static const std::string BACKUP_INCLUDE = "INCLUDES"; +static const std::string BACKUP_EXCLUDE = "EXCLUDES"; + // 应用备份数据暂存路径 static inline std::string_view SA_BUNDLE_BACKUP_BACKUP = "/backup/"; static inline std::string_view SA_BUNDLE_BACKUP_RESTORE = "/restore/"; -- Gitee