• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2008 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 /*
17  * Class loader.
18  */
19 #ifndef DALVIK_OO_CLASS_H_
20 #define DALVIK_OO_CLASS_H_
21 
22 /*
23  * The classpath and bootclasspath differ in that only the latter is
24  * consulted when looking for classes needed by the VM.  When searching
25  * for an arbitrary class definition, we start with the bootclasspath,
26  * look for optional packages (a/k/a standard extensions), and then try
27  * the classpath.
28  *
29  * In Dalvik, a class can be found in one of two ways:
30  *  - in a .dex file
31  *  - in a .dex file named specifically "classes.dex", which is held
32  *    inside a jar file
33  *
34  * These two may be freely intermixed in a classpath specification.
35  * Ordering is significant.
36  */
37 enum ClassPathEntryKind {
38     kCpeUnknown = 0,
39     kCpeJar,
40     kCpeDex,
41     kCpeLastEntry       /* used as sentinel at end of array */
42 };
43 
44 struct ClassPathEntry {
45     ClassPathEntryKind kind;
46     char*   fileName;
47     void*   ptr;            /* JarFile* or DexFile* */
48 };
49 
50 bool dvmClassStartup(void);
51 void dvmClassShutdown(void);
52 bool dvmPrepBootClassPath(bool isNormalStart);
53 
54 /*
55  * Boot class path accessors, for class loader getResources().
56  */
57 int dvmGetBootPathSize(void);
58 StringObject* dvmGetBootPathResource(const char* name, int idx);
59 void dvmDumpBootClassPath(void);
60 
61 /*
62  * Determine whether "path" is a member of "cpe".
63  */
64 bool dvmClassPathContains(const ClassPathEntry* cpe, const char* path);
65 
66 /*
67  * Set clazz->serialNumber to the next available value.
68  */
69 void dvmSetClassSerialNumber(ClassObject* clazz);
70 
71 /*
72  * Find the class object representing the primitive type with the
73  * given descriptor. This returns NULL if the given type character
74  * is invalid.
75  */
76 ClassObject* dvmFindPrimitiveClass(char type);
77 
78 /*
79  * Find the class with the given descriptor.  Load it if it hasn't already
80  * been.
81  *
82  * "loader" is the initiating class loader.
83  */
84 ClassObject* dvmFindClass(const char* descriptor, Object* loader);
85 ClassObject* dvmFindClassNoInit(const char* descriptor, Object* loader);
86 
87 /*
88  * Like dvmFindClass, but only for system classes.
89  */
90 ClassObject* dvmFindSystemClass(const char* descriptor);
91 ClassObject* dvmFindSystemClassNoInit(const char* descriptor);
92 
93 /*
94  * Find a loaded class by descriptor. Returns the first one found.
95  * Because there can be more than one if class loaders are involved,
96  * this is not an especially good API. (Currently only used by the
97  * debugger and "checking" JNI.)
98  *
99  * "descriptor" should have the form "Ljava/lang/Class;" or
100  * "[Ljava/lang/Class;", i.e. a descriptor and not an internal-form
101  * class name.
102  */
103 ClassObject* dvmFindLoadedClass(const char* descriptor);
104 
105 /*
106  * Load the named class (by descriptor) from the specified DEX file.
107  * Used by class loaders to instantiate a class object from a
108  * VM-managed DEX.
109  */
110 ClassObject* dvmDefineClass(DvmDex* pDvmDex, const char* descriptor,
111     Object* classLoader);
112 
113 /*
114  * Link a loaded class.  Normally done as part of one of the "find class"
115  * variations, this is only called explicitly for synthetic class
116  * generation (e.g. reflect.Proxy).
117  */
118 bool dvmLinkClass(ClassObject* clazz);
119 
120 /*
121  * Determine if a class has been initialized.
122  */
dvmIsClassInitialized(const ClassObject * clazz)123 INLINE bool dvmIsClassInitialized(const ClassObject* clazz) {
124     return (clazz->status == CLASS_INITIALIZED);
125 }
126 bool dvmIsClassInitializing(const ClassObject* clazz);
127 
128 /*
129  * Initialize a class.
130  */
131 extern "C" bool dvmInitClass(ClassObject* clazz);
132 
133 /*
134  * Retrieve the system class loader.
135  */
136 Object* dvmGetSystemClassLoader(void);
137 
138 /*
139  * Utility functions.
140  */
141 ClassObject* dvmLookupClass(const char* descriptor, Object* loader,
142     bool unprepOkay);
143 void dvmFreeClassInnards(ClassObject* clazz);
144 bool dvmAddClassToHash(ClassObject* clazz);
145 void dvmAddInitiatingLoader(ClassObject* clazz, Object* loader);
146 bool dvmLoaderInInitiatingList(const ClassObject* clazz, const Object* loader);
147 
148 /*
149  * Update method's "nativeFunc" and "insns".  If "insns" is NULL, the
150  * current method->insns value is not changed.
151  */
152 void dvmSetNativeFunc(Method* method, DalvikBridgeFunc func, const u2* insns);
153 
154 /*
155  * Set the method's "registerMap" field.
156  */
157 void dvmSetRegisterMap(Method* method, const RegisterMap* pMap);
158 
159 /*
160  * Make a method's DexCode (which includes the bytecode) read-write or
161  * read-only.  The conversion to read-write may involve making a new copy
162  * of the DexCode, and in normal operation the read-only state is not
163  * actually enforced.
164  */
165 void dvmMakeCodeReadWrite(Method* meth);
166 void dvmMakeCodeReadOnly(Method* meth);
167 
168 /*
169  * During DEX optimizing, add an extra DEX to the bootstrap class path.
170  */
171 void dvmSetBootPathExtraDex(DvmDex* pDvmDex);
172 
173 /*
174  * Debugging.
175  */
176 void dvmDumpClass(const ClassObject* clazz, int flags);
177 void dvmDumpAllClasses(int flags);
178 void dvmDumpLoaderStats(const char* msg);
179 int  dvmGetNumLoadedClasses();
180 
181 /* flags for dvmDumpClass / dvmDumpAllClasses */
182 #define kDumpClassFullDetail    1
183 #define kDumpClassClassLoader   (1 << 1)
184 #define kDumpClassInitialized   (1 << 2)
185 
186 
187 /*
188  * Store a copy of the method prototype descriptor string
189  * for the given method into the given DexStringCache, returning the
190  * stored string for convenience.
191  */
dvmCopyDescriptorStringFromMethod(const Method * method,DexStringCache * pCache)192 INLINE char* dvmCopyDescriptorStringFromMethod(const Method* method,
193         DexStringCache *pCache)
194 {
195     const char* result =
196         dexProtoGetMethodDescriptor(&method->prototype, pCache);
197     return dexStringCacheEnsureCopy(pCache, result);
198 }
199 
200 /*
201  * Compute the number of argument words (u4 units) required by the
202  * given method's prototype. For example, if the method descriptor is
203  * "(IJ)D", this would return 3 (one for the int, two for the long;
204  * return value isn't relevant).
205  */
dvmComputeMethodArgsSize(const Method * method)206 INLINE int dvmComputeMethodArgsSize(const Method* method)
207 {
208     return dexProtoComputeArgsSize(&method->prototype);
209 }
210 
211 /*
212  * Compare the two method prototypes. The two prototypes are compared
213  * as if by strcmp() on the result of dexProtoGetMethodDescriptor().
214  */
dvmCompareMethodProtos(const Method * method1,const Method * method2)215 INLINE int dvmCompareMethodProtos(const Method* method1,
216         const Method* method2)
217 {
218     return dexProtoCompare(&method1->prototype, &method2->prototype);
219 }
220 
221 /*
222  * Compare the two method prototypes, considering only the parameters
223  * (i.e. ignoring the return types). The two prototypes are compared
224  * as if by strcmp() on the result of dexProtoGetMethodDescriptor().
225  */
dvmCompareMethodParameterProtos(const Method * method1,const Method * method2)226 INLINE int dvmCompareMethodParameterProtos(const Method* method1,
227         const Method* method2)
228 {
229     return dexProtoCompareParameters(&method1->prototype, &method2->prototype);
230 }
231 
232 /*
233  * Compare the two method names and prototypes, a la strcmp(). The
234  * name is considered the "major" order and the prototype the "minor"
235  * order. The prototypes are compared as if by dexProtoGetMethodDescriptor().
236  */
237 int dvmCompareMethodNamesAndProtos(const Method* method1,
238         const Method* method2);
239 
240 /*
241  * Compare the two method names and prototypes, a la strcmp(), ignoring
242  * the return type. The name is considered the "major" order and the
243  * prototype the "minor" order. The prototypes are compared as if by
244  * dexProtoGetMethodDescriptor().
245  */
246 int dvmCompareMethodNamesAndParameterProtos(const Method* method1,
247         const Method* method2);
248 
249 /*
250  * Compare a method descriptor string with the prototype of a method,
251  * as if by converting the descriptor to a DexProto and comparing it
252  * with dexProtoCompare().
253  */
dvmCompareDescriptorAndMethodProto(const char * descriptor,const Method * method)254 INLINE int dvmCompareDescriptorAndMethodProto(const char* descriptor,
255     const Method* method)
256 {
257     // Sense is reversed.
258     return -dexProtoCompareToDescriptor(&method->prototype, descriptor);
259 }
260 
261 /*
262  * Compare a (name, prototype) pair with the (name, prototype) of
263  * a method, a la strcmp(). The name is considered the "major" order and
264  * the prototype the "minor" order. The descriptor and prototype are
265  * compared as if by dvmCompareDescriptorAndMethodProto().
266  */
267 int dvmCompareNameProtoAndMethod(const char* name,
268     const DexProto* proto, const Method* method);
269 
270 /*
271  * Compare a (name, method descriptor) pair with the (name, prototype) of
272  * a method, a la strcmp(). The name is considered the "major" order and
273  * the prototype the "minor" order. The descriptor and prototype are
274  * compared as if by dvmCompareDescriptorAndMethodProto().
275  */
276 int dvmCompareNameDescriptorAndMethod(const char* name,
277     const char* descriptor, const Method* method);
278 
279 /*
280  * Returns the size of the given class object in bytes.
281  */
282 size_t dvmClassObjectSize(const ClassObject *clazz);
283 
284 #endif  // DALVIK_OO_CLASS_H_
285