423 BasicType dest = java_lang_Class::as_BasicType(chain().adapter_arg_oop(), &dest_klass); |
423 BasicType dest = java_lang_Class::as_BasicType(chain().adapter_arg_oop(), &dest_klass); |
424 assert(dest == T_OBJECT, ""); |
424 assert(dest == T_OBJECT, ""); |
425 ArgToken arg = _outgoing.at(arg_slot); |
425 ArgToken arg = _outgoing.at(arg_slot); |
426 assert(dest == arg.basic_type(), ""); |
426 assert(dest == arg.basic_type(), ""); |
427 arg = make_conversion(T_OBJECT, dest_klass, Bytecodes::_checkcast, arg, CHECK_(empty)); |
427 arg = make_conversion(T_OBJECT, dest_klass, Bytecodes::_checkcast, arg, CHECK_(empty)); |
|
428 // replace the object by the result of the cast, to make the compiler happy: |
|
429 change_argument(T_OBJECT, arg_slot, T_OBJECT, arg); |
428 debug_only(dest_klass = (klassOop)badOop); |
430 debug_only(dest_klass = (klassOop)badOop); |
429 break; |
431 break; |
430 } |
432 } |
431 |
433 |
432 case java_lang_invoke_AdapterMethodHandle::OP_PRIM_TO_PRIM: { |
434 case java_lang_invoke_AdapterMethodHandle::OP_PRIM_TO_PRIM: { |
465 lose("no unboxing method", CHECK_(empty)); |
467 lose("no unboxing method", CHECK_(empty)); |
466 } |
468 } |
467 ArgToken arglist[2]; |
469 ArgToken arglist[2]; |
468 arglist[0] = arg; // outgoing 'this' |
470 arglist[0] = arg; // outgoing 'this' |
469 arglist[1] = ArgToken(); // sentinel |
471 arglist[1] = ArgToken(); // sentinel |
470 arg = make_invoke(NULL, unboxer, Bytecodes::_invokevirtual, false, 1, &arglist[0], CHECK_(empty)); |
472 arg = make_invoke(methodHandle(), unboxer, Bytecodes::_invokevirtual, false, 1, &arglist[0], CHECK_(empty)); |
471 change_argument(T_OBJECT, arg_slot, dest, arg); |
473 change_argument(T_OBJECT, arg_slot, dest, arg); |
472 break; |
474 break; |
473 } |
475 } |
474 |
476 |
475 case java_lang_invoke_AdapterMethodHandle::OP_PRIM_TO_REF: { |
477 case java_lang_invoke_AdapterMethodHandle::OP_PRIM_TO_REF: { |
481 } |
483 } |
482 ArgToken arg = _outgoing.at(arg_slot); |
484 ArgToken arg = _outgoing.at(arg_slot); |
483 ArgToken arglist[2]; |
485 ArgToken arglist[2]; |
484 arglist[0] = arg; // outgoing value |
486 arglist[0] = arg; // outgoing value |
485 arglist[1] = ArgToken(); // sentinel |
487 arglist[1] = ArgToken(); // sentinel |
486 arg = make_invoke(NULL, boxer, Bytecodes::_invokestatic, false, 1, &arglist[0], CHECK_(empty)); |
488 arg = make_invoke(methodHandle(), boxer, Bytecodes::_invokestatic, false, 1, &arglist[0], CHECK_(empty)); |
487 change_argument(src, arg_slot, T_OBJECT, arg); |
489 change_argument(src, arg_slot, T_OBJECT, arg); |
488 break; |
490 break; |
489 } |
491 } |
490 |
492 |
491 case java_lang_invoke_AdapterMethodHandle::OP_SWAP_ARGS: { |
493 case java_lang_invoke_AdapterMethodHandle::OP_SWAP_ARGS: { |
597 java_lang_invoke_MethodType::form(recursive_mtype()) ); |
599 java_lang_invoke_MethodType::form(recursive_mtype()) ); |
598 if (invoker == NULL || !invoker->is_method()) { |
600 if (invoker == NULL || !invoker->is_method()) { |
599 lose("bad vmlayout slot", CHECK_(empty)); |
601 lose("bad vmlayout slot", CHECK_(empty)); |
600 } |
602 } |
601 // FIXME: consider inlining the invokee at the bytecode level |
603 // FIXME: consider inlining the invokee at the bytecode level |
602 ArgToken ret = make_invoke(methodOop(invoker), vmIntrinsics::_none, |
604 ArgToken ret = make_invoke(methodHandle(THREAD, methodOop(invoker)), vmIntrinsics::_invokeGeneric, |
603 Bytecodes::_invokevirtual, false, 1+argc, &arglist[0], CHECK_(empty)); |
605 Bytecodes::_invokevirtual, false, 1+argc, &arglist[0], CHECK_(empty)); |
|
606 // The iid = _invokeGeneric really means to adjust reference types as needed. |
604 DEBUG_ONLY(invoker = NULL); |
607 DEBUG_ONLY(invoker = NULL); |
605 if (rtype == T_OBJECT) { |
608 if (rtype == T_OBJECT) { |
606 klassOop rklass = java_lang_Class::as_klassOop( java_lang_invoke_MethodType::rtype(recursive_mtype()) ); |
609 klassOop rklass = java_lang_Class::as_klassOop( java_lang_invoke_MethodType::rtype(recursive_mtype()) ); |
607 if (rklass != SystemDictionary::Object_klass() && |
610 if (rklass != SystemDictionary::Object_klass() && |
608 !Klass::cast(rklass)->is_interface()) { |
611 !Klass::cast(rklass)->is_interface()) { |
655 // Call a built-in method known to the JVM to validate the length. |
658 // Call a built-in method known to the JVM to validate the length. |
656 ArgToken arglist[3]; |
659 ArgToken arglist[3]; |
657 arglist[0] = array_arg; // value to check |
660 arglist[0] = array_arg; // value to check |
658 arglist[1] = length_arg; // length to check |
661 arglist[1] = length_arg; // length to check |
659 arglist[2] = ArgToken(); // sentinel |
662 arglist[2] = ArgToken(); // sentinel |
660 make_invoke(NULL, vmIntrinsics::_checkSpreadArgument, |
663 make_invoke(methodHandle(), vmIntrinsics::_checkSpreadArgument, |
661 Bytecodes::_invokestatic, false, 2, &arglist[0], CHECK_(empty)); |
664 Bytecodes::_invokestatic, false, 2, &arglist[0], CHECK_(empty)); |
662 |
665 |
663 // Spread out the array elements. |
666 // Spread out the array elements. |
664 Bytecodes::Code aload_op = Bytecodes::_nop; |
667 Bytecodes::Code aload_op = Bytecodes::_nop; |
665 switch (element_type) { |
668 switch (element_type) { |
678 for (int i = 0; i < spread_length; i++) { |
681 for (int i = 0; i < spread_length; i++) { |
679 jvalue offset_jvalue; offset_jvalue.i = i; |
682 jvalue offset_jvalue; offset_jvalue.i = i; |
680 ArgToken offset_arg = make_prim_constant(T_INT, &offset_jvalue, CHECK_(empty)); |
683 ArgToken offset_arg = make_prim_constant(T_INT, &offset_jvalue, CHECK_(empty)); |
681 ArgToken element_arg = make_fetch(element_type, element_klass(), aload_op, array_arg, offset_arg, CHECK_(empty)); |
684 ArgToken element_arg = make_fetch(element_type, element_klass(), aload_op, array_arg, offset_arg, CHECK_(empty)); |
682 change_argument(T_VOID, ap, element_type, element_arg); |
685 change_argument(T_VOID, ap, element_type, element_arg); |
683 ap += type2size[element_type]; |
686 //ap += type2size[element_type]; // don't do this; insert next arg to *right* of previous |
684 } |
687 } |
685 break; |
688 break; |
686 } |
689 } |
687 |
690 |
688 default: |
691 default: |
729 if (arg_state.basic_type() == T_VOID) continue; |
732 if (arg_state.basic_type() == T_VOID) continue; |
730 arglist[ap++] = _outgoing.at(i); |
733 arglist[ap++] = _outgoing.at(i); |
731 } |
734 } |
732 assert(ap == _outgoing_argc, ""); |
735 assert(ap == _outgoing_argc, ""); |
733 arglist[ap] = ArgToken(); // add a sentinel, for the sake of asserts |
736 arglist[ap] = ArgToken(); // add a sentinel, for the sake of asserts |
734 return make_invoke(chain().last_method_oop(), |
737 return make_invoke(chain().last_method(), |
735 vmIntrinsics::_none, |
738 vmIntrinsics::_none, |
736 chain().last_invoke_code(), true, |
739 chain().last_invoke_code(), true, |
737 ap, arglist, THREAD); |
740 ap, arglist, THREAD); |
738 } |
741 } |
739 |
742 |
851 // Do the raw retype conversions for OP_RETYPE_RAW. |
854 // Do the raw retype conversions for OP_RETYPE_RAW. |
852 void MethodHandleWalker::retype_raw_conversion(BasicType src, BasicType dst, bool for_return, int slot, TRAPS) { |
855 void MethodHandleWalker::retype_raw_conversion(BasicType src, BasicType dst, bool for_return, int slot, TRAPS) { |
853 if (src != dst) { |
856 if (src != dst) { |
854 if (MethodHandles::same_basic_type_for_returns(src, dst, /*raw*/ true)) { |
857 if (MethodHandles::same_basic_type_for_returns(src, dst, /*raw*/ true)) { |
855 if (MethodHandles::is_float_fixed_reinterpretation_cast(src, dst)) { |
858 if (MethodHandles::is_float_fixed_reinterpretation_cast(src, dst)) { |
856 if (for_return) Untested("MHW return raw conversion"); // still untested |
|
857 vmIntrinsics::ID iid = vmIntrinsics::for_raw_conversion(src, dst); |
859 vmIntrinsics::ID iid = vmIntrinsics::for_raw_conversion(src, dst); |
858 if (iid == vmIntrinsics::_none) { |
860 if (iid == vmIntrinsics::_none) { |
859 lose("no raw conversion method", CHECK); |
861 lose("no raw conversion method", CHECK); |
860 } |
862 } |
861 ArgToken arglist[2]; |
863 ArgToken arglist[2]; |
863 // argument type conversion |
865 // argument type conversion |
864 ArgToken arg = _outgoing.at(slot); |
866 ArgToken arg = _outgoing.at(slot); |
865 assert(arg.token_type() >= tt_symbolic || src == arg.basic_type(), "sanity"); |
867 assert(arg.token_type() >= tt_symbolic || src == arg.basic_type(), "sanity"); |
866 arglist[0] = arg; // outgoing 'this' |
868 arglist[0] = arg; // outgoing 'this' |
867 arglist[1] = ArgToken(); // sentinel |
869 arglist[1] = ArgToken(); // sentinel |
868 arg = make_invoke(NULL, iid, Bytecodes::_invokestatic, false, 1, &arglist[0], CHECK); |
870 arg = make_invoke(methodHandle(), iid, Bytecodes::_invokestatic, false, 1, &arglist[0], CHECK); |
869 change_argument(src, slot, dst, arg); |
871 change_argument(src, slot, dst, arg); |
870 } else { |
872 } else { |
871 // return type conversion |
873 // return type conversion |
872 klassOop arg_klass = NULL; |
874 if (_return_conv == vmIntrinsics::_none) { |
873 arglist[0] = make_parameter(src, arg_klass, -1, CHECK); // return value |
875 _return_conv = iid; |
874 arglist[1] = ArgToken(); // sentinel |
876 } else if (_return_conv == vmIntrinsics::for_raw_conversion(dst, src)) { |
875 (void) make_invoke(NULL, iid, Bytecodes::_invokestatic, false, 1, &arglist[0], CHECK); |
877 _return_conv = vmIntrinsics::_none; |
|
878 } else if (_return_conv != zero_return_conv()) { |
|
879 lose(err_msg("requested raw return conversion not allowed: %s -> %s (before %s)", type2name(src), type2name(dst), vmIntrinsics::name_at(_return_conv)), CHECK); |
|
880 } |
876 } |
881 } |
877 } else { |
882 } else { |
878 // Nothing to do. |
883 // Nothing to do. |
879 } |
884 } |
|
885 } else if (for_return && (!is_subword_type(src) || !is_subword_type(dst))) { |
|
886 // This can occur in exception-throwing MHs, which have a fictitious return value encoded as Void or Empty. |
|
887 _return_conv = zero_return_conv(); |
880 } else if (src == T_OBJECT && is_java_primitive(dst)) { |
888 } else if (src == T_OBJECT && is_java_primitive(dst)) { |
881 // ref-to-prim: discard ref, push zero |
889 // ref-to-prim: discard ref, push zero |
882 lose("requested ref-to-prim conversion not expected", CHECK); |
890 lose("requested ref-to-prim conversion not expected", CHECK); |
883 } else { |
891 } else { |
884 lose(err_msg("requested raw conversion not allowed: %s -> %s", type2name(src), type2name(dst)), CHECK); |
892 lose(err_msg("requested raw conversion not allowed: %s -> %s", type2name(src), type2name(dst)), CHECK); |
905 (void) _constants.append(NULL); |
914 (void) _constants.append(NULL); |
906 |
915 |
907 // Set name and signature index. |
916 // Set name and signature index. |
908 _name_index = cpool_symbol_put(name); |
917 _name_index = cpool_symbol_put(name); |
909 _signature_index = cpool_symbol_put(signature); |
918 _signature_index = cpool_symbol_put(signature); |
|
919 |
|
920 // To make the resulting methods more recognizable by |
|
921 // stack walkers and compiler heuristics, |
|
922 // we put them in holder class MethodHandle. |
|
923 // See klass_is_method_handle_adapter_holder |
|
924 // and methodOopDesc::is_method_handle_adapter. |
|
925 _target_klass = SystemDictionaryHandles::MethodHandle_klass(); |
|
926 |
|
927 check_non_bcp_klasses(java_lang_invoke_MethodHandle::type(root()), CHECK); |
910 |
928 |
911 // Get return type klass. |
929 // Get return type klass. |
912 Handle first_mtype(THREAD, chain().method_type_oop()); |
930 Handle first_mtype(THREAD, chain().method_type_oop()); |
913 // _rklass is NULL for primitives. |
931 // _rklass is NULL for primitives. |
914 _rtype = java_lang_Class::as_BasicType(java_lang_invoke_MethodType::rtype(first_mtype()), &_rklass); |
932 _rtype = java_lang_Class::as_BasicType(java_lang_invoke_MethodType::rtype(first_mtype()), &_rklass); |
1258 } else { |
1285 } else { |
1259 emit_load(srctype, src.index()); |
1286 emit_load(srctype, src.index()); |
1260 index = src.index(); |
1287 index = src.index(); |
1261 } |
1288 } |
1262 emit_bc(op, cpool_klass_put(tk)); |
1289 emit_bc(op, cpool_klass_put(tk)); |
|
1290 check_non_bcp_klass(tk, CHECK_(src)); |
1263 // Allocate a new local for the type so that we don't hide the |
1291 // Allocate a new local for the type so that we don't hide the |
1264 // previous type from the verifier. |
1292 // previous type from the verifier. |
1265 index = new_local_index(type); |
1293 index = new_local_index(type); |
1266 emit_store(srctype, index); |
1294 emit_store(srctype, index); |
1267 break; |
1295 break; |
1290 jvalue MethodHandleCompiler::zero_jvalue = { 0 }; |
1318 jvalue MethodHandleCompiler::zero_jvalue = { 0 }; |
1291 jvalue MethodHandleCompiler::one_jvalue = { 1 }; |
1319 jvalue MethodHandleCompiler::one_jvalue = { 1 }; |
1292 |
1320 |
1293 // Emit bytecodes for the given invoke instruction. |
1321 // Emit bytecodes for the given invoke instruction. |
1294 MethodHandleWalker::ArgToken |
1322 MethodHandleWalker::ArgToken |
1295 MethodHandleCompiler::make_invoke(methodOop m, vmIntrinsics::ID iid, |
1323 MethodHandleCompiler::make_invoke(methodHandle m, vmIntrinsics::ID iid, |
1296 Bytecodes::Code op, bool tailcall, |
1324 Bytecodes::Code op, bool tailcall, |
1297 int argc, MethodHandleWalker::ArgToken* argv, |
1325 int argc, MethodHandleWalker::ArgToken* argv, |
1298 TRAPS) { |
1326 TRAPS) { |
1299 ArgToken zero; |
1327 ArgToken zero; |
1300 if (m == NULL) { |
1328 if (m.is_null()) { |
1301 // Get the intrinsic methodOop. |
1329 // Get the intrinsic methodOop. |
1302 m = vmIntrinsics::method_for(iid); |
1330 m = methodHandle(THREAD, vmIntrinsics::method_for(iid)); |
1303 if (m == NULL) { |
1331 if (m.is_null()) { |
1304 lose(vmIntrinsics::name_at(iid), CHECK_(zero)); |
1332 lose(vmIntrinsics::name_at(iid), CHECK_(zero)); |
1305 } |
1333 } |
1306 } |
1334 } |
1307 |
1335 |
1308 klassOop klass = m->method_holder(); |
1336 klassOop klass = m->method_holder(); |
1309 Symbol* name = m->name(); |
1337 Symbol* name = m->name(); |
1310 Symbol* signature = m->signature(); |
1338 Symbol* signature = m->signature(); |
|
1339 |
|
1340 if (iid == vmIntrinsics::_invokeGeneric && |
|
1341 argc >= 1 && argv[0].token_type() == tt_constant) { |
|
1342 assert(m->intrinsic_id() == vmIntrinsics::_invokeExact, ""); |
|
1343 Handle receiver = argv[0].object(); |
|
1344 Handle rtype(THREAD, java_lang_invoke_MethodHandle::type(receiver())); |
|
1345 Handle mtype(THREAD, m->method_handle_type()); |
|
1346 if (rtype() != mtype()) { |
|
1347 assert(java_lang_invoke_MethodType::form(rtype()) == |
|
1348 java_lang_invoke_MethodType::form(mtype()), |
|
1349 "must be the same shape"); |
|
1350 // customize m to the exact required rtype |
|
1351 bool has_non_bcp_klass = check_non_bcp_klasses(rtype(), CHECK_(zero)); |
|
1352 TempNewSymbol sig2 = java_lang_invoke_MethodType::as_signature(rtype(), true, CHECK_(zero)); |
|
1353 methodHandle m2; |
|
1354 if (!has_non_bcp_klass) { |
|
1355 methodOop m2_oop = SystemDictionary::find_method_handle_invoke(m->name(), sig2, |
|
1356 KlassHandle(), CHECK_(zero)); |
|
1357 m2 = methodHandle(THREAD, m2_oop); |
|
1358 } |
|
1359 if (m2.is_null()) { |
|
1360 // just build it fresh |
|
1361 m2 = methodOopDesc::make_invoke_method(klass, m->name(), sig2, rtype, CHECK_(zero)); |
|
1362 if (m2.is_null()) |
|
1363 lose(err_msg("no customized invoker %s", sig2->as_utf8()), CHECK_(zero)); |
|
1364 } |
|
1365 m = m2; |
|
1366 signature = m->signature(); |
|
1367 } |
|
1368 } |
|
1369 |
|
1370 check_non_bcp_klass(klass, CHECK_(zero)); |
|
1371 if (m->is_method_handle_invoke()) { |
|
1372 check_non_bcp_klasses(m->method_handle_type(), CHECK_(zero)); |
|
1373 } |
1311 |
1374 |
1312 // Count the number of arguments, not the size |
1375 // Count the number of arguments, not the size |
1313 ArgumentCount asc(signature); |
1376 ArgumentCount asc(signature); |
1314 assert(argc == asc.size() + ((op == Bytecodes::_invokestatic || op == Bytecodes::_invokedynamic) ? 0 : 1), |
1377 assert(argc == asc.size() + ((op == Bytecodes::_invokestatic || op == Bytecodes::_invokedynamic) ? 0 : 1), |
1315 "argc mismatch"); |
1378 "argc mismatch"); |
1316 |
|
1317 if (tailcall) { |
|
1318 // Actually, in order to make these methods more recognizable, |
|
1319 // let's put them in holder class MethodHandle. That way stack |
|
1320 // walkers and compiler heuristics can recognize them. |
|
1321 _target_klass = SystemDictionary::MethodHandle_klass(); |
|
1322 } |
|
1323 |
1379 |
1324 // Inline the method. |
1380 // Inline the method. |
1325 InvocationCounter* ic = m->invocation_counter(); |
1381 InvocationCounter* ic = m->invocation_counter(); |
1326 ic->set_carry_flag(); |
1382 ic->set_carry_flag(); |
1327 |
1383 |
1351 // Populate constant pool. |
1407 // Populate constant pool. |
1352 int name_index = cpool_symbol_put(name); |
1408 int name_index = cpool_symbol_put(name); |
1353 int signature_index = cpool_symbol_put(signature); |
1409 int signature_index = cpool_symbol_put(signature); |
1354 int name_and_type_index = cpool_name_and_type_put(name_index, signature_index); |
1410 int name_and_type_index = cpool_name_and_type_put(name_index, signature_index); |
1355 int klass_index = cpool_klass_put(klass); |
1411 int klass_index = cpool_klass_put(klass); |
1356 int methodref_index = cpool_methodref_put(klass_index, name_and_type_index); |
1412 int methodref_index = cpool_methodref_put(op, klass_index, name_and_type_index, m); |
1357 |
1413 |
1358 // Generate invoke. |
1414 // Generate invoke. |
1359 switch (op) { |
1415 switch (op) { |
1360 case Bytecodes::_invokestatic: |
1416 case Bytecodes::_invokestatic: |
1361 case Bytecodes::_invokespecial: |
1417 case Bytecodes::_invokespecial: |
1378 BasicType rbt = m->result_type(); |
1434 BasicType rbt = m->result_type(); |
1379 if (rbt == T_ARRAY) rbt = T_OBJECT; |
1435 if (rbt == T_ARRAY) rbt = T_OBJECT; |
1380 stack_push(rbt); // The return value is already pushed onto the stack. |
1436 stack_push(rbt); // The return value is already pushed onto the stack. |
1381 ArgToken ret; |
1437 ArgToken ret; |
1382 if (tailcall) { |
1438 if (tailcall) { |
|
1439 if (return_conv() == zero_return_conv()) { |
|
1440 rbt = T_VOID; // discard value |
|
1441 } else if (return_conv() != vmIntrinsics::_none) { |
|
1442 // return value conversion |
|
1443 int index = new_local_index(rbt); |
|
1444 emit_store(rbt, index); |
|
1445 ArgToken arglist[2]; |
|
1446 arglist[0] = ArgToken(tt_temporary, rbt, index); |
|
1447 arglist[1] = ArgToken(); // sentinel |
|
1448 ret = make_invoke(methodHandle(), return_conv(), Bytecodes::_invokestatic, false, 1, &arglist[0], CHECK_(zero)); |
|
1449 set_return_conv(vmIntrinsics::_none); |
|
1450 rbt = ret.basic_type(); |
|
1451 emit_load(rbt, ret.index()); |
|
1452 } |
1383 if (rbt != _rtype) { |
1453 if (rbt != _rtype) { |
1384 if (rbt == T_VOID) { |
1454 if (rbt == T_VOID) { |
1385 // push a zero of the right sort |
1455 // push a zero of the right sort |
1386 if (_rtype == T_OBJECT) { |
1456 if (_rtype == T_OBJECT) { |
1387 zero = make_oop_constant(NULL, CHECK_(zero)); |
1457 zero = make_oop_constant(NULL, CHECK_(zero)); |
1523 (void) _constants.append(NULL); |
1594 (void) _constants.append(NULL); |
1524 |
1595 |
1525 return index; |
1596 return index; |
1526 } |
1597 } |
1527 |
1598 |
|
1599 bool MethodHandleCompiler::check_non_bcp_klasses(Handle method_type, TRAPS) { |
|
1600 bool res = false; |
|
1601 for (int i = -1, len = java_lang_invoke_MethodType::ptype_count(method_type()); i < len; i++) { |
|
1602 oop ptype = (i == -1 |
|
1603 ? java_lang_invoke_MethodType::rtype(method_type()) |
|
1604 : java_lang_invoke_MethodType::ptype(method_type(), i)); |
|
1605 res |= check_non_bcp_klass(java_lang_Class::as_klassOop(ptype), CHECK_(false)); |
|
1606 } |
|
1607 return res; |
|
1608 } |
|
1609 |
|
1610 bool MethodHandleCompiler::check_non_bcp_klass(klassOop klass, TRAPS) { |
|
1611 klass = methodOopDesc::check_non_bcp_klass(klass); |
|
1612 if (klass != NULL) { |
|
1613 Symbol* name = Klass::cast(klass)->name(); |
|
1614 for (int i = _non_bcp_klasses.length() - 1; i >= 0; i--) { |
|
1615 klassOop k2 = _non_bcp_klasses.at(i)(); |
|
1616 if (Klass::cast(k2)->name() == name) { |
|
1617 if (k2 != klass) { |
|
1618 lose(err_msg("unsupported klass name alias %s", name->as_utf8()), THREAD); |
|
1619 } |
|
1620 return true; |
|
1621 } |
|
1622 } |
|
1623 _non_bcp_klasses.append(KlassHandle(THREAD, klass)); |
|
1624 return true; |
|
1625 } |
|
1626 return false; |
|
1627 } |
|
1628 |
|
1629 void MethodHandleCompiler::record_non_bcp_klasses() { |
|
1630 // Append extra klasses to constant pool, to guide klass lookup. |
|
1631 for (int k = 0; k < _non_bcp_klasses.length(); k++) { |
|
1632 klassOop non_bcp_klass = _non_bcp_klasses.at(k)(); |
|
1633 bool add_to_cp = true; |
|
1634 for (int j = 1; j < _constants.length(); j++) { |
|
1635 ConstantValue* cv = _constants.at(j); |
|
1636 if (cv != NULL && cv->tag() == JVM_CONSTANT_Class |
|
1637 && cv->klass_oop() == non_bcp_klass) { |
|
1638 add_to_cp = false; |
|
1639 break; |
|
1640 } |
|
1641 } |
|
1642 if (add_to_cp) cpool_klass_put(non_bcp_klass); |
|
1643 } |
|
1644 } |
1528 |
1645 |
1529 constantPoolHandle MethodHandleCompiler::get_constant_pool(TRAPS) const { |
1646 constantPoolHandle MethodHandleCompiler::get_constant_pool(TRAPS) const { |
1530 constantPoolHandle nullHandle; |
1647 constantPoolHandle nullHandle; |
1531 constantPoolOop cpool_oop = oopFactory::new_constantPool(_constants.length(), |
1648 constantPoolOop cpool_oop = oopFactory::new_constantPool(_constants.length(), |
1532 oopDesc::IsSafeConc, |
1649 oopDesc::IsSafeConc, |
1542 case JVM_CONSTANT_Float: cpool->float_at_put( i, cv->get_jfloat() ); break; |
1659 case JVM_CONSTANT_Float: cpool->float_at_put( i, cv->get_jfloat() ); break; |
1543 case JVM_CONSTANT_Long: cpool->long_at_put( i, cv->get_jlong() ); break; |
1660 case JVM_CONSTANT_Long: cpool->long_at_put( i, cv->get_jlong() ); break; |
1544 case JVM_CONSTANT_Double: cpool->double_at_put( i, cv->get_jdouble() ); break; |
1661 case JVM_CONSTANT_Double: cpool->double_at_put( i, cv->get_jdouble() ); break; |
1545 case JVM_CONSTANT_Class: cpool->klass_at_put( i, cv->klass_oop() ); break; |
1662 case JVM_CONSTANT_Class: cpool->klass_at_put( i, cv->klass_oop() ); break; |
1546 case JVM_CONSTANT_Methodref: cpool->method_at_put( i, cv->first_index(), cv->second_index()); break; |
1663 case JVM_CONSTANT_Methodref: cpool->method_at_put( i, cv->first_index(), cv->second_index()); break; |
|
1664 case JVM_CONSTANT_InterfaceMethodref: |
|
1665 cpool->interface_method_at_put(i, cv->first_index(), cv->second_index()); break; |
1547 case JVM_CONSTANT_NameAndType: cpool->name_and_type_at_put(i, cv->first_index(), cv->second_index()); break; |
1666 case JVM_CONSTANT_NameAndType: cpool->name_and_type_at_put(i, cv->first_index(), cv->second_index()); break; |
1548 case JVM_CONSTANT_Object: cpool->object_at_put( i, cv->object_oop() ); break; |
1667 case JVM_CONSTANT_Object: cpool->object_at_put( i, cv->object_oop() ); break; |
1549 default: ShouldNotReachHere(); |
1668 default: ShouldNotReachHere(); |
1550 } |
1669 } |
1551 |
1670 |
1603 objArrayOop m_array = oopFactory::new_system_objArray(1, CHECK_(empty)); |
1724 objArrayOop m_array = oopFactory::new_system_objArray(1, CHECK_(empty)); |
1604 objArrayHandle methods(THREAD, m_array); |
1725 objArrayHandle methods(THREAD, m_array); |
1605 methods->obj_at_put(0, m()); |
1726 methods->obj_at_put(0, m()); |
1606 Rewriter::rewrite(_target_klass(), cpool, methods, CHECK_(empty)); // Use fake class. |
1727 Rewriter::rewrite(_target_klass(), cpool, methods, CHECK_(empty)); // Use fake class. |
1607 Rewriter::relocate_and_link(_target_klass(), methods, CHECK_(empty)); // Use fake class. |
1728 Rewriter::relocate_and_link(_target_klass(), methods, CHECK_(empty)); // Use fake class. |
|
1729 |
|
1730 // Pre-resolve selected CP cache entries, to avoid problems with class loader scoping. |
|
1731 constantPoolCacheHandle cpc(THREAD, cpool->cache()); |
|
1732 for (int i = 0; i < cpc->length(); i++) { |
|
1733 ConstantPoolCacheEntry* e = cpc->entry_at(i); |
|
1734 assert(!e->is_secondary_entry(), "no indy instructions in here, yet"); |
|
1735 int constant_pool_index = e->constant_pool_index(); |
|
1736 ConstantValue* cv = _constants.at(constant_pool_index); |
|
1737 if (!cv->has_linkage()) continue; |
|
1738 methodHandle m = cv->linkage(); |
|
1739 int index; |
|
1740 switch (cv->tag()) { |
|
1741 case JVM_CONSTANT_Methodref: |
|
1742 index = m->vtable_index(); |
|
1743 if (m->is_static()) { |
|
1744 e->set_method(Bytecodes::_invokestatic, m, index); |
|
1745 } else { |
|
1746 e->set_method(Bytecodes::_invokespecial, m, index); |
|
1747 e->set_method(Bytecodes::_invokevirtual, m, index); |
|
1748 } |
|
1749 break; |
|
1750 case JVM_CONSTANT_InterfaceMethodref: |
|
1751 index = klassItable::compute_itable_index(m()); |
|
1752 e->set_interface_call(m, index); |
|
1753 break; |
|
1754 } |
|
1755 } |
1608 |
1756 |
1609 // Set the invocation counter's count to the invoke count of the |
1757 // Set the invocation counter's count to the invoke count of the |
1610 // original call site. |
1758 // original call site. |
1611 InvocationCounter* ic = m->invocation_counter(); |
1759 InvocationCounter* ic = m->invocation_counter(); |
1612 ic->set(InvocationCounter::wait_for_compile, _invoke_count); |
1760 ic->set(InvocationCounter::wait_for_compile, _invoke_count); |
1757 put_type_name(type, tk, &_strbuf); |
1908 put_type_name(type, tk, &_strbuf); |
1758 } |
1909 } |
1759 _strbuf.print(")"); |
1910 _strbuf.print(")"); |
1760 return maybe_make_temp("fetch", type, "x"); |
1911 return maybe_make_temp("fetch", type, "x"); |
1761 } |
1912 } |
1762 virtual ArgToken make_invoke(methodOop m, vmIntrinsics::ID iid, |
1913 virtual ArgToken make_invoke(methodHandle m, vmIntrinsics::ID iid, |
1763 Bytecodes::Code op, bool tailcall, |
1914 Bytecodes::Code op, bool tailcall, |
1764 int argc, ArgToken* argv, TRAPS) { |
1915 int argc, ArgToken* argv, TRAPS) { |
1765 Symbol* name; |
1916 Symbol* name; |
1766 Symbol* sig; |
1917 Symbol* sig; |
1767 if (m != NULL) { |
1918 if (m.not_null()) { |
1768 name = m->name(); |
1919 name = m->name(); |
1769 sig = m->signature(); |
1920 sig = m->signature(); |
1770 } else { |
1921 } else { |
1771 name = vmSymbols::symbol_at(vmIntrinsics::name_for(iid)); |
1922 name = vmSymbols::symbol_at(vmIntrinsics::name_for(iid)); |
1772 sig = vmSymbols::symbol_at(vmIntrinsics::signature_for(iid)); |
1923 sig = vmSymbols::symbol_at(vmIntrinsics::signature_for(iid)); |