• 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  * JNI innards, common to the regular and "checked" interfaces.
18  */
19 #ifndef DALVIK_JNIINTERNAL_H_
20 #define DALVIK_JNIINTERNAL_H_
21 
22 #include "jni.h"
23 
24 /* system init/shutdown */
25 bool dvmJniStartup(void);
26 void dvmJniShutdown(void);
27 
28 bool dvmIsBadJniVersion(int version);
29 
30 /*
31  * Our data structures for JNIEnv and JavaVM.
32  *
33  * Native code thinks it has a pointer to a pointer.  We know better.
34  */
35 struct JavaVMExt;
36 
37 struct JNIEnvExt {
38     const struct JNINativeInterface* funcTable;     /* must be first */
39 
40     const struct JNINativeInterface* baseFuncTable;
41 
42     u4      envThreadId;
43     Thread* self;
44 
45     /* if nonzero, we are in a "critical" JNI call */
46     int     critical;
47 
48     struct JNIEnvExt* prev;
49     struct JNIEnvExt* next;
50 };
51 
52 struct JavaVMExt {
53     const struct JNIInvokeInterface* funcTable;     /* must be first */
54 
55     const struct JNIInvokeInterface* baseFuncTable;
56 
57     /* head of list of JNIEnvs associated with this VM */
58     JNIEnvExt*      envList;
59     pthread_mutex_t envListLock;
60 };
61 
62 /*
63  * Native function return type; used by dvmPlatformInvoke().
64  *
65  * This is part of Method.jniArgInfo, and must fit in 3 bits.
66  * Note: Assembly code in arch/<arch>/Call<arch>.S relies on
67  * the enum values defined here.
68  */
69 enum DalvikJniReturnType {
70     DALVIK_JNI_RETURN_VOID = 0,     /* must be zero */
71     DALVIK_JNI_RETURN_FLOAT = 1,
72     DALVIK_JNI_RETURN_DOUBLE = 2,
73     DALVIK_JNI_RETURN_S8 = 3,
74     DALVIK_JNI_RETURN_S4 = 4,
75     DALVIK_JNI_RETURN_S2 = 5,
76     DALVIK_JNI_RETURN_U2 = 6,
77     DALVIK_JNI_RETURN_S1 = 7
78 };
79 
80 #define DALVIK_JNI_NO_ARG_INFO  0x80000000
81 #define DALVIK_JNI_RETURN_MASK  0x70000000
82 #define DALVIK_JNI_RETURN_SHIFT 28
83 #define DALVIK_JNI_COUNT_MASK   0x0f000000
84 #define DALVIK_JNI_COUNT_SHIFT  24
85 
86 
87 /*
88  * Pop the JNI local stack when we return from a native method.  "saveArea"
89  * points to the StackSaveArea for the method we're leaving.
90  *
91  * (This may be implemented directly in assembly in mterp, so changes here
92  * may only affect the portable interpreter.)
93  */
dvmPopJniLocals(Thread * self,StackSaveArea * saveArea)94 INLINE void dvmPopJniLocals(Thread* self, StackSaveArea* saveArea)
95 {
96     self->jniLocalRefTable.segmentState.all = saveArea->xtra.localRefCookie;
97 }
98 
99 /*
100  * Set the envThreadId field.
101  */
dvmSetJniEnvThreadId(JNIEnv * pEnv,Thread * self)102 INLINE void dvmSetJniEnvThreadId(JNIEnv* pEnv, Thread* self)
103 {
104     ((JNIEnvExt*)pEnv)->envThreadId = self->threadId;
105     ((JNIEnvExt*)pEnv)->self = self;
106 }
107 
108 void dvmCallJNIMethod(const u4* args, JValue* pResult,
109     const Method* method, Thread* self);
110 void dvmCheckCallJNIMethod(const u4* args, JValue* pResult,
111     const Method* method, Thread* self);
112 
113 /*
114  * Configure "method" to use the JNI bridge to call "func".
115  */
116 void dvmUseJNIBridge(Method* method, void* func);
117 
118 
119 /*
120  * Enable the "checked" versions.
121  */
122 void dvmUseCheckedJniEnv(JNIEnvExt* pEnv);
123 void dvmUseCheckedJniVm(JavaVMExt* pVm);
124 void dvmLateEnableCheckedJni(void);
125 
126 /*
127  * Decode a local, global, or weak-global reference.
128  */
129 Object* dvmDecodeIndirectRef(Thread* self, jobject jobj);
130 
131 /*
132  * Verify that a reference passed in from native code is valid.  Returns
133  * an indication of local/global/invalid.
134  */
135 jobjectRefType dvmGetJNIRefType(Thread* self, jobject jobj);
136 
137 /*
138  * Get the last method called on the interp stack.  This is the method
139  * "responsible" for calling into JNI.
140  */
141 const Method* dvmGetCurrentJNIMethod(void);
142 
143 /*
144  * Create/destroy a JNIEnv for the current thread.
145  */
146 JNIEnv* dvmCreateJNIEnv(Thread* self);
147 void dvmDestroyJNIEnv(JNIEnv* env);
148 
149 /*
150  * Find the JNIEnv associated with the current thread.
151  */
152 JNIEnvExt* dvmGetJNIEnvForThread(void);
153 
154 /*
155  * Release all MonitorEnter-acquired locks that are still held.  Called at
156  * DetachCurrentThread time.
157  */
158 void dvmReleaseJniMonitors(Thread* self);
159 
160 /*
161  * Dump the contents of the JNI reference tables to the log file.
162  *
163  * The local ref tables associated with other threads are not included.
164  */
165 void dvmDumpJniReferenceTables(void);
166 
167 // Dumps JNI statistics in response to SIGQUIT.
168 struct DebugOutputTarget;
169 void dvmDumpJniStats(DebugOutputTarget* target);
170 
171 #endif  // DALVIK_JNIINTERNAL_H_
172