diff options
author | 2022-01-05 16:41:02 +0000 | |
---|---|---|
committer | 2022-01-06 08:44:46 +0000 | |
commit | dcf9570d756aa74a2330406c13330c18c34e0db2 (patch) | |
tree | 7e927ba5ac2671dc721ea0b248a2f1e0064ce617 | |
parent | 8884d3dd47c7aa786d3b1ae0d3394f0b2adc5019 (diff) |
Revert "Remove old unquickening of vdex logic."
This reverts commit 537f477453823db37130f9c1562f328ad3360b6a.
Bug: 170086509
Reason for revert: Fails some tests.
Change-Id: I965884b5039f4bce42450091fce04d2c87129c02
-rw-r--r-- | dex2oat/dex2oat.cc | 73 | ||||
-rw-r--r-- | dex2oat/dex2oat_test.cc | 1 | ||||
-rw-r--r-- | dex2oat/dex2oat_vdex_test.cc | 1 | ||||
-rw-r--r-- | dex2oat/linker/oat_writer.cc | 34 | ||||
-rw-r--r-- | dex2oat/linker/oat_writer.h | 10 | ||||
-rw-r--r-- | dexlayout/dexdiag.cc | 1 | ||||
-rw-r--r-- | dexlayout/dexlayout.h | 3 | ||||
-rw-r--r-- | runtime/oat_file.cc | 23 | ||||
-rw-r--r-- | runtime/oat_file_assistant.cc | 2 | ||||
-rw-r--r-- | runtime/oat_file_manager.cc | 1 | ||||
-rw-r--r-- | runtime/vdex_file.cc | 4 | ||||
-rw-r--r-- | runtime/vdex_file.h | 6 | ||||
-rw-r--r-- | runtime/vdex_file_test.cc | 3 |
13 files changed, 110 insertions, 52 deletions
diff --git a/dex2oat/dex2oat.cc b/dex2oat/dex2oat.cc index 1486fadd47..81db30de1c 100644 --- a/dex2oat/dex2oat.cc +++ b/dex2oat/dex2oat.cc @@ -1237,6 +1237,7 @@ class Dex2Oat final { input_vdex_file_ = VdexFile::Open(input_vdex_, /* writable */ false, /* low_4gb */ false, + DoEagerUnquickeningOfVdex(), &error_msg); } @@ -1245,8 +1246,8 @@ class Dex2Oat final { ? ReplaceFileExtension(oat_filename, "vdex") : output_vdex_; if (vdex_filename == input_vdex_ && output_vdex_.empty()) { - use_existing_vdex_ = true; - std::unique_ptr<File> vdex_file(OS::OpenFileForReading(vdex_filename.c_str())); + update_input_vdex_ = true; + std::unique_ptr<File> vdex_file(OS::OpenFileReadWrite(vdex_filename.c_str())); vdex_files_.push_back(std::move(vdex_file)); } else { std::unique_ptr<File> vdex_file(OS::CreateEmptyFile(vdex_filename.c_str())); @@ -1288,6 +1289,7 @@ class Dex2Oat final { "vdex", /* writable */ false, /* low_4gb */ false, + DoEagerUnquickeningOfVdex(), &error_msg); // If there's any problem with the passed vdex, just warn and proceed // without it. @@ -1299,20 +1301,15 @@ class Dex2Oat final { DCHECK_NE(output_vdex_fd_, -1); std::string vdex_location = ReplaceFileExtension(oat_location_, "vdex"); - if (input_vdex_file_ != nullptr && output_vdex_fd_ == input_vdex_fd_) { - use_existing_vdex_ = true; - } - - std::unique_ptr<File> vdex_file(new File(DupCloexec(output_vdex_fd_), - vdex_location, - /* check_usage= */ true, - /* read_only_mode= */ use_existing_vdex_)); + std::unique_ptr<File> vdex_file(new File( + DupCloexec(output_vdex_fd_), vdex_location, /* check_usage */ true)); if (!vdex_file->IsOpened()) { PLOG(ERROR) << "Failed to create vdex file: " << vdex_location; return false; } - - if (!use_existing_vdex_) { + if (input_vdex_file_ != nullptr && output_vdex_fd_ == input_vdex_fd_) { + update_input_vdex_ = true; + } else { if (vdex_file->SetLength(0) != 0) { PLOG(ERROR) << "Truncating vdex file " << vdex_location << " failed."; vdex_file->Erase(); @@ -1324,6 +1321,26 @@ class Dex2Oat final { oat_filenames_.push_back(oat_location_); } + // If we're updating in place a vdex file, be defensive and put an invalid vdex magic in case + // dex2oat gets killed. + // Note: we're only invalidating the magic data in the file, as dex2oat needs the rest of + // the information to remain valid. + if (update_input_vdex_) { + File* vdex_file = vdex_files_.back().get(); + if (!vdex_file->PwriteFully(&VdexFile::VdexFileHeader::kVdexInvalidMagic, + arraysize(VdexFile::VdexFileHeader::kVdexInvalidMagic), + /*offset=*/ 0u)) { + PLOG(ERROR) << "Failed to invalidate vdex header. File: " << vdex_file->GetPath(); + return false; + } + + if (vdex_file->Flush() != 0) { + PLOG(ERROR) << "Failed to flush stream after invalidating header of vdex file." + << " File: " << vdex_file->GetPath(); + return false; + } + } + if (dm_fd_ != -1 || !dm_file_location_.empty()) { std::string error_msg; if (dm_fd_ != -1) { @@ -1372,12 +1389,9 @@ class Dex2Oat final { void EraseOutputFiles() { for (auto& files : { &vdex_files_, &oat_files_ }) { for (size_t i = 0; i < files->size(); ++i) { - auto& file = (*files)[i]; - if (file != nullptr) { - if (!file->ReadOnlyMode()) { - file->Erase(); - } - file.reset(); + if ((*files)[i].get() != nullptr) { + (*files)[i]->Erase(); + (*files)[i].reset(); } } } @@ -1441,7 +1455,7 @@ class Dex2Oat final { if (!oat_writers_[i]->WriteAndOpenDexFiles( vdex_files_[i].get(), verify, - use_existing_vdex_, + update_input_vdex_, copy_dex_files_, &opened_dex_files_map, &opened_dex_files)) { @@ -1690,15 +1704,12 @@ class Dex2Oat final { } // Setup VerifierDeps for compilation and report if we fail to parse the data. - // When we do profile guided optimizations, the compiler currently needs to run - // full verification. - if (!DoProfileGuidedOptimizations() && input_vdex_file_ != nullptr) { + if (!DoEagerUnquickeningOfVdex() && input_vdex_file_ != nullptr) { std::unique_ptr<verifier::VerifierDeps> verifier_deps( new verifier::VerifierDeps(dex_files, /*output_only=*/ false)); if (!verifier_deps->ParseStoredData(dex_files, input_vdex_file_->GetVerifierDepsData())) { return dex2oat::ReturnCode::kOther; } - // We can do fast verification. callbacks_->SetVerifierDeps(verifier_deps.release()); } else { // Create the main VerifierDeps, here instead of in the compiler since we want to aggregate @@ -1781,7 +1792,7 @@ class Dex2Oat final { // This means extract, no-vdex verify, and quicken, will use the individual compilation // mode (to reduce RAM used by the compiler). return compile_individually_ && - (!IsImage() && !use_existing_vdex_ && + (!IsImage() && !update_input_vdex_ && compiler_options_->dex_files_for_oat_file_.size() > 1 && !CompilerFilter::IsAotCompilationEnabled(compiler_options_->GetCompilerFilter())); } @@ -2058,7 +2069,7 @@ class Dex2Oat final { oat_writer->Initialize(driver_.get(), image_writer_.get(), dex_files); } - if (!use_existing_vdex_) { + { TimingLogger::ScopedTiming t2("dex2oat Write VDEX", timings_); DCHECK(IsBootImage() || IsBootImageExtension() || oat_files_.size() == 1u); verifier::VerifierDeps* verifier_deps = callbacks_->GetVerifierDeps(); @@ -2314,6 +2325,16 @@ class Dex2Oat final { return DoProfileGuidedOptimizations(); } + bool MayInvalidateVdexMetadata() const { + // DexLayout can invalidate the vdex metadata if changing the class def order is enabled, so + // we need to unquicken the vdex file eagerly, before passing it to dexlayout. + return DoDexLayoutOptimizations(); + } + + bool DoEagerUnquickeningOfVdex() const { + return MayInvalidateVdexMetadata() && dm_file_ == nullptr; + } + bool LoadProfile() { DCHECK(HasProfileInput()); profile_load_attempted_ = true; @@ -2908,7 +2929,7 @@ class Dex2Oat final { std::string classpath_dir_; // Whether the given input vdex is also the output. - bool use_existing_vdex_ = false; + bool update_input_vdex_ = false; // By default, copy the dex to the vdex file only if dex files are // compressed in APK. diff --git a/dex2oat/dex2oat_test.cc b/dex2oat/dex2oat_test.cc index 3cab12ded4..083e1c9967 100644 --- a/dex2oat/dex2oat_test.cc +++ b/dex2oat/dex2oat_test.cc @@ -1762,6 +1762,7 @@ TEST_F(Dex2oatTest, DontExtract) { std::unique_ptr<VdexFile> vdex(VdexFile::Open(vdex_location.c_str(), /*writable=*/ false, /*low_4gb=*/ false, + /*unquicken=*/ false, &error_msg)); ASSERT_TRUE(vdex != nullptr); EXPECT_FALSE(vdex->HasDexSection()) << output_; diff --git a/dex2oat/dex2oat_vdex_test.cc b/dex2oat/dex2oat_vdex_test.cc index 895e9c21e3..1f486e6aec 100644 --- a/dex2oat/dex2oat_vdex_test.cc +++ b/dex2oat/dex2oat_vdex_test.cc @@ -73,6 +73,7 @@ class Dex2oatVdexTest : public Dex2oatEnvironmentTest { std::unique_ptr<VdexFile> vdex(VdexFile::Open(vdex_location.c_str(), /*writable=*/ false, /*low_4gb=*/ false, + /*unquicken=*/ false, &error_msg_)); // Check the vdex doesn't have dex. if (vdex->HasDexSection()) { diff --git a/dex2oat/linker/oat_writer.cc b/dex2oat/linker/oat_writer.cc index 7e7bca57db..5ac2bbf487 100644 --- a/dex2oat/linker/oat_writer.cc +++ b/dex2oat/linker/oat_writer.cc @@ -683,7 +683,7 @@ bool OatWriter::MayHaveCompiledMethods() const { bool OatWriter::WriteAndOpenDexFiles( File* vdex_file, bool verify, - bool use_existing_vdex, + bool update_input_vdex, CopyOption copy_dex_files, /*out*/ std::vector<MemMap>* opened_dex_files_map, /*out*/ std::vector<std::unique_ptr<const DexFile>>* opened_dex_files) { @@ -697,7 +697,7 @@ bool OatWriter::WriteAndOpenDexFiles( // Write DEX files into VDEX, mmap and open them. std::vector<MemMap> dex_files_map; std::vector<std::unique_ptr<const DexFile>> dex_files; - if (!WriteDexFiles(vdex_file, use_existing_vdex, copy_dex_files, &dex_files_map) || + if (!WriteDexFiles(vdex_file, update_input_vdex, copy_dex_files, &dex_files_map) || !OpenDexFiles(vdex_file, verify, &dex_files_map, &dex_files)) { return false; } @@ -3103,7 +3103,7 @@ bool OatWriter::RecordOatDataOffset(OutputStream* out) { } bool OatWriter::WriteDexFiles(File* file, - bool use_existing_vdex, + bool update_input_vdex, CopyOption copy_dex_files, /*out*/ std::vector<MemMap>* opened_dex_files_map) { TimingLogger::ScopedTiming split("Write Dex files", timings_); @@ -3136,8 +3136,8 @@ bool OatWriter::WriteDexFiles(File* file, if (profile_compilation_info_ != nullptr || compact_dex_level_ != CompactDexLevel::kCompactDexLevelNone) { for (OatDexFile& oat_dex_file : oat_dex_files_) { - // use_existing_vdex should not be used with compact dex and layout. - CHECK(!use_existing_vdex) + // update_input_vdex disables compact dex and layout. + CHECK(!update_input_vdex) << "We should never update the input vdex when doing dexlayout or compact dex"; if (!LayoutDexFile(&oat_dex_file)) { return false; @@ -3202,7 +3202,7 @@ bool OatWriter::WriteDexFiles(File* file, // Extend the file and include the full page at the end as we need to write // additional data there and do not want to mmap that page twice. size_t page_aligned_size = RoundUp(vdex_size_with_dex_files, kPageSize); - if (!use_existing_vdex) { + if (!update_input_vdex) { if (file->SetLength(page_aligned_size) != 0) { PLOG(ERROR) << "Failed to resize vdex file " << file->GetPath(); return false; @@ -3233,7 +3233,7 @@ bool OatWriter::WriteDexFiles(File* file, vdex_size_ = RoundUp(vdex_size_, 4u); size_dex_file_alignment_ += vdex_size_ - old_vdex_size; // Write the actual dex file. - if (!WriteDexFile(file, &oat_dex_file, use_existing_vdex)) { + if (!WriteDexFile(file, &oat_dex_file, update_input_vdex)) { return false; } } @@ -3241,27 +3241,27 @@ bool OatWriter::WriteDexFiles(File* file, // Write shared dex file data section and fix up the dex file headers. if (shared_data_size != 0u) { DCHECK_EQ(RoundUp(vdex_size_, 4u), vdex_dex_shared_data_offset_); - if (!use_existing_vdex) { + if (!update_input_vdex) { memset(vdex_begin_ + vdex_size_, 0, vdex_dex_shared_data_offset_ - vdex_size_); } size_dex_file_alignment_ += vdex_dex_shared_data_offset_ - vdex_size_; vdex_size_ = vdex_dex_shared_data_offset_; if (dex_container_ != nullptr) { - CHECK(!use_existing_vdex) << "Use existing vdex should have empty dex container"; + CHECK(!update_input_vdex) << "Update input vdex should have empty dex container"; CHECK(compact_dex_level_ != CompactDexLevel::kCompactDexLevelNone); DexContainer::Section* const section = dex_container_->GetDataSection(); DCHECK_EQ(shared_data_size, section->Size()); memcpy(vdex_begin_ + vdex_size_, section->Begin(), shared_data_size); section->Clear(); dex_container_.reset(); - } else if (!use_existing_vdex) { + } else if (!update_input_vdex) { // If we are not updating the input vdex, write out the shared data section. memcpy(vdex_begin_ + vdex_size_, raw_dex_file_shared_data_begin, shared_data_size); } vdex_size_ += shared_data_size; size_dex_file_ += shared_data_size; - if (!use_existing_vdex) { + if (!update_input_vdex) { // Fix up the dex headers to have correct offsets to the data section. for (OatDexFile& oat_dex_file : oat_dex_files_) { DexFile::Header* header = @@ -3297,22 +3297,22 @@ void OatWriter::CloseSources() { bool OatWriter::WriteDexFile(File* file, OatDexFile* oat_dex_file, - bool use_existing_vdex) { + bool update_input_vdex) { DCHECK_EQ(vdex_size_, oat_dex_file->dex_file_offset_); if (oat_dex_file->source_.IsZipEntry()) { - DCHECK(!use_existing_vdex); + DCHECK(!update_input_vdex); if (!WriteDexFile(file, oat_dex_file, oat_dex_file->source_.GetZipEntry())) { return false; } } else if (oat_dex_file->source_.IsRawFile()) { - DCHECK(!use_existing_vdex); + DCHECK(!update_input_vdex); if (!WriteDexFile(file, oat_dex_file, oat_dex_file->source_.GetRawFile())) { return false; } } else { DCHECK(oat_dex_file->source_.IsRawData()); const uint8_t* raw_data = oat_dex_file->source_.GetRawData(); - if (!WriteDexFile(oat_dex_file, raw_data, use_existing_vdex)) { + if (!WriteDexFile(oat_dex_file, raw_data, update_input_vdex)) { return false; } } @@ -3447,14 +3447,14 @@ bool OatWriter::WriteDexFile(File* file, bool OatWriter::WriteDexFile(OatDexFile* oat_dex_file, const uint8_t* dex_file, - bool use_existing_vdex) { + bool update_input_vdex) { // Note: The raw data has already been checked to contain the header // and all the data that the header specifies as the file size. DCHECK(dex_file != nullptr); DCHECK(ValidateDexFileHeader(dex_file, oat_dex_file->GetLocation())); DCHECK_EQ(oat_dex_file->dex_file_size_, AsUnalignedDexFileHeader(dex_file)->file_size_); - if (use_existing_vdex) { + if (update_input_vdex) { // The vdex already contains the dex code, no need to write it again. } else { uint8_t* raw_output = vdex_begin_ + oat_dex_file->dex_file_offset_; diff --git a/dex2oat/linker/oat_writer.h b/dex2oat/linker/oat_writer.h index ad14d60189..87174eb21d 100644 --- a/dex2oat/linker/oat_writer.h +++ b/dex2oat/linker/oat_writer.h @@ -157,11 +157,11 @@ class OatWriter { // Write raw dex files to the vdex file, mmap the file and open the dex files from it. // The `verify` setting dictates whether the dex file verifier should check the dex files. // This is generally the case, and should only be false for tests. - // If `use_existing_vdex` is true, then this method won't actually write the dex files, + // If `update_input_vdex` is true, then this method won't actually write the dex files, // and the compiler will just re-use the existing vdex file. bool WriteAndOpenDexFiles(File* vdex_file, bool verify, - bool use_existing_vdex, + bool update_input_vdex, CopyOption copy_dex_files, /*out*/ std::vector<MemMap>* opened_dex_files_map, /*out*/ std::vector<std::unique_ptr<const DexFile>>* opened_dex_files); @@ -276,12 +276,12 @@ class OatWriter { // If `update_input_vdex` is true, then this method won't actually write the dex files, // and the compiler will just re-use the existing vdex file. bool WriteDexFiles(File* file, - bool use_existing_vdex, + bool update_input_vdex, CopyOption copy_dex_files, /*out*/ std::vector<MemMap>* opened_dex_files_map); bool WriteDexFile(File* file, OatDexFile* oat_dex_file, - bool use_existing_vdex); + bool update_input_vdex); bool LayoutDexFile(OatDexFile* oat_dex_file); bool WriteDexFile(File* file, OatDexFile* oat_dex_file, @@ -291,7 +291,7 @@ class OatWriter { File* dex_file); bool WriteDexFile(OatDexFile* oat_dex_file, const uint8_t* dex_file, - bool use_existing_vdex); + bool update_input_vdex); bool OpenDexFiles(File* file, bool verify, /*inout*/ std::vector<MemMap>* opened_dex_files_map, diff --git a/dexlayout/dexdiag.cc b/dexlayout/dexdiag.cc index 9aa0353345..a9ea27d225 100644 --- a/dexlayout/dexdiag.cc +++ b/dexlayout/dexdiag.cc @@ -330,6 +330,7 @@ static bool DisplayMappingIfFromVdexFile(ProcMemInfo& proc, const Vma& vma, Prin std::unique_ptr<VdexFile> vdex(VdexFile::Open(vdex_name, /*writable=*/ false, /*low_4gb=*/ false, + /*unquicken= */ false, &error_msg /*out*/)); if (vdex == nullptr) { std::cerr << "Could not open vdex file " diff --git a/dexlayout/dexlayout.h b/dexlayout/dexlayout.h index bdc7863cd1..9bb7b8b2e8 100644 --- a/dexlayout/dexlayout.h +++ b/dexlayout/dexlayout.h @@ -99,10 +99,7 @@ class DexLayout { // Setting this to false disables class def layout entirely, which is stronger than strictly // necessary to ensure the partial order w.r.t. class derivation. TODO: Re-enable (b/68317550). - // This should never be set for a device build, as changing class defs ids - // conflict with profiles and verification passed by Play. static constexpr bool kChangeClassDefOrder = false; - static_assert(!(kIsTargetBuild && kChangeClassDefOrder), "Never set class reordering on target"); DexLayout(Options& options, ProfileCompilationInfo* info, diff --git a/runtime/oat_file.cc b/runtime/oat_file.cc index c80feafd06..54e3712ec4 100644 --- a/runtime/oat_file.cc +++ b/runtime/oat_file.cc @@ -190,6 +190,10 @@ class OatFileBase : public OatFile { } private: + // Returns true if we want to remove quickened opcodes before loading the VDEX file, false + // otherwise. + bool ShouldUnquickenVDex() const; + DISALLOW_COPY_AND_ASSIGN(OatFileBase); }; @@ -276,6 +280,23 @@ OatFileBase* OatFileBase::OpenOatFile(int zip_fd, return ret.release(); } +bool OatFileBase::ShouldUnquickenVDex() const { + // We sometimes load oat files without a runtime (eg oatdump) and don't want to do anything in + // that case. If we are debuggable there are no -quick opcodes to unquicken. If the runtime is not + // debuggable we don't care whether there are -quick opcodes or not so no need to do anything. + Runtime* runtime = Runtime::Current(); + return (runtime != nullptr && runtime->IsJavaDebuggable()) && + // Note: This is called before `OatFileBase::Setup()` where we validate the + // oat file contents. Check that we have at least a valid header, including + // oat file version, to avoid parsing the key-value store for a different + // version (out-of-date oat file) which can lead to crashes. b/179221298. + // TODO: While this is a poor workaround and the correct solution would be + // to postpone the unquickening check until after `OatFileBase::Setup()`, + // we prefer to avoid larger rewrites because quickening is deprecated and + // should be removed completely anyway. b/170086509 + (GetOatHeader().IsValid() && !IsDebuggable()); +} + bool OatFileBase::LoadVdex(const std::string& vdex_filename, bool writable, bool low_4gb, @@ -286,6 +307,7 @@ bool OatFileBase::LoadVdex(const std::string& vdex_filename, vdex_filename, writable, low_4gb, + ShouldUnquickenVDex(), error_msg); if (vdex_.get() == nullptr) { *error_msg = StringPrintf("Failed to load vdex file '%s' %s", @@ -316,6 +338,7 @@ bool OatFileBase::LoadVdex(int vdex_fd, vdex_filename, writable, low_4gb, + ShouldUnquickenVDex(), error_msg); if (vdex_.get() == nullptr) { *error_msg = "Failed opening vdex file."; diff --git a/runtime/oat_file_assistant.cc b/runtime/oat_file_assistant.cc index c303a7b3d2..414b24e419 100644 --- a/runtime/oat_file_assistant.cc +++ b/runtime/oat_file_assistant.cc @@ -877,6 +877,7 @@ const OatFile* OatFileAssistant::OatFileInfo::GetFile() { filename_, /*writable=*/ false, /*low_4gb=*/ false, + /*unquicken=*/ false, &error_msg); } } @@ -884,6 +885,7 @@ const OatFile* OatFileAssistant::OatFileInfo::GetFile() { vdex = VdexFile::Open(filename_, /*writable=*/ false, /*low_4gb=*/ false, + /*unquicken=*/ false, &error_msg); } if (vdex == nullptr) { diff --git a/runtime/oat_file_manager.cc b/runtime/oat_file_manager.cc index aaa6600d08..f172ee030e 100644 --- a/runtime/oat_file_manager.cc +++ b/runtime/oat_file_manager.cc @@ -497,6 +497,7 @@ std::vector<std::unique_ptr<const DexFile>> OatFileManager::OpenDexFilesFromOat_ vdex_file = VdexFile::Open(vdex_path, /* writable= */ false, /* low_4gb= */ false, + /* unquicken= */ false, &error_msg); if (vdex_file == nullptr) { LOG(WARNING) << "Failed to open vdex " << vdex_path << ": " << error_msg; diff --git a/runtime/vdex_file.cc b/runtime/vdex_file.cc index ba80886f09..0afa13161b 100644 --- a/runtime/vdex_file.cc +++ b/runtime/vdex_file.cc @@ -72,6 +72,7 @@ std::unique_ptr<VdexFile> VdexFile::OpenAtAddress(uint8_t* mmap_addr, const std::string& vdex_filename, bool writable, bool low_4gb, + bool unquicken, std::string* error_msg) { ScopedTrace trace(("VdexFile::OpenAtAddress " + vdex_filename).c_str()); if (!OS::FileExists(vdex_filename.c_str())) { @@ -105,6 +106,7 @@ std::unique_ptr<VdexFile> VdexFile::OpenAtAddress(uint8_t* mmap_addr, vdex_filename, writable, low_4gb, + unquicken, error_msg); } @@ -116,6 +118,7 @@ std::unique_ptr<VdexFile> VdexFile::OpenAtAddress(uint8_t* mmap_addr, const std::string& vdex_filename, bool writable, bool low_4gb, + bool unquicken, std::string* error_msg) { if (mmap_addr != nullptr && mmap_size < vdex_length) { LOG(WARNING) << "Insufficient pre-allocated space to mmap vdex."; @@ -123,6 +126,7 @@ std::unique_ptr<VdexFile> VdexFile::OpenAtAddress(uint8_t* mmap_addr, mmap_reuse = false; } CHECK(!mmap_reuse || mmap_addr != nullptr); + CHECK(!(writable && unquicken)) << "We don't want to be writing unquickened files out to disk!"; // Start as PROT_WRITE so we can mprotect back to it if we want to. MemMap mmap = MemMap::MapFileAtAddress( mmap_addr, diff --git a/runtime/vdex_file.h b/runtime/vdex_file.h index 3ccbfa5567..35be4fb1ac 100644 --- a/runtime/vdex_file.h +++ b/runtime/vdex_file.h @@ -194,6 +194,7 @@ class VdexFile { const std::string& vdex_filename, bool writable, bool low_4gb, + bool unquicken, std::string* error_msg); // Returns nullptr if the vdex file cannot be opened or is not valid. @@ -206,12 +207,14 @@ class VdexFile { const std::string& vdex_filename, bool writable, bool low_4gb, + bool unquicken, std::string* error_msg); // Returns nullptr if the vdex file cannot be opened or is not valid. static std::unique_ptr<VdexFile> Open(const std::string& vdex_filename, bool writable, bool low_4gb, + bool unquicken, std::string* error_msg) { return OpenAtAddress(nullptr, 0, @@ -219,6 +222,7 @@ class VdexFile { vdex_filename, writable, low_4gb, + unquicken, error_msg); } @@ -228,6 +232,7 @@ class VdexFile { const std::string& vdex_filename, bool writable, bool low_4gb, + bool unquicken, std::string* error_msg) { return OpenAtAddress(nullptr, 0, @@ -237,6 +242,7 @@ class VdexFile { vdex_filename, writable, low_4gb, + unquicken, error_msg); } diff --git a/runtime/vdex_file_test.cc b/runtime/vdex_file_test.cc index 565487e275..9d92b42140 100644 --- a/runtime/vdex_file_test.cc +++ b/runtime/vdex_file_test.cc @@ -36,11 +36,12 @@ TEST_F(VdexFileTest, OpenEmptyVdex) { tmp.GetFilename(), /*writable=*/false, /*low_4gb=*/false, + /*unquicken=*/false, &error_msg); EXPECT_TRUE(vdex == nullptr); vdex = VdexFile::Open( - tmp.GetFilename(), /*writable=*/false, /*low_4gb=*/false, &error_msg); + tmp.GetFilename(), /*writable=*/false, /*low_4gb=*/false, /*unquicken=*/ false, &error_msg); EXPECT_TRUE(vdex == nullptr); } |