Loading PREUPLOAD.cfg +1 −0 Original line number Diff line number Diff line Loading @@ -30,6 +30,7 @@ clang_format = --commit ${PREUPLOAD_COMMIT} --style file --extensions c,h,cc,cpp services/vibratorservice/ services/vr/ vulkan/ bpfmt = -d [Hook Scripts] owners_hook = ${REPO_ROOT}/frameworks/base/tools/aosp/aosp_sha.sh ${PREUPLOAD_COMMIT} "OWNERS$" Loading cmds/atrace/atrace.cpp +1 −0 Original line number Diff line number Diff line Loading @@ -244,6 +244,7 @@ static const TracingCategory k_categories[] = { { OPT, "events/kmem/ion_heap_shrink/enable" }, { OPT, "events/ion/ion_stat/enable" }, { OPT, "events/gpu_mem/gpu_mem_total/enable" }, { OPT, "events/fastrpc/fastrpc_dma_stat/enable" }, } }, { "thermal", "Thermal event", ATRACE_TAG_THERMAL, { { REQ, "events/thermal/thermal_temperature/enable" }, Loading cmds/atrace/atrace.rc +2 −0 Original line number Diff line number Diff line Loading @@ -63,6 +63,8 @@ on late-init chmod 0666 /sys/kernel/tracing/events/cpuhp/cpuhp_pause/enable chmod 0666 /sys/kernel/debug/tracing/events/power/gpu_frequency/enable chmod 0666 /sys/kernel/tracing/events/power/gpu_frequency/enable chmod 0666 /sys/kernel/debug/tracing/events/power/gpu_work_period/enable chmod 0666 /sys/kernel/tracing/events/power/gpu_work_period/enable chmod 0666 /sys/kernel/debug/tracing/events/power/suspend_resume/enable chmod 0666 /sys/kernel/tracing/events/power/suspend_resume/enable chmod 0666 /sys/kernel/debug/tracing/events/cpufreq_interactive/enable Loading cmds/installd/InstalldNativeService.cpp +140 −56 Original line number Diff line number Diff line Loading @@ -80,7 +80,7 @@ #define LOG_TAG "installd" #endif // #define GRANULAR_LOCKS #define GRANULAR_LOCKS using android::base::ParseUint; using android::base::Split; Loading Loading @@ -485,7 +485,6 @@ done: free(after); return res; } static bool internal_storage_has_project_id() { // The following path is populated in setFirstBoot, so if this file is present // then project ids can be used. Using call once to cache the result of this check Loading Loading @@ -1204,6 +1203,25 @@ binder::Status InstalldNativeService::destroyAppProfiles(const std::string& pack return res; } binder::Status InstalldNativeService::deleteReferenceProfile(const std::string& packageName, const std::string& profileName) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_PACKAGE_NAME(packageName); LOCK_PACKAGE(); // This function only supports primary dex'es. std::string path = create_reference_profile_path(packageName, profileName, /*is_secondary_dex=*/false); if (unlink(path.c_str()) != 0) { if (errno == ENOENT) { return ok(); } else { return error("Failed to delete profile " + profileName + " for " + packageName); } } return ok(); } binder::Status InstalldNativeService::destroyAppData(const std::optional<std::string>& uuid, const std::string& packageName, int32_t userId, int32_t flags, int64_t ceDataInode) { ENFORCE_UID(AID_SYSTEM); Loading Loading @@ -1919,7 +1937,7 @@ binder::Status InstalldNativeService::destroyUserData(const std::optional<std::s } binder::Status InstalldNativeService::freeCache(const std::optional<std::string>& uuid, int64_t targetFreeBytes, int64_t cacheReservedBytes, int32_t flags) { int64_t targetFreeBytes, int32_t flags) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_UUID(uuid); #ifndef GRANULAR_LOCKS Loading @@ -1930,6 +1948,7 @@ binder::Status InstalldNativeService::freeCache(const std::optional<std::string> const char* uuid_ = uuid ? uuid->c_str() : nullptr; auto data_path = create_data_path(uuid_); auto noop = (flags & FLAG_FREE_CACHE_NOOP); auto defy_target = (flags & FLAG_FREE_CACHE_DEFY_TARGET_FREE_BYTES); int64_t free = data_disk_free(data_path); if (free < 0) { Loading @@ -1938,12 +1957,14 @@ binder::Status InstalldNativeService::freeCache(const std::optional<std::string> int64_t cleared = 0; int64_t needed = targetFreeBytes - free; if (!defy_target) { LOG(DEBUG) << "Device " << data_path << " has " << free << " free; requested " << targetFreeBytes << "; needed " << needed; if (free >= targetFreeBytes) { return ok(); } } if (flags & FLAG_FREE_CACHE_V2) { // This new cache strategy fairly removes files from UIDs by deleting Loading @@ -1966,17 +1987,43 @@ binder::Status InstalldNativeService::freeCache(const std::optional<std::string> #endif // GRANULAR_LOCKS FTS *fts; FTSENT *p; // Create a list of data paths whose children have cache directories auto ce_path = create_data_user_ce_path(uuid_, userId); auto de_path = create_data_user_de_path(uuid_, userId); auto media_path = findDataMediaPath(uuid, userId) + "/Android/data/"; char *argv[] = { (char*) ce_path.c_str(), (char*) de_path.c_str(), (char*) media_path.c_str(), nullptr }; auto ce_sdk_path = create_data_misc_sdk_sandbox_path(uuid_, /*isCeData=*/true, userId); auto de_sdk_path = create_data_misc_sdk_sandbox_path(uuid_, /*isCeData=*/false, userId); std::vector<std::string> dataPaths = {ce_path, de_path, media_path}; foreach_subdir(ce_sdk_path, [&ce_sdk_path, &dataPaths](const std::string subDir) { const auto fullpath = ce_sdk_path + "/" + subDir; dataPaths.push_back(fullpath); }); foreach_subdir(de_sdk_path, [&de_sdk_path, &dataPaths](const std::string subDir) { const auto fullpath = de_sdk_path + "/" + subDir; dataPaths.push_back((char*)fullpath.c_str()); }); char* argv[dataPaths.size() + 1]; for (unsigned int i = 0; i < dataPaths.size(); i++) { argv[i] = (char*)dataPaths[i].c_str(); } argv[dataPaths.size()] = nullptr; if (!(fts = fts_open(argv, FTS_PHYSICAL | FTS_NOCHDIR | FTS_XDEV, nullptr))) { return error("Failed to fts_open"); } while ((p = fts_read(fts)) != nullptr) { if (p->fts_info == FTS_D && p->fts_level == 1) { uid_t uid = p->fts_statp->st_uid; // If uid belongs to sdk sandbox, then the cache should be attributed to the // original client app. const auto client_uid = multiuser_convert_sdk_sandbox_to_app_uid(uid); const bool isSandboxUid = (client_uid != (uid_t)-1); if (isSandboxUid) uid = client_uid; if (multiuser_get_app_id(uid) == AID_MEDIA_RW) { uid = (multiuser_get_app_id(p->fts_statp->st_gid) - AID_EXT_GID_START) + AID_APP_START; Loading Loading @@ -2035,12 +2082,6 @@ binder::Status InstalldNativeService::freeCache(const std::optional<std::string> break; } // Only keep clearing when we haven't pushed into reserved area if (cacheReservedBytes > 0 && cleared >= (cacheTotal - cacheReservedBytes)) { LOG(DEBUG) << "Refusing to clear cached data in reserved space"; break; } // Find the best tracker to work with; this might involve swapping // if the active tracker is no longer the most over quota bool nextBetter = active && !queue.empty() Loading Loading @@ -2073,6 +2114,7 @@ binder::Status InstalldNativeService::freeCache(const std::optional<std::string> cleared += item->size; } if (!defy_target) { // Verify that we're actually done before bailing, since sneaky // apps might be using hardlinks if (needed <= 0) { Loading @@ -2085,12 +2127,14 @@ binder::Status InstalldNativeService::freeCache(const std::optional<std::string> } } } } ATRACE_END(); } else { return error("Legacy cache logic no longer supported"); } if (!defy_target) { free = data_disk_free(data_path); if (free >= targetFreeBytes) { return ok(); Loading @@ -2098,6 +2142,9 @@ binder::Status InstalldNativeService::freeCache(const std::optional<std::string> return error(StringPrintf("Failed to free up %" PRId64 " on %s; final free space %" PRId64, targetFreeBytes, data_path.c_str(), free)); } } else { return ok(); } } binder::Status InstalldNativeService::rmdex(const std::string& codePath, Loading Loading @@ -2149,6 +2196,7 @@ static std::string toString(std::vector<int64_t> values) { return res.str(); } #endif // On devices without sdcardfs, if internal and external are on // the same volume, a uid such as u0_a123 is used for both // internal and external storage; therefore, subtract that Loading Loading @@ -2362,6 +2410,7 @@ static bool ownsExternalStorage(int32_t appId) { if (internal_storage_has_project_id()) { return false; } // Fetch external storage owner appid and check if it is the same as the // current appId whose size is calculated struct stat s; Loading Loading @@ -2986,13 +3035,15 @@ binder::Status InstalldNativeService::setAppQuota(const std::optional<std::strin // Dumps the contents of a profile file, using pkgname's dex files for pretty // printing the result. binder::Status InstalldNativeService::dumpProfiles(int32_t uid, const std::string& packageName, const std::string& profileName, const std::string& codePath, bool* _aidl_return) { const std::string& profileName, const std::string& codePath, bool dumpClassesAndMethods, bool* _aidl_return) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_PACKAGE_NAME(packageName); CHECK_ARGUMENT_PATH(codePath); LOCK_PACKAGE(); *_aidl_return = dump_profiles(uid, packageName, profileName, codePath); *_aidl_return = dump_profiles(uid, packageName, profileName, codePath, dumpClassesAndMethods); return ok(); } Loading Loading @@ -3058,22 +3109,20 @@ static const char* getCStr(const std::optional<std::string>& data, const char* default_value = nullptr) { return data ? data->c_str() : default_value; } binder::Status InstalldNativeService::dexopt(const std::string& apkPath, int32_t uid, const std::optional<std::string>& packageName, const std::string& instructionSet, int32_t dexoptNeeded, const std::optional<std::string>& outputPath, int32_t dexFlags, binder::Status InstalldNativeService::dexopt( const std::string& apkPath, int32_t uid, const std::string& packageName, const std::string& instructionSet, int32_t dexoptNeeded, const std::optional<std::string>& outputPath, int32_t dexFlags, const std::string& compilerFilter, const std::optional<std::string>& uuid, const std::optional<std::string>& classLoaderContext, const std::optional<std::string>& seInfo, bool downgrade, int32_t targetSdkVersion, const std::optional<std::string>& profileName, const std::optional<std::string>& dexMetadataPath, const std::optional<std::string>& compilationReason, bool* aidl_return) { const std::optional<std::string>& compilationReason, bool* aidl_return) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_UUID(uuid); CHECK_ARGUMENT_PATH(apkPath); if (packageName && *packageName != "*") { CHECK_ARGUMENT_PACKAGE_NAME(*packageName); } CHECK_ARGUMENT_PACKAGE_NAME(packageName); CHECK_ARGUMENT_PATH(outputPath); CHECK_ARGUMENT_PATH(dexMetadataPath); const auto userId = multiuser_get_user_id(uid); Loading @@ -3081,13 +3130,13 @@ binder::Status InstalldNativeService::dexopt(const std::string& apkPath, int32_t const char* oat_dir = getCStr(outputPath); const char* instruction_set = instructionSet.c_str(); if (oat_dir != nullptr && !createOatDir(oat_dir, instruction_set).isOk()) { if (oat_dir != nullptr && !createOatDir(packageName, oat_dir, instruction_set).isOk()) { // Can't create oat dir - let dexopt use cache dir. oat_dir = nullptr; } const char* apk_path = apkPath.c_str(); const char* pkgname = getCStr(packageName, "*"); const char* pkgname = packageName.c_str(); const char* compiler_filter = compilerFilter.c_str(); const char* volume_uuid = getCStr(uuid); const char* class_loader_context = getCStr(classLoaderContext); Loading Loading @@ -3297,9 +3346,11 @@ binder::Status InstalldNativeService::restoreconSdkDataLocked( return res; } binder::Status InstalldNativeService::createOatDir(const std::string& oatDir, binder::Status InstalldNativeService::createOatDir(const std::string& packageName, const std::string& oatDir, const std::string& instructionSet) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_PACKAGE_NAME(packageName); CHECK_ARGUMENT_PATH(oatDir); LOCK_PACKAGE(); Loading @@ -3323,7 +3374,8 @@ binder::Status InstalldNativeService::createOatDir(const std::string& oatDir, return ok(); } binder::Status InstalldNativeService::rmPackageDir(const std::string& packageDir) { binder::Status InstalldNativeService::rmPackageDir(const std::string& packageName, const std::string& packageDir) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_PATH(packageDir); LOCK_PACKAGE(); Loading @@ -3337,9 +3389,12 @@ binder::Status InstalldNativeService::rmPackageDir(const std::string& packageDir return ok(); } binder::Status InstalldNativeService::linkFile(const std::string& relativePath, const std::string& fromBase, const std::string& toBase) { binder::Status InstalldNativeService::linkFile(const std::string& packageName, const std::string& relativePath, const std::string& fromBase, const std::string& toBase) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_PACKAGE_NAME(packageName); CHECK_ARGUMENT_PATH(fromBase); CHECK_ARGUMENT_PATH(toBase); LOCK_PACKAGE(); Loading Loading @@ -3367,9 +3422,12 @@ binder::Status InstalldNativeService::linkFile(const std::string& relativePath, return ok(); } binder::Status InstalldNativeService::moveAb(const std::string& apkPath, const std::string& instructionSet, const std::string& outputPath) { binder::Status InstalldNativeService::moveAb(const std::string& packageName, const std::string& apkPath, const std::string& instructionSet, const std::string& outputPath) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_PACKAGE_NAME(packageName); CHECK_ARGUMENT_PATH(apkPath); CHECK_ARGUMENT_PATH(outputPath); LOCK_PACKAGE(); Loading @@ -3382,10 +3440,13 @@ binder::Status InstalldNativeService::moveAb(const std::string& apkPath, return success ? ok() : error(); } binder::Status InstalldNativeService::deleteOdex(const std::string& apkPath, const std::string& instructionSet, const std::optional<std::string>& outputPath, binder::Status InstalldNativeService::deleteOdex(const std::string& packageName, const std::string& apkPath, const std::string& instructionSet, const std::optional<std::string>& outputPath, int64_t* _aidl_return) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_PACKAGE_NAME(packageName); CHECK_ARGUMENT_PATH(apkPath); CHECK_ARGUMENT_PATH(outputPath); LOCK_PACKAGE(); Loading Loading @@ -3430,15 +3491,20 @@ binder::Status InstalldNativeService::hashSecondaryDexFile( dexPath, packageName, uid, volumeUuid, storageFlag, _aidl_return); return result ? ok() : error(); } /** * Returns true if ioctl feature (F2FS_IOC_FS{GET,SET}XATTR) is supported as * these were introduced in Linux 4.14, so kernel versions before that will fail * while setting project id attributes. Only when these features are enabled, * storage calculation using project_id is enabled */ bool check_if_ioctl_feature_is_supported() { bool result = false; auto temp_path = StringPrintf("%smisc/installd/ioctl_check", android_data_dir.c_str()); if (access(temp_path.c_str(), F_OK) != 0) { open(temp_path.c_str(), O_CREAT | O_TRUNC | O_RDWR | O_CLOEXEC, 0644); int fd = open(temp_path.c_str(), O_CREAT | O_TRUNC | O_RDWR | O_CLOEXEC, 0644); result = set_quota_project_id(temp_path, 0, false) == 0; close(fd); // delete the temp file // remove the external file remove(temp_path.c_str()); } return result; Loading @@ -3452,7 +3518,7 @@ binder::Status InstalldNativeService::setFirstBoot() { auto first_boot_path = StringPrintf("%smisc/installd/using_project_ids", android_data_dir.c_str()); if (access(first_boot_path.c_str(), F_OK) != 0) { open(first_boot_path.c_str(), O_CREAT | O_TRUNC | O_RDWR | O_CLOEXEC, 0644); close(open(first_boot_path.c_str(), O_CREAT | O_TRUNC | O_RDWR | O_CLOEXEC, 0644)); } } return ok(); Loading Loading @@ -3677,5 +3743,23 @@ binder::Status InstalldNativeService::cleanupInvalidPackageDirs( return ok(); } binder::Status InstalldNativeService::getOdexVisibility( const std::string& packageName, const std::string& apkPath, const std::string& instructionSet, const std::optional<std::string>& outputPath, int32_t* _aidl_return) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_PACKAGE_NAME(packageName); CHECK_ARGUMENT_PATH(apkPath); CHECK_ARGUMENT_PATH(outputPath); LOCK_PACKAGE(); const char* apk_path = apkPath.c_str(); const char* instruction_set = instructionSet.c_str(); const char* oat_dir = outputPath ? outputPath->c_str() : nullptr; *_aidl_return = get_odex_visibility(apk_path, instruction_set, oat_dir); return *_aidl_return == -1 ? error() : ok(); } } // namespace installd } // namespace android cmds/installd/InstalldNativeService.h +29 −20 Original line number Diff line number Diff line Loading @@ -114,16 +114,15 @@ public: int32_t appId, const std::string& seInfo, int32_t targetSdkVersion, const std::string& fromCodePath); binder::Status dexopt(const std::string& apkPath, int32_t uid, const std::optional<std::string>& packageName, const std::string& instructionSet, int32_t dexoptNeeded, const std::optional<std::string>& outputPath, int32_t dexFlags, binder::Status dexopt(const std::string& apkPath, int32_t uid, const std::string& packageName, const std::string& instructionSet, int32_t dexoptNeeded, const std::optional<std::string>& outputPath, int32_t dexFlags, const std::string& compilerFilter, const std::optional<std::string>& uuid, const std::optional<std::string>& classLoaderContext, const std::optional<std::string>& seInfo, bool downgrade, int32_t targetSdkVersion, const std::optional<std::string>& profileName, const std::optional<std::string>& dexMetadataPath, const std::optional<std::string>& compilationReason, bool* aidl_return); const std::optional<std::string>& compilationReason, bool* aidl_return); binder::Status controlDexOptBlocking(bool block); Loading @@ -135,29 +134,34 @@ public: binder::Status mergeProfiles(int32_t uid, const std::string& packageName, const std::string& profileName, int* _aidl_return); binder::Status dumpProfiles(int32_t uid, const std::string& packageName, const std::string& profileName, const std::string& codePath, bool* _aidl_return); const std::string& profileName, const std::string& codePath, bool dumpClassesAndMethods, bool* _aidl_return); binder::Status copySystemProfile(const std::string& systemProfile, int32_t uid, const std::string& packageName, const std::string& profileName, bool* _aidl_return); binder::Status clearAppProfiles(const std::string& packageName, const std::string& profileName); binder::Status destroyAppProfiles(const std::string& packageName); binder::Status deleteReferenceProfile(const std::string& packageName, const std::string& profileName); binder::Status createProfileSnapshot(int32_t appId, const std::string& packageName, const std::string& profileName, const std::string& classpath, bool* _aidl_return); binder::Status destroyProfileSnapshot(const std::string& packageName, const std::string& profileName); binder::Status rmPackageDir(const std::string& packageDir); binder::Status rmPackageDir(const std::string& packageName, const std::string& packageDir); binder::Status freeCache(const std::optional<std::string>& uuid, int64_t targetFreeBytes, int64_t cacheReservedBytes, int32_t flags); int32_t flags); binder::Status linkNativeLibraryDirectory(const std::optional<std::string>& uuid, const std::string& packageName, const std::string& nativeLibPath32, int32_t userId); binder::Status createOatDir(const std::string& oatDir, const std::string& instructionSet); binder::Status linkFile(const std::string& relativePath, const std::string& fromBase, const std::string& toBase); binder::Status moveAb(const std::string& apkPath, const std::string& instructionSet, const std::string& outputPath); binder::Status deleteOdex(const std::string& apkPath, const std::string& instructionSet, binder::Status createOatDir(const std::string& packageName, const std::string& oatDir, const std::string& instructionSet); binder::Status linkFile(const std::string& packageName, const std::string& relativePath, const std::string& fromBase, const std::string& toBase); binder::Status moveAb(const std::string& packageName, const std::string& apkPath, const std::string& instructionSet, const std::string& outputPath); binder::Status deleteOdex(const std::string& packageName, const std::string& apkPath, const std::string& instructionSet, const std::optional<std::string>& outputPath, int64_t* _aidl_return); binder::Status reconcileSecondaryDexFile(const std::string& dexPath, const std::string& packageName, int32_t uid, const std::vector<std::string>& isa, Loading @@ -183,6 +187,11 @@ public: binder::Status cleanupInvalidPackageDirs(const std::optional<std::string>& uuid, int32_t userId, int32_t flags); binder::Status getOdexVisibility(const std::string& packageName, const std::string& apkPath, const std::string& instructionSet, const std::optional<std::string>& outputPath, int32_t* _aidl_return); private: std::recursive_mutex mLock; std::unordered_map<userid_t, std::weak_ptr<std::shared_mutex>> mUserIdLock; Loading Loading
PREUPLOAD.cfg +1 −0 Original line number Diff line number Diff line Loading @@ -30,6 +30,7 @@ clang_format = --commit ${PREUPLOAD_COMMIT} --style file --extensions c,h,cc,cpp services/vibratorservice/ services/vr/ vulkan/ bpfmt = -d [Hook Scripts] owners_hook = ${REPO_ROOT}/frameworks/base/tools/aosp/aosp_sha.sh ${PREUPLOAD_COMMIT} "OWNERS$" Loading
cmds/atrace/atrace.cpp +1 −0 Original line number Diff line number Diff line Loading @@ -244,6 +244,7 @@ static const TracingCategory k_categories[] = { { OPT, "events/kmem/ion_heap_shrink/enable" }, { OPT, "events/ion/ion_stat/enable" }, { OPT, "events/gpu_mem/gpu_mem_total/enable" }, { OPT, "events/fastrpc/fastrpc_dma_stat/enable" }, } }, { "thermal", "Thermal event", ATRACE_TAG_THERMAL, { { REQ, "events/thermal/thermal_temperature/enable" }, Loading
cmds/atrace/atrace.rc +2 −0 Original line number Diff line number Diff line Loading @@ -63,6 +63,8 @@ on late-init chmod 0666 /sys/kernel/tracing/events/cpuhp/cpuhp_pause/enable chmod 0666 /sys/kernel/debug/tracing/events/power/gpu_frequency/enable chmod 0666 /sys/kernel/tracing/events/power/gpu_frequency/enable chmod 0666 /sys/kernel/debug/tracing/events/power/gpu_work_period/enable chmod 0666 /sys/kernel/tracing/events/power/gpu_work_period/enable chmod 0666 /sys/kernel/debug/tracing/events/power/suspend_resume/enable chmod 0666 /sys/kernel/tracing/events/power/suspend_resume/enable chmod 0666 /sys/kernel/debug/tracing/events/cpufreq_interactive/enable Loading
cmds/installd/InstalldNativeService.cpp +140 −56 Original line number Diff line number Diff line Loading @@ -80,7 +80,7 @@ #define LOG_TAG "installd" #endif // #define GRANULAR_LOCKS #define GRANULAR_LOCKS using android::base::ParseUint; using android::base::Split; Loading Loading @@ -485,7 +485,6 @@ done: free(after); return res; } static bool internal_storage_has_project_id() { // The following path is populated in setFirstBoot, so if this file is present // then project ids can be used. Using call once to cache the result of this check Loading Loading @@ -1204,6 +1203,25 @@ binder::Status InstalldNativeService::destroyAppProfiles(const std::string& pack return res; } binder::Status InstalldNativeService::deleteReferenceProfile(const std::string& packageName, const std::string& profileName) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_PACKAGE_NAME(packageName); LOCK_PACKAGE(); // This function only supports primary dex'es. std::string path = create_reference_profile_path(packageName, profileName, /*is_secondary_dex=*/false); if (unlink(path.c_str()) != 0) { if (errno == ENOENT) { return ok(); } else { return error("Failed to delete profile " + profileName + " for " + packageName); } } return ok(); } binder::Status InstalldNativeService::destroyAppData(const std::optional<std::string>& uuid, const std::string& packageName, int32_t userId, int32_t flags, int64_t ceDataInode) { ENFORCE_UID(AID_SYSTEM); Loading Loading @@ -1919,7 +1937,7 @@ binder::Status InstalldNativeService::destroyUserData(const std::optional<std::s } binder::Status InstalldNativeService::freeCache(const std::optional<std::string>& uuid, int64_t targetFreeBytes, int64_t cacheReservedBytes, int32_t flags) { int64_t targetFreeBytes, int32_t flags) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_UUID(uuid); #ifndef GRANULAR_LOCKS Loading @@ -1930,6 +1948,7 @@ binder::Status InstalldNativeService::freeCache(const std::optional<std::string> const char* uuid_ = uuid ? uuid->c_str() : nullptr; auto data_path = create_data_path(uuid_); auto noop = (flags & FLAG_FREE_CACHE_NOOP); auto defy_target = (flags & FLAG_FREE_CACHE_DEFY_TARGET_FREE_BYTES); int64_t free = data_disk_free(data_path); if (free < 0) { Loading @@ -1938,12 +1957,14 @@ binder::Status InstalldNativeService::freeCache(const std::optional<std::string> int64_t cleared = 0; int64_t needed = targetFreeBytes - free; if (!defy_target) { LOG(DEBUG) << "Device " << data_path << " has " << free << " free; requested " << targetFreeBytes << "; needed " << needed; if (free >= targetFreeBytes) { return ok(); } } if (flags & FLAG_FREE_CACHE_V2) { // This new cache strategy fairly removes files from UIDs by deleting Loading @@ -1966,17 +1987,43 @@ binder::Status InstalldNativeService::freeCache(const std::optional<std::string> #endif // GRANULAR_LOCKS FTS *fts; FTSENT *p; // Create a list of data paths whose children have cache directories auto ce_path = create_data_user_ce_path(uuid_, userId); auto de_path = create_data_user_de_path(uuid_, userId); auto media_path = findDataMediaPath(uuid, userId) + "/Android/data/"; char *argv[] = { (char*) ce_path.c_str(), (char*) de_path.c_str(), (char*) media_path.c_str(), nullptr }; auto ce_sdk_path = create_data_misc_sdk_sandbox_path(uuid_, /*isCeData=*/true, userId); auto de_sdk_path = create_data_misc_sdk_sandbox_path(uuid_, /*isCeData=*/false, userId); std::vector<std::string> dataPaths = {ce_path, de_path, media_path}; foreach_subdir(ce_sdk_path, [&ce_sdk_path, &dataPaths](const std::string subDir) { const auto fullpath = ce_sdk_path + "/" + subDir; dataPaths.push_back(fullpath); }); foreach_subdir(de_sdk_path, [&de_sdk_path, &dataPaths](const std::string subDir) { const auto fullpath = de_sdk_path + "/" + subDir; dataPaths.push_back((char*)fullpath.c_str()); }); char* argv[dataPaths.size() + 1]; for (unsigned int i = 0; i < dataPaths.size(); i++) { argv[i] = (char*)dataPaths[i].c_str(); } argv[dataPaths.size()] = nullptr; if (!(fts = fts_open(argv, FTS_PHYSICAL | FTS_NOCHDIR | FTS_XDEV, nullptr))) { return error("Failed to fts_open"); } while ((p = fts_read(fts)) != nullptr) { if (p->fts_info == FTS_D && p->fts_level == 1) { uid_t uid = p->fts_statp->st_uid; // If uid belongs to sdk sandbox, then the cache should be attributed to the // original client app. const auto client_uid = multiuser_convert_sdk_sandbox_to_app_uid(uid); const bool isSandboxUid = (client_uid != (uid_t)-1); if (isSandboxUid) uid = client_uid; if (multiuser_get_app_id(uid) == AID_MEDIA_RW) { uid = (multiuser_get_app_id(p->fts_statp->st_gid) - AID_EXT_GID_START) + AID_APP_START; Loading Loading @@ -2035,12 +2082,6 @@ binder::Status InstalldNativeService::freeCache(const std::optional<std::string> break; } // Only keep clearing when we haven't pushed into reserved area if (cacheReservedBytes > 0 && cleared >= (cacheTotal - cacheReservedBytes)) { LOG(DEBUG) << "Refusing to clear cached data in reserved space"; break; } // Find the best tracker to work with; this might involve swapping // if the active tracker is no longer the most over quota bool nextBetter = active && !queue.empty() Loading Loading @@ -2073,6 +2114,7 @@ binder::Status InstalldNativeService::freeCache(const std::optional<std::string> cleared += item->size; } if (!defy_target) { // Verify that we're actually done before bailing, since sneaky // apps might be using hardlinks if (needed <= 0) { Loading @@ -2085,12 +2127,14 @@ binder::Status InstalldNativeService::freeCache(const std::optional<std::string> } } } } ATRACE_END(); } else { return error("Legacy cache logic no longer supported"); } if (!defy_target) { free = data_disk_free(data_path); if (free >= targetFreeBytes) { return ok(); Loading @@ -2098,6 +2142,9 @@ binder::Status InstalldNativeService::freeCache(const std::optional<std::string> return error(StringPrintf("Failed to free up %" PRId64 " on %s; final free space %" PRId64, targetFreeBytes, data_path.c_str(), free)); } } else { return ok(); } } binder::Status InstalldNativeService::rmdex(const std::string& codePath, Loading Loading @@ -2149,6 +2196,7 @@ static std::string toString(std::vector<int64_t> values) { return res.str(); } #endif // On devices without sdcardfs, if internal and external are on // the same volume, a uid such as u0_a123 is used for both // internal and external storage; therefore, subtract that Loading Loading @@ -2362,6 +2410,7 @@ static bool ownsExternalStorage(int32_t appId) { if (internal_storage_has_project_id()) { return false; } // Fetch external storage owner appid and check if it is the same as the // current appId whose size is calculated struct stat s; Loading Loading @@ -2986,13 +3035,15 @@ binder::Status InstalldNativeService::setAppQuota(const std::optional<std::strin // Dumps the contents of a profile file, using pkgname's dex files for pretty // printing the result. binder::Status InstalldNativeService::dumpProfiles(int32_t uid, const std::string& packageName, const std::string& profileName, const std::string& codePath, bool* _aidl_return) { const std::string& profileName, const std::string& codePath, bool dumpClassesAndMethods, bool* _aidl_return) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_PACKAGE_NAME(packageName); CHECK_ARGUMENT_PATH(codePath); LOCK_PACKAGE(); *_aidl_return = dump_profiles(uid, packageName, profileName, codePath); *_aidl_return = dump_profiles(uid, packageName, profileName, codePath, dumpClassesAndMethods); return ok(); } Loading Loading @@ -3058,22 +3109,20 @@ static const char* getCStr(const std::optional<std::string>& data, const char* default_value = nullptr) { return data ? data->c_str() : default_value; } binder::Status InstalldNativeService::dexopt(const std::string& apkPath, int32_t uid, const std::optional<std::string>& packageName, const std::string& instructionSet, int32_t dexoptNeeded, const std::optional<std::string>& outputPath, int32_t dexFlags, binder::Status InstalldNativeService::dexopt( const std::string& apkPath, int32_t uid, const std::string& packageName, const std::string& instructionSet, int32_t dexoptNeeded, const std::optional<std::string>& outputPath, int32_t dexFlags, const std::string& compilerFilter, const std::optional<std::string>& uuid, const std::optional<std::string>& classLoaderContext, const std::optional<std::string>& seInfo, bool downgrade, int32_t targetSdkVersion, const std::optional<std::string>& profileName, const std::optional<std::string>& dexMetadataPath, const std::optional<std::string>& compilationReason, bool* aidl_return) { const std::optional<std::string>& compilationReason, bool* aidl_return) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_UUID(uuid); CHECK_ARGUMENT_PATH(apkPath); if (packageName && *packageName != "*") { CHECK_ARGUMENT_PACKAGE_NAME(*packageName); } CHECK_ARGUMENT_PACKAGE_NAME(packageName); CHECK_ARGUMENT_PATH(outputPath); CHECK_ARGUMENT_PATH(dexMetadataPath); const auto userId = multiuser_get_user_id(uid); Loading @@ -3081,13 +3130,13 @@ binder::Status InstalldNativeService::dexopt(const std::string& apkPath, int32_t const char* oat_dir = getCStr(outputPath); const char* instruction_set = instructionSet.c_str(); if (oat_dir != nullptr && !createOatDir(oat_dir, instruction_set).isOk()) { if (oat_dir != nullptr && !createOatDir(packageName, oat_dir, instruction_set).isOk()) { // Can't create oat dir - let dexopt use cache dir. oat_dir = nullptr; } const char* apk_path = apkPath.c_str(); const char* pkgname = getCStr(packageName, "*"); const char* pkgname = packageName.c_str(); const char* compiler_filter = compilerFilter.c_str(); const char* volume_uuid = getCStr(uuid); const char* class_loader_context = getCStr(classLoaderContext); Loading Loading @@ -3297,9 +3346,11 @@ binder::Status InstalldNativeService::restoreconSdkDataLocked( return res; } binder::Status InstalldNativeService::createOatDir(const std::string& oatDir, binder::Status InstalldNativeService::createOatDir(const std::string& packageName, const std::string& oatDir, const std::string& instructionSet) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_PACKAGE_NAME(packageName); CHECK_ARGUMENT_PATH(oatDir); LOCK_PACKAGE(); Loading @@ -3323,7 +3374,8 @@ binder::Status InstalldNativeService::createOatDir(const std::string& oatDir, return ok(); } binder::Status InstalldNativeService::rmPackageDir(const std::string& packageDir) { binder::Status InstalldNativeService::rmPackageDir(const std::string& packageName, const std::string& packageDir) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_PATH(packageDir); LOCK_PACKAGE(); Loading @@ -3337,9 +3389,12 @@ binder::Status InstalldNativeService::rmPackageDir(const std::string& packageDir return ok(); } binder::Status InstalldNativeService::linkFile(const std::string& relativePath, const std::string& fromBase, const std::string& toBase) { binder::Status InstalldNativeService::linkFile(const std::string& packageName, const std::string& relativePath, const std::string& fromBase, const std::string& toBase) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_PACKAGE_NAME(packageName); CHECK_ARGUMENT_PATH(fromBase); CHECK_ARGUMENT_PATH(toBase); LOCK_PACKAGE(); Loading Loading @@ -3367,9 +3422,12 @@ binder::Status InstalldNativeService::linkFile(const std::string& relativePath, return ok(); } binder::Status InstalldNativeService::moveAb(const std::string& apkPath, const std::string& instructionSet, const std::string& outputPath) { binder::Status InstalldNativeService::moveAb(const std::string& packageName, const std::string& apkPath, const std::string& instructionSet, const std::string& outputPath) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_PACKAGE_NAME(packageName); CHECK_ARGUMENT_PATH(apkPath); CHECK_ARGUMENT_PATH(outputPath); LOCK_PACKAGE(); Loading @@ -3382,10 +3440,13 @@ binder::Status InstalldNativeService::moveAb(const std::string& apkPath, return success ? ok() : error(); } binder::Status InstalldNativeService::deleteOdex(const std::string& apkPath, const std::string& instructionSet, const std::optional<std::string>& outputPath, binder::Status InstalldNativeService::deleteOdex(const std::string& packageName, const std::string& apkPath, const std::string& instructionSet, const std::optional<std::string>& outputPath, int64_t* _aidl_return) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_PACKAGE_NAME(packageName); CHECK_ARGUMENT_PATH(apkPath); CHECK_ARGUMENT_PATH(outputPath); LOCK_PACKAGE(); Loading Loading @@ -3430,15 +3491,20 @@ binder::Status InstalldNativeService::hashSecondaryDexFile( dexPath, packageName, uid, volumeUuid, storageFlag, _aidl_return); return result ? ok() : error(); } /** * Returns true if ioctl feature (F2FS_IOC_FS{GET,SET}XATTR) is supported as * these were introduced in Linux 4.14, so kernel versions before that will fail * while setting project id attributes. Only when these features are enabled, * storage calculation using project_id is enabled */ bool check_if_ioctl_feature_is_supported() { bool result = false; auto temp_path = StringPrintf("%smisc/installd/ioctl_check", android_data_dir.c_str()); if (access(temp_path.c_str(), F_OK) != 0) { open(temp_path.c_str(), O_CREAT | O_TRUNC | O_RDWR | O_CLOEXEC, 0644); int fd = open(temp_path.c_str(), O_CREAT | O_TRUNC | O_RDWR | O_CLOEXEC, 0644); result = set_quota_project_id(temp_path, 0, false) == 0; close(fd); // delete the temp file // remove the external file remove(temp_path.c_str()); } return result; Loading @@ -3452,7 +3518,7 @@ binder::Status InstalldNativeService::setFirstBoot() { auto first_boot_path = StringPrintf("%smisc/installd/using_project_ids", android_data_dir.c_str()); if (access(first_boot_path.c_str(), F_OK) != 0) { open(first_boot_path.c_str(), O_CREAT | O_TRUNC | O_RDWR | O_CLOEXEC, 0644); close(open(first_boot_path.c_str(), O_CREAT | O_TRUNC | O_RDWR | O_CLOEXEC, 0644)); } } return ok(); Loading Loading @@ -3677,5 +3743,23 @@ binder::Status InstalldNativeService::cleanupInvalidPackageDirs( return ok(); } binder::Status InstalldNativeService::getOdexVisibility( const std::string& packageName, const std::string& apkPath, const std::string& instructionSet, const std::optional<std::string>& outputPath, int32_t* _aidl_return) { ENFORCE_UID(AID_SYSTEM); CHECK_ARGUMENT_PACKAGE_NAME(packageName); CHECK_ARGUMENT_PATH(apkPath); CHECK_ARGUMENT_PATH(outputPath); LOCK_PACKAGE(); const char* apk_path = apkPath.c_str(); const char* instruction_set = instructionSet.c_str(); const char* oat_dir = outputPath ? outputPath->c_str() : nullptr; *_aidl_return = get_odex_visibility(apk_path, instruction_set, oat_dir); return *_aidl_return == -1 ? error() : ok(); } } // namespace installd } // namespace android
cmds/installd/InstalldNativeService.h +29 −20 Original line number Diff line number Diff line Loading @@ -114,16 +114,15 @@ public: int32_t appId, const std::string& seInfo, int32_t targetSdkVersion, const std::string& fromCodePath); binder::Status dexopt(const std::string& apkPath, int32_t uid, const std::optional<std::string>& packageName, const std::string& instructionSet, int32_t dexoptNeeded, const std::optional<std::string>& outputPath, int32_t dexFlags, binder::Status dexopt(const std::string& apkPath, int32_t uid, const std::string& packageName, const std::string& instructionSet, int32_t dexoptNeeded, const std::optional<std::string>& outputPath, int32_t dexFlags, const std::string& compilerFilter, const std::optional<std::string>& uuid, const std::optional<std::string>& classLoaderContext, const std::optional<std::string>& seInfo, bool downgrade, int32_t targetSdkVersion, const std::optional<std::string>& profileName, const std::optional<std::string>& dexMetadataPath, const std::optional<std::string>& compilationReason, bool* aidl_return); const std::optional<std::string>& compilationReason, bool* aidl_return); binder::Status controlDexOptBlocking(bool block); Loading @@ -135,29 +134,34 @@ public: binder::Status mergeProfiles(int32_t uid, const std::string& packageName, const std::string& profileName, int* _aidl_return); binder::Status dumpProfiles(int32_t uid, const std::string& packageName, const std::string& profileName, const std::string& codePath, bool* _aidl_return); const std::string& profileName, const std::string& codePath, bool dumpClassesAndMethods, bool* _aidl_return); binder::Status copySystemProfile(const std::string& systemProfile, int32_t uid, const std::string& packageName, const std::string& profileName, bool* _aidl_return); binder::Status clearAppProfiles(const std::string& packageName, const std::string& profileName); binder::Status destroyAppProfiles(const std::string& packageName); binder::Status deleteReferenceProfile(const std::string& packageName, const std::string& profileName); binder::Status createProfileSnapshot(int32_t appId, const std::string& packageName, const std::string& profileName, const std::string& classpath, bool* _aidl_return); binder::Status destroyProfileSnapshot(const std::string& packageName, const std::string& profileName); binder::Status rmPackageDir(const std::string& packageDir); binder::Status rmPackageDir(const std::string& packageName, const std::string& packageDir); binder::Status freeCache(const std::optional<std::string>& uuid, int64_t targetFreeBytes, int64_t cacheReservedBytes, int32_t flags); int32_t flags); binder::Status linkNativeLibraryDirectory(const std::optional<std::string>& uuid, const std::string& packageName, const std::string& nativeLibPath32, int32_t userId); binder::Status createOatDir(const std::string& oatDir, const std::string& instructionSet); binder::Status linkFile(const std::string& relativePath, const std::string& fromBase, const std::string& toBase); binder::Status moveAb(const std::string& apkPath, const std::string& instructionSet, const std::string& outputPath); binder::Status deleteOdex(const std::string& apkPath, const std::string& instructionSet, binder::Status createOatDir(const std::string& packageName, const std::string& oatDir, const std::string& instructionSet); binder::Status linkFile(const std::string& packageName, const std::string& relativePath, const std::string& fromBase, const std::string& toBase); binder::Status moveAb(const std::string& packageName, const std::string& apkPath, const std::string& instructionSet, const std::string& outputPath); binder::Status deleteOdex(const std::string& packageName, const std::string& apkPath, const std::string& instructionSet, const std::optional<std::string>& outputPath, int64_t* _aidl_return); binder::Status reconcileSecondaryDexFile(const std::string& dexPath, const std::string& packageName, int32_t uid, const std::vector<std::string>& isa, Loading @@ -183,6 +187,11 @@ public: binder::Status cleanupInvalidPackageDirs(const std::optional<std::string>& uuid, int32_t userId, int32_t flags); binder::Status getOdexVisibility(const std::string& packageName, const std::string& apkPath, const std::string& instructionSet, const std::optional<std::string>& outputPath, int32_t* _aidl_return); private: std::recursive_mutex mLock; std::unordered_map<userid_t, std::weak_ptr<std::shared_mutex>> mUserIdLock; Loading