summaryrefslogtreecommitdiff
path: root/runtime/runtime.cc
diff options
context:
space:
mode:
Diffstat (limited to 'runtime/runtime.cc')
-rw-r--r--runtime/runtime.cc126
1 files changed, 59 insertions, 67 deletions
diff --git a/runtime/runtime.cc b/runtime/runtime.cc
index 2618661ae3..65ea77ad29 100644
--- a/runtime/runtime.cc
+++ b/runtime/runtime.cc
@@ -49,6 +49,7 @@
#include "arch/x86_64/quick_method_frame_info_x86_64.h"
#include "arch/x86_64/registers_x86_64.h"
#include "art_field-inl.h"
+#include "art_method-inl.h"
#include "asm_support.h"
#include "atomic.h"
#include "base/arena_allocator.h"
@@ -73,7 +74,6 @@
#include "jni_internal.h"
#include "linear_alloc.h"
#include "mirror/array.h"
-#include "mirror/art_method-inl.h"
#include "mirror/class-inl.h"
#include "mirror/class_loader.h"
#include "mirror/field.h"
@@ -189,6 +189,7 @@ Runtime::Runtime()
is_native_bridge_loaded_(false),
zygote_max_failed_boots_(0) {
CheckAsmSupportOffsetsAndSizes();
+ std::fill(callee_save_methods_, callee_save_methods_ + arraysize(callee_save_methods_), 0u);
}
Runtime::~Runtime() {
@@ -425,20 +426,20 @@ static jobject CreateSystemClassLoader(Runtime* runtime) {
ScopedObjectAccess soa(Thread::Current());
ClassLinker* cl = Runtime::Current()->GetClassLinker();
+ auto pointer_size = cl->GetImagePointerSize();
StackHandleScope<2> hs(soa.Self());
Handle<mirror::Class> class_loader_class(
hs.NewHandle(soa.Decode<mirror::Class*>(WellKnownClasses::java_lang_ClassLoader)));
CHECK(cl->EnsureInitialized(soa.Self(), class_loader_class, true, true));
- mirror::ArtMethod* getSystemClassLoader =
- class_loader_class->FindDirectMethod("getSystemClassLoader", "()Ljava/lang/ClassLoader;");
+ ArtMethod* getSystemClassLoader = class_loader_class->FindDirectMethod(
+ "getSystemClassLoader", "()Ljava/lang/ClassLoader;", pointer_size);
CHECK(getSystemClassLoader != nullptr);
JValue result = InvokeWithJValues(soa, nullptr, soa.EncodeMethod(getSystemClassLoader), nullptr);
JNIEnv* env = soa.Self()->GetJniEnv();
- ScopedLocalRef<jobject> system_class_loader(env,
- soa.AddLocalReference<jobject>(result.GetL()));
+ ScopedLocalRef<jobject> system_class_loader(env, soa.AddLocalReference<jobject>(result.GetL()));
CHECK(system_class_loader.get() != nullptr);
soa.Self()->SetClassLoaderOverride(system_class_loader.get());
@@ -867,18 +868,17 @@ bool Runtime::Init(const RuntimeOptions& raw_options, bool ignore_unrecognized)
}
jit_options_.reset(jit::JitOptions::CreateFromRuntimeArguments(runtime_options));
- bool use_jit = jit_options_->UseJIT();
if (IsAotCompiler()) {
// If we are already the compiler at this point, we must be dex2oat. Don't create the jit in
// this case.
// If runtime_options doesn't have UseJIT set to true then CreateFromRuntimeArguments returns
// null and we don't create the jit.
- use_jit = false;
+ jit_options_->SetUseJIT(false);
}
// Use MemMap arena pool for jit, malloc otherwise. Malloc arenas are faster to allocate but
// can't be trimmed as easily.
- const bool use_malloc = !use_jit;
+ const bool use_malloc = IsAotCompiler();
arena_pool_.reset(new ArenaPool(use_malloc, false));
if (IsCompiler() && Is64BitInstructionSet(kRuntimeISA)) {
// 4gb, no malloc. Explanation in header.
@@ -1089,6 +1089,7 @@ bool Runtime::Init(const RuntimeOptions& raw_options, bool ignore_unrecognized)
}
VLOG(startup) << "Runtime::Init exiting";
+
return true;
}
@@ -1311,7 +1312,6 @@ mirror::Throwable* Runtime::GetPreAllocatedNoClassDefFoundError() {
void Runtime::VisitConstantRoots(RootVisitor* visitor) {
// Visit the classes held as static in mirror classes, these can be visited concurrently and only
// need to be visited once per GC since they never change.
- mirror::ArtMethod::VisitRoots(visitor);
mirror::Class::VisitRoots(visitor);
mirror::Constructor::VisitRoots(visitor);
mirror::Reference::VisitRoots(visitor);
@@ -1329,6 +1329,24 @@ void Runtime::VisitConstantRoots(RootVisitor* visitor) {
mirror::PrimitiveArray<int32_t>::VisitRoots(visitor); // IntArray
mirror::PrimitiveArray<int64_t>::VisitRoots(visitor); // LongArray
mirror::PrimitiveArray<int16_t>::VisitRoots(visitor); // ShortArray
+ // Visiting the roots of these ArtMethods is not currently required since all the GcRoots are
+ // null.
+ BufferedRootVisitor<16> buffered_visitor(visitor, RootInfo(kRootVMInternal));
+ if (HasResolutionMethod()) {
+ resolution_method_->VisitRoots(buffered_visitor);
+ }
+ if (HasImtConflictMethod()) {
+ imt_conflict_method_->VisitRoots(buffered_visitor);
+ }
+ if (imt_unimplemented_method_ != nullptr) {
+ imt_unimplemented_method_->VisitRoots(buffered_visitor);
+ }
+ for (size_t i = 0; i < kLastCalleeSaveType; ++i) {
+ auto* m = reinterpret_cast<ArtMethod*>(callee_save_methods_[i]);
+ if (m != nullptr) {
+ m->VisitRoots(buffered_visitor);
+ }
+ }
}
void Runtime::VisitConcurrentRoots(RootVisitor* visitor, VisitRootFlags flags) {
@@ -1350,17 +1368,9 @@ void Runtime::VisitNonThreadRoots(RootVisitor* visitor) {
java_vm_->VisitRoots(visitor);
sentinel_.VisitRootIfNonNull(visitor, RootInfo(kRootVMInternal));
pre_allocated_OutOfMemoryError_.VisitRootIfNonNull(visitor, RootInfo(kRootVMInternal));
- resolution_method_.VisitRoot(visitor, RootInfo(kRootVMInternal));
pre_allocated_NoClassDefFoundError_.VisitRootIfNonNull(visitor, RootInfo(kRootVMInternal));
- imt_conflict_method_.VisitRootIfNonNull(visitor, RootInfo(kRootVMInternal));
- imt_unimplemented_method_.VisitRootIfNonNull(visitor, RootInfo(kRootVMInternal));
- default_imt_.VisitRootIfNonNull(visitor, RootInfo(kRootVMInternal));
- for (int i = 0; i < Runtime::kLastCalleeSaveType; i++) {
- callee_save_methods_[i].VisitRootIfNonNull(visitor, RootInfo(kRootVMInternal));
- }
verifier::MethodVerifier::VisitStaticRoots(visitor);
VisitTransactionRoots(visitor);
- instrumentation_.VisitRoots(visitor);
}
void Runtime::VisitNonConcurrentRoots(RootVisitor* visitor) {
@@ -1399,73 +1409,43 @@ void Runtime::VisitImageRoots(RootVisitor* visitor) {
}
}
-mirror::ObjectArray<mirror::ArtMethod>* Runtime::CreateDefaultImt(ClassLinker* cl) {
- Thread* self = Thread::Current();
- StackHandleScope<1> hs(self);
- Handle<mirror::ObjectArray<mirror::ArtMethod>> imtable(
- hs.NewHandle(cl->AllocArtMethodArray(self, 64)));
- mirror::ArtMethod* imt_conflict_method = Runtime::Current()->GetImtConflictMethod();
- for (size_t i = 0; i < static_cast<size_t>(imtable->GetLength()); i++) {
- imtable->Set<false>(i, imt_conflict_method);
- }
- return imtable.Get();
-}
-
-mirror::ArtMethod* Runtime::CreateImtConflictMethod() {
- Thread* self = Thread::Current();
- Runtime* runtime = Runtime::Current();
- ClassLinker* class_linker = runtime->GetClassLinker();
- StackHandleScope<1> hs(self);
- Handle<mirror::ArtMethod> method(hs.NewHandle(class_linker->AllocArtMethod(self)));
- method->SetDeclaringClass(mirror::ArtMethod::GetJavaLangReflectArtMethod());
- // TODO: use a special method for imt conflict method saves.
- method->SetDexMethodIndex(DexFile::kDexNoIndex);
+ArtMethod* Runtime::CreateImtConflictMethod() {
+ auto* method = Runtime::Current()->GetClassLinker()->CreateRuntimeMethod();
// When compiling, the code pointer will get set later when the image is loaded.
- if (runtime->IsAotCompiler()) {
+ if (IsAotCompiler()) {
size_t pointer_size = GetInstructionSetPointerSize(instruction_set_);
method->SetEntryPointFromQuickCompiledCodePtrSize(nullptr, pointer_size);
} else {
method->SetEntryPointFromQuickCompiledCode(GetQuickImtConflictStub());
}
- return method.Get();
+ return method;
}
-void Runtime::SetImtConflictMethod(mirror::ArtMethod* method) {
- imt_conflict_method_ = GcRoot<mirror::ArtMethod>(method);
+void Runtime::SetImtConflictMethod(ArtMethod* method) {
+ CHECK(method != nullptr);
+ CHECK(method->IsRuntimeMethod());
+ imt_conflict_method_ = method;
}
-mirror::ArtMethod* Runtime::CreateResolutionMethod() {
- Thread* self = Thread::Current();
- Runtime* runtime = Runtime::Current();
- ClassLinker* class_linker = runtime->GetClassLinker();
- StackHandleScope<1> hs(self);
- Handle<mirror::ArtMethod> method(hs.NewHandle(class_linker->AllocArtMethod(self)));
- method->SetDeclaringClass(mirror::ArtMethod::GetJavaLangReflectArtMethod());
- // TODO: use a special method for resolution method saves
- method->SetDexMethodIndex(DexFile::kDexNoIndex);
+ArtMethod* Runtime::CreateResolutionMethod() {
+ auto* method = Runtime::Current()->GetClassLinker()->CreateRuntimeMethod();
// When compiling, the code pointer will get set later when the image is loaded.
- if (runtime->IsAotCompiler()) {
+ if (IsAotCompiler()) {
size_t pointer_size = GetInstructionSetPointerSize(instruction_set_);
method->SetEntryPointFromQuickCompiledCodePtrSize(nullptr, pointer_size);
} else {
method->SetEntryPointFromQuickCompiledCode(GetQuickResolutionStub());
}
- return method.Get();
+ return method;
}
-mirror::ArtMethod* Runtime::CreateCalleeSaveMethod() {
- Thread* self = Thread::Current();
- Runtime* runtime = Runtime::Current();
- ClassLinker* class_linker = runtime->GetClassLinker();
- StackHandleScope<1> hs(self);
- Handle<mirror::ArtMethod> method(hs.NewHandle(class_linker->AllocArtMethod(self)));
- method->SetDeclaringClass(mirror::ArtMethod::GetJavaLangReflectArtMethod());
- // TODO: use a special method for callee saves
- method->SetDexMethodIndex(DexFile::kDexNoIndex);
+ArtMethod* Runtime::CreateCalleeSaveMethod() {
+ auto* method = Runtime::Current()->GetClassLinker()->CreateRuntimeMethod();
size_t pointer_size = GetInstructionSetPointerSize(instruction_set_);
method->SetEntryPointFromQuickCompiledCodePtrSize(nullptr, pointer_size);
DCHECK_NE(instruction_set_, kNone);
- return method.Get();
+ DCHECK(method->IsRuntimeMethod());
+ return method;
}
void Runtime::DisallowNewSystemWeaks() {
@@ -1525,15 +1505,16 @@ void Runtime::SetInstructionSet(InstructionSet instruction_set) {
}
}
-void Runtime::SetCalleeSaveMethod(mirror::ArtMethod* method, CalleeSaveType type) {
+void Runtime::SetCalleeSaveMethod(ArtMethod* method, CalleeSaveType type) {
DCHECK_LT(static_cast<int>(type), static_cast<int>(kLastCalleeSaveType));
- callee_save_methods_[type] = GcRoot<mirror::ArtMethod>(method);
+ CHECK(method != nullptr);
+ callee_save_methods_[type] = reinterpret_cast<uintptr_t>(method);
}
void Runtime::StartProfiler(const char* profile_output_filename) {
profile_output_filename_ = profile_output_filename;
profiler_started_ =
- BackgroundMethodSamplingProfiler::Start(profile_output_filename_, profiler_options_);
+ BackgroundMethodSamplingProfiler::Start(profile_output_filename_, profiler_options_);
}
// Transaction support.
@@ -1550,7 +1531,6 @@ void Runtime::ExitTransactionMode() {
preinitialization_transaction_ = nullptr;
}
-
bool Runtime::IsTransactionAborted() const {
if (!IsActiveTransaction()) {
return false;
@@ -1709,4 +1689,16 @@ bool Runtime::IsCompilingBootImage() const {
return IsCompiler() && compiler_callbacks_->IsBootImage();
}
+void Runtime::SetResolutionMethod(ArtMethod* method) {
+ CHECK(method != nullptr);
+ CHECK(method->IsRuntimeMethod()) << method;
+ resolution_method_ = method;
+}
+
+void Runtime::SetImtUnimplementedMethod(ArtMethod* method) {
+ CHECK(method != nullptr);
+ CHECK(method->IsRuntimeMethod());
+ imt_unimplemented_method_ = method;
+}
+
} // namespace art