blob: 18079644ccd4043e27cb0b648b90a92988556eb0 [file] [log] [blame]
Brian Carlstrom9ea1cb12011-08-24 23:18:18 -07001// Copyright 2011 Google Inc. All Rights Reserved.
2
3#ifndef ART_SRC_COMPILER_H_
4#define ART_SRC_COMPILER_H_
5
Brian Carlstrom3320cf42011-10-04 14:58:28 -07006#include "compiled_method.h"
Ian Rogers2c8f6532011-09-02 17:16:34 -07007#include "constants.h"
Brian Carlstrom9ea1cb12011-08-24 23:18:18 -07008#include "dex_file.h"
Ian Rogers2c8f6532011-09-02 17:16:34 -07009#include "jni_compiler.h"
Brian Carlstrom3320cf42011-10-04 14:58:28 -070010#include "oat_file.h"
Brian Carlstrom9ea1cb12011-08-24 23:18:18 -070011#include "object.h"
Ian Rogers1cb0a1d2011-10-06 15:24:35 -070012#include "runtime.h"
Brian Carlstrom3320cf42011-10-04 14:58:28 -070013#include "unordered_map.h"
Ian Rogersd6b1f612011-09-27 13:38:14 -070014
Ian Rogers0571d352011-11-03 19:51:38 -070015#include <string>
16
Brian Carlstrom9ea1cb12011-08-24 23:18:18 -070017namespace art {
18
19class Compiler {
20 public:
Brian Carlstromaded5f72011-10-07 17:15:04 -070021 // Create a compiler targeting the requested "instruction_set".
22 // "image" should be true if image specific optimizations should be enabled.
23 explicit Compiler(InstructionSet instruction_set, bool image);
Brian Carlstrom3320cf42011-10-04 14:58:28 -070024
25 ~Compiler();
Ian Rogers2c8f6532011-09-02 17:16:34 -070026
Brian Carlstrom8a487412011-08-29 20:08:52 -070027 // Compile all Methods of all the Classes of all the DexFiles that are part of a ClassLoader.
28 void CompileAll(const ClassLoader* class_loader);
29
30 // Compile a single Method
Brian Carlstrom3320cf42011-10-04 14:58:28 -070031 void CompileOne(const Method* method);
Brian Carlstrom9ea1cb12011-08-24 23:18:18 -070032
Brian Carlstrom3320cf42011-10-04 14:58:28 -070033 InstructionSet GetInstructionSet() const {
34 return instruction_set_;
35 }
36
Brian Carlstromaded5f72011-10-07 17:15:04 -070037 bool IsImage() const {
38 return image_;
39 }
40
41 void SetVerbose(bool verbose) {
42 verbose_ = verbose;
43 }
44
Brian Carlstrom16192862011-09-12 17:50:06 -070045 bool IsVerbose() const {
46 return verbose_;
47 }
48
Brian Carlstrome24fa612011-09-29 00:53:55 -070049 // Stub to throw AbstractMethodError
Brian Carlstrome24fa612011-09-29 00:53:55 -070050 static ByteArray* CreateAbstractMethodErrorStub(InstructionSet instruction_set);
51
Brian Carlstrom3320cf42011-10-04 14:58:28 -070052
Ian Rogersad25ac52011-10-04 19:13:33 -070053 // Generate the trampoline that's invoked by unresolved direct methods
Ian Rogers1cb0a1d2011-10-06 15:24:35 -070054 static ByteArray* CreateResolutionStub(InstructionSet instruction_set,
55 Runtime::TrampolineType type);
Ian Rogersad25ac52011-10-04 19:13:33 -070056
Ian Rogers169c9a72011-11-13 20:13:17 -080057 static ByteArray* CreateJniDlysmLookupStub(InstructionSet instruction_set);
58
Ian Rogers0571d352011-11-03 19:51:38 -070059 // A method is uniquely located by its DexFile and index into the method_id table of that dex file
60 typedef std::pair<const DexFile*, uint32_t> MethodReference;
61
62 CompiledMethod* GetCompiledMethod(MethodReference ref) const;
63 const CompiledInvokeStub* FindInvokeStub(bool is_static, const char* shorty) const;
Brian Carlstrom3320cf42011-10-04 14:58:28 -070064
Ian Rogers28ad40d2011-10-27 15:19:26 -070065 // Callbacks from OAT/ART compiler to see what runtime checks must be generated
66 bool CanAssumeTypeIsPresentInDexCache(const Method* referrer, uint32_t type_idx) const {
67 return IsImage() && referrer->GetDexCacheResolvedTypes()->Get(type_idx) != NULL;
68 }
69 bool CanAssumeStringIsPresentInDexCache(const Method* referrer, uint32_t string_idx) const {
70 return IsImage() && referrer->GetDexCacheStrings()->Get(string_idx) != NULL;
71 }
72 bool CanAccessTypeWithoutChecks(const Method* referrer, uint32_t type_idx) const {
73 Class* resolved_class = referrer->GetDexCacheResolvedTypes()->Get(type_idx);
74 // We should never ask whether a type needs access checks to raise a verification error,
75 // all other cases where this following test could fail should have been rewritten by the
76 // verifier to verification errors.
77 DCHECK(resolved_class == NULL || referrer->GetDeclaringClass()->CanAccess(resolved_class));
78 return resolved_class != NULL;
79 }
Ian Rogers0571d352011-11-03 19:51:38 -070080
Brian Carlstrom9ea1cb12011-08-24 23:18:18 -070081 private:
82 // Attempt to resolve all type, methods, fields, and strings
83 // referenced from code in the dex file following PathClassLoader
84 // ordering semantics.
85 void Resolve(const ClassLoader* class_loader);
86 void ResolveDexFile(const ClassLoader* class_loader, const DexFile& dex_file);
87
jeffhao98eacac2011-09-14 16:11:53 -070088 void Verify(const ClassLoader* class_loader);
89 void VerifyDexFile(const ClassLoader* class_loader, const DexFile& dex_file);
90
Brian Carlstroma5a97a22011-09-15 14:08:49 -070091 void InitializeClassesWithoutClinit(const ClassLoader* class_loader);
92 void InitializeClassesWithoutClinit(const ClassLoader* class_loader, const DexFile& dex_file);
93
Brian Carlstrom83db7722011-08-26 17:32:56 -070094 void Compile(const ClassLoader* class_loader);
Brian Carlstrom9ea1cb12011-08-24 23:18:18 -070095 void CompileDexFile(const ClassLoader* class_loader, const DexFile& dex_file);
Ian Rogers0571d352011-11-03 19:51:38 -070096 void CompileClass(const DexFile::ClassDef& class_def, const ClassLoader* class_loader,
97 const DexFile& dex_file);
Ian Rogers169c9a72011-11-13 20:13:17 -080098 void CompileMethod(uint32_t access_flags, uint32_t method_idx, const ClassLoader* class_loader,
99 const DexFile& dex_file);
Brian Carlstrom83db7722011-08-26 17:32:56 -0700100
101 // After compiling, walk all the DexCaches and set the code and
Brian Carlstrom9cc262e2011-08-28 12:45:30 -0700102 // method pointers of CodeAndDirectMethods entries in the DexCaches.
103 void SetCodeAndDirectMethods(const ClassLoader* class_loader);
Brian Carlstrom8a487412011-08-29 20:08:52 -0700104 void SetCodeAndDirectMethodsDexFile(const DexFile& dex_file);
Ian Rogers2c8f6532011-09-02 17:16:34 -0700105
Ian Rogers0571d352011-11-03 19:51:38 -0700106 void InsertInvokeStub(bool is_static, const char* shorty,
107 const CompiledInvokeStub* compiled_invoke_stub);
108
Ian Rogers2c8f6532011-09-02 17:16:34 -0700109 InstructionSet instruction_set_;
110 JniCompiler jni_compiler_;
111
Ian Rogers0571d352011-11-03 19:51:38 -0700112 struct MethodReferenceHash {
113 size_t operator()(const MethodReference id) const {
114 size_t dex = reinterpret_cast<size_t>(id.first);
115 DCHECK_NE(dex, static_cast<size_t>(0));
116 dex += 33; // dex is an aligned pointer, get some non-zero low bits
117 size_t idx = id.second;
118 if (idx == 0) { // special case of a method index of 0
119 return dex * 5381;
120 } else {
121 return dex * idx;
122 }
123 }
124 };
125 typedef std::tr1::unordered_map<const MethodReference, CompiledMethod*, MethodReferenceHash> MethodTable;
126 // All method references that this compiler has compiled
Brian Carlstrom3320cf42011-10-04 14:58:28 -0700127 MethodTable compiled_methods_;
128
Ian Rogers0571d352011-11-03 19:51:38 -0700129 typedef std::tr1::unordered_map<std::string, const CompiledInvokeStub*> InvokeStubTable;
130 // Invocation stubs created to allow invocation of the compiled methods
Brian Carlstrom3320cf42011-10-04 14:58:28 -0700131 InvokeStubTable compiled_invoke_stubs_;
132
Brian Carlstromaded5f72011-10-07 17:15:04 -0700133 bool image_;
134
Brian Carlstrom16192862011-09-12 17:50:06 -0700135 bool verbose_;
136
Ian Rogers2c8f6532011-09-02 17:16:34 -0700137 DISALLOW_COPY_AND_ASSIGN(Compiler);
Brian Carlstrom9ea1cb12011-08-24 23:18:18 -0700138};
139
140} // namespace art
141
142#endif // ART_SRC_COMPILER_H_