comparison jvmci/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/HotSpotConstantPool.java @ 23741:6542cd8da2da

include VarHandle in signature polymorphic method test (JDK-8164214)
author Doug Simon <doug.simon@oracle.com>
date Tue, 23 Aug 2016 22:58:50 +0200
parents 9e1235406b59
children f0bfcd6688ce
comparison
equal deleted inserted replaced
23740:724fbad94ee3 23741:6542cd8da2da
280 * 280 *
281 * @param index constant pool index 281 * @param index constant pool index
282 * @return constant pool tag 282 * @return constant pool tag
283 */ 283 */
284 private JVM_CONSTANT getTagAt(int index) { 284 private JVM_CONSTANT getTagAt(int index) {
285 assertBounds(index); 285 assert checkBounds(index);
286 HotSpotVMConfig config = config(); 286 HotSpotVMConfig config = config();
287 final long metaspaceConstantPoolTags = UNSAFE.getAddress(getMetaspaceConstantPool() + config.constantPoolTagsOffset); 287 final long metaspaceConstantPoolTags = UNSAFE.getAddress(getMetaspaceConstantPool() + config.constantPoolTagsOffset);
288 final int tag = UNSAFE.getByteVolatile(null, metaspaceConstantPoolTags + config.arrayU1DataOffset + index); 288 final int tag = UNSAFE.getByteVolatile(null, metaspaceConstantPoolTags + config.arrayU1DataOffset + index);
289 if (tag == 0) { 289 if (tag == 0) {
290 return null; 290 return null;
297 * 297 *
298 * @param index constant pool index 298 * @param index constant pool index
299 * @return constant pool entry 299 * @return constant pool entry
300 */ 300 */
301 private long getEntryAt(int index) { 301 private long getEntryAt(int index) {
302 assertBounds(index); 302 assert checkBounds(index);
303 int offset = index * runtime().getHostJVMCIBackend().getTarget().wordSize; 303 int offset = index * runtime().getHostJVMCIBackend().getTarget().wordSize;
304 return UNSAFE.getAddress(getMetaspaceConstantPool() + config().constantPoolSize + offset); 304 return UNSAFE.getAddress(getMetaspaceConstantPool() + config().constantPoolSize + offset);
305 } 305 }
306 306
307 /** 307 /**
309 * 309 *
310 * @param index constant pool index 310 * @param index constant pool index
311 * @return integer constant pool entry at index 311 * @return integer constant pool entry at index
312 */ 312 */
313 private int getIntAt(int index) { 313 private int getIntAt(int index) {
314 assertTag(index, JVM_CONSTANT.Integer); 314 assert checkTag(index, JVM_CONSTANT.Integer);
315 int offset = index * runtime().getHostJVMCIBackend().getTarget().wordSize; 315 int offset = index * runtime().getHostJVMCIBackend().getTarget().wordSize;
316 return UNSAFE.getInt(getMetaspaceConstantPool() + config().constantPoolSize + offset); 316 return UNSAFE.getInt(getMetaspaceConstantPool() + config().constantPoolSize + offset);
317 } 317 }
318 318
319 /** 319 /**
321 * 321 *
322 * @param index constant pool index 322 * @param index constant pool index
323 * @return long constant pool entry 323 * @return long constant pool entry
324 */ 324 */
325 private long getLongAt(int index) { 325 private long getLongAt(int index) {
326 assertTag(index, JVM_CONSTANT.Long); 326 assert checkTag(index, JVM_CONSTANT.Long);
327 int offset = index * runtime().getHostJVMCIBackend().getTarget().wordSize; 327 int offset = index * runtime().getHostJVMCIBackend().getTarget().wordSize;
328 return UNSAFE.getLong(getMetaspaceConstantPool() + config().constantPoolSize + offset); 328 return UNSAFE.getLong(getMetaspaceConstantPool() + config().constantPoolSize + offset);
329 } 329 }
330 330
331 /** 331 /**
333 * 333 *
334 * @param index constant pool index 334 * @param index constant pool index
335 * @return float constant pool entry 335 * @return float constant pool entry
336 */ 336 */
337 private float getFloatAt(int index) { 337 private float getFloatAt(int index) {
338 assertTag(index, JVM_CONSTANT.Float); 338 assert checkTag(index, JVM_CONSTANT.Float);
339 int offset = index * runtime().getHostJVMCIBackend().getTarget().wordSize; 339 int offset = index * runtime().getHostJVMCIBackend().getTarget().wordSize;
340 return UNSAFE.getFloat(getMetaspaceConstantPool() + config().constantPoolSize + offset); 340 return UNSAFE.getFloat(getMetaspaceConstantPool() + config().constantPoolSize + offset);
341 } 341 }
342 342
343 /** 343 /**
345 * 345 *
346 * @param index constant pool index 346 * @param index constant pool index
347 * @return float constant pool entry 347 * @return float constant pool entry
348 */ 348 */
349 private double getDoubleAt(int index) { 349 private double getDoubleAt(int index) {
350 assertTag(index, JVM_CONSTANT.Double); 350 assert checkTag(index, JVM_CONSTANT.Double);
351 int offset = index * runtime().getHostJVMCIBackend().getTarget().wordSize; 351 int offset = index * runtime().getHostJVMCIBackend().getTarget().wordSize;
352 return UNSAFE.getDouble(getMetaspaceConstantPool() + config().constantPoolSize + offset); 352 return UNSAFE.getDouble(getMetaspaceConstantPool() + config().constantPoolSize + offset);
353 } 353 }
354 354
355 /** 355 /**
357 * 357 *
358 * @param index constant pool index 358 * @param index constant pool index
359 * @return {@code JVM_CONSTANT_NameAndType} constant pool entry 359 * @return {@code JVM_CONSTANT_NameAndType} constant pool entry
360 */ 360 */
361 private int getNameAndTypeAt(int index) { 361 private int getNameAndTypeAt(int index) {
362 assertTag(index, JVM_CONSTANT.NameAndType); 362 assert checkTag(index, JVM_CONSTANT.NameAndType);
363 int offset = index * runtime().getHostJVMCIBackend().getTarget().wordSize; 363 int offset = index * runtime().getHostJVMCIBackend().getTarget().wordSize;
364 return UNSAFE.getInt(getMetaspaceConstantPool() + config().constantPoolSize + offset); 364 return UNSAFE.getInt(getMetaspaceConstantPool() + config().constantPoolSize + offset);
365 } 365 }
366 366
367 /** 367 /**
439 * 439 *
440 * @param index constant pool index 440 * @param index constant pool index
441 * @return klass reference index 441 * @return klass reference index
442 */ 442 */
443 private int getUncachedKlassRefIndexAt(int index) { 443 private int getUncachedKlassRefIndexAt(int index) {
444 assertTagIsFieldOrMethod(index); 444 assert checkTagIsFieldOrMethod(index);
445 int offset = index * runtime().getHostJVMCIBackend().getTarget().wordSize; 445 int offset = index * runtime().getHostJVMCIBackend().getTarget().wordSize;
446 final int refIndex = UNSAFE.getInt(getMetaspaceConstantPool() + config().constantPoolSize + offset); 446 final int refIndex = UNSAFE.getInt(getMetaspaceConstantPool() + config().constantPoolSize + offset);
447 // klass ref index is in the low 16-bits. 447 // klass ref index is in the low 16-bits.
448 return refIndex & 0xFFFF; 448 return refIndex & 0xFFFF;
449 } 449 }
450 450
451 /** 451 /**
452 * Asserts that the constant pool index {@code index} is in the bounds of the constant pool. 452 * Checks that the constant pool index {@code index} is in the bounds of the constant pool.
453 * 453 *
454 * @param index constant pool index 454 * @param index constant pool index
455 */ 455 * @throws AssertionError if the check fails
456 private void assertBounds(int index) { 456 */
457 private boolean checkBounds(int index) {
457 assert 0 <= index && index < length() : "index " + index + " not between 0 and " + length(); 458 assert 0 <= index && index < length() : "index " + index + " not between 0 and " + length();
458 } 459 return true;
459 460 }
460 /** 461
461 * Asserts that the constant pool tag at index {@code index} is equal to {@code tag}. 462 /**
463 * Checks that the constant pool tag at index {@code index} is equal to {@code tag}.
462 * 464 *
463 * @param index constant pool index 465 * @param index constant pool index
464 * @param tag expected tag 466 * @param tag expected tag
465 */ 467 * @throws AssertionError if the check fails
466 private void assertTag(int index, JVM_CONSTANT tag) { 468 */
469 private boolean checkTag(int index, JVM_CONSTANT tag) {
467 final JVM_CONSTANT tagAt = getTagAt(index); 470 final JVM_CONSTANT tagAt = getTagAt(index);
468 assert tagAt == tag : "constant pool tag at index " + index + " is " + tagAt + " but expected " + tag; 471 assert tagAt == tag : "constant pool tag at index " + index + " is " + tagAt + " but expected " + tag;
472 return true;
469 } 473 }
470 474
471 /** 475 /**
472 * Asserts that the constant pool tag at index {@code index} is a {@link JVM_CONSTANT#Fieldref}, 476 * Asserts that the constant pool tag at index {@code index} is a {@link JVM_CONSTANT#Fieldref},
473 * or a {@link JVM_CONSTANT#MethodRef}, or a {@link JVM_CONSTANT#InterfaceMethodref}. 477 * or a {@link JVM_CONSTANT#MethodRef}, or a {@link JVM_CONSTANT#InterfaceMethodref}.
474 * 478 *
475 * @param index constant pool index 479 * @param index constant pool index
476 */ 480 * @throws AssertionError if the check fails
477 private void assertTagIsFieldOrMethod(int index) { 481 */
482 private boolean checkTagIsFieldOrMethod(int index) {
478 final JVM_CONSTANT tagAt = getTagAt(index); 483 final JVM_CONSTANT tagAt = getTagAt(index);
479 assert tagAt == JVM_CONSTANT.Fieldref || tagAt == JVM_CONSTANT.MethodRef || tagAt == JVM_CONSTANT.InterfaceMethodref : tagAt; 484 assert tagAt == JVM_CONSTANT.Fieldref || tagAt == JVM_CONSTANT.MethodRef || tagAt == JVM_CONSTANT.InterfaceMethodref : tagAt;
485 return true;
480 } 486 }
481 487
482 @Override 488 @Override
483 public int length() { 489 public int length() {
484 return UNSAFE.getInt(getMetaspaceConstantPool() + config().constantPoolLengthOffset); 490 return UNSAFE.getInt(getMetaspaceConstantPool() + config().constantPoolLengthOffset);
521 } 527 }
522 } 528 }
523 529
524 @Override 530 @Override
525 public String lookupUtf8(int cpi) { 531 public String lookupUtf8(int cpi) {
526 assertTag(cpi, JVM_CONSTANT.Utf8); 532 assert checkTag(cpi, JVM_CONSTANT.Utf8);
527 return compilerToVM().getSymbol(getEntryAt(cpi)); 533 return compilerToVM().getSymbol(getEntryAt(cpi));
528 } 534 }
529 535
530 @Override 536 @Override
531 public Signature lookupSignature(int cpi) { 537 public Signature lookupSignature(int cpi) {
688 Class<?> klass = type.mirror(); 694 Class<?> klass = type.mirror();
689 if (!klass.isPrimitive() && !klass.isArray()) { 695 if (!klass.isPrimitive() && !klass.isArray()) {
690 UNSAFE.ensureClassInitialized(klass); 696 UNSAFE.ensureClassInitialized(klass);
691 } 697 }
692 if (tag == JVM_CONSTANT.MethodRef) { 698 if (tag == JVM_CONSTANT.MethodRef) {
693 if (Bytecodes.isInvokeHandleAlias(opcode)) { 699 if (Bytecodes.isInvokeHandleAlias(opcode) && isSignaturePolymorphicHolder(type)) {
694 final int methodRefCacheIndex = rawIndexToConstantPoolIndex(cpi, opcode); 700 final int methodRefCacheIndex = rawIndexToConstantPoolIndex(cpi, opcode);
695 if (isInvokeHandle(methodRefCacheIndex, type)) { 701 assert checkTag(compilerToVM().constantPoolRemapInstructionOperandFromCache(this, methodRefCacheIndex), JVM_CONSTANT.MethodRef);
696 compilerToVM().resolveInvokeHandleInPool(this, methodRefCacheIndex); 702 compilerToVM().resolveInvokeHandleInPool(this, methodRefCacheIndex);
697 }
698 } 703 }
699 } 704 }
700 705
701 break; 706 break;
702 case InvokeDynamic: 707 case InvokeDynamic:
706 break; 711 break;
707 default: 712 default:
708 // nothing 713 // nothing
709 break; 714 break;
710 } 715 }
711 } 716
712 717 }
713 private boolean isInvokeHandle(int methodRefCacheIndex, HotSpotResolvedObjectTypeImpl klass) { 718
714 assertTag(compilerToVM().constantPoolRemapInstructionOperandFromCache(this, methodRefCacheIndex), JVM_CONSTANT.MethodRef); 719 // Lazily initialized.
715 return ResolvedJavaMethod.isSignaturePolymorphic(klass, getNameOf(methodRefCacheIndex), runtime().getHostJVMCIBackend().getMetaAccess()); 720 private static String[] signaturePolymorphicHolders;
721
722 /**
723 * Determines if {@code type} contains signature polymorphic methods.
724 */
725 private static boolean isSignaturePolymorphicHolder(final HotSpotResolvedObjectTypeImpl type) {
726 String name = type.getName();
727 if (signaturePolymorphicHolders == null) {
728 signaturePolymorphicHolders = compilerToVM().getSignaturePolymorphicHolders();
729 }
730 for (String holder : signaturePolymorphicHolders) {
731 if (name.equals(holder)) {
732 return true;
733 }
734 }
735 return false;
716 } 736 }
717 737
718 @Override 738 @Override
719 public String toString() { 739 public String toString() {
720 HotSpotResolvedObjectType holder = getHolder(); 740 HotSpotResolvedObjectType holder = getHolder();