summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAndreas Gampe <agampe@google.com>2014-12-10 20:51:45 -0800
committerThe Android Automerger <android-build@google.com>2014-12-11 13:49:24 -0800
commit38078c6449ea5c53ce390343eb57327552a7eaff (patch)
treea77c30bcba28b28fc7633c48020c19fa8de2d7c3
parent8a483aa099041683b8e11f2b62e45a9cf63e09de (diff)
downloadandroid_art-38078c6449ea5c53ce390343eb57327552a7eaff.tar.gz
android_art-38078c6449ea5c53ce390343eb57327552a7eaff.tar.bz2
android_art-38078c6449ea5c53ce390343eb57327552a7eaff.zip
ART: More ELF and oat file safety measures
In an ELF file, look for a shstrtab section when loading in program-header-only mode. If the section is outside the file size, it strongly indicates a broken compile. When compiling oat files in the class linker, explicitly unlink on failure. This should catch cases when dex2oat is killed or crashes and doesn't have a chance to delete its (partial) output. Bug: 15567083 Change-Id: Ia0c75f151d91c6f26a71696967255d6d409ca882
-rw-r--r--runtime/class_linker.cc10
-rw-r--r--runtime/elf_file.cc14
2 files changed, 23 insertions, 1 deletions
diff --git a/runtime/class_linker.cc b/runtime/class_linker.cc
index cb2831cf33..cd1a93a30c 100644
--- a/runtime/class_linker.cc
+++ b/runtime/class_linker.cc
@@ -19,6 +19,7 @@
#include <fcntl.h>
#include <sys/file.h>
#include <sys/stat.h>
+#include <unistd.h>
#include <deque>
#include <memory>
#include <string>
@@ -662,7 +663,14 @@ bool ClassLinker::GenerateOatFile(const char* dex_filename,
argv.push_back(compiler_options[i].c_str());
}
- return Exec(argv, error_msg);
+ if (!Exec(argv, error_msg)) {
+ // Manually delete the file. Ensures there is no garbage left over if the process unexpectedly
+ // died. Ignore unlink failure, propagate the original error.
+ TEMP_FAILURE_RETRY(unlink(oat_cache_filename));
+ return false;
+ }
+
+ return true;
}
const OatFile* ClassLinker::RegisterOatFile(const OatFile* oat_file) {
diff --git a/runtime/elf_file.cc b/runtime/elf_file.cc
index 6ec0712f0d..29628f1e0d 100644
--- a/runtime/elf_file.cc
+++ b/runtime/elf_file.cc
@@ -432,6 +432,20 @@ bool ElfFile::CheckSectionsExist(std::string* error_msg) const {
return false;
}
+ // We'd also like to confirm a shstrtab in program_header_only_ mode (else Open() does this for
+ // us). This is usually the last in an oat file, and a good indicator of whether writing was
+ // successful (or the process crashed and left garbage).
+ if (program_header_only_) {
+ // It might not be mapped, but we can compare against the file size.
+ int64_t offset = static_cast<int64_t>(GetHeader().e_shoff +
+ (GetHeader().e_shstrndx * GetHeader().e_shentsize));
+ if (offset >= file_->GetLength()) {
+ *error_msg = StringPrintf("Shstrtab is not in the mapped ELF file: '%s'",
+ file_->GetPath().c_str());
+ return false;
+ }
+ }
+
return true;
}