blob: 7660f6f37ec7d9c8998eb185e0d862d7343b9608 [file] [log] [blame]
Shih-wei Liao31384c52011-09-06 15:27:45 -07001// Copyright 2011 Google Inc. All Rights Reserved.
2
3#include "assembler_x86.h"
4#include "jni_internal.h"
5#include "object.h"
Brian Carlstrom40381fb2011-10-19 14:13:40 -07006#include "stack_indirect_reference_table.h"
Shih-wei Liao31384c52011-09-06 15:27:45 -07007
8#define __ assembler->
9
10namespace art {
11namespace x86 {
12
Ian Rogers1cb0a1d2011-10-06 15:24:35 -070013ByteArray* X86CreateResolutionTrampoline(Runtime::TrampolineType) {
Elliott Hughes362f9bc2011-10-17 18:56:41 -070014 UniquePtr<X86Assembler> assembler(static_cast<X86Assembler*>(Assembler::Create(kX86)));
Ian Rogersad25ac52011-10-04 19:13:33 -070015
16 // TODO: unimplemented
17 __ int3();
18
19 assembler->EmitSlowPaths();
20 size_t cs = assembler->CodeSize();
Brian Carlstrom40381fb2011-10-19 14:13:40 -070021 SirtRef<ByteArray> resolution_trampoline(ByteArray::Alloc(cs));
22 CHECK(resolution_trampoline.get() != NULL);
Ian Rogersad25ac52011-10-04 19:13:33 -070023 MemoryRegion code(resolution_trampoline->GetData(), resolution_trampoline->GetLength());
24 assembler->FinalizeInstructions(code);
25
Brian Carlstrom40381fb2011-10-19 14:13:40 -070026 return resolution_trampoline.get();
Ian Rogersad25ac52011-10-04 19:13:33 -070027}
28
Shih-wei Liaoc486c112011-09-13 16:43:52 -070029typedef void (*ThrowAme)(Method*, Thread*);
30
Ian Rogersbdb03912011-09-14 00:55:44 -070031ByteArray* CreateAbstractMethodErrorStub() {
Elliott Hughes362f9bc2011-10-17 18:56:41 -070032 UniquePtr<X86Assembler> assembler(static_cast<X86Assembler*>(Assembler::Create(kX86)));
Shih-wei Liaoc486c112011-09-13 16:43:52 -070033
34 // Pad stack to ensure 16-byte alignment
35 __ pushl(Immediate(0));
Shih-wei Liaoc486c112011-09-13 16:43:52 -070036 __ fs()->pushl(Address::Absolute(Thread::SelfOffset())); // Thread*
Ian Rogers67375ac2011-09-14 00:55:44 -070037 __ pushl(EAX); // Method*
Shih-wei Liaoc486c112011-09-13 16:43:52 -070038
Ian Rogersbdb03912011-09-14 00:55:44 -070039 // Call to throw AbstractMethodError
40 __ Call(ThreadOffset(OFFSETOF_MEMBER(Thread, pThrowAbstractMethodErrorFromCode)),
41 X86ManagedRegister::FromCpuRegister(ECX));
Shih-wei Liaoc486c112011-09-13 16:43:52 -070042
43 // Because the call above never returns, we do not need to do ESP+=16 here.
44
45 __ int3();
46
47 assembler->EmitSlowPaths();
48
49 size_t cs = assembler->CodeSize();
Brian Carlstrom40381fb2011-10-19 14:13:40 -070050 SirtRef<ByteArray> abstract_stub(ByteArray::Alloc(cs));
51 CHECK(abstract_stub.get() != NULL);
Shih-wei Liaoc486c112011-09-13 16:43:52 -070052 MemoryRegion code(abstract_stub->GetData(), abstract_stub->GetLength());
53 assembler->FinalizeInstructions(code);
54
Brian Carlstrom40381fb2011-10-19 14:13:40 -070055 return abstract_stub.get();
Shih-wei Liaoc486c112011-09-13 16:43:52 -070056}
57
Shih-wei Liao31384c52011-09-06 15:27:45 -070058ByteArray* CreateJniStub() {
Elliott Hughes362f9bc2011-10-17 18:56:41 -070059 UniquePtr<X86Assembler> assembler(static_cast<X86Assembler*>(Assembler::Create(kX86)));
Shih-wei Liao31384c52011-09-06 15:27:45 -070060
61 // Pad stack to ensure 16-byte alignment
62 __ pushl(Immediate(0));
63 __ pushl(Immediate(0));
Ian Rogers67375ac2011-09-14 00:55:44 -070064 __ fs()->pushl(Address::Absolute(Thread::SelfOffset())); // Thread*
Shih-wei Liao31384c52011-09-06 15:27:45 -070065
Ian Rogersbdb03912011-09-14 00:55:44 -070066 __ Call(ThreadOffset(OFFSETOF_MEMBER(Thread, pFindNativeMethod)),
67 X86ManagedRegister::FromCpuRegister(ECX));
Shih-wei Liao31384c52011-09-06 15:27:45 -070068
Ian Rogers67375ac2011-09-14 00:55:44 -070069 __ addl(ESP, Immediate(12));
Shih-wei Liao31384c52011-09-06 15:27:45 -070070
71 Label no_native_code_found; // forward declaration
72 __ cmpl(EAX, Immediate(0));
73 __ j(kEqual, &no_native_code_found);
74
75 __ jmp(EAX); // Tail call into native code
76
77 __ Bind(&no_native_code_found);
78 __ ret(); // return to caller to handle exception
79
80 assembler->EmitSlowPaths();
81
82 size_t cs = assembler->CodeSize();
Brian Carlstrom40381fb2011-10-19 14:13:40 -070083 SirtRef<ByteArray> jni_stub(ByteArray::Alloc(cs));
84 CHECK(jni_stub.get() != NULL);
Shih-wei Liao31384c52011-09-06 15:27:45 -070085 MemoryRegion code(jni_stub->GetData(), jni_stub->GetLength());
86 assembler->FinalizeInstructions(code);
87
Brian Carlstrom40381fb2011-10-19 14:13:40 -070088 return jni_stub.get();
Shih-wei Liao31384c52011-09-06 15:27:45 -070089}
90
91} // namespace x86
92} // namespace art