Merge
This commit is contained in:
commit
c725ebc3ea
14
.hgtags
14
.hgtags
@ -399,3 +399,17 @@ d7034ff7f8e257e81c9f95c7785dd4eaaa3c2afc jdk-9+153
|
||||
8c70d170e62c0c58b5bc3ba666bd140399b98c9c jdk-10+0
|
||||
45b751afd11e6c05991cf4913c5a0ac3304fcc4e jdk-9+154
|
||||
f4aff695ffe05cfdb69d8af25a4ddc6a029754ea jdk-9+155
|
||||
06bce0388880b5ff8e040e4a9d72a3ea11dac321 jdk-9+156
|
||||
fa3e76b477829afc4476f0b725cfaa440a6fd917 jdk-9+157
|
||||
b5015f742ba648184bb7fc547197bd33ebfde30d jdk-9+158
|
||||
fd1497902bbe3aa24b21f270ecdcb8de5f7aa9ac jdk-9+159
|
||||
6aa8be0c4e054fe8b3ab016ae00d16d680f92145 jdk-9+160
|
||||
f6883b1a5a6478437cd4181c4bd45328ab24feaf jdk-9+161
|
||||
d16aebbb56d37f12e0c0b0a4fb427db65e1fb1a8 jdk-9+162
|
||||
18c41483a082e097ac2f5f983c1226ed94aa4215 jdk-9+163
|
||||
32db52c675e7d5bc413605d2e89b68b608b19be0 jdk-9+164
|
||||
3965b747cfe1e6cbd66b8739da5a1ea6ec6985e9 jdk-9+165
|
||||
d3e973f1809606c67412361041ad197e50fe8cec jdk-9+166
|
||||
8fd0a4569191f33c98ee90c2709174a342fefb0d jdk-9+167
|
||||
fcabc74bd44e56c7419d111d59b95669ecb33c55 jdk-9+168
|
||||
c7efde2b60fc1ec04630be769d9ad60efb39c39c jdk-9+169
|
||||
|
@ -398,3 +398,15 @@ ff8cb43c07c069b1debdee44cb88ca22db1ec757 jdk-9+152
|
||||
68a8e8658511093b322a46ed04b2a321e1da2a43 jdk-9+153
|
||||
078ebe23b584466dc8346e620d7821d91751e5a9 jdk-9+154
|
||||
a545f54babfa31aa7eb611f36031609acd617cbc jdk-9+155
|
||||
907c26240cd481579e919bfd23740797ff8ce1c8 jdk-9+156
|
||||
9383da04b385cca46b7ca67f3a39ac1b673e09fe jdk-9+157
|
||||
de6bdf38935fa753183ca288bed5c06a23c0bb12 jdk-9+158
|
||||
6feea77d2083c99e44aa3e272d07b7fb3b801683 jdk-9+159
|
||||
c7688f2fa07936b089ca0e9a0a0eff68ff37a542 jdk-9+160
|
||||
18f02bc43fe96aef36791d0df7aca748485210cc jdk-9+161
|
||||
18ffcf99a3b4a10457853d94190e825bdf07e39b jdk-9+162
|
||||
493011dee80e51c2a2b064d049183c047df36d80 jdk-9+163
|
||||
965bbae3072702f7c0d95c240523b65e6bb19261 jdk-9+164
|
||||
a510b2201154abdd12ede42788086b5283bfb9a6 jdk-9+165
|
||||
934c18145915b06d3fcc0de1a30f91f5aab8a192 jdk-9+166
|
||||
43de67f51801b9e16507865fcb7e8344f4ca4aa9 jdk-9+167
|
||||
|
14
corba/README
14
corba/README
@ -1,14 +0,0 @@
|
||||
README:
|
||||
This file should be located at the top of the corba Mercurial repository.
|
||||
|
||||
See http://openjdk.java.net/ for more information about the OpenJDK.
|
||||
|
||||
See ../README-builds.html for complete details on build machine requirements.
|
||||
|
||||
Simple Build Instructions:
|
||||
|
||||
cd make && gnumake
|
||||
|
||||
The files that will be imported into the jdk build will be in the "dist"
|
||||
directory.
|
||||
|
@ -25,6 +25,9 @@
|
||||
|
||||
/**
|
||||
* Defines the Java binding of the OMG CORBA APIs, and the RMI-IIOP API.
|
||||
*
|
||||
* @moduleGraph
|
||||
* @since 9
|
||||
*/
|
||||
@Deprecated(since="9", forRemoval=true)
|
||||
module java.corba {
|
||||
|
@ -106,13 +106,13 @@ import java.security.PrivilegedAction;
|
||||
*
|
||||
* <LI>check in properties parameter, if any
|
||||
*
|
||||
* <LI>check in the System properties
|
||||
* <LI>check in the System properties, if any
|
||||
*
|
||||
* <LI>check in the orb.properties file located in the user.home
|
||||
* directory (if any)
|
||||
* directory, if any
|
||||
*
|
||||
* <LI>check in the orb.properties file located in the java.home/lib
|
||||
* directory (if any)
|
||||
* <LI>check in the orb.properties file located in the run-time image,
|
||||
* if any
|
||||
*
|
||||
* <LI>fall back on a hardcoded default behavior (use the Java IDL
|
||||
* implementation)
|
||||
@ -170,9 +170,15 @@ import java.security.PrivilegedAction;
|
||||
* Thus, where appropriate, it is necessary that
|
||||
* the classes for this alternative ORBSingleton are available on the application's class path.
|
||||
* It should be noted that the singleton ORB is system wide.
|
||||
*
|
||||
* <P>
|
||||
* When a per-application ORB is created via the 2-arg init methods,
|
||||
* then it will be located using the thread context class loader.
|
||||
* <P>
|
||||
* The IDL to Java Language OMG specification documents the ${java.home}/lib directory as the location,
|
||||
* in the Java run-time image, to search for orb.properties.
|
||||
* This location is not intended for user editable configuration files.
|
||||
* Therefore, the implementation first checks the ${java.home}/conf directory for orb.properties,
|
||||
* and thereafter the ${java.home}/lib directory.
|
||||
*
|
||||
* @since JDK1.2
|
||||
*/
|
||||
@ -271,14 +277,25 @@ abstract public class ORB {
|
||||
}
|
||||
|
||||
String javaHome = System.getProperty("java.home");
|
||||
fileName = javaHome + File.separator
|
||||
+ "lib" + File.separator + "orb.properties";
|
||||
props = getFileProperties( fileName ) ;
|
||||
|
||||
fileName = javaHome + File.separator + "conf"
|
||||
+ File.separator + "orb.properties";
|
||||
props = getFileProperties(fileName);
|
||||
|
||||
if (props != null) {
|
||||
String value = props.getProperty(name);
|
||||
if (value != null)
|
||||
return value;
|
||||
}
|
||||
|
||||
fileName = javaHome + File.separator + "lib"
|
||||
+ File.separator + "orb.properties";
|
||||
props = getFileProperties(fileName);
|
||||
|
||||
if (props == null)
|
||||
return null ;
|
||||
return null;
|
||||
else
|
||||
return props.getProperty( name ) ;
|
||||
return props.getProperty(name);
|
||||
}
|
||||
}
|
||||
);
|
||||
|
@ -59,10 +59,10 @@ import sun.reflect.ReflectionFactory;
|
||||
* </ul>
|
||||
* The code that calls Bridge.get() must have the following Permissions:
|
||||
* <ul>
|
||||
* <li>RuntimePermission "reflectionFactoryAccess"</li>
|
||||
* <li>BridgePermission "getBridge"</li>
|
||||
* <li>ReflectPermission "suppressAccessChecks"</li>
|
||||
* <li>StackFramePermission "retainClassReference"</li>
|
||||
* <li>RuntimePermission "getStackWalkerWithClassReference"</li>
|
||||
* <li>RuntimePermission "reflectionFactoryAccess"</li>
|
||||
* </ul>
|
||||
* <p>
|
||||
* All of these permissions are required to obtain and correctly initialize
|
||||
@ -105,10 +105,10 @@ public final class Bridge
|
||||
/** Fetch the Bridge singleton. This requires the following
|
||||
* permissions:
|
||||
* <ul>
|
||||
* <li>RuntimePermission "reflectionFactoryAccess"</li>
|
||||
* <li>BridgePermission "getBridge"</li>
|
||||
* <li>ReflectPermission "suppressAccessChecks"</li>
|
||||
* <li>StackFramePermission "retainClassReference"</li>
|
||||
* <li>RuntimePermission "getStackWalkerWithClassReference"</li>
|
||||
* <li>RuntimePermission "reflectionFactoryAccess"</li>
|
||||
* </ul>
|
||||
* @return The singleton instance of the Bridge class
|
||||
* @throws SecurityException if the caller does not have the
|
||||
|
@ -15,10 +15,10 @@
|
||||
^\.mx.jvmci/hotspot/eclipse/.*
|
||||
^\.idea/
|
||||
^workingsets.xml
|
||||
^src/jdk.vm.ci/share/classes/\w[\w\.]*/.*\.xml
|
||||
^src/jdk.vm.ci/share/classes/\w[\w\.]*/.*\.iml
|
||||
^src/jdk.vm.ci/share/classes/\w[\w\.]*/nbproject
|
||||
^src/jdk.vm.ci/share/classes/\w[\w\.]*/\..*
|
||||
^src/jdk.internal.vm.ci/share/classes/\w[\w\.]*/.*\.xml
|
||||
^src/jdk.internal.vm.ci/share/classes/\w[\w\.]*/.*\.iml
|
||||
^src/jdk.internal.vm.ci/share/classes/\w[\w\.]*/nbproject
|
||||
^src/jdk.internal.vm.ci/share/classes/\w[\w\.]*/\..*
|
||||
^test/compiler/jvmci/\w[\w\.]*/.*\.xml
|
||||
^test/compiler/jvmci/\w[\w\.]*/.*\.iml
|
||||
^test/compiler/jvmci/\w[\w\.]*/nbproject
|
||||
@ -27,15 +27,15 @@
|
||||
^test/compiler/aot/\w[\w\.]*/.*\.iml
|
||||
^test/compiler/aot/\w[\w\.]*/nbproject
|
||||
^test/compiler/aot/\w[\w\.]*/\..*
|
||||
^src/jdk.vm.compiler/\.mx.graal/env
|
||||
^src/jdk.vm.compiler/\.mx.graal/.*\.pyc
|
||||
^src/jdk.vm.compiler/\.mx.graal/eclipse-launches/.*
|
||||
^src/jdk.internal.vm.compiler/\.mx.graal/env
|
||||
^src/jdk.internal.vm.compiler/\.mx.graal/.*\.pyc
|
||||
^src/jdk.internal.vm.compiler/\.mx.graal/eclipse-launches/.*
|
||||
^src/jdk.aot/share/classes/\w[\w\.]*/.*\.xml
|
||||
^src/jdk.aot/share/classes/\w[\w\.]*/.*\.iml
|
||||
^src/jdk.aot/share/classes/\w[\w\.]*/nbproject
|
||||
^src/jdk.aot/share/classes/\w[\w\.]*/\..*
|
||||
^src/jdk.vm.compiler/share/classes/\w[\w\.]*/.*\.xml
|
||||
^src/jdk.vm.compiler/share/classes/\w[\w\.]*/.*\.iml
|
||||
^src/jdk.vm.compiler/share/classes/\w[\w\.]*/nbproject
|
||||
^src/jdk.vm.compiler/share/classes/\w[\w\.]*/\..*
|
||||
^src/jdk.internal.vm.compiler/share/classes/\w[\w\.]*/.*\.xml
|
||||
^src/jdk.internal.vm.compiler/share/classes/\w[\w\.]*/.*\.iml
|
||||
^src/jdk.internal.vm.compiler/share/classes/\w[\w\.]*/nbproject
|
||||
^src/jdk.internal.vm.compiler/share/classes/\w[\w\.]*/\..*
|
||||
|
||||
|
@ -558,3 +558,16 @@ a82cb5350cad96a0b4de496afebe3ded89f27efa jdk-9+146
|
||||
217ba81b9a4ce8698200370175aa2db86a39f66c jdk-9+153
|
||||
a9fdfd55835ef9dccb7f317b07249bd66653b874 jdk-9+154
|
||||
f3b3d77a1751897413aae43ac340a130b6fa2ae1 jdk-9+155
|
||||
43139c588ea48b6504e52b6c3dec530b17b1fdb4 jdk-9+156
|
||||
b2d0a906afd73dcf27f572217eb1be0f196ec16c jdk-9+157
|
||||
4e78f30935229f13ce7c43089621cf7169f5abac jdk-9+158
|
||||
9211c2e89c1cd11ec2d5752b0f97131a7d7525c7 jdk-9+159
|
||||
94b4e2e5331d38eab6a3639c3511b2e0715df0e9 jdk-9+160
|
||||
191ffbdb3d7b734288daa7fb76b37a0a85dfe7eb jdk-9+161
|
||||
b01c519b715ef6f785d0631adee0a6537cf6c12e jdk-9+162
|
||||
983fe207555724d98f4876991e1cbafbcf2733e8 jdk-9+163
|
||||
0af429be8bbaeaaf0cb838e9af28c953dda6a9c8 jdk-9+164
|
||||
c92c6416ca03b1464d5ed99cf6201e52b5ba0a70 jdk-9+165
|
||||
560d7aa083a24b6a56443feb8de0f40435d33aa9 jdk-9+166
|
||||
1ca7ed1b17b5776930d641d1379834f3140a74e4 jdk-9+167
|
||||
fbb9c802649585d19f6d7e81b4a519d44806225a jdk-9+168
|
||||
|
@ -3,7 +3,7 @@
|
||||
<pydev_property name="org.python.pydev.PYTHON_PROJECT_INTERPRETER">Default</pydev_property>
|
||||
<pydev_property name="org.python.pydev.PYTHON_PROJECT_VERSION">python 2.7</pydev_property>
|
||||
<pydev_pathproperty name="org.python.pydev.PROJECT_SOURCE_PATH">
|
||||
<path>/.mx.jvmci</path>
|
||||
<path>/mx.jvmci</path>
|
||||
</pydev_pathproperty>
|
||||
<pydev_pathproperty name="org.python.pydev.PROJECT_SOURCE_PATH">
|
||||
<path>/mx</path>
|
||||
|
@ -158,8 +158,8 @@ To build hotspot and import it into the JDK: "mx make hotspot import-hotspot"
|
||||
# JDK9 must be bootstrapped with a JDK8
|
||||
compliance = mx.JavaCompliance('8')
|
||||
jdk8 = mx.get_jdk(compliance.exactMatch, versionDescription=compliance.value)
|
||||
cmd = ['sh', 'configure', '--with-debug-level=' + _vm.debugLevel, '--with-native-debug-symbols=external', '--disable-precompiled-headers',
|
||||
'--with-jvm-variants=' + _vm.jvmVariant, '--disable-warnings-as-errors', '--with-boot-jdk=' + jdk8.home]
|
||||
cmd = ['sh', 'configure', '--with-debug-level=' + _vm.debugLevel, '--with-native-debug-symbols=external', '--disable-precompiled-headers', '--with-jvm-features=graal',
|
||||
'--with-jvm-variants=' + _vm.jvmVariant, '--disable-warnings-as-errors', '--with-boot-jdk=' + jdk8.home, '--with-jvm-features=graal']
|
||||
mx.run(cmd, cwd=_jdkSourceRoot)
|
||||
cmd = [mx.gmake_cmd(), 'CONF=' + _vm.debugLevel]
|
||||
if mx.get_opts().verbose:
|
||||
@ -176,66 +176,6 @@ To build hotspot and import it into the JDK: "mx make hotspot import-hotspot"
|
||||
|
||||
mx.run(cmd, cwd=_jdkSourceRoot)
|
||||
|
||||
if 'images' in cmd:
|
||||
jdkImageDir = join(jdkBuildDir, 'images', 'jdk')
|
||||
|
||||
# The OpenJDK build creates an empty cacerts file so copy one from
|
||||
# the default JDK (which is assumed to be an OracleJDK)
|
||||
srcCerts = join(mx.get_jdk(tag='default').home, 'lib', 'security', 'cacerts')
|
||||
if not exists(srcCerts):
|
||||
# Might be building with JDK8 which has cacerts under jre/
|
||||
srcCerts = join(mx.get_jdk(tag='default').home, 'jre', 'lib', 'security', 'cacerts')
|
||||
dstCerts = join(jdkImageDir, 'lib', 'security', 'cacerts')
|
||||
if srcCerts != dstCerts:
|
||||
shutil.copyfile(srcCerts, dstCerts)
|
||||
|
||||
_create_jdk_bundle(jdkBuildDir, _vm.debugLevel, jdkImageDir)
|
||||
|
||||
def _get_jdk_bundle_arches():
|
||||
"""
|
||||
Gets a list of names that will be the part of a JDK bundle's file name denoting the architecture.
|
||||
The first element in the list is the canonical name. Symlinks should be created for the
|
||||
remaining names.
|
||||
"""
|
||||
cpu = mx.get_arch()
|
||||
if cpu == 'amd64':
|
||||
return ['x64', 'x86_64', 'amd64']
|
||||
elif cpu == 'sparcv9':
|
||||
return ['sparcv9']
|
||||
mx.abort('Unsupported JDK bundle arch: ' + cpu)
|
||||
|
||||
def _create_jdk_bundle(jdkBuildDir, debugLevel, jdkImageDir):
|
||||
"""
|
||||
Creates a tar.gz JDK archive, an accompanying tar.gz.sha1 file with its
|
||||
SHA1 signature plus symlinks to the archive for non-canonical architecture names.
|
||||
"""
|
||||
|
||||
arches = _get_jdk_bundle_arches()
|
||||
jdkTgzPath = join(_suite.get_output_root(), 'jdk-bundles', 'jdk9-{}-{}-{}.tar.gz'.format(debugLevel, _get_openjdk_os(), arches[0]))
|
||||
with mx.Archiver(jdkTgzPath, kind='tgz') as arc:
|
||||
mx.log('Creating ' + jdkTgzPath)
|
||||
for root, _, filenames in os.walk(jdkImageDir):
|
||||
for name in filenames:
|
||||
f = join(root, name)
|
||||
arcname = 'jdk1.9.0/' + os.path.relpath(f, jdkImageDir)
|
||||
arc.zf.add(name=f, arcname=arcname, recursive=False)
|
||||
|
||||
with open(jdkTgzPath + '.sha1', 'w') as fp:
|
||||
mx.log('Creating ' + jdkTgzPath + '.sha1')
|
||||
fp.write(mx.sha1OfFile(jdkTgzPath))
|
||||
|
||||
def _create_link(source, link_name):
|
||||
if exists(link_name):
|
||||
os.remove(link_name)
|
||||
mx.log('Creating ' + link_name + ' -> ' + source)
|
||||
os.symlink(source, link_name)
|
||||
|
||||
for arch in arches[1:]:
|
||||
link_name = join(_suite.get_output_root(), 'jdk-bundles', 'jdk9-{}-{}-{}.tar.gz'.format(debugLevel, _get_openjdk_os(), arch))
|
||||
jdkTgzName = os.path.basename(jdkTgzPath)
|
||||
_create_link(jdkTgzName, link_name)
|
||||
_create_link(jdkTgzName + '.sha1', link_name + '.sha1')
|
||||
|
||||
def _runmultimake(args):
|
||||
"""run the JDK make process for one or more configurations"""
|
||||
|
||||
|
@ -43,7 +43,7 @@ suite = {
|
||||
# ------------- JVMCI:Service -------------
|
||||
|
||||
"jdk.vm.ci.services" : {
|
||||
"subDir" : "src/jdk.vm.ci/share/classes",
|
||||
"subDir" : "src/jdk.internal.vm.ci/share/classes",
|
||||
"sourceDirs" : ["src"],
|
||||
"javaCompliance" : "9",
|
||||
"workingSets" : "API,JVMCI",
|
||||
@ -52,7 +52,7 @@ suite = {
|
||||
# ------------- JVMCI:API -------------
|
||||
|
||||
"jdk.vm.ci.common" : {
|
||||
"subDir" : "src/jdk.vm.ci/share/classes",
|
||||
"subDir" : "src/jdk.internal.vm.ci/share/classes",
|
||||
"sourceDirs" : ["src"],
|
||||
"checkstyle" : "jdk.vm.ci.services",
|
||||
"javaCompliance" : "9",
|
||||
@ -60,7 +60,7 @@ suite = {
|
||||
},
|
||||
|
||||
"jdk.vm.ci.meta" : {
|
||||
"subDir" : "src/jdk.vm.ci/share/classes",
|
||||
"subDir" : "src/jdk.internal.vm.ci/share/classes",
|
||||
"sourceDirs" : ["src"],
|
||||
"checkstyle" : "jdk.vm.ci.services",
|
||||
"javaCompliance" : "9",
|
||||
@ -68,7 +68,7 @@ suite = {
|
||||
},
|
||||
|
||||
"jdk.vm.ci.code" : {
|
||||
"subDir" : "src/jdk.vm.ci/share/classes",
|
||||
"subDir" : "src/jdk.internal.vm.ci/share/classes",
|
||||
"sourceDirs" : ["src"],
|
||||
"dependencies" : ["jdk.vm.ci.meta"],
|
||||
"checkstyle" : "jdk.vm.ci.services",
|
||||
@ -92,7 +92,7 @@ suite = {
|
||||
},
|
||||
|
||||
"jdk.vm.ci.runtime" : {
|
||||
"subDir" : "src/jdk.vm.ci/share/classes",
|
||||
"subDir" : "src/jdk.internal.vm.ci/share/classes",
|
||||
"sourceDirs" : ["src"],
|
||||
"dependencies" : [
|
||||
"jdk.vm.ci.code",
|
||||
@ -119,7 +119,7 @@ suite = {
|
||||
# ------------- JVMCI:HotSpot -------------
|
||||
|
||||
"jdk.vm.ci.aarch64" : {
|
||||
"subDir" : "src/jdk.vm.ci/share/classes",
|
||||
"subDir" : "src/jdk.internal.vm.ci/share/classes",
|
||||
"sourceDirs" : ["src"],
|
||||
"dependencies" : ["jdk.vm.ci.code"],
|
||||
"checkstyle" : "jdk.vm.ci.services",
|
||||
@ -128,7 +128,7 @@ suite = {
|
||||
},
|
||||
|
||||
"jdk.vm.ci.amd64" : {
|
||||
"subDir" : "src/jdk.vm.ci/share/classes",
|
||||
"subDir" : "src/jdk.internal.vm.ci/share/classes",
|
||||
"sourceDirs" : ["src"],
|
||||
"dependencies" : ["jdk.vm.ci.code"],
|
||||
"checkstyle" : "jdk.vm.ci.services",
|
||||
@ -137,7 +137,7 @@ suite = {
|
||||
},
|
||||
|
||||
"jdk.vm.ci.sparc" : {
|
||||
"subDir" : "src/jdk.vm.ci/share/classes",
|
||||
"subDir" : "src/jdk.internal.vm.ci/share/classes",
|
||||
"sourceDirs" : ["src"],
|
||||
"dependencies" : ["jdk.vm.ci.code"],
|
||||
"checkstyle" : "jdk.vm.ci.services",
|
||||
@ -146,7 +146,7 @@ suite = {
|
||||
},
|
||||
|
||||
"jdk.vm.ci.hotspot" : {
|
||||
"subDir" : "src/jdk.vm.ci/share/classes",
|
||||
"subDir" : "src/jdk.internal.vm.ci/share/classes",
|
||||
"sourceDirs" : ["src"],
|
||||
"dependencies" : [
|
||||
"jdk.vm.ci.common",
|
||||
@ -175,7 +175,7 @@ suite = {
|
||||
},
|
||||
|
||||
"jdk.vm.ci.hotspot.aarch64" : {
|
||||
"subDir" : "src/jdk.vm.ci/share/classes",
|
||||
"subDir" : "src/jdk.internal.vm.ci/share/classes",
|
||||
"sourceDirs" : ["src"],
|
||||
"dependencies" : [
|
||||
"jdk.vm.ci.aarch64",
|
||||
@ -187,7 +187,7 @@ suite = {
|
||||
},
|
||||
|
||||
"jdk.vm.ci.hotspot.amd64" : {
|
||||
"subDir" : "src/jdk.vm.ci/share/classes",
|
||||
"subDir" : "src/jdk.internal.vm.ci/share/classes",
|
||||
"sourceDirs" : ["src"],
|
||||
"dependencies" : [
|
||||
"jdk.vm.ci.amd64",
|
||||
@ -199,7 +199,7 @@ suite = {
|
||||
},
|
||||
|
||||
"jdk.vm.ci.hotspot.sparc" : {
|
||||
"subDir" : "src/jdk.vm.ci/share/classes",
|
||||
"subDir" : "src/jdk.internal.vm.ci/share/classes",
|
||||
"sourceDirs" : ["src"],
|
||||
"dependencies" : [
|
||||
"jdk.vm.ci.sparc",
|
||||
@ -221,12 +221,12 @@ suite = {
|
||||
# ------------- Distributions -------------
|
||||
|
||||
"JVMCI_SERVICES" : {
|
||||
"subDir" : "src/jdk.vm.ci/share/classes",
|
||||
"subDir" : "src/jdk.internal.vm.ci/share/classes",
|
||||
"dependencies" : ["jdk.vm.ci.services"],
|
||||
},
|
||||
|
||||
"JVMCI_API" : {
|
||||
"subDir" : "src/jdk.vm.ci/share/classes",
|
||||
"subDir" : "src/jdk.internal.vm.ci/share/classes",
|
||||
"dependencies" : [
|
||||
"jdk.vm.ci.runtime",
|
||||
"jdk.vm.ci.common",
|
||||
@ -240,7 +240,7 @@ suite = {
|
||||
},
|
||||
|
||||
"JVMCI_HOTSPOT" : {
|
||||
"subDir" : "src/jdk.vm.ci/share/classes",
|
||||
"subDir" : "src/jdk.internal.vm.ci/share/classes",
|
||||
"dependencies" : [
|
||||
"jdk.vm.ci.hotspot.aarch64",
|
||||
"jdk.vm.ci.hotspot.amd64",
|
||||
|
@ -1,14 +0,0 @@
|
||||
README:
|
||||
This file should be located at the top of the hotspot Mercurial repository.
|
||||
|
||||
See http://openjdk.java.net/ for more information about the OpenJDK.
|
||||
|
||||
See ../README-builds.html for complete details on build machine requirements.
|
||||
|
||||
Simple Build Instructions:
|
||||
|
||||
cd make && gnumake
|
||||
|
||||
The files that will be imported into the jdk build will be in the "build"
|
||||
directory.
|
||||
|
@ -38,9 +38,9 @@ TARGETS :=
|
||||
$(eval $(call IncludeCustomExtension, hotspot, CompileTools.gmk))
|
||||
|
||||
ifeq ($(INCLUDE_GRAAL), true)
|
||||
VM_CI_SRC_DIR := $(HOTSPOT_TOPDIR)/src/jdk.vm.ci/share/classes
|
||||
VM_CI_SRC_DIR := $(HOTSPOT_TOPDIR)/src/jdk.internal.vm.ci/share/classes
|
||||
|
||||
SRC_DIR := $(HOTSPOT_TOPDIR)/src/jdk.vm.compiler/share/classes
|
||||
SRC_DIR := $(HOTSPOT_TOPDIR)/src/jdk.internal.vm.compiler/share/classes
|
||||
|
||||
##############################################################################
|
||||
# Compile the annotation processors
|
||||
|
@ -28,7 +28,7 @@ default: all
|
||||
include $(SPEC)
|
||||
include MakeBase.gmk
|
||||
|
||||
$(eval $(call IncludeCustomExtension, hotspot, gensrc/Gensrc-jdk.vm.compiler.gmk))
|
||||
$(eval $(call IncludeCustomExtension, hotspot, gensrc/Gensrc-jdk.internal.vm.compiler.gmk))
|
||||
|
||||
GENSRC_DIR := $(SUPPORT_OUTPUTDIR)/gensrc/$(MODULE)
|
||||
SRC_DIR := $(HOTSPOT_TOPDIR)/src/$(MODULE)/share/classes
|
||||
@ -81,23 +81,24 @@ PROCESSOR_JARS := \
|
||||
PROCESSOR_PATH := $(call PathList, $(PROCESSOR_JARS))
|
||||
|
||||
ADD_EXPORTS := \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.aarch64=ALL-UNNAMED \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.amd64=ALL-UNNAMED \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.code=ALL-UNNAMED \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.code.site=ALL-UNNAMED \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.code.stack=ALL-UNNAMED \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.common=ALL-UNNAMED \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.hotspot=ALL-UNNAMED \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.hotspot.aarch64=ALL-UNNAMED \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.hotspot.amd64=ALL-UNNAMED \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.hotspot.events=ALL-UNNAMED \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.hotspot.sparc=ALL-UNNAMED \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.hotspotvmconfig=ALL-UNNAMED \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.inittimer=ALL-UNNAMED \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.meta=ALL-UNNAMED \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.runtime=ALL-UNNAMED \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.services=ALL-UNNAMED \
|
||||
--add-exports jdk.vm.ci/jdk.vm.ci.sparc=ALL-UNNAMED \
|
||||
--add-modules jdk.internal.vm.ci \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.aarch64=ALL-UNNAMED \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.amd64=ALL-UNNAMED \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.code=ALL-UNNAMED \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.code.site=ALL-UNNAMED \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.code.stack=ALL-UNNAMED \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.common=ALL-UNNAMED \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.hotspot=ALL-UNNAMED \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.hotspot.aarch64=ALL-UNNAMED \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.hotspot.amd64=ALL-UNNAMED \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.hotspot.events=ALL-UNNAMED \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.hotspot.sparc=ALL-UNNAMED \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.hotspotvmconfig=ALL-UNNAMED \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.inittimer=ALL-UNNAMED \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.meta=ALL-UNNAMED \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.runtime=ALL-UNNAMED \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.services=ALL-UNNAMED \
|
||||
--add-exports jdk.internal.vm.ci/jdk.vm.ci.sparc=ALL-UNNAMED \
|
||||
#
|
||||
|
||||
$(GENSRC_DIR)/_gensrc_proc_done: $(PROC_SRCS) $(PROCESSOR_JARS)
|
||||
@ -138,7 +139,7 @@ $(GENSRC_DIR)/module-info.java.extra: $(GENSRC_DIR)/_gensrc_proc_done
|
||||
$(ECHO) "uses org.graalvm.compiler.options.OptionDescriptors;" >> $@; \
|
||||
$(ECHO) "provides org.graalvm.compiler.options.OptionDescriptors with" >> $@; \
|
||||
for i in $$($(FIND) $(GENSRC_DIR) -name '*_OptionDescriptors.java'); do \
|
||||
c=$$($(ECHO) $$i | $(SED) 's:.*/jdk\.vm\.compiler/\(.*\)\.java:\1:' | $(TR) '/' '.'); \
|
||||
c=$$($(ECHO) $$i | $(SED) 's:.*/jdk\.internal\.vm\.compiler/\(.*\)\.java:\1:' | $(TR) '/' '.'); \
|
||||
$(ECHO) " $$c," >> $@; \
|
||||
done; \
|
||||
$(ECHO) " ;" >> $@;
|
@ -112,8 +112,10 @@ ifeq ($(OPENJDK_TARGET_OS), windows)
|
||||
-relativeSrcInclude src \
|
||||
-hidePath .hg \
|
||||
-hidePath .jcheck \
|
||||
-hidePath jdk.aot \
|
||||
-hidePath jdk.hotspot.agent \
|
||||
-hidePath jdk.vm.ci \
|
||||
-hidePath jdk.internal.vm.ci \
|
||||
-hidePath jdk.internal.vm.compiler \
|
||||
-hidePath jdk.jfr \
|
||||
-compiler VC10 \
|
||||
-jdkTargetRoot $(call FixPath, $(JDK_OUTPUTDIR)) \
|
||||
|
@ -118,6 +118,12 @@ ifeq ($(OPENJDK_TARGET_CPU), x86_64)
|
||||
OPENJDK_TARGET_CPU_VM_VERSION := amd64
|
||||
else ifeq ($(OPENJDK_TARGET_CPU), sparcv9)
|
||||
OPENJDK_TARGET_CPU_VM_VERSION := sparc
|
||||
else ifeq ($(HOTSPOT_TARGET_CPU_ARCH), arm)
|
||||
ifeq ($(OPENJDK_TARGET_CPU), aarch64)
|
||||
# This sets the Oracle Aarch64 port to use arm64
|
||||
# while the original Aarch64 port uses aarch64
|
||||
OPENJDK_TARGET_CPU_VM_VERSION := arm64
|
||||
endif
|
||||
else
|
||||
OPENJDK_TARGET_CPU_VM_VERSION := $(OPENJDK_TARGET_CPU)
|
||||
endif
|
||||
|
@ -1,5 +1,5 @@
|
||||
#
|
||||
# Copyright (c) 2015, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
# Copyright (c) 2015, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
#
|
||||
# This code is free software; you can redistribute it and/or modify it
|
||||
@ -48,6 +48,8 @@ BUILD_HOTSPOT_JTREG_NATIVE_SRC := \
|
||||
$(HOTSPOT_TOPDIR)/test/runtime/jni/PrivateInterfaceMethods \
|
||||
$(HOTSPOT_TOPDIR)/test/runtime/jni/ToStringInInterfaceTest \
|
||||
$(HOTSPOT_TOPDIR)/test/runtime/jni/CalleeSavedRegisters \
|
||||
$(HOTSPOT_TOPDIR)/test/runtime/jni/CallWithJNIWeak \
|
||||
$(HOTSPOT_TOPDIR)/test/runtime/jni/ReturnJNIWeak \
|
||||
$(HOTSPOT_TOPDIR)/test/runtime/modules/getModuleJNI \
|
||||
$(HOTSPOT_TOPDIR)/test/runtime/SameObject \
|
||||
$(HOTSPOT_TOPDIR)/test/runtime/BoolReturn \
|
||||
|
@ -15501,7 +15501,7 @@ instruct string_compareLU(iRegP_R1 str1, iRegI_R2 cnt1, iRegP_R3 str2, iRegI_R4
|
||||
%}
|
||||
|
||||
instruct string_indexofUU(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2, iRegI_R2 cnt2,
|
||||
iRegI_R0 result, iRegI tmp1, iRegI tmp2, iRegI tmp3, iRegI tmp4, rFlagsReg cr)
|
||||
iRegI_R0 result, iRegINoSp tmp1, iRegINoSp tmp2, iRegINoSp tmp3, iRegINoSp tmp4, rFlagsReg cr)
|
||||
%{
|
||||
predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::UU);
|
||||
match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 cnt2)));
|
||||
@ -15520,7 +15520,7 @@ instruct string_indexofUU(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2, iRegI_R2
|
||||
%}
|
||||
|
||||
instruct string_indexofLL(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2, iRegI_R2 cnt2,
|
||||
iRegI_R0 result, iRegI tmp1, iRegI tmp2, iRegI tmp3, iRegI tmp4, rFlagsReg cr)
|
||||
iRegI_R0 result, iRegINoSp tmp1, iRegINoSp tmp2, iRegINoSp tmp3, iRegINoSp tmp4, rFlagsReg cr)
|
||||
%{
|
||||
predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::LL);
|
||||
match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 cnt2)));
|
||||
@ -15539,7 +15539,7 @@ instruct string_indexofLL(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2, iRegI_R2
|
||||
%}
|
||||
|
||||
instruct string_indexofUL(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2, iRegI_R2 cnt2,
|
||||
iRegI_R0 result, iRegI tmp1, iRegI tmp2, iRegI tmp3, iRegI tmp4, rFlagsReg cr)
|
||||
iRegI_R0 result, iRegINoSp tmp1, iRegINoSp tmp2, iRegINoSp tmp3, iRegINoSp tmp4, rFlagsReg cr)
|
||||
%{
|
||||
predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::UL);
|
||||
match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 cnt2)));
|
||||
@ -15558,7 +15558,7 @@ instruct string_indexofUL(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2, iRegI_R2
|
||||
%}
|
||||
|
||||
instruct string_indexofLU(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2, iRegI_R2 cnt2,
|
||||
iRegI_R0 result, iRegI tmp1, iRegI tmp2, iRegI tmp3, iRegI tmp4, rFlagsReg cr)
|
||||
iRegI_R0 result, iRegINoSp tmp1, iRegINoSp tmp2, iRegINoSp tmp3, iRegINoSp tmp4, rFlagsReg cr)
|
||||
%{
|
||||
predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::LU);
|
||||
match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 cnt2)));
|
||||
@ -15577,8 +15577,8 @@ instruct string_indexofLU(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2, iRegI_R2
|
||||
%}
|
||||
|
||||
instruct string_indexof_conUU(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2,
|
||||
immI_le_4 int_cnt2, iRegI_R0 result, iRegI tmp1, iRegI tmp2,
|
||||
iRegI tmp3, iRegI tmp4, rFlagsReg cr)
|
||||
immI_le_4 int_cnt2, iRegI_R0 result, iRegINoSp tmp1, iRegINoSp tmp2,
|
||||
iRegINoSp tmp3, iRegINoSp tmp4, rFlagsReg cr)
|
||||
%{
|
||||
predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::UU);
|
||||
match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 int_cnt2)));
|
||||
@ -15598,8 +15598,8 @@ instruct string_indexof_conUU(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2,
|
||||
%}
|
||||
|
||||
instruct string_indexof_conLL(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2,
|
||||
immI_le_4 int_cnt2, iRegI_R0 result, iRegI tmp1, iRegI tmp2,
|
||||
iRegI tmp3, iRegI tmp4, rFlagsReg cr)
|
||||
immI_le_4 int_cnt2, iRegI_R0 result, iRegINoSp tmp1, iRegINoSp tmp2,
|
||||
iRegINoSp tmp3, iRegINoSp tmp4, rFlagsReg cr)
|
||||
%{
|
||||
predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::LL);
|
||||
match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 int_cnt2)));
|
||||
@ -15619,8 +15619,8 @@ instruct string_indexof_conLL(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2,
|
||||
%}
|
||||
|
||||
instruct string_indexof_conUL(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2,
|
||||
immI_1 int_cnt2, iRegI_R0 result, iRegI tmp1, iRegI tmp2,
|
||||
iRegI tmp3, iRegI tmp4, rFlagsReg cr)
|
||||
immI_1 int_cnt2, iRegI_R0 result, iRegINoSp tmp1, iRegINoSp tmp2,
|
||||
iRegINoSp tmp3, iRegINoSp tmp4, rFlagsReg cr)
|
||||
%{
|
||||
predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::UL);
|
||||
match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 int_cnt2)));
|
||||
@ -15640,8 +15640,8 @@ instruct string_indexof_conUL(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2,
|
||||
%}
|
||||
|
||||
instruct string_indexof_conLU(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2,
|
||||
immI_1 int_cnt2, iRegI_R0 result, iRegI tmp1, iRegI tmp2,
|
||||
iRegI tmp3, iRegI tmp4, rFlagsReg cr)
|
||||
immI_1 int_cnt2, iRegI_R0 result, iRegINoSp tmp1, iRegINoSp tmp2,
|
||||
iRegINoSp tmp3, iRegINoSp tmp4, rFlagsReg cr)
|
||||
%{
|
||||
predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::LU);
|
||||
match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 int_cnt2)));
|
||||
@ -15661,8 +15661,8 @@ instruct string_indexof_conLU(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2,
|
||||
%}
|
||||
|
||||
instruct string_indexofU_char(iRegP_R1 str1, iRegI_R2 cnt1, iRegI_R3 ch,
|
||||
iRegI_R0 result, iRegI tmp1, iRegI tmp2,
|
||||
iRegI tmp3, rFlagsReg cr)
|
||||
iRegI_R0 result, iRegINoSp tmp1, iRegINoSp tmp2,
|
||||
iRegINoSp tmp3, rFlagsReg cr)
|
||||
%{
|
||||
match(Set result (StrIndexOfChar (Binary str1 cnt1) ch));
|
||||
effect(USE_KILL str1, USE_KILL cnt1, USE_KILL ch,
|
||||
@ -16101,7 +16101,7 @@ instruct replicate2D(vecX dst, vRegD src)
|
||||
|
||||
// ====================REDUCTION ARITHMETIC====================================
|
||||
|
||||
instruct reduce_add2I(iRegINoSp dst, iRegIorL2I src1, vecD src2, iRegI tmp, iRegI tmp2)
|
||||
instruct reduce_add2I(iRegINoSp dst, iRegIorL2I src1, vecD src2, iRegINoSp tmp, iRegINoSp tmp2)
|
||||
%{
|
||||
match(Set dst (AddReductionVI src1 src2));
|
||||
ins_cost(INSN_COST);
|
||||
@ -16120,7 +16120,7 @@ instruct reduce_add2I(iRegINoSp dst, iRegIorL2I src1, vecD src2, iRegI tmp, iReg
|
||||
ins_pipe(pipe_class_default);
|
||||
%}
|
||||
|
||||
instruct reduce_add4I(iRegINoSp dst, iRegIorL2I src1, vecX src2, vecX tmp, iRegI tmp2)
|
||||
instruct reduce_add4I(iRegINoSp dst, iRegIorL2I src1, vecX src2, vecX tmp, iRegINoSp tmp2)
|
||||
%{
|
||||
match(Set dst (AddReductionVI src1 src2));
|
||||
ins_cost(INSN_COST);
|
||||
@ -16138,7 +16138,7 @@ instruct reduce_add4I(iRegINoSp dst, iRegIorL2I src1, vecX src2, vecX tmp, iRegI
|
||||
ins_pipe(pipe_class_default);
|
||||
%}
|
||||
|
||||
instruct reduce_mul2I(iRegINoSp dst, iRegIorL2I src1, vecD src2, iRegI tmp)
|
||||
instruct reduce_mul2I(iRegINoSp dst, iRegIorL2I src1, vecD src2, iRegINoSp tmp)
|
||||
%{
|
||||
match(Set dst (MulReductionVI src1 src2));
|
||||
ins_cost(INSN_COST);
|
||||
@ -16157,7 +16157,7 @@ instruct reduce_mul2I(iRegINoSp dst, iRegIorL2I src1, vecD src2, iRegI tmp)
|
||||
ins_pipe(pipe_class_default);
|
||||
%}
|
||||
|
||||
instruct reduce_mul4I(iRegINoSp dst, iRegIorL2I src1, vecX src2, vecX tmp, iRegI tmp2)
|
||||
instruct reduce_mul4I(iRegINoSp dst, iRegIorL2I src1, vecX src2, vecX tmp, iRegINoSp tmp2)
|
||||
%{
|
||||
match(Set dst (MulReductionVI src1 src2));
|
||||
ins_cost(INSN_COST);
|
||||
|
@ -1,8 +1,7 @@
|
||||
/*
|
||||
* Copyright (c) 1997, 2012, Oracle and/or its affiliates. All rights All rights reserved.
|
||||
* Copyright (c) 1997, 2012, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2014, Red Hat Inc. All rights reserved.
|
||||
* reserved. DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE
|
||||
* HEADER.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
@ -21,7 +20,6 @@
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
|
@ -1922,12 +1922,17 @@ void LIR_Assembler::comp_op(LIR_Condition condition, LIR_Opr opr1, LIR_Opr opr2,
|
||||
}
|
||||
|
||||
if (opr2->is_constant()) {
|
||||
bool is_32bit = false; // width of register operand
|
||||
jlong imm;
|
||||
|
||||
switch(opr2->type()) {
|
||||
case T_INT:
|
||||
imm = opr2->as_constant_ptr()->as_jint();
|
||||
is_32bit = true;
|
||||
break;
|
||||
case T_LONG:
|
||||
imm = opr2->as_constant_ptr()->as_jlong();
|
||||
break;
|
||||
case T_INT:
|
||||
case T_ADDRESS:
|
||||
imm = opr2->as_constant_ptr()->as_jint();
|
||||
break;
|
||||
@ -1942,14 +1947,14 @@ void LIR_Assembler::comp_op(LIR_Condition condition, LIR_Opr opr1, LIR_Opr opr2,
|
||||
}
|
||||
|
||||
if (Assembler::operand_valid_for_add_sub_immediate(imm)) {
|
||||
if (type2aelembytes(opr1->type()) <= 4)
|
||||
if (is_32bit)
|
||||
__ cmpw(reg1, imm);
|
||||
else
|
||||
__ cmp(reg1, imm);
|
||||
return;
|
||||
} else {
|
||||
__ mov(rscratch1, imm);
|
||||
if (type2aelembytes(opr1->type()) <= 4)
|
||||
if (is_32bit)
|
||||
__ cmpw(reg1, rscratch1);
|
||||
else
|
||||
__ cmp(reg1, rscratch1);
|
||||
|
@ -1221,12 +1221,19 @@ void LIRGenerator::do_CheckCast(CheckCast* x) {
|
||||
obj.load_item();
|
||||
|
||||
// info for exceptions
|
||||
CodeEmitInfo* info_for_exception = state_for(x);
|
||||
CodeEmitInfo* info_for_exception =
|
||||
(x->needs_exception_state() ? state_for(x) :
|
||||
state_for(x, x->state_before(), true /*ignore_xhandler*/));
|
||||
|
||||
CodeStub* stub;
|
||||
if (x->is_incompatible_class_change_check()) {
|
||||
assert(patching_info == NULL, "can't patch this");
|
||||
stub = new SimpleExceptionStub(Runtime1::throw_incompatible_class_change_error_id, LIR_OprFact::illegalOpr, info_for_exception);
|
||||
} else if (x->is_invokespecial_receiver_check()) {
|
||||
assert(patching_info == NULL, "can't patch this");
|
||||
stub = new DeoptimizeStub(info_for_exception,
|
||||
Deoptimization::Reason_class_check,
|
||||
Deoptimization::Action_none);
|
||||
} else {
|
||||
stub = new SimpleExceptionStub(Runtime1::throw_class_cast_exception_id, obj.result(), info_for_exception);
|
||||
}
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2004, 2010, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2004, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2014, Red Hat Inc. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
@ -82,6 +82,11 @@ address JNI_FastGetField::generate_fast_get_int_field0(BasicType type) {
|
||||
__ eor(robj, robj, rcounter); // obj, since
|
||||
// robj ^ rcounter ^ rcounter == robj
|
||||
// robj is address dependent on rcounter.
|
||||
|
||||
// If mask changes we need to ensure that the inverse is still encodable as an immediate
|
||||
STATIC_ASSERT(JNIHandles::weak_tag_mask == 1);
|
||||
__ andr(robj, robj, ~JNIHandles::weak_tag_mask);
|
||||
|
||||
__ ldr(robj, Address(robj, 0)); // *obj
|
||||
__ lsr(roffset, c_rarg2, 2); // offset
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2003, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2014, 2015, Red Hat Inc. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
@ -2052,13 +2052,31 @@ nmethod* SharedRuntime::generate_native_wrapper(MacroAssembler* masm,
|
||||
|
||||
__ reset_last_Java_frame(false);
|
||||
|
||||
// Unpack oop result
|
||||
// Unbox oop result, e.g. JNIHandles::resolve result.
|
||||
if (ret_type == T_OBJECT || ret_type == T_ARRAY) {
|
||||
Label L;
|
||||
__ cbz(r0, L);
|
||||
__ ldr(r0, Address(r0, 0));
|
||||
__ bind(L);
|
||||
__ verify_oop(r0);
|
||||
Label done, not_weak;
|
||||
__ cbz(r0, done); // Use NULL as-is.
|
||||
STATIC_ASSERT(JNIHandles::weak_tag_mask == 1u);
|
||||
__ tbz(r0, 0, not_weak); // Test for jweak tag.
|
||||
// Resolve jweak.
|
||||
__ ldr(r0, Address(r0, -JNIHandles::weak_tag_value));
|
||||
__ verify_oop(r0);
|
||||
#if INCLUDE_ALL_GCS
|
||||
if (UseG1GC) {
|
||||
__ g1_write_barrier_pre(noreg /* obj */,
|
||||
r0 /* pre_val */,
|
||||
rthread /* thread */,
|
||||
rscratch1 /* tmp */,
|
||||
true /* tosca_live */,
|
||||
true /* expand_call */);
|
||||
}
|
||||
#endif // INCLUDE_ALL_GCS
|
||||
__ b(done);
|
||||
__ bind(not_weak);
|
||||
// Resolve (untagged) jobject.
|
||||
__ ldr(r0, Address(r0, 0));
|
||||
__ verify_oop(r0);
|
||||
__ bind(done);
|
||||
}
|
||||
|
||||
if (CheckJNICalls) {
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2003, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2014, Red Hat Inc. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
@ -1399,13 +1399,32 @@ address TemplateInterpreterGenerator::generate_native_entry(bool synchronized) {
|
||||
// and result handler will pick it up
|
||||
|
||||
{
|
||||
Label no_oop, store_result;
|
||||
Label no_oop, not_weak, store_result;
|
||||
__ adr(t, ExternalAddress(AbstractInterpreter::result_handler(T_OBJECT)));
|
||||
__ cmp(t, result_handler);
|
||||
__ br(Assembler::NE, no_oop);
|
||||
// retrieve result
|
||||
// Unbox oop result, e.g. JNIHandles::resolve result.
|
||||
__ pop(ltos);
|
||||
__ cbz(r0, store_result);
|
||||
__ cbz(r0, store_result); // Use NULL as-is.
|
||||
STATIC_ASSERT(JNIHandles::weak_tag_mask == 1u);
|
||||
__ tbz(r0, 0, not_weak); // Test for jweak tag.
|
||||
// Resolve jweak.
|
||||
__ ldr(r0, Address(r0, -JNIHandles::weak_tag_value));
|
||||
#if INCLUDE_ALL_GCS
|
||||
if (UseG1GC) {
|
||||
__ enter(); // Barrier may call runtime.
|
||||
__ g1_write_barrier_pre(noreg /* obj */,
|
||||
r0 /* pre_val */,
|
||||
rthread /* thread */,
|
||||
t /* tmp */,
|
||||
true /* tosca_live */,
|
||||
true /* expand_call */);
|
||||
__ leave();
|
||||
}
|
||||
#endif // INCLUDE_ALL_GCS
|
||||
__ b(store_result);
|
||||
__ bind(not_weak);
|
||||
// Resolve (untagged) jobject.
|
||||
__ ldr(r0, Address(r0, 0));
|
||||
__ bind(store_result);
|
||||
__ str(r0, Address(rfp, frame::interpreter_frame_oop_temp_offset*wordSize));
|
||||
|
@ -1453,10 +1453,11 @@ void LIR_Assembler::emit_opTypeCheck(LIR_OpTypeCheck* op) {
|
||||
ciKlass* k = op->klass();
|
||||
assert_different_registers(res, k_RInfo, klass_RInfo, Rtemp);
|
||||
|
||||
if (stub->is_simple_exception_stub()) {
|
||||
// TODO: ARM - Late binding is used to prevent confusion of register allocator
|
||||
assert(stub->is_exception_throw_stub(), "must be");
|
||||
((SimpleExceptionStub*)stub)->set_obj(op->result_opr());
|
||||
|
||||
}
|
||||
ciMethodData* md;
|
||||
ciProfileData* data;
|
||||
int mdo_offset_bias = 0;
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2008, 2015, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2008, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -1412,12 +1412,20 @@ void LIRGenerator::do_CheckCast(CheckCast* x) {
|
||||
|
||||
obj.load_item();
|
||||
|
||||
CodeEmitInfo* info_for_exception = state_for(x);
|
||||
CodeEmitInfo* info_for_exception =
|
||||
(x->needs_exception_state() ? state_for(x) :
|
||||
state_for(x, x->state_before(), true /*ignore_xhandler*/));
|
||||
|
||||
CodeStub* stub;
|
||||
if (x->is_incompatible_class_change_check()) {
|
||||
assert(patching_info == NULL, "can't patch this");
|
||||
stub = new SimpleExceptionStub(Runtime1::throw_incompatible_class_change_error_id,
|
||||
LIR_OprFact::illegalOpr, info_for_exception);
|
||||
} else if (x->is_invokespecial_receiver_check()) {
|
||||
assert(patching_info == NULL, "can't patch this");
|
||||
stub = new DeoptimizeStub(info_for_exception,
|
||||
Deoptimization::Reason_class_check,
|
||||
Deoptimization::Action_none);
|
||||
} else {
|
||||
stub = new SimpleExceptionStub(Runtime1::throw_class_cast_exception_id,
|
||||
LIR_OprFact::illegalOpr, info_for_exception);
|
||||
|
@ -618,7 +618,7 @@ OopMapSet* Runtime1::generate_code_for(StubID id, StubAssembler* sasm) {
|
||||
Address buffer(Rthread, in_bytes(JavaThread::dirty_card_queue_offset() +
|
||||
DirtyCardQueue::byte_offset_of_buf()));
|
||||
|
||||
AddressLiteral cardtable((address)ct->byte_map_base);
|
||||
AddressLiteral cardtable((address)ct->byte_map_base, relocInfo::none);
|
||||
assert(sizeof(*ct->byte_map_base) == sizeof(jbyte), "adjust this code");
|
||||
|
||||
// save at least the registers that need saving if the runtime is called
|
||||
@ -645,7 +645,7 @@ OopMapSet* Runtime1::generate_code_for(StubID id, StubAssembler* sasm) {
|
||||
// Note: there is a comment in x86 code about not using
|
||||
// ExternalAddress / lea, due to relocation not working
|
||||
// properly for that address. Should be OK for arm, where we
|
||||
// explicitly specify that 'cartable' has a relocInfo::none
|
||||
// explicitly specify that 'cardtable' has a relocInfo::none
|
||||
// type.
|
||||
__ lea(r_card_base_1, cardtable);
|
||||
__ add(r_card_addr_0, r_card_base_1, AsmOperand(r_obj_0, lsr, CardTableModRefBS::card_shift));
|
||||
|
@ -85,17 +85,17 @@ address CompiledStaticCall::emit_to_interp_stub(CodeBuffer &cbuf, address mark)
|
||||
}
|
||||
#undef __
|
||||
|
||||
// size of C2 call stub, compiled java to interpretor
|
||||
int CompiledStaticCall::to_interp_stub_size() {
|
||||
return 8 * NativeInstruction::instruction_size;
|
||||
}
|
||||
|
||||
// Relocation entries for call stub, compiled java to interpreter.
|
||||
int CompiledStaticCall::reloc_to_interp_stub() {
|
||||
return 10; // 4 in emit_to_interp_stub + 1 in Java_Static_Call
|
||||
}
|
||||
#endif // COMPILER2 || JVMCI
|
||||
|
||||
// size of C2 call stub, compiled java to interpretor
|
||||
int CompiledStaticCall::to_interp_stub_size() {
|
||||
return 8 * NativeInstruction::instruction_size;
|
||||
}
|
||||
|
||||
void CompiledDirectStaticCall::set_to_interpreted(const methodHandle& callee, address entry) {
|
||||
address stub = find_stub(/*is_aot*/ false);
|
||||
guarantee(stub != NULL, "stub not found");
|
||||
@ -125,6 +125,8 @@ void CompiledDirectStaticCall::set_to_interpreted(const methodHandle& callee, ad
|
||||
method_holder->set_data((intptr_t)callee());
|
||||
jump->set_jump_destination(entry);
|
||||
|
||||
ICache::invalidate_range(stub, to_interp_stub_size());
|
||||
|
||||
// Update jump to call.
|
||||
set_destination_mt_safe(stub);
|
||||
}
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2008, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2008, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -476,185 +476,6 @@ void InterpreterMacroAssembler::set_card(Register card_table_base, Address card_
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
#if INCLUDE_ALL_GCS
|
||||
|
||||
// G1 pre-barrier.
|
||||
// Blows all volatile registers (R0-R3 on 32-bit ARM, R0-R18 on AArch64, Rtemp, LR).
|
||||
// If store_addr != noreg, then previous value is loaded from [store_addr];
|
||||
// in such case store_addr and new_val registers are preserved;
|
||||
// otherwise pre_val register is preserved.
|
||||
void InterpreterMacroAssembler::g1_write_barrier_pre(Register store_addr,
|
||||
Register new_val,
|
||||
Register pre_val,
|
||||
Register tmp1,
|
||||
Register tmp2) {
|
||||
Label done;
|
||||
Label runtime;
|
||||
|
||||
if (store_addr != noreg) {
|
||||
assert_different_registers(store_addr, new_val, pre_val, tmp1, tmp2, noreg);
|
||||
} else {
|
||||
assert (new_val == noreg, "should be");
|
||||
assert_different_registers(pre_val, tmp1, tmp2, noreg);
|
||||
}
|
||||
|
||||
Address in_progress(Rthread, in_bytes(JavaThread::satb_mark_queue_offset() +
|
||||
SATBMarkQueue::byte_offset_of_active()));
|
||||
Address index(Rthread, in_bytes(JavaThread::satb_mark_queue_offset() +
|
||||
SATBMarkQueue::byte_offset_of_index()));
|
||||
Address buffer(Rthread, in_bytes(JavaThread::satb_mark_queue_offset() +
|
||||
SATBMarkQueue::byte_offset_of_buf()));
|
||||
|
||||
// Is marking active?
|
||||
assert(in_bytes(SATBMarkQueue::byte_width_of_active()) == 1, "adjust this code");
|
||||
ldrb(tmp1, in_progress);
|
||||
cbz(tmp1, done);
|
||||
|
||||
// Do we need to load the previous value?
|
||||
if (store_addr != noreg) {
|
||||
load_heap_oop(pre_val, Address(store_addr, 0));
|
||||
}
|
||||
|
||||
// Is the previous value null?
|
||||
cbz(pre_val, done);
|
||||
|
||||
// Can we store original value in the thread's buffer?
|
||||
// Is index == 0?
|
||||
// (The index field is typed as size_t.)
|
||||
|
||||
ldr(tmp1, index); // tmp1 := *index_adr
|
||||
ldr(tmp2, buffer);
|
||||
|
||||
subs(tmp1, tmp1, wordSize); // tmp1 := tmp1 - wordSize
|
||||
b(runtime, lt); // If negative, goto runtime
|
||||
|
||||
str(tmp1, index); // *index_adr := tmp1
|
||||
|
||||
// Record the previous value
|
||||
str(pre_val, Address(tmp2, tmp1));
|
||||
b(done);
|
||||
|
||||
bind(runtime);
|
||||
|
||||
// save the live input values
|
||||
#ifdef AARCH64
|
||||
if (store_addr != noreg) {
|
||||
raw_push(store_addr, new_val);
|
||||
} else {
|
||||
raw_push(pre_val, ZR);
|
||||
}
|
||||
#else
|
||||
if (store_addr != noreg) {
|
||||
// avoid raw_push to support any ordering of store_addr and new_val
|
||||
push(RegisterSet(store_addr) | RegisterSet(new_val));
|
||||
} else {
|
||||
push(pre_val);
|
||||
}
|
||||
#endif // AARCH64
|
||||
|
||||
if (pre_val != R0) {
|
||||
mov(R0, pre_val);
|
||||
}
|
||||
mov(R1, Rthread);
|
||||
|
||||
call_VM_leaf(CAST_FROM_FN_PTR(address, SharedRuntime::g1_wb_pre), R0, R1);
|
||||
|
||||
#ifdef AARCH64
|
||||
if (store_addr != noreg) {
|
||||
raw_pop(store_addr, new_val);
|
||||
} else {
|
||||
raw_pop(pre_val, ZR);
|
||||
}
|
||||
#else
|
||||
if (store_addr != noreg) {
|
||||
pop(RegisterSet(store_addr) | RegisterSet(new_val));
|
||||
} else {
|
||||
pop(pre_val);
|
||||
}
|
||||
#endif // AARCH64
|
||||
|
||||
bind(done);
|
||||
}
|
||||
|
||||
// G1 post-barrier.
|
||||
// Blows all volatile registers (R0-R3 on 32-bit ARM, R0-R18 on AArch64, Rtemp, LR).
|
||||
void InterpreterMacroAssembler::g1_write_barrier_post(Register store_addr,
|
||||
Register new_val,
|
||||
Register tmp1,
|
||||
Register tmp2,
|
||||
Register tmp3) {
|
||||
|
||||
Address queue_index(Rthread, in_bytes(JavaThread::dirty_card_queue_offset() +
|
||||
DirtyCardQueue::byte_offset_of_index()));
|
||||
Address buffer(Rthread, in_bytes(JavaThread::dirty_card_queue_offset() +
|
||||
DirtyCardQueue::byte_offset_of_buf()));
|
||||
|
||||
BarrierSet* bs = Universe::heap()->barrier_set();
|
||||
CardTableModRefBS* ct = (CardTableModRefBS*)bs;
|
||||
Label done;
|
||||
Label runtime;
|
||||
|
||||
// Does store cross heap regions?
|
||||
|
||||
eor(tmp1, store_addr, new_val);
|
||||
#ifdef AARCH64
|
||||
logical_shift_right(tmp1, tmp1, HeapRegion::LogOfHRGrainBytes);
|
||||
cbz(tmp1, done);
|
||||
#else
|
||||
movs(tmp1, AsmOperand(tmp1, lsr, HeapRegion::LogOfHRGrainBytes));
|
||||
b(done, eq);
|
||||
#endif
|
||||
|
||||
// crosses regions, storing NULL?
|
||||
|
||||
cbz(new_val, done);
|
||||
|
||||
// storing region crossing non-NULL, is card already dirty?
|
||||
const Register card_addr = tmp1;
|
||||
assert(sizeof(*ct->byte_map_base) == sizeof(jbyte), "adjust this code");
|
||||
|
||||
mov_address(tmp2, (address)ct->byte_map_base, symbolic_Relocation::card_table_reference);
|
||||
add(card_addr, tmp2, AsmOperand(store_addr, lsr, CardTableModRefBS::card_shift));
|
||||
|
||||
ldrb(tmp2, Address(card_addr));
|
||||
cmp(tmp2, (int)G1SATBCardTableModRefBS::g1_young_card_val());
|
||||
b(done, eq);
|
||||
|
||||
membar(MacroAssembler::Membar_mask_bits(MacroAssembler::StoreLoad), tmp2);
|
||||
|
||||
assert(CardTableModRefBS::dirty_card_val() == 0, "adjust this code");
|
||||
ldrb(tmp2, Address(card_addr));
|
||||
cbz(tmp2, done);
|
||||
|
||||
// storing a region crossing, non-NULL oop, card is clean.
|
||||
// dirty card and log.
|
||||
|
||||
strb(zero_register(tmp2), Address(card_addr));
|
||||
|
||||
ldr(tmp2, queue_index);
|
||||
ldr(tmp3, buffer);
|
||||
|
||||
subs(tmp2, tmp2, wordSize);
|
||||
b(runtime, lt); // go to runtime if now negative
|
||||
|
||||
str(tmp2, queue_index);
|
||||
|
||||
str(card_addr, Address(tmp3, tmp2));
|
||||
b(done);
|
||||
|
||||
bind(runtime);
|
||||
|
||||
if (card_addr != R0) {
|
||||
mov(R0, card_addr);
|
||||
}
|
||||
mov(R1, Rthread);
|
||||
call_VM_leaf(CAST_FROM_FN_PTR(address, SharedRuntime::g1_wb_post), R0, R1);
|
||||
|
||||
bind(done);
|
||||
}
|
||||
|
||||
#endif // INCLUDE_ALL_GCS
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
// Java Expression Stack
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2008, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2008, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -146,27 +146,6 @@ class InterpreterMacroAssembler: public MacroAssembler {
|
||||
|
||||
void set_card(Register card_table_base, Address card_table_addr, Register tmp);
|
||||
|
||||
#if INCLUDE_ALL_GCS
|
||||
// G1 pre-barrier.
|
||||
// Blows all volatile registers (R0-R3 on 32-bit ARM, R0-R18 on AArch64, Rtemp, LR).
|
||||
// If store_addr != noreg, then previous value is loaded from [store_addr];
|
||||
// in such case store_addr and new_val registers are preserved;
|
||||
// otherwise pre_val register is preserved.
|
||||
void g1_write_barrier_pre(Register store_addr,
|
||||
Register new_val,
|
||||
Register pre_val,
|
||||
Register tmp1,
|
||||
Register tmp2);
|
||||
|
||||
// G1 post-barrier.
|
||||
// Blows all volatile registers (R0-R3 on 32-bit ARM, R0-R18 on AArch64, Rtemp, LR).
|
||||
void g1_write_barrier_post(Register store_addr,
|
||||
Register new_val,
|
||||
Register tmp1,
|
||||
Register tmp2,
|
||||
Register tmp3);
|
||||
#endif // INCLUDE_ALL_GCS
|
||||
|
||||
void pop_ptr(Register r);
|
||||
void pop_i(Register r = R0_tos);
|
||||
#ifdef AARCH64
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2008, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2008, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -119,6 +119,14 @@ address JNI_FastGetField::generate_fast_get_int_field0(BasicType type) {
|
||||
__ ldr_s32(Rsafept_cnt, Address(Rsafepoint_counter_addr));
|
||||
__ tbnz(Rsafept_cnt, 0, slow_case);
|
||||
|
||||
#ifdef AARCH64
|
||||
// If mask changes we need to ensure that the inverse is still encodable as an immediate
|
||||
STATIC_ASSERT(JNIHandles::weak_tag_mask == 1);
|
||||
__ andr(R1, R1, ~JNIHandles::weak_tag_mask);
|
||||
#else
|
||||
__ bic(R1, R1, JNIHandles::weak_tag_mask);
|
||||
#endif
|
||||
|
||||
if (os::is_MP()) {
|
||||
// Address dependency restricts memory access ordering. It's cheaper than explicit LoadLoad barrier
|
||||
__ andr(Rtmp1, Rsafept_cnt, (unsigned)1);
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2008, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2008, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -2211,6 +2211,219 @@ void MacroAssembler::biased_locking_exit(Register obj_reg, Register tmp_reg, Lab
|
||||
b(done, eq);
|
||||
}
|
||||
|
||||
|
||||
void MacroAssembler::resolve_jobject(Register value,
|
||||
Register tmp1,
|
||||
Register tmp2) {
|
||||
assert_different_registers(value, tmp1, tmp2);
|
||||
Label done, not_weak;
|
||||
cbz(value, done); // Use NULL as-is.
|
||||
STATIC_ASSERT(JNIHandles::weak_tag_mask == 1u);
|
||||
tbz(value, 0, not_weak); // Test for jweak tag.
|
||||
// Resolve jweak.
|
||||
ldr(value, Address(value, -JNIHandles::weak_tag_value));
|
||||
verify_oop(value);
|
||||
#if INCLUDE_ALL_GCS
|
||||
if (UseG1GC) {
|
||||
g1_write_barrier_pre(noreg, // store_addr
|
||||
noreg, // new_val
|
||||
value, // pre_val
|
||||
tmp1, // tmp1
|
||||
tmp2); // tmp2
|
||||
}
|
||||
#endif // INCLUDE_ALL_GCS
|
||||
b(done);
|
||||
bind(not_weak);
|
||||
// Resolve (untagged) jobject.
|
||||
ldr(value, Address(value));
|
||||
verify_oop(value);
|
||||
bind(done);
|
||||
}
|
||||
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#if INCLUDE_ALL_GCS
|
||||
|
||||
// G1 pre-barrier.
|
||||
// Blows all volatile registers (R0-R3 on 32-bit ARM, R0-R18 on AArch64, Rtemp, LR).
|
||||
// If store_addr != noreg, then previous value is loaded from [store_addr];
|
||||
// in such case store_addr and new_val registers are preserved;
|
||||
// otherwise pre_val register is preserved.
|
||||
void MacroAssembler::g1_write_barrier_pre(Register store_addr,
|
||||
Register new_val,
|
||||
Register pre_val,
|
||||
Register tmp1,
|
||||
Register tmp2) {
|
||||
Label done;
|
||||
Label runtime;
|
||||
|
||||
if (store_addr != noreg) {
|
||||
assert_different_registers(store_addr, new_val, pre_val, tmp1, tmp2, noreg);
|
||||
} else {
|
||||
assert (new_val == noreg, "should be");
|
||||
assert_different_registers(pre_val, tmp1, tmp2, noreg);
|
||||
}
|
||||
|
||||
Address in_progress(Rthread, in_bytes(JavaThread::satb_mark_queue_offset() +
|
||||
SATBMarkQueue::byte_offset_of_active()));
|
||||
Address index(Rthread, in_bytes(JavaThread::satb_mark_queue_offset() +
|
||||
SATBMarkQueue::byte_offset_of_index()));
|
||||
Address buffer(Rthread, in_bytes(JavaThread::satb_mark_queue_offset() +
|
||||
SATBMarkQueue::byte_offset_of_buf()));
|
||||
|
||||
// Is marking active?
|
||||
assert(in_bytes(SATBMarkQueue::byte_width_of_active()) == 1, "adjust this code");
|
||||
ldrb(tmp1, in_progress);
|
||||
cbz(tmp1, done);
|
||||
|
||||
// Do we need to load the previous value?
|
||||
if (store_addr != noreg) {
|
||||
load_heap_oop(pre_val, Address(store_addr, 0));
|
||||
}
|
||||
|
||||
// Is the previous value null?
|
||||
cbz(pre_val, done);
|
||||
|
||||
// Can we store original value in the thread's buffer?
|
||||
// Is index == 0?
|
||||
// (The index field is typed as size_t.)
|
||||
|
||||
ldr(tmp1, index); // tmp1 := *index_adr
|
||||
ldr(tmp2, buffer);
|
||||
|
||||
subs(tmp1, tmp1, wordSize); // tmp1 := tmp1 - wordSize
|
||||
b(runtime, lt); // If negative, goto runtime
|
||||
|
||||
str(tmp1, index); // *index_adr := tmp1
|
||||
|
||||
// Record the previous value
|
||||
str(pre_val, Address(tmp2, tmp1));
|
||||
b(done);
|
||||
|
||||
bind(runtime);
|
||||
|
||||
// save the live input values
|
||||
#ifdef AARCH64
|
||||
if (store_addr != noreg) {
|
||||
raw_push(store_addr, new_val);
|
||||
} else {
|
||||
raw_push(pre_val, ZR);
|
||||
}
|
||||
#else
|
||||
if (store_addr != noreg) {
|
||||
// avoid raw_push to support any ordering of store_addr and new_val
|
||||
push(RegisterSet(store_addr) | RegisterSet(new_val));
|
||||
} else {
|
||||
push(pre_val);
|
||||
}
|
||||
#endif // AARCH64
|
||||
|
||||
if (pre_val != R0) {
|
||||
mov(R0, pre_val);
|
||||
}
|
||||
mov(R1, Rthread);
|
||||
|
||||
call_VM_leaf(CAST_FROM_FN_PTR(address, SharedRuntime::g1_wb_pre), R0, R1);
|
||||
|
||||
#ifdef AARCH64
|
||||
if (store_addr != noreg) {
|
||||
raw_pop(store_addr, new_val);
|
||||
} else {
|
||||
raw_pop(pre_val, ZR);
|
||||
}
|
||||
#else
|
||||
if (store_addr != noreg) {
|
||||
pop(RegisterSet(store_addr) | RegisterSet(new_val));
|
||||
} else {
|
||||
pop(pre_val);
|
||||
}
|
||||
#endif // AARCH64
|
||||
|
||||
bind(done);
|
||||
}
|
||||
|
||||
// G1 post-barrier.
|
||||
// Blows all volatile registers (R0-R3 on 32-bit ARM, R0-R18 on AArch64, Rtemp, LR).
|
||||
void MacroAssembler::g1_write_barrier_post(Register store_addr,
|
||||
Register new_val,
|
||||
Register tmp1,
|
||||
Register tmp2,
|
||||
Register tmp3) {
|
||||
|
||||
Address queue_index(Rthread, in_bytes(JavaThread::dirty_card_queue_offset() +
|
||||
DirtyCardQueue::byte_offset_of_index()));
|
||||
Address buffer(Rthread, in_bytes(JavaThread::dirty_card_queue_offset() +
|
||||
DirtyCardQueue::byte_offset_of_buf()));
|
||||
|
||||
BarrierSet* bs = Universe::heap()->barrier_set();
|
||||
CardTableModRefBS* ct = (CardTableModRefBS*)bs;
|
||||
Label done;
|
||||
Label runtime;
|
||||
|
||||
// Does store cross heap regions?
|
||||
|
||||
eor(tmp1, store_addr, new_val);
|
||||
#ifdef AARCH64
|
||||
logical_shift_right(tmp1, tmp1, HeapRegion::LogOfHRGrainBytes);
|
||||
cbz(tmp1, done);
|
||||
#else
|
||||
movs(tmp1, AsmOperand(tmp1, lsr, HeapRegion::LogOfHRGrainBytes));
|
||||
b(done, eq);
|
||||
#endif
|
||||
|
||||
// crosses regions, storing NULL?
|
||||
|
||||
cbz(new_val, done);
|
||||
|
||||
// storing region crossing non-NULL, is card already dirty?
|
||||
const Register card_addr = tmp1;
|
||||
assert(sizeof(*ct->byte_map_base) == sizeof(jbyte), "adjust this code");
|
||||
|
||||
mov_address(tmp2, (address)ct->byte_map_base, symbolic_Relocation::card_table_reference);
|
||||
add(card_addr, tmp2, AsmOperand(store_addr, lsr, CardTableModRefBS::card_shift));
|
||||
|
||||
ldrb(tmp2, Address(card_addr));
|
||||
cmp(tmp2, (int)G1SATBCardTableModRefBS::g1_young_card_val());
|
||||
b(done, eq);
|
||||
|
||||
membar(MacroAssembler::Membar_mask_bits(MacroAssembler::StoreLoad), tmp2);
|
||||
|
||||
assert(CardTableModRefBS::dirty_card_val() == 0, "adjust this code");
|
||||
ldrb(tmp2, Address(card_addr));
|
||||
cbz(tmp2, done);
|
||||
|
||||
// storing a region crossing, non-NULL oop, card is clean.
|
||||
// dirty card and log.
|
||||
|
||||
strb(zero_register(tmp2), Address(card_addr));
|
||||
|
||||
ldr(tmp2, queue_index);
|
||||
ldr(tmp3, buffer);
|
||||
|
||||
subs(tmp2, tmp2, wordSize);
|
||||
b(runtime, lt); // go to runtime if now negative
|
||||
|
||||
str(tmp2, queue_index);
|
||||
|
||||
str(card_addr, Address(tmp3, tmp2));
|
||||
b(done);
|
||||
|
||||
bind(runtime);
|
||||
|
||||
if (card_addr != R0) {
|
||||
mov(R0, card_addr);
|
||||
}
|
||||
mov(R1, Rthread);
|
||||
call_VM_leaf(CAST_FROM_FN_PTR(address, SharedRuntime::g1_wb_post), R0, R1);
|
||||
|
||||
bind(done);
|
||||
}
|
||||
|
||||
#endif // INCLUDE_ALL_GCS
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#ifdef AARCH64
|
||||
|
||||
void MacroAssembler::load_sized_value(Register dst, Address src, size_t size_in_bytes, bool is_signed) {
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2008, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2008, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -402,6 +402,29 @@ public:
|
||||
void biased_locking_enter_with_cas(Register obj_reg, Register old_mark_reg, Register new_mark_reg,
|
||||
Register tmp, Label& slow_case, int* counter_addr);
|
||||
|
||||
void resolve_jobject(Register value, Register tmp1, Register tmp2);
|
||||
|
||||
#if INCLUDE_ALL_GCS
|
||||
// G1 pre-barrier.
|
||||
// Blows all volatile registers (R0-R3 on 32-bit ARM, R0-R18 on AArch64, Rtemp, LR).
|
||||
// If store_addr != noreg, then previous value is loaded from [store_addr];
|
||||
// in such case store_addr and new_val registers are preserved;
|
||||
// otherwise pre_val register is preserved.
|
||||
void g1_write_barrier_pre(Register store_addr,
|
||||
Register new_val,
|
||||
Register pre_val,
|
||||
Register tmp1,
|
||||
Register tmp2);
|
||||
|
||||
// G1 post-barrier.
|
||||
// Blows all volatile registers (R0-R3 on 32-bit ARM, R0-R18 on AArch64, Rtemp, LR).
|
||||
void g1_write_barrier_post(Register store_addr,
|
||||
Register new_val,
|
||||
Register tmp1,
|
||||
Register tmp2,
|
||||
Register tmp3);
|
||||
#endif // INCLUDE_ALL_GCS
|
||||
|
||||
#ifndef AARCH64
|
||||
void nop() {
|
||||
mov(R0, R0);
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2008, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2008, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -1732,14 +1732,7 @@ nmethod* SharedRuntime::generate_native_wrapper(MacroAssembler* masm,
|
||||
case T_FLOAT : // fall through
|
||||
case T_DOUBLE : /* nothing to do */ break;
|
||||
case T_OBJECT : // fall through
|
||||
case T_ARRAY : {
|
||||
Label L;
|
||||
__ cbz(R0, L);
|
||||
__ ldr(R0, Address(R0));
|
||||
__ verify_oop(R0);
|
||||
__ bind(L);
|
||||
break;
|
||||
}
|
||||
case T_ARRAY : break; // See JNIHandles::resolve below
|
||||
default:
|
||||
ShouldNotReachHere();
|
||||
}
|
||||
@ -1748,14 +1741,15 @@ nmethod* SharedRuntime::generate_native_wrapper(MacroAssembler* masm,
|
||||
if (CheckJNICalls) {
|
||||
__ str(__ zero_register(Rtemp), Address(Rthread, JavaThread::pending_jni_exception_check_fn_offset()));
|
||||
}
|
||||
|
||||
// Unhandle the result
|
||||
if (ret_type == T_OBJECT || ret_type == T_ARRAY) {
|
||||
__ cmp(R0, 0);
|
||||
__ ldr(R0, Address(R0), ne);
|
||||
}
|
||||
#endif // AARCH64
|
||||
|
||||
// Unbox oop result, e.g. JNIHandles::resolve value in R0.
|
||||
if (ret_type == T_OBJECT || ret_type == T_ARRAY) {
|
||||
__ resolve_jobject(R0, // value
|
||||
Rtemp, // tmp1
|
||||
R1_tmp); // tmp2
|
||||
}
|
||||
|
||||
// Any exception pending?
|
||||
__ ldr(Rtemp, Address(Rthread, Thread::pending_exception_offset()));
|
||||
__ mov(SP, FP);
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2008, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2008, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -1240,28 +1240,25 @@ address TemplateInterpreterGenerator::generate_native_entry(bool synchronized) {
|
||||
__ str(__ zero_register(Rtemp), Address(Rthread, JavaThread::pending_jni_exception_check_fn_offset()));
|
||||
}
|
||||
|
||||
// Unbox if the result is non-zero object
|
||||
#ifdef AARCH64
|
||||
// Unbox oop result, e.g. JNIHandles::resolve result if it's an oop.
|
||||
{
|
||||
Label L, Lnull;
|
||||
Label Lnot_oop;
|
||||
#ifdef AARCH64
|
||||
__ mov_slow(Rtemp, AbstractInterpreter::result_handler(T_OBJECT));
|
||||
__ cmp(Rresult_handler, Rtemp);
|
||||
__ b(L, ne);
|
||||
__ cbz(Rsaved_result, Lnull);
|
||||
__ ldr(Rsaved_result, Address(Rsaved_result));
|
||||
__ bind(Lnull);
|
||||
// Store oop on the stack for GC
|
||||
__ str(Rsaved_result, Address(FP, frame::interpreter_frame_oop_temp_offset * wordSize));
|
||||
__ bind(L);
|
||||
__ b(Lnot_oop, ne);
|
||||
#else // !AARCH64
|
||||
// For ARM32, Rresult_handler is -1 for oop result, 0 otherwise.
|
||||
__ cbz(Rresult_handler, Lnot_oop);
|
||||
#endif // !AARCH64
|
||||
Register value = AARCH64_ONLY(Rsaved_result) NOT_AARCH64(Rsaved_result_lo);
|
||||
__ resolve_jobject(value, // value
|
||||
Rtemp, // tmp1
|
||||
R1_tmp); // tmp2
|
||||
// Store resolved result in frame for GC visibility.
|
||||
__ str(value, Address(FP, frame::interpreter_frame_oop_temp_offset * wordSize));
|
||||
__ bind(Lnot_oop);
|
||||
}
|
||||
#else
|
||||
__ tst(Rsaved_result_lo, Rresult_handler);
|
||||
__ ldr(Rsaved_result_lo, Address(Rsaved_result_lo), ne);
|
||||
|
||||
// Store oop on the stack for GC
|
||||
__ cmp(Rresult_handler, 0);
|
||||
__ str(Rsaved_result_lo, Address(FP, frame::interpreter_frame_oop_temp_offset * wordSize), ne);
|
||||
#endif // AARCH64
|
||||
|
||||
#ifdef AARCH64
|
||||
// Restore SP (drop native parameters area), to keep SP in sync with extended_sp in frame
|
||||
|
@ -1131,12 +1131,19 @@ void LIRGenerator::do_CheckCast(CheckCast* x) {
|
||||
obj.load_item();
|
||||
LIR_Opr out_reg = rlock_result(x);
|
||||
CodeStub* stub;
|
||||
CodeEmitInfo* info_for_exception = state_for(x);
|
||||
CodeEmitInfo* info_for_exception =
|
||||
(x->needs_exception_state() ? state_for(x) :
|
||||
state_for(x, x->state_before(), true /*ignore_xhandler*/));
|
||||
|
||||
if (x->is_incompatible_class_change_check()) {
|
||||
assert(patching_info == NULL, "can't patch this");
|
||||
stub = new SimpleExceptionStub(Runtime1::throw_incompatible_class_change_error_id,
|
||||
LIR_OprFact::illegalOpr, info_for_exception);
|
||||
} else if (x->is_invokespecial_receiver_check()) {
|
||||
assert(patching_info == NULL, "can't patch this");
|
||||
stub = new DeoptimizeStub(info_for_exception,
|
||||
Deoptimization::Reason_class_check,
|
||||
Deoptimization::Action_none);
|
||||
} else {
|
||||
stub = new SimpleExceptionStub(Runtime1::throw_class_cast_exception_id, obj.result(), info_for_exception);
|
||||
}
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*
|
||||
* Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2012, 2015 SAP SE. All rights reserved.
|
||||
* Copyright (c) 2000, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2012, 2017 SAP SE. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -171,10 +171,7 @@ BasicType frame::interpreter_frame_result(oop* oop_result, jvalue* value_result)
|
||||
switch (method->result_type()) {
|
||||
case T_OBJECT:
|
||||
case T_ARRAY: {
|
||||
oop* obj_p = *(oop**)lresult;
|
||||
oop obj = (obj_p == NULL) ? (oop)NULL : *obj_p;
|
||||
assert(obj == NULL || Universe::heap()->is_in(obj), "sanity check");
|
||||
*oop_result = obj;
|
||||
*oop_result = JNIHandles::resolve(*(jobject*)lresult);
|
||||
break;
|
||||
}
|
||||
// We use std/stfd to store the values.
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*
|
||||
* Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2012, 2016 SAP SE. All rights reserved.
|
||||
* Copyright (c) 1997, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2012, 2017 SAP SE. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -3033,6 +3033,34 @@ void MacroAssembler::card_table_write(jbyte* byte_map_base, Register Rtmp, Regis
|
||||
stbx(R0, Rtmp, Robj);
|
||||
}
|
||||
|
||||
// Kills R31 if value is a volatile register.
|
||||
void MacroAssembler::resolve_jobject(Register value, Register tmp1, Register tmp2, bool needs_frame) {
|
||||
Label done;
|
||||
cmpdi(CCR0, value, 0);
|
||||
beq(CCR0, done); // Use NULL as-is.
|
||||
|
||||
clrrdi(tmp1, value, JNIHandles::weak_tag_size);
|
||||
#if INCLUDE_ALL_GCS
|
||||
if (UseG1GC) { andi_(tmp2, value, JNIHandles::weak_tag_mask); }
|
||||
#endif
|
||||
ld(value, 0, tmp1); // Resolve (untagged) jobject.
|
||||
|
||||
#if INCLUDE_ALL_GCS
|
||||
if (UseG1GC) {
|
||||
Label not_weak;
|
||||
beq(CCR0, not_weak); // Test for jweak tag.
|
||||
verify_oop(value);
|
||||
g1_write_barrier_pre(noreg, // obj
|
||||
noreg, // offset
|
||||
value, // pre_val
|
||||
tmp1, tmp2, needs_frame);
|
||||
bind(not_weak);
|
||||
}
|
||||
#endif // INCLUDE_ALL_GCS
|
||||
verify_oop(value);
|
||||
bind(done);
|
||||
}
|
||||
|
||||
#if INCLUDE_ALL_GCS
|
||||
// General G1 pre-barrier generator.
|
||||
// Goal: record the previous value if it is not null.
|
||||
@ -3094,7 +3122,7 @@ void MacroAssembler::g1_write_barrier_pre(Register Robj, RegisterOrConstant offs
|
||||
|
||||
bind(runtime);
|
||||
|
||||
// VM call need frame to access(write) O register.
|
||||
// May need to preserve LR. Also needed if current frame is not compatible with C calling convention.
|
||||
if (needs_frame) {
|
||||
save_LR_CR(Rtmp1);
|
||||
push_frame_reg_args(0, Rtmp2);
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*
|
||||
* Copyright (c) 2002, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2012, 2016 SAP SE. All rights reserved.
|
||||
* Copyright (c) 2002, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2012, 2017 SAP SE. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -649,6 +649,8 @@ class MacroAssembler: public Assembler {
|
||||
void card_write_barrier_post(Register Rstore_addr, Register Rnew_val, Register Rtmp);
|
||||
void card_table_write(jbyte* byte_map_base, Register Rtmp, Register Robj);
|
||||
|
||||
void resolve_jobject(Register value, Register tmp1, Register tmp2, bool needs_frame);
|
||||
|
||||
#if INCLUDE_ALL_GCS
|
||||
// General G1 pre-barrier generator.
|
||||
void g1_write_barrier_pre(Register Robj, RegisterOrConstant offset, Register Rpre_val,
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*
|
||||
* Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2012, 2016 SAP SE. All rights reserved.
|
||||
* Copyright (c) 1997, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2012, 2017 SAP SE. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -2477,16 +2477,11 @@ nmethod *SharedRuntime::generate_native_wrapper(MacroAssembler *masm,
|
||||
|
||||
__ reset_last_Java_frame();
|
||||
|
||||
// Unpack oop result.
|
||||
// Unbox oop result, e.g. JNIHandles::resolve value.
|
||||
// --------------------------------------------------------------------------
|
||||
|
||||
if (ret_type == T_OBJECT || ret_type == T_ARRAY) {
|
||||
Label skip_unboxing;
|
||||
__ cmpdi(CCR0, R3_RET, 0);
|
||||
__ beq(CCR0, skip_unboxing);
|
||||
__ ld(R3_RET, 0, R3_RET);
|
||||
__ bind(skip_unboxing);
|
||||
__ verify_oop(R3_RET);
|
||||
__ resolve_jobject(R3_RET, r_temp_1, r_temp_2, /* needs_frame */ false); // kills R31
|
||||
}
|
||||
|
||||
if (CheckJNICalls) {
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*
|
||||
* Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2015, 2016 SAP SE. All rights reserved.
|
||||
* Copyright (c) 2014, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2015, 2017 SAP SE. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -401,11 +401,8 @@ address TemplateInterpreterGenerator::generate_result_handler_for(BasicType type
|
||||
case T_LONG:
|
||||
break;
|
||||
case T_OBJECT:
|
||||
// unbox result if not null
|
||||
__ cmpdi(CCR0, R3_RET, 0);
|
||||
__ beq(CCR0, done);
|
||||
__ ld(R3_RET, 0, R3_RET);
|
||||
__ verify_oop(R3_RET);
|
||||
// JNIHandles::resolve result.
|
||||
__ resolve_jobject(R3_RET, R11_scratch1, R12_scratch2, /* needs_frame */ true); // kills R31
|
||||
break;
|
||||
case T_FLOAT:
|
||||
break;
|
||||
|
@ -993,12 +993,19 @@ void LIRGenerator::do_CheckCast(CheckCast* x) {
|
||||
obj.load_item();
|
||||
|
||||
// info for exceptions
|
||||
CodeEmitInfo* info_for_exception = state_for (x);
|
||||
CodeEmitInfo* info_for_exception =
|
||||
(x->needs_exception_state() ? state_for(x) :
|
||||
state_for(x, x->state_before(), true /*ignore_xhandler*/));
|
||||
|
||||
CodeStub* stub;
|
||||
if (x->is_incompatible_class_change_check()) {
|
||||
assert(patching_info == NULL, "can't patch this");
|
||||
stub = new SimpleExceptionStub(Runtime1::throw_incompatible_class_change_error_id, LIR_OprFact::illegalOpr, info_for_exception);
|
||||
} else if (x->is_invokespecial_receiver_check()) {
|
||||
assert(patching_info == NULL, "can't patch this");
|
||||
stub = new DeoptimizeStub(info_for_exception,
|
||||
Deoptimization::Reason_class_check,
|
||||
Deoptimization::Action_none);
|
||||
} else {
|
||||
stub = new SimpleExceptionStub(Runtime1::throw_class_cast_exception_id, obj.result(), info_for_exception);
|
||||
}
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2016, 2017 Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2016, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2016 SAP SE. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
|
@ -3439,6 +3439,34 @@ void MacroAssembler::card_write_barrier_post(Register store_addr, Register tmp)
|
||||
z_mvi(0, store_addr, 0); // Store byte 0.
|
||||
}
|
||||
|
||||
void MacroAssembler::resolve_jobject(Register value, Register tmp1, Register tmp2) {
|
||||
NearLabel Ldone;
|
||||
z_ltgr(tmp1, value);
|
||||
z_bre(Ldone); // Use NULL result as-is.
|
||||
|
||||
z_nill(value, ~JNIHandles::weak_tag_mask);
|
||||
z_lg(value, 0, value); // Resolve (untagged) jobject.
|
||||
|
||||
#if INCLUDE_ALL_GCS
|
||||
if (UseG1GC) {
|
||||
NearLabel Lnot_weak;
|
||||
z_tmll(tmp1, JNIHandles::weak_tag_mask); // Test for jweak tag.
|
||||
z_braz(Lnot_weak);
|
||||
verify_oop(value);
|
||||
g1_write_barrier_pre(noreg /* obj */,
|
||||
noreg /* offset */,
|
||||
value /* pre_val */,
|
||||
noreg /* val */,
|
||||
tmp1 /* tmp1 */,
|
||||
tmp2 /* tmp2 */,
|
||||
true /* pre_val_needed */);
|
||||
bind(Lnot_weak);
|
||||
}
|
||||
#endif // INCLUDE_ALL_GCS
|
||||
verify_oop(value);
|
||||
bind(Ldone);
|
||||
}
|
||||
|
||||
#if INCLUDE_ALL_GCS
|
||||
|
||||
//------------------------------------------------------
|
||||
|
@ -726,6 +726,8 @@ class MacroAssembler: public Assembler {
|
||||
// Write to card table for modification at store_addr - register is destroyed afterwards.
|
||||
void card_write_barrier_post(Register store_addr, Register tmp);
|
||||
|
||||
void resolve_jobject(Register value, Register tmp1, Register tmp2);
|
||||
|
||||
#if INCLUDE_ALL_GCS
|
||||
// General G1 pre-barrier generator.
|
||||
// Purpose: record the previous value if it is not null.
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*
|
||||
* Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2016 SAP SE. All rights reserved.
|
||||
* Copyright (c) 2016, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2016, 2017 SAP SE. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -2272,13 +2272,9 @@ nmethod *SharedRuntime::generate_native_wrapper(MacroAssembler *masm,
|
||||
|
||||
__ reset_last_Java_frame();
|
||||
|
||||
// Unpack oop result
|
||||
// Unpack oop result, e.g. JNIHandles::resolve result.
|
||||
if (ret_type == T_OBJECT || ret_type == T_ARRAY) {
|
||||
NearLabel L;
|
||||
__ compare64_and_branch(Z_RET, (RegisterOrConstant)0L, Assembler::bcondEqual, L);
|
||||
__ z_lg(Z_RET, 0, Z_RET);
|
||||
__ bind(L);
|
||||
__ verify_oop(Z_RET);
|
||||
__ resolve_jobject(Z_RET, /* tmp1 */ Z_R13, /* tmp2 */ Z_R7);
|
||||
}
|
||||
|
||||
if (CheckJNICalls) {
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*
|
||||
* Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2016 SAP SE. All rights reserved.
|
||||
* Copyright (c) 2016, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2016, 2017 SAP SE. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -1695,14 +1695,11 @@ address TemplateInterpreterGenerator::generate_native_entry(bool synchronized) {
|
||||
// from the jni handle to z_ijava_state.oop_temp. This is
|
||||
// necessary, because we reset the jni handle block below.
|
||||
// NOTE: frame::interpreter_frame_result() depends on this, too.
|
||||
{ NearLabel no_oop_result, store_oop_result;
|
||||
{ NearLabel no_oop_result;
|
||||
__ load_absolute_address(Z_R1, AbstractInterpreter::result_handler(T_OBJECT));
|
||||
__ compareU64_and_branch(Z_R1, Rresult_handler, Assembler::bcondNotEqual, no_oop_result);
|
||||
__ compareU64_and_branch(Rlresult, (intptr_t)0L, Assembler::bcondEqual, store_oop_result);
|
||||
__ z_lg(Rlresult, 0, Rlresult); // unbox
|
||||
__ bind(store_oop_result);
|
||||
__ resolve_jobject(Rlresult, /* tmp1 */ Rmethod, /* tmp2 */ Z_R1);
|
||||
__ z_stg(Rlresult, oop_tmp_offset, Z_fp);
|
||||
__ verify_oop(Rlresult);
|
||||
__ bind(no_oop_result);
|
||||
}
|
||||
|
||||
|
@ -1196,11 +1196,18 @@ void LIRGenerator::do_CheckCast(CheckCast* x) {
|
||||
obj.load_item();
|
||||
LIR_Opr out_reg = rlock_result(x);
|
||||
CodeStub* stub;
|
||||
CodeEmitInfo* info_for_exception = state_for(x);
|
||||
CodeEmitInfo* info_for_exception =
|
||||
(x->needs_exception_state() ? state_for(x) :
|
||||
state_for(x, x->state_before(), true /*ignore_xhandler*/));
|
||||
|
||||
if (x->is_incompatible_class_change_check()) {
|
||||
assert(patching_info == NULL, "can't patch this");
|
||||
stub = new SimpleExceptionStub(Runtime1::throw_incompatible_class_change_error_id, LIR_OprFact::illegalOpr, info_for_exception);
|
||||
} else if (x->is_invokespecial_receiver_check()) {
|
||||
assert(patching_info == NULL, "can't patch this");
|
||||
stub = new DeoptimizeStub(info_for_exception,
|
||||
Deoptimization::Reason_class_check,
|
||||
Deoptimization::Action_none);
|
||||
} else {
|
||||
stub = new SimpleExceptionStub(Runtime1::throw_class_cast_exception_id, obj.result(), info_for_exception);
|
||||
}
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2004, 2010, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2004, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -68,6 +68,7 @@ address JNI_FastGetField::generate_fast_get_int_field0(BasicType type) {
|
||||
__ andcc (G4, 1, G0);
|
||||
__ br (Assembler::notZero, false, Assembler::pn, label1);
|
||||
__ delayed()->srl (O2, 2, O4);
|
||||
__ andn (O1, JNIHandles::weak_tag_mask, O1);
|
||||
__ ld_ptr (O1, 0, O5);
|
||||
|
||||
assert(count < LIST_CAPACITY, "LIST_CAPACITY too small");
|
||||
@ -147,6 +148,7 @@ address JNI_FastGetField::generate_fast_get_long_field() {
|
||||
__ andcc (G4, 1, G0);
|
||||
__ br (Assembler::notZero, false, Assembler::pn, label1);
|
||||
__ delayed()->srl (O2, 2, O4);
|
||||
__ andn (O1, JNIHandles::weak_tag_mask, O1);
|
||||
__ ld_ptr (O1, 0, O5);
|
||||
__ add (O5, O4, O5);
|
||||
|
||||
@ -219,6 +221,7 @@ address JNI_FastGetField::generate_fast_get_float_field0(BasicType type) {
|
||||
__ andcc (G4, 1, G0);
|
||||
__ br (Assembler::notZero, false, Assembler::pn, label1);
|
||||
__ delayed()->srl (O2, 2, O4);
|
||||
__ andn (O1, JNIHandles::weak_tag_mask, O1);
|
||||
__ ld_ptr (O1, 0, O5);
|
||||
|
||||
assert(count < LIST_CAPACITY, "LIST_CAPACITY too small");
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2003, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -2754,15 +2754,30 @@ nmethod* SharedRuntime::generate_native_wrapper(MacroAssembler* masm,
|
||||
__ verify_thread(); // G2_thread must be correct
|
||||
__ reset_last_Java_frame();
|
||||
|
||||
// Unpack oop result
|
||||
// Unbox oop result, e.g. JNIHandles::resolve value in I0.
|
||||
if (ret_type == T_OBJECT || ret_type == T_ARRAY) {
|
||||
Label L;
|
||||
__ addcc(G0, I0, G0);
|
||||
__ brx(Assembler::notZero, true, Assembler::pt, L);
|
||||
__ delayed()->ld_ptr(I0, 0, I0);
|
||||
__ mov(G0, I0);
|
||||
__ bind(L);
|
||||
__ verify_oop(I0);
|
||||
Label done, not_weak;
|
||||
__ br_null(I0, false, Assembler::pn, done); // Use NULL as-is.
|
||||
__ delayed()->andcc(I0, JNIHandles::weak_tag_mask, G0); // Test for jweak
|
||||
__ brx(Assembler::zero, true, Assembler::pt, not_weak);
|
||||
__ delayed()->ld_ptr(I0, 0, I0); // Maybe resolve (untagged) jobject.
|
||||
// Resolve jweak.
|
||||
__ ld_ptr(I0, -JNIHandles::weak_tag_value, I0);
|
||||
#if INCLUDE_ALL_GCS
|
||||
if (UseG1GC) {
|
||||
// Copy to O0 because macro doesn't allow pre_val in input reg.
|
||||
__ mov(I0, O0);
|
||||
__ g1_write_barrier_pre(noreg /* obj */,
|
||||
noreg /* index */,
|
||||
0 /* offset */,
|
||||
O0 /* pre_val */,
|
||||
G3_scratch /* tmp */,
|
||||
true /* preserve_o_regs */);
|
||||
}
|
||||
#endif // INCLUDE_ALL_GCS
|
||||
__ bind(not_weak);
|
||||
__ verify_oop(I0);
|
||||
__ bind(done);
|
||||
}
|
||||
|
||||
if (CheckJNICalls) {
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 1997, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -1516,11 +1516,23 @@ address TemplateInterpreterGenerator::generate_native_entry(bool synchronized) {
|
||||
|
||||
__ set((intptr_t)AbstractInterpreter::result_handler(T_OBJECT), G3_scratch);
|
||||
__ cmp_and_brx_short(G3_scratch, Lscratch, Assembler::notEqual, Assembler::pt, no_oop);
|
||||
__ addcc(G0, O0, O0);
|
||||
__ brx(Assembler::notZero, true, Assembler::pt, store_result); // if result is not NULL:
|
||||
__ delayed()->ld_ptr(O0, 0, O0); // unbox it
|
||||
__ mov(G0, O0);
|
||||
|
||||
// Unbox oop result, e.g. JNIHandles::resolve value in O0.
|
||||
__ br_null(O0, false, Assembler::pn, store_result); // Use NULL as-is.
|
||||
__ delayed()->andcc(O0, JNIHandles::weak_tag_mask, G0); // Test for jweak
|
||||
__ brx(Assembler::zero, true, Assembler::pt, store_result);
|
||||
__ delayed()->ld_ptr(O0, 0, O0); // Maybe resolve (untagged) jobject.
|
||||
// Resolve jweak.
|
||||
__ ld_ptr(O0, -JNIHandles::weak_tag_value, O0);
|
||||
#if INCLUDE_ALL_GCS
|
||||
if (UseG1GC) {
|
||||
__ g1_write_barrier_pre(noreg /* obj */,
|
||||
noreg /* index */,
|
||||
0 /* offset */,
|
||||
O0 /* pre_val */,
|
||||
G3_scratch /* tmp */,
|
||||
true /* preserve_o_regs */);
|
||||
}
|
||||
#endif // INCLUDE_ALL_GCS
|
||||
__ bind(store_result);
|
||||
// Store it where gc will look for it and result handler expects it.
|
||||
__ st_ptr(O0, FP, (frame::interpreter_frame_oop_temp_offset*wordSize) + STACK_BIAS);
|
||||
|
@ -917,7 +917,7 @@ address Assembler::locate_operand(address inst, WhichOperand which) {
|
||||
break;
|
||||
|
||||
case 0x62: // EVEX_4bytes
|
||||
assert((UseAVX > 0), "shouldn't have EVEX prefix");
|
||||
assert(VM_Version::supports_evex(), "shouldn't have EVEX prefix");
|
||||
assert(ip == inst+1, "no prefixes allowed");
|
||||
// no EVEX collisions, all instructions that have 0x62 opcodes
|
||||
// have EVEX versions and are subopcodes of 0x66
|
||||
|
@ -1429,12 +1429,17 @@ void LIRGenerator::do_CheckCast(CheckCast* x) {
|
||||
obj.load_item();
|
||||
|
||||
// info for exceptions
|
||||
CodeEmitInfo* info_for_exception = state_for(x);
|
||||
CodeEmitInfo* info_for_exception =
|
||||
(x->needs_exception_state() ? state_for(x) :
|
||||
state_for(x, x->state_before(), true /*ignore_xhandler*/));
|
||||
|
||||
CodeStub* stub;
|
||||
if (x->is_incompatible_class_change_check()) {
|
||||
assert(patching_info == NULL, "can't patch this");
|
||||
stub = new SimpleExceptionStub(Runtime1::throw_incompatible_class_change_error_id, LIR_OprFact::illegalOpr, info_for_exception);
|
||||
} else if (x->is_invokespecial_receiver_check()) {
|
||||
assert(patching_info == NULL, "can't patch this");
|
||||
stub = new DeoptimizeStub(info_for_exception, Deoptimization::Reason_class_check, Deoptimization::Action_none);
|
||||
} else {
|
||||
stub = new SimpleExceptionStub(Runtime1::throw_class_cast_exception_id, obj.result(), info_for_exception);
|
||||
}
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2004, 2010, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2004, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -85,6 +85,9 @@ address JNI_FastGetField::generate_fast_get_int_field0(BasicType type) {
|
||||
__ movptr (rdx, Address(rsp, 2*wordSize)); // obj
|
||||
}
|
||||
__ movptr(rax, Address(rsp, 3*wordSize)); // jfieldID
|
||||
|
||||
__ clear_jweak_tag(rdx);
|
||||
|
||||
__ movptr(rdx, Address(rdx, 0)); // *obj
|
||||
__ shrptr (rax, 2); // offset
|
||||
|
||||
@ -202,6 +205,9 @@ address JNI_FastGetField::generate_fast_get_long_field() {
|
||||
__ movptr(rdx, Address(rsp, 3*wordSize)); // obj
|
||||
}
|
||||
__ movptr(rsi, Address(rsp, 4*wordSize)); // jfieldID
|
||||
|
||||
__ clear_jweak_tag(rdx);
|
||||
|
||||
__ movptr(rdx, Address(rdx, 0)); // *obj
|
||||
__ shrptr(rsi, 2); // offset
|
||||
|
||||
@ -291,6 +297,9 @@ address JNI_FastGetField::generate_fast_get_float_field0(BasicType type) {
|
||||
__ movptr(rdx, Address(rsp, 2*wordSize)); // obj
|
||||
}
|
||||
__ movptr(rax, Address(rsp, 3*wordSize)); // jfieldID
|
||||
|
||||
__ clear_jweak_tag(rdx);
|
||||
|
||||
__ movptr(rdx, Address(rdx, 0)); // *obj
|
||||
__ shrptr(rax, 2); // offset
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2004, 2010, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2004, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -80,6 +80,9 @@ address JNI_FastGetField::generate_fast_get_int_field0(BasicType type) {
|
||||
// robj ^ rcounter ^ rcounter == robj
|
||||
// robj is data dependent on rcounter.
|
||||
}
|
||||
|
||||
__ clear_jweak_tag(robj);
|
||||
|
||||
__ movptr(robj, Address(robj, 0)); // *obj
|
||||
__ mov (roffset, c_rarg2);
|
||||
__ shrptr(roffset, 2); // offset
|
||||
@ -178,6 +181,9 @@ address JNI_FastGetField::generate_fast_get_float_field0(BasicType type) {
|
||||
// robj ^ rcounter ^ rcounter == robj
|
||||
// robj is data dependent on rcounter.
|
||||
}
|
||||
|
||||
__ clear_jweak_tag(robj);
|
||||
|
||||
__ movptr(robj, Address(robj, 0)); // *obj
|
||||
__ mov (roffset, c_rarg2);
|
||||
__ shrptr(roffset, 2); // offset
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 1997, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -5129,6 +5129,43 @@ void MacroAssembler::vxorps(XMMRegister dst, XMMRegister nds, AddressLiteral src
|
||||
}
|
||||
|
||||
|
||||
void MacroAssembler::resolve_jobject(Register value,
|
||||
Register thread,
|
||||
Register tmp) {
|
||||
assert_different_registers(value, thread, tmp);
|
||||
Label done, not_weak;
|
||||
testptr(value, value);
|
||||
jcc(Assembler::zero, done); // Use NULL as-is.
|
||||
testptr(value, JNIHandles::weak_tag_mask); // Test for jweak tag.
|
||||
jcc(Assembler::zero, not_weak);
|
||||
// Resolve jweak.
|
||||
movptr(value, Address(value, -JNIHandles::weak_tag_value));
|
||||
verify_oop(value);
|
||||
#if INCLUDE_ALL_GCS
|
||||
if (UseG1GC) {
|
||||
g1_write_barrier_pre(noreg /* obj */,
|
||||
value /* pre_val */,
|
||||
thread /* thread */,
|
||||
tmp /* tmp */,
|
||||
true /* tosca_live */,
|
||||
true /* expand_call */);
|
||||
}
|
||||
#endif // INCLUDE_ALL_GCS
|
||||
jmp(done);
|
||||
bind(not_weak);
|
||||
// Resolve (untagged) jobject.
|
||||
movptr(value, Address(value, 0));
|
||||
verify_oop(value);
|
||||
bind(done);
|
||||
}
|
||||
|
||||
void MacroAssembler::clear_jweak_tag(Register possibly_jweak) {
|
||||
const int32_t inverted_jweak_mask = ~static_cast<int32_t>(JNIHandles::weak_tag_mask);
|
||||
STATIC_ASSERT(inverted_jweak_mask == -2); // otherwise check this code
|
||||
// The inverted mask is sign-extended
|
||||
andptr(possibly_jweak, inverted_jweak_mask);
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
#if INCLUDE_ALL_GCS
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 1997, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -297,6 +297,9 @@ class MacroAssembler: public Assembler {
|
||||
void store_check(Register obj); // store check for obj - register is destroyed afterwards
|
||||
void store_check(Register obj, Address dst); // same as above, dst is exact store location (reg. is destroyed)
|
||||
|
||||
void resolve_jobject(Register value, Register thread, Register tmp);
|
||||
void clear_jweak_tag(Register possibly_jweak);
|
||||
|
||||
#if INCLUDE_ALL_GCS
|
||||
|
||||
void g1_write_barrier_pre(Register obj,
|
||||
|
@ -365,6 +365,10 @@ int NativeMovRegMem::instruction_start() const {
|
||||
NOT_LP64(assert((0xC0 & ubyte_at(1)) == 0xC0, "shouldn't have LDS and LES instructions"));
|
||||
return 3;
|
||||
}
|
||||
if (instr_0 == instruction_EVEX_prefix_4bytes) {
|
||||
assert(VM_Version::supports_evex(), "shouldn't have EVEX prefix");
|
||||
return 4;
|
||||
}
|
||||
|
||||
// First check to see if we have a (prefixed or not) xor
|
||||
if (instr_0 >= instruction_prefix_wide_lo && // 0x40
|
||||
|
@ -356,6 +356,7 @@ class NativeMovRegMem: public NativeInstruction {
|
||||
|
||||
instruction_VEX_prefix_2bytes = Assembler::VEX_2bytes,
|
||||
instruction_VEX_prefix_3bytes = Assembler::VEX_3bytes,
|
||||
instruction_EVEX_prefix_4bytes = Assembler::EVEX_4bytes,
|
||||
|
||||
instruction_size = 4,
|
||||
instruction_offset = 0,
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2003, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -2226,14 +2226,11 @@ nmethod* SharedRuntime::generate_native_wrapper(MacroAssembler* masm,
|
||||
|
||||
__ reset_last_Java_frame(thread, false);
|
||||
|
||||
// Unpack oop result
|
||||
// Unbox oop result, e.g. JNIHandles::resolve value.
|
||||
if (ret_type == T_OBJECT || ret_type == T_ARRAY) {
|
||||
Label L;
|
||||
__ cmpptr(rax, (int32_t)NULL_WORD);
|
||||
__ jcc(Assembler::equal, L);
|
||||
__ movptr(rax, Address(rax, 0));
|
||||
__ bind(L);
|
||||
__ verify_oop(rax);
|
||||
__ resolve_jobject(rax /* value */,
|
||||
thread /* thread */,
|
||||
rcx /* tmp */);
|
||||
}
|
||||
|
||||
if (CheckJNICalls) {
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2003, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -2579,14 +2579,11 @@ nmethod* SharedRuntime::generate_native_wrapper(MacroAssembler* masm,
|
||||
|
||||
__ reset_last_Java_frame(false);
|
||||
|
||||
// Unpack oop result
|
||||
// Unbox oop result, e.g. JNIHandles::resolve value.
|
||||
if (ret_type == T_OBJECT || ret_type == T_ARRAY) {
|
||||
Label L;
|
||||
__ testptr(rax, rax);
|
||||
__ jcc(Assembler::zero, L);
|
||||
__ movptr(rax, Address(rax, 0));
|
||||
__ bind(L);
|
||||
__ verify_oop(rax);
|
||||
__ resolve_jobject(rax /* value */,
|
||||
r15_thread /* thread */,
|
||||
rcx /* tmp */);
|
||||
}
|
||||
|
||||
if (CheckJNICalls) {
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2003, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -1193,16 +1193,16 @@ address TemplateInterpreterGenerator::generate_native_entry(bool synchronized) {
|
||||
// and result handler will pick it up
|
||||
|
||||
{
|
||||
Label no_oop, store_result;
|
||||
Label no_oop, not_weak, store_result;
|
||||
__ lea(t, ExternalAddress(AbstractInterpreter::result_handler(T_OBJECT)));
|
||||
__ cmpptr(t, Address(rbp, frame::interpreter_frame_result_handler_offset*wordSize));
|
||||
__ jcc(Assembler::notEqual, no_oop);
|
||||
// retrieve result
|
||||
__ pop(ltos);
|
||||
__ testptr(rax, rax);
|
||||
__ jcc(Assembler::zero, store_result);
|
||||
__ movptr(rax, Address(rax, 0));
|
||||
__ bind(store_result);
|
||||
// Unbox oop result, e.g. JNIHandles::resolve value.
|
||||
__ resolve_jobject(rax /* value */,
|
||||
thread /* thread */,
|
||||
t /* tmp */);
|
||||
__ movptr(Address(rbp, frame::interpreter_frame_oop_temp_offset*wordSize), rax);
|
||||
// keep stack depth as expected by pushing oop which will eventually be discarded
|
||||
__ push(ltos);
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 1997, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -2210,7 +2210,6 @@ void TemplateTable::branch(bool is_jsr, bool is_wide) {
|
||||
// Out-of-line code to allocate method data oop.
|
||||
__ bind(profile_method);
|
||||
__ call_VM(noreg, CAST_FROM_FN_PTR(address, InterpreterRuntime::profile_method));
|
||||
__ load_unsigned_byte(rbx, Address(rbcp, 0)); // restore target bytecode
|
||||
__ set_method_data_pointer_for_bcp();
|
||||
__ jmp(dispatch);
|
||||
}
|
||||
@ -2225,10 +2224,8 @@ void TemplateTable::branch(bool is_jsr, bool is_wide) {
|
||||
CAST_FROM_FN_PTR(address,
|
||||
InterpreterRuntime::frequency_counter_overflow),
|
||||
rdx);
|
||||
__ load_unsigned_byte(rbx, Address(rbcp, 0)); // restore target bytecode
|
||||
|
||||
// rax: osr nmethod (osr ok) or NULL (osr not possible)
|
||||
// rbx: target bytecode
|
||||
// rdx: scratch
|
||||
// r14: locals pointer
|
||||
// r13: bcp
|
||||
@ -2238,12 +2235,13 @@ void TemplateTable::branch(bool is_jsr, bool is_wide) {
|
||||
__ cmpb(Address(rax, nmethod::state_offset()), nmethod::in_use);
|
||||
__ jcc(Assembler::notEqual, dispatch);
|
||||
|
||||
// We have the address of an on stack replacement routine in rax
|
||||
// We need to prepare to execute the OSR method. First we must
|
||||
// migrate the locals and monitors off of the stack.
|
||||
// We have the address of an on stack replacement routine in rax.
|
||||
// In preparation of invoking it, first we must migrate the locals
|
||||
// and monitors from off the interpreter frame on the stack.
|
||||
// Ensure to save the osr nmethod over the migration call,
|
||||
// it will be preserved in rbx.
|
||||
__ mov(rbx, rax);
|
||||
|
||||
LP64_ONLY(__ mov(r13, rax)); // save the nmethod
|
||||
NOT_LP64(__ mov(rbx, rax)); // save the nmethod
|
||||
NOT_LP64(__ get_thread(rcx));
|
||||
|
||||
call_VM(noreg, CAST_FROM_FN_PTR(address, SharedRuntime::OSR_migration_begin));
|
||||
@ -2258,7 +2256,6 @@ void TemplateTable::branch(bool is_jsr, bool is_wide) {
|
||||
const Register retaddr = LP64_ONLY(j_rarg2) NOT_LP64(rdi);
|
||||
const Register sender_sp = LP64_ONLY(j_rarg1) NOT_LP64(rdx);
|
||||
|
||||
|
||||
// pop the interpreter frame
|
||||
__ movptr(sender_sp, Address(rbp, frame::interpreter_frame_sender_sp_offset * wordSize)); // get sender sp
|
||||
__ leave(); // remove frame anchor
|
||||
@ -2274,8 +2271,7 @@ void TemplateTable::branch(bool is_jsr, bool is_wide) {
|
||||
__ push(retaddr);
|
||||
|
||||
// and begin the OSR nmethod
|
||||
LP64_ONLY(__ jmp(Address(r13, nmethod::osr_entry_point_offset())));
|
||||
NOT_LP64(__ jmp(Address(rbx, nmethod::osr_entry_point_offset())));
|
||||
__ jmp(Address(rbx, nmethod::osr_entry_point_offset()));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 1997, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -763,12 +763,11 @@ void VM_Version::get_processor_features() {
|
||||
FLAG_SET_DEFAULT(UseCRC32Intrinsics, false);
|
||||
}
|
||||
|
||||
if (supports_sse4_2()) {
|
||||
if (supports_sse4_2() && supports_clmul()) {
|
||||
if (FLAG_IS_DEFAULT(UseCRC32CIntrinsics)) {
|
||||
UseCRC32CIntrinsics = true;
|
||||
}
|
||||
}
|
||||
else if (UseCRC32CIntrinsics) {
|
||||
} else if (UseCRC32CIntrinsics) {
|
||||
if (!FLAG_IS_DEFAULT(UseCRC32CIntrinsics)) {
|
||||
warning("CRC32C intrinsics are not available on this CPU");
|
||||
}
|
||||
@ -850,6 +849,12 @@ void VM_Version::get_processor_features() {
|
||||
|
||||
#if INCLUDE_RTM_OPT
|
||||
if (UseRTMLocking) {
|
||||
if (is_client_compilation_mode_vm()) {
|
||||
// Only C2 does RTM locking optimization.
|
||||
// Can't continue because UseRTMLocking affects UseBiasedLocking flag
|
||||
// setting during arguments processing. See use_biased_locking().
|
||||
vm_exit_during_initialization("RTM locking optimization is not supported in emulated client VM");
|
||||
}
|
||||
if (is_intel_family_core()) {
|
||||
if ((_model == CPU_MODEL_HASWELL_E3) ||
|
||||
(_model == CPU_MODEL_HASWELL_E7 && _stepping < 3) ||
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2003, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright 2007, 2008, 2009, 2010, 2011 Red Hat, Inc.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
@ -406,10 +406,12 @@ int CppInterpreter::native_entry(Method* method, intptr_t UNUSED, TRAPS) {
|
||||
// oop_temp where the garbage collector can see it before
|
||||
// we release the handle it might be protected by.
|
||||
if (handler->result_type() == &ffi_type_pointer) {
|
||||
if (result[0])
|
||||
istate->set_oop_temp(*(oop *) result[0]);
|
||||
else
|
||||
if (result[0] == 0) {
|
||||
istate->set_oop_temp(NULL);
|
||||
} else {
|
||||
jobject handle = reinterpret_cast<jobject>(result[0]);
|
||||
istate->set_oop_temp(JNIHandles::resolve(handle));
|
||||
}
|
||||
}
|
||||
|
||||
// Reset handle block
|
||||
|
@ -25,6 +25,7 @@ package jdk.tools.jaotc;
|
||||
|
||||
import org.graalvm.compiler.code.CompilationResult;
|
||||
import org.graalvm.compiler.core.target.Backend;
|
||||
import org.graalvm.compiler.hotspot.HotSpotCompiledCodeBuilder;
|
||||
import org.graalvm.compiler.hotspot.stubs.Stub;
|
||||
|
||||
import jdk.vm.ci.hotspot.HotSpotCompiledCode;
|
||||
@ -48,7 +49,7 @@ public class AOTStub implements JavaMethodInfo {
|
||||
}
|
||||
|
||||
public HotSpotCompiledCode compiledCode(CompilationResult result) {
|
||||
return stub.getCompiledCode(backend);
|
||||
return HotSpotCompiledCodeBuilder.createCompiledCode(null, null, result);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -59,12 +59,6 @@ abstract class CallSiteRelocationSymbol {
|
||||
addExternalPltToGotRelocation(binaryContainer, symbol, relocationOffset);
|
||||
}
|
||||
|
||||
protected static void addMetaspaceGotRelocation(BinaryContainer binaryContainer, String symbolName, int symbolOffset, int relocationOffset) {
|
||||
ByteContainer container = binaryContainer.getMetaspaceGotContainer();
|
||||
Symbol symbol = container.createGotSymbol(symbolOffset, symbolName);
|
||||
addExternalPltToGotRelocation(binaryContainer, symbol, relocationOffset);
|
||||
}
|
||||
|
||||
/**
|
||||
* Add an {@link RelocType#EXTERNAL_GOT_TO_PLT} relocation to the
|
||||
* {@link BinaryContainer#getExtLinkageGOTContainer()}.
|
||||
|
@ -70,8 +70,8 @@ class DataBuilder {
|
||||
*/
|
||||
private void fillVMAddresses(HotSpotVMConfigStore config) {
|
||||
for (VMField vmField : config.getFields().values()) {
|
||||
if (vmField.value != null) {
|
||||
final long address = vmField.value;
|
||||
if (vmField.value != null && vmField.value instanceof Long) {
|
||||
final long address = (Long) vmField.value;
|
||||
String value = vmField.name;
|
||||
/*
|
||||
* Some fields don't contain addresses but integer values. At least don't add zero
|
||||
|
@ -37,6 +37,7 @@ import jdk.vm.ci.hotspot.HotSpotResolvedJavaMethod;
|
||||
final class JavaCallSiteRelocationSymbol extends CallSiteRelocationSymbol {
|
||||
|
||||
private static final byte[] zeroSlot = new byte[8];
|
||||
// -1 represents Universe::non_oop_word() value
|
||||
private static final byte[] minusOneSlot = {-1, -1, -1, -1, -1, -1, -1, -1};
|
||||
|
||||
public JavaCallSiteRelocationSymbol(CompiledMethodInfo mi, Call call, CallSiteRelocationInfo callSiteRelocation, BinaryContainer binaryContainer) {
|
||||
@ -79,30 +80,39 @@ final class JavaCallSiteRelocationSymbol extends CallSiteRelocationSymbol {
|
||||
}
|
||||
|
||||
// Add relocation to GOT cell for call resolution jump.
|
||||
// This GOT cell will be initialized during JVM startup with address
|
||||
// of JVM runtime call resolution function.
|
||||
String gotSymbolName = "got." + getResolveSymbolName(binaryContainer, mi, call);
|
||||
Symbol gotSymbol = binaryContainer.getGotSymbol(gotSymbolName);
|
||||
addExternalPltToGotRelocation(binaryContainer, gotSymbol, stub.getResolveJumpOffset());
|
||||
|
||||
// Add relocation to resolve call jump instruction address for GOT cell.
|
||||
// This GOT cell will be initialized with address of resolution jump instruction and
|
||||
// will be updated with call destination address by JVM runtime call resolution code.
|
||||
String pltJmpSymbolName = relocationSymbolName("plt.jmp", mi, call, callSiteRelocation);
|
||||
addCodeContainerRelocation(binaryContainer, pltJmpSymbolName, stub.getResolveJumpStart(), gotStartOffset);
|
||||
|
||||
// Add relocation to GOT cell for dispatch jump.
|
||||
// The dispatch jump loads destination address from this GOT cell.
|
||||
String gotEntrySymbolName = relocationSymbolName("got.entry", mi, call, callSiteRelocation);
|
||||
addExtLinkageGotContainerRelocation(binaryContainer, gotEntrySymbolName, gotStartOffset, stub.getDispatchJumpOffset());
|
||||
|
||||
// Virtual call needs initial -1 value.
|
||||
// Virtual call needs initial -1 value for Klass pointer.
|
||||
// Non virtual call needs initial 0 value for Method pointer to call c2i adapter.
|
||||
byte[] slot = isVirtualCall ? minusOneSlot : zeroSlot;
|
||||
final int gotMetaOffset = binaryContainer.appendMetaspaceGotBytes(slot, 0, slot.length);
|
||||
final int gotMetaOffset = binaryContainer.appendExtLinkageGotBytes(slot, 0, slot.length);
|
||||
|
||||
// Add relocation to GOT cell for move instruction (Klass* for virtual, Method* otherwise).
|
||||
String gotMoveSymbolName = relocationSymbolName("got.move", mi, call, callSiteRelocation);
|
||||
addMetaspaceGotRelocation(binaryContainer, gotMoveSymbolName, gotMetaOffset, stub.getMovOffset());
|
||||
addExtLinkageGotContainerRelocation(binaryContainer, gotMoveSymbolName, gotMetaOffset, stub.getMovOffset());
|
||||
|
||||
if (isVirtualCall) {
|
||||
// Nothing.
|
||||
} else {
|
||||
// Add relocation to GOT cell for c2i adapter jump.
|
||||
// The c2i jump instruction loads destination address from this GOT cell.
|
||||
// This GOT cell is initialized with -1 and will be updated
|
||||
// by JVM runtime call resolution code.
|
||||
String gotC2ISymbolName = relocationSymbolName("got.c2i", mi, call, callSiteRelocation);
|
||||
addExtLinkageGotContainerRelocation(binaryContainer, gotC2ISymbolName, gotStartOffset + 8, stub.getC2IJumpOffset());
|
||||
}
|
||||
|
@ -625,7 +625,9 @@ public class Main implements LogPrinter {
|
||||
|
||||
private void reportError(Throwable e) {
|
||||
log.println("Error: " + e.getMessage());
|
||||
e.printStackTrace(log);
|
||||
if (options.info) {
|
||||
e.printStackTrace(log);
|
||||
}
|
||||
log.flush();
|
||||
}
|
||||
|
||||
|
@ -77,7 +77,7 @@ public class ClassSearch {
|
||||
}
|
||||
|
||||
if (found == null) {
|
||||
throw new InternalError("Failed to find: " + searchFor.toString());
|
||||
throw new InternalError("Failed to find " + searchFor.getType() + " file: " + searchFor.getName());
|
||||
}
|
||||
return found;
|
||||
}
|
||||
|
@ -27,7 +27,7 @@ public class SearchFor {
|
||||
private final String type;
|
||||
|
||||
public SearchFor(String name) {
|
||||
this(name, "unknown");
|
||||
this(name, "");
|
||||
}
|
||||
|
||||
public SearchFor(String name, String type) {
|
||||
@ -36,7 +36,7 @@ public class SearchFor {
|
||||
}
|
||||
|
||||
public boolean isUnknown() {
|
||||
return "unknown".equals(type);
|
||||
return "".equals(type);
|
||||
}
|
||||
|
||||
public String getType() {
|
||||
@ -49,6 +49,6 @@ public class SearchFor {
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return type + ":" + name;
|
||||
return type + ": " + name;
|
||||
}
|
||||
}
|
||||
|
@ -31,7 +31,7 @@ import java.nio.file.Path;
|
||||
import java.nio.file.Paths;
|
||||
|
||||
public class ClassNameSourceProvider implements SourceProvider {
|
||||
public final static String TYPE = "classname";
|
||||
public final static String TYPE = "class";
|
||||
private final ClassLoader classLoader;
|
||||
|
||||
public ClassNameSourceProvider(FileSupport fileSupport) {
|
||||
@ -47,6 +47,10 @@ public class ClassNameSourceProvider implements SourceProvider {
|
||||
|
||||
@Override
|
||||
public ClassSource findSource(String name, SearchPath searchPath) {
|
||||
Path path = Paths.get(name);
|
||||
if (ClassSource.pathIsClassFile(path)) {
|
||||
name = ClassSource.makeClassName(path);
|
||||
}
|
||||
try {
|
||||
classLoader.loadClass(name);
|
||||
return new ClassNameSource(name, classLoader);
|
||||
|
@ -25,6 +25,6 @@
|
||||
|
||||
module jdk.aot {
|
||||
requires jdk.management;
|
||||
requires jdk.vm.ci;
|
||||
requires jdk.vm.compiler;
|
||||
requires jdk.internal.vm.ci;
|
||||
requires jdk.internal.vm.compiler;
|
||||
}
|
||||
|
@ -70,18 +70,17 @@ JNIEXPORT jint JNICALL Java_jdk_tools_jaotc_jnilibelf_JNILibELFAPI_elf_1version
|
||||
*/
|
||||
|
||||
static jlong getNativeAddress(JNIEnv* env, jobject ptrObj) {
|
||||
jclass ptrClass;
|
||||
jfieldID fidNumber;
|
||||
jlong nativeAddress = -1;
|
||||
assert (ptrObj != NULL);
|
||||
assert (ptrObj != NULL);
|
||||
// Get a reference to ptr object's class
|
||||
ptrClass = (*env)->GetObjectClass(env, ptrObj);
|
||||
|
||||
// Get the Field ID of the instance variables "address"
|
||||
fidNumber = (*env)->GetFieldID(env, ptrClass, "address", "J");
|
||||
if (fidNumber != NULL) {
|
||||
// Get the long given the Field ID
|
||||
nativeAddress = (*env)->GetLongField(env, ptrObj, fidNumber);
|
||||
jclass ptrClass = (*env)->GetObjectClass(env, ptrObj);
|
||||
if (ptrClass != NULL) {
|
||||
// Get the Field ID of the instance variables "address"
|
||||
jfieldID fidNumber = (*env)->GetFieldID(env, ptrClass, "address", "J");
|
||||
if (fidNumber != NULL) {
|
||||
// Get the long given the Field ID
|
||||
nativeAddress = (*env)->GetLongField(env, ptrObj, fidNumber);
|
||||
}
|
||||
}
|
||||
// fprintf(stderr, "Native address : %lx\n", nativeAddress);
|
||||
return nativeAddress;
|
||||
@ -91,10 +90,15 @@ static jlong getNativeAddress(JNIEnv* env, jobject ptrObj) {
|
||||
* Box the nativeAddress as a Pointer object.
|
||||
*/
|
||||
static jobject makePointerObject(JNIEnv* env, jlong nativeAddr) {
|
||||
jobject retObj = NULL;
|
||||
jclass ptrClass = (*env)->FindClass(env, "jdk/tools/jaotc/jnilibelf/Pointer");
|
||||
// Call back constructor to allocate a Pointer object, with an int argument
|
||||
jmethodID constructorId = (*env)->GetMethodID(env, ptrClass, "<init>", "(J)V");
|
||||
jobject retObj = (*env)->NewObject(env, ptrClass, constructorId, nativeAddr);
|
||||
if (ptrClass != NULL) {
|
||||
// Call back constructor to allocate a Pointer object, with an int argument
|
||||
jmethodID constructorId = (*env)->GetMethodID(env, ptrClass, "<init>", "(J)V");
|
||||
if (constructorId != NULL) {
|
||||
retObj = (*env)->NewObject(env, ptrClass, constructorId, nativeAddr);
|
||||
}
|
||||
}
|
||||
return retObj;
|
||||
}
|
||||
|
||||
|
@ -33,6 +33,7 @@
|
||||
#define ELF_NHDR Elf64_Nhdr
|
||||
#define ELF_DYN Elf64_Dyn
|
||||
#define ELF_ADDR Elf64_Addr
|
||||
#define ELF_AUXV Elf64_auxv_t
|
||||
|
||||
#define ELF_ST_TYPE ELF64_ST_TYPE
|
||||
|
||||
@ -45,6 +46,7 @@
|
||||
#define ELF_NHDR Elf32_Nhdr
|
||||
#define ELF_DYN Elf32_Dyn
|
||||
#define ELF_ADDR Elf32_Addr
|
||||
#define ELF_AUXV Elf32_auxv_t
|
||||
|
||||
#define ELF_ST_TYPE ELF32_ST_TYPE
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2003, 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2003, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -50,7 +50,7 @@ int pathmap_open(const char* name) {
|
||||
}
|
||||
|
||||
|
||||
if (strlen(alt_root) + strlen(name) < PATH_MAX) {
|
||||
if (strlen(alt_root) + strlen(name) > PATH_MAX) {
|
||||
// Buffer too small.
|
||||
return -1;
|
||||
}
|
||||
|
@ -642,6 +642,18 @@ static bool core_handle_note(struct ps_prochandle* ph, ELF_PHDR* note_phdr) {
|
||||
if (core_handle_prstatus(ph, descdata, notep->n_descsz) != true) {
|
||||
return false;
|
||||
}
|
||||
} else if (notep->n_type == NT_AUXV) {
|
||||
// Get first segment from entry point
|
||||
ELF_AUXV *auxv = (ELF_AUXV *)descdata;
|
||||
while (auxv->a_type != AT_NULL) {
|
||||
if (auxv->a_type == AT_ENTRY) {
|
||||
// Set entry point address to address of dynamic section.
|
||||
// We will adjust it in read_exec_segments().
|
||||
ph->core->dynamic_addr = auxv->a_un.a_val;
|
||||
break;
|
||||
}
|
||||
auxv++;
|
||||
}
|
||||
}
|
||||
p = descdata + ROUNDUP(notep->n_descsz, 4);
|
||||
}
|
||||
@ -832,7 +844,13 @@ static bool read_exec_segments(struct ps_prochandle* ph, ELF_EHDR* exec_ehdr) {
|
||||
|
||||
// from PT_DYNAMIC we want to read address of first link_map addr
|
||||
case PT_DYNAMIC: {
|
||||
ph->core->dynamic_addr = exec_php->p_vaddr;
|
||||
if (exec_ehdr->e_type == ET_EXEC) {
|
||||
ph->core->dynamic_addr = exec_php->p_vaddr;
|
||||
} else { // ET_DYN
|
||||
// dynamic_addr has entry point of executable.
|
||||
// Thus we should substract it.
|
||||
ph->core->dynamic_addr += exec_php->p_vaddr - exec_ehdr->e_entry;
|
||||
}
|
||||
print_debug("address of _DYNAMIC is 0x%lx\n", ph->core->dynamic_addr);
|
||||
break;
|
||||
}
|
||||
@ -1030,8 +1048,9 @@ struct ps_prochandle* Pgrab_core(const char* exec_file, const char* core_file) {
|
||||
goto err;
|
||||
}
|
||||
|
||||
if (read_elf_header(ph->core->exec_fd, &exec_ehdr) != true || exec_ehdr.e_type != ET_EXEC) {
|
||||
print_debug("executable file is not a valid ELF ET_EXEC file\n");
|
||||
if (read_elf_header(ph->core->exec_fd, &exec_ehdr) != true ||
|
||||
((exec_ehdr.e_type != ET_EXEC) && (exec_ehdr.e_type != ET_DYN))) {
|
||||
print_debug("executable file is not a valid ELF file\n");
|
||||
goto err;
|
||||
}
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 20014, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2004, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -114,6 +114,8 @@ public abstract class AbstractHeapGraphWriter implements HeapGraphWriter {
|
||||
}
|
||||
});
|
||||
|
||||
writeHeapRecordPrologue();
|
||||
|
||||
// write JavaThreads
|
||||
writeJavaThreads();
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2004, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2004, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -45,8 +45,8 @@ import sun.jvm.hotspot.classfile.*;
|
||||
* WARNING: This format is still under development, and is subject to
|
||||
* change without notice.
|
||||
*
|
||||
* header "JAVA PROFILE 1.0.1" or "JAVA PROFILE 1.0.2" (0-terminated)
|
||||
* u4 size of identifiers. Identifiers are used to represent
|
||||
* header "JAVA PROFILE 1.0.2" (0-terminated)
|
||||
* u4 size of identifiers. Identifiers are used to represent
|
||||
* UTF8 strings, objects, stack traces, etc. They usually
|
||||
* have the same size as host pointers. For example, on
|
||||
* Solaris and Win32, the size is 4.
|
||||
@ -294,10 +294,9 @@ import sun.jvm.hotspot.classfile.*;
|
||||
* u2 stack trace depth
|
||||
*
|
||||
*
|
||||
* When the header is "JAVA PROFILE 1.0.2" a heap dump can optionally
|
||||
* be generated as a sequence of heap dump segments. This sequence is
|
||||
* terminated by an end record. The additional tags allowed by format
|
||||
* "JAVA PROFILE 1.0.2" are:
|
||||
* A heap dump can optionally be generated as a sequence of heap dump
|
||||
* segments. This sequence is terminated by an end record. The additional
|
||||
* tags allowed by format "JAVA PROFILE 1.0.2" are:
|
||||
*
|
||||
* HPROF_HEAP_DUMP_SEGMENT denote a heap dump segment
|
||||
*
|
||||
@ -310,8 +309,6 @@ import sun.jvm.hotspot.classfile.*;
|
||||
|
||||
public class HeapHprofBinWriter extends AbstractHeapGraphWriter {
|
||||
|
||||
// The heap size threshold used to determine if segmented format
|
||||
// ("JAVA PROFILE 1.0.2") should be used.
|
||||
private static final long HPROF_SEGMENTED_HEAP_DUMP_THRESHOLD = 2L * 0x40000000;
|
||||
|
||||
// The approximate size of a heap segment. Used to calculate when to create
|
||||
@ -319,7 +316,6 @@ public class HeapHprofBinWriter extends AbstractHeapGraphWriter {
|
||||
private static final long HPROF_SEGMENTED_HEAP_DUMP_SEGMENT_SIZE = 1L * 0x40000000;
|
||||
|
||||
// hprof binary file header
|
||||
private static final String HPROF_HEADER_1_0_1 = "JAVA PROFILE 1.0.1";
|
||||
private static final String HPROF_HEADER_1_0_2 = "JAVA PROFILE 1.0.2";
|
||||
|
||||
// constants in enum HprofTag
|
||||
@ -380,6 +376,7 @@ public class HeapHprofBinWriter extends AbstractHeapGraphWriter {
|
||||
private static final int JVM_SIGNATURE_ARRAY = '[';
|
||||
private static final int JVM_SIGNATURE_CLASS = 'L';
|
||||
|
||||
private static final long MAX_U4_VALUE = 0xFFFFFFFFL;
|
||||
int serialNum = 1;
|
||||
|
||||
public synchronized void write(String fileName) throws IOException {
|
||||
@ -469,7 +466,6 @@ public class HeapHprofBinWriter extends AbstractHeapGraphWriter {
|
||||
// length later - hprof format requires length.
|
||||
out.flush();
|
||||
currentSegmentStart = fos.getChannel().position();
|
||||
|
||||
// write dummy length of 0 and we'll fix it later.
|
||||
out.writeInt(0);
|
||||
}
|
||||
@ -479,7 +475,7 @@ public class HeapHprofBinWriter extends AbstractHeapGraphWriter {
|
||||
protected void writeHeapRecordEpilogue() throws IOException {
|
||||
if (useSegmentedHeapDump) {
|
||||
out.flush();
|
||||
if ((fos.getChannel().position() - currentSegmentStart - 4) >= HPROF_SEGMENTED_HEAP_DUMP_SEGMENT_SIZE) {
|
||||
if ((fos.getChannel().position() - currentSegmentStart - 4L) >= HPROF_SEGMENTED_HEAP_DUMP_SEGMENT_SIZE) {
|
||||
fillInHeapRecordLength();
|
||||
currentSegmentStart = 0;
|
||||
}
|
||||
@ -488,14 +484,14 @@ public class HeapHprofBinWriter extends AbstractHeapGraphWriter {
|
||||
|
||||
private void fillInHeapRecordLength() throws IOException {
|
||||
|
||||
// now get current position to calculate length
|
||||
// now get the current position to calculate length
|
||||
long dumpEnd = fos.getChannel().position();
|
||||
|
||||
// calculate length of heap data
|
||||
// calculate the length of heap data
|
||||
long dumpLenLong = (dumpEnd - currentSegmentStart - 4L);
|
||||
|
||||
// Check length boundary, overflow could happen but is _very_ unlikely
|
||||
if(dumpLenLong >= (4L * 0x40000000)){
|
||||
if (dumpLenLong >= (4L * 0x40000000)) {
|
||||
throw new RuntimeException("Heap segment size overflow.");
|
||||
}
|
||||
|
||||
@ -517,6 +513,71 @@ public class HeapHprofBinWriter extends AbstractHeapGraphWriter {
|
||||
fos.getChannel().position(currentPosition);
|
||||
}
|
||||
|
||||
// get the size in bytes for the requested type
|
||||
private long getSizeForType(int type) throws IOException {
|
||||
switch (type) {
|
||||
case TypeArrayKlass.T_BOOLEAN:
|
||||
return BOOLEAN_SIZE;
|
||||
case TypeArrayKlass.T_INT:
|
||||
return INT_SIZE;
|
||||
case TypeArrayKlass.T_CHAR:
|
||||
return CHAR_SIZE;
|
||||
case TypeArrayKlass.T_SHORT:
|
||||
return SHORT_SIZE;
|
||||
case TypeArrayKlass.T_BYTE:
|
||||
return BYTE_SIZE;
|
||||
case TypeArrayKlass.T_LONG:
|
||||
return LONG_SIZE;
|
||||
case TypeArrayKlass.T_FLOAT:
|
||||
return FLOAT_SIZE;
|
||||
case TypeArrayKlass.T_DOUBLE:
|
||||
return DOUBLE_SIZE;
|
||||
default:
|
||||
throw new RuntimeException(
|
||||
"Should not reach here: Unknown type: " + type);
|
||||
}
|
||||
}
|
||||
|
||||
private int getArrayHeaderSize(boolean isObjectAarray) {
|
||||
return isObjectAarray?
|
||||
((int) BYTE_SIZE + 2 * (int) INT_SIZE + 2 * (int) OBJ_ID_SIZE):
|
||||
(2 * (int) BYTE_SIZE + 2 * (int) INT_SIZE + (int) OBJ_ID_SIZE);
|
||||
}
|
||||
|
||||
// Check if we need to truncate an array
|
||||
private int calculateArrayMaxLength(long originalArrayLength,
|
||||
int headerSize,
|
||||
long typeSize,
|
||||
String typeName) throws IOException {
|
||||
|
||||
long length = originalArrayLength;
|
||||
|
||||
// now get the current position to calculate length
|
||||
long dumpEnd = fos.getChannel().position();
|
||||
long originalLengthInBytes = originalArrayLength * typeSize;
|
||||
|
||||
// calculate the length of heap data
|
||||
long currentRecordLength = (dumpEnd - currentSegmentStart - 4L);
|
||||
if (currentRecordLength > 0 &&
|
||||
(currentRecordLength + headerSize + originalLengthInBytes) > MAX_U4_VALUE) {
|
||||
fillInHeapRecordLength();
|
||||
currentSegmentStart = 0;
|
||||
writeHeapRecordPrologue();
|
||||
currentRecordLength = 0;
|
||||
}
|
||||
|
||||
// Calculate the max bytes we can use.
|
||||
long maxBytes = (MAX_U4_VALUE - (headerSize + currentRecordLength));
|
||||
|
||||
if (originalLengthInBytes > maxBytes) {
|
||||
length = maxBytes/typeSize;
|
||||
System.err.println("WARNING: Cannot dump array of type " + typeName
|
||||
+ " with length " + originalArrayLength
|
||||
+ "; truncating to length " + length);
|
||||
}
|
||||
return (int) length;
|
||||
}
|
||||
|
||||
private void writeClassDumpRecords() throws IOException {
|
||||
SystemDictionary sysDict = VM.getVM().getSystemDictionary();
|
||||
ClassLoaderDataGraph cldGraph = VM.getVM().getClassLoaderDataGraph();
|
||||
@ -694,12 +755,16 @@ public class HeapHprofBinWriter extends AbstractHeapGraphWriter {
|
||||
}
|
||||
|
||||
protected void writeObjectArray(ObjArray array) throws IOException {
|
||||
int headerSize = getArrayHeaderSize(true);
|
||||
final int length = calculateArrayMaxLength(array.getLength(),
|
||||
headerSize,
|
||||
OBJ_ID_SIZE,
|
||||
"Object");
|
||||
out.writeByte((byte) HPROF_GC_OBJ_ARRAY_DUMP);
|
||||
writeObjectID(array);
|
||||
out.writeInt(DUMMY_STACK_TRACE_ID);
|
||||
out.writeInt((int) array.getLength());
|
||||
out.writeInt(length);
|
||||
writeObjectID(array.getKlass().getJavaMirror());
|
||||
final int length = (int) array.getLength();
|
||||
for (int index = 0; index < length; index++) {
|
||||
OopHandle handle = array.getOopHandleAt(index);
|
||||
writeObjectID(getAddressValue(handle));
|
||||
@ -707,101 +772,101 @@ public class HeapHprofBinWriter extends AbstractHeapGraphWriter {
|
||||
}
|
||||
|
||||
protected void writePrimitiveArray(TypeArray array) throws IOException {
|
||||
int headerSize = getArrayHeaderSize(false);
|
||||
TypeArrayKlass tak = (TypeArrayKlass) array.getKlass();
|
||||
final int type = (int) tak.getElementType();
|
||||
final String typeName = tak.getElementTypeName();
|
||||
final long typeSize = getSizeForType(type);
|
||||
final int length = calculateArrayMaxLength(array.getLength(),
|
||||
headerSize,
|
||||
typeSize,
|
||||
typeName);
|
||||
out.writeByte((byte) HPROF_GC_PRIM_ARRAY_DUMP);
|
||||
writeObjectID(array);
|
||||
out.writeInt(DUMMY_STACK_TRACE_ID);
|
||||
out.writeInt((int) array.getLength());
|
||||
TypeArrayKlass tak = (TypeArrayKlass) array.getKlass();
|
||||
final int type = (int) tak.getElementType();
|
||||
out.writeInt(length);
|
||||
out.writeByte((byte) type);
|
||||
switch (type) {
|
||||
case TypeArrayKlass.T_BOOLEAN:
|
||||
writeBooleanArray(array);
|
||||
writeBooleanArray(array, length);
|
||||
break;
|
||||
case TypeArrayKlass.T_CHAR:
|
||||
writeCharArray(array);
|
||||
writeCharArray(array, length);
|
||||
break;
|
||||
case TypeArrayKlass.T_FLOAT:
|
||||
writeFloatArray(array);
|
||||
writeFloatArray(array, length);
|
||||
break;
|
||||
case TypeArrayKlass.T_DOUBLE:
|
||||
writeDoubleArray(array);
|
||||
writeDoubleArray(array, length);
|
||||
break;
|
||||
case TypeArrayKlass.T_BYTE:
|
||||
writeByteArray(array);
|
||||
writeByteArray(array, length);
|
||||
break;
|
||||
case TypeArrayKlass.T_SHORT:
|
||||
writeShortArray(array);
|
||||
writeShortArray(array, length);
|
||||
break;
|
||||
case TypeArrayKlass.T_INT:
|
||||
writeIntArray(array);
|
||||
writeIntArray(array, length);
|
||||
break;
|
||||
case TypeArrayKlass.T_LONG:
|
||||
writeLongArray(array);
|
||||
writeLongArray(array, length);
|
||||
break;
|
||||
default:
|
||||
throw new RuntimeException("should not reach here");
|
||||
throw new RuntimeException(
|
||||
"Should not reach here: Unknown type: " + type);
|
||||
}
|
||||
}
|
||||
|
||||
private void writeBooleanArray(TypeArray array) throws IOException {
|
||||
final int length = (int) array.getLength();
|
||||
private void writeBooleanArray(TypeArray array, int length) throws IOException {
|
||||
for (int index = 0; index < length; index++) {
|
||||
long offset = BOOLEAN_BASE_OFFSET + index * BOOLEAN_SIZE;
|
||||
out.writeBoolean(array.getHandle().getJBooleanAt(offset));
|
||||
}
|
||||
}
|
||||
|
||||
private void writeByteArray(TypeArray array) throws IOException {
|
||||
final int length = (int) array.getLength();
|
||||
private void writeByteArray(TypeArray array, int length) throws IOException {
|
||||
for (int index = 0; index < length; index++) {
|
||||
long offset = BYTE_BASE_OFFSET + index * BYTE_SIZE;
|
||||
out.writeByte(array.getHandle().getJByteAt(offset));
|
||||
}
|
||||
}
|
||||
|
||||
private void writeShortArray(TypeArray array) throws IOException {
|
||||
final int length = (int) array.getLength();
|
||||
private void writeShortArray(TypeArray array, int length) throws IOException {
|
||||
for (int index = 0; index < length; index++) {
|
||||
long offset = SHORT_BASE_OFFSET + index * SHORT_SIZE;
|
||||
out.writeShort(array.getHandle().getJShortAt(offset));
|
||||
}
|
||||
}
|
||||
|
||||
private void writeIntArray(TypeArray array) throws IOException {
|
||||
final int length = (int) array.getLength();
|
||||
private void writeIntArray(TypeArray array, int length) throws IOException {
|
||||
for (int index = 0; index < length; index++) {
|
||||
long offset = INT_BASE_OFFSET + index * INT_SIZE;
|
||||
out.writeInt(array.getHandle().getJIntAt(offset));
|
||||
}
|
||||
}
|
||||
|
||||
private void writeLongArray(TypeArray array) throws IOException {
|
||||
final int length = (int) array.getLength();
|
||||
private void writeLongArray(TypeArray array, int length) throws IOException {
|
||||
for (int index = 0; index < length; index++) {
|
||||
long offset = LONG_BASE_OFFSET + index * LONG_SIZE;
|
||||
out.writeLong(array.getHandle().getJLongAt(offset));
|
||||
}
|
||||
}
|
||||
|
||||
private void writeCharArray(TypeArray array) throws IOException {
|
||||
final int length = (int) array.getLength();
|
||||
private void writeCharArray(TypeArray array, int length) throws IOException {
|
||||
for (int index = 0; index < length; index++) {
|
||||
long offset = CHAR_BASE_OFFSET + index * CHAR_SIZE;
|
||||
out.writeChar(array.getHandle().getJCharAt(offset));
|
||||
}
|
||||
}
|
||||
|
||||
private void writeFloatArray(TypeArray array) throws IOException {
|
||||
final int length = (int) array.getLength();
|
||||
private void writeFloatArray(TypeArray array, int length) throws IOException {
|
||||
for (int index = 0; index < length; index++) {
|
||||
long offset = FLOAT_BASE_OFFSET + index * FLOAT_SIZE;
|
||||
out.writeFloat(array.getHandle().getJFloatAt(offset));
|
||||
}
|
||||
}
|
||||
|
||||
private void writeDoubleArray(TypeArray array) throws IOException {
|
||||
final int length = (int) array.getLength();
|
||||
private void writeDoubleArray(TypeArray array, int length) throws IOException {
|
||||
for (int index = 0; index < length; index++) {
|
||||
long offset = DOUBLE_BASE_OFFSET + index * DOUBLE_SIZE;
|
||||
out.writeDouble(array.getHandle().getJDoubleAt(offset));
|
||||
@ -996,12 +1061,7 @@ public class HeapHprofBinWriter extends AbstractHeapGraphWriter {
|
||||
// writes hprof binary file header
|
||||
private void writeFileHeader() throws IOException {
|
||||
// version string
|
||||
if(useSegmentedHeapDump) {
|
||||
out.writeBytes(HPROF_HEADER_1_0_2);
|
||||
}
|
||||
else {
|
||||
out.writeBytes(HPROF_HEADER_1_0_1);
|
||||
}
|
||||
out.writeBytes(HPROF_HEADER_1_0_2);
|
||||
out.writeByte((byte)'\0');
|
||||
|
||||
// write identifier size. we use pointers as identifiers.
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user