diff options
-rw-r--r-- | src/class_linker.cc | 62 | ||||
-rw-r--r-- | src/class_linker.h | 14 | ||||
-rw-r--r-- | src/compiler/dex/quick/gen_invoke.cc | 14 | ||||
-rw-r--r-- | src/compiler/driver/compiler_driver.cc | 21 | ||||
-rw-r--r-- | src/compiler/driver/compiler_driver.h | 2 | ||||
-rw-r--r-- | src/compiler/driver/dex_compilation_unit.cc | 30 | ||||
-rw-r--r-- | src/compiler/driver/dex_compilation_unit.h | 6 | ||||
-rw-r--r-- | src/compiler/llvm/llvm_compilation_unit.h | 6 | ||||
-rw-r--r-- | src/locks.cc | 5 | ||||
-rw-r--r-- | src/locks.h | 2 | ||||
-rw-r--r-- | src/verifier/method_verifier.cc | 14 | ||||
-rw-r--r-- | src/verifier/method_verifier.h | 9 | ||||
-rw-r--r-- | src/verifier/reg_type.cc | 121 | ||||
-rw-r--r-- | src/verifier/reg_type.h | 94 | ||||
-rw-r--r-- | src/verifier/reg_type_cache-inl.h | 8 | ||||
-rw-r--r-- | src/verifier/reg_type_cache.cc | 102 | ||||
-rw-r--r-- | src/verifier/reg_type_cache.h | 8 |
17 files changed, 295 insertions, 223 deletions
diff --git a/src/class_linker.cc b/src/class_linker.cc index 46c2ade314..cbdcbe0b31 100644 --- a/src/class_linker.cc +++ b/src/class_linker.cc @@ -196,7 +196,7 @@ ClassLinker* ClassLinker::CreateFromImage(InternTable* intern_table) { ClassLinker::ClassLinker(InternTable* intern_table) // dex_lock_ is recursive as it may be used in stack dumping. - : dex_lock_("ClassLinker dex lock", kDefaultMutexLevel, true), + : dex_lock_("ClassLinker dex lock", kDefaultMutexLevel), class_roots_(NULL), array_iftable_(NULL), init_done_(false), @@ -663,22 +663,22 @@ bool ClassLinker::GenerateOatFile(const std::string& dex_filename, } void ClassLinker::RegisterOatFile(const OatFile& oat_file) { - MutexLock mu(Thread::Current(), dex_lock_); + WriterMutexLock mu(Thread::Current(), dex_lock_); RegisterOatFileLocked(oat_file); } void ClassLinker::RegisterOatFileLocked(const OatFile& oat_file) { - dex_lock_.AssertHeld(Thread::Current()); -#ifndef NDEBUG - for (size_t i = 0; i < oat_files_.size(); ++i) { - CHECK_NE(&oat_file, oat_files_[i]) << oat_file.GetLocation(); + dex_lock_.AssertExclusiveHeld(Thread::Current()); + if (kIsDebugBuild) { + for (size_t i = 0; i < oat_files_.size(); ++i) { + CHECK_NE(&oat_file, oat_files_[i]) << oat_file.GetLocation(); + } } -#endif oat_files_.push_back(&oat_file); } OatFile* ClassLinker::OpenOat(const ImageSpace* space) { - MutexLock mu(Thread::Current(), dex_lock_); + WriterMutexLock mu(Thread::Current(), dex_lock_); const Runtime* runtime = Runtime::Current(); const ImageHeader& image_header = space->GetImageHeader(); // Grab location but don't use Object::AsString as we haven't yet initialized the roots to @@ -709,7 +709,7 @@ OatFile* ClassLinker::OpenOat(const ImageSpace* space) { } const OatFile* ClassLinker::FindOpenedOatFileForDexFile(const DexFile& dex_file) { - MutexLock mu(Thread::Current(), dex_lock_); + ReaderMutexLock mu(Thread::Current(), dex_lock_); return FindOpenedOatFileFromDexLocation(dex_file.GetLocation()); } @@ -755,7 +755,7 @@ static const DexFile* FindDexFileInOatLocation(const std::string& dex_location, const DexFile* ClassLinker::FindOrCreateOatFileForDexLocation(const std::string& dex_location, const std::string& oat_location) { - MutexLock mu(Thread::Current(), dex_lock_); + WriterMutexLock mu(Thread::Current(), dex_lock_); return FindOrCreateOatFileForDexLocationLocked(dex_location, oat_location); } @@ -857,7 +857,7 @@ const DexFile* ClassLinker::VerifyAndOpenDexFileFromOatFile(const OatFile* oat_f } const DexFile* ClassLinker::FindDexFileInOatFileFromDexLocation(const std::string& dex_location) { - MutexLock mu(Thread::Current(), dex_lock_); + WriterMutexLock mu(Thread::Current(), dex_lock_); const OatFile* open_oat_file = FindOpenedOatFileFromDexLocation(dex_location); if (open_oat_file != NULL) { @@ -924,7 +924,7 @@ const OatFile* ClassLinker::FindOpenedOatFileFromOatLocation(const std::string& } const OatFile* ClassLinker::FindOatFileFromOatLocation(const std::string& oat_location) { - MutexLock mu(Thread::Current(), dex_lock_); + ReaderMutexLock mu(Thread::Current(), dex_lock_); return FindOatFileFromOatLocationLocked(oat_location); } @@ -1062,14 +1062,14 @@ void ClassLinker::VisitRoots(RootVisitor* visitor, void* arg) { visitor(class_roots_, arg); Thread* self = Thread::Current(); { - MutexLock mu(self, dex_lock_); + ReaderMutexLock mu(self, dex_lock_); for (size_t i = 0; i < dex_caches_.size(); i++) { visitor(dex_caches_[i], arg); } } { - MutexLock mu(self, *Locks::classlinker_classes_lock_); + ReaderMutexLock mu(self, *Locks::classlinker_classes_lock_); typedef Table::const_iterator It; // TODO: C++0x auto for (It it = classes_.begin(), end = classes_.end(); it != end; ++it) { visitor(it->second, arg); @@ -1084,7 +1084,7 @@ void ClassLinker::VisitRoots(RootVisitor* visitor, void* arg) { } void ClassLinker::VisitClasses(ClassVisitor* visitor, void* arg) const { - MutexLock mu(Thread::Current(), *Locks::classlinker_classes_lock_); + ReaderMutexLock mu(Thread::Current(), *Locks::classlinker_classes_lock_); typedef Table::const_iterator It; // TODO: C++0x auto for (It it = classes_.begin(), end = classes_.end(); it != end; ++it) { if (!visitor(it->second, arg)) { @@ -1813,7 +1813,7 @@ void ClassLinker::AppendToBootClassPath(const DexFile& dex_file, SirtRef<mirror: } bool ClassLinker::IsDexFileRegisteredLocked(const DexFile& dex_file) const { - dex_lock_.AssertHeld(Thread::Current()); + dex_lock_.AssertSharedHeld(Thread::Current()); for (size_t i = 0; i != dex_caches_.size(); ++i) { if (dex_caches_[i]->GetDexFile() == &dex_file) { return true; @@ -1823,12 +1823,12 @@ bool ClassLinker::IsDexFileRegisteredLocked(const DexFile& dex_file) const { } bool ClassLinker::IsDexFileRegistered(const DexFile& dex_file) const { - MutexLock mu(Thread::Current(), dex_lock_); + ReaderMutexLock mu(Thread::Current(), dex_lock_); return IsDexFileRegisteredLocked(dex_file); } void ClassLinker::RegisterDexFileLocked(const DexFile& dex_file, SirtRef<mirror::DexCache>& dex_cache) { - dex_lock_.AssertHeld(Thread::Current()); + dex_lock_.AssertExclusiveHeld(Thread::Current()); CHECK(dex_cache.get() != NULL) << dex_file.GetLocation(); CHECK(dex_cache->GetLocation()->Equals(dex_file.GetLocation())); dex_caches_.push_back(dex_cache.get()); @@ -1839,7 +1839,7 @@ void ClassLinker::RegisterDexFileLocked(const DexFile& dex_file, SirtRef<mirror: void ClassLinker::RegisterDexFile(const DexFile& dex_file) { Thread* self = Thread::Current(); { - MutexLock mu(self, dex_lock_); + ReaderMutexLock mu(self, dex_lock_); if (IsDexFileRegisteredLocked(dex_file)) { return; } @@ -1849,7 +1849,7 @@ void ClassLinker::RegisterDexFile(const DexFile& dex_file) { // get to a suspend point. SirtRef<mirror::DexCache> dex_cache(self, AllocDexCache(self, dex_file)); { - MutexLock mu(self, dex_lock_); + WriterMutexLock mu(self, dex_lock_); if (IsDexFileRegisteredLocked(dex_file)) { return; } @@ -1858,12 +1858,12 @@ void ClassLinker::RegisterDexFile(const DexFile& dex_file) { } void ClassLinker::RegisterDexFile(const DexFile& dex_file, SirtRef<mirror::DexCache>& dex_cache) { - MutexLock mu(Thread::Current(), dex_lock_); + WriterMutexLock mu(Thread::Current(), dex_lock_); RegisterDexFileLocked(dex_file, dex_cache); } mirror::DexCache* ClassLinker::FindDexCache(const DexFile& dex_file) const { - MutexLock mu(Thread::Current(), dex_lock_); + ReaderMutexLock mu(Thread::Current(), dex_lock_); // Search assuming unique-ness of dex file. for (size_t i = 0; i != dex_caches_.size(); ++i) { mirror::DexCache* dex_cache = dex_caches_[i]; @@ -1889,7 +1889,7 @@ mirror::DexCache* ClassLinker::FindDexCache(const DexFile& dex_file) const { } void ClassLinker::FixupDexCaches(mirror::AbstractMethod* resolution_method) const { - MutexLock mu(Thread::Current(), dex_lock_); + ReaderMutexLock mu(Thread::Current(), dex_lock_); for (size_t i = 0; i != dex_caches_.size(); ++i) { dex_caches_[i]->Fixup(resolution_method); } @@ -2085,7 +2085,7 @@ mirror::Class* ClassLinker::InsertClass(const StringPiece& descriptor, mirror::C LOG(INFO) << "Loaded class " << descriptor << source; } size_t hash = StringPieceHash()(descriptor); - MutexLock mu(Thread::Current(), *Locks::classlinker_classes_lock_); + WriterMutexLock mu(Thread::Current(), *Locks::classlinker_classes_lock_); Table& classes = image_class ? image_classes_ : classes_; mirror::Class* existing = LookupClassLocked(descriptor.data(), klass->GetClassLoader(), hash, classes); #ifndef NDEBUG @@ -2103,7 +2103,7 @@ mirror::Class* ClassLinker::InsertClass(const StringPiece& descriptor, mirror::C bool ClassLinker::RemoveClass(const char* descriptor, const mirror::ClassLoader* class_loader) { size_t hash = Hash(descriptor); - MutexLock mu(Thread::Current(), *Locks::classlinker_classes_lock_); + WriterMutexLock mu(Thread::Current(), *Locks::classlinker_classes_lock_); typedef Table::iterator It; // TODO: C++0x auto // TODO: determine if its better to search classes_ or image_classes_ first ClassHelper kh; @@ -2131,7 +2131,7 @@ bool ClassLinker::RemoveClass(const char* descriptor, const mirror::ClassLoader* mirror::Class* ClassLinker::LookupClass(const char* descriptor, const mirror::ClassLoader* class_loader) { size_t hash = Hash(descriptor); - MutexLock mu(Thread::Current(), *Locks::classlinker_classes_lock_); + ReaderMutexLock mu(Thread::Current(), *Locks::classlinker_classes_lock_); // TODO: determine if its better to search classes_ or image_classes_ first mirror::Class* klass = NULL; // Use image class only if the class_loader is null. @@ -2171,7 +2171,7 @@ mirror::Class* ClassLinker::LookupClassLocked(const char* descriptor, void ClassLinker::LookupClasses(const char* descriptor, std::vector<mirror::Class*>& classes) { classes.clear(); size_t hash = Hash(descriptor); - MutexLock mu(Thread::Current(), *Locks::classlinker_classes_lock_); + ReaderMutexLock mu(Thread::Current(), *Locks::classlinker_classes_lock_); typedef Table::const_iterator It; // TODO: C++0x auto // TODO: determine if its better to search classes_ or image_classes_ first ClassHelper kh(NULL, this); @@ -2505,7 +2505,7 @@ mirror::AbstractMethod* ClassLinker::FindMethodForProxy(const mirror::Class* pro mirror::DexCache* dex_cache = NULL; { mirror::ObjectArray<mirror::Class>* resolved_types = proxy_method->GetDexCacheResolvedTypes(); - MutexLock mu(Thread::Current(), dex_lock_); + ReaderMutexLock mu(Thread::Current(), dex_lock_); for (size_t i = 0; i != dex_caches_.size(); ++i) { if (dex_caches_[i]->GetResolvedTypes() == resolved_types) { dex_cache = dex_caches_[i]; @@ -3885,7 +3885,7 @@ void ClassLinker::DumpAllClasses(int flags) const { // lock held, because it might need to resolve a field's type, which would try to take the lock. std::vector<mirror::Class*> all_classes; { - MutexLock mu(Thread::Current(), *Locks::classlinker_classes_lock_); + ReaderMutexLock mu(Thread::Current(), *Locks::classlinker_classes_lock_); typedef Table::const_iterator It; // TODO: C++0x auto for (It it = classes_.begin(), end = classes_.end(); it != end; ++it) { all_classes.push_back(it->second); @@ -3901,13 +3901,13 @@ void ClassLinker::DumpAllClasses(int flags) const { } void ClassLinker::DumpForSigQuit(std::ostream& os) const { - MutexLock mu(Thread::Current(), *Locks::classlinker_classes_lock_); + ReaderMutexLock mu(Thread::Current(), *Locks::classlinker_classes_lock_); os << "Loaded classes: " << image_classes_.size() << " image classes; " << classes_.size() << " allocated classes\n"; } size_t ClassLinker::NumLoadedClasses() const { - MutexLock mu(Thread::Current(), *Locks::classlinker_classes_lock_); + ReaderMutexLock mu(Thread::Current(), *Locks::classlinker_classes_lock_); return classes_.size() + image_classes_.size(); } diff --git a/src/class_linker.h b/src/class_linker.h index d41373c7d7..79fa8bafbb 100644 --- a/src/class_linker.h +++ b/src/class_linker.h @@ -240,7 +240,7 @@ class ClassLinker { LOCKS_EXCLUDED(dex_lock_); const OatFile* FindOatFileFromOatLocationLocked(const std::string& location) - EXCLUSIVE_LOCKS_REQUIRED(dex_lock_); + SHARED_LOCKS_REQUIRED(dex_lock_); // Finds the oat file for a dex location, generating the oat file if // it is missing or out of date. Returns the DexFile from within the @@ -420,7 +420,7 @@ class ClassLinker { void RegisterDexFileLocked(const DexFile& dex_file, SirtRef<mirror::DexCache>& dex_cache) EXCLUSIVE_LOCKS_REQUIRED(dex_lock_) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); - bool IsDexFileRegisteredLocked(const DexFile& dex_file) const EXCLUSIVE_LOCKS_REQUIRED(dex_lock_); + bool IsDexFileRegisteredLocked(const DexFile& dex_file) const SHARED_LOCKS_REQUIRED(dex_lock_); void RegisterOatFileLocked(const OatFile& oat_file) EXCLUSIVE_LOCKS_REQUIRED(dex_lock_) EXCLUSIVE_LOCKS_REQUIRED(dex_lock_); @@ -489,10 +489,9 @@ class ClassLinker { LOCKS_EXCLUDED(dex_lock_) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); const OatFile* FindOpenedOatFileFromDexLocation(const std::string& dex_location) - EXCLUSIVE_LOCKS_REQUIRED(dex_lock_) - SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); + SHARED_LOCKS_REQUIRED(Locks::mutator_lock_, dex_lock_); const OatFile* FindOpenedOatFileFromOatLocation(const std::string& oat_location) - EXCLUSIVE_LOCKS_REQUIRED(dex_lock_); + SHARED_LOCKS_REQUIRED(dex_lock_); const DexFile* VerifyAndOpenDexFileFromOatFile(const OatFile* oat_file, const std::string& dex_location, uint32_t dex_location_checksum) @@ -508,7 +507,7 @@ class ClassLinker { std::vector<const DexFile*> boot_class_path_; - mutable Mutex dex_lock_ DEFAULT_MUTEX_ACQUIRED_AFTER; + mutable ReaderWriterMutex dex_lock_ DEFAULT_MUTEX_ACQUIRED_AFTER; std::vector<mirror::DexCache*> dex_caches_ GUARDED_BY(dex_lock_); std::vector<const OatFile*> oat_files_ GUARDED_BY(dex_lock_); @@ -522,8 +521,7 @@ class ClassLinker { mirror::Class* LookupClassLocked(const char* descriptor, const mirror::ClassLoader* class_loader, size_t hash, const Table& classes) - SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) - EXCLUSIVE_LOCKS_REQUIRED(Locks::classlinker_classes_lock_); + SHARED_LOCKS_REQUIRED(Locks::mutator_lock_, Locks::classlinker_classes_lock_); // indexes into class_roots_. // needs to be kept in sync with class_roots_descriptors_. diff --git a/src/compiler/dex/quick/gen_invoke.cc b/src/compiler/dex/quick/gen_invoke.cc index f44272a641..733fdc9848 100644 --- a/src/compiler/dex/quick/gen_invoke.cc +++ b/src/compiler/dex/quick/gen_invoke.cc @@ -15,6 +15,7 @@ */ #include "compiler/dex/compiler_ir.h" +#include "dex_file-inl.h" #include "invoke_type.h" #include "mirror/array.h" #include "mirror/string.h" @@ -1177,6 +1178,10 @@ bool Mir2Lir::GenInlinedUnsafePut(CallInfo* info, bool is_long, // TODO - add Mips implementation return false; } + if (cu_->instruction_set == kX86 && is_object) { + // TODO: fix X86, it exhausts registers for card marking. + return false; + } // Unused - RegLocation rl_src_unsafe = info->args[0]; RegLocation rl_src_obj = info->args[1]; // Object RegLocation rl_src_offset = info->args[2]; // long low @@ -1220,8 +1225,10 @@ bool Mir2Lir::GenIntrinsic(CallInfo* info) * method. By doing this during basic block construction, we can also * take advantage of/generate new useful dataflow info. */ - std::string tgt_method(PrettyMethod(info->index, *cu_->dex_file)); - if (tgt_method.find(" java.lang") != std::string::npos) { + const char* tgt_methods_declaring_class = + cu_->dex_file->GetMethodDeclaringClassDescriptor(cu_->dex_file->GetMethodId(info->index)); + if (strstr(tgt_methods_declaring_class, "Ljava/lang") != NULL) { + std::string tgt_method(PrettyMethod(info->index, *cu_->dex_file)); if (tgt_method == "long java.lang.Double.doubleToRawLongBits(double)") { return GenInlinedDoubleCvt(info); } @@ -1275,7 +1282,8 @@ bool Mir2Lir::GenIntrinsic(CallInfo* info) if (tgt_method == "java.lang.Thread java.lang.Thread.currentThread()") { return GenInlinedCurrentThread(info); } - } else if (tgt_method.find(" sun.misc.Unsafe") != std::string::npos) { + } else if (strstr(tgt_methods_declaring_class, "Lsun/misc/Unsafe;") != NULL) { + std::string tgt_method(PrettyMethod(info->index, *cu_->dex_file)); if (tgt_method == "boolean sun.misc.Unsafe.compareAndSwapInt(java.lang.Object, long, int, int)") { return GenInlinedCas32(info, false); } diff --git a/src/compiler/driver/compiler_driver.cc b/src/compiler/driver/compiler_driver.cc index 85dcdf671b..cc65cbee67 100644 --- a/src/compiler/driver/compiler_driver.cc +++ b/src/compiler/driver/compiler_driver.cc @@ -500,7 +500,7 @@ void CompilerDriver::PreCompile(jobject class_loader, const std::vector<const De InitializeClasses(class_loader, dex_files, thread_pool, timings); } -bool CompilerDriver::IsImageClass(const std::string& descriptor) const { +bool CompilerDriver::IsImageClass(const char* descriptor) const { if (image_classes_ == NULL) { return false; } @@ -610,9 +610,14 @@ bool CompilerDriver::CanAccessInstantiableTypeWithoutChecks(uint32_t referrer_id } static mirror::Class* ComputeCompilingMethodsClass(ScopedObjectAccess& soa, + mirror::DexCache* dex_cache, const DexCompilationUnit* mUnit) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { - mirror::DexCache* dex_cache = mUnit->GetClassLinker()->FindDexCache(*mUnit->GetDexFile()); + // The passed dex_cache is a hint, sanity check before asking the class linker that will take a + // lock. + if (dex_cache->GetDexFile() != mUnit->GetDexFile()) { + dex_cache = mUnit->GetClassLinker()->FindDexCache(*mUnit->GetDexFile()); + } mirror::ClassLoader* class_loader = soa.Decode<mirror::ClassLoader*>(mUnit->GetClassLoader()); const DexFile::MethodId& referrer_method_id = mUnit->GetDexFile()->GetMethodId(mUnit->GetDexMethodIndex()); return mUnit->GetClassLinker()->ResolveType(*mUnit->GetDexFile(), referrer_method_id.class_idx_, @@ -649,7 +654,9 @@ bool CompilerDriver::ComputeInstanceFieldInfo(uint32_t field_idx, const DexCompi // Try to resolve field and ignore if an Incompatible Class Change Error (ie is static). mirror::Field* resolved_field = ComputeFieldReferencedFromCompilingMethod(soa, mUnit, field_idx); if (resolved_field != NULL && !resolved_field->IsStatic()) { - mirror::Class* referrer_class = ComputeCompilingMethodsClass(soa, mUnit); + mirror::Class* referrer_class = + ComputeCompilingMethodsClass(soa, resolved_field->GetDeclaringClass()->GetDexCache(), + mUnit); if (referrer_class != NULL) { mirror::Class* fields_class = resolved_field->GetDeclaringClass(); bool access_ok = referrer_class->CanAccess(fields_class) && @@ -698,7 +705,9 @@ bool CompilerDriver::ComputeStaticFieldInfo(uint32_t field_idx, const DexCompila // Try to resolve field and ignore if an Incompatible Class Change Error (ie isn't static). mirror::Field* resolved_field = ComputeFieldReferencedFromCompilingMethod(soa, mUnit, field_idx); if (resolved_field != NULL && resolved_field->IsStatic()) { - mirror::Class* referrer_class = ComputeCompilingMethodsClass(soa, mUnit); + mirror::Class* referrer_class = + ComputeCompilingMethodsClass(soa, resolved_field->GetDeclaringClass()->GetDexCache(), + mUnit); if (referrer_class != NULL) { mirror::Class* fields_class = resolved_field->GetDeclaringClass(); if (fields_class == referrer_class) { @@ -842,7 +851,9 @@ bool CompilerDriver::ComputeInvokeInfo(const DexCompilationUnit* mUnit, const ui if (resolved_method != NULL) { // Don't try to fast-path if we don't understand the caller's class or this appears to be an // Incompatible Class Change Error. - mirror::Class* referrer_class = ComputeCompilingMethodsClass(soa, mUnit); + mirror::Class* referrer_class = + ComputeCompilingMethodsClass(soa, resolved_method->GetDeclaringClass()->GetDexCache(), + mUnit); bool icce = resolved_method->CheckIncompatibleClassChange(invoke_type); if (referrer_class != NULL && !icce) { mirror::Class* methods_class = resolved_method->GetDeclaringClass(); diff --git a/src/compiler/driver/compiler_driver.h b/src/compiler/driver/compiler_driver.h index 250532b920..c1e449e6ed 100644 --- a/src/compiler/driver/compiler_driver.h +++ b/src/compiler/driver/compiler_driver.h @@ -267,7 +267,7 @@ class CompilerDriver { } // Checks if class specified by type_idx is one of the image_classes_ - bool IsImageClass(const std::string& descriptor) const; + bool IsImageClass(const char* descriptor) const; void RecordClassStatus(ClassReference ref, CompiledClass* compiled_class); diff --git a/src/compiler/driver/dex_compilation_unit.cc b/src/compiler/driver/dex_compilation_unit.cc index 962df42a21..c7a4df6ea4 100644 --- a/src/compiler/driver/dex_compilation_unit.cc +++ b/src/compiler/driver/dex_compilation_unit.cc @@ -31,18 +31,17 @@ DexCompilationUnit::DexCompilationUnit(CompilationUnit* cu) code_item_(cu->code_item), class_def_idx_(cu->class_def_idx), dex_method_idx_(cu->method_idx), - access_flags_(cu->access_flags), - symbol_(StringPrintf("dex_%s", MangleForJni(PrettyMethod(dex_method_idx_, *dex_file_)).c_str())) { + access_flags_(cu->access_flags) { } -DexCompilationUnit:: DexCompilationUnit(CompilationUnit* cu, - jobject class_loader, - ClassLinker* class_linker, - const DexFile& dex_file, - const DexFile::CodeItem* code_item, - uint32_t class_def_idx, - uint32_t method_idx, - uint32_t access_flags) +DexCompilationUnit::DexCompilationUnit(CompilationUnit* cu, + jobject class_loader, + ClassLinker* class_linker, + const DexFile& dex_file, + const DexFile::CodeItem* code_item, + uint32_t class_def_idx, + uint32_t method_idx, + uint32_t access_flags) : cu_(cu), class_loader_(class_loader), class_linker_(class_linker), @@ -50,8 +49,15 @@ DexCompilationUnit:: DexCompilationUnit(CompilationUnit* cu, code_item_(code_item), class_def_idx_(class_def_idx), dex_method_idx_(method_idx), - access_flags_(access_flags), - symbol_(StringPrintf("dex_%s", MangleForJni(PrettyMethod(dex_method_idx_, *dex_file_)).c_str())) { + access_flags_(access_flags) { +} + +const std::string& DexCompilationUnit::GetSymbol() { + if (symbol_.empty()) { + symbol_ = "dex_"; + symbol_ += MangleForJni(PrettyMethod(dex_method_idx_, *dex_file_)); + } + return symbol_; } } // namespace art diff --git a/src/compiler/driver/dex_compilation_unit.h b/src/compiler/driver/dex_compilation_unit.h index 0b90aaafdf..3c6129d642 100644 --- a/src/compiler/driver/dex_compilation_unit.h +++ b/src/compiler/driver/dex_compilation_unit.h @@ -92,9 +92,7 @@ class DexCompilationUnit { return ((access_flags_ & kAccSynchronized) != 0); } - const std::string& GetSymbol() const { - return symbol_; - } + const std::string& GetSymbol(); private: CompilationUnit* const cu_; @@ -110,7 +108,7 @@ class DexCompilationUnit { const uint32_t dex_method_idx_; const uint32_t access_flags_; - const std::string symbol_; + std::string symbol_; }; } // namespace art diff --git a/src/compiler/llvm/llvm_compilation_unit.h b/src/compiler/llvm/llvm_compilation_unit.h index d96e778912..857d924840 100644 --- a/src/compiler/llvm/llvm_compilation_unit.h +++ b/src/compiler/llvm/llvm_compilation_unit.h @@ -81,10 +81,10 @@ class LlvmCompilationUnit { void SetCompilerDriver(CompilerDriver* driver) { driver_ = driver; } - const DexCompilationUnit* GetDexCompilationUnit() { + DexCompilationUnit* GetDexCompilationUnit() { return dex_compilation_unit_; } - void SetDexCompilationUnit(const DexCompilationUnit* dex_compilation_unit) { + void SetDexCompilationUnit(DexCompilationUnit* dex_compilation_unit) { dex_compilation_unit_ = dex_compilation_unit; } @@ -113,7 +113,7 @@ class LlvmCompilationUnit { UniquePtr<IntrinsicHelper> intrinsic_helper_; UniquePtr<LLVMInfo> llvm_info_; CompilerDriver* driver_; - const DexCompilationUnit* dex_compilation_unit_; + DexCompilationUnit* dex_compilation_unit_; std::string bitcode_filename_; diff --git a/src/locks.cc b/src/locks.cc index eb0620c0c3..51a40c383a 100644 --- a/src/locks.cc +++ b/src/locks.cc @@ -22,7 +22,7 @@ namespace art { Mutex* Locks::abort_lock_ = NULL; Mutex* Locks::breakpoint_lock_ = NULL; -Mutex* Locks::classlinker_classes_lock_ = NULL; +ReaderWriterMutex* Locks::classlinker_classes_lock_ = NULL; ReaderWriterMutex* Locks::heap_bitmap_lock_ = NULL; Mutex* Locks::logging_lock_ = NULL; ReaderWriterMutex* Locks::mutator_lock_ = NULL; @@ -52,7 +52,8 @@ void Locks::Init() { DCHECK(breakpoint_lock_ == NULL); breakpoint_lock_ = new Mutex("breakpoint lock", kBreakpointLock); DCHECK(classlinker_classes_lock_ == NULL); - classlinker_classes_lock_ = new Mutex("ClassLinker classes lock", kClassLinkerClassesLock); + classlinker_classes_lock_ = new ReaderWriterMutex("ClassLinker classes lock", + kClassLinkerClassesLock); DCHECK(heap_bitmap_lock_ == NULL); heap_bitmap_lock_ = new ReaderWriterMutex("heap bitmap lock", kHeapBitmapLock); DCHECK(mutator_lock_ == NULL); diff --git a/src/locks.h b/src/locks.h index 431a14816a..ceb04b937a 100644 --- a/src/locks.h +++ b/src/locks.h @@ -143,7 +143,7 @@ class Locks { static Mutex* trace_lock_ ACQUIRED_AFTER(breakpoint_lock_); // Guards lists of classes within the class linker. - static Mutex* classlinker_classes_lock_ ACQUIRED_AFTER(trace_lock_); + static ReaderWriterMutex* classlinker_classes_lock_ ACQUIRED_AFTER(trace_lock_); // When declaring any Mutex add DEFAULT_MUTEX_ACQUIRED_AFTER to use annotalysis to check the code // doesn't try to hold a higher level Mutex. diff --git a/src/verifier/method_verifier.cc b/src/verifier/method_verifier.cc index 1b2d9f35bf..a7d26bb602 100644 --- a/src/verifier/method_verifier.cc +++ b/src/verifier/method_verifier.cc @@ -955,9 +955,9 @@ bool MethodVerifier::VerifyCodeFlow() { const std::vector<uint8_t>* dex_gc_map = CreateLengthPrefixedDexGcMap(*(map.get())); verifier::MethodVerifier::SetDexGcMap(ref, *dex_gc_map); - MethodVerifier::PcToConreteMethod* pc_to_conrete_method = GenerateDevirtMap(); - if(pc_to_conrete_method != NULL ) { - SetDevirtMap(ref, pc_to_conrete_method); + MethodVerifier::PcToConcreteMethod* pc_to_concrete_method = GenerateDevirtMap(); + if(pc_to_concrete_method != NULL ) { + SetDevirtMap(ref, pc_to_concrete_method); } return true; } @@ -3160,7 +3160,7 @@ void MethodVerifier::ComputeGcMapSizes(size_t* gc_points, size_t* ref_bitmap_bit *log2_max_gc_pc = i; } -MethodVerifier::PcToConreteMethod* MethodVerifier::GenerateDevirtMap() { +MethodVerifier::PcToConcreteMethod* MethodVerifier::GenerateDevirtMap() { // It is risky to rely on reg_types for sharpening in cases of soft // verification, we might end up sharpening to a wrong implementation. Just abort. @@ -3168,7 +3168,7 @@ MethodVerifier::PcToConreteMethod* MethodVerifier::GenerateDevirtMap() { return NULL; } - UniquePtr<PcToConreteMethod> pc_to_concrete_method(new PcToConreteMethod()); + UniquePtr<PcToConcreteMethod> pc_to_concrete_method(new PcToConcreteMethod()); uint32_t dex_pc = 0; const uint16_t* insns = code_item_->insns_ ; const Instruction* inst = Instruction::At(insns); @@ -3338,7 +3338,7 @@ void MethodVerifier::SetDexGcMap(CompilerDriver::MethodReference ref, const std: CHECK(GetDexGcMap(ref) != NULL); } -void MethodVerifier::SetDevirtMap(CompilerDriver::MethodReference ref, const PcToConreteMethod* devirt_map) { +void MethodVerifier::SetDevirtMap(CompilerDriver::MethodReference ref, const PcToConcreteMethod* devirt_map) { MutexLock mu(Thread::Current(), *devirt_maps_lock_); DevirtualizationMapTable::iterator it = devirt_maps_->find(ref); @@ -3371,7 +3371,7 @@ const CompilerDriver::MethodReference* MethodVerifier::GetDevirtMap(const Compil } // Look up the PC in the map, get the concrete method to execute and return its reference. - MethodVerifier::PcToConreteMethod::const_iterator pc_to_concrete_method = it->second->find(dex_pc); + MethodVerifier::PcToConcreteMethod::const_iterator pc_to_concrete_method = it->second->find(dex_pc); if(pc_to_concrete_method != it->second->end()) { return &(pc_to_concrete_method->second); } else { diff --git a/src/verifier/method_verifier.h b/src/verifier/method_verifier.h index 755d089bd6..9b4b8e5503 100644 --- a/src/verifier/method_verifier.h +++ b/src/verifier/method_verifier.h @@ -584,15 +584,16 @@ class MethodVerifier { // Devirtualization map. - typedef SafeMap<const uint32_t, CompilerDriver::MethodReference> PcToConreteMethod; - typedef SafeMap<const CompilerDriver::MethodReference, const PcToConreteMethod*, + typedef SafeMap<const uint32_t, CompilerDriver::MethodReference> PcToConcreteMethod; + typedef SafeMap<const CompilerDriver::MethodReference, const PcToConcreteMethod*, CompilerDriver::MethodReferenceComparator> DevirtualizationMapTable; - MethodVerifier::PcToConreteMethod* GenerateDevirtMap() + MethodVerifier::PcToConcreteMethod* GenerateDevirtMap() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static Mutex* devirt_maps_lock_ DEFAULT_MUTEX_ACQUIRED_AFTER; static DevirtualizationMapTable* devirt_maps_ GUARDED_BY(devirt_maps_lock_); - static void SetDevirtMap(CompilerDriver::MethodReference ref, const PcToConreteMethod* pc_method_map); + static void SetDevirtMap(CompilerDriver::MethodReference ref, + const PcToConcreteMethod* pc_method_map) LOCKS_EXCLUDED(devirt_maps_lock_); typedef std::set<CompilerDriver::ClassReference> RejectedClassesTable; static Mutex* rejected_classes_lock_ DEFAULT_MUTEX_ACQUIRED_AFTER; diff --git a/src/verifier/reg_type.cc b/src/verifier/reg_type.cc index 32679f6100..5db6affcae 100644 --- a/src/verifier/reg_type.cc +++ b/src/verifier/reg_type.cc @@ -32,7 +32,6 @@ namespace art { namespace verifier { -static const bool kIsDebugBuild = false; UndefinedType* UndefinedType::instance_ = NULL; ConflictType* ConflictType::instance_ = NULL; BooleanType* BooleanType::instance = NULL; @@ -70,36 +69,44 @@ std::string BooleanType::Dump() const { std::string ConflictType::Dump() const { return "Conflict"; } + std::string ByteType::Dump() const { return "Byte"; } + std::string ShortType::Dump() const { return "short"; } + std::string CharType::Dump() const { return "Char"; } + std::string FloatType::Dump() const { return "float"; } + std::string LongLoType::Dump() const { return "long (Low Half)"; } + std::string LongHiType::Dump() const { return "long (High Half)"; } + std::string DoubleLoType::Dump() const { return "Double (Low Half)"; } + std::string DoubleHiType::Dump() const { return "Double (High Half)"; } + std::string IntegerType::Dump() const { return "Integer"; } - -DoubleHiType* DoubleHiType::CreateInstance(mirror::Class* klass, std::string& descriptor, +DoubleHiType* DoubleHiType::CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) { if (instance_ == NULL) { instance_ = new DoubleHiType(klass, descriptor, cache_id); @@ -119,7 +126,7 @@ void DoubleHiType::Destroy() { } } -DoubleLoType* DoubleLoType::CreateInstance(mirror::Class* klass, std::string& descriptor, +DoubleLoType* DoubleLoType::CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) { if (instance_ == NULL) { instance_ = new DoubleLoType(klass, descriptor, cache_id); @@ -139,7 +146,7 @@ void DoubleLoType::Destroy() { } } -LongLoType* LongLoType::CreateInstance(mirror::Class* klass, std::string& descriptor, +LongLoType* LongLoType::CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) { if (instance_ == NULL) { instance_ = new LongLoType(klass, descriptor, cache_id); @@ -147,7 +154,7 @@ LongLoType* LongLoType::CreateInstance(mirror::Class* klass, std::string& descri return instance_; } -LongHiType* LongHiType::CreateInstance(mirror::Class* klass, std::string& descriptor, +LongHiType* LongHiType::CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) { if (instance_ == NULL) { instance_ = new LongHiType(klass, descriptor, cache_id); @@ -179,9 +186,8 @@ void LongLoType::Destroy() { } } -FloatType* FloatType::CreateInstance(mirror::Class* klass, std::string& descriptor, - uint16_t cache_id) - SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { +FloatType* FloatType::CreateInstance(mirror::Class* klass, const std::string& descriptor, + uint16_t cache_id) { if (instance_ == NULL) { instance_ = new FloatType(klass, descriptor, cache_id); } @@ -199,17 +205,19 @@ void FloatType::Destroy() { } } -CharType* CharType::CreateInstance(mirror::Class* klass, std::string& descriptor, +CharType* CharType::CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) { if (instance_ == NULL) { instance_ = new CharType(klass, descriptor, cache_id); } return instance_; } + CharType* CharType::GetInstance() { CHECK(instance_ != NULL); return instance_; } + void CharType::Destroy() { if (instance_ != NULL) { delete instance_; @@ -217,81 +225,94 @@ void CharType::Destroy() { } } -ShortType* ShortType::CreateInstance(mirror::Class* klass, std::string& descriptor, +ShortType* ShortType::CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) { if (instance_ == NULL) { instance_ = new ShortType(klass, descriptor, cache_id); } return instance_; } + ShortType* ShortType::GetInstance() { CHECK(instance_ != NULL); return instance_; } + void ShortType::Destroy() { if (instance_ != NULL) { delete instance_; instance_ = NULL; } } -ByteType* ByteType::CreateInstance(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) - SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { + +ByteType* ByteType::CreateInstance(mirror::Class* klass, const std::string& descriptor, + uint16_t cache_id) { if (instance_ == NULL) { instance_ = new ByteType(klass, descriptor, cache_id); } return instance_; } + ByteType* ByteType::GetInstance() { CHECK(instance_ != NULL); return instance_; } + void ByteType::Destroy() { if (instance_ != NULL) { delete instance_; instance_ = NULL; } } -IntegerType* IntegerType::CreateInstance(mirror::Class* klass, std::string& descriptor, + +IntegerType* IntegerType::CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) { if (instance_ == NULL) { instance_ = new IntegerType(klass, descriptor, cache_id); } return instance_; } + IntegerType* IntegerType::GetInstance() { CHECK(instance_ != NULL); return instance_; } + void IntegerType::Destroy() { if (instance_ != NULL) { delete instance_; instance_ = NULL; } } -ConflictType* ConflictType::CreateInstance(mirror::Class* klass, std::string& descriptor, + +ConflictType* ConflictType::CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) { if (instance_ == NULL) { instance_ = new ConflictType(klass, descriptor, cache_id); } return instance_; } + ConflictType* ConflictType::GetInstance() { CHECK(instance_ != NULL); return instance_; } + void ConflictType::Destroy() { if (instance_ != NULL) { delete instance_; instance_ = NULL; } } -BooleanType* BooleanType::CreateInstance(mirror::Class* klass, std::string& descriptor, + +BooleanType* BooleanType::CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) { if (BooleanType::instance == NULL) { instance = new BooleanType(klass, descriptor, cache_id); } return BooleanType::instance; } + BooleanType* BooleanType::GetInstance() { CHECK(BooleanType::instance != NULL); return BooleanType::instance; @@ -307,23 +328,27 @@ void BooleanType::Destroy() { std::string UndefinedType::Dump() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { return "Undefined"; } -UndefinedType* UndefinedType::CreateInstance(mirror::Class* klass, std::string& descriptor, + +UndefinedType* UndefinedType::CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) { if (instance_ == NULL) { instance_ = new UndefinedType(klass, descriptor, cache_id); } return instance_; } + UndefinedType* UndefinedType::GetInstance() { CHECK(instance_ != NULL); return instance_; } + void UndefinedType::Destroy() { if (instance_ != NULL) { delete instance_; instance_ = NULL; } } + std::string UnresolvedMergedType::Dump() const { std::stringstream result; std::set<uint16_t> types = GetMergedTypes(); @@ -338,6 +363,7 @@ std::string UnresolvedMergedType::Dump() const { result << ")"; return result.str(); } + std::string UnresolvedSuperClass::Dump() const { std::stringstream result; uint16_t super_type_id = GetUnresolvedSuperClassChildId(); @@ -358,7 +384,7 @@ std::string UnresolvedUninitializedRefType::Dump() const { return result.str(); } -std::string UnresolvedUninitialisedThisRefType::Dump() const { +std::string UnresolvedUninitializedThisRefType::Dump() const { std::stringstream result; result << "Unresolved And Uninitialized This Reference" << PrettyDescriptor(GetDescriptor()); return result.str(); @@ -376,13 +402,14 @@ std::string PreciseReferenceType::Dump() const { return result.str(); } -std::string UninitialisedReferenceType::Dump() const { +std::string UninitializedReferenceType::Dump() const { std::stringstream result; result << "Uninitialized Reference" << ": " << PrettyDescriptor(GetClass()); result << " Allocation PC: " << GetAllocationPc(); return result.str(); } -std::string UninitialisedThisReferenceType::Dump() const { + +std::string UninitializedThisReferenceType::Dump() const { std::stringstream result; result << "Uninitialized This Reference" << ": " << PrettyDescriptor(GetClass()); result << "Allocation PC: " << GetAllocationPc(); @@ -459,76 +486,77 @@ std::string ImpreciseConstHiType::Dump() const { return result.str(); } -BooleanType::BooleanType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) - : RegType(klass, descriptor, cache_id) { +BooleanType::BooleanType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) + : RegType(klass, descriptor, cache_id) { } -ConflictType::ConflictType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) +ConflictType::ConflictType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) : RegType(klass, descriptor, cache_id) { } -ByteType::ByteType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) +ByteType::ByteType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) : RegType(klass, descriptor, cache_id) { } -ShortType::ShortType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) +ShortType::ShortType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) : RegType(klass, descriptor, cache_id) { } -CharType::CharType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) +CharType::CharType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) : RegType(klass, descriptor, cache_id) { } -IntegerType::IntegerType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) +IntegerType::IntegerType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) : RegType(klass, descriptor, cache_id) { } -ConstantType::ConstantType(uint32_t constat, uint16_t cache_id) - SHARED_LOCKS_REQUIRED(Locks::mutator_lock_): RegType(NULL, "", cache_id), constant_(constat) { +ConstantType::ConstantType(uint32_t constant, uint16_t cache_id) + : RegType(NULL, "", cache_id), constant_(constant) { } -ReferenceType::ReferenceType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) +ReferenceType::ReferenceType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) : RegType(klass, descriptor, cache_id) { } -PreciseReferenceType::PreciseReferenceType(mirror::Class* klass, std::string& descriptor, +PreciseReferenceType::PreciseReferenceType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) : RegType(klass, descriptor, cache_id) { DCHECK(klass->IsInstantiable()); } -UnresolvedUninitialisedThisRefType::UnresolvedUninitialisedThisRefType(std::string& descriptor, +UnresolvedUninitializedThisRefType::UnresolvedUninitializedThisRefType(const std::string& descriptor, uint16_t cache_id) : UninitializedType(NULL, descriptor, 0, cache_id) { } -UnresolvedUninitializedRefType::UnresolvedUninitializedRefType( std::string& descriptor, +UnresolvedUninitializedRefType::UnresolvedUninitializedRefType(const std::string& descriptor, uint32_t allocation_pc, uint16_t cache_id) : UninitializedType(NULL, descriptor, allocation_pc, cache_id) { } -UninitialisedReferenceType::UninitialisedReferenceType(mirror::Class* klass, - std::string& descriptor, uint32_t allocation_pc, uint16_t cache_id) +UninitializedReferenceType::UninitializedReferenceType(mirror::Class* klass, + const std::string& descriptor, + uint32_t allocation_pc, uint16_t cache_id) : UninitializedType(klass, descriptor, allocation_pc, cache_id) { } -LongHiType::LongHiType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) +LongHiType::LongHiType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) : RegType(klass, descriptor, cache_id) { } -FloatType::FloatType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) +FloatType::FloatType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) : RegType(klass, descriptor, cache_id) { } -DoubleLoType::DoubleLoType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) +DoubleLoType::DoubleLoType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) : RegType(klass, descriptor, cache_id) { } -DoubleHiType::DoubleHiType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) +DoubleHiType::DoubleHiType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) : RegType(klass, descriptor, cache_id) { } -LongLoType::LongLoType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) +LongLoType::LongLoType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) : RegType(klass, descriptor, cache_id) { } @@ -749,10 +777,12 @@ int32_t ConstantType::ConstantValue() const { DCHECK(IsConstantTypes()); return constant_; } + int32_t ConstantType::ConstantValueLo() const { DCHECK(IsConstantLo()); return constant_; } + int32_t ConstantType::ConstantValueHi() const { if (IsConstantHi() || IsPreciseConstantHi() || IsImpreciseConstantHi()) { return constant_; @@ -761,6 +791,7 @@ int32_t ConstantType::ConstantValueHi() const { return 0; } } + static const RegType& SelectNonConstant(const RegType& a, const RegType& b) { return a.IsConstant() ? b : a; } @@ -951,7 +982,7 @@ void RegType::CheckInvariants() const { } } -UninitializedType::UninitializedType(mirror::Class* klass, std::string& descriptor, +UninitializedType::UninitializedType(mirror::Class* klass, const std::string& descriptor, uint32_t allocation_pc, uint16_t cache_id) : RegType(klass, descriptor, cache_id), allocation_pc_(allocation_pc) { } @@ -960,15 +991,15 @@ void UninitializedType::CheckInvariants() const { CHECK_EQ(allocation_pc_, 0U) << *this; } -void UninitialisedThisReferenceType::CheckInvariants() const { +void UninitializedThisReferenceType::CheckInvariants() const { UninitializedType::CheckInvariants(); } -UninitialisedThisReferenceType::UninitialisedThisReferenceType(mirror::Class* klass, - std::string& descriptor, uint16_t cache_id) : UninitializedType(klass, descriptor, 0, cache_id) { +UninitializedThisReferenceType::UninitializedThisReferenceType(mirror::Class* klass, + const std::string& descriptor, uint16_t cache_id) : UninitializedType(klass, descriptor, 0, cache_id) { } -void UnresolvedUninitialisedThisRefType::CheckInvariants() const { +void UnresolvedUninitializedThisRefType::CheckInvariants() const { UninitializedType::CheckInvariants(); CHECK(!descriptor_.empty()) << *this; CHECK(klass_ == NULL) << *this; diff --git a/src/verifier/reg_type.h b/src/verifier/reg_type.h index 7c4253604c..39c33c6c97 100644 --- a/src/verifier/reg_type.h +++ b/src/verifier/reg_type.h @@ -268,9 +268,8 @@ class RegType { inline virtual bool IsLong() const { return false; } - bool HasClass() const { - return IsReference() || IsPreciseReference() || IsUninitializedReference() || - IsUninitializedThisReference(); + virtual bool HasClass() const { + return false; } bool IsJavaLangObject() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); bool IsArrayTypes() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); @@ -326,7 +325,7 @@ class RegType { static mirror::Class* ClassJoin(mirror::Class* s, mirror::Class* t) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); - RegType(mirror::Class* klass, std::string descriptor, uint16_t cache_id) + RegType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) : descriptor_(descriptor), klass_(klass), cache_id_(cache_id) { } @@ -349,12 +348,13 @@ class ConflictType : public RegType { return true; } std::string Dump() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); - static ConflictType* CreateInstance(mirror::Class* klass, std::string& descriptor, - uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); + static ConflictType* CreateInstance(mirror::Class* klass, const std::string& descriptor, + uint16_t cache_id) + SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static ConflictType* GetInstance(); static void Destroy(); private: - ConflictType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) + ConflictType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static ConflictType* instance_; }; @@ -365,13 +365,13 @@ class UndefinedType : public RegType { return true; } std::string Dump() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); - static UndefinedType* CreateInstance(mirror::Class* klass, std::string& descriptor, + static UndefinedType* CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static UndefinedType* GetInstance(); static void Destroy(); private: - UndefinedType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) + UndefinedType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) : RegType(klass, descriptor, cache_id) { } @@ -386,13 +386,13 @@ class IntegerType : public RegType { return true; } std::string Dump() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); - static IntegerType* CreateInstance(mirror::Class* klass, std::string& descriptor, + static IntegerType* CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static IntegerType* GetInstance(); static void Destroy(); private: - IntegerType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) + IntegerType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static IntegerType* instance_; }; @@ -403,13 +403,13 @@ class BooleanType : public RegType { return true; } std::string Dump() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); - static BooleanType* CreateInstance(mirror::Class* klass, std::string& descriptor, + static BooleanType* CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static BooleanType* GetInstance(); static void Destroy(); private: - BooleanType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) + BooleanType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static BooleanType* instance; }; @@ -420,13 +420,13 @@ class ByteType : public RegType { return true; } std::string Dump() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); - static ByteType* CreateInstance(mirror::Class* klass, std::string& descriptor, + static ByteType* CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static ByteType* GetInstance(); static void Destroy(); private: - ByteType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) + ByteType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static ByteType* instance_; }; @@ -437,13 +437,13 @@ class ShortType : public RegType { return true; } std::string Dump() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); - static ShortType* CreateInstance(mirror::Class* klass, std::string& descriptor, + static ShortType* CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static ShortType* GetInstance(); static void Destroy(); private: - ShortType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) + ShortType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static ShortType* instance_; }; @@ -454,13 +454,13 @@ class CharType : public RegType { return true; } std::string Dump() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); - static CharType* CreateInstance(mirror::Class* klass, std::string& descriptor, + static CharType* CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static CharType* GetInstance(); static void Destroy(); private: - CharType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) + CharType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static CharType* instance_; }; @@ -471,13 +471,13 @@ class FloatType : public RegType { return true; } std::string Dump() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); - static FloatType* CreateInstance(mirror::Class* klass, std::string& descriptor, + static FloatType* CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static FloatType* GetInstance(); static void Destroy(); private: - FloatType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) + FloatType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static FloatType* instance_; }; @@ -491,13 +491,13 @@ class LongLoType : public RegType { bool IsLong() const { return true; } - static LongLoType* CreateInstance(mirror::Class* klass, std::string& descriptor, + static LongLoType* CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static LongLoType* GetInstance(); static void Destroy(); private: - LongLoType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) + LongLoType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static LongLoType* instance_; }; @@ -508,13 +508,13 @@ class LongHiType : public RegType { bool IsLongHi() const { return true; } - static LongHiType* CreateInstance(mirror::Class* klass, std::string& descriptor, + static LongHiType* CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static LongHiType* GetInstance(); static void Destroy(); private: - LongHiType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) + LongHiType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static LongHiType* instance_; }; @@ -528,13 +528,13 @@ class DoubleLoType : public RegType { bool IsDouble() const { return true; } - static DoubleLoType* CreateInstance(mirror::Class* klass, std::string& descriptor, + static DoubleLoType* CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static DoubleLoType* GetInstance(); static void Destroy(); private: - DoubleLoType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) + DoubleLoType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static DoubleLoType* instance_; }; @@ -545,13 +545,13 @@ class DoubleHiType : public RegType { virtual bool IsDoubleHi() const { return true; } - static DoubleHiType* CreateInstance(mirror::Class* klass, std::string& descriptor, + static DoubleHiType* CreateInstance(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static DoubleHiType* GetInstance(); static void Destroy(); private: - DoubleHiType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) + DoubleHiType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); static DoubleHiType* instance_; }; @@ -664,7 +664,7 @@ class ImpreciseConstHiType : public ConstantType { class UninitializedType : public RegType { public: - UninitializedType(mirror::Class* klass, std::string& descriptor, uint32_t allocation_pc, + UninitializedType(mirror::Class* klass, const std::string& descriptor, uint32_t allocation_pc, uint16_t cache_id); inline virtual ~UninitializedType() { } @@ -679,20 +679,23 @@ class UninitializedType : public RegType { const uint32_t allocation_pc_; }; -class UninitialisedReferenceType : public UninitializedType { +class UninitializedReferenceType : public UninitializedType { public: - UninitialisedReferenceType(mirror::Class* klass, std::string& descriptor, uint32_t allocation_pc, + UninitializedReferenceType(mirror::Class* klass, const std::string& descriptor, uint32_t allocation_pc, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); bool IsUninitializedReference() const { return true; } + bool HasClass() const { + return true; + } std::string Dump() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); }; class UnresolvedUninitializedRefType : public UninitializedType { public: - UnresolvedUninitializedRefType(std::string& descriptor, uint32_t allocation_pc, + UnresolvedUninitializedRefType(const std::string& descriptor, uint32_t allocation_pc, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); void CheckInvariants() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); bool IsUnresolvedAndUninitializedReference() const { @@ -701,20 +704,23 @@ class UnresolvedUninitializedRefType : public UninitializedType { std::string Dump() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); }; -class UninitialisedThisReferenceType : public UninitializedType { +class UninitializedThisReferenceType : public UninitializedType { public: - UninitialisedThisReferenceType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) + UninitializedThisReferenceType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); std::string Dump() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); void CheckInvariants() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); - inline virtual bool IsUninitializedThisReference() const { + virtual bool IsUninitializedThisReference() const { + return true; + } + bool HasClass() const { return true; } }; -class UnresolvedUninitialisedThisRefType : public UninitializedType { +class UnresolvedUninitializedThisRefType : public UninitializedType { public: - UnresolvedUninitialisedThisRefType(std::string& descriptor, uint16_t cache_id) + UnresolvedUninitializedThisRefType(const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); void CheckInvariants() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); std::string Dump() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); @@ -725,27 +731,33 @@ class UnresolvedUninitialisedThisRefType : public UninitializedType { class ReferenceType : public RegType { public: - ReferenceType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) + ReferenceType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); bool IsReference() const { return true; } + bool HasClass() const { + return true; + } std::string Dump() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); }; class PreciseReferenceType : public RegType { public: - PreciseReferenceType(mirror::Class* klass, std::string& descriptor, uint16_t cache_id) + PreciseReferenceType(mirror::Class* klass, const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); std::string Dump() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); bool IsPreciseReference() const { return true; } + bool HasClass() const { + return true; + } }; class UnresolvedReferenceType : public RegType { public: - UnresolvedReferenceType(std::string& descriptor, uint16_t cache_id) + UnresolvedReferenceType(const std::string& descriptor, uint16_t cache_id) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) : RegType(NULL, descriptor, cache_id) { } std::string Dump() const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); diff --git a/src/verifier/reg_type_cache-inl.h b/src/verifier/reg_type_cache-inl.h index f6b0056536..42474d1849 100644 --- a/src/verifier/reg_type_cache-inl.h +++ b/src/verifier/reg_type_cache-inl.h @@ -24,7 +24,7 @@ namespace art { namespace verifier { template <class Type> -Type* RegTypeCache::CreatePrimitiveTypeInstance(std::string descriptor) { +Type* RegTypeCache::CreatePrimitiveTypeInstance(const std::string& descriptor) { mirror::Class* klass = NULL; // Try loading the class from linker. if (!descriptor.empty()) { @@ -35,6 +35,12 @@ Type* RegTypeCache::CreatePrimitiveTypeInstance(std::string descriptor) { return entry; } +inline const art::verifier::RegType& RegTypeCache::GetFromId(uint16_t id) const { + DCHECK_LT(id, entries_.size()); + RegType* result = entries_[id]; + DCHECK(result != NULL); + return *result; +} } // namespace verifier } // namespace art #endif // ART_SRC_VERIFIER_REG_TYPE_CACHE_INL_H_ diff --git a/src/verifier/reg_type_cache.cc b/src/verifier/reg_type_cache.cc index e914d1e679..57a825b0bb 100644 --- a/src/verifier/reg_type_cache.cc +++ b/src/verifier/reg_type_cache.cc @@ -24,6 +24,7 @@ namespace art { namespace verifier { + bool RegTypeCache::primitive_initialized_ = false; uint16_t RegTypeCache::primitive_start_ = 0; uint16_t RegTypeCache::primitive_count_ = 0; @@ -49,9 +50,10 @@ void RegTypeCache::FillPrimitiveTypes() { DCHECK_EQ(entries_.size(), primitive_count_); } -const RegType& RegTypeCache::FromDescriptor(mirror::ClassLoader* loader, const char* descriptor, bool precise) { - CHECK(RegTypeCache::primitive_initialized_); - if (std::string(descriptor).length() == 1) { +const RegType& RegTypeCache::FromDescriptor(mirror::ClassLoader* loader, const char* descriptor, + bool precise) { + DCHECK(RegTypeCache::primitive_initialized_); + if (descriptor[1] == '\0') { switch (descriptor[0]) { case 'Z': return Boolean(); @@ -80,15 +82,7 @@ const RegType& RegTypeCache::FromDescriptor(mirror::ClassLoader* loader, const c } }; -const art::verifier::RegType& RegTypeCache::GetFromId(uint16_t id) const { - DCHECK_LT(id, entries_.size()); - RegType* result = entries_[id]; - DCHECK(result != NULL); - return *result; -} - -const RegType& RegTypeCache::RegTypeFromPrimitiveType( - Primitive::Type prim_type) const { +const RegType& RegTypeCache::RegTypeFromPrimitiveType(Primitive::Type prim_type) const { CHECK(RegTypeCache::primitive_initialized_); switch (prim_type) { case Primitive::kPrimBoolean: @@ -113,21 +107,22 @@ const RegType& RegTypeCache::RegTypeFromPrimitiveType( } } -bool RegTypeCache::MatchDescriptor(size_t idx, std::string& descriptor, bool precise) { +bool RegTypeCache::MatchDescriptor(size_t idx, const char* descriptor, bool precise) { RegType* cur_entry = entries_[idx]; if (cur_entry->HasClass()) { // Check the descriptor in the reg_type if available. if(!cur_entry->descriptor_.empty()) { - if (descriptor == cur_entry->descriptor_ && MatchingPrecisionForClass(cur_entry, precise)) { + if (cur_entry->descriptor_ == descriptor && MatchingPrecisionForClass(cur_entry, precise)) { return true; } } else { - // Descriptor not found in reg_type , maybe available in Class object. + // TODO: maintain an invariant that when we have a Class the descriptor is computed from that. + // Descriptor not found in reg_type, maybe available in Class object. // So we might have cases where we have the class but not the descriptor // for that class we need the class helper to get the descriptor // and match it with the one we are given. ClassHelper kh(cur_entry->GetClass()); - if ((strcmp(descriptor.c_str(), kh.GetDescriptor()) == 0) && + if ((strcmp(descriptor, kh.GetDescriptor()) == 0) && MatchingPrecisionForClass(cur_entry, precise)) { return true; } @@ -138,16 +133,15 @@ bool RegTypeCache::MatchDescriptor(size_t idx, std::string& descriptor, bool pre return false; } - -mirror::Class* RegTypeCache::ResolveClass(std::string descriptor, mirror::ClassLoader* loader) { +mirror::Class* RegTypeCache::ResolveClass(const char* descriptor, mirror::ClassLoader* loader) { // Class was not found, must create new type. // Try resolving class ClassLinker* class_linker = Runtime::Current()->GetClassLinker(); mirror::Class* klass = NULL; if (can_load_classes_) { - klass = class_linker->FindClass(descriptor.c_str(), loader); + klass = class_linker->FindClass(descriptor, loader); } else { - klass = class_linker->LookupClass(descriptor.c_str(), loader); + klass = class_linker->LookupClass(descriptor, loader); if (klass != NULL && !klass->IsLoaded()) { // We found the class but without it being loaded its not safe for use. klass = NULL; @@ -155,6 +149,7 @@ mirror::Class* RegTypeCache::ResolveClass(std::string descriptor, mirror::ClassL } return klass; } + void RegTypeCache::ClearException() { if (can_load_classes_) { DCHECK(Thread::Current()->IsExceptionPending()); @@ -163,8 +158,9 @@ void RegTypeCache::ClearException() { DCHECK(!Thread::Current()->IsExceptionPending()); } } -const RegType& RegTypeCache::From(mirror::ClassLoader* loader, std::string descriptor, bool precise) { +const RegType& RegTypeCache::From(mirror::ClassLoader* loader, const char* descriptor, + bool precise) { // Try looking up the class in the cache first. for (size_t i = primitive_count_; i < entries_.size(); i++) { if (MatchDescriptor(i, descriptor, precise)) { @@ -198,7 +194,7 @@ const RegType& RegTypeCache::From(mirror::ClassLoader* loader, std::string descr // We tried loading the class and failed, this might get an exception raised // so we want to clear it before we go on. ClearException(); - if (IsValidDescriptor(descriptor.c_str())) { + if (IsValidDescriptor(descriptor)) { RegType* entry = new UnresolvedReferenceType(descriptor, entries_.size()); entries_.push_back(entry); return *entry; @@ -209,6 +205,7 @@ const RegType& RegTypeCache::From(mirror::ClassLoader* loader, std::string descr } } } + const RegType& RegTypeCache::FromClass(mirror::Class* klass, bool precise) { if (klass->IsPrimitive()) { return RegTypeFromPrimitiveType(klass->GetPrimitiveType()); @@ -223,11 +220,10 @@ const RegType& RegTypeCache::FromClass(mirror::Class* klass, bool precise) { } // No reference to the class was found, create new reference. RegType* entry; - std::string empty = ""; if (precise) { - entry = new PreciseReferenceType(klass, empty, entries_.size()); + entry = new PreciseReferenceType(klass, "", entries_.size()); } else { - entry = new ReferenceType(klass, empty, entries_.size()); + entry = new ReferenceType(klass, "", entries_.size()); } entries_.push_back(entry); return *entry; @@ -309,13 +305,14 @@ const RegType& RegTypeCache::FromUnresolvedMerge(const RegType& left, const RegT // Create entry. RegType* entry = new UnresolvedMergedType(left.GetId(), right.GetId(), this, entries_.size()); entries_.push_back(entry); -#ifndef NDEBUG - UnresolvedMergedType* tmp_entry = down_cast<UnresolvedMergedType*>(entry); - std::set<uint16_t> check_types = tmp_entry->GetMergedTypes(); - CHECK(check_types == types); -#endif + if (kIsDebugBuild) { + UnresolvedMergedType* tmp_entry = down_cast<UnresolvedMergedType*>(entry); + std::set<uint16_t> check_types = tmp_entry->GetMergedTypes(); + CHECK(check_types == types); + } return *entry; } + const RegType& RegTypeCache::FromUnresolvedSuperClass(const RegType& child) { // Check if entry already exists. for (size_t i = primitive_count_; i < entries_.size(); i++) { @@ -334,11 +331,12 @@ const RegType& RegTypeCache::FromUnresolvedSuperClass(const RegType& child) { entries_.push_back(entry); return *entry; } + const RegType& RegTypeCache::Uninitialized(const RegType& type, uint32_t allocation_pc) { RegType* entry = NULL; RegType* cur_entry = NULL; if (type.IsUnresolvedTypes()) { - std::string descriptor(type.GetDescriptor()); + const std::string& descriptor(type.GetDescriptor()); for (size_t i = primitive_count_; i < entries_.size(); i++) { cur_entry = entries_[i]; if (cur_entry->IsUnresolvedAndUninitializedReference() && @@ -347,29 +345,29 @@ const RegType& RegTypeCache::Uninitialized(const RegType& type, uint32_t allocat return *cur_entry; } } - entry = new UnresolvedUninitializedRefType(descriptor, allocation_pc, entries_.size()); + entry = new UnresolvedUninitializedRefType(descriptor.c_str(), allocation_pc, entries_.size()); } else { mirror::Class* klass = type.GetClass(); for (size_t i = primitive_count_; i < entries_.size(); i++) { cur_entry = entries_[i]; if (cur_entry->IsUninitializedReference() && - down_cast<UninitialisedReferenceType*>(cur_entry) + down_cast<UninitializedReferenceType*>(cur_entry) ->GetAllocationPc() == allocation_pc && cur_entry->GetClass() == klass) { return *cur_entry; } } - std::string descriptor(""); - entry = new UninitialisedReferenceType(klass, descriptor, allocation_pc, entries_.size()); + entry = new UninitializedReferenceType(klass, "", allocation_pc, entries_.size()); } entries_.push_back(entry); return *entry; } + const RegType& RegTypeCache::FromUninitialized(const RegType& uninit_type) { RegType* entry; if (uninit_type.IsUnresolvedTypes()) { - std::string descriptor(uninit_type.GetDescriptor()); + const std::string& descriptor(uninit_type.GetDescriptor()); for (size_t i = primitive_count_; i < entries_.size(); i++) { RegType* cur_entry = entries_[i]; if (cur_entry->IsUnresolvedReference() && @@ -377,7 +375,7 @@ const RegType& RegTypeCache::FromUninitialized(const RegType& uninit_type) { return *cur_entry; } } - entry = new UnresolvedReferenceType(descriptor, entries_.size()); + entry = new UnresolvedReferenceType(descriptor.c_str(), entries_.size()); } else { mirror::Class* klass = uninit_type.GetClass(); if(uninit_type.IsUninitializedThisReference() && !klass->IsFinal()) { @@ -388,10 +386,8 @@ const RegType& RegTypeCache::FromUninitialized(const RegType& uninit_type) { return *cur_entry; } } - std::string descriptor(""); - entry = new ReferenceType(klass, descriptor, entries_.size()); + entry = new ReferenceType(klass, "", entries_.size()); } else { - std::string descriptor; if (klass->IsFinal()) { if (klass->IsInstantiable()) { for (size_t i = primitive_count_; i < entries_.size(); i++) { @@ -401,7 +397,7 @@ const RegType& RegTypeCache::FromUninitialized(const RegType& uninit_type) { } } // Precise type was not found , create one ! - entry = new PreciseReferenceType(klass, descriptor, entries_.size()); + entry = new PreciseReferenceType(klass, "", entries_.size()); } else { return Conflict(); } @@ -414,26 +410,30 @@ const RegType& RegTypeCache::FromUninitialized(const RegType& uninit_type) { return *cur_entry; } } - entry = new ReferenceType(klass, descriptor, entries_.size()); + entry = new ReferenceType(klass, "", entries_.size()); } } } entries_.push_back(entry); return *entry; } -const RegType& RegTypeCache::ByteConstant() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { + +const RegType& RegTypeCache::ByteConstant() { return FromCat1Const(std::numeric_limits<jbyte>::min(), false); } -const RegType& RegTypeCache::ShortConstant() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { + +const RegType& RegTypeCache::ShortConstant() { return FromCat1Const(std::numeric_limits<jshort>::min(), false); } -const RegType& RegTypeCache::IntConstant() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { + +const RegType& RegTypeCache::IntConstant() { return FromCat1Const(std::numeric_limits<jint>::max(), false); } + const RegType& RegTypeCache::UninitializedThisArgument(const RegType& type) { RegType* entry; if (type.IsUnresolvedTypes()) { - std::string descriptor(type.GetDescriptor()); + const std::string& descriptor(type.GetDescriptor()); for (size_t i = primitive_count_; i < entries_.size(); i++) { RegType* cur_entry = entries_[i]; if (cur_entry->IsUnresolvedAndUninitializedThisReference() && @@ -441,7 +441,7 @@ const RegType& RegTypeCache::UninitializedThisArgument(const RegType& type) { return *cur_entry; } } - entry = new UnresolvedUninitialisedThisRefType(descriptor, entries_.size()); + entry = new UnresolvedUninitializedThisRefType(descriptor, entries_.size()); } else { mirror::Class* klass = type.GetClass(); for (size_t i = primitive_count_; i < entries_.size(); i++) { @@ -451,12 +451,12 @@ const RegType& RegTypeCache::UninitializedThisArgument(const RegType& type) { return *cur_entry; } } - std::string descriptor(""); - entry = new UninitialisedThisReferenceType(klass, descriptor, entries_.size()); + entry = new UninitializedThisReferenceType(klass, "", entries_.size()); } entries_.push_back(entry); return *entry; } + const RegType& RegTypeCache::FromCat1Const(int32_t value, bool precise) { for (size_t i = primitive_count_; i < entries_.size(); i++) { RegType* cur_entry = entries_[i]; @@ -514,8 +514,8 @@ const RegType& RegTypeCache::FromCat2ConstHi(int32_t value, bool precise) { const RegType& RegTypeCache::GetComponentType(const RegType& array, mirror::ClassLoader* loader) { CHECK(array.IsArrayTypes()); if (array.IsUnresolvedTypes()) { - std::string descriptor(array.GetDescriptor()); - std::string component(descriptor.substr(1, descriptor.size() - 1)); + const std::string& descriptor(array.GetDescriptor()); + const std::string component(descriptor.substr(1, descriptor.size() - 1)); return FromDescriptor(loader, component.c_str(), false); } else { mirror::Class* klass = array.GetClass()->GetComponentType(); diff --git a/src/verifier/reg_type_cache.h b/src/verifier/reg_type_cache.h index 602c95086b..a5304dbbb4 100644 --- a/src/verifier/reg_type_cache.h +++ b/src/verifier/reg_type_cache.h @@ -52,10 +52,10 @@ class RegTypeCache { } static void ShutDown(); const art::verifier::RegType& GetFromId(uint16_t id) const; - const RegType& From(mirror::ClassLoader* loader, std::string descriptor, bool precise) + const RegType& From(mirror::ClassLoader* loader, const char* descriptor, bool precise) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); template <class Type> - static Type* CreatePrimitiveTypeInstance(std::string descriptor) + static Type* CreatePrimitiveTypeInstance(const std::string& descriptor) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); void FillPrimitiveTypes() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); const RegType& FromClass(mirror::Class* klass, bool precise) @@ -152,10 +152,10 @@ class RegTypeCache { // Whether or not we're allowed to load classes. const bool can_load_classes_; DISALLOW_COPY_AND_ASSIGN(RegTypeCache); - mirror::Class* ResolveClass(std::string descriptor, mirror::ClassLoader* loader) + mirror::Class* ResolveClass(const char* descriptor, mirror::ClassLoader* loader) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); void ClearException(); - bool MatchDescriptor(size_t idx, std::string& descriptor, bool precise) + bool MatchDescriptor(size_t idx, const char* descriptor, bool precise) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); }; |