< prev index next >

src/hotspot/share/runtime/reflection.cpp

Print this page




  23  */
  24 
  25 #include "precompiled.hpp"
  26 #include "jvm.h"
  27 #include "classfile/javaClasses.inline.hpp"
  28 #include "classfile/moduleEntry.hpp"
  29 #include "classfile/packageEntry.hpp"
  30 #include "classfile/stringTable.hpp"
  31 #include "classfile/systemDictionary.hpp"
  32 #include "classfile/verifier.hpp"
  33 #include "classfile/vmSymbols.hpp"
  34 #include "interpreter/linkResolver.hpp"
  35 #include "logging/log.hpp"
  36 #include "memory/oopFactory.hpp"
  37 #include "memory/resourceArea.hpp"
  38 #include "memory/universe.hpp"
  39 #include "oops/instanceKlass.hpp"
  40 #include "oops/objArrayKlass.hpp"
  41 #include "oops/objArrayOop.inline.hpp"
  42 #include "oops/oop.inline.hpp"

  43 #include "oops/typeArrayOop.inline.hpp"
  44 #include "prims/jvmtiExport.hpp"
  45 #include "runtime/arguments.hpp"
  46 #include "runtime/fieldDescriptor.inline.hpp"
  47 #include "runtime/handles.inline.hpp"
  48 #include "runtime/javaCalls.hpp"
  49 #include "runtime/reflection.hpp"
  50 #include "runtime/reflectionUtils.hpp"
  51 #include "runtime/signature.hpp"
  52 #include "runtime/thread.inline.hpp"
  53 #include "runtime/vframe.inline.hpp"

  54 
  55 static void trace_class_resolution(const Klass* to_class) {
  56   ResourceMark rm;
  57   int line_number = -1;
  58   const char * source_file = NULL;
  59   Klass* caller = NULL;
  60   JavaThread* jthread = JavaThread::current();
  61   if (jthread->has_last_Java_frame()) {
  62     vframeStream vfst(jthread);
  63     // skip over any frames belonging to java.lang.Class
  64     while (!vfst.at_end() &&
  65            vfst.method()->method_holder()->name() == vmSymbols::java_lang_Class()) {
  66       vfst.next();
  67     }
  68     if (!vfst.at_end()) {
  69       // this frame is a likely suspect
  70       caller = vfst.method()->method_holder();
  71       line_number = vfst.method()->line_number_from_bci(vfst.bci());
  72       Symbol* s = vfst.method()->method_holder()->source_file_name();
  73       if (s != NULL) {


  75       }
  76     }
  77   }
  78   if (caller != NULL) {
  79     const char * from = caller->external_name();
  80     const char * to = to_class->external_name();
  81     // print in a single call to reduce interleaving between threads
  82     if (source_file != NULL) {
  83       log_debug(class, resolve)("%s %s %s:%d (reflection)", from, to, source_file, line_number);
  84     } else {
  85       log_debug(class, resolve)("%s %s (reflection)", from, to);
  86     }
  87   }
  88 }
  89 
  90 
  91 oop Reflection::box(jvalue* value, BasicType type, TRAPS) {
  92   if (type == T_VOID) {
  93     return NULL;
  94   }
  95   if (type == T_OBJECT || type == T_ARRAY) {
  96     // regular objects are not boxed
  97     return (oop) value->l;
  98   }
  99   oop result = java_lang_boxing_object::create(type, value, CHECK_NULL);
 100   if (result == NULL) {
 101     THROW_(vmSymbols::java_lang_IllegalArgumentException(), result);
 102   }
 103   return result;
 104 }
 105 
 106 
 107 BasicType Reflection::unbox_for_primitive(oop box, jvalue* value, TRAPS) {
 108   if (box == NULL) {
 109     THROW_(vmSymbols::java_lang_IllegalArgumentException(), T_ILLEGAL);
 110   }
 111   return java_lang_boxing_object::get_value(box, value);
 112 }
 113 
 114 BasicType Reflection::unbox_for_regular_object(oop box, jvalue* value) {
 115   // Note:  box is really the unboxed oop.  It might even be a Short, etc.!


 325   else {
 326     return Universe::typeArrayKlassObj(type);
 327   }
 328 }
 329 
 330 arrayOop Reflection::reflect_new_array(oop element_mirror, jint length, TRAPS) {
 331   if (element_mirror == NULL) {
 332     THROW_0(vmSymbols::java_lang_NullPointerException());
 333   }
 334   if (length < 0) {
 335     THROW_MSG_0(vmSymbols::java_lang_NegativeArraySizeException(), err_msg("%d", length));
 336   }
 337   if (java_lang_Class::is_primitive(element_mirror)) {
 338     Klass* tak = basic_type_mirror_to_arrayklass(element_mirror, CHECK_NULL);
 339     return TypeArrayKlass::cast(tak)->allocate(length, THREAD);
 340   } else {
 341     Klass* k = java_lang_Class::as_Klass(element_mirror);
 342     if (k->is_array_klass() && ArrayKlass::cast(k)->dimension() >= MAX_DIM) {
 343       THROW_0(vmSymbols::java_lang_IllegalArgumentException());
 344     }
 345     return oopFactory::new_objArray(k, length, THREAD);




 346   }
 347 }
 348 
 349 
 350 arrayOop Reflection::reflect_new_multi_array(oop element_mirror, typeArrayOop dim_array, TRAPS) {
 351   assert(dim_array->is_typeArray(), "just checking");
 352   assert(TypeArrayKlass::cast(dim_array->klass())->element_type() == T_INT, "just checking");
 353 
 354   if (element_mirror == NULL) {
 355     THROW_0(vmSymbols::java_lang_NullPointerException());
 356   }
 357 
 358   int len = dim_array->length();
 359   if (len <= 0 || len > MAX_DIM) {
 360     THROW_0(vmSymbols::java_lang_IllegalArgumentException());
 361   }
 362 
 363   jint dimensions[MAX_DIM];   // C array copy of intArrayOop
 364   for (int i = 0; i < len; i++) {
 365     int d = dim_array->int_at(i);
 366     if (d < 0) {
 367       THROW_MSG_0(vmSymbols::java_lang_NegativeArraySizeException(), err_msg("%d", d));
 368     }
 369     dimensions[i] = d;
 370   }
 371 
 372   Klass* klass;
 373   int dim = len;
 374   if (java_lang_Class::is_primitive(element_mirror)) {
 375     klass = basic_type_mirror_to_arrayklass(element_mirror, CHECK_NULL);
 376   } else {
 377     klass = java_lang_Class::as_Klass(element_mirror);
 378     if (klass->is_array_klass()) {
 379       int k_dim = ArrayKlass::cast(klass)->dimension();
 380       if (k_dim + len > MAX_DIM) {
 381         THROW_0(vmSymbols::java_lang_IllegalArgumentException());
 382       }
 383       dim += k_dim;
 384     }
 385   }
 386   klass = klass->array_klass(dim, CHECK_NULL);

 387   oop obj = ArrayKlass::cast(klass)->multi_allocate(len, dimensions, CHECK_NULL);
 388   assert(obj->is_array(), "just checking");
 389   return arrayOop(obj);
 390 }
 391 
 392 
 393 static bool under_unsafe_anonymous_host(const InstanceKlass* ik, const InstanceKlass* unsafe_anonymous_host) {
 394   DEBUG_ONLY(int inf_loop_check = 1000 * 1000 * 1000);
 395   for (;;) {
 396     const InstanceKlass* hc = ik->unsafe_anonymous_host();
 397     if (hc == NULL)        return false;
 398     if (hc == unsafe_anonymous_host)  return true;
 399     ik = hc;
 400 
 401     // There's no way to make a host class loop short of patching memory.
 402     // Therefore there cannot be a loop here unless there's another bug.
 403     // Still, let's check for it.
 404     assert(--inf_loop_check > 0, "no unsafe_anonymous_host loop");
 405   }
 406 }


 733     if (!inner_is_member && ioff != 0 && ooff == 0 &&
 734         cp->klass_name_at_matches(inner, ioff)) {
 735       Klass* i = cp->klass_at(ioff, CHECK);
 736       if (i == inner) {
 737         return;
 738       }
 739     }
 740   }
 741 
 742   // 'inner' not declared as an inner klass in outer
 743   ResourceMark rm(THREAD);
 744   Exceptions::fthrow(
 745     THREAD_AND_LOCATION,
 746     vmSymbols::java_lang_IncompatibleClassChangeError(),
 747     "%s and %s disagree on InnerClasses attribute",
 748     outer->external_name(),
 749     inner->external_name()
 750   );
 751 }
 752 











 753 // Utility method converting a single SignatureStream element into java.lang.Class instance
 754 static oop get_mirror_from_signature(const methodHandle& method,
 755                                      SignatureStream* ss,
 756                                      TRAPS) {
 757 
 758 
 759   if (T_OBJECT == ss->type() || T_ARRAY == ss->type()) {
 760     Symbol* name = ss->as_symbol();
 761     oop loader = method->method_holder()->class_loader();
 762     oop protection_domain = method->method_holder()->protection_domain();
 763     const Klass* k = SystemDictionary::resolve_or_fail(name,
 764                                                        Handle(THREAD, loader),
 765                                                        Handle(THREAD, protection_domain),
 766                                                        true,
 767                                                        CHECK_NULL);
 768     if (log_is_enabled(Debug, class, resolve)) {
 769       trace_class_resolution(k);
 770     }
 771     return k->java_mirror();
 772   }
 773 
 774   assert(ss->type() != T_VOID || ss->at_return_type(),
 775     "T_VOID should only appear as return type");
 776 
 777   return java_lang_Class::primitive_mirror(ss->type());
 778 }
 779 
 780 static objArrayHandle get_parameter_types(const methodHandle& method,
 781                                           int parameter_count,
 782                                           oop* return_type,
 783                                           TRAPS) {
 784   // Allocate array holding parameter types (java.lang.Class instances)
 785   objArrayOop m = oopFactory::new_objArray(SystemDictionary::Class_klass(), parameter_count, CHECK_(objArrayHandle()));
 786   objArrayHandle mirrors(THREAD, m);
 787   int index = 0;
 788   // Collect parameter types
 789   ResourceMark rm(THREAD);
 790   Symbol*  signature = method->signature();
 791   SignatureStream ss(signature);
 792   while (!ss.at_return_type()) {
 793     oop mirror = get_mirror_from_signature(method, &ss, CHECK_(objArrayHandle()));
 794     mirrors->obj_at_put(index++, mirror);
 795     ss.next();
 796   }
 797   assert(index == parameter_count, "invalid parameter count");
 798   if (return_type != NULL) {
 799     // Collect return type as well
 800     assert(ss.at_return_type(), "return type should be present");
 801     *return_type = get_mirror_from_signature(method, &ss, CHECK_(objArrayHandle()));
 802   }
 803   return mirrors;
 804 }
 805 
 806 static objArrayHandle get_exception_types(const methodHandle& method, TRAPS) {
 807   return method->resolved_checked_exceptions(THREAD);
 808 }
 809 
 810 static Handle new_type(Symbol* signature, Klass* k, TRAPS) {
 811   // Basic types
 812   BasicType type = vmSymbols::signature_type(signature);
 813   if (type != T_OBJECT) {
 814     return Handle(THREAD, Universe::java_mirror(type));
 815   }
 816 
 817   Klass* result =
 818     SystemDictionary::resolve_or_fail(signature,
 819                                       Handle(THREAD, k->class_loader()),
 820                                       Handle(THREAD, k->protection_domain()),
 821                                       true, CHECK_(Handle()));
 822 
 823   if (log_is_enabled(Debug, class, resolve)) {
 824     trace_class_resolution(result);
 825   }
 826 
 827   oop nt = result->java_mirror();
 828   return Handle(THREAD, nt);
 829 }
 830 
 831 
 832 oop Reflection::new_method(const methodHandle& method, bool for_constant_pool_access, TRAPS) {
 833   // Allow sun.reflect.ConstantPool to refer to <clinit> methods as java.lang.reflect.Methods.
 834   assert(!method()->is_initializer() ||
 835          (for_constant_pool_access && method()->is_static()),
 836          "should call new_constructor instead");
 837   InstanceKlass* holder = method->method_holder();
 838   int slot = method->method_idnum();
 839 
 840   Symbol*  signature  = method->signature();
 841   int parameter_count = ArgumentCount(signature).size();
 842   oop return_type_oop = NULL;
 843   objArrayHandle parameter_types = get_parameter_types(method, parameter_count, &return_type_oop, CHECK_NULL);
 844   if (parameter_types.is_null() || return_type_oop == NULL) return NULL;
 845 
 846   Handle return_type(THREAD, return_type_oop);
 847 
 848   objArrayHandle exception_types = get_exception_types(method, CHECK_NULL);
 849 
 850   if (exception_types.is_null()) return NULL;
 851 
 852   Symbol*  method_name = method->name();
 853   oop name_oop = StringTable::intern(method_name, CHECK_NULL);
 854   Handle name = Handle(THREAD, name_oop);
 855   if (name == NULL) return NULL;


 865   java_lang_reflect_Method::set_parameter_types(mh(), parameter_types());
 866   java_lang_reflect_Method::set_exception_types(mh(), exception_types());
 867   java_lang_reflect_Method::set_modifiers(mh(), modifiers);
 868   java_lang_reflect_Method::set_override(mh(), false);
 869   if (method->generic_signature() != NULL) {
 870     Symbol*  gs = method->generic_signature();
 871     Handle sig = java_lang_String::create_from_symbol(gs, CHECK_NULL);
 872     java_lang_reflect_Method::set_signature(mh(), sig());
 873   }
 874   typeArrayOop an_oop = Annotations::make_java_array(method->annotations(), CHECK_NULL);
 875   java_lang_reflect_Method::set_annotations(mh(), an_oop);
 876   an_oop = Annotations::make_java_array(method->parameter_annotations(), CHECK_NULL);
 877   java_lang_reflect_Method::set_parameter_annotations(mh(), an_oop);
 878   an_oop = Annotations::make_java_array(method->annotation_default(), CHECK_NULL);
 879   java_lang_reflect_Method::set_annotation_default(mh(), an_oop);
 880   return mh();
 881 }
 882 
 883 
 884 oop Reflection::new_constructor(const methodHandle& method, TRAPS) {
 885   assert(method()->is_initializer(), "should call new_method instead");


 886 
 887   InstanceKlass* holder = method->method_holder();
 888   int slot = method->method_idnum();
 889 
 890   Symbol*  signature  = method->signature();
 891   int parameter_count = ArgumentCount(signature).size();
 892   objArrayHandle parameter_types = get_parameter_types(method, parameter_count, NULL, CHECK_NULL);
 893   if (parameter_types.is_null()) return NULL;
 894 
 895   objArrayHandle exception_types = get_exception_types(method, CHECK_NULL);
 896   if (exception_types.is_null()) return NULL;
 897 
 898   const int modifiers = method->access_flags().as_int() & JVM_RECOGNIZED_METHOD_MODIFIERS;
 899 
 900   Handle ch = java_lang_reflect_Constructor::create(CHECK_NULL);
 901 
 902   java_lang_reflect_Constructor::set_clazz(ch(), holder->java_mirror());
 903   java_lang_reflect_Constructor::set_slot(ch(), slot);
 904   java_lang_reflect_Constructor::set_parameter_types(ch(), parameter_types());
 905   java_lang_reflect_Constructor::set_exception_types(ch(), exception_types());


 915   an_oop = Annotations::make_java_array(method->parameter_annotations(), CHECK_NULL);
 916   java_lang_reflect_Constructor::set_parameter_annotations(ch(), an_oop);
 917   return ch();
 918 }
 919 
 920 
 921 oop Reflection::new_field(fieldDescriptor* fd, TRAPS) {
 922   Symbol*  field_name = fd->name();
 923   oop name_oop = StringTable::intern(field_name, CHECK_NULL);
 924   Handle name = Handle(THREAD, name_oop);
 925   Symbol*  signature  = fd->signature();
 926   InstanceKlass* holder = fd->field_holder();
 927   Handle type = new_type(signature, holder, CHECK_NULL);
 928   Handle rh  = java_lang_reflect_Field::create(CHECK_NULL);
 929 
 930   java_lang_reflect_Field::set_clazz(rh(), fd->field_holder()->java_mirror());
 931   java_lang_reflect_Field::set_slot(rh(), fd->index());
 932   java_lang_reflect_Field::set_name(rh(), name());
 933   java_lang_reflect_Field::set_type(rh(), type());
 934   // Note the ACC_ANNOTATION bit, which is a per-class access flag, is never set here.
 935   java_lang_reflect_Field::set_modifiers(rh(), fd->access_flags().as_int() & JVM_RECOGNIZED_FIELD_MODIFIERS);









 936   java_lang_reflect_Field::set_override(rh(), false);
 937   if (fd->has_generic_signature()) {
 938     Symbol*  gs = fd->generic_signature();
 939     Handle sig = java_lang_String::create_from_symbol(gs, CHECK_NULL);
 940     java_lang_reflect_Field::set_signature(rh(), sig());
 941   }
 942   typeArrayOop an_oop = Annotations::make_java_array(fd->annotations(), CHECK_NULL);
 943   java_lang_reflect_Field::set_annotations(rh(), an_oop);
 944   return rh();
 945 }
 946 
 947 oop Reflection::new_parameter(Handle method, int index, Symbol* sym,
 948                               int flags, TRAPS) {
 949 
 950   Handle rh = java_lang_reflect_Parameter::create(CHECK_NULL);
 951 
 952   if(NULL != sym) {
 953     Handle name = java_lang_String::create_from_symbol(sym, CHECK_NULL);
 954     java_lang_reflect_Parameter::set_name(rh(), name());
 955   } else {


1190     if (rtype == T_BOOLEAN || rtype == T_BYTE || rtype == T_CHAR || rtype == T_SHORT) {
1191       narrow((jvalue*)result.get_value_addr(), rtype, CHECK_NULL);
1192     }
1193     return Reflection::box((jvalue*)result.get_value_addr(), rtype, THREAD);
1194   }
1195 }
1196 
1197 // This would be nicer if, say, java.lang.reflect.Method was a subclass
1198 // of java.lang.reflect.Constructor
1199 
1200 oop Reflection::invoke_method(oop method_mirror, Handle receiver, objArrayHandle args, TRAPS) {
1201   oop mirror             = java_lang_reflect_Method::clazz(method_mirror);
1202   int slot               = java_lang_reflect_Method::slot(method_mirror);
1203   bool override          = java_lang_reflect_Method::override(method_mirror) != 0;
1204   objArrayHandle ptypes(THREAD, objArrayOop(java_lang_reflect_Method::parameter_types(method_mirror)));
1205 
1206   oop return_type_mirror = java_lang_reflect_Method::return_type(method_mirror);
1207   BasicType rtype;
1208   if (java_lang_Class::is_primitive(return_type_mirror)) {
1209     rtype = basic_type_mirror_to_basic_type(return_type_mirror, CHECK_NULL);


1210   } else {
1211     rtype = T_OBJECT;
1212   }
1213 
1214   InstanceKlass* klass = InstanceKlass::cast(java_lang_Class::as_Klass(mirror));
1215   Method* m = klass->method_with_idnum(slot);
1216   if (m == NULL) {
1217     THROW_MSG_0(vmSymbols::java_lang_InternalError(), "invoke");
1218   }
1219   methodHandle method(THREAD, m);
1220 
1221   return invoke(klass, method, receiver, override, ptypes, rtype, args, true, THREAD);
1222 }
1223 
1224 
1225 oop Reflection::invoke_constructor(oop constructor_mirror, objArrayHandle args, TRAPS) {
1226   oop mirror             = java_lang_reflect_Constructor::clazz(constructor_mirror);
1227   int slot               = java_lang_reflect_Constructor::slot(constructor_mirror);
1228   bool override          = java_lang_reflect_Constructor::override(constructor_mirror) != 0;
1229   objArrayHandle ptypes(THREAD, objArrayOop(java_lang_reflect_Constructor::parameter_types(constructor_mirror)));
1230 
1231   InstanceKlass* klass = InstanceKlass::cast(java_lang_Class::as_Klass(mirror));
1232   Method* m = klass->method_with_idnum(slot);
1233   if (m == NULL) {
1234     THROW_MSG_0(vmSymbols::java_lang_InternalError(), "invoke");
1235   }
1236   methodHandle method(THREAD, m);
1237   assert(method->name() == vmSymbols::object_initializer_name(), "invalid constructor");
1238 
1239   // Make sure klass gets initialize
1240   klass->initialize(CHECK_NULL);
1241 
1242   // Create new instance (the receiver)
1243   klass->check_valid_for_instantiation(false, CHECK_NULL);










1244   Handle receiver = klass->allocate_instance_handle(CHECK_NULL);
1245 
1246   // Ignore result from call and return receiver
1247   invoke(klass, method, receiver, override, ptypes, T_VOID, args, false, CHECK_NULL);
1248   return receiver();
1249 }


  23  */
  24 
  25 #include "precompiled.hpp"
  26 #include "jvm.h"
  27 #include "classfile/javaClasses.inline.hpp"
  28 #include "classfile/moduleEntry.hpp"
  29 #include "classfile/packageEntry.hpp"
  30 #include "classfile/stringTable.hpp"
  31 #include "classfile/systemDictionary.hpp"
  32 #include "classfile/verifier.hpp"
  33 #include "classfile/vmSymbols.hpp"
  34 #include "interpreter/linkResolver.hpp"
  35 #include "logging/log.hpp"
  36 #include "memory/oopFactory.hpp"
  37 #include "memory/resourceArea.hpp"
  38 #include "memory/universe.hpp"
  39 #include "oops/instanceKlass.hpp"
  40 #include "oops/objArrayKlass.hpp"
  41 #include "oops/objArrayOop.inline.hpp"
  42 #include "oops/oop.inline.hpp"
  43 #include "oops/valueKlass.hpp"
  44 #include "oops/typeArrayOop.inline.hpp"
  45 #include "prims/jvmtiExport.hpp"
  46 #include "runtime/arguments.hpp"
  47 #include "runtime/fieldDescriptor.inline.hpp"
  48 #include "runtime/handles.inline.hpp"
  49 #include "runtime/javaCalls.hpp"
  50 #include "runtime/reflection.hpp"
  51 #include "runtime/reflectionUtils.hpp"
  52 #include "runtime/signature.hpp"
  53 #include "runtime/thread.inline.hpp"
  54 #include "runtime/vframe.inline.hpp"
  55 #include "utilities/globalDefinitions.hpp"
  56 
  57 static void trace_class_resolution(const Klass* to_class) {
  58   ResourceMark rm;
  59   int line_number = -1;
  60   const char * source_file = NULL;
  61   Klass* caller = NULL;
  62   JavaThread* jthread = JavaThread::current();
  63   if (jthread->has_last_Java_frame()) {
  64     vframeStream vfst(jthread);
  65     // skip over any frames belonging to java.lang.Class
  66     while (!vfst.at_end() &&
  67            vfst.method()->method_holder()->name() == vmSymbols::java_lang_Class()) {
  68       vfst.next();
  69     }
  70     if (!vfst.at_end()) {
  71       // this frame is a likely suspect
  72       caller = vfst.method()->method_holder();
  73       line_number = vfst.method()->line_number_from_bci(vfst.bci());
  74       Symbol* s = vfst.method()->method_holder()->source_file_name();
  75       if (s != NULL) {


  77       }
  78     }
  79   }
  80   if (caller != NULL) {
  81     const char * from = caller->external_name();
  82     const char * to = to_class->external_name();
  83     // print in a single call to reduce interleaving between threads
  84     if (source_file != NULL) {
  85       log_debug(class, resolve)("%s %s %s:%d (reflection)", from, to, source_file, line_number);
  86     } else {
  87       log_debug(class, resolve)("%s %s (reflection)", from, to);
  88     }
  89   }
  90 }
  91 
  92 
  93 oop Reflection::box(jvalue* value, BasicType type, TRAPS) {
  94   if (type == T_VOID) {
  95     return NULL;
  96   }
  97   if (type == T_OBJECT || type == T_ARRAY || type == T_VALUETYPE) {
  98     // regular objects are not boxed
  99     return (oop) value->l;
 100   }
 101   oop result = java_lang_boxing_object::create(type, value, CHECK_NULL);
 102   if (result == NULL) {
 103     THROW_(vmSymbols::java_lang_IllegalArgumentException(), result);
 104   }
 105   return result;
 106 }
 107 
 108 
 109 BasicType Reflection::unbox_for_primitive(oop box, jvalue* value, TRAPS) {
 110   if (box == NULL) {
 111     THROW_(vmSymbols::java_lang_IllegalArgumentException(), T_ILLEGAL);
 112   }
 113   return java_lang_boxing_object::get_value(box, value);
 114 }
 115 
 116 BasicType Reflection::unbox_for_regular_object(oop box, jvalue* value) {
 117   // Note:  box is really the unboxed oop.  It might even be a Short, etc.!


 327   else {
 328     return Universe::typeArrayKlassObj(type);
 329   }
 330 }
 331 
 332 arrayOop Reflection::reflect_new_array(oop element_mirror, jint length, TRAPS) {
 333   if (element_mirror == NULL) {
 334     THROW_0(vmSymbols::java_lang_NullPointerException());
 335   }
 336   if (length < 0) {
 337     THROW_MSG_0(vmSymbols::java_lang_NegativeArraySizeException(), err_msg("%d", length));
 338   }
 339   if (java_lang_Class::is_primitive(element_mirror)) {
 340     Klass* tak = basic_type_mirror_to_arrayklass(element_mirror, CHECK_NULL);
 341     return TypeArrayKlass::cast(tak)->allocate(length, THREAD);
 342   } else {
 343     Klass* k = java_lang_Class::as_Klass(element_mirror);
 344     if (k->is_array_klass() && ArrayKlass::cast(k)->dimension() >= MAX_DIM) {
 345       THROW_0(vmSymbols::java_lang_IllegalArgumentException());
 346     }
 347     if (java_lang_Class::is_indirect_type(element_mirror)) {
 348       return oopFactory::new_objArray(k, length, THREAD);
 349     } else {
 350       return oopFactory::new_valueArray(k, length, THREAD);
 351     }
 352   }
 353 }
 354 
 355 
 356 arrayOop Reflection::reflect_new_multi_array(oop element_mirror, typeArrayOop dim_array, TRAPS) {
 357   assert(dim_array->is_typeArray(), "just checking");
 358   assert(TypeArrayKlass::cast(dim_array->klass())->element_type() == T_INT, "just checking");
 359 
 360   if (element_mirror == NULL) {
 361     THROW_0(vmSymbols::java_lang_NullPointerException());
 362   }
 363 
 364   int len = dim_array->length();
 365   if (len <= 0 || len > MAX_DIM) {
 366     THROW_0(vmSymbols::java_lang_IllegalArgumentException());
 367   }
 368 
 369   jint dimensions[MAX_DIM];   // C array copy of intArrayOop
 370   for (int i = 0; i < len; i++) {
 371     int d = dim_array->int_at(i);
 372     if (d < 0) {
 373       THROW_MSG_0(vmSymbols::java_lang_NegativeArraySizeException(), err_msg("%d", d));
 374     }
 375     dimensions[i] = d;
 376   }
 377 
 378   Klass* klass;
 379   int dim = len;
 380   if (java_lang_Class::is_primitive(element_mirror)) {
 381     klass = basic_type_mirror_to_arrayklass(element_mirror, CHECK_NULL);
 382   } else {
 383     klass = java_lang_Class::as_Klass(element_mirror);
 384     if (klass->is_array_klass()) {
 385       int k_dim = ArrayKlass::cast(klass)->dimension();
 386       if (k_dim + len > MAX_DIM) {
 387         THROW_0(vmSymbols::java_lang_IllegalArgumentException());
 388       }
 389       dim += k_dim;
 390     }
 391   }
 392   ArrayStorageProperties storage_props = FieldType::get_array_storage_properties(klass->name());
 393   klass = klass->array_klass(storage_props, dim, CHECK_NULL);
 394   oop obj = ArrayKlass::cast(klass)->multi_allocate(len, dimensions, CHECK_NULL);
 395   assert(obj->is_array(), "just checking");
 396   return arrayOop(obj);
 397 }
 398 
 399 
 400 static bool under_unsafe_anonymous_host(const InstanceKlass* ik, const InstanceKlass* unsafe_anonymous_host) {
 401   DEBUG_ONLY(int inf_loop_check = 1000 * 1000 * 1000);
 402   for (;;) {
 403     const InstanceKlass* hc = ik->unsafe_anonymous_host();
 404     if (hc == NULL)        return false;
 405     if (hc == unsafe_anonymous_host)  return true;
 406     ik = hc;
 407 
 408     // There's no way to make a host class loop short of patching memory.
 409     // Therefore there cannot be a loop here unless there's another bug.
 410     // Still, let's check for it.
 411     assert(--inf_loop_check > 0, "no unsafe_anonymous_host loop");
 412   }
 413 }


 740     if (!inner_is_member && ioff != 0 && ooff == 0 &&
 741         cp->klass_name_at_matches(inner, ioff)) {
 742       Klass* i = cp->klass_at(ioff, CHECK);
 743       if (i == inner) {
 744         return;
 745       }
 746     }
 747   }
 748 
 749   // 'inner' not declared as an inner klass in outer
 750   ResourceMark rm(THREAD);
 751   Exceptions::fthrow(
 752     THREAD_AND_LOCATION,
 753     vmSymbols::java_lang_IncompatibleClassChangeError(),
 754     "%s and %s disagree on InnerClasses attribute",
 755     outer->external_name(),
 756     inner->external_name()
 757   );
 758 }
 759 
 760 // Returns Q-mirror if qtype_if_value is true and k is a ValueKlass;
 761 // otherwise returns java_mirror or L-mirror for ValueKlass
 762 static oop java_mirror(Klass* k, jboolean qtype_if_value) {
 763   if (k->is_value()) {
 764     ValueKlass* vk = ValueKlass::cast(InstanceKlass::cast(k));
 765     return qtype_if_value ? vk->value_mirror() : vk->indirect_mirror();
 766   } else {
 767     return k->java_mirror();
 768   }
 769 }
 770 
 771 // Utility method converting a single SignatureStream element into java.lang.Class instance
 772 static oop get_mirror_from_signature(const methodHandle& method,
 773                                      SignatureStream* ss,
 774                                      TRAPS) {
 775 
 776   BasicType bt = ss->type();
 777   if (T_OBJECT == bt || T_ARRAY == bt || T_VALUETYPE == bt) {
 778     Symbol* name = ss->as_symbol();
 779     oop loader = method->method_holder()->class_loader();
 780     oop protection_domain = method->method_holder()->protection_domain();
 781     const Klass* k = SystemDictionary::resolve_or_fail(name,
 782                                                        Handle(THREAD, loader),
 783                                                        Handle(THREAD, protection_domain),
 784                                                        true,
 785                                                        CHECK_NULL);
 786     if (log_is_enabled(Debug, class, resolve)) {
 787       trace_class_resolution(k);
 788     }
 789     return java_mirror((Klass*)k, bt == T_VALUETYPE);
 790   }
 791 
 792   assert(bt != T_VOID || ss->at_return_type(),
 793     "T_VOID should only appear as return type");
 794 
 795   return java_lang_Class::primitive_mirror(bt);
 796 }
 797 
 798 static objArrayHandle get_parameter_types(const methodHandle& method,
 799                                           int parameter_count,
 800                                           oop* return_type,
 801                                           TRAPS) {
 802   // Allocate array holding parameter types (java.lang.Class instances)
 803   objArrayOop m = oopFactory::new_objArray(SystemDictionary::Class_klass(), parameter_count, CHECK_(objArrayHandle()));
 804   objArrayHandle mirrors(THREAD, m);
 805   int index = 0;
 806   // Collect parameter types
 807   ResourceMark rm(THREAD);
 808   Symbol*  signature = method->signature();
 809   SignatureStream ss(signature);
 810   while (!ss.at_return_type()) {
 811     oop mirror = get_mirror_from_signature(method, &ss, CHECK_(objArrayHandle()));
 812     mirrors->obj_at_put(index++, mirror);
 813     ss.next();
 814   }
 815   assert(index == parameter_count, "invalid parameter count");
 816   if (return_type != NULL) {
 817     // Collect return type as well
 818     assert(ss.at_return_type(), "return type should be present");
 819     *return_type = get_mirror_from_signature(method, &ss, CHECK_(objArrayHandle()));
 820   }
 821   return mirrors;
 822 }
 823 
 824 static objArrayHandle get_exception_types(const methodHandle& method, TRAPS) {
 825   return method->resolved_checked_exceptions(THREAD);
 826 }
 827 
 828 static Handle new_type(Symbol* signature, Klass* k, TRAPS) {
 829   // Basic types
 830   BasicType type = vmSymbols::signature_type(signature);
 831   if (type != T_OBJECT && type != T_VALUETYPE) {
 832     return Handle(THREAD, Universe::java_mirror(type));
 833   }
 834 
 835   Klass* result =
 836     SystemDictionary::resolve_or_fail(signature,
 837                                       Handle(THREAD, k->class_loader()),
 838                                       Handle(THREAD, k->protection_domain()),
 839                                       true, CHECK_(Handle()));
 840 
 841   if (log_is_enabled(Debug, class, resolve)) {
 842     trace_class_resolution(result);
 843   }
 844   oop nt = java_mirror(result, type == T_VALUETYPE);

 845   return Handle(THREAD, nt);
 846 }
 847 
 848 
 849 oop Reflection::new_method(const methodHandle& method, bool for_constant_pool_access, TRAPS) {
 850   // Allow sun.reflect.ConstantPool to refer to <clinit> methods as java.lang.reflect.Methods.
 851   assert(!method()->name()->starts_with('<') || for_constant_pool_access,

 852          "should call new_constructor instead");
 853   InstanceKlass* holder = method->method_holder();
 854   int slot = method->method_idnum();
 855 
 856   Symbol*  signature  = method->signature();
 857   int parameter_count = ArgumentCount(signature).size();
 858   oop return_type_oop = NULL;
 859   objArrayHandle parameter_types = get_parameter_types(method, parameter_count, &return_type_oop, CHECK_NULL);
 860   if (parameter_types.is_null() || return_type_oop == NULL) return NULL;
 861 
 862   Handle return_type(THREAD, return_type_oop);
 863 
 864   objArrayHandle exception_types = get_exception_types(method, CHECK_NULL);
 865 
 866   if (exception_types.is_null()) return NULL;
 867 
 868   Symbol*  method_name = method->name();
 869   oop name_oop = StringTable::intern(method_name, CHECK_NULL);
 870   Handle name = Handle(THREAD, name_oop);
 871   if (name == NULL) return NULL;


 881   java_lang_reflect_Method::set_parameter_types(mh(), parameter_types());
 882   java_lang_reflect_Method::set_exception_types(mh(), exception_types());
 883   java_lang_reflect_Method::set_modifiers(mh(), modifiers);
 884   java_lang_reflect_Method::set_override(mh(), false);
 885   if (method->generic_signature() != NULL) {
 886     Symbol*  gs = method->generic_signature();
 887     Handle sig = java_lang_String::create_from_symbol(gs, CHECK_NULL);
 888     java_lang_reflect_Method::set_signature(mh(), sig());
 889   }
 890   typeArrayOop an_oop = Annotations::make_java_array(method->annotations(), CHECK_NULL);
 891   java_lang_reflect_Method::set_annotations(mh(), an_oop);
 892   an_oop = Annotations::make_java_array(method->parameter_annotations(), CHECK_NULL);
 893   java_lang_reflect_Method::set_parameter_annotations(mh(), an_oop);
 894   an_oop = Annotations::make_java_array(method->annotation_default(), CHECK_NULL);
 895   java_lang_reflect_Method::set_annotation_default(mh(), an_oop);
 896   return mh();
 897 }
 898 
 899 
 900 oop Reflection::new_constructor(const methodHandle& method, TRAPS) {
 901   assert(method()->is_object_constructor() ||
 902          method()->is_static_init_factory(),
 903          "should call new_method instead");
 904 
 905   InstanceKlass* holder = method->method_holder();
 906   int slot = method->method_idnum();
 907 
 908   Symbol*  signature  = method->signature();
 909   int parameter_count = ArgumentCount(signature).size();
 910   objArrayHandle parameter_types = get_parameter_types(method, parameter_count, NULL, CHECK_NULL);
 911   if (parameter_types.is_null()) return NULL;
 912 
 913   objArrayHandle exception_types = get_exception_types(method, CHECK_NULL);
 914   if (exception_types.is_null()) return NULL;
 915 
 916   const int modifiers = method->access_flags().as_int() & JVM_RECOGNIZED_METHOD_MODIFIERS;
 917 
 918   Handle ch = java_lang_reflect_Constructor::create(CHECK_NULL);
 919 
 920   java_lang_reflect_Constructor::set_clazz(ch(), holder->java_mirror());
 921   java_lang_reflect_Constructor::set_slot(ch(), slot);
 922   java_lang_reflect_Constructor::set_parameter_types(ch(), parameter_types());
 923   java_lang_reflect_Constructor::set_exception_types(ch(), exception_types());


 933   an_oop = Annotations::make_java_array(method->parameter_annotations(), CHECK_NULL);
 934   java_lang_reflect_Constructor::set_parameter_annotations(ch(), an_oop);
 935   return ch();
 936 }
 937 
 938 
 939 oop Reflection::new_field(fieldDescriptor* fd, TRAPS) {
 940   Symbol*  field_name = fd->name();
 941   oop name_oop = StringTable::intern(field_name, CHECK_NULL);
 942   Handle name = Handle(THREAD, name_oop);
 943   Symbol*  signature  = fd->signature();
 944   InstanceKlass* holder = fd->field_holder();
 945   Handle type = new_type(signature, holder, CHECK_NULL);
 946   Handle rh  = java_lang_reflect_Field::create(CHECK_NULL);
 947 
 948   java_lang_reflect_Field::set_clazz(rh(), fd->field_holder()->java_mirror());
 949   java_lang_reflect_Field::set_slot(rh(), fd->index());
 950   java_lang_reflect_Field::set_name(rh(), name());
 951   java_lang_reflect_Field::set_type(rh(), type());
 952   // Note the ACC_ANNOTATION bit, which is a per-class access flag, is never set here.
 953   int modifiers = fd->access_flags().as_int() & JVM_RECOGNIZED_FIELD_MODIFIERS;
 954   if (fd->is_flattenable()) {
 955     modifiers |= JVM_ACC_FIELD_FLATTENABLE;
 956     // JVM_ACC_FLATTENABLE should not be set in LWorld.  set_is_flattenable should be re-examined.
 957     modifiers &= ~JVM_ACC_FLATTENABLE;
 958   }
 959   if (fd->is_flattened()) {
 960     modifiers |= JVM_ACC_FIELD_FLATTENED;
 961   }
 962   java_lang_reflect_Field::set_modifiers(rh(), modifiers);
 963   java_lang_reflect_Field::set_override(rh(), false);
 964   if (fd->has_generic_signature()) {
 965     Symbol*  gs = fd->generic_signature();
 966     Handle sig = java_lang_String::create_from_symbol(gs, CHECK_NULL);
 967     java_lang_reflect_Field::set_signature(rh(), sig());
 968   }
 969   typeArrayOop an_oop = Annotations::make_java_array(fd->annotations(), CHECK_NULL);
 970   java_lang_reflect_Field::set_annotations(rh(), an_oop);
 971   return rh();
 972 }
 973 
 974 oop Reflection::new_parameter(Handle method, int index, Symbol* sym,
 975                               int flags, TRAPS) {
 976 
 977   Handle rh = java_lang_reflect_Parameter::create(CHECK_NULL);
 978 
 979   if(NULL != sym) {
 980     Handle name = java_lang_String::create_from_symbol(sym, CHECK_NULL);
 981     java_lang_reflect_Parameter::set_name(rh(), name());
 982   } else {


1217     if (rtype == T_BOOLEAN || rtype == T_BYTE || rtype == T_CHAR || rtype == T_SHORT) {
1218       narrow((jvalue*)result.get_value_addr(), rtype, CHECK_NULL);
1219     }
1220     return Reflection::box((jvalue*)result.get_value_addr(), rtype, THREAD);
1221   }
1222 }
1223 
1224 // This would be nicer if, say, java.lang.reflect.Method was a subclass
1225 // of java.lang.reflect.Constructor
1226 
1227 oop Reflection::invoke_method(oop method_mirror, Handle receiver, objArrayHandle args, TRAPS) {
1228   oop mirror             = java_lang_reflect_Method::clazz(method_mirror);
1229   int slot               = java_lang_reflect_Method::slot(method_mirror);
1230   bool override          = java_lang_reflect_Method::override(method_mirror) != 0;
1231   objArrayHandle ptypes(THREAD, objArrayOop(java_lang_reflect_Method::parameter_types(method_mirror)));
1232 
1233   oop return_type_mirror = java_lang_reflect_Method::return_type(method_mirror);
1234   BasicType rtype;
1235   if (java_lang_Class::is_primitive(return_type_mirror)) {
1236     rtype = basic_type_mirror_to_basic_type(return_type_mirror, CHECK_NULL);
1237   } else if (java_lang_Class::inline_type_mirror(return_type_mirror) == return_type_mirror) {
1238     rtype = T_VALUETYPE;
1239   } else {
1240     rtype = T_OBJECT;
1241   }
1242 
1243   InstanceKlass* klass = InstanceKlass::cast(java_lang_Class::as_Klass(mirror));
1244   Method* m = klass->method_with_idnum(slot);
1245   if (m == NULL) {
1246     THROW_MSG_0(vmSymbols::java_lang_InternalError(), "invoke");
1247   }
1248   methodHandle method(THREAD, m);
1249 
1250   return invoke(klass, method, receiver, override, ptypes, rtype, args, true, THREAD);
1251 }
1252 
1253 
1254 oop Reflection::invoke_constructor(oop constructor_mirror, objArrayHandle args, TRAPS) {
1255   oop mirror             = java_lang_reflect_Constructor::clazz(constructor_mirror);
1256   int slot               = java_lang_reflect_Constructor::slot(constructor_mirror);
1257   bool override          = java_lang_reflect_Constructor::override(constructor_mirror) != 0;
1258   objArrayHandle ptypes(THREAD, objArrayOop(java_lang_reflect_Constructor::parameter_types(constructor_mirror)));
1259 
1260   InstanceKlass* klass = InstanceKlass::cast(java_lang_Class::as_Klass(mirror));
1261   Method* m = klass->method_with_idnum(slot);
1262   if (m == NULL) {
1263     THROW_MSG_0(vmSymbols::java_lang_InternalError(), "invoke");
1264   }
1265   methodHandle method(THREAD, m);
1266   assert(method->name() == vmSymbols::object_initializer_name(), "invalid constructor");
1267 
1268   // Make sure klass gets initialize
1269   klass->initialize(CHECK_NULL);
1270 
1271   // Create new instance (the receiver)
1272   klass->check_valid_for_instantiation(false, CHECK_NULL);
1273 
1274   // Special case for factory methods
1275   if (!method->signature()->is_void_method_signature()) {
1276     assert(klass->is_value(), "inline classes must use factory methods");
1277     Handle no_receiver; // null instead of receiver
1278     return invoke(klass, method, no_receiver, override, ptypes, T_VALUETYPE, args, false, CHECK_NULL);
1279   }
1280 
1281   // main branch of code creates a non-inline object:
1282   assert(!klass->is_value(), "classic constructors are only for non-inline classes");
1283   Handle receiver = klass->allocate_instance_handle(CHECK_NULL);
1284 
1285   // Ignore result from call and return receiver
1286   invoke(klass, method, receiver, override, ptypes, T_VOID, args, false, CHECK_NULL);
1287   return receiver();
1288 }
< prev index next >