Mon, 03 Jun 2019 16:14:54 +0100
8059575: JEP-JDK-8043304: Test task: Tiered Compilation level transition tests
Summary: Includes compile_id addition from JDK-8054492
Reviewed-by: andrew
1 /*
2 * Copyright (c) 2001, 2015, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.
8 *
9 * This code is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
12 * version 2 for more details (a copy is included in the LICENSE file that
13 * accompanied this code).
14 *
15 * You should have received a copy of the GNU General Public License version
16 * 2 along with this work; if not, write to the Free Software Foundation,
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 *
23 */
25 #include "precompiled.hpp"
26 #include "classfile/systemDictionary.hpp"
27 #include "classfile/vmSymbols.hpp"
28 #include "memory/guardedMemory.hpp"
29 #include "oops/instanceKlass.hpp"
30 #include "oops/oop.inline.hpp"
31 #include "oops/symbol.hpp"
32 #include "prims/jni.h"
33 #include "prims/jniCheck.hpp"
34 #include "prims/jvm_misc.hpp"
35 #include "runtime/fieldDescriptor.hpp"
36 #include "runtime/handles.hpp"
37 #include "runtime/interfaceSupport.hpp"
38 #include "runtime/jfieldIDWorkaround.hpp"
39 #include "runtime/thread.inline.hpp"
40 #ifdef TARGET_ARCH_x86
41 # include "jniTypes_x86.hpp"
42 #endif
43 #ifdef TARGET_ARCH_sparc
44 # include "jniTypes_sparc.hpp"
45 #endif
46 #ifdef TARGET_ARCH_zero
47 # include "jniTypes_zero.hpp"
48 #endif
49 #ifdef TARGET_ARCH_arm
50 # include "jniTypes_arm.hpp"
51 #endif
52 #ifdef TARGET_ARCH_ppc
53 # include "jniTypes_ppc.hpp"
54 #endif
56 // Complain every extra number of unplanned local refs
57 #define CHECK_JNI_LOCAL_REF_CAP_WARN_THRESHOLD 32
59 // Heap objects are allowed to be directly referenced only in VM code,
60 // not in native code.
62 #define ASSERT_OOPS_ALLOWED \
63 assert(JavaThread::current()->thread_state() == _thread_in_vm, \
64 "jniCheck examining oops in bad state.")
67 // Execute the given block of source code with the thread in VM state.
68 // To do this, transition from the NATIVE state to the VM state, execute
69 // the code, and transtition back. The ThreadInVMfromNative constructor
70 // performs the transition to VM state, its destructor restores the
71 // NATIVE state.
73 #define IN_VM(source_code) { \
74 { \
75 ThreadInVMfromNative __tiv(thr); \
76 source_code \
77 } \
78 }
81 /*
82 * DECLARATIONS
83 */
85 static struct JNINativeInterface_ * unchecked_jni_NativeInterface;
88 /*
89 * MACRO DEFINITIONS
90 */
92 // All JNI checked functions here use JNI_ENTRY_CHECKED() instead of the
93 // QUICK_ENTRY or LEAF variants found in jni.cpp. This allows handles
94 // to be created if a fatal error should occur.
96 // Check for thread not attached to VM; need to catch this before
97 // assertions in the wrapper routines might fire
99 // Check for env being the one value appropriate for this thread.
101 #define JNI_ENTRY_CHECKED(result_type, header) \
102 extern "C" { \
103 result_type JNICALL header { \
104 JavaThread* thr = (JavaThread*)ThreadLocalStorage::get_thread_slow();\
105 if (thr == NULL || !thr->is_Java_thread()) { \
106 tty->print_cr("%s", fatal_using_jnienv_in_nonjava); \
107 os::abort(true); \
108 } \
109 JNIEnv* xenv = thr->jni_environment(); \
110 if (env != xenv) { \
111 NativeReportJNIFatalError(thr, warn_wrong_jnienv); \
112 } \
113 VM_ENTRY_BASE(result_type, header, thr)
116 #define UNCHECKED() (unchecked_jni_NativeInterface)
118 static const char * warn_wrong_jnienv = "Using JNIEnv in the wrong thread";
119 static const char * warn_bad_class_descriptor = "JNI FindClass received a bad class descriptor \"%s\". A correct class descriptor " \
120 "has no leading \"L\" or trailing \";\". Incorrect descriptors will not be accepted in future releases.";
121 static const char * fatal_using_jnienv_in_nonjava = "FATAL ERROR in native method: Using JNIEnv in non-Java thread";
122 static const char * warn_other_function_in_critical = "Warning: Calling other JNI functions in the scope of " \
123 "Get/ReleasePrimitiveArrayCritical or Get/ReleaseStringCritical";
124 static const char * fatal_bad_ref_to_jni = "Bad global or local ref passed to JNI";
125 static const char * fatal_received_null_class = "JNI received a null class";
126 static const char * fatal_class_not_a_class = "JNI received a class argument that is not a class";
127 static const char * fatal_class_not_a_throwable_class = "JNI Throw or ThrowNew received a class argument that is not a Throwable or Throwable subclass";
128 static const char * fatal_wrong_class_or_method = "Wrong object class or methodID passed to JNI call";
129 static const char * fatal_non_weak_method = "non-weak methodID passed to JNI call";
130 static const char * fatal_unknown_array_object = "Unknown array object passed to JNI array operations";
131 static const char * fatal_object_array_expected = "Object array expected but not received for JNI array operation";
132 static const char * fatal_prim_type_array_expected = "Primitive type array expected but not received for JNI array operation";
133 static const char * fatal_non_array = "Non-array passed to JNI array operations";
134 static const char * fatal_element_type_mismatch = "Array element type mismatch in JNI";
135 static const char * fatal_should_be_static = "Non-static field ID passed to JNI";
136 static const char * fatal_wrong_static_field = "Wrong static field ID passed to JNI";
137 static const char * fatal_static_field_not_found = "Static field not found in JNI get/set field operations";
138 static const char * fatal_static_field_mismatch = "Field type (static) mismatch in JNI get/set field operations";
139 static const char * fatal_should_be_nonstatic = "Static field ID passed to JNI";
140 static const char * fatal_null_object = "Null object passed to JNI";
141 static const char * fatal_wrong_field = "Wrong field ID passed to JNI";
142 static const char * fatal_instance_field_not_found = "Instance field not found in JNI get/set field operations";
143 static const char * fatal_instance_field_mismatch = "Field type (instance) mismatch in JNI get/set field operations";
144 static const char * fatal_non_string = "JNI string operation received a non-string";
147 // When in VM state:
148 static void ReportJNIWarning(JavaThread* thr, const char *msg) {
149 tty->print_cr("WARNING in native method: %s", msg);
150 thr->print_stack();
151 }
153 // When in NATIVE state:
154 static void NativeReportJNIFatalError(JavaThread* thr, const char *msg) {
155 IN_VM(
156 ReportJNIFatalError(thr, msg);
157 )
158 }
160 static void NativeReportJNIWarning(JavaThread* thr, const char *msg) {
161 IN_VM(
162 ReportJNIWarning(thr, msg);
163 )
164 }
169 /*
170 * SUPPORT FUNCTIONS
171 */
173 /**
174 * Check whether or not a programmer has actually checked for exceptions. According
175 * to the JNI Specification ("jni/spec/design.html#java_exceptions"):
176 *
177 * There are two cases where the programmer needs to check for exceptions without
178 * being able to first check an error code:
179 *
180 * - The JNI functions that invoke a Java method return the result of the Java method.
181 * The programmer must call ExceptionOccurred() to check for possible exceptions
182 * that occurred during the execution of the Java method.
183 *
184 * - Some of the JNI array access functions do not return an error code, but may
185 * throw an ArrayIndexOutOfBoundsException or ArrayStoreException.
186 *
187 * In all other cases, a non-error return value guarantees that no exceptions have been thrown.
188 *
189 * Programmers often defend against ArrayIndexOutOfBoundsException, so warning
190 * for these functions would be pedantic.
191 */
192 static inline void
193 check_pending_exception(JavaThread* thr) {
194 if (thr->has_pending_exception()) {
195 NativeReportJNIWarning(thr, "JNI call made with exception pending");
196 }
197 if (thr->is_pending_jni_exception_check()) {
198 IN_VM(
199 tty->print_cr("WARNING in native method: JNI call made without checking exceptions when required to from %s",
200 thr->get_pending_jni_exception_check());
201 thr->print_stack();
202 )
203 thr->clear_pending_jni_exception_check(); // Just complain once
204 }
205 }
207 /**
208 * Add to the planned number of handles. I.e. plus current live & warning threshold
209 */
210 static inline void
211 add_planned_handle_capacity(JNIHandleBlock* handles, size_t capacity) {
212 handles->set_planned_capacity(capacity +
213 handles->get_number_of_live_handles() +
214 CHECK_JNI_LOCAL_REF_CAP_WARN_THRESHOLD);
215 }
218 static inline void
219 functionEnterCritical(JavaThread* thr)
220 {
221 check_pending_exception(thr);
222 }
224 static inline void
225 functionEnterCriticalExceptionAllowed(JavaThread* thr)
226 {
227 }
229 static inline void
230 functionEnter(JavaThread* thr)
231 {
232 if (thr->in_critical()) {
233 tty->print_cr("%s", warn_other_function_in_critical);
234 }
235 check_pending_exception(thr);
236 }
238 static inline void
239 functionEnterExceptionAllowed(JavaThread* thr)
240 {
241 if (thr->in_critical()) {
242 tty->print_cr("%s", warn_other_function_in_critical);
243 }
244 }
246 static inline void
247 functionExit(JavaThread* thr)
248 {
249 JNIHandleBlock* handles = thr->active_handles();
250 size_t planned_capacity = handles->get_planned_capacity();
251 size_t live_handles = handles->get_number_of_live_handles();
252 if (live_handles > planned_capacity) {
253 IN_VM(
254 tty->print_cr("WARNING: JNI local refs: %zu, exceeds capacity: %zu",
255 live_handles, planned_capacity);
256 thr->print_stack();
257 )
258 // Complain just the once, reset to current + warn threshold
259 add_planned_handle_capacity(handles, 0);
260 }
261 }
263 static inline void
264 checkStaticFieldID(JavaThread* thr, jfieldID fid, jclass cls, int ftype)
265 {
266 fieldDescriptor fd;
268 /* make sure it is a static field */
269 if (!jfieldIDWorkaround::is_static_jfieldID(fid))
270 ReportJNIFatalError(thr, fatal_should_be_static);
272 /* validate the class being passed */
273 ASSERT_OOPS_ALLOWED;
274 Klass* k_oop = jniCheck::validate_class(thr, cls, false);
276 /* check for proper subclass hierarchy */
277 JNIid* id = jfieldIDWorkaround::from_static_jfieldID(fid);
278 Klass* f_oop = id->holder();
279 if (!InstanceKlass::cast(k_oop)->is_subtype_of(f_oop))
280 ReportJNIFatalError(thr, fatal_wrong_static_field);
282 /* check for proper field type */
283 if (!id->find_local_field(&fd))
284 ReportJNIFatalError(thr, fatal_static_field_not_found);
285 if ((fd.field_type() != ftype) &&
286 !(fd.field_type() == T_ARRAY && ftype == T_OBJECT)) {
287 ReportJNIFatalError(thr, fatal_static_field_mismatch);
288 }
289 }
291 static inline void
292 checkInstanceFieldID(JavaThread* thr, jfieldID fid, jobject obj, int ftype)
293 {
294 fieldDescriptor fd;
296 /* make sure it is an instance field */
297 if (jfieldIDWorkaround::is_static_jfieldID(fid))
298 ReportJNIFatalError(thr, fatal_should_be_nonstatic);
300 /* validate the object being passed and then get its class */
301 ASSERT_OOPS_ALLOWED;
302 oop oopObj = jniCheck::validate_object(thr, obj);
303 if (!oopObj) {
304 ReportJNIFatalError(thr, fatal_null_object);
305 }
306 Klass* k_oop = oopObj->klass();
308 if (!jfieldIDWorkaround::is_valid_jfieldID(k_oop, fid)) {
309 ReportJNIFatalError(thr, fatal_wrong_field);
310 }
312 /* make sure the field exists */
313 int offset = jfieldIDWorkaround::from_instance_jfieldID(k_oop, fid);
314 if (!InstanceKlass::cast(k_oop)->contains_field_offset(offset))
315 ReportJNIFatalError(thr, fatal_wrong_field);
317 /* check for proper field type */
318 if (!InstanceKlass::cast(k_oop)->find_field_from_offset(offset,
319 false, &fd))
320 ReportJNIFatalError(thr, fatal_instance_field_not_found);
322 if ((fd.field_type() != ftype) &&
323 !(fd.field_type() == T_ARRAY && ftype == T_OBJECT)) {
324 ReportJNIFatalError(thr, fatal_instance_field_mismatch);
325 }
326 }
328 static inline void
329 checkString(JavaThread* thr, jstring js)
330 {
331 ASSERT_OOPS_ALLOWED;
332 oop s = jniCheck::validate_object(thr, js);
333 if (!s || !java_lang_String::is_instance(s))
334 ReportJNIFatalError(thr, fatal_non_string);
335 }
337 static inline arrayOop
338 check_is_array(JavaThread* thr, jarray jArray)
339 {
340 ASSERT_OOPS_ALLOWED;
341 arrayOop aOop;
343 aOop = (arrayOop)jniCheck::validate_object(thr, jArray);
344 if (aOop == NULL || !aOop->is_array()) {
345 ReportJNIFatalError(thr, fatal_non_array);
346 }
347 return aOop;
348 }
350 static inline arrayOop
351 check_is_primitive_array(JavaThread* thr, jarray jArray) {
352 arrayOop aOop = check_is_array(thr, jArray);
354 if (!aOop->is_typeArray()) {
355 ReportJNIFatalError(thr, fatal_prim_type_array_expected);
356 }
357 return aOop;
358 }
360 static inline void
361 check_primitive_array_type(JavaThread* thr, jarray jArray, BasicType elementType)
362 {
363 BasicType array_type;
364 arrayOop aOop;
366 aOop = check_is_primitive_array(thr, jArray);
367 array_type = TypeArrayKlass::cast(aOop->klass())->element_type();
368 if (array_type != elementType) {
369 ReportJNIFatalError(thr, fatal_element_type_mismatch);
370 }
371 }
373 static inline void
374 check_is_obj_array(JavaThread* thr, jarray jArray) {
375 arrayOop aOop = check_is_array(thr, jArray);
376 if (!aOop->is_objArray()) {
377 ReportJNIFatalError(thr, fatal_object_array_expected);
378 }
379 }
381 /*
382 * Copy and wrap array elements for bounds checking.
383 * Remember the original elements (GuardedMemory::get_tag())
384 */
385 static void* check_jni_wrap_copy_array(JavaThread* thr, jarray array,
386 void* orig_elements) {
387 void* result;
388 IN_VM(
389 oop a = JNIHandles::resolve_non_null(array);
390 size_t len = arrayOop(a)->length() <<
391 TypeArrayKlass::cast(a->klass())->log2_element_size();
392 result = GuardedMemory::wrap_copy(orig_elements, len, orig_elements);
393 )
394 return result;
395 }
397 static void* check_wrapped_array(JavaThread* thr, const char* fn_name,
398 void* obj, void* carray, size_t* rsz) {
399 if (carray == NULL) {
400 tty->print_cr("%s: elements vector NULL" PTR_FORMAT, fn_name, p2i(obj));
401 NativeReportJNIFatalError(thr, "Elements vector NULL");
402 }
403 GuardedMemory guarded(carray);
404 void* orig_result = guarded.get_tag();
405 if (!guarded.verify_guards()) {
406 tty->print_cr("ReleasePrimitiveArrayCritical: release array failed bounds "
407 "check, incorrect pointer returned ? array: " PTR_FORMAT " carray: "
408 PTR_FORMAT, p2i(obj), p2i(carray));
409 guarded.print_on(tty);
410 NativeReportJNIFatalError(thr, "ReleasePrimitiveArrayCritical: "
411 "failed bounds check");
412 }
413 if (orig_result == NULL) {
414 tty->print_cr("ReleasePrimitiveArrayCritical: unrecognized elements. array: "
415 PTR_FORMAT " carray: " PTR_FORMAT, p2i(obj), p2i(carray));
416 guarded.print_on(tty);
417 NativeReportJNIFatalError(thr, "ReleasePrimitiveArrayCritical: "
418 "unrecognized elements");
419 }
420 if (rsz != NULL) {
421 *rsz = guarded.get_user_size();
422 }
423 return orig_result;
424 }
426 static void* check_wrapped_array_release(JavaThread* thr, const char* fn_name,
427 void* obj, void* carray, jint mode) {
428 size_t sz;
429 void* orig_result = check_wrapped_array(thr, fn_name, obj, carray, &sz);
430 switch (mode) {
431 case 0:
432 memcpy(orig_result, carray, sz);
433 GuardedMemory::free_copy(carray);
434 break;
435 case JNI_COMMIT:
436 memcpy(orig_result, carray, sz);
437 break;
438 case JNI_ABORT:
439 GuardedMemory::free_copy(carray);
440 break;
441 default:
442 tty->print_cr("%s: Unrecognized mode %i releasing array "
443 PTR_FORMAT " elements " PTR_FORMAT, fn_name, mode, p2i(obj), p2i(carray));
444 NativeReportJNIFatalError(thr, "Unrecognized array release mode");
445 }
446 return orig_result;
447 }
449 oop jniCheck::validate_handle(JavaThread* thr, jobject obj) {
450 if (JNIHandles::is_frame_handle(thr, obj) ||
451 JNIHandles::is_local_handle(thr, obj) ||
452 JNIHandles::is_global_handle(obj) ||
453 JNIHandles::is_weak_global_handle(obj)) {
454 ASSERT_OOPS_ALLOWED;
455 return JNIHandles::resolve_external_guard(obj);
456 }
457 ReportJNIFatalError(thr, fatal_bad_ref_to_jni);
458 return NULL;
459 }
462 Method* jniCheck::validate_jmethod_id(JavaThread* thr, jmethodID method_id) {
463 ASSERT_OOPS_ALLOWED;
464 // Do the jmethodID check
465 Method* moop = Method::checked_resolve_jmethod_id(method_id);
466 if (moop == NULL) {
467 ReportJNIFatalError(thr, fatal_wrong_class_or_method);
468 }
469 return moop;
470 }
473 oop jniCheck::validate_object(JavaThread* thr, jobject obj) {
474 if (!obj)
475 return NULL;
476 ASSERT_OOPS_ALLOWED;
477 oop oopObj = jniCheck::validate_handle(thr, obj);
478 if (!oopObj) {
479 ReportJNIFatalError(thr, fatal_bad_ref_to_jni);
480 }
481 return oopObj;
482 }
484 // Warn if a class descriptor is in decorated form; class descriptors
485 // passed to JNI findClass should not be decorated unless they are
486 // array descriptors.
487 void jniCheck::validate_class_descriptor(JavaThread* thr, const char* name) {
488 if (name == NULL) return; // implementation accepts NULL so just return
490 size_t len = strlen(name);
492 if (len >= 2 &&
493 name[0] == JVM_SIGNATURE_CLASS && // 'L'
494 name[len-1] == JVM_SIGNATURE_ENDCLASS ) { // ';'
495 char msg[JVM_MAXPATHLEN];
496 jio_snprintf(msg, JVM_MAXPATHLEN, warn_bad_class_descriptor, name);
497 ReportJNIWarning(thr, msg);
498 }
499 }
501 Klass* jniCheck::validate_class(JavaThread* thr, jclass clazz, bool allow_primitive) {
502 ASSERT_OOPS_ALLOWED;
503 oop mirror = jniCheck::validate_handle(thr, clazz);
504 if (!mirror) {
505 ReportJNIFatalError(thr, fatal_received_null_class);
506 }
508 if (mirror->klass() != SystemDictionary::Class_klass()) {
509 ReportJNIFatalError(thr, fatal_class_not_a_class);
510 }
512 Klass* k = java_lang_Class::as_Klass(mirror);
513 // Make allowances for primitive classes ...
514 if (!(k != NULL || allow_primitive && java_lang_Class::is_primitive(mirror))) {
515 ReportJNIFatalError(thr, fatal_class_not_a_class);
516 }
517 return k;
518 }
520 void jniCheck::validate_throwable_klass(JavaThread* thr, Klass* klass) {
521 ASSERT_OOPS_ALLOWED;
522 assert(klass != NULL, "klass argument must have a value");
524 if (!klass->oop_is_instance() ||
525 !InstanceKlass::cast(klass)->is_subclass_of(SystemDictionary::Throwable_klass())) {
526 ReportJNIFatalError(thr, fatal_class_not_a_throwable_class);
527 }
528 }
530 void jniCheck::validate_call_object(JavaThread* thr, jobject obj, jmethodID method_id) {
531 /* validate the object being passed */
532 ASSERT_OOPS_ALLOWED;
533 jniCheck::validate_jmethod_id(thr, method_id);
534 jniCheck::validate_object(thr, obj);
535 }
537 void jniCheck::validate_call_class(JavaThread* thr, jclass clazz, jmethodID method_id) {
538 /* validate the class being passed */
539 ASSERT_OOPS_ALLOWED;
540 jniCheck::validate_jmethod_id(thr, method_id);
541 jniCheck::validate_class(thr, clazz, false);
542 }
545 /*
546 * IMPLEMENTATION OF FUNCTIONS IN CHECKED TABLE
547 */
549 JNI_ENTRY_CHECKED(jclass,
550 checked_jni_DefineClass(JNIEnv *env,
551 const char *name,
552 jobject loader,
553 const jbyte *buf,
554 jsize len))
555 functionEnter(thr);
556 IN_VM(
557 jniCheck::validate_object(thr, loader);
558 )
559 jclass result = UNCHECKED()->DefineClass(env, name, loader, buf, len);
560 functionExit(thr);
561 return result;
562 JNI_END
564 JNI_ENTRY_CHECKED(jclass,
565 checked_jni_FindClass(JNIEnv *env,
566 const char *name))
567 functionEnter(thr);
568 IN_VM(
569 jniCheck::validate_class_descriptor(thr, name);
570 )
571 jclass result = UNCHECKED()->FindClass(env, name);
572 functionExit(thr);
573 return result;
574 JNI_END
576 JNI_ENTRY_CHECKED(jmethodID,
577 checked_jni_FromReflectedMethod(JNIEnv *env,
578 jobject method))
579 functionEnter(thr);
580 IN_VM(
581 jniCheck::validate_object(thr, method);
582 )
583 jmethodID result = UNCHECKED()->FromReflectedMethod(env, method);
584 functionExit(thr);
585 return result;
586 JNI_END
588 JNI_ENTRY_CHECKED(jfieldID,
589 checked_jni_FromReflectedField(JNIEnv *env,
590 jobject field))
591 functionEnter(thr);
592 IN_VM(
593 jniCheck::validate_object(thr, field);
594 )
595 jfieldID result = UNCHECKED()->FromReflectedField(env, field);
596 functionExit(thr);
597 return result;
598 JNI_END
600 JNI_ENTRY_CHECKED(jobject,
601 checked_jni_ToReflectedMethod(JNIEnv *env,
602 jclass cls,
603 jmethodID methodID,
604 jboolean isStatic))
605 functionEnter(thr);
606 IN_VM(
607 jniCheck::validate_class(thr, cls, false);
608 jniCheck::validate_jmethod_id(thr, methodID);
609 )
610 jobject result = UNCHECKED()->ToReflectedMethod(env, cls, methodID,
611 isStatic);
612 functionExit(thr);
613 return result;
614 JNI_END
616 JNI_ENTRY_CHECKED(jclass,
617 checked_jni_GetSuperclass(JNIEnv *env,
618 jclass sub))
619 functionEnter(thr);
620 IN_VM(
621 jniCheck::validate_class(thr, sub, true);
622 )
623 jclass result = UNCHECKED()->GetSuperclass(env, sub);
624 functionExit(thr);
625 return result;
626 JNI_END
628 JNI_ENTRY_CHECKED(jboolean,
629 checked_jni_IsAssignableFrom(JNIEnv *env,
630 jclass sub,
631 jclass sup))
632 functionEnter(thr);
633 IN_VM(
634 jniCheck::validate_class(thr, sub, true);
635 jniCheck::validate_class(thr, sup, true);
636 )
637 jboolean result = UNCHECKED()->IsAssignableFrom(env, sub, sup);
638 functionExit(thr);
639 return result;
640 JNI_END
642 JNI_ENTRY_CHECKED(jobject,
643 checked_jni_ToReflectedField(JNIEnv *env,
644 jclass cls,
645 jfieldID fieldID,
646 jboolean isStatic))
647 functionEnter(thr);
648 IN_VM(
649 jniCheck::validate_class(thr, cls, false);
650 )
651 jobject result = UNCHECKED()->ToReflectedField(env, cls, fieldID,
652 isStatic);
653 functionExit(thr);
654 return result;
655 JNI_END
657 JNI_ENTRY_CHECKED(jint,
658 checked_jni_Throw(JNIEnv *env,
659 jthrowable obj))
660 functionEnter(thr);
661 IN_VM(
662 oop oopObj = jniCheck::validate_object(thr, obj);
663 if (oopObj == NULL) {
664 // Unchecked Throw tolerates a NULL obj, so just warn
665 ReportJNIWarning(thr, "JNI Throw called with NULL throwable");
666 } else {
667 jniCheck::validate_throwable_klass(thr, oopObj->klass());
668 }
669 )
670 jint result = UNCHECKED()->Throw(env, obj);
671 functionExit(thr);
672 return result;
673 JNI_END
675 JNI_ENTRY_CHECKED(jint,
676 checked_jni_ThrowNew(JNIEnv *env,
677 jclass clazz,
678 const char *msg))
679 functionEnter(thr);
680 IN_VM(
681 Klass* k = jniCheck::validate_class(thr, clazz, false);
682 assert(k != NULL, "validate_class shouldn't return NULL Klass*");
683 jniCheck::validate_throwable_klass(thr, k);
684 )
685 jint result = UNCHECKED()->ThrowNew(env, clazz, msg);
686 functionExit(thr);
687 return result;
688 JNI_END
690 JNI_ENTRY_CHECKED(jthrowable,
691 checked_jni_ExceptionOccurred(JNIEnv *env))
692 thr->clear_pending_jni_exception_check();
693 functionEnterExceptionAllowed(thr);
694 jthrowable result = UNCHECKED()->ExceptionOccurred(env);
695 functionExit(thr);
696 return result;
697 JNI_END
699 JNI_ENTRY_CHECKED(void,
700 checked_jni_ExceptionDescribe(JNIEnv *env))
701 functionEnterExceptionAllowed(thr);
702 UNCHECKED()->ExceptionDescribe(env);
703 functionExit(thr);
704 JNI_END
706 JNI_ENTRY_CHECKED(void,
707 checked_jni_ExceptionClear(JNIEnv *env))
708 thr->clear_pending_jni_exception_check();
709 functionEnterExceptionAllowed(thr);
710 UNCHECKED()->ExceptionClear(env);
711 functionExit(thr);
712 JNI_END
714 JNI_ENTRY_CHECKED(void,
715 checked_jni_FatalError(JNIEnv *env,
716 const char *msg))
717 thr->clear_pending_jni_exception_check();
718 functionEnter(thr);
719 UNCHECKED()->FatalError(env, msg);
720 functionExit(thr);
721 JNI_END
723 JNI_ENTRY_CHECKED(jint,
724 checked_jni_PushLocalFrame(JNIEnv *env,
725 jint capacity))
726 functionEnterExceptionAllowed(thr);
727 if (capacity < 0)
728 NativeReportJNIFatalError(thr, "negative capacity");
729 jint result = UNCHECKED()->PushLocalFrame(env, capacity);
730 if (result == JNI_OK) {
731 add_planned_handle_capacity(thr->active_handles(), capacity);
732 }
733 functionExit(thr);
734 return result;
735 JNI_END
737 JNI_ENTRY_CHECKED(jobject,
738 checked_jni_PopLocalFrame(JNIEnv *env,
739 jobject result))
740 functionEnterExceptionAllowed(thr);
741 jobject res = UNCHECKED()->PopLocalFrame(env, result);
742 functionExit(thr);
743 return res;
744 JNI_END
746 JNI_ENTRY_CHECKED(jobject,
747 checked_jni_NewGlobalRef(JNIEnv *env,
748 jobject lobj))
749 functionEnter(thr);
750 IN_VM(
751 if (lobj != NULL) {
752 jniCheck::validate_handle(thr, lobj);
753 }
754 )
755 jobject result = UNCHECKED()->NewGlobalRef(env,lobj);
756 functionExit(thr);
757 return result;
758 JNI_END
760 JNI_ENTRY_CHECKED(void,
761 checked_jni_DeleteGlobalRef(JNIEnv *env,
762 jobject gref))
763 functionEnterExceptionAllowed(thr);
764 IN_VM(
765 jniCheck::validate_object(thr, gref);
766 if (gref && !JNIHandles::is_global_handle(gref)) {
767 ReportJNIFatalError(thr,
768 "Invalid global JNI handle passed to DeleteGlobalRef");
769 }
770 )
771 UNCHECKED()->DeleteGlobalRef(env,gref);
772 functionExit(thr);
773 JNI_END
775 JNI_ENTRY_CHECKED(void,
776 checked_jni_DeleteLocalRef(JNIEnv *env,
777 jobject obj))
778 functionEnterExceptionAllowed(thr);
779 IN_VM(
780 jniCheck::validate_object(thr, obj);
781 if (obj && !(JNIHandles::is_local_handle(thr, obj) ||
782 JNIHandles::is_frame_handle(thr, obj)))
783 ReportJNIFatalError(thr,
784 "Invalid local JNI handle passed to DeleteLocalRef");
785 )
786 UNCHECKED()->DeleteLocalRef(env, obj);
787 functionExit(thr);
788 JNI_END
790 JNI_ENTRY_CHECKED(jboolean,
791 checked_jni_IsSameObject(JNIEnv *env,
792 jobject obj1,
793 jobject obj2))
794 functionEnterExceptionAllowed(thr);
795 IN_VM(
796 /* This JNI function can be used to compare weak global references
797 * to NULL objects. If the handles are valid, but contain NULL,
798 * then don't attempt to validate the object.
799 */
800 if (obj1 != NULL && jniCheck::validate_handle(thr, obj1) != NULL) {
801 jniCheck::validate_object(thr, obj1);
802 }
803 if (obj2 != NULL && jniCheck::validate_handle(thr, obj2) != NULL) {
804 jniCheck::validate_object(thr, obj2);
805 }
806 )
807 jboolean result = UNCHECKED()->IsSameObject(env,obj1,obj2);
808 functionExit(thr);
809 return result;
810 JNI_END
812 JNI_ENTRY_CHECKED(jobject,
813 checked_jni_NewLocalRef(JNIEnv *env,
814 jobject ref))
815 functionEnter(thr);
816 IN_VM(
817 if (ref != NULL) {
818 jniCheck::validate_handle(thr, ref);
819 }
820 )
821 jobject result = UNCHECKED()->NewLocalRef(env, ref);
822 functionExit(thr);
823 return result;
824 JNI_END
826 JNI_ENTRY_CHECKED(jint,
827 checked_jni_EnsureLocalCapacity(JNIEnv *env,
828 jint capacity))
829 functionEnter(thr);
830 if (capacity < 0) {
831 NativeReportJNIFatalError(thr, "negative capacity");
832 }
833 jint result = UNCHECKED()->EnsureLocalCapacity(env, capacity);
834 if (result == JNI_OK) {
835 add_planned_handle_capacity(thr->active_handles(), capacity);
836 }
837 functionExit(thr);
838 return result;
839 JNI_END
841 JNI_ENTRY_CHECKED(jobject,
842 checked_jni_AllocObject(JNIEnv *env,
843 jclass clazz))
844 functionEnter(thr);
845 IN_VM(
846 jniCheck::validate_class(thr, clazz, false);
847 )
848 jobject result = UNCHECKED()->AllocObject(env,clazz);
849 functionExit(thr);
850 return result;
851 JNI_END
853 JNI_ENTRY_CHECKED(jobject,
854 checked_jni_NewObject(JNIEnv *env,
855 jclass clazz,
856 jmethodID methodID,
857 ...))
858 functionEnter(thr);
859 va_list args;
860 IN_VM(
861 jniCheck::validate_class(thr, clazz, false);
862 jniCheck::validate_jmethod_id(thr, methodID);
863 )
864 va_start(args, methodID);
865 jobject result = UNCHECKED()->NewObjectV(env,clazz,methodID,args);
866 va_end(args);
867 functionExit(thr);
868 return result;
869 JNI_END
871 JNI_ENTRY_CHECKED(jobject,
872 checked_jni_NewObjectV(JNIEnv *env,
873 jclass clazz,
874 jmethodID methodID,
875 va_list args))
876 functionEnter(thr);
877 IN_VM(
878 jniCheck::validate_class(thr, clazz, false);
879 jniCheck::validate_jmethod_id(thr, methodID);
880 )
881 jobject result = UNCHECKED()->NewObjectV(env,clazz,methodID,args);
882 functionExit(thr);
883 return result;
884 JNI_END
886 JNI_ENTRY_CHECKED(jobject,
887 checked_jni_NewObjectA(JNIEnv *env,
888 jclass clazz,
889 jmethodID methodID,
890 const jvalue *args))
891 functionEnter(thr);
892 IN_VM(
893 jniCheck::validate_class(thr, clazz, false);
894 jniCheck::validate_jmethod_id(thr, methodID);
895 )
896 jobject result = UNCHECKED()->NewObjectA(env,clazz,methodID,args);
897 functionExit(thr);
898 return result;
899 JNI_END
901 JNI_ENTRY_CHECKED(jclass,
902 checked_jni_GetObjectClass(JNIEnv *env,
903 jobject obj))
904 functionEnter(thr);
905 IN_VM(
906 jniCheck::validate_object(thr, obj);
907 )
908 jclass result = UNCHECKED()->GetObjectClass(env,obj);
909 functionExit(thr);
910 return result;
911 JNI_END
913 JNI_ENTRY_CHECKED(jboolean,
914 checked_jni_IsInstanceOf(JNIEnv *env,
915 jobject obj,
916 jclass clazz))
917 functionEnter(thr);
918 IN_VM(
919 jniCheck::validate_object(thr, obj);
920 jniCheck::validate_class(thr, clazz, true);
921 )
922 jboolean result = UNCHECKED()->IsInstanceOf(env,obj,clazz);
923 functionExit(thr);
924 return result;
925 JNI_END
927 JNI_ENTRY_CHECKED(jmethodID,
928 checked_jni_GetMethodID(JNIEnv *env,
929 jclass clazz,
930 const char *name,
931 const char *sig))
932 functionEnter(thr);
933 IN_VM(
934 jniCheck::validate_class(thr, clazz, false);
935 )
936 jmethodID result = UNCHECKED()->GetMethodID(env,clazz,name,sig);
937 functionExit(thr);
938 return result;
939 JNI_END
941 #define WRAPPER_CallMethod(ResultType, Result) \
942 JNI_ENTRY_CHECKED(ResultType, \
943 checked_jni_Call##Result##Method(JNIEnv *env, \
944 jobject obj, \
945 jmethodID methodID, \
946 ...)) \
947 functionEnter(thr); \
948 va_list args; \
949 IN_VM( \
950 jniCheck::validate_call_object(thr, obj, methodID); \
951 ) \
952 va_start(args,methodID); \
953 ResultType result =UNCHECKED()->Call##Result##MethodV(env, obj, methodID, \
954 args); \
955 va_end(args); \
956 thr->set_pending_jni_exception_check("Call"#Result"Method"); \
957 functionExit(thr); \
958 return result; \
959 JNI_END \
960 \
961 JNI_ENTRY_CHECKED(ResultType, \
962 checked_jni_Call##Result##MethodV(JNIEnv *env, \
963 jobject obj, \
964 jmethodID methodID, \
965 va_list args)) \
966 functionEnter(thr); \
967 IN_VM(\
968 jniCheck::validate_call_object(thr, obj, methodID); \
969 ) \
970 ResultType result = UNCHECKED()->Call##Result##MethodV(env, obj, methodID,\
971 args); \
972 thr->set_pending_jni_exception_check("Call"#Result"MethodV"); \
973 functionExit(thr); \
974 return result; \
975 JNI_END \
976 \
977 JNI_ENTRY_CHECKED(ResultType, \
978 checked_jni_Call##Result##MethodA(JNIEnv *env, \
979 jobject obj, \
980 jmethodID methodID, \
981 const jvalue * args)) \
982 functionEnter(thr); \
983 IN_VM( \
984 jniCheck::validate_call_object(thr, obj, methodID); \
985 ) \
986 ResultType result = UNCHECKED()->Call##Result##MethodA(env, obj, methodID,\
987 args); \
988 thr->set_pending_jni_exception_check("Call"#Result"MethodA"); \
989 functionExit(thr); \
990 return result; \
991 JNI_END
993 WRAPPER_CallMethod(jobject,Object)
994 WRAPPER_CallMethod(jboolean,Boolean)
995 WRAPPER_CallMethod(jbyte,Byte)
996 WRAPPER_CallMethod(jshort,Short)
997 WRAPPER_CallMethod(jchar,Char)
998 WRAPPER_CallMethod(jint,Int)
999 WRAPPER_CallMethod(jlong,Long)
1000 WRAPPER_CallMethod(jfloat,Float)
1001 WRAPPER_CallMethod(jdouble,Double)
1003 JNI_ENTRY_CHECKED(void,
1004 checked_jni_CallVoidMethod(JNIEnv *env, \
1005 jobject obj, \
1006 jmethodID methodID, \
1007 ...))
1008 functionEnter(thr);
1009 va_list args;
1010 IN_VM(
1011 jniCheck::validate_call_object(thr, obj, methodID);
1012 )
1013 va_start(args,methodID);
1014 UNCHECKED()->CallVoidMethodV(env,obj,methodID,args);
1015 va_end(args);
1016 thr->set_pending_jni_exception_check("CallVoidMethod");
1017 functionExit(thr);
1018 JNI_END
1020 JNI_ENTRY_CHECKED(void,
1021 checked_jni_CallVoidMethodV(JNIEnv *env,
1022 jobject obj,
1023 jmethodID methodID,
1024 va_list args))
1025 functionEnter(thr);
1026 IN_VM(
1027 jniCheck::validate_call_object(thr, obj, methodID);
1028 )
1029 UNCHECKED()->CallVoidMethodV(env,obj,methodID,args);
1030 thr->set_pending_jni_exception_check("CallVoidMethodV");
1031 functionExit(thr);
1032 JNI_END
1034 JNI_ENTRY_CHECKED(void,
1035 checked_jni_CallVoidMethodA(JNIEnv *env,
1036 jobject obj,
1037 jmethodID methodID,
1038 const jvalue * args))
1039 functionEnter(thr);
1040 IN_VM(
1041 jniCheck::validate_call_object(thr, obj, methodID);
1042 )
1043 UNCHECKED()->CallVoidMethodA(env,obj,methodID,args);
1044 thr->set_pending_jni_exception_check("CallVoidMethodA");
1045 functionExit(thr);
1046 JNI_END
1048 #define WRAPPER_CallNonvirtualMethod(ResultType, Result) \
1049 JNI_ENTRY_CHECKED(ResultType, \
1050 checked_jni_CallNonvirtual##Result##Method(JNIEnv *env, \
1051 jobject obj, \
1052 jclass clazz, \
1053 jmethodID methodID, \
1054 ...)) \
1055 functionEnter(thr); \
1056 va_list args; \
1057 IN_VM( \
1058 jniCheck::validate_call_object(thr, obj, methodID); \
1059 jniCheck::validate_call_class(thr, clazz, methodID); \
1060 ) \
1061 va_start(args,methodID); \
1062 ResultType result = UNCHECKED()->CallNonvirtual##Result##MethodV(env, \
1063 obj, \
1064 clazz, \
1065 methodID,\
1066 args); \
1067 va_end(args); \
1068 thr->set_pending_jni_exception_check("CallNonvirtual"#Result"Method"); \
1069 functionExit(thr); \
1070 return result; \
1071 JNI_END \
1072 \
1073 JNI_ENTRY_CHECKED(ResultType, \
1074 checked_jni_CallNonvirtual##Result##MethodV(JNIEnv *env, \
1075 jobject obj, \
1076 jclass clazz, \
1077 jmethodID methodID, \
1078 va_list args)) \
1079 functionEnter(thr); \
1080 IN_VM( \
1081 jniCheck::validate_call_object(thr, obj, methodID); \
1082 jniCheck::validate_call_class(thr, clazz, methodID); \
1083 ) \
1084 ResultType result = UNCHECKED()->CallNonvirtual##Result##MethodV(env, \
1085 obj, \
1086 clazz, \
1087 methodID,\
1088 args); \
1089 thr->set_pending_jni_exception_check("CallNonvirtual"#Result"MethodV"); \
1090 functionExit(thr); \
1091 return result; \
1092 JNI_END \
1093 \
1094 JNI_ENTRY_CHECKED(ResultType, \
1095 checked_jni_CallNonvirtual##Result##MethodA(JNIEnv *env, \
1096 jobject obj, \
1097 jclass clazz, \
1098 jmethodID methodID, \
1099 const jvalue * args)) \
1100 functionEnter(thr); \
1101 IN_VM( \
1102 jniCheck::validate_call_object(thr, obj, methodID); \
1103 jniCheck::validate_call_class(thr, clazz, methodID); \
1104 ) \
1105 ResultType result = UNCHECKED()->CallNonvirtual##Result##MethodA(env, \
1106 obj, \
1107 clazz, \
1108 methodID,\
1109 args); \
1110 thr->set_pending_jni_exception_check("CallNonvirtual"#Result"MethodA"); \
1111 functionExit(thr); \
1112 return result; \
1113 JNI_END
1115 WRAPPER_CallNonvirtualMethod(jobject,Object)
1116 WRAPPER_CallNonvirtualMethod(jboolean,Boolean)
1117 WRAPPER_CallNonvirtualMethod(jbyte,Byte)
1118 WRAPPER_CallNonvirtualMethod(jshort,Short)
1119 WRAPPER_CallNonvirtualMethod(jchar,Char)
1120 WRAPPER_CallNonvirtualMethod(jint,Int)
1121 WRAPPER_CallNonvirtualMethod(jlong,Long)
1122 WRAPPER_CallNonvirtualMethod(jfloat,Float)
1123 WRAPPER_CallNonvirtualMethod(jdouble,Double)
1125 JNI_ENTRY_CHECKED(void,
1126 checked_jni_CallNonvirtualVoidMethod(JNIEnv *env,
1127 jobject obj,
1128 jclass clazz,
1129 jmethodID methodID,
1130 ...))
1131 functionEnter(thr);
1132 va_list args;
1133 IN_VM(
1134 jniCheck::validate_call_object(thr, obj, methodID);
1135 jniCheck::validate_call_class(thr, clazz, methodID);
1136 )
1137 va_start(args,methodID);
1138 UNCHECKED()->CallNonvirtualVoidMethodV(env,obj,clazz,methodID,args);
1139 va_end(args);
1140 thr->set_pending_jni_exception_check("CallNonvirtualVoidMethod");
1141 functionExit(thr);
1142 JNI_END
1144 JNI_ENTRY_CHECKED(void,
1145 checked_jni_CallNonvirtualVoidMethodV(JNIEnv *env,
1146 jobject obj,
1147 jclass clazz,
1148 jmethodID methodID,
1149 va_list args))
1150 functionEnter(thr);
1151 IN_VM(
1152 jniCheck::validate_call_object(thr, obj, methodID);
1153 jniCheck::validate_call_class(thr, clazz, methodID);
1154 )
1155 UNCHECKED()->CallNonvirtualVoidMethodV(env,obj,clazz,methodID,args);
1156 thr->set_pending_jni_exception_check("CallNonvirtualVoidMethodV");
1157 functionExit(thr);
1158 JNI_END
1160 JNI_ENTRY_CHECKED(void,
1161 checked_jni_CallNonvirtualVoidMethodA(JNIEnv *env,
1162 jobject obj,
1163 jclass clazz,
1164 jmethodID methodID,
1165 const jvalue * args))
1166 functionEnter(thr);
1167 IN_VM(
1168 jniCheck::validate_call_object(thr, obj, methodID);
1169 jniCheck::validate_call_class(thr, clazz, methodID);
1170 )
1171 UNCHECKED()->CallNonvirtualVoidMethodA(env,obj,clazz,methodID,args);
1172 thr->set_pending_jni_exception_check("CallNonvirtualVoidMethodA");
1173 functionExit(thr);
1174 JNI_END
1176 JNI_ENTRY_CHECKED(jfieldID,
1177 checked_jni_GetFieldID(JNIEnv *env,
1178 jclass clazz,
1179 const char *name,
1180 const char *sig))
1181 functionEnter(thr);
1182 IN_VM(
1183 jniCheck::validate_class(thr, clazz, false);
1184 )
1185 jfieldID result = UNCHECKED()->GetFieldID(env,clazz,name,sig);
1186 functionExit(thr);
1187 return result;
1188 JNI_END
1190 #define WRAPPER_GetField(ReturnType,Result,FieldType) \
1191 JNI_ENTRY_CHECKED(ReturnType, \
1192 checked_jni_Get##Result##Field(JNIEnv *env, \
1193 jobject obj, \
1194 jfieldID fieldID)) \
1195 functionEnter(thr); \
1196 IN_VM( \
1197 checkInstanceFieldID(thr, fieldID, obj, FieldType); \
1198 ) \
1199 ReturnType result = UNCHECKED()->Get##Result##Field(env,obj,fieldID); \
1200 functionExit(thr); \
1201 return result; \
1202 JNI_END
1204 WRAPPER_GetField(jobject, Object, T_OBJECT)
1205 WRAPPER_GetField(jboolean, Boolean, T_BOOLEAN)
1206 WRAPPER_GetField(jbyte, Byte, T_BYTE)
1207 WRAPPER_GetField(jshort, Short, T_SHORT)
1208 WRAPPER_GetField(jchar, Char, T_CHAR)
1209 WRAPPER_GetField(jint, Int, T_INT)
1210 WRAPPER_GetField(jlong, Long, T_LONG)
1211 WRAPPER_GetField(jfloat, Float, T_FLOAT)
1212 WRAPPER_GetField(jdouble, Double, T_DOUBLE)
1214 #define WRAPPER_SetField(ValueType,Result,FieldType) \
1215 JNI_ENTRY_CHECKED(void, \
1216 checked_jni_Set##Result##Field(JNIEnv *env, \
1217 jobject obj, \
1218 jfieldID fieldID, \
1219 ValueType val)) \
1220 functionEnter(thr); \
1221 IN_VM( \
1222 checkInstanceFieldID(thr, fieldID, obj, FieldType); \
1223 ) \
1224 UNCHECKED()->Set##Result##Field(env,obj,fieldID,val); \
1225 functionExit(thr); \
1226 JNI_END
1228 WRAPPER_SetField(jobject, Object, T_OBJECT)
1229 WRAPPER_SetField(jboolean, Boolean, T_BOOLEAN)
1230 WRAPPER_SetField(jbyte, Byte, T_BYTE)
1231 WRAPPER_SetField(jshort, Short, T_SHORT)
1232 WRAPPER_SetField(jchar, Char, T_CHAR)
1233 WRAPPER_SetField(jint, Int, T_INT)
1234 WRAPPER_SetField(jlong, Long, T_LONG)
1235 WRAPPER_SetField(jfloat, Float, T_FLOAT)
1236 WRAPPER_SetField(jdouble, Double, T_DOUBLE)
1239 JNI_ENTRY_CHECKED(jmethodID,
1240 checked_jni_GetStaticMethodID(JNIEnv *env,
1241 jclass clazz,
1242 const char *name,
1243 const char *sig))
1244 functionEnter(thr);
1245 IN_VM(
1246 jniCheck::validate_class(thr, clazz, false);
1247 )
1248 jmethodID result = UNCHECKED()->GetStaticMethodID(env,clazz,name,sig);
1249 functionExit(thr);
1250 return result;
1251 JNI_END
1253 #define WRAPPER_CallStaticMethod(ReturnType,Result) \
1254 JNI_ENTRY_CHECKED(ReturnType, \
1255 checked_jni_CallStatic##Result##Method(JNIEnv *env, \
1256 jclass clazz, \
1257 jmethodID methodID, \
1258 ...)) \
1259 functionEnter(thr); \
1260 va_list args; \
1261 IN_VM( \
1262 jniCheck::validate_jmethod_id(thr, methodID); \
1263 jniCheck::validate_class(thr, clazz, false); \
1264 ) \
1265 va_start(args,methodID); \
1266 ReturnType result = UNCHECKED()->CallStatic##Result##MethodV(env, \
1267 clazz, \
1268 methodID, \
1269 args); \
1270 va_end(args); \
1271 thr->set_pending_jni_exception_check("CallStatic"#Result"Method"); \
1272 functionExit(thr); \
1273 return result; \
1274 JNI_END \
1275 \
1276 JNI_ENTRY_CHECKED(ReturnType, \
1277 checked_jni_CallStatic##Result##MethodV(JNIEnv *env, \
1278 jclass clazz, \
1279 jmethodID methodID,\
1280 va_list args)) \
1281 functionEnter(thr); \
1282 IN_VM( \
1283 jniCheck::validate_jmethod_id(thr, methodID); \
1284 jniCheck::validate_class(thr, clazz, false); \
1285 ) \
1286 ReturnType result = UNCHECKED()->CallStatic##Result##MethodV(env, \
1287 clazz, \
1288 methodID, \
1289 args); \
1290 thr->set_pending_jni_exception_check("CallStatic"#Result"MethodV"); \
1291 functionExit(thr); \
1292 return result; \
1293 JNI_END \
1294 \
1295 JNI_ENTRY_CHECKED(ReturnType, \
1296 checked_jni_CallStatic##Result##MethodA(JNIEnv *env, \
1297 jclass clazz, \
1298 jmethodID methodID, \
1299 const jvalue *args)) \
1300 functionEnter(thr); \
1301 IN_VM( \
1302 jniCheck::validate_jmethod_id(thr, methodID); \
1303 jniCheck::validate_class(thr, clazz, false); \
1304 ) \
1305 ReturnType result = UNCHECKED()->CallStatic##Result##MethodA(env, \
1306 clazz, \
1307 methodID, \
1308 args); \
1309 thr->set_pending_jni_exception_check("CallStatic"#Result"MethodA"); \
1310 functionExit(thr); \
1311 return result; \
1312 JNI_END
1314 WRAPPER_CallStaticMethod(jobject,Object)
1315 WRAPPER_CallStaticMethod(jboolean,Boolean)
1316 WRAPPER_CallStaticMethod(jbyte,Byte)
1317 WRAPPER_CallStaticMethod(jshort,Short)
1318 WRAPPER_CallStaticMethod(jchar,Char)
1319 WRAPPER_CallStaticMethod(jint,Int)
1320 WRAPPER_CallStaticMethod(jlong,Long)
1321 WRAPPER_CallStaticMethod(jfloat,Float)
1322 WRAPPER_CallStaticMethod(jdouble,Double)
1324 JNI_ENTRY_CHECKED(void,
1325 checked_jni_CallStaticVoidMethod(JNIEnv *env,
1326 jclass cls,
1327 jmethodID methodID,
1328 ...))
1329 functionEnter(thr);
1330 va_list args;
1331 IN_VM(
1332 jniCheck::validate_jmethod_id(thr, methodID);
1333 jniCheck::validate_class(thr, cls, false);
1334 )
1335 va_start(args,methodID);
1336 UNCHECKED()->CallStaticVoidMethodV(env,cls,methodID,args);
1337 va_end(args);
1338 thr->set_pending_jni_exception_check("CallStaticVoidMethod");
1339 functionExit(thr);
1340 JNI_END
1342 JNI_ENTRY_CHECKED(void,
1343 checked_jni_CallStaticVoidMethodV(JNIEnv *env,
1344 jclass cls,
1345 jmethodID methodID,
1346 va_list args))
1347 functionEnter(thr);
1348 IN_VM(
1349 jniCheck::validate_jmethod_id(thr, methodID);
1350 jniCheck::validate_class(thr, cls, false);
1351 )
1352 UNCHECKED()->CallStaticVoidMethodV(env,cls,methodID,args);
1353 thr->set_pending_jni_exception_check("CallStaticVoidMethodV");
1354 functionExit(thr);
1355 JNI_END
1357 JNI_ENTRY_CHECKED(void,
1358 checked_jni_CallStaticVoidMethodA(JNIEnv *env,
1359 jclass cls,
1360 jmethodID methodID,
1361 const jvalue * args))
1362 functionEnter(thr);
1363 IN_VM(
1364 jniCheck::validate_jmethod_id(thr, methodID);
1365 jniCheck::validate_class(thr, cls, false);
1366 )
1367 UNCHECKED()->CallStaticVoidMethodA(env,cls,methodID,args);
1368 thr->set_pending_jni_exception_check("CallStaticVoidMethodA");
1369 functionExit(thr);
1370 JNI_END
1372 JNI_ENTRY_CHECKED(jfieldID,
1373 checked_jni_GetStaticFieldID(JNIEnv *env,
1374 jclass clazz,
1375 const char *name,
1376 const char *sig))
1377 functionEnter(thr);
1378 IN_VM(
1379 jniCheck::validate_class(thr, clazz, false);
1380 )
1381 jfieldID result = UNCHECKED()->GetStaticFieldID(env,clazz,name,sig);
1382 functionExit(thr);
1383 return result;
1384 JNI_END
1386 #define WRAPPER_GetStaticField(ReturnType,Result,FieldType) \
1387 JNI_ENTRY_CHECKED(ReturnType, \
1388 checked_jni_GetStatic##Result##Field(JNIEnv *env, \
1389 jclass clazz, \
1390 jfieldID fieldID)) \
1391 functionEnter(thr); \
1392 IN_VM( \
1393 jniCheck::validate_class(thr, clazz, false); \
1394 checkStaticFieldID(thr, fieldID, clazz, FieldType); \
1395 ) \
1396 ReturnType result = UNCHECKED()->GetStatic##Result##Field(env, \
1397 clazz, \
1398 fieldID); \
1399 functionExit(thr); \
1400 return result; \
1401 JNI_END
1403 WRAPPER_GetStaticField(jobject, Object, T_OBJECT)
1404 WRAPPER_GetStaticField(jboolean, Boolean, T_BOOLEAN)
1405 WRAPPER_GetStaticField(jbyte, Byte, T_BYTE)
1406 WRAPPER_GetStaticField(jshort, Short, T_SHORT)
1407 WRAPPER_GetStaticField(jchar, Char, T_CHAR)
1408 WRAPPER_GetStaticField(jint, Int, T_INT)
1409 WRAPPER_GetStaticField(jlong, Long, T_LONG)
1410 WRAPPER_GetStaticField(jfloat, Float, T_FLOAT)
1411 WRAPPER_GetStaticField(jdouble, Double, T_DOUBLE)
1413 #define WRAPPER_SetStaticField(ValueType,Result,FieldType) \
1414 JNI_ENTRY_CHECKED(void, \
1415 checked_jni_SetStatic##Result##Field(JNIEnv *env, \
1416 jclass clazz, \
1417 jfieldID fieldID, \
1418 ValueType value)) \
1419 functionEnter(thr); \
1420 IN_VM( \
1421 jniCheck::validate_class(thr, clazz, false); \
1422 checkStaticFieldID(thr, fieldID, clazz, FieldType); \
1423 ) \
1424 UNCHECKED()->SetStatic##Result##Field(env,clazz,fieldID,value); \
1425 functionExit(thr); \
1426 JNI_END
1428 WRAPPER_SetStaticField(jobject, Object, T_OBJECT)
1429 WRAPPER_SetStaticField(jboolean, Boolean, T_BOOLEAN)
1430 WRAPPER_SetStaticField(jbyte, Byte, T_BYTE)
1431 WRAPPER_SetStaticField(jshort, Short, T_SHORT)
1432 WRAPPER_SetStaticField(jchar, Char, T_CHAR)
1433 WRAPPER_SetStaticField(jint, Int, T_INT)
1434 WRAPPER_SetStaticField(jlong, Long, T_LONG)
1435 WRAPPER_SetStaticField(jfloat, Float, T_FLOAT)
1436 WRAPPER_SetStaticField(jdouble, Double, T_DOUBLE)
1439 JNI_ENTRY_CHECKED(jstring,
1440 checked_jni_NewString(JNIEnv *env,
1441 const jchar *unicode,
1442 jsize len))
1443 functionEnter(thr);
1444 jstring result = UNCHECKED()->NewString(env,unicode,len);
1445 functionExit(thr);
1446 return result;
1447 JNI_END
1449 JNI_ENTRY_CHECKED(jsize,
1450 checked_jni_GetStringLength(JNIEnv *env,
1451 jstring str))
1452 functionEnter(thr);
1453 IN_VM(
1454 checkString(thr, str);
1455 )
1456 jsize result = UNCHECKED()->GetStringLength(env,str);
1457 functionExit(thr);
1458 return result;
1459 JNI_END
1461 // Arbitrary (but well-known) tag
1462 const void* STRING_TAG = (void*)0x47114711;
1464 JNI_ENTRY_CHECKED(const jchar *,
1465 checked_jni_GetStringChars(JNIEnv *env,
1466 jstring str,
1467 jboolean *isCopy))
1468 functionEnter(thr);
1469 IN_VM(
1470 checkString(thr, str);
1471 )
1472 jchar* new_result = NULL;
1473 const jchar *result = UNCHECKED()->GetStringChars(env,str,isCopy);
1474 assert (isCopy == NULL || *isCopy == JNI_TRUE, "GetStringChars didn't return a copy as expected");
1475 if (result != NULL) {
1476 size_t len = UNCHECKED()->GetStringLength(env,str) + 1; // + 1 for NULL termination
1477 len *= sizeof(jchar);
1478 new_result = (jchar*) GuardedMemory::wrap_copy(result, len, STRING_TAG);
1479 if (new_result == NULL) {
1480 vm_exit_out_of_memory(len, OOM_MALLOC_ERROR, "checked_jni_GetStringChars");
1481 }
1482 // Avoiding call to UNCHECKED()->ReleaseStringChars() since that will fire unexpected dtrace probes
1483 // Note that the dtrace arguments for the allocated memory will not match up with this solution.
1484 FreeHeap((char*)result);
1485 }
1486 functionExit(thr);
1487 return new_result;
1488 JNI_END
1490 JNI_ENTRY_CHECKED(void,
1491 checked_jni_ReleaseStringChars(JNIEnv *env,
1492 jstring str,
1493 const jchar *chars))
1494 functionEnterExceptionAllowed(thr);
1495 IN_VM(
1496 checkString(thr, str);
1497 )
1498 if (chars == NULL) {
1499 // still do the unchecked call to allow dtrace probes
1500 UNCHECKED()->ReleaseStringChars(env,str,chars);
1501 }
1502 else {
1503 GuardedMemory guarded((void*)chars);
1504 if (!guarded.verify_guards()) {
1505 tty->print_cr("ReleaseStringChars: release chars failed bounds check. "
1506 "string: " PTR_FORMAT " chars: " PTR_FORMAT, p2i(str), p2i(chars));
1507 guarded.print_on(tty);
1508 NativeReportJNIFatalError(thr, "ReleaseStringChars: "
1509 "release chars failed bounds check.");
1510 }
1511 if (guarded.get_tag() != STRING_TAG) {
1512 tty->print_cr("ReleaseStringChars: called on something not allocated "
1513 "by GetStringChars. string: " PTR_FORMAT " chars: " PTR_FORMAT,
1514 p2i(str), p2i(chars));
1515 NativeReportJNIFatalError(thr, "ReleaseStringChars called on something "
1516 "not allocated by GetStringChars");
1517 }
1518 UNCHECKED()->ReleaseStringChars(env, str,
1519 (const jchar*) guarded.release_for_freeing());
1520 }
1521 functionExit(thr);
1522 JNI_END
1524 JNI_ENTRY_CHECKED(jstring,
1525 checked_jni_NewStringUTF(JNIEnv *env,
1526 const char *utf))
1527 functionEnter(thr);
1528 jstring result = UNCHECKED()->NewStringUTF(env,utf);
1529 functionExit(thr);
1530 return result;
1531 JNI_END
1533 JNI_ENTRY_CHECKED(jsize,
1534 checked_jni_GetStringUTFLength(JNIEnv *env,
1535 jstring str))
1536 functionEnter(thr);
1537 IN_VM(
1538 checkString(thr, str);
1539 )
1540 jsize result = UNCHECKED()->GetStringUTFLength(env,str);
1541 functionExit(thr);
1542 return result;
1543 JNI_END
1545 // Arbitrary (but well-known) tag - different than GetStringChars
1546 const void* STRING_UTF_TAG = (void*) 0x48124812;
1548 JNI_ENTRY_CHECKED(const char *,
1549 checked_jni_GetStringUTFChars(JNIEnv *env,
1550 jstring str,
1551 jboolean *isCopy))
1552 functionEnter(thr);
1553 IN_VM(
1554 checkString(thr, str);
1555 )
1556 char* new_result = NULL;
1557 const char *result = UNCHECKED()->GetStringUTFChars(env,str,isCopy);
1558 assert (isCopy == NULL || *isCopy == JNI_TRUE, "GetStringUTFChars didn't return a copy as expected");
1559 if (result != NULL) {
1560 size_t len = strlen(result) + 1; // + 1 for NULL termination
1561 new_result = (char*) GuardedMemory::wrap_copy(result, len, STRING_UTF_TAG);
1562 if (new_result == NULL) {
1563 vm_exit_out_of_memory(len, OOM_MALLOC_ERROR, "checked_jni_GetStringUTFChars");
1564 }
1565 // Avoiding call to UNCHECKED()->ReleaseStringUTFChars() since that will fire unexpected dtrace probes
1566 // Note that the dtrace arguments for the allocated memory will not match up with this solution.
1567 FreeHeap((char*)result, mtInternal);
1568 }
1569 functionExit(thr);
1570 return new_result;
1571 JNI_END
1573 JNI_ENTRY_CHECKED(void,
1574 checked_jni_ReleaseStringUTFChars(JNIEnv *env,
1575 jstring str,
1576 const char* chars))
1577 functionEnterExceptionAllowed(thr);
1578 IN_VM(
1579 checkString(thr, str);
1580 )
1581 if (chars == NULL) {
1582 // still do the unchecked call to allow dtrace probes
1583 UNCHECKED()->ReleaseStringUTFChars(env,str,chars);
1584 }
1585 else {
1586 GuardedMemory guarded((void*)chars);
1587 if (!guarded.verify_guards()) {
1588 tty->print_cr("ReleaseStringUTFChars: release chars failed bounds check. "
1589 "string: " PTR_FORMAT " chars: " PTR_FORMAT, p2i(str), p2i(chars));
1590 guarded.print_on(tty);
1591 NativeReportJNIFatalError(thr, "ReleaseStringUTFChars: "
1592 "release chars failed bounds check.");
1593 }
1594 if (guarded.get_tag() != STRING_UTF_TAG) {
1595 tty->print_cr("ReleaseStringUTFChars: called on something not "
1596 "allocated by GetStringUTFChars. string: " PTR_FORMAT " chars: "
1597 PTR_FORMAT, p2i(str), p2i(chars));
1598 NativeReportJNIFatalError(thr, "ReleaseStringUTFChars "
1599 "called on something not allocated by GetStringUTFChars");
1600 }
1601 UNCHECKED()->ReleaseStringUTFChars(env, str,
1602 (const char*) guarded.release_for_freeing());
1603 }
1604 functionExit(thr);
1605 JNI_END
1607 JNI_ENTRY_CHECKED(jsize,
1608 checked_jni_GetArrayLength(JNIEnv *env,
1609 jarray array))
1610 functionEnter(thr);
1611 IN_VM(
1612 check_is_array(thr, array);
1613 )
1614 jsize result = UNCHECKED()->GetArrayLength(env,array);
1615 functionExit(thr);
1616 return result;
1617 JNI_END
1619 JNI_ENTRY_CHECKED(jobjectArray,
1620 checked_jni_NewObjectArray(JNIEnv *env,
1621 jsize len,
1622 jclass clazz,
1623 jobject init))
1624 functionEnter(thr);
1625 jobjectArray result = UNCHECKED()->NewObjectArray(env,len,clazz,init);
1626 functionExit(thr);
1627 return result;
1628 JNI_END
1630 JNI_ENTRY_CHECKED(jobject,
1631 checked_jni_GetObjectArrayElement(JNIEnv *env,
1632 jobjectArray array,
1633 jsize index))
1634 functionEnter(thr);
1635 IN_VM(
1636 check_is_obj_array(thr, array);
1637 )
1638 jobject result = UNCHECKED()->GetObjectArrayElement(env,array,index);
1639 functionExit(thr);
1640 return result;
1641 JNI_END
1643 JNI_ENTRY_CHECKED(void,
1644 checked_jni_SetObjectArrayElement(JNIEnv *env,
1645 jobjectArray array,
1646 jsize index,
1647 jobject val))
1648 functionEnter(thr);
1649 IN_VM(
1650 check_is_obj_array(thr, array);
1651 )
1652 UNCHECKED()->SetObjectArrayElement(env,array,index,val);
1653 functionExit(thr);
1654 JNI_END
1656 #define WRAPPER_NewScalarArray(Return, Result) \
1657 JNI_ENTRY_CHECKED(Return, \
1658 checked_jni_New##Result##Array(JNIEnv *env, \
1659 jsize len)) \
1660 functionEnter(thr); \
1661 Return result = UNCHECKED()->New##Result##Array(env,len); \
1662 functionExit(thr); \
1663 return (Return) result; \
1664 JNI_END
1666 WRAPPER_NewScalarArray(jbooleanArray, Boolean)
1667 WRAPPER_NewScalarArray(jbyteArray, Byte)
1668 WRAPPER_NewScalarArray(jshortArray, Short)
1669 WRAPPER_NewScalarArray(jcharArray, Char)
1670 WRAPPER_NewScalarArray(jintArray, Int)
1671 WRAPPER_NewScalarArray(jlongArray, Long)
1672 WRAPPER_NewScalarArray(jfloatArray, Float)
1673 WRAPPER_NewScalarArray(jdoubleArray, Double)
1675 #define WRAPPER_GetScalarArrayElements(ElementTag,ElementType,Result) \
1676 JNI_ENTRY_CHECKED(ElementType *, \
1677 checked_jni_Get##Result##ArrayElements(JNIEnv *env, \
1678 ElementType##Array array, \
1679 jboolean *isCopy)) \
1680 functionEnter(thr); \
1681 IN_VM( \
1682 check_primitive_array_type(thr, array, ElementTag); \
1683 ) \
1684 ElementType *result = UNCHECKED()->Get##Result##ArrayElements(env, \
1685 array, \
1686 isCopy); \
1687 if (result != NULL) { \
1688 result = (ElementType *) check_jni_wrap_copy_array(thr, array, result); \
1689 } \
1690 functionExit(thr); \
1691 return result; \
1692 JNI_END
1694 WRAPPER_GetScalarArrayElements(T_BOOLEAN, jboolean, Boolean)
1695 WRAPPER_GetScalarArrayElements(T_BYTE, jbyte, Byte)
1696 WRAPPER_GetScalarArrayElements(T_SHORT, jshort, Short)
1697 WRAPPER_GetScalarArrayElements(T_CHAR, jchar, Char)
1698 WRAPPER_GetScalarArrayElements(T_INT, jint, Int)
1699 WRAPPER_GetScalarArrayElements(T_LONG, jlong, Long)
1700 WRAPPER_GetScalarArrayElements(T_FLOAT, jfloat, Float)
1701 WRAPPER_GetScalarArrayElements(T_DOUBLE, jdouble, Double)
1703 #define WRAPPER_ReleaseScalarArrayElements(ElementTag,ElementType,Result,Tag) \
1704 JNI_ENTRY_CHECKED(void, \
1705 checked_jni_Release##Result##ArrayElements(JNIEnv *env, \
1706 ElementType##Array array, \
1707 ElementType *elems, \
1708 jint mode)) \
1709 functionEnterExceptionAllowed(thr); \
1710 IN_VM( \
1711 check_primitive_array_type(thr, array, ElementTag); \
1712 ASSERT_OOPS_ALLOWED; \
1713 typeArrayOop a = typeArrayOop(JNIHandles::resolve_non_null(array)); \
1714 ) \
1715 ElementType* orig_result = (ElementType *) check_wrapped_array_release( \
1716 thr, "checked_jni_Release"#Result"ArrayElements", array, elems, mode); \
1717 UNCHECKED()->Release##Result##ArrayElements(env, array, orig_result, mode); \
1718 functionExit(thr); \
1719 JNI_END
1721 WRAPPER_ReleaseScalarArrayElements(T_BOOLEAN,jboolean, Boolean, bool)
1722 WRAPPER_ReleaseScalarArrayElements(T_BYTE, jbyte, Byte, byte)
1723 WRAPPER_ReleaseScalarArrayElements(T_SHORT, jshort, Short, short)
1724 WRAPPER_ReleaseScalarArrayElements(T_CHAR, jchar, Char, char)
1725 WRAPPER_ReleaseScalarArrayElements(T_INT, jint, Int, int)
1726 WRAPPER_ReleaseScalarArrayElements(T_LONG, jlong, Long, long)
1727 WRAPPER_ReleaseScalarArrayElements(T_FLOAT, jfloat, Float, float)
1728 WRAPPER_ReleaseScalarArrayElements(T_DOUBLE, jdouble, Double, double)
1730 #define WRAPPER_GetScalarArrayRegion(ElementTag,ElementType,Result) \
1731 JNI_ENTRY_CHECKED(void, \
1732 checked_jni_Get##Result##ArrayRegion(JNIEnv *env, \
1733 ElementType##Array array, \
1734 jsize start, \
1735 jsize len, \
1736 ElementType *buf)) \
1737 functionEnter(thr); \
1738 IN_VM( \
1739 check_primitive_array_type(thr, array, ElementTag); \
1740 ) \
1741 UNCHECKED()->Get##Result##ArrayRegion(env,array,start,len,buf); \
1742 functionExit(thr); \
1743 JNI_END
1745 WRAPPER_GetScalarArrayRegion(T_BOOLEAN, jboolean, Boolean)
1746 WRAPPER_GetScalarArrayRegion(T_BYTE, jbyte, Byte)
1747 WRAPPER_GetScalarArrayRegion(T_SHORT, jshort, Short)
1748 WRAPPER_GetScalarArrayRegion(T_CHAR, jchar, Char)
1749 WRAPPER_GetScalarArrayRegion(T_INT, jint, Int)
1750 WRAPPER_GetScalarArrayRegion(T_LONG, jlong, Long)
1751 WRAPPER_GetScalarArrayRegion(T_FLOAT, jfloat, Float)
1752 WRAPPER_GetScalarArrayRegion(T_DOUBLE, jdouble, Double)
1754 #define WRAPPER_SetScalarArrayRegion(ElementTag,ElementType,Result) \
1755 JNI_ENTRY_CHECKED(void, \
1756 checked_jni_Set##Result##ArrayRegion(JNIEnv *env, \
1757 ElementType##Array array, \
1758 jsize start, \
1759 jsize len, \
1760 const ElementType *buf)) \
1761 functionEnter(thr); \
1762 IN_VM( \
1763 check_primitive_array_type(thr, array, ElementTag); \
1764 ) \
1765 UNCHECKED()->Set##Result##ArrayRegion(env,array,start,len,buf); \
1766 functionExit(thr); \
1767 JNI_END
1769 WRAPPER_SetScalarArrayRegion(T_BOOLEAN, jboolean, Boolean)
1770 WRAPPER_SetScalarArrayRegion(T_BYTE, jbyte, Byte)
1771 WRAPPER_SetScalarArrayRegion(T_SHORT, jshort, Short)
1772 WRAPPER_SetScalarArrayRegion(T_CHAR, jchar, Char)
1773 WRAPPER_SetScalarArrayRegion(T_INT, jint, Int)
1774 WRAPPER_SetScalarArrayRegion(T_LONG, jlong, Long)
1775 WRAPPER_SetScalarArrayRegion(T_FLOAT, jfloat, Float)
1776 WRAPPER_SetScalarArrayRegion(T_DOUBLE, jdouble, Double)
1778 JNI_ENTRY_CHECKED(jint,
1779 checked_jni_RegisterNatives(JNIEnv *env,
1780 jclass clazz,
1781 const JNINativeMethod *methods,
1782 jint nMethods))
1783 functionEnter(thr);
1784 jint result = UNCHECKED()->RegisterNatives(env,clazz,methods,nMethods);
1785 functionExit(thr);
1786 return result;
1787 JNI_END
1789 JNI_ENTRY_CHECKED(jint,
1790 checked_jni_UnregisterNatives(JNIEnv *env,
1791 jclass clazz))
1792 functionEnter(thr);
1793 jint result = UNCHECKED()->UnregisterNatives(env,clazz);
1794 functionExit(thr);
1795 return result;
1796 JNI_END
1798 JNI_ENTRY_CHECKED(jint,
1799 checked_jni_MonitorEnter(JNIEnv *env,
1800 jobject obj))
1801 functionEnter(thr);
1802 IN_VM(
1803 jniCheck::validate_object(thr, obj);
1804 )
1805 jint result = UNCHECKED()->MonitorEnter(env,obj);
1806 functionExit(thr);
1807 return result;
1808 JNI_END
1810 JNI_ENTRY_CHECKED(jint,
1811 checked_jni_MonitorExit(JNIEnv *env,
1812 jobject obj))
1813 functionEnterExceptionAllowed(thr);
1814 IN_VM(
1815 jniCheck::validate_object(thr, obj);
1816 )
1817 jint result = UNCHECKED()->MonitorExit(env,obj);
1818 functionExit(thr);
1819 return result;
1820 JNI_END
1822 JNI_ENTRY_CHECKED(jint,
1823 checked_jni_GetJavaVM(JNIEnv *env,
1824 JavaVM **vm))
1825 functionEnter(thr);
1826 jint result = UNCHECKED()->GetJavaVM(env,vm);
1827 functionExit(thr);
1828 return result;
1829 JNI_END
1831 JNI_ENTRY_CHECKED(void,
1832 checked_jni_GetStringRegion(JNIEnv *env,
1833 jstring str,
1834 jsize start,
1835 jsize len,
1836 jchar *buf))
1837 functionEnter(thr);
1838 IN_VM(
1839 checkString(thr, str);
1840 )
1841 UNCHECKED()->GetStringRegion(env, str, start, len, buf);
1842 functionExit(thr);
1843 JNI_END
1845 JNI_ENTRY_CHECKED(void,
1846 checked_jni_GetStringUTFRegion(JNIEnv *env,
1847 jstring str,
1848 jsize start,
1849 jsize len,
1850 char *buf))
1851 functionEnter(thr);
1852 IN_VM(
1853 checkString(thr, str);
1854 )
1855 UNCHECKED()->GetStringUTFRegion(env, str, start, len, buf);
1856 functionExit(thr);
1857 JNI_END
1859 JNI_ENTRY_CHECKED(void *,
1860 checked_jni_GetPrimitiveArrayCritical(JNIEnv *env,
1861 jarray array,
1862 jboolean *isCopy))
1863 functionEnterCritical(thr);
1864 IN_VM(
1865 check_is_primitive_array(thr, array);
1866 )
1867 void *result = UNCHECKED()->GetPrimitiveArrayCritical(env, array, isCopy);
1868 if (result != NULL) {
1869 result = check_jni_wrap_copy_array(thr, array, result);
1870 }
1871 functionExit(thr);
1872 return result;
1873 JNI_END
1875 JNI_ENTRY_CHECKED(void,
1876 checked_jni_ReleasePrimitiveArrayCritical(JNIEnv *env,
1877 jarray array,
1878 void *carray,
1879 jint mode))
1880 functionEnterCriticalExceptionAllowed(thr);
1881 IN_VM(
1882 check_is_primitive_array(thr, array);
1883 )
1884 // Check the element array...
1885 void* orig_result = check_wrapped_array_release(thr, "ReleasePrimitiveArrayCritical", array, carray, mode);
1886 UNCHECKED()->ReleasePrimitiveArrayCritical(env, array, orig_result, mode);
1887 functionExit(thr);
1888 JNI_END
1890 JNI_ENTRY_CHECKED(const jchar*,
1891 checked_jni_GetStringCritical(JNIEnv *env,
1892 jstring string,
1893 jboolean *isCopy))
1894 functionEnterCritical(thr);
1895 IN_VM(
1896 checkString(thr, string);
1897 )
1898 const jchar *result = UNCHECKED()->GetStringCritical(env, string, isCopy);
1899 functionExit(thr);
1900 return result;
1901 JNI_END
1903 JNI_ENTRY_CHECKED(void,
1904 checked_jni_ReleaseStringCritical(JNIEnv *env,
1905 jstring str,
1906 const jchar *chars))
1907 functionEnterCriticalExceptionAllowed(thr);
1908 IN_VM(
1909 checkString(thr, str);
1910 )
1911 /* The Hotspot JNI code does not use the parameters, so just check the
1912 * string parameter as a minor sanity check
1913 */
1914 UNCHECKED()->ReleaseStringCritical(env, str, chars);
1915 functionExit(thr);
1916 JNI_END
1918 JNI_ENTRY_CHECKED(jweak,
1919 checked_jni_NewWeakGlobalRef(JNIEnv *env,
1920 jobject obj))
1921 functionEnter(thr);
1922 IN_VM(
1923 if (obj != NULL) {
1924 jniCheck::validate_handle(thr, obj);
1925 }
1926 )
1927 jweak result = UNCHECKED()->NewWeakGlobalRef(env, obj);
1928 functionExit(thr);
1929 return result;
1930 JNI_END
1932 JNI_ENTRY_CHECKED(void,
1933 checked_jni_DeleteWeakGlobalRef(JNIEnv *env,
1934 jweak ref))
1935 functionEnterExceptionAllowed(thr);
1936 UNCHECKED()->DeleteWeakGlobalRef(env, ref);
1937 functionExit(thr);
1938 JNI_END
1940 JNI_ENTRY_CHECKED(jboolean,
1941 checked_jni_ExceptionCheck(JNIEnv *env))
1942 thr->clear_pending_jni_exception_check();
1943 functionEnterExceptionAllowed(thr);
1944 jboolean result = UNCHECKED()->ExceptionCheck(env);
1945 functionExit(thr);
1946 return result;
1947 JNI_END
1949 JNI_ENTRY_CHECKED(jobject,
1950 checked_jni_NewDirectByteBuffer(JNIEnv *env,
1951 void *address,
1952 jlong capacity))
1953 functionEnter(thr);
1954 jobject result = UNCHECKED()->NewDirectByteBuffer(env, address, capacity);
1955 functionExit(thr);
1956 return result;
1957 JNI_END
1959 JNI_ENTRY_CHECKED(void *,
1960 checked_jni_GetDirectBufferAddress(JNIEnv *env,
1961 jobject buf))
1962 functionEnter(thr);
1963 void* result = UNCHECKED()->GetDirectBufferAddress(env, buf);
1964 functionExit(thr);
1965 return result;
1966 JNI_END
1968 JNI_ENTRY_CHECKED(jlong,
1969 checked_jni_GetDirectBufferCapacity(JNIEnv *env,
1970 jobject buf))
1971 functionEnter(thr);
1972 jlong result = UNCHECKED()->GetDirectBufferCapacity(env, buf);
1973 functionExit(thr);
1974 return result;
1975 JNI_END
1977 JNI_ENTRY_CHECKED(jobjectRefType,
1978 checked_jni_GetObjectRefType(JNIEnv *env,
1979 jobject obj))
1980 functionEnter(thr);
1981 /* validate the object being passed */
1982 IN_VM(
1983 jniCheck::validate_object(thr, obj);
1984 )
1985 jobjectRefType result = UNCHECKED()->GetObjectRefType(env, obj);
1986 functionExit(thr);
1987 return result;
1988 JNI_END
1991 JNI_ENTRY_CHECKED(jint,
1992 checked_jni_GetVersion(JNIEnv *env))
1993 functionEnter(thr);
1994 jint result = UNCHECKED()->GetVersion(env);
1995 functionExit(thr);
1996 return result;
1997 JNI_END
2001 /*
2002 * Structure containing all checked jni functions
2003 */
2004 struct JNINativeInterface_ checked_jni_NativeInterface = {
2005 NULL,
2006 NULL,
2007 NULL,
2009 NULL,
2011 checked_jni_GetVersion,
2013 checked_jni_DefineClass,
2014 checked_jni_FindClass,
2016 checked_jni_FromReflectedMethod,
2017 checked_jni_FromReflectedField,
2019 checked_jni_ToReflectedMethod,
2021 checked_jni_GetSuperclass,
2022 checked_jni_IsAssignableFrom,
2024 checked_jni_ToReflectedField,
2026 checked_jni_Throw,
2027 checked_jni_ThrowNew,
2028 checked_jni_ExceptionOccurred,
2029 checked_jni_ExceptionDescribe,
2030 checked_jni_ExceptionClear,
2031 checked_jni_FatalError,
2033 checked_jni_PushLocalFrame,
2034 checked_jni_PopLocalFrame,
2036 checked_jni_NewGlobalRef,
2037 checked_jni_DeleteGlobalRef,
2038 checked_jni_DeleteLocalRef,
2039 checked_jni_IsSameObject,
2041 checked_jni_NewLocalRef,
2042 checked_jni_EnsureLocalCapacity,
2044 checked_jni_AllocObject,
2045 checked_jni_NewObject,
2046 checked_jni_NewObjectV,
2047 checked_jni_NewObjectA,
2049 checked_jni_GetObjectClass,
2050 checked_jni_IsInstanceOf,
2052 checked_jni_GetMethodID,
2054 checked_jni_CallObjectMethod,
2055 checked_jni_CallObjectMethodV,
2056 checked_jni_CallObjectMethodA,
2057 checked_jni_CallBooleanMethod,
2058 checked_jni_CallBooleanMethodV,
2059 checked_jni_CallBooleanMethodA,
2060 checked_jni_CallByteMethod,
2061 checked_jni_CallByteMethodV,
2062 checked_jni_CallByteMethodA,
2063 checked_jni_CallCharMethod,
2064 checked_jni_CallCharMethodV,
2065 checked_jni_CallCharMethodA,
2066 checked_jni_CallShortMethod,
2067 checked_jni_CallShortMethodV,
2068 checked_jni_CallShortMethodA,
2069 checked_jni_CallIntMethod,
2070 checked_jni_CallIntMethodV,
2071 checked_jni_CallIntMethodA,
2072 checked_jni_CallLongMethod,
2073 checked_jni_CallLongMethodV,
2074 checked_jni_CallLongMethodA,
2075 checked_jni_CallFloatMethod,
2076 checked_jni_CallFloatMethodV,
2077 checked_jni_CallFloatMethodA,
2078 checked_jni_CallDoubleMethod,
2079 checked_jni_CallDoubleMethodV,
2080 checked_jni_CallDoubleMethodA,
2081 checked_jni_CallVoidMethod,
2082 checked_jni_CallVoidMethodV,
2083 checked_jni_CallVoidMethodA,
2085 checked_jni_CallNonvirtualObjectMethod,
2086 checked_jni_CallNonvirtualObjectMethodV,
2087 checked_jni_CallNonvirtualObjectMethodA,
2088 checked_jni_CallNonvirtualBooleanMethod,
2089 checked_jni_CallNonvirtualBooleanMethodV,
2090 checked_jni_CallNonvirtualBooleanMethodA,
2091 checked_jni_CallNonvirtualByteMethod,
2092 checked_jni_CallNonvirtualByteMethodV,
2093 checked_jni_CallNonvirtualByteMethodA,
2094 checked_jni_CallNonvirtualCharMethod,
2095 checked_jni_CallNonvirtualCharMethodV,
2096 checked_jni_CallNonvirtualCharMethodA,
2097 checked_jni_CallNonvirtualShortMethod,
2098 checked_jni_CallNonvirtualShortMethodV,
2099 checked_jni_CallNonvirtualShortMethodA,
2100 checked_jni_CallNonvirtualIntMethod,
2101 checked_jni_CallNonvirtualIntMethodV,
2102 checked_jni_CallNonvirtualIntMethodA,
2103 checked_jni_CallNonvirtualLongMethod,
2104 checked_jni_CallNonvirtualLongMethodV,
2105 checked_jni_CallNonvirtualLongMethodA,
2106 checked_jni_CallNonvirtualFloatMethod,
2107 checked_jni_CallNonvirtualFloatMethodV,
2108 checked_jni_CallNonvirtualFloatMethodA,
2109 checked_jni_CallNonvirtualDoubleMethod,
2110 checked_jni_CallNonvirtualDoubleMethodV,
2111 checked_jni_CallNonvirtualDoubleMethodA,
2112 checked_jni_CallNonvirtualVoidMethod,
2113 checked_jni_CallNonvirtualVoidMethodV,
2114 checked_jni_CallNonvirtualVoidMethodA,
2116 checked_jni_GetFieldID,
2118 checked_jni_GetObjectField,
2119 checked_jni_GetBooleanField,
2120 checked_jni_GetByteField,
2121 checked_jni_GetCharField,
2122 checked_jni_GetShortField,
2123 checked_jni_GetIntField,
2124 checked_jni_GetLongField,
2125 checked_jni_GetFloatField,
2126 checked_jni_GetDoubleField,
2128 checked_jni_SetObjectField,
2129 checked_jni_SetBooleanField,
2130 checked_jni_SetByteField,
2131 checked_jni_SetCharField,
2132 checked_jni_SetShortField,
2133 checked_jni_SetIntField,
2134 checked_jni_SetLongField,
2135 checked_jni_SetFloatField,
2136 checked_jni_SetDoubleField,
2138 checked_jni_GetStaticMethodID,
2140 checked_jni_CallStaticObjectMethod,
2141 checked_jni_CallStaticObjectMethodV,
2142 checked_jni_CallStaticObjectMethodA,
2143 checked_jni_CallStaticBooleanMethod,
2144 checked_jni_CallStaticBooleanMethodV,
2145 checked_jni_CallStaticBooleanMethodA,
2146 checked_jni_CallStaticByteMethod,
2147 checked_jni_CallStaticByteMethodV,
2148 checked_jni_CallStaticByteMethodA,
2149 checked_jni_CallStaticCharMethod,
2150 checked_jni_CallStaticCharMethodV,
2151 checked_jni_CallStaticCharMethodA,
2152 checked_jni_CallStaticShortMethod,
2153 checked_jni_CallStaticShortMethodV,
2154 checked_jni_CallStaticShortMethodA,
2155 checked_jni_CallStaticIntMethod,
2156 checked_jni_CallStaticIntMethodV,
2157 checked_jni_CallStaticIntMethodA,
2158 checked_jni_CallStaticLongMethod,
2159 checked_jni_CallStaticLongMethodV,
2160 checked_jni_CallStaticLongMethodA,
2161 checked_jni_CallStaticFloatMethod,
2162 checked_jni_CallStaticFloatMethodV,
2163 checked_jni_CallStaticFloatMethodA,
2164 checked_jni_CallStaticDoubleMethod,
2165 checked_jni_CallStaticDoubleMethodV,
2166 checked_jni_CallStaticDoubleMethodA,
2167 checked_jni_CallStaticVoidMethod,
2168 checked_jni_CallStaticVoidMethodV,
2169 checked_jni_CallStaticVoidMethodA,
2171 checked_jni_GetStaticFieldID,
2173 checked_jni_GetStaticObjectField,
2174 checked_jni_GetStaticBooleanField,
2175 checked_jni_GetStaticByteField,
2176 checked_jni_GetStaticCharField,
2177 checked_jni_GetStaticShortField,
2178 checked_jni_GetStaticIntField,
2179 checked_jni_GetStaticLongField,
2180 checked_jni_GetStaticFloatField,
2181 checked_jni_GetStaticDoubleField,
2183 checked_jni_SetStaticObjectField,
2184 checked_jni_SetStaticBooleanField,
2185 checked_jni_SetStaticByteField,
2186 checked_jni_SetStaticCharField,
2187 checked_jni_SetStaticShortField,
2188 checked_jni_SetStaticIntField,
2189 checked_jni_SetStaticLongField,
2190 checked_jni_SetStaticFloatField,
2191 checked_jni_SetStaticDoubleField,
2193 checked_jni_NewString,
2194 checked_jni_GetStringLength,
2195 checked_jni_GetStringChars,
2196 checked_jni_ReleaseStringChars,
2198 checked_jni_NewStringUTF,
2199 checked_jni_GetStringUTFLength,
2200 checked_jni_GetStringUTFChars,
2201 checked_jni_ReleaseStringUTFChars,
2203 checked_jni_GetArrayLength,
2205 checked_jni_NewObjectArray,
2206 checked_jni_GetObjectArrayElement,
2207 checked_jni_SetObjectArrayElement,
2209 checked_jni_NewBooleanArray,
2210 checked_jni_NewByteArray,
2211 checked_jni_NewCharArray,
2212 checked_jni_NewShortArray,
2213 checked_jni_NewIntArray,
2214 checked_jni_NewLongArray,
2215 checked_jni_NewFloatArray,
2216 checked_jni_NewDoubleArray,
2218 checked_jni_GetBooleanArrayElements,
2219 checked_jni_GetByteArrayElements,
2220 checked_jni_GetCharArrayElements,
2221 checked_jni_GetShortArrayElements,
2222 checked_jni_GetIntArrayElements,
2223 checked_jni_GetLongArrayElements,
2224 checked_jni_GetFloatArrayElements,
2225 checked_jni_GetDoubleArrayElements,
2227 checked_jni_ReleaseBooleanArrayElements,
2228 checked_jni_ReleaseByteArrayElements,
2229 checked_jni_ReleaseCharArrayElements,
2230 checked_jni_ReleaseShortArrayElements,
2231 checked_jni_ReleaseIntArrayElements,
2232 checked_jni_ReleaseLongArrayElements,
2233 checked_jni_ReleaseFloatArrayElements,
2234 checked_jni_ReleaseDoubleArrayElements,
2236 checked_jni_GetBooleanArrayRegion,
2237 checked_jni_GetByteArrayRegion,
2238 checked_jni_GetCharArrayRegion,
2239 checked_jni_GetShortArrayRegion,
2240 checked_jni_GetIntArrayRegion,
2241 checked_jni_GetLongArrayRegion,
2242 checked_jni_GetFloatArrayRegion,
2243 checked_jni_GetDoubleArrayRegion,
2245 checked_jni_SetBooleanArrayRegion,
2246 checked_jni_SetByteArrayRegion,
2247 checked_jni_SetCharArrayRegion,
2248 checked_jni_SetShortArrayRegion,
2249 checked_jni_SetIntArrayRegion,
2250 checked_jni_SetLongArrayRegion,
2251 checked_jni_SetFloatArrayRegion,
2252 checked_jni_SetDoubleArrayRegion,
2254 checked_jni_RegisterNatives,
2255 checked_jni_UnregisterNatives,
2257 checked_jni_MonitorEnter,
2258 checked_jni_MonitorExit,
2260 checked_jni_GetJavaVM,
2262 checked_jni_GetStringRegion,
2263 checked_jni_GetStringUTFRegion,
2265 checked_jni_GetPrimitiveArrayCritical,
2266 checked_jni_ReleasePrimitiveArrayCritical,
2268 checked_jni_GetStringCritical,
2269 checked_jni_ReleaseStringCritical,
2271 checked_jni_NewWeakGlobalRef,
2272 checked_jni_DeleteWeakGlobalRef,
2274 checked_jni_ExceptionCheck,
2276 checked_jni_NewDirectByteBuffer,
2277 checked_jni_GetDirectBufferAddress,
2278 checked_jni_GetDirectBufferCapacity,
2280 // New 1.6 Features
2282 checked_jni_GetObjectRefType
2283 };
2286 // Returns the function structure
2287 struct JNINativeInterface_* jni_functions_check() {
2289 unchecked_jni_NativeInterface = jni_functions_nocheck();
2291 // make sure the last pointer in the checked table is not null, indicating
2292 // an addition to the JNINativeInterface_ structure without initializing
2293 // it in the checked table.
2294 debug_only(int *lastPtr = (int *)((char *)&checked_jni_NativeInterface + \
2295 sizeof(*unchecked_jni_NativeInterface) - sizeof(char *));)
2296 assert(*lastPtr != 0,
2297 "Mismatched JNINativeInterface tables, check for new entries");
2299 // with -verbose:jni this message will print
2300 if (PrintJNIResolving) {
2301 tty->print_cr("Checked JNI functions are being used to " \
2302 "validate JNI usage");
2303 }
2305 return &checked_jni_NativeInterface;
2306 }