< prev index next >

src/share/vm/prims/jni.cpp

Print this page




 322   jclass cls = NULL;
 323   DT_RETURN_MARK(DefineClass, jclass, (const jclass&)cls);
 324 
 325   TempNewSymbol class_name = NULL;
 326   // Since exceptions can be thrown, class initialization can take place
 327   // if name is NULL no check for class name in .class stream has to be made.
 328   if (name != NULL) {
 329     const int str_len = (int)strlen(name);
 330     if (str_len > Symbol::max_length()) {
 331       // It's impossible to create this class;  the name cannot fit
 332       // into the constant pool.
 333       THROW_MSG_0(vmSymbols::java_lang_NoClassDefFoundError(), name);
 334     }
 335     class_name = SymbolTable::new_symbol(name, CHECK_NULL);
 336   }
 337   ResourceMark rm(THREAD);
 338   ClassFileStream st((u1*) buf, bufLen, NULL);
 339   Handle class_loader (THREAD, JNIHandles::resolve(loaderRef));
 340 
 341   if (UsePerfData && !class_loader.is_null()) {

 342     // check whether the current caller thread holds the lock or not.
 343     // If not, increment the corresponding counter
 344     if (ObjectSynchronizer::
 345         query_lock_ownership((JavaThread*)THREAD, class_loader) !=
 346         ObjectSynchronizer::owner_self) {
 347       ClassLoader::sync_JNIDefineClassLockFreeCounter()->inc();
 348     }
 349   }
 350   Klass* k = SystemDictionary::resolve_from_stream(class_name, class_loader,
 351                                                      Handle(), &st, true,
 352                                                      CHECK_NULL);
 353 
 354   if (TraceClassResolution && k != NULL) {
 355     trace_class_resolution(k);
 356   }
 357 
 358   cls = (jclass)JNIHandles::make_local(
 359     env, k->java_mirror());
 360   return cls;
 361 JNI_END
 362 
 363 
 364 
 365 static bool first_time_FindClass = true;


 561   // super2 is the value computed by the compiler's getSuperClass intrinsic:
 562   debug_only(Klass* super2 = ( k->oop_is_array()
 563                                  ? SystemDictionary::Object_klass()
 564                                  : k->super() ) );
 565   assert(super == super2,
 566          "java_super computation depends on interface, array, other super");
 567   obj = (super == NULL) ? NULL : (jclass) JNIHandles::make_local(super->java_mirror());
 568   return obj;
 569 JNI_END
 570 
 571 JNI_QUICK_ENTRY(jboolean, jni_IsAssignableFrom(JNIEnv *env, jclass sub, jclass super))
 572   JNIWrapper("IsSubclassOf");
 573 
 574   HOTSPOT_JNI_ISASSIGNABLEFROM_ENTRY(env, sub, super);
 575 
 576   oop sub_mirror   = JNIHandles::resolve_non_null(sub);
 577   oop super_mirror = JNIHandles::resolve_non_null(super);
 578   if (java_lang_Class::is_primitive(sub_mirror) ||
 579       java_lang_Class::is_primitive(super_mirror)) {
 580     jboolean ret = (sub_mirror == super_mirror);
 581 




 582     HOTSPOT_JNI_ISASSIGNABLEFROM_RETURN(ret);
 583     return ret;
 584   }
 585   Klass* sub_klass   = java_lang_Class::as_Klass(sub_mirror);
 586   Klass* super_klass = java_lang_Class::as_Klass(super_mirror);
 587   assert(sub_klass != NULL && super_klass != NULL, "invalid arguments to jni_IsAssignableFrom");
 588   jboolean ret = sub_klass->is_subtype_of(super_klass) ?
 589                    JNI_TRUE : JNI_FALSE;
 590 
 591   HOTSPOT_JNI_ISASSIGNABLEFROM_RETURN(ret);
 592   return ret;
 593 JNI_END
 594 
 595 
 596 DT_RETURN_MARK_DECL(Throw, jint
 597                     , HOTSPOT_JNI_THROW_RETURN(_ret_ref));
 598 
 599 JNI_ENTRY(jint, jni_Throw(JNIEnv *env, jthrowable obj))
 600   JNIWrapper("Throw");
 601 


 803 
 804 JNI_QUICK_ENTRY(void, jni_DeleteLocalRef(JNIEnv *env, jobject obj))
 805   JNIWrapper("DeleteLocalRef");
 806 
 807   HOTSPOT_JNI_DELETELOCALREF_ENTRY(env, obj);
 808 
 809   JNIHandles::destroy_local(obj);
 810 
 811   HOTSPOT_JNI_DELETELOCALREF_RETURN();
 812 JNI_END
 813 
 814 JNI_QUICK_ENTRY(jboolean, jni_IsSameObject(JNIEnv *env, jobject r1, jobject r2))
 815   JNIWrapper("IsSameObject");
 816 
 817   HOTSPOT_JNI_ISSAMEOBJECT_ENTRY(env, r1, r2);
 818 
 819   oop a = JNIHandles::resolve(r1);
 820   oop b = JNIHandles::resolve(r2);
 821   jboolean ret = (a == b) ? JNI_TRUE : JNI_FALSE;
 822 





 823   HOTSPOT_JNI_ISSAMEOBJECT_RETURN(ret);
 824   return ret;
 825 JNI_END
 826 
 827 
 828 JNI_ENTRY(jobject, jni_NewLocalRef(JNIEnv *env, jobject ref))
 829   JNIWrapper("NewLocalRef");
 830 
 831   HOTSPOT_JNI_NEWLOCALREF_ENTRY(env, ref);
 832 
 833   jobject ret = JNIHandles::make_local(env, JNIHandles::resolve(ref));
 834 
 835   HOTSPOT_JNI_NEWLOCALREF_RETURN(ret);
 836   return ret;
 837 JNI_END
 838 
 839 JNI_LEAF(jint, jni_EnsureLocalCapacity(JNIEnv *env, jint capacity))
 840   JNIWrapper("EnsureLocalCapacity");
 841 
 842   HOTSPOT_JNI_ENSURELOCALCAPACITY_ENTRY(env, capacity);


