src/jdk.internal.vm.compiler/share/classes/org.graalvm.compiler.hotspot/src/org/graalvm/compiler/hotspot/meta/HotSpotGraphBuilderPlugins.java
changeset 59095 03fbcd06b4c0
parent 58901 2700c409ff10
equal deleted inserted replaced
59094:5d4c3724e4c7 59095:03fbcd06b4c0
    33 
    33 
    34 import java.lang.invoke.ConstantCallSite;
    34 import java.lang.invoke.ConstantCallSite;
    35 import java.lang.invoke.MutableCallSite;
    35 import java.lang.invoke.MutableCallSite;
    36 import java.lang.invoke.VolatileCallSite;
    36 import java.lang.invoke.VolatileCallSite;
    37 import java.lang.reflect.Array;
    37 import java.lang.reflect.Array;
       
    38 import java.lang.reflect.Type;
    38 import java.math.BigInteger;
    39 import java.math.BigInteger;
    39 import java.util.zip.CRC32;
    40 import java.util.zip.CRC32;
    40 
    41 
       
    42 import jdk.internal.vm.compiler.collections.Pair;
    41 import org.graalvm.compiler.api.replacements.SnippetReflectionProvider;
    43 import org.graalvm.compiler.api.replacements.SnippetReflectionProvider;
    42 import org.graalvm.compiler.core.common.spi.ForeignCallsProvider;
    44 import org.graalvm.compiler.core.common.spi.ForeignCallsProvider;
    43 import org.graalvm.compiler.core.common.type.ObjectStamp;
    45 import org.graalvm.compiler.core.common.type.ObjectStamp;
    44 import org.graalvm.compiler.core.common.type.StampFactory;
    46 import org.graalvm.compiler.core.common.type.StampFactory;
    45 import org.graalvm.compiler.core.common.type.TypeReference;
    47 import org.graalvm.compiler.core.common.type.TypeReference;
   113 import jdk.vm.ci.meta.ConstantReflectionProvider;
   115 import jdk.vm.ci.meta.ConstantReflectionProvider;
   114 import jdk.vm.ci.meta.DeoptimizationAction;
   116 import jdk.vm.ci.meta.DeoptimizationAction;
   115 import jdk.vm.ci.meta.JavaKind;
   117 import jdk.vm.ci.meta.JavaKind;
   116 import jdk.vm.ci.meta.MetaAccessProvider;
   118 import jdk.vm.ci.meta.MetaAccessProvider;
   117 import jdk.vm.ci.meta.ResolvedJavaMethod;
   119 import jdk.vm.ci.meta.ResolvedJavaMethod;
       
   120 import jdk.vm.ci.services.Services;
   118 import sun.misc.Unsafe;
   121 import sun.misc.Unsafe;
   119 
   122 
   120 /**
   123 /**
   121  * Defines the {@link Plugins} used when running on HotSpot.
   124  * Defines the {@link Plugins} used when running on HotSpot.
   122  */
   125  */
   459             constantPoolClass = "jdk.internal.reflect.ConstantPool";
   462             constantPoolClass = "jdk.internal.reflect.ConstantPool";
   460         }
   463         }
   461     }
   464     }
   462 
   465 
   463     public static String lookupIntrinsicName(GraalHotSpotVMConfig config, String className, String name1, String name2) {
   466     public static String lookupIntrinsicName(GraalHotSpotVMConfig config, String className, String name1, String name2) {
       
   467         return selectIntrinsicName(config, className, name1, name2).getLeft();
       
   468     }
       
   469 
       
   470     /**
       
   471      * Returns a pair of Strings where the left one represents the matched intrinsic name and the
       
   472      * right one represents the mismatched intrinsic name.
       
   473      */
       
   474     public static Pair<String, String> selectIntrinsicName(GraalHotSpotVMConfig config, String className, String name1, String name2) {
   464         boolean foundName1 = false;
   475         boolean foundName1 = false;
   465         boolean foundName2 = false;
   476         boolean foundName2 = false;
   466         String name = name1;
       
   467         for (VMIntrinsicMethod intrinsic : config.getStore().getIntrinsics()) {
   477         for (VMIntrinsicMethod intrinsic : config.getStore().getIntrinsics()) {
   468             if (className.equals(intrinsic.declaringClass)) {
   478             if (className.equals(intrinsic.declaringClass)) {
   469                 if (name1.equals(intrinsic.name)) {
   479                 if (name1.equals(intrinsic.name)) {
   470                     foundName1 = true;
   480                     foundName1 = true;
   471                 } else if (name2.equals(intrinsic.name)) {
   481                 } else if (name2.equals(intrinsic.name)) {
   472                     foundName2 = true;
   482                     foundName2 = true;
   473                     name = name2;
       
   474                 }
   483                 }
   475             }
   484             }
   476         }
   485         }
   477         if (foundName1 != foundName2) {
   486         if (foundName1 && !foundName2) {
   478             return name;
   487             return Pair.create(name1, name2);
       
   488         } else if (foundName2 && !foundName1) {
       
   489             return Pair.create(name2, name1);
   479         }
   490         }
   480         throw GraalError.shouldNotReachHere();
   491         throw GraalError.shouldNotReachHere();
   481     }
   492     }
   482 
   493 
   483     public static boolean isIntrinsicName(GraalHotSpotVMConfig config, String className, String name) {
   494     public static boolean isIntrinsicName(GraalHotSpotVMConfig config, String className, String name) {
   498             assert config.cipherBlockChainingEncryptAESCryptStub != 0L;
   509             assert config.cipherBlockChainingEncryptAESCryptStub != 0L;
   499             assert config.cipherBlockChainingDecryptAESCryptStub != 0L;
   510             assert config.cipherBlockChainingDecryptAESCryptStub != 0L;
   500             String arch = config.osArch;
   511             String arch = config.osArch;
   501             String decryptSuffix = arch.equals("sparc") ? "WithOriginalKey" : "";
   512             String decryptSuffix = arch.equals("sparc") ? "WithOriginalKey" : "";
   502 
   513 
   503             String cbcEncryptName = lookupIntrinsicName(config, "com/sun/crypto/provider/CipherBlockChaining", "implEncrypt", "encrypt");
       
   504             String cbcDecryptName = lookupIntrinsicName(config, "com/sun/crypto/provider/CipherBlockChaining", "implDecrypt", "decrypt");
       
   505             Registration r = new Registration(plugins, "com.sun.crypto.provider.CipherBlockChaining", replacements);
   514             Registration r = new Registration(plugins, "com.sun.crypto.provider.CipherBlockChaining", replacements);
   506             r.registerMethodSubstitution(CipherBlockChainingSubstitutions.class, cbcEncryptName, Receiver.class, byte[].class, int.class, int.class, byte[].class, int.class);
   515 
   507             r.registerMethodSubstitution(CipherBlockChainingSubstitutions.class, cbcDecryptName, cbcDecryptName + decryptSuffix, Receiver.class, byte[].class, int.class, int.class, byte[].class,
   516             Pair<String, String> cbcEncryptName = selectIntrinsicName(config, "com/sun/crypto/provider/CipherBlockChaining", "implEncrypt", "encrypt");
   508                             int.class);
   517             registerAndCheckMismatch(r, CipherBlockChainingSubstitutions.class, cbcEncryptName, Receiver.class, byte[].class, int.class, int.class,
   509 
   518                             byte[].class, int.class);
   510             String aesEncryptName = lookupIntrinsicName(config, "com/sun/crypto/provider/AESCrypt", "implEncryptBlock", "encryptBlock");
   519 
   511             String aesDecryptName = lookupIntrinsicName(config, "com/sun/crypto/provider/AESCrypt", "implDecryptBlock", "decryptBlock");
   520             Pair<String, String> cbcDecryptName = selectIntrinsicName(config, "com/sun/crypto/provider/CipherBlockChaining", "implDecrypt", "decrypt");
       
   521             registerAndCheckMismatch(r, CipherBlockChainingSubstitutions.class, cbcDecryptName, cbcDecryptName.getLeft() + decryptSuffix, Receiver.class, byte[].class, int.class, int.class,
       
   522                             byte[].class, int.class);
   512 
   523 
   513             r = new Registration(plugins, "com.sun.crypto.provider.AESCrypt", replacements);
   524             r = new Registration(plugins, "com.sun.crypto.provider.AESCrypt", replacements);
   514             r.registerMethodSubstitution(AESCryptSubstitutions.class, aesEncryptName, Receiver.class, byte[].class, int.class, byte[].class, int.class);
   525 
   515             r.registerMethodSubstitution(AESCryptSubstitutions.class, aesDecryptName, aesDecryptName + decryptSuffix, Receiver.class, byte[].class, int.class, byte[].class, int.class);
   526             Pair<String, String> aesEncryptName = selectIntrinsicName(config, "com/sun/crypto/provider/AESCrypt", "implEncryptBlock", "encryptBlock");
       
   527             registerAndCheckMismatch(r, AESCryptSubstitutions.class, aesEncryptName, Receiver.class, byte[].class, int.class, byte[].class, int.class);
       
   528 
       
   529             Pair<String, String> aesDecryptName = selectIntrinsicName(config, "com/sun/crypto/provider/AESCrypt", "implDecryptBlock", "decryptBlock");
       
   530             registerAndCheckMismatch(r, AESCryptSubstitutions.class, aesDecryptName, aesDecryptName.getLeft() + decryptSuffix, Receiver.class, byte[].class, int.class, byte[].class, int.class);
       
   531         }
       
   532     }
       
   533 
       
   534     private static void registerAndCheckMismatch(Registration r, Class<?> substitutionClass, Pair<String, String> intrinsicNames, Type... argumentTypes) {
       
   535         try {
       
   536             r.registerMethodSubstitution(substitutionClass, intrinsicNames.getLeft(), argumentTypes);
       
   537         } catch (NoSuchMethodError e) {
       
   538             throw new GraalError(e, "Found method named '%s' instead of '%s' in class '%s'. This is most likely because the JVMCI JDK in %s was built on an incompatible base JDK.",
       
   539                             intrinsicNames.getRight(), intrinsicNames.getLeft(), r.getDeclaringType().getTypeName(), Services.getSavedProperties().get("java.home"));
       
   540         }
       
   541     }
       
   542 
       
   543     private static void registerAndCheckMismatch(Registration r, Class<?> substitutionClass, Pair<String, String> intrinsicNames, String substituteName, Type... argumentTypes) {
       
   544         try {
       
   545             r.registerMethodSubstitution(substitutionClass, intrinsicNames.getLeft(), substituteName, argumentTypes);
       
   546         } catch (NoSuchMethodError e) {
       
   547             throw new GraalError(e, "Found method named '%s' instead of '%s' in class '%s'. This is most likely because the JVMCI JDK in %s was built on an incompatible base JDK.",
       
   548                             intrinsicNames.getRight(), intrinsicNames.getLeft(), r.getDeclaringType().getTypeName(), Services.getSavedProperties().get("java.home"));
   516         }
   549         }
   517     }
   550     }
   518 
   551 
   519     private static void registerBigIntegerPlugins(InvocationPlugins plugins, GraalHotSpotVMConfig config, Replacements replacements) {
   552     private static void registerBigIntegerPlugins(InvocationPlugins plugins, GraalHotSpotVMConfig config, Replacements replacements) {
   520         Registration r = new Registration(plugins, BigInteger.class, replacements);
   553         Registration r = new Registration(plugins, BigInteger.class, replacements);
   542         if (isIntrinsicName(config, "sun/security/provider/DigestBase", "implCompressMultiBlock0") && (useSha1 || useSha256 || useSha512)) {
   575         if (isIntrinsicName(config, "sun/security/provider/DigestBase", "implCompressMultiBlock0") && (useSha1 || useSha256 || useSha512)) {
   543             Registration r = new Registration(plugins, "sun.security.provider.DigestBase", replacements);
   576             Registration r = new Registration(plugins, "sun.security.provider.DigestBase", replacements);
   544             r.registerMethodSubstitution(DigestBaseSubstitutions.class, "implCompressMultiBlock0", Receiver.class, byte[].class, int.class, int.class);
   577             r.registerMethodSubstitution(DigestBaseSubstitutions.class, "implCompressMultiBlock0", Receiver.class, byte[].class, int.class, int.class);
   545         }
   578         }
   546 
   579 
   547         String implCompressName = lookupIntrinsicName(config, "sun/security/provider/SHA", "implCompress", "implCompress0");
   580         Pair<String, String> implCompressName = selectIntrinsicName(config, "sun/security/provider/SHA", "implCompress", "implCompress0");
   548         if (useSha1) {
   581         if (useSha1) {
   549             assert config.sha1ImplCompress != 0L;
   582             assert config.sha1ImplCompress != 0L;
   550             Registration r = new Registration(plugins, "sun.security.provider.SHA", replacements);
   583             Registration r = new Registration(plugins, "sun.security.provider.SHA", replacements);
   551             r.registerMethodSubstitution(SHASubstitutions.class, implCompressName, "implCompress0", Receiver.class, byte[].class, int.class);
   584             registerAndCheckMismatch(r, SHASubstitutions.class, implCompressName, "implCompress0", Receiver.class, byte[].class, int.class);
   552         }
   585         }
   553         if (useSha256) {
   586         if (useSha256) {
   554             assert config.sha256ImplCompress != 0L;
   587             assert config.sha256ImplCompress != 0L;
   555             Registration r = new Registration(plugins, "sun.security.provider.SHA2", replacements);
   588             Registration r = new Registration(plugins, "sun.security.provider.SHA2", replacements);
   556             r.registerMethodSubstitution(SHA2Substitutions.class, implCompressName, "implCompress0", Receiver.class, byte[].class, int.class);
   589             registerAndCheckMismatch(r, SHA2Substitutions.class, implCompressName, "implCompress0", Receiver.class, byte[].class, int.class);
   557         }
   590         }
   558         if (useSha512) {
   591         if (useSha512) {
   559             assert config.sha512ImplCompress != 0L;
   592             assert config.sha512ImplCompress != 0L;
   560             Registration r = new Registration(plugins, "sun.security.provider.SHA5", replacements);
   593             Registration r = new Registration(plugins, "sun.security.provider.SHA5", replacements);
   561             r.registerMethodSubstitution(SHA5Substitutions.class, implCompressName, "implCompress0", Receiver.class, byte[].class, int.class);
   594             registerAndCheckMismatch(r, SHA5Substitutions.class, implCompressName, "implCompress0", Receiver.class, byte[].class, int.class);
   562         }
   595         }
   563     }
   596     }
   564 
   597 
   565     private static void registerGHASHPlugins(InvocationPlugins plugins, GraalHotSpotVMConfig config, MetaAccessProvider metaAccess, ForeignCallsProvider foreignCalls) {
   598     private static void registerGHASHPlugins(InvocationPlugins plugins, GraalHotSpotVMConfig config, MetaAccessProvider metaAccess, ForeignCallsProvider foreignCalls) {
   566         if (config.useGHASHIntrinsics()) {
   599         if (config.useGHASHIntrinsics()) {