From: Nicolas Geoffray Date: Mon, 5 Jun 2017 12:38:10 +0000 (+0000) Subject: Revert "Disable in-place vdex update" X-Git-Tag: android-x86-9.0-r1~245^2~1^2^2~5^2~10^2 X-Git-Url: http://git.osdn.net/view?a=commitdiff_plain;h=b03814f39559c824e097bf2d869c7a56d8b41b67;p=android-x86%2Fframeworks-native.git Revert "Disable in-place vdex update" Reverting to only apply this when doing dexlayout. PS1 is a pure revert. PS2 contains the fix. This reverts commit e446fede9258359b61d4c8753d7e96477fa29388. Change-Id: I04a7dbde142d59e8dcdf4e93ab0456c4aa3d02ab --- diff --git a/cmds/installd/dexopt.cpp b/cmds/installd/dexopt.cpp index 840bb096c7..f683dfa0c8 100644 --- a/cmds/installd/dexopt.cpp +++ b/cmds/installd/dexopt.cpp @@ -1161,7 +1161,7 @@ Dex2oatFileWrapper maybe_open_reference_profile(const std::string& pkgname, // out_vdex_wrapper_fd. Returns true for success or false in case of errors. bool open_vdex_files(const char* apk_path, const char* out_oat_path, int dexopt_needed, const char* instruction_set, bool is_public, int uid, bool is_secondary_dex, - Dex2oatFileWrapper* in_vdex_wrapper_fd, + bool profile_guided, Dex2oatFileWrapper* in_vdex_wrapper_fd, Dex2oatFileWrapper* out_vdex_wrapper_fd) { CHECK(in_vdex_wrapper_fd != nullptr); CHECK(out_vdex_wrapper_fd != nullptr); @@ -1171,6 +1171,14 @@ bool open_vdex_files(const char* apk_path, const char* out_oat_path, int dexopt_ int dexopt_action = abs(dexopt_needed); bool is_odex_location = dexopt_needed < 0; std::string in_vdex_path_str; + + // Infer the name of the output VDEX. + const std::string out_vdex_path_str = create_vdex_filename(out_oat_path); + if (out_vdex_path_str.empty()) { + return false; + } + + bool update_vdex_in_place = false; if (dexopt_action != DEX2OAT_FROM_SCRATCH) { // Open the possibly existing vdex. If none exist, we pass -1 to dex2oat for input-vdex-fd. const char* path = nullptr; @@ -1189,21 +1197,48 @@ bool open_vdex_files(const char* apk_path, const char* out_oat_path, int dexopt_ ALOGE("installd cannot compute input vdex location for '%s'\n", path); return false; } - in_vdex_wrapper_fd->reset(open(in_vdex_path_str.c_str(), O_RDONLY, 0)); - } - - // Infer the name of the output VDEX and create it. - const std::string out_vdex_path_str = create_vdex_filename(out_oat_path); - if (out_vdex_path_str.empty()) { - return false; + // We can update in place when all these conditions are met: + // 1) The vdex location to write to is the same as the vdex location to read (vdex files + // on /system typically cannot be updated in place). + // 2) We dex2oat due to boot image change, because we then know the existing vdex file + // cannot be currently used by a running process. + // 3) We are not doing a profile guided compilation, because dexlayout requires two + // different vdex files to operate. + update_vdex_in_place = + (in_vdex_path_str == out_vdex_path_str) && + (dexopt_action == DEX2OAT_FOR_BOOT_IMAGE) && + !profile_guided; + if (update_vdex_in_place) { + // Open the file read-write to be able to update it. + in_vdex_wrapper_fd->reset(open(in_vdex_path_str.c_str(), O_RDWR, 0)); + if (in_vdex_wrapper_fd->get() == -1) { + // If we failed to open the file, we cannot update it in place. + update_vdex_in_place = false; + } + } else { + in_vdex_wrapper_fd->reset(open(in_vdex_path_str.c_str(), O_RDONLY, 0)); + } } - out_vdex_wrapper_fd->reset( - open_output_file(out_vdex_path_str.c_str(), /*recreate*/true, /*permissions*/0644), - [out_vdex_path_str]() { unlink(out_vdex_path_str.c_str()); }); - if (out_vdex_wrapper_fd->get() < 0) { - ALOGE("installd cannot open vdex'%s' during dexopt\n", out_vdex_path_str.c_str()); - return false; + // If we are updating the vdex in place, we do not need to recreate a vdex, + // and can use the same existing one. + if (update_vdex_in_place) { + // We unlink the file in case the invocation of dex2oat fails, to ensure we don't + // have bogus stale vdex files. + out_vdex_wrapper_fd->reset( + in_vdex_wrapper_fd->get(), + [out_vdex_path_str]() { unlink(out_vdex_path_str.c_str()); }); + // Disable auto close for the in wrapper fd (it will be done when destructing the out + // wrapper). + in_vdex_wrapper_fd->DisableAutoClose(); + } else { + out_vdex_wrapper_fd->reset( + open_output_file(out_vdex_path_str.c_str(), /*recreate*/true, /*permissions*/0644), + [out_vdex_path_str]() { unlink(out_vdex_path_str.c_str()); }); + if (out_vdex_wrapper_fd->get() < 0) { + ALOGE("installd cannot open vdex'%s' during dexopt\n", out_vdex_path_str.c_str()); + return false; + } } if (!set_permissions_and_ownership(out_vdex_wrapper_fd->get(), is_public, uid, out_vdex_path_str.c_str(), is_secondary_dex)) { @@ -1513,7 +1548,7 @@ int dexopt(const char* dex_path, uid_t uid, const char* pkgname, const char* ins Dex2oatFileWrapper in_vdex_fd; Dex2oatFileWrapper out_vdex_fd; if (!open_vdex_files(dex_path, out_oat_path, dexopt_needed, instruction_set, is_public, uid, - is_secondary_dex, &in_vdex_fd, &out_vdex_fd)) { + is_secondary_dex, profile_guided, &in_vdex_fd, &out_vdex_fd)) { return -1; }