2045   return ret;
2046 JNI_END
2047 
2048 
2049 JNI_ENTRY(jobject, jni_GetObjectField(JNIEnv *env, jobject obj, jfieldID fieldID))
2050   JNIWrapper("GetObjectField");
2051   HOTSPOT_JNI_GETOBJECTFIELD_ENTRY(env, obj, (uintptr_t) fieldID);
2052   oop o = JNIHandles::resolve_non_null(obj);
2053   Klass* k = o->klass();
2054   int offset = jfieldIDWorkaround::from_instance_jfieldID(k, fieldID);
2055   // Keep JVMTI addition small and only check enabled flag here.
2056   // jni_GetField_probe() assumes that is okay to create handles.
2057   if (JvmtiExport::should_post_field_access()) {
2058     o = JvmtiExport::jni_GetField_probe(thread, obj, o, k, fieldID, false);
2059   }
2060   jobject ret = JNIHandles::make_local(env, o->obj_field(offset));
2061 #if INCLUDE_ALL_GCS
2062   // If G1 is enabled and we are accessing the value of the referent
2063   // field in a reference object then we need to register a non-null
2064   // referent with the SATB barrier.
2065   if (UseG1GC) {
2066     bool needs_barrier = false;
2067 
2068     if (ret != NULL &&
2069         offset == java_lang_ref_Reference::referent_offset &&
2070         InstanceKlass::cast(k)->reference_type() != REF_NONE) {
2071       assert(InstanceKlass::cast(k)->is_subclass_of(SystemDictionary::Reference_klass()), "sanity");
2072       needs_barrier = true;
2073     }
2074 
2075     if (needs_barrier) {
2076       oop referent = JNIHandles::resolve(ret);
2077       G1SATBCardTableModRefBS::enqueue(referent);
2078     }
2079   }
2080 #endif // INCLUDE_ALL_GCS
2081 HOTSPOT_JNI_GETOBJECTFIELD_RETURN(ret);
2082   return ret;
2083 JNI_END
2084 
2085 


2698     if (bad_address != NULL) {
2699       os::protect_memory(bad_address, size, os::MEM_PROT_READ,
2700                          /*is_committed*/false);
2701       MemTracker::record_virtual_memory_type((void*)bad_address, mtInternal);
2702     }
2703   }
2704   return bad_address;
2705 }
2706 
2707 
2708 
2709 #define DEFINE_GETSCALARARRAYELEMENTS(ElementTag,ElementType,Result, Tag \
2710                                       , EntryProbe, ReturnProbe) \
2711 \
2712 JNI_QUICK_ENTRY(ElementType*, \
2713           jni_Get##Result##ArrayElements(JNIEnv *env, ElementType##Array array, jboolean *isCopy)) \
2714   JNIWrapper("Get" XSTR(Result) "ArrayElements"); \
2715   EntryProbe; \
2716   /* allocate an chunk of memory in c land */ \
2717   typeArrayOop a = typeArrayOop(JNIHandles::resolve_non_null(array)); \

2718   ElementType* result; \
2719   int len = a->length(); \
2720   if (len == 0) { \
2721     /* Empty array: legal but useless, can't return NULL. \
2722      * Return a pointer to something useless. \
2723      * Avoid asserts in typeArrayOop. */ \
2724     result = (ElementType*)get_bad_address(); \
2725   } else { \
2726     /* JNI Specification states return NULL on OOM */                    \
2727     result = NEW_C_HEAP_ARRAY_RETURN_NULL(ElementType, len, mtInternal); \
2728     if (result != NULL) {                                                \
2729       /* copy the array to the c chunk */                                \
2730       memcpy(result, a->Tag##_at_addr(0), sizeof(ElementType)*len);      \
2731       if (isCopy) {                                                      \
2732         *isCopy = JNI_TRUE;                                              \
2733       }                                                                  \
2734     }                                                                    \
2735   } \
2736   ReturnProbe; \
2737   return result; \


2756                               , HOTSPOT_JNI_GETLONGARRAYELEMENTS_ENTRY(env, array, (uintptr_t *) isCopy),
2757                               HOTSPOT_JNI_GETLONGARRAYELEMENTS_RETURN(((uintptr_t*)result)))
2758 // Float and double probes don't return value because dtrace doesn't currently support it
2759 DEFINE_GETSCALARARRAYELEMENTS(T_FLOAT,   jfloat,   Float,   float
2760                               , HOTSPOT_JNI_GETFLOATARRAYELEMENTS_ENTRY(env, array, (uintptr_t *) isCopy),
2761                               HOTSPOT_JNI_GETFLOATARRAYELEMENTS_RETURN(result))
2762 DEFINE_GETSCALARARRAYELEMENTS(T_DOUBLE,  jdouble,  Double,  double
2763                               , HOTSPOT_JNI_GETDOUBLEARRAYELEMENTS_ENTRY(env, array, (uintptr_t *) isCopy),
2764                               HOTSPOT_JNI_GETDOUBLEARRAYELEMENTS_RETURN(result))
2765 
2766 
2767 #define DEFINE_RELEASESCALARARRAYELEMENTS(ElementTag,ElementType,Result,Tag \
2768                                           , EntryProbe, ReturnProbe);\
2769 \
2770 JNI_QUICK_ENTRY(void, \
2771           jni_Release##Result##ArrayElements(JNIEnv *env, ElementType##Array array, \
2772                                              ElementType *buf, jint mode)) \
2773   JNIWrapper("Release" XSTR(Result) "ArrayElements"); \
2774   EntryProbe; \
2775   typeArrayOop a = typeArrayOop(JNIHandles::resolve_non_null(array)); \

