diff options
| author | 2016-11-01 15:17:58 +0000 | |
|---|---|---|
| committer | 2016-11-01 15:17:58 +0000 | |
| commit | df6896eb62ca0e09a2d976c9482c6e0c4288cc9e (patch) | |
| tree | 04b48b84f1c0efa59de9622182a6ebe671cf69b6 | |
| parent | bda454e9a09018cde1ea2ee10f0fdd5bf2ad756b (diff) | |
| parent | e70dd560154ea38af87ce8b783ab6e382eb49d4b (diff) | |
Merge "Dump VerifierDeps in oatdump."
| -rw-r--r-- | compiler/verifier_deps_test.cc | 4 | ||||
| -rw-r--r-- | oatdump/oatdump.cc | 23 | ||||
| -rw-r--r-- | runtime/vdex_file.h | 13 | ||||
| -rw-r--r-- | runtime/verifier/verifier_deps.cc | 9 | ||||
| -rw-r--r-- | runtime/verifier/verifier_deps.h | 8 |
5 files changed, 50 insertions, 7 deletions
diff --git a/compiler/verifier_deps_test.cc b/compiler/verifier_deps_test.cc index cd6ca4c6df..3a53998e17 100644 --- a/compiler/verifier_deps_test.cc +++ b/compiler/verifier_deps_test.cc @@ -1076,7 +1076,7 @@ TEST_F(VerifierDepsTest, EncodeDecode) { verifier_deps_->Encode(dex_files_, &buffer); ASSERT_FALSE(buffer.empty()); - VerifierDeps decoded_deps(dex_files_, ArrayRef<uint8_t>(buffer)); + VerifierDeps decoded_deps(dex_files_, ArrayRef<const uint8_t>(buffer)); ASSERT_TRUE(verifier_deps_->Equals(decoded_deps)); } @@ -1102,7 +1102,7 @@ TEST_F(VerifierDepsTest, EncodeDecodeMulti) { } // Dump the new verifier deps to ensure it can properly read the data. - VerifierDeps decoded_deps(dex_files, ArrayRef<uint8_t>(buffer)); + VerifierDeps decoded_deps(dex_files, ArrayRef<const uint8_t>(buffer)); std::ostringstream stream; VariableIndentationOutputStream os(&stream); decoded_deps.Dump(&os); diff --git a/oatdump/oatdump.cc b/oatdump/oatdump.cc index da0db01386..3d208b5d28 100644 --- a/oatdump/oatdump.cc +++ b/oatdump/oatdump.cc @@ -66,6 +66,7 @@ #include "type_lookup_table.h" #include "vdex_file.h" #include "verifier/method_verifier.h" +#include "verifier/verifier_deps.h" #include "well_known_classes.h" #include <sys/stat.h> @@ -483,6 +484,28 @@ class OatDumper { os << "\n"; if (!options_.dump_header_only_) { + VariableIndentationOutputStream vios(&os); + VdexFile::Header vdex_header = oat_file_.GetVdexFile()->GetHeader(); + if (vdex_header.IsValid()) { + std::string error_msg; + std::vector<const DexFile*> dex_files; + for (size_t i = 0; i < oat_dex_files_.size(); i++) { + const DexFile* dex_file = OpenDexFile(oat_dex_files_[i], &error_msg); + if (dex_file == nullptr) { + os << "Error opening dex file: " << error_msg << std::endl; + return false; + } + dex_files.push_back(dex_file); + } + verifier::VerifierDeps deps(dex_files, oat_file_.GetVdexFile()->GetVerifierDepsData()); + deps.Dump(&vios); + } else { + os << "UNRECOGNIZED vdex file, magic " + << vdex_header.GetMagic() + << ", version " + << vdex_header.GetVersion() + << "\n"; + } for (size_t i = 0; i < oat_dex_files_.size(); i++) { const OatFile::OatDexFile* oat_dex_file = oat_dex_files_[i]; CHECK(oat_dex_file != nullptr); diff --git a/runtime/vdex_file.h b/runtime/vdex_file.h index 28f9bb3481..edd6ffe89d 100644 --- a/runtime/vdex_file.h +++ b/runtime/vdex_file.h @@ -20,6 +20,7 @@ #include <stdint.h> #include <string> +#include "base/array_ref.h" #include "base/macros.h" #include "mem_map.h" #include "os.h" @@ -44,8 +45,11 @@ class VdexFile { public: Header(uint32_t dex_size, uint32_t verifier_deps_size, uint32_t quickening_info_size); + const char* GetMagic() const { return reinterpret_cast<const char*>(magic_); } + const char* GetVersion() const { return reinterpret_cast<const char*>(version_); } bool IsMagicValid() const; bool IsVersionValid() const; + bool IsValid() const { return IsMagicValid() && IsVersionValid(); } uint32_t GetDexSize() const { return dex_size_; } uint32_t GetVerifierDepsSize() const { return verifier_deps_size_; } @@ -71,6 +75,15 @@ class VdexFile { const uint8_t* End() const { return mmap_->End(); } size_t Size() const { return mmap_->Size(); } + const Header& GetHeader() const { + return *reinterpret_cast<const Header*>(Begin()); + } + + ArrayRef<const uint8_t> GetVerifierDepsData() const { + return ArrayRef<const uint8_t>( + Begin() + sizeof(Header) + GetHeader().GetDexSize(), GetHeader().GetVerifierDepsSize()); + } + private: explicit VdexFile(MemMap* mmap) : mmap_(mmap) {} diff --git a/runtime/verifier/verifier_deps.cc b/runtime/verifier/verifier_deps.cc index 69708713d6..149861c243 100644 --- a/runtime/verifier/verifier_deps.cc +++ b/runtime/verifier/verifier_deps.cc @@ -453,8 +453,15 @@ void VerifierDeps::Encode(const std::vector<const DexFile*>& dex_files, } } -VerifierDeps::VerifierDeps(const std::vector<const DexFile*>& dex_files, ArrayRef<uint8_t> data) +VerifierDeps::VerifierDeps(const std::vector<const DexFile*>& dex_files, + ArrayRef<const uint8_t> data) : VerifierDeps(dex_files) { + if (data.empty()) { + // Return eagerly, as the first thing we expect from VerifierDeps data is + // the number of created strings, even if there is no dependency. + // Currently, only the boot image does not have any VerifierDeps data. + return; + } const uint8_t* data_start = data.data(); const uint8_t* data_end = data_start + data.size(); for (const DexFile* dex_file : dex_files) { diff --git a/runtime/verifier/verifier_deps.h b/runtime/verifier/verifier_deps.h index 6b0c959c08..fab432347f 100644 --- a/runtime/verifier/verifier_deps.h +++ b/runtime/verifier/verifier_deps.h @@ -51,6 +51,10 @@ class VerifierDeps { explicit VerifierDeps(const std::vector<const DexFile*>& dex_files) REQUIRES(!Locks::verifier_deps_lock_); + VerifierDeps(const std::vector<const DexFile*>& dex_files, + ArrayRef<const uint8_t> data) + REQUIRES(!Locks::verifier_deps_lock_); + // Record the verification status of the class at `type_idx`. static void MaybeRecordVerificationStatus(const DexFile& dex_file, uint16_t type_idx, @@ -108,10 +112,6 @@ class VerifierDeps { private: static constexpr uint16_t kUnresolvedMarker = static_cast<uint16_t>(-1); - // Only used in tests to reconstruct the data structure from serialized data. - VerifierDeps(const std::vector<const DexFile*>& dex_files, ArrayRef<uint8_t> data) - REQUIRES(!Locks::verifier_deps_lock_); - using ClassResolutionBase = std::tuple<uint32_t, uint16_t>; struct ClassResolution : public ClassResolutionBase { ClassResolution() = default; |