diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/object_test.cc | 23 | ||||
| -rw-r--r-- | src/runtime_support.cc | 22 | ||||
| -rw-r--r-- | src/runtime_support_asm.S | 28 |
3 files changed, 30 insertions, 43 deletions
diff --git a/src/object_test.cc b/src/object_test.cc index c13a19de62..6979b75327 100644 --- a/src/object_test.cc +++ b/src/object_test.cc @@ -162,29 +162,6 @@ TEST_F(ObjectTest, PrimitiveArray_Short_Alloc) { TestPrimitiveArray<ShortArray>(class_linker_); } -extern "C" Object* artAllocObjectFromCode(uint32_t type_idx, Method* method); -TEST_F(ObjectTest, AllocObjectFromCode) { - // pretend we are trying to call 'new String' from Object.toString - Class* java_lang_Object = class_linker_->FindSystemClass("Ljava/lang/Object;"); - Method* toString = java_lang_Object->FindVirtualMethod("toString", "()Ljava/lang/String;"); - uint32_t type_idx = FindTypeIdxByDescriptor(*java_lang_dex_file_.get(), "Ljava/lang/String;"); - Object* string = artAllocObjectFromCode(type_idx, toString); - EXPECT_TRUE(string->IsString()); -} - -extern "C" Array* artAllocArrayFromCode(uint32_t type_idx, Method* method, int32_t component_count); -TEST_F(ObjectTest, AllocArrayFromCode) { - // pretend we are trying to call 'new char[3]' from String.toCharArray - Class* java_lang_String = class_linker_->FindSystemClass("Ljava/lang/String;"); - Method* toCharArray = java_lang_String->FindVirtualMethod("toCharArray", "()[C"); - uint32_t type_idx = FindTypeIdxByDescriptor(*java_lang_dex_file_.get(), "[C"); - Object* array = artAllocArrayFromCode(type_idx, toCharArray, 3); - EXPECT_TRUE(array->IsArrayInstance()); - EXPECT_EQ(3, array->AsArray()->GetLength()); - EXPECT_TRUE(array->GetClass()->IsArrayClass()); - EXPECT_TRUE(array->GetClass()->GetComponentType()->IsPrimitive()); -} - extern "C" Array* artCheckAndAllocArrayFromCode(uint32_t type_idx, Method* method, int32_t component_count); TEST_F(ObjectTest, CheckAndAllocArrayFromCode) { diff --git a/src/runtime_support.cc b/src/runtime_support.cc index 2bcd7d9ead..49191b73c2 100644 --- a/src/runtime_support.cc +++ b/src/runtime_support.cc @@ -414,17 +414,22 @@ void ResolveMethodFromCode(Method* method, uint32_t method_idx) { // Given the context of a calling Method, use its DexCache to resolve a type to a Class. If it // cannot be resolved, throw an error. If it can, use it to create an instance. -extern "C" Object* artAllocObjectFromCode(uint32_t type_idx, Method* method) { +extern "C" Object* artAllocObjectFromCode(uint32_t type_idx, Method* method, Thread* self, Method** sp) { + // Place a special frame at the TOS that will save all callee saves + Runtime* runtime = Runtime::Current(); + *sp = runtime->GetCalleeSaveMethod(); + self->SetTopOfStack(sp, 0); + Class* klass = method->GetDexCacheResolvedTypes()->Get(type_idx); if (klass == NULL) { - klass = Runtime::Current()->GetClassLinker()->ResolveType(type_idx, method); + klass = runtime->GetClassLinker()->ResolveType(type_idx, method); if (klass == NULL) { - DCHECK(Thread::Current()->IsExceptionPending()); + DCHECK(self->IsExceptionPending()); return NULL; // Failure } } - if (!Runtime::Current()->GetClassLinker()->EnsureInitialized(klass, true)) { - DCHECK(Thread::Current()->IsExceptionPending()); + if (!runtime->GetClassLinker()->EnsureInitialized(klass, true)) { + DCHECK(self->IsExceptionPending()); return NULL; // Failure } return klass->AllocObject(); @@ -465,7 +470,12 @@ extern "C" Array* artCheckAndAllocArrayFromCode(uint32_t type_idx, Method* metho // Given the context of a calling Method, use its DexCache to resolve a type to an array Class. If // it cannot be resolved, throw an error. If it can, use it to create an array. -extern "C" Array* artAllocArrayFromCode(uint32_t type_idx, Method* method, int32_t component_count) { +extern "C" Array* artAllocArrayFromCode(uint32_t type_idx, Method* method, int32_t component_count, Thread* self, Method** sp) { + // Place a special frame at the TOS that will save all callee saves + Runtime* runtime = Runtime::Current(); + *sp = runtime->GetCalleeSaveMethod(); + self->SetTopOfStack(sp, 0); + if (component_count < 0) { Thread::Current()->ThrowNewExceptionF("Ljava/lang/NegativeArraySizeException;", "%d", component_count); diff --git a/src/runtime_support_asm.S b/src/runtime_support_asm.S index 7d4c906156..0e73d83a9b 100644 --- a/src/runtime_support_asm.S +++ b/src/runtime_support_asm.S @@ -245,13 +245,13 @@ art_initialize_static_storage_from_code: * Called by managed code to allocate an object */ art_alloc_object_from_code: - str sp, [R9, #THREAD_TOP_OF_MANAGED_STACK_OFFSET] @ record top of stack and pc in case of - str lr, [R9, #THREAD_TOP_OF_MANAGED_STACK_PC_OFFSET] @ walking stack - stmdb sp!, {lr} @ Save LR - sub sp, #12 @ Align stack - bl artAllocObjectFromCode @ (uint32_t type_idx, Method* method) - add sp, #12 - ldmia sp!, {lr} @ restore LR + SETUP_CALLEE_SAVE_FRAME + mov r2, r9 @ pass Thread::Current + mov r3, sp @ pass SP + bl artAllocObjectFromCode @ (uint32_t type_idx, Method* method, Thread*, SP) + add sp, #16 + vpop {s0-s31} + pop {r1-r11, lr} cmp r0, #0 @ success if result is non-null movne pc, lr @ return on success @ set up for throwing exception @@ -266,13 +266,13 @@ art_alloc_object_from_code: * Called by managed code to allocate an array */ art_alloc_array_from_code: - str sp, [R9, #THREAD_TOP_OF_MANAGED_STACK_OFFSET] @ record top of stack and pc in case of - str lr, [R9, #THREAD_TOP_OF_MANAGED_STACK_PC_OFFSET] @ walking stack - stmdb sp!, {lr} @ Save LR - sub sp, #12 @ Align stack - bl artAllocArrayFromCode @ (uint32_t type_idx, Method* method, int32_t component_count) - add sp, #12 - ldmia sp!, {lr} @ restore LR + SETUP_CALLEE_SAVE_FRAME + mov r3, r9 @ pass Thread::Current + str sp, [sp, #0] @ pass SP + bl artAllocArrayFromCode @ (uint32_t type_idx, Method* method, int32_t component_count, Thread*, SP) + add sp, #16 + vpop {s0-s31} + pop {r1-r11, lr} cmp r0, #0 @ success if result is non-null movne pc, lr @ return on success @ set up for throwing exception |