2776   int len = a->length(); \
2777   if (len != 0) {   /* Empty array:  nothing to free or copy. */  \
2778     if ((mode == 0) || (mode == JNI_COMMIT)) { \
2779       memcpy(a->Tag##_at_addr(0), buf, sizeof(ElementType)*len); \
2780     } \
2781     if ((mode == 0) || (mode == JNI_ABORT)) { \
2782       FreeHeap(buf); \
2783     } \
2784   } \
2785   ReturnProbe; \
2786 JNI_END
2787 
2788 DEFINE_RELEASESCALARARRAYELEMENTS(T_BOOLEAN, jboolean, Boolean, bool
2789                                   , HOTSPOT_JNI_RELEASEBOOLEANARRAYELEMENTS_ENTRY(env, array, (uintptr_t *) buf, mode),
2790                                   HOTSPOT_JNI_RELEASEBOOLEANARRAYELEMENTS_RETURN())
2791 DEFINE_RELEASESCALARARRAYELEMENTS(T_BYTE,    jbyte,    Byte,    byte
2792                                   , HOTSPOT_JNI_RELEASEBYTEARRAYELEMENTS_ENTRY(env, array, (char *) buf, mode),
2793                                   HOTSPOT_JNI_RELEASEBYTEARRAYELEMENTS_RETURN())
2794 DEFINE_RELEASESCALARARRAYELEMENTS(T_SHORT,   jshort,   Short,   short
2795                                   ,  HOTSPOT_JNI_RELEASESHORTARRAYELEMENTS_ENTRY(env, array, (uint16_t *) buf, mode),


2806 DEFINE_RELEASESCALARARRAYELEMENTS(T_FLOAT,   jfloat,   Float,   float
2807                                   , HOTSPOT_JNI_RELEASEFLOATARRAYELEMENTS_ENTRY(env, array, (float *) buf, mode),
2808                                   HOTSPOT_JNI_RELEASEFLOATARRAYELEMENTS_RETURN())
2809 DEFINE_RELEASESCALARARRAYELEMENTS(T_DOUBLE,  jdouble,  Double,  double
2810                                   , HOTSPOT_JNI_RELEASEDOUBLEARRAYELEMENTS_ENTRY(env, array, (double *) buf, mode),
2811                                   HOTSPOT_JNI_RELEASEDOUBLEARRAYELEMENTS_RETURN())
2812 
2813 
2814 #define DEFINE_GETSCALARARRAYREGION(ElementTag,ElementType,Result, Tag \
2815                                     , EntryProbe, ReturnProbe); \
2816   DT_VOID_RETURN_MARK_DECL(Get##Result##ArrayRegion \
2817                            , ReturnProbe); \
2818 \
2819 JNI_ENTRY(void, \
2820 jni_Get##Result##ArrayRegion(JNIEnv *env, ElementType##Array array, jsize start, \
2821              jsize len, ElementType *buf)) \
2822   JNIWrapper("Get" XSTR(Result) "ArrayRegion"); \
2823   EntryProbe; \
2824   DT_VOID_RETURN_MARK(Get##Result##ArrayRegion); \
2825   typeArrayOop src = typeArrayOop(JNIHandles::resolve_non_null(array)); \

2826   if (start < 0 || len < 0 || ((unsigned int)start + (unsigned int)len > (unsigned int)src->length())) { \
2827     THROW(vmSymbols::java_lang_ArrayIndexOutOfBoundsException()); \
2828   } else { \
2829     if (len > 0) { \
2830       int sc = TypeArrayKlass::cast(src->klass())->log2_element_size(); \
2831       memcpy((u_char*) buf, \
2832              (u_char*) src->Tag##_at_addr(start), \
2833              len << sc);                          \
2834     } \
2835   } \
2836 JNI_END
2837 
2838 DEFINE_GETSCALARARRAYREGION(T_BOOLEAN, jboolean,Boolean, bool
2839                             , HOTSPOT_JNI_GETBOOLEANARRAYREGION_ENTRY(env, array, start, len, (uintptr_t *) buf),
2840                             HOTSPOT_JNI_GETBOOLEANARRAYREGION_RETURN());
2841 DEFINE_GETSCALARARRAYREGION(T_BYTE,    jbyte,   Byte,    byte
2842                             ,  HOTSPOT_JNI_GETBYTEARRAYREGION_ENTRY(env, array, start, len, (char *) buf),
2843                             HOTSPOT_JNI_GETBYTEARRAYREGION_RETURN());
2844 DEFINE_GETSCALARARRAYREGION(T_SHORT,   jshort,  Short,   short
2845                             , HOTSPOT_JNI_GETSHORTARRAYREGION_ENTRY(env, array, start, len, (uint16_t *) buf),


2856 DEFINE_GETSCALARARRAYREGION(T_FLOAT,   jfloat,  Float,   float
2857                             , HOTSPOT_JNI_GETFLOATARRAYREGION_ENTRY(env, array, start, len, (float *) buf),
2858                             HOTSPOT_JNI_GETFLOATARRAYREGION_RETURN());
2859 DEFINE_GETSCALARARRAYREGION(T_DOUBLE,  jdouble, Double,  double
2860                             , HOTSPOT_JNI_GETDOUBLEARRAYREGION_ENTRY(env, array, start, len, (double *) buf),
2861                             HOTSPOT_JNI_GETDOUBLEARRAYREGION_RETURN());
2862 
2863 
2864 #define DEFINE_SETSCALARARRAYREGION(ElementTag,ElementType,Result, Tag \
2865                                     , EntryProbe, ReturnProbe); \
2866   DT_VOID_RETURN_MARK_DECL(Set##Result##ArrayRegion \
2867                            ,ReturnProbe);           \
2868 \
2869 JNI_ENTRY(void, \
2870 jni_Set##Result##ArrayRegion(JNIEnv *env, ElementType##Array array, jsize start, \
2871              jsize len, const ElementType *buf)) \
2872   JNIWrapper("Set" XSTR(Result) "ArrayRegion"); \
2873   EntryProbe; \
2874   DT_VOID_RETURN_MARK(Set##Result##ArrayRegion); \
2875   typeArrayOop dst = typeArrayOop(JNIHandles::resolve_non_null(array)); \

2876   if (start < 0 || len < 0 || ((unsigned int)start + (unsigned int)len > (unsigned int)dst->length())) { \
2877     THROW(vmSymbols::java_lang_ArrayIndexOutOfBoundsException()); \
2878   } else { \
2879     if (len > 0) { \
2880       int sc = TypeArrayKlass::cast(dst->klass())->log2_element_size(); \
2881       memcpy((u_char*) dst->Tag##_at_addr(start), \
2882              (u_char*) buf, \
2883              len << sc);    \
2884     } \
2885   } \
2886 JNI_END
2887 
2888 DEFINE_SETSCALARARRAYREGION(T_BOOLEAN, jboolean, Boolean, bool
2889                             , HOTSPOT_JNI_SETBOOLEANARRAYREGION_ENTRY(env, array, start, len, (uintptr_t *)buf),
2890                             HOTSPOT_JNI_SETBOOLEANARRAYREGION_RETURN())
2891 DEFINE_SETSCALARARRAYREGION(T_BYTE,    jbyte,    Byte,    byte
2892                             , HOTSPOT_JNI_SETBYTEARRAYREGION_ENTRY(env, array, start, len, (char *) buf),
2893                             HOTSPOT_JNI_SETBYTEARRAYREGION_RETURN())
2894 DEFINE_SETSCALARARRAYREGION(T_SHORT,   jshort,   Short,   short
2895                             , HOTSPOT_JNI_SETSHORTARRAYREGION_ENTRY(env, array, start, len, (uint16_t *) buf),


3054   return 0;
3055 JNI_END
3056 
3057 //
3058 // Monitor functions
3059 //
3060 
3061 DT_RETURN_MARK_DECL(MonitorEnter, jint
3062                     , HOTSPOT_JNI_MONITORENTER_RETURN(_ret_ref));
3063 
3064 JNI_ENTRY(jint, jni_MonitorEnter(JNIEnv *env, jobject jobj))
3065  HOTSPOT_JNI_MONITORENTER_ENTRY(env, jobj);
3066   jint ret = JNI_ERR;
3067   DT_RETURN_MARK(MonitorEnter, jint, (const jint&)ret);
3068 
3069   // If the object is null, we can't do anything with it
3070   if (jobj == NULL) {
3071     THROW_(vmSymbols::java_lang_NullPointerException(), JNI_ERR);
3072   }
3073 
3074   Handle obj(thread, JNIHandles::resolve_non_null(jobj));
3075   ObjectSynchronizer::jni_enter(obj, CHECK_(JNI_ERR));
3076   ret = JNI_OK;
3077   return ret;
3078 JNI_END
3079 
3080 DT_RETURN_MARK_DECL(MonitorExit, jint
3081                     , HOTSPOT_JNI_MONITOREXIT_RETURN(_ret_ref));
3082 
3083 JNI_ENTRY(jint, jni_MonitorExit(JNIEnv *env, jobject jobj))
3084  HOTSPOT_JNI_MONITOREXIT_ENTRY(env, jobj);
3085   jint ret = JNI_ERR;
3086   DT_RETURN_MARK(MonitorExit, jint, (const jint&)ret);
3087 
3088   // Don't do anything with a null object
3089   if (jobj == NULL) {
3090     THROW_(vmSymbols::java_lang_NullPointerException(), JNI_ERR);
3091   }
3092 
3093   Handle obj(THREAD, JNIHandles::resolve_non_null(jobj));
3094   ObjectSynchronizer::jni_exit(obj(), CHECK_(JNI_ERR));
3095 
3096   ret = JNI_OK;
3097   return ret;
3098 JNI_END
3099 
3100 //
3101 // Extensions
3102 //
3103 
3104 DT_VOID_RETURN_MARK_DECL(GetStringRegion
3105                          , HOTSPOT_JNI_GETSTRINGREGION_RETURN());
3106 
3107 JNI_ENTRY(void, jni_GetStringRegion(JNIEnv *env, jstring string, jsize start, jsize len, jchar *buf))
3108   JNIWrapper("GetStringRegion");
3109  HOTSPOT_JNI_GETSTRINGREGION_ENTRY(env, string, start, len, buf);
3110   DT_VOID_RETURN_MARK(GetStringRegion);
3111   oop s = JNIHandles::resolve_non_null(string);
3112   int s_len = java_lang_String::length(s);
3113   if (start < 0 || len < 0 || start + len > s_len) {


3139       java_lang_String::as_utf8_string(s, start, len, buf, INT_MAX);
3140       // as_utf8_string null-terminates the result string
3141     } else {
3142       // JDK null-terminates the buffer even in len is zero
3143       if (buf != NULL) {
3144         buf[0] = 0;
3145       }
3146     }
3147   }
3148 JNI_END
3149 
3150 
3151 JNI_ENTRY(void*, jni_GetPrimitiveArrayCritical(JNIEnv *env, jarray array, jboolean *isCopy))
3152   JNIWrapper("GetPrimitiveArrayCritical");
3153  HOTSPOT_JNI_GETPRIMITIVEARRAYCRITICAL_ENTRY(env, array, (uintptr_t *) isCopy);
3154   GC_locker::lock_critical(thread);
3155   if (isCopy != NULL) {
3156     *isCopy = JNI_FALSE;
3157   }
3158   oop a = JNIHandles::resolve_non_null(array);

3159   assert(a->is_array(), "just checking");
3160   BasicType type;
3161   if (a->is_objArray()) {
3162     type = T_OBJECT;
3163   } else {
3164     type = TypeArrayKlass::cast(a->klass())->element_type();
3165   }
3166   void* ret = arrayOop(a)->base(type);
3167  HOTSPOT_JNI_GETPRIMITIVEARRAYCRITICAL_RETURN(ret);
3168   return ret;
3169 JNI_END
3170 
3171 
3172 JNI_ENTRY(void, jni_ReleasePrimitiveArrayCritical(JNIEnv *env, jarray array, void *carray, jint mode))
3173   JNIWrapper("ReleasePrimitiveArrayCritical");
3174   HOTSPOT_JNI_RELEASEPRIMITIVEARRAYCRITICAL_ENTRY(env, array, carray, mode);
3175   // The array, carray and mode arguments are ignored
3176   GC_locker::unlock_critical(thread);
3177 HOTSPOT_JNI_RELEASEPRIMITIVEARRAYCRITICAL_RETURN();
3178 JNI_END




 322   jclass cls = NULL;
 323   DT_RETURN_MARK(DefineClass, jclass, (const jclass&)cls);
 324 
 325   TempNewSymbol class_name = NULL;
 326   // Since exceptions can be thrown, class initialization can take place
 327   // if name is NULL no check for class name in .class stream has to be made.
 328   if (name != NULL) {
 329     const int str_len = (int)strlen(name);
 330     if (str_len > Symbol::max_length()) {
 331       // It's impossible to create this class;  the name cannot fit
 332       // into the constant pool.
 333       THROW_MSG_0(vmSymbols::java_lang_NoClassDefFoundError(), name);
 334     }
 335     class_name = SymbolTable::new_symbol(name, CHECK_NULL);
 336   }
 337   ResourceMark rm(THREAD);
 338   ClassFileStream st((u1*) buf, bufLen, NULL);
 339   Handle class_loader (THREAD, JNIHandles::resolve(loaderRef));
 340 
 341   if (UsePerfData && !class_loader.is_null()) {
 342     Handle class_loader1 (THREAD, oopDesc::bs()->write_barrier(class_loader()));
 343     // check whether the current caller thread holds the lock or not.
 344     // If not, increment the corresponding counter
 345     if (ObjectSynchronizer::
 346         query_lock_ownership((JavaThread*)THREAD, class_loader1) !=
 347         ObjectSynchronizer::owner_self) {
 348       ClassLoader::sync_JNIDefineClassLockFreeCounter()->inc();
 349     }
 350   }
 351   Klass* k = SystemDictionary::resolve_from_stream(class_name, class_loader,
 352                                                      Handle(), &st, true,
 353                                                      CHECK_NULL);
 354 
 355   if (TraceClassResolution && k != NULL) {
 356     trace_class_resolution(k);
 357   }
 358 
 359   cls = (jclass)JNIHandles::make_local(
 360     env, k->java_mirror());
 361   return cls;
 362 JNI_END
 363 
 364 
 365 
 366 static bool first_time_FindClass = true;


 562   // super2 is the value computed by the compiler's getSuperClass intrinsic:
 563   debug_only(Klass* super2 = ( k->oop_is_array()
 564                                  ? SystemDictionary::Object_klass()
 565                                  : k->super() ) );
 566   assert(super == super2,
 567          "java_super computation depends on interface, array, other super");
 568   obj = (super == NULL) ? NULL : (jclass) JNIHandles::make_local(super->java_mirror());
 569   return obj;
 570 JNI_END
 571 
 572 JNI_QUICK_ENTRY(jboolean, jni_IsAssignableFrom(JNIEnv *env, jclass sub, jclass super))
 573   JNIWrapper("IsSubclassOf");
 574 
 575   HOTSPOT_JNI_ISASSIGNABLEFROM_ENTRY(env, sub, super);
 576 
 577   oop sub_mirror   = JNIHandles::resolve_non_null(sub);
 578   oop super_mirror = JNIHandles::resolve_non_null(super);
 579   if (java_lang_Class::is_primitive(sub_mirror) ||
 580       java_lang_Class::is_primitive(super_mirror)) {
 581     jboolean ret = (sub_mirror == super_mirror);
 582     if (UseShenandoahGC && ret == JNI_FALSE) {
 583       sub_mirror = oopDesc::bs()->read_barrier(sub_mirror);
 584       super_mirror = oopDesc::bs()->read_barrier(super_mirror);
 585       ret = (sub_mirror == super_mirror);
 586     }
 587     HOTSPOT_JNI_ISASSIGNABLEFROM_RETURN(ret);
 588     return ret;
 589   }
 590   Klass* sub_klass   = java_lang_Class::as_Klass(sub_mirror);
 591   Klass* super_klass = java_lang_Class::as_Klass(super_mirror);
 592   assert(sub_klass != NULL && super_klass != NULL, "invalid arguments to jni_IsAssignableFrom");
 593   jboolean ret = sub_klass->is_subtype_of(super_klass) ?
 594                    JNI_TRUE : JNI_FALSE;
 595 
 596   HOTSPOT_JNI_ISASSIGNABLEFROM_RETURN(ret);
 597   return ret;
 598 JNI_END
 599 
 600 
 601 DT_RETURN_MARK_DECL(Throw, jint
 602                     , HOTSPOT_JNI_THROW_RETURN(_ret_ref));
 603 
 604 JNI_ENTRY(jint, jni_Throw(JNIEnv *env, jthrowable obj))
 605   JNIWrapper("Throw");
 606 


 808 
 809 JNI_QUICK_ENTRY(void, jni_DeleteLocalRef(JNIEnv *env, jobject obj))
 810   JNIWrapper("DeleteLocalRef");
 811 
 812   HOTSPOT_JNI_DELETELOCALREF_ENTRY(env, obj);
 813 
 814   JNIHandles::destroy_local(obj);
 815 
 816   HOTSPOT_JNI_DELETELOCALREF_RETURN();
 817 JNI_END
 818 
 819 JNI_QUICK_ENTRY(jboolean, jni_IsSameObject(JNIEnv *env, jobject r1, jobject r2))
 820   JNIWrapper("IsSameObject");
 821 
 822   HOTSPOT_JNI_ISSAMEOBJECT_ENTRY(env, r1, r2);
 823 
 824   oop a = JNIHandles::resolve(r1);
 825   oop b = JNIHandles::resolve(r2);
 826   jboolean ret = (a == b) ? JNI_TRUE : JNI_FALSE;
 827 
 828   if (UseShenandoahGC && ret == JNI_FALSE) {
 829     a = oopDesc::bs()->read_barrier(a);
 830     b = oopDesc::bs()->read_barrier(b);
 831     ret = (a == b) ? JNI_TRUE : JNI_FALSE;
 832   }
 833   HOTSPOT_JNI_ISSAMEOBJECT_RETURN(ret);
 834   return ret;
 835 JNI_END
 836 
 837 
 838 JNI_ENTRY(jobject, jni_NewLocalRef(JNIEnv *env, jobject ref))
 839   JNIWrapper("NewLocalRef");
 840 
 841   HOTSPOT_JNI_NEWLOCALREF_ENTRY(env, ref);
 842 
 843   jobject ret = JNIHandles::make_local(env, JNIHandles::resolve(ref));
 844 
 845   HOTSPOT_JNI_NEWLOCALREF_RETURN(ret);
 846   return ret;
 847 JNI_END
 848 
 849 JNI_LEAF(jint, jni_EnsureLocalCapacity(JNIEnv *env, jint capacity))
 850   JNIWrapper("EnsureLocalCapacity");
 851 
 852   HOTSPOT_JNI_ENSURELOCALCAPACITY_ENTRY(env, capacity);


2055   return ret;
2056 JNI_END
2057 
2058 
2059 JNI_ENTRY(jobject, jni_GetObjectField(JNIEnv *env, jobject obj, jfieldID fieldID))
2060   JNIWrapper("GetObjectField");
2061   HOTSPOT_JNI_GETOBJECTFIELD_ENTRY(env, obj, (uintptr_t) fieldID);
2062   oop o = JNIHandles::resolve_non_null(obj);
2063   Klass* k = o->klass();
2064   int offset = jfieldIDWorkaround::from_instance_jfieldID(k, fieldID);
2065   // Keep JVMTI addition small and only check enabled flag here.
2066   // jni_GetField_probe() assumes that is okay to create handles.
2067   if (JvmtiExport::should_post_field_access()) {
2068     o = JvmtiExport::jni_GetField_probe(thread, obj, o, k, fieldID, false);
2069   }
2070   jobject ret = JNIHandles::make_local(env, o->obj_field(offset));
2071 #if INCLUDE_ALL_GCS
2072   // If G1 is enabled and we are accessing the value of the referent
2073   // field in a reference object then we need to register a non-null
2074   // referent with the SATB barrier.
2075   if (UseG1GC || UseShenandoahGC) {
2076     bool needs_barrier = false;
2077 
2078     if (ret != NULL &&
2079         offset == java_lang_ref_Reference::referent_offset &&
2080         InstanceKlass::cast(k)->reference_type() != REF_NONE) {
2081       assert(InstanceKlass::cast(k)->is_subclass_of(SystemDictionary::Reference_klass()), "sanity");
2082       needs_barrier = true;
2083     }
2084 
2085     if (needs_barrier) {
2086       oop referent = JNIHandles::resolve(ret);
2087       G1SATBCardTableModRefBS::enqueue(referent);
2088     }
2089   }
2090 #endif // INCLUDE_ALL_GCS
2091 HOTSPOT_JNI_GETOBJECTFIELD_RETURN(ret);
2092   return ret;
2093 JNI_END
2094 
2095 


2708     if (bad_address != NULL) {
2709       os::protect_memory(bad_address, size, os::MEM_PROT_READ,
2710                          /*is_committed*/false);
2711       MemTracker::record_virtual_memory_type((void*)bad_address, mtInternal);
2712     }
2713   }
2714   return bad_address;
2715 }
2716 
2717 
2718 
2719 #define DEFINE_GETSCALARARRAYELEMENTS(ElementTag,ElementType,Result, Tag \
2720                                       , EntryProbe, ReturnProbe) \
2721 \
2722 JNI_QUICK_ENTRY(ElementType*, \
2723           jni_Get##Result##ArrayElements(JNIEnv *env, ElementType##Array array, jboolean *isCopy)) \
2724   JNIWrapper("Get" XSTR(Result) "ArrayElements"); \
2725   EntryProbe; \
2726   /* allocate an chunk of memory in c land */ \
2727   typeArrayOop a = typeArrayOop(JNIHandles::resolve_non_null(array)); \
2728   a = typeArrayOop(oopDesc::bs()->read_barrier(a)); \
2729   ElementType* result; \
2730   int len = a->length(); \
2731   if (len == 0) { \
2732     /* Empty array: legal but useless, can't return NULL. \
2733      * Return a pointer to something useless. \
2734      * Avoid asserts in typeArrayOop. */ \
2735     result = (ElementType*)get_bad_address(); \
2736   } else { \
2737     /* JNI Specification states return NULL on OOM */                    \
2738     result = NEW_C_HEAP_ARRAY_RETURN_NULL(ElementType, len, mtInternal); \
2739     if (result != NULL) {                                                \
2740       /* copy the array to the c chunk */                                \
2741       memcpy(result, a->Tag##_at_addr(0), sizeof(ElementType)*len);      \
2742       if (isCopy) {                                                      \
2743         *isCopy = JNI_TRUE;                                              \
2744       }                                                                  \
2745     }                                                                    \
2746   } \
2747   ReturnProbe; \
2748   return result; \


2767                               , HOTSPOT_JNI_GETLONGARRAYELEMENTS_ENTRY(env, array, (uintptr_t *) isCopy),
2768                               HOTSPOT_JNI_GETLONGARRAYELEMENTS_RETURN(((uintptr_t*)result)))
2769 // Float and double probes don't return value because dtrace doesn't currently support it
2770 DEFINE_GETSCALARARRAYELEMENTS(T_FLOAT,   jfloat,   Float,   float
2771                               , HOTSPOT_JNI_GETFLOATARRAYELEMENTS_ENTRY(env, array, (uintptr_t *) isCopy),
2772                               HOTSPOT_JNI_GETFLOATARRAYELEMENTS_RETURN(result))
2773 DEFINE_GETSCALARARRAYELEMENTS(T_DOUBLE,  jdouble,  Double,  double
2774                               , HOTSPOT_JNI_GETDOUBLEARRAYELEMENTS_ENTRY(env, array, (uintptr_t *) isCopy),
2775                               HOTSPOT_JNI_GETDOUBLEARRAYELEMENTS_RETURN(result))
2776 
2777 
2778 #define DEFINE_RELEASESCALARARRAYELEMENTS(ElementTag,ElementType,Result,Tag \
2779                                           , EntryProbe, ReturnProbe);\
2780 \
2781 JNI_QUICK_ENTRY(void, \
2782           jni_Release##Result##ArrayElements(JNIEnv *env, ElementType##Array array, \
2783                                              ElementType *buf, jint mode)) \
2784   JNIWrapper("Release" XSTR(Result) "ArrayElements"); \
2785   EntryProbe; \
2786   typeArrayOop a = typeArrayOop(JNIHandles::resolve_non_null(array)); \
2787   a = typeArrayOop(oopDesc::bs()->write_barrier(a)); \
2788   int len = a->length(); \
2789   if (len != 0) {   /* Empty array:  nothing to free or copy. */  \
2790     if ((mode == 0) || (mode == JNI_COMMIT)) { \
2791       memcpy(a->Tag##_at_addr(0), buf, sizeof(ElementType)*len); \
2792     } \
2793     if ((mode == 0) || (mode == JNI_ABORT)) { \
2794       FreeHeap(buf); \
2795     } \
2796   } \
2797   ReturnProbe; \
2798 JNI_END
2799 
2800 DEFINE_RELEASESCALARARRAYELEMENTS(T_BOOLEAN, jboolean, Boolean, bool
2801                                   , HOTSPOT_JNI_RELEASEBOOLEANARRAYELEMENTS_ENTRY(env, array, (uintptr_t *) buf, mode),
2802                                   HOTSPOT_JNI_RELEASEBOOLEANARRAYELEMENTS_RETURN())
2803 DEFINE_RELEASESCALARARRAYELEMENTS(T_BYTE,    jbyte,    Byte,    byte
2804                                   , HOTSPOT_JNI_RELEASEBYTEARRAYELEMENTS_ENTRY(env, array, (char *) buf, mode),
2805                                   HOTSPOT_JNI_RELEASEBYTEARRAYELEMENTS_RETURN())
2806 DEFINE_RELEASESCALARARRAYELEMENTS(T_SHORT,   jshort,   Short,   short
2807                                   ,  HOTSPOT_JNI_RELEASESHORTARRAYELEMENTS_ENTRY(env, array, (uint16_t *) buf, mode),


2818 DEFINE_RELEASESCALARARRAYELEMENTS(T_FLOAT,   jfloat,   Float,   float
2819                                   , HOTSPOT_JNI_RELEASEFLOATARRAYELEMENTS_ENTRY(env, array, (float *) buf, mode),
2820                                   HOTSPOT_JNI_RELEASEFLOATARRAYELEMENTS_RETURN())
2821 DEFINE_RELEASESCALARARRAYELEMENTS(T_DOUBLE,  jdouble,  Double,  double
2822                                   , HOTSPOT_JNI_RELEASEDOUBLEARRAYELEMENTS_ENTRY(env, array, (double *) buf, mode),
2823                                   HOTSPOT_JNI_RELEASEDOUBLEARRAYELEMENTS_RETURN())
2824 
2825 
2826 #define DEFINE_GETSCALARARRAYREGION(ElementTag,ElementType,Result, Tag \
2827                                     , EntryProbe, ReturnProbe); \
2828   DT_VOID_RETURN_MARK_DECL(Get##Result##ArrayRegion \
2829                            , ReturnProbe); \
2830 \
2831 JNI_ENTRY(void, \
2832 jni_Get##Result##ArrayRegion(JNIEnv *env, ElementType##Array array, jsize start, \
2833              jsize len, ElementType *buf)) \
2834   JNIWrapper("Get" XSTR(Result) "ArrayRegion"); \
2835   EntryProbe; \
2836   DT_VOID_RETURN_MARK(Get##Result##ArrayRegion); \
2837   typeArrayOop src = typeArrayOop(JNIHandles::resolve_non_null(array)); \
2838   src = typeArrayOop(oopDesc::bs()->read_barrier(src)); \
2839   if (start < 0 || len < 0 || ((unsigned int)start + (unsigned int)len > (unsigned int)src->length())) { \
2840     THROW(vmSymbols::java_lang_ArrayIndexOutOfBoundsException()); \
2841   } else { \
2842     if (len > 0) { \
2843       int sc = TypeArrayKlass::cast(src->klass())->log2_element_size(); \
2844       memcpy((u_char*) buf, \
2845              (u_char*) src->Tag##_at_addr(start), \
2846              len << sc);                          \
2847     } \
2848   } \
2849 JNI_END
2850 
2851 DEFINE_GETSCALARARRAYREGION(T_BOOLEAN, jboolean,Boolean, bool
2852                             , HOTSPOT_JNI_GETBOOLEANARRAYREGION_ENTRY(env, array, start, len, (uintptr_t *) buf),
2853                             HOTSPOT_JNI_GETBOOLEANARRAYREGION_RETURN());
2854 DEFINE_GETSCALARARRAYREGION(T_BYTE,    jbyte,   Byte,    byte
2855                             ,  HOTSPOT_JNI_GETBYTEARRAYREGION_ENTRY(env, array, start, len, (char *) buf),
2856                             HOTSPOT_JNI_GETBYTEARRAYREGION_RETURN());
2857 DEFINE_GETSCALARARRAYREGION(T_SHORT,   jshort,  Short,   short
2858                             , HOTSPOT_JNI_GETSHORTARRAYREGION_ENTRY(env, array, start, len, (uint16_t *) buf),


2869 DEFINE_GETSCALARARRAYREGION(T_FLOAT,   jfloat,  Float,   float
2870                             , HOTSPOT_JNI_GETFLOATARRAYREGION_ENTRY(env, array, start, len, (float *) buf),
2871                             HOTSPOT_JNI_GETFLOATARRAYREGION_RETURN());
2872 DEFINE_GETSCALARARRAYREGION(T_DOUBLE,  jdouble, Double,  double
2873                             , HOTSPOT_JNI_GETDOUBLEARRAYREGION_ENTRY(env, array, start, len, (double *) buf),
2874                             HOTSPOT_JNI_GETDOUBLEARRAYREGION_RETURN());
2875 
2876 
2877 #define DEFINE_SETSCALARARRAYREGION(ElementTag,ElementType,Result, Tag \
2878                                     , EntryProbe, ReturnProbe); \
2879   DT_VOID_RETURN_MARK_DECL(Set##Result##ArrayRegion \
2880                            ,ReturnProbe);           \
2881 \
2882 JNI_ENTRY(void, \
2883 jni_Set##Result##ArrayRegion(JNIEnv *env, ElementType##Array array, jsize start, \
2884              jsize len, const ElementType *buf)) \
2885   JNIWrapper("Set" XSTR(Result) "ArrayRegion"); \
2886   EntryProbe; \
2887   DT_VOID_RETURN_MARK(Set##Result##ArrayRegion); \
2888   typeArrayOop dst = typeArrayOop(JNIHandles::resolve_non_null(array)); \
2889   dst = typeArrayOop(oopDesc::bs()->write_barrier(dst)); \
2890   if (start < 0 || len < 0 || ((unsigned int)start + (unsigned int)len > (unsigned int)dst->length())) { \
2891     THROW(vmSymbols::java_lang_ArrayIndexOutOfBoundsException()); \
2892   } else { \
2893     if (len > 0) { \
2894       int sc = TypeArrayKlass::cast(dst->klass())->log2_element_size(); \
2895       memcpy((u_char*) dst->Tag##_at_addr(start), \
2896              (u_char*) buf, \
2897              len << sc);    \
2898     } \
2899   } \
2900 JNI_END
2901 
2902 DEFINE_SETSCALARARRAYREGION(T_BOOLEAN, jboolean, Boolean, bool
2903                             , HOTSPOT_JNI_SETBOOLEANARRAYREGION_ENTRY(env, array, start, len, (uintptr_t *)buf),
2904                             HOTSPOT_JNI_SETBOOLEANARRAYREGION_RETURN())
2905 DEFINE_SETSCALARARRAYREGION(T_BYTE,    jbyte,    Byte,    byte
2906                             , HOTSPOT_JNI_SETBYTEARRAYREGION_ENTRY(env, array, start, len, (char *) buf),
2907                             HOTSPOT_JNI_SETBYTEARRAYREGION_RETURN())
2908 DEFINE_SETSCALARARRAYREGION(T_SHORT,   jshort,   Short,   short
2909                             , HOTSPOT_JNI_SETSHORTARRAYREGION_ENTRY(env, array, start, len, (uint16_t *) buf),


3068   return 0;
3069 JNI_END
3070 
3071 //
3072 // Monitor functions
3073 //
3074 
3075 DT_RETURN_MARK_DECL(MonitorEnter, jint
3076                     , HOTSPOT_JNI_MONITORENTER_RETURN(_ret_ref));
3077 
3078 JNI_ENTRY(jint, jni_MonitorEnter(JNIEnv *env, jobject jobj))
3079  HOTSPOT_JNI_MONITORENTER_ENTRY(env, jobj);
3080   jint ret = JNI_ERR;
3081   DT_RETURN_MARK(MonitorEnter, jint, (const jint&)ret);
3082 
3083   // If the object is null, we can't do anything with it
3084   if (jobj == NULL) {
3085     THROW_(vmSymbols::java_lang_NullPointerException(), JNI_ERR);
3086   }
3087 
3088   Handle obj(thread, oopDesc::bs()->write_barrier(JNIHandles::resolve_non_null(jobj)));
3089   ObjectSynchronizer::jni_enter(obj, CHECK_(JNI_ERR));
3090   ret = JNI_OK;
3091   return ret;
3092 JNI_END
3093 
3094 DT_RETURN_MARK_DECL(MonitorExit, jint
3095                     , HOTSPOT_JNI_MONITOREXIT_RETURN(_ret_ref));
3096 
3097 JNI_ENTRY(jint, jni_MonitorExit(JNIEnv *env, jobject jobj))
3098  HOTSPOT_JNI_MONITOREXIT_ENTRY(env, jobj);
3099   jint ret = JNI_ERR;
3100   DT_RETURN_MARK(MonitorExit, jint, (const jint&)ret);
3101 
3102   // Don't do anything with a null object
3103   if (jobj == NULL) {
3104     THROW_(vmSymbols::java_lang_NullPointerException(), JNI_ERR);
3105   }
3106 
3107   Handle obj(THREAD, oopDesc::bs()->write_barrier(JNIHandles::resolve_non_null(jobj)));
3108   ObjectSynchronizer::jni_exit(obj(), CHECK_(JNI_ERR));
3109 
3110   ret = JNI_OK;
3111   return ret;
3112 JNI_END
3113 
3114 //
3115 // Extensions
3116 //
3117 
3118 DT_VOID_RETURN_MARK_DECL(GetStringRegion
3119                          , HOTSPOT_JNI_GETSTRINGREGION_RETURN());
3120 
3121 JNI_ENTRY(void, jni_GetStringRegion(JNIEnv *env, jstring string, jsize start, jsize len, jchar *buf))
3122   JNIWrapper("GetStringRegion");
3123  HOTSPOT_JNI_GETSTRINGREGION_ENTRY(env, string, start, len, buf);
3124   DT_VOID_RETURN_MARK(GetStringRegion);
3125   oop s = JNIHandles::resolve_non_null(string);
3126   int s_len = java_lang_String::length(s);
3127   if (start < 0 || len < 0 || start + len > s_len) {


3153       java_lang_String::as_utf8_string(s, start, len, buf, INT_MAX);
3154       // as_utf8_string null-terminates the result string
3155     } else {
3156       // JDK null-terminates the buffer even in len is zero
3157       if (buf != NULL) {
3158         buf[0] = 0;
3159       }
3160     }
3161   }
3162 JNI_END
3163 
3164 
3165 JNI_ENTRY(void*, jni_GetPrimitiveArrayCritical(JNIEnv *env, jarray array, jboolean *isCopy))
3166   JNIWrapper("GetPrimitiveArrayCritical");
3167  HOTSPOT_JNI_GETPRIMITIVEARRAYCRITICAL_ENTRY(env, array, (uintptr_t *) isCopy);
3168   GC_locker::lock_critical(thread);
3169   if (isCopy != NULL) {
3170     *isCopy = JNI_FALSE;
3171   }
3172   oop a = JNIHandles::resolve_non_null(array);
3173   a = oopDesc::bs()->write_barrier(a);
3174   assert(a->is_array(), "just checking");
3175   BasicType type;
3176   if (a->is_objArray()) {
3177     type = T_OBJECT;
3178   } else {
3179     type = TypeArrayKlass::cast(a->klass())->element_type();
3180   }
3181   void* ret = arrayOop(a)->base(type);
3182  HOTSPOT_JNI_GETPRIMITIVEARRAYCRITICAL_RETURN(ret);
3183   return ret;
3184 JNI_END
3185 
3186 
3187 JNI_ENTRY(void, jni_ReleasePrimitiveArrayCritical(JNIEnv *env, jarray array, void *carray, jint mode))
3188   JNIWrapper("ReleasePrimitiveArrayCritical");
3189   HOTSPOT_JNI_RELEASEPRIMITIVEARRAYCRITICAL_ENTRY(env, array, carray, mode);
3190   // The array, carray and mode arguments are ignored
3191   GC_locker::unlock_critical(thread);
3192 HOTSPOT_JNI_RELEASEPRIMITIVEARRAYCRITICAL_RETURN();
3193 JNI_END


< prev index next >