equal
deleted
inserted
replaced
23 * |
23 * |
24 */ |
24 */ |
25 |
25 |
26 #include "precompiled.hpp" |
26 #include "precompiled.hpp" |
27 #include "jni.h" |
27 #include "jni.h" |
|
28 #include "jvm.h" |
28 #include "ci/ciReplay.hpp" |
29 #include "ci/ciReplay.hpp" |
29 #include "classfile/altHashing.hpp" |
30 #include "classfile/altHashing.hpp" |
30 #include "classfile/classFileStream.hpp" |
31 #include "classfile/classFileStream.hpp" |
31 #include "classfile/classLoader.hpp" |
32 #include "classfile/classLoader.hpp" |
32 #include "classfile/javaClasses.hpp" |
33 #include "classfile/javaClasses.hpp" |
53 #include "oops/typeArrayKlass.hpp" |
54 #include "oops/typeArrayKlass.hpp" |
54 #include "oops/typeArrayOop.hpp" |
55 #include "oops/typeArrayOop.hpp" |
55 #include "prims/jniCheck.hpp" |
56 #include "prims/jniCheck.hpp" |
56 #include "prims/jniExport.hpp" |
57 #include "prims/jniExport.hpp" |
57 #include "prims/jniFastGetField.hpp" |
58 #include "prims/jniFastGetField.hpp" |
58 #include "prims/jvm.h" |
|
59 #include "prims/jvm_misc.hpp" |
59 #include "prims/jvm_misc.hpp" |
60 #include "prims/jvmtiExport.hpp" |
60 #include "prims/jvmtiExport.hpp" |
61 #include "prims/jvmtiThreadState.hpp" |
61 #include "prims/jvmtiThreadState.hpp" |
62 #include "runtime/atomic.hpp" |
62 #include "runtime/atomic.hpp" |
63 #include "runtime/compilationPolicy.hpp" |
63 #include "runtime/compilationPolicy.hpp" |
261 |
261 |
262 // Wrapper to trace JNI functions |
262 // Wrapper to trace JNI functions |
263 |
263 |
264 #ifdef ASSERT |
264 #ifdef ASSERT |
265 Histogram* JNIHistogram; |
265 Histogram* JNIHistogram; |
266 static volatile jint JNIHistogram_lock = 0; |
266 static volatile int JNIHistogram_lock = 0; |
267 |
267 |
268 class JNIHistogramElement : public HistogramElement { |
268 class JNIHistogramElement : public HistogramElement { |
269 public: |
269 public: |
270 JNIHistogramElement(const char* name); |
270 JNIHistogramElement(const char* name); |
271 }; |
271 }; |
3275 JNI_END |
3275 JNI_END |
3276 |
3276 |
3277 |
3277 |
3278 // Initialization state for three routines below relating to |
3278 // Initialization state for three routines below relating to |
3279 // java.nio.DirectBuffers |
3279 // java.nio.DirectBuffers |
3280 static jint directBufferSupportInitializeStarted = 0; |
3280 static int directBufferSupportInitializeStarted = 0; |
3281 static volatile jint directBufferSupportInitializeEnded = 0; |
3281 static volatile int directBufferSupportInitializeEnded = 0; |
3282 static volatile jint directBufferSupportInitializeFailed = 0; |
3282 static volatile int directBufferSupportInitializeFailed = 0; |
3283 static jclass bufferClass = NULL; |
3283 static jclass bufferClass = NULL; |
3284 static jclass directBufferClass = NULL; |
3284 static jclass directBufferClass = NULL; |
3285 static jclass directByteBufferClass = NULL; |
3285 static jclass directByteBufferClass = NULL; |
3286 static jmethodID directByteBufferConstructor = NULL; |
3286 static jmethodID directByteBufferConstructor = NULL; |
3287 static jfieldID directBufferAddressField = NULL; |
3287 static jfieldID directBufferAddressField = NULL; |
3842 |
3842 |
3843 // Forward declaration |
3843 // Forward declaration |
3844 extern const struct JNIInvokeInterface_ jni_InvokeInterface; |
3844 extern const struct JNIInvokeInterface_ jni_InvokeInterface; |
3845 |
3845 |
3846 // Global invocation API vars |
3846 // Global invocation API vars |
3847 volatile jint vm_created = 0; |
3847 volatile int vm_created = 0; |
3848 // Indicate whether it is safe to recreate VM |
3848 // Indicate whether it is safe to recreate VM |
3849 volatile jint safe_to_recreate_vm = 1; |
3849 volatile int safe_to_recreate_vm = 1; |
3850 struct JavaVM_ main_vm = {&jni_InvokeInterface}; |
3850 struct JavaVM_ main_vm = {&jni_InvokeInterface}; |
3851 |
3851 |
3852 |
3852 |
3853 #define JAVASTACKSIZE (400 * 1024) /* Default size of a thread java stack */ |
3853 #define JAVASTACKSIZE (400 * 1024) /* Default size of a thread java stack */ |
3854 enum { VERIFY_NONE, VERIFY_REMOTE, VERIFY_ALL }; |
3854 enum { VERIFY_NONE, VERIFY_REMOTE, VERIFY_ALL }; |
4043 // See bug 4367188, the wrapper can sometimes cause VM crashes |
4043 // See bug 4367188, the wrapper can sometimes cause VM crashes |
4044 // JNIWrapper("GetCreatedJavaVMs"); |
4044 // JNIWrapper("GetCreatedJavaVMs"); |
4045 |
4045 |
4046 HOTSPOT_JNI_GETCREATEDJAVAVMS_ENTRY((void **) vm_buf, bufLen, (uintptr_t *) numVMs); |
4046 HOTSPOT_JNI_GETCREATEDJAVAVMS_ENTRY((void **) vm_buf, bufLen, (uintptr_t *) numVMs); |
4047 |
4047 |
4048 if (vm_created) { |
4048 if (vm_created == 1) { |
4049 if (numVMs != NULL) *numVMs = 1; |
4049 if (numVMs != NULL) *numVMs = 1; |
4050 if (bufLen > 0) *vm_buf = (JavaVM *)(&main_vm); |
4050 if (bufLen > 0) *vm_buf = (JavaVM *)(&main_vm); |
4051 } else { |
4051 } else { |
4052 if (numVMs != NULL) *numVMs = 0; |
4052 if (numVMs != NULL) *numVMs = 0; |
4053 } |
4053 } |
4063 static jint JNICALL jni_DestroyJavaVM_inner(JavaVM *vm) { |
4063 static jint JNICALL jni_DestroyJavaVM_inner(JavaVM *vm) { |
4064 HOTSPOT_JNI_DESTROYJAVAVM_ENTRY(vm); |
4064 HOTSPOT_JNI_DESTROYJAVAVM_ENTRY(vm); |
4065 jint res = JNI_ERR; |
4065 jint res = JNI_ERR; |
4066 DT_RETURN_MARK(DestroyJavaVM, jint, (const jint&)res); |
4066 DT_RETURN_MARK(DestroyJavaVM, jint, (const jint&)res); |
4067 |
4067 |
4068 if (!vm_created) { |
4068 if (vm_created == 0) { |
4069 res = JNI_ERR; |
4069 res = JNI_ERR; |
4070 return res; |
4070 return res; |
4071 } |
4071 } |
4072 |
4072 |
4073 JNIWrapper("DestroyJavaVM"); |
4073 JNIWrapper("DestroyJavaVM"); |
4084 // Since this is not a JVM_ENTRY we have to set the thread state manually before entering. |
4084 // Since this is not a JVM_ENTRY we have to set the thread state manually before entering. |
4085 JavaThread* thread = JavaThread::current(); |
4085 JavaThread* thread = JavaThread::current(); |
4086 ThreadStateTransition::transition_from_native(thread, _thread_in_vm); |
4086 ThreadStateTransition::transition_from_native(thread, _thread_in_vm); |
4087 if (Threads::destroy_vm()) { |
4087 if (Threads::destroy_vm()) { |
4088 // Should not change thread state, VM is gone |
4088 // Should not change thread state, VM is gone |
4089 vm_created = false; |
4089 vm_created = 0; |
4090 res = JNI_OK; |
4090 res = JNI_OK; |
4091 return res; |
4091 return res; |
4092 } else { |
4092 } else { |
4093 ThreadStateTransition::transition_and_fence(thread, _thread_in_vm, _thread_in_native); |
4093 ThreadStateTransition::transition_and_fence(thread, _thread_in_vm, _thread_in_native); |
4094 res = JNI_ERR; |
4094 res = JNI_ERR; |
4224 } |
4224 } |
4225 |
4225 |
4226 |
4226 |
4227 jint JNICALL jni_AttachCurrentThread(JavaVM *vm, void **penv, void *_args) { |
4227 jint JNICALL jni_AttachCurrentThread(JavaVM *vm, void **penv, void *_args) { |
4228 HOTSPOT_JNI_ATTACHCURRENTTHREAD_ENTRY(vm, penv, _args); |
4228 HOTSPOT_JNI_ATTACHCURRENTTHREAD_ENTRY(vm, penv, _args); |
4229 if (!vm_created) { |
4229 if (vm_created == 0) { |
4230 HOTSPOT_JNI_ATTACHCURRENTTHREAD_RETURN((uint32_t) JNI_ERR); |
4230 HOTSPOT_JNI_ATTACHCURRENTTHREAD_RETURN((uint32_t) JNI_ERR); |
4231 return JNI_ERR; |
4231 return JNI_ERR; |
4232 } |
4232 } |
4233 |
4233 |
4234 JNIWrapper("AttachCurrentThread"); |
4234 JNIWrapper("AttachCurrentThread"); |
4283 jint JNICALL jni_GetEnv(JavaVM *vm, void **penv, jint version) { |
4283 jint JNICALL jni_GetEnv(JavaVM *vm, void **penv, jint version) { |
4284 HOTSPOT_JNI_GETENV_ENTRY(vm, penv, version); |
4284 HOTSPOT_JNI_GETENV_ENTRY(vm, penv, version); |
4285 jint ret = JNI_ERR; |
4285 jint ret = JNI_ERR; |
4286 DT_RETURN_MARK(GetEnv, jint, (const jint&)ret); |
4286 DT_RETURN_MARK(GetEnv, jint, (const jint&)ret); |
4287 |
4287 |
4288 if (!vm_created) { |
4288 if (vm_created == 0) { |
4289 *penv = NULL; |
4289 *penv = NULL; |
4290 ret = JNI_EDETACHED; |
4290 ret = JNI_EDETACHED; |
4291 return ret; |
4291 return ret; |
4292 } |
4292 } |
4293 |
4293 |
4334 } |
4334 } |
4335 |
4335 |
4336 |
4336 |
4337 jint JNICALL jni_AttachCurrentThreadAsDaemon(JavaVM *vm, void **penv, void *_args) { |
4337 jint JNICALL jni_AttachCurrentThreadAsDaemon(JavaVM *vm, void **penv, void *_args) { |
4338 HOTSPOT_JNI_ATTACHCURRENTTHREADASDAEMON_ENTRY(vm, penv, _args); |
4338 HOTSPOT_JNI_ATTACHCURRENTTHREADASDAEMON_ENTRY(vm, penv, _args); |
4339 if (!vm_created) { |
4339 if (vm_created == 0) { |
4340 HOTSPOT_JNI_ATTACHCURRENTTHREADASDAEMON_RETURN((uint32_t) JNI_ERR); |
4340 HOTSPOT_JNI_ATTACHCURRENTTHREADASDAEMON_RETURN((uint32_t) JNI_ERR); |
4341 return JNI_ERR; |
4341 return JNI_ERR; |
4342 } |
4342 } |
4343 |
4343 |
4344 JNIWrapper("AttachCurrentThreadAsDaemon"); |
4344 JNIWrapper("AttachCurrentThreadAsDaemon"); |