Loading cmds/installd/InstalldNativeService.cpp +26 −17 Original line number Diff line number Diff line Loading @@ -1602,6 +1602,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 @@ -1610,12 +1611,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 Loading @@ -1739,6 +1742,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 @@ -1751,12 +1755,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 @@ -1764,6 +1770,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 cmds/installd/binder/android/os/IInstalld.aidl +2 −0 Original line number Diff line number Diff line Loading @@ -140,6 +140,8 @@ interface IInstalld { const int FLAG_FREE_CACHE_V2 = 0x100; const int FLAG_FREE_CACHE_V2_DEFY_QUOTA = 0x200; const int FLAG_FREE_CACHE_NOOP = 0x400; // Set below flag to clear cache irrespective of target free bytes required const int FLAG_FREE_CACHE_DEFY_TARGET_FREE_BYTES = 0x800; const int FLAG_USE_QUOTA = 0x1000; const int FLAG_FORCE = 0x2000; Loading cmds/installd/tests/installd_cache_test.cpp +30 −0 Original line number Diff line number Diff line Loading @@ -42,6 +42,7 @@ constexpr int64_t kTbInBytes = 1024 * kGbInBytes; #define FLAG_FREE_CACHE_V2 InstalldNativeService::FLAG_FREE_CACHE_V2 #define FLAG_FREE_CACHE_V2_DEFY_QUOTA InstalldNativeService::FLAG_FREE_CACHE_V2_DEFY_QUOTA #define FLAG_FREE_CACHE_DEFY_TARGET_FREE_BYTES InstalldNativeService::FLAG_FREE_CACHE_DEFY_TARGET_FREE_BYTES int get_property(const char *key, char *value, const char *default_value) { return property_get(key, value, default_value); Loading Loading @@ -181,6 +182,35 @@ TEST_F(CacheTest, FreeCache_NonAggressive) { EXPECT_EQ(0, exists("com.example/cache/foo/two")); } TEST_F(CacheTest, FreeCache_DefyTargetFreeBytes) { LOG(INFO) << "FreeCache_DefyTargetFreeBytes"; mkdir("com.example"); touch("com.example/normal", 1 * kMbInBytes, 60); mkdir("com.example/cache"); mkdir("com.example/cache/foo"); touch("com.example/cache/foo/one", 65 * kMbInBytes, 60); touch("com.example/cache/foo/two", 2 * kMbInBytes, 120); EXPECT_EQ(0, exists("com.example/normal")); EXPECT_EQ(0, exists("com.example/cache/foo/one")); EXPECT_EQ(0, exists("com.example/cache/foo/two")); service->freeCache(testUuid, kMbInBytes, FLAG_FREE_CACHE_V2 | FLAG_FREE_CACHE_DEFY_TARGET_FREE_BYTES); EXPECT_EQ(0, exists("com.example/normal")); EXPECT_EQ(-1, exists("com.example/cache/foo/one")); EXPECT_EQ(0, exists("com.example/cache/foo/two")); service->freeCache(testUuid, kMbInBytes, FLAG_FREE_CACHE_V2 | FLAG_FREE_CACHE_DEFY_TARGET_FREE_BYTES); EXPECT_EQ(0, exists("com.example/normal")); EXPECT_EQ(-1, exists("com.example/cache/foo/one")); EXPECT_EQ(0, exists("com.example/cache/foo/two")); } TEST_F(CacheTest, FreeCache_Age) { LOG(INFO) << "FreeCache_Age"; Loading Loading
cmds/installd/InstalldNativeService.cpp +26 −17 Original line number Diff line number Diff line Loading @@ -1602,6 +1602,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 @@ -1610,12 +1611,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 Loading @@ -1739,6 +1742,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 @@ -1751,12 +1755,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 @@ -1764,6 +1770,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
cmds/installd/binder/android/os/IInstalld.aidl +2 −0 Original line number Diff line number Diff line Loading @@ -140,6 +140,8 @@ interface IInstalld { const int FLAG_FREE_CACHE_V2 = 0x100; const int FLAG_FREE_CACHE_V2_DEFY_QUOTA = 0x200; const int FLAG_FREE_CACHE_NOOP = 0x400; // Set below flag to clear cache irrespective of target free bytes required const int FLAG_FREE_CACHE_DEFY_TARGET_FREE_BYTES = 0x800; const int FLAG_USE_QUOTA = 0x1000; const int FLAG_FORCE = 0x2000; Loading
cmds/installd/tests/installd_cache_test.cpp +30 −0 Original line number Diff line number Diff line Loading @@ -42,6 +42,7 @@ constexpr int64_t kTbInBytes = 1024 * kGbInBytes; #define FLAG_FREE_CACHE_V2 InstalldNativeService::FLAG_FREE_CACHE_V2 #define FLAG_FREE_CACHE_V2_DEFY_QUOTA InstalldNativeService::FLAG_FREE_CACHE_V2_DEFY_QUOTA #define FLAG_FREE_CACHE_DEFY_TARGET_FREE_BYTES InstalldNativeService::FLAG_FREE_CACHE_DEFY_TARGET_FREE_BYTES int get_property(const char *key, char *value, const char *default_value) { return property_get(key, value, default_value); Loading Loading @@ -181,6 +182,35 @@ TEST_F(CacheTest, FreeCache_NonAggressive) { EXPECT_EQ(0, exists("com.example/cache/foo/two")); } TEST_F(CacheTest, FreeCache_DefyTargetFreeBytes) { LOG(INFO) << "FreeCache_DefyTargetFreeBytes"; mkdir("com.example"); touch("com.example/normal", 1 * kMbInBytes, 60); mkdir("com.example/cache"); mkdir("com.example/cache/foo"); touch("com.example/cache/foo/one", 65 * kMbInBytes, 60); touch("com.example/cache/foo/two", 2 * kMbInBytes, 120); EXPECT_EQ(0, exists("com.example/normal")); EXPECT_EQ(0, exists("com.example/cache/foo/one")); EXPECT_EQ(0, exists("com.example/cache/foo/two")); service->freeCache(testUuid, kMbInBytes, FLAG_FREE_CACHE_V2 | FLAG_FREE_CACHE_DEFY_TARGET_FREE_BYTES); EXPECT_EQ(0, exists("com.example/normal")); EXPECT_EQ(-1, exists("com.example/cache/foo/one")); EXPECT_EQ(0, exists("com.example/cache/foo/two")); service->freeCache(testUuid, kMbInBytes, FLAG_FREE_CACHE_V2 | FLAG_FREE_CACHE_DEFY_TARGET_FREE_BYTES); EXPECT_EQ(0, exists("com.example/normal")); EXPECT_EQ(-1, exists("com.example/cache/foo/one")); EXPECT_EQ(0, exists("com.example/cache/foo/two")); } TEST_F(CacheTest, FreeCache_Age) { LOG(INFO) << "FreeCache_Age"; Loading