This commit is contained in:
J. Duke 2017-07-05 22:36:07 +02:00
commit b0e2047cea
3725 changed files with 461501 additions and 19457 deletions

View File

@ -391,3 +391,4 @@ ff98aa9ec9fae991e426ce5926fc9036d25f5562 jdk-9+145
a22e2671d88f6b22a4aa82e3966986542ed2a381 jdk-9+146
5f6920274c48eb00d31afee6c034826a754c13d9 jdk-9+147
3ffc3e886c74736e387f3685e86b557cdea706c8 jdk-9+148
b119012d1c2ab2570fe8718633840d0c1f1f441d jdk-9+149

File diff suppressed because it is too large Load Diff

View File

@ -50,9 +50,6 @@ BOOT_JDK := $(JDK_IMAGE_DIR)
# The bootcycle build has a different output directory
OLD_BUILD_OUTPUT:=@BUILD_OUTPUT@
BUILD_OUTPUT:=$(OLD_BUILD_OUTPUT)/bootcycle-build
# The HOTSPOT_DIST dir is not defined relative to BUILD_OUTPUT in spec.gmk. Must not
# use space in this patsubst to avoid leading space in HOTSPOT_DIST.
HOTSPOT_DIST:=$(patsubst $(OLD_BUILD_OUTPUT)%,$(BUILD_OUTPUT)%,$(HOTSPOT_DIST))
SJAVAC_SERVER_DIR:=$(patsubst $(OLD_BUILD_OUTPUT)%, $(BUILD_OUTPUT)%, $(SJAVAC_SERVER_DIR))
JAVA_CMD:=$(BOOT_JDK)/bin/java

View File

@ -44,15 +44,12 @@ SYSROOT_LDFLAGS := @BUILD_SYSROOT_LDFLAGS@
# These directories should not be moved to BUILDJDK_OUTPUTDIR
HOTSPOT_OUTPUTDIR := $(patsubst $(BUILD_OUTPUT)%,$(BUILDJDK_OUTPUTDIR)%,$(HOTSPOT_OUTPUTDIR))
HOTSPOT_DIST := $(patsubst $(BUILD_OUTPUT)%,$(BUILDJDK_OUTPUTDIR)%,$(HOTSPOT_DIST))
SUPPORT_OUTPUTDIR := $(patsubst $(BUILD_OUTPUT)%,$(BUILDJDK_OUTPUTDIR)%,$(SUPPORT_OUTPUTDIR))
JDK_OUTPUTDIR := $(patsubst $(BUILD_OUTPUT)%,$(BUILDJDK_OUTPUTDIR)%,$(JDK_OUTPUTDIR))
IMAGES_OUTPUTDIR := $(patsubst $(BUILD_OUTPUT)%,$(BUILDJDK_OUTPUTDIR)%,$(IMAGES_OUTPUTDIR))
OPENJDK_BUILD_CPU_LEGACY := @OPENJDK_BUILD_CPU_LEGACY@
OPENJDK_BUILD_CPU_LEGACY_LIB := @OPENJDK_BUILD_CPU_LEGACY_LIB@
OPENJDK_BUILD_CPU_LIBDIR := @OPENJDK_BUILD_CPU_LIBDIR@
OPENJDK_TARGET_CPU_LIBDIR := @OPENJDK_BUILD_CPU_LIBDIR@
OPENJDK_TARGET_CPU := @OPENJDK_BUILD_CPU@
OPENJDK_TARGET_CPU_ARCH := @OPENJDK_BUILD_CPU_ARCH@
OPENJDK_TARGET_CPU_BITS := @OPENJDK_BUILD_CPU_BITS@
@ -90,6 +87,7 @@ ENABLE_DEBUG_SYMBOLS := false
BUILD_GTEST := false
JVM_VARIANTS := server
JVM_VARIANT_MAIN := server
# Some users still set EXTRA_*FLAGS on the make command line. Must
# make sure to override that when building buildjdk.

View File

@ -33,7 +33,6 @@ export LEGACY_BUILD_DIR=@OPENJDK_TARGET_OS@-@OPENJDK_TARGET_CPU_LEGACY@
export OPENJDK_TARGET_OS="@OPENJDK_TARGET_OS@"
export OPENJDK_TARGET_CPU="@OPENJDK_TARGET_CPU@"
export OPENJDK_TARGET_CPU_LIBDIR="@OPENJDK_TARGET_CPU_LIBDIR@"
export DEBUG_LEVEL="@DEBUG_LEVEL@"
export AWK="@AWK@"

View File

@ -205,7 +205,7 @@ JDKOPT_SETUP_CODE_COVERAGE
# Need toolchain to setup dtrace
HOTSPOT_SETUP_DTRACE
HOTSPOT_SETUP_JVM_FEATURES
HOTSPOT_ENABLE_DISABLE_AOT
HOTSPOT_ENABLE_DISABLE_GTEST
###############################################################################
@ -220,6 +220,10 @@ BASIC_COMPILE_FIXPATH
LIB_DETERMINE_DEPENDENCIES
LIB_SETUP_LIBRARIES
# Hotspot setup depends on lib checks (AOT needs libelf).
HOTSPOT_SETUP_JVM_FEATURES
###############################################################################
#
# We need to do some final tweaking, when everything else is done.

View File

@ -23,6 +23,101 @@
# questions.
#
################################################################################
#
# Setup ABI profile (for arm)
#
AC_DEFUN([FLAGS_SETUP_ABI_PROFILE],
[
AC_ARG_WITH(abi-profile, [AS_HELP_STRING([--with-abi-profile],
[specify ABI profile for ARM builds (arm-vfp-sflt,arm-vfp-hflt,arm-sflt, armv5-vfp-sflt,armv6-vfp-hflt,arm64,aarch64) @<:@toolchain dependent@:>@ ])])
if test "x$with_abi_profile" != x; then
if test "x$OPENJDK_TARGET_CPU" != xarm && \
test "x$OPENJDK_TARGET_CPU" != xaarch64; then
AC_MSG_ERROR([--with-abi-profile only available on arm/aarch64])
fi
OPENJDK_TARGET_ABI_PROFILE=$with_abi_profile
AC_MSG_CHECKING([for ABI profle])
AC_MSG_RESULT([$OPENJDK_TARGET_ABI_PROFILE])
if test "x$OPENJDK_TARGET_ABI_PROFILE" = xarm-vfp-sflt; then
ARM_FLOAT_TYPE=vfp-sflt
ARM_ARCH_TYPE_FLAGS='-march=armv7-a -mthumb'
elif test "x$OPENJDK_TARGET_ABI_PROFILE" = xarm-vfp-hflt; then
ARM_FLOAT_TYPE=vfp-hflt
ARM_ARCH_TYPE_FLAGS='-march=armv7-a -mthumb'
elif test "x$OPENJDK_TARGET_ABI_PROFILE" = xarm-sflt; then
ARM_FLOAT_TYPE=sflt
ARM_ARCH_TYPE_FLAGS='-march=armv5t -marm'
elif test "x$OPENJDK_TARGET_ABI_PROFILE" = xarmv5-vfp-sflt; then
ARM_FLOAT_TYPE=vfp-sflt
ARM_ARCH_TYPE_FLAGS='-march=armv5t -marm'
elif test "x$OPENJDK_TARGET_ABI_PROFILE" = xarmv6-vfp-hflt; then
ARM_FLOAT_TYPE=vfp-hflt
ARM_ARCH_TYPE_FLAGS='-march=armv6 -marm'
elif test "x$OPENJDK_TARGET_ABI_PROFILE" = xarm64; then
# No special flags, just need to trigger setting JDK_ARCH_ABI_PROP_NAME
ARM_FLOAT_TYPE=
ARM_ARCH_TYPE_FLAGS=
elif test "x$OPENJDK_TARGET_ABI_PROFILE" = xaarch64; then
# No special flags, just need to trigger setting JDK_ARCH_ABI_PROP_NAME
ARM_FLOAT_TYPE=
ARM_ARCH_TYPE_FLAGS=
else
AC_MSG_ERROR([Invalid ABI profile: "$OPENJDK_TARGET_ABI_PROFILE"])
fi
if test "x$ARM_FLOAT_TYPE" = xvfp-sflt; then
ARM_FLOAT_TYPE_FLAGS='-mfloat-abi=softfp -mfpu=vfp -DFLOAT_ARCH=-vfp-sflt'
elif test "x$ARM_FLOAT_TYPE" = xvfp-hflt; then
ARM_FLOAT_TYPE_FLAGS='-mfloat-abi=hard -mfpu=vfp -DFLOAT_ARCH=-vfp-hflt'
elif test "x$ARM_FLOAT_TYPE" = xsflt; then
ARM_FLOAT_TYPE_FLAGS='-msoft-float -mfpu=vfp'
fi
AC_MSG_CHECKING([for $ARM_FLOAT_TYPE floating point flags])
AC_MSG_RESULT([$ARM_FLOAT_TYPE_FLAGS])
AC_MSG_CHECKING([for arch type flags])
AC_MSG_RESULT([$ARM_ARCH_TYPE_FLAGS])
# Now set JDK_ARCH_ABI_PROP_NAME. This is equivalent to the last part of the
# autoconf target triplet.
[ JDK_ARCH_ABI_PROP_NAME=`$ECHO $OPENJDK_TARGET_AUTOCONF_NAME | $SED -e 's/.*-\([^-]*\)$/\1/'` ]
# Sanity check that it is a known ABI.
if test "x$JDK_ARCH_ABI_PROP_NAME" != xgnu && \
test "x$JDK_ARCH_ABI_PROP_NAME" != xgnueabi && \
test "x$JDK_ARCH_ABI_PROP_NAME" != xgnueabihf; then
AC_MSG_WARN([Unknown autoconf target triplet ABI: "$JDK_ARCH_ABI_PROP_NAME"])
fi
AC_MSG_CHECKING([for ABI property name])
AC_MSG_RESULT([$JDK_ARCH_ABI_PROP_NAME])
AC_SUBST(JDK_ARCH_ABI_PROP_NAME)
# Pass these on to the open part of configure as if they were set using
# --with-extra-c[xx]flags.
EXTRA_CFLAGS="$EXTRA_CFLAGS $ARM_ARCH_TYPE_FLAGS $ARM_FLOAT_TYPE_FLAGS"
EXTRA_CXXFLAGS="$EXTRA_CXXFLAGS $ARM_ARCH_TYPE_FLAGS $ARM_FLOAT_TYPE_FLAGS"
# Get rid of annoying "note: the mangling of 'va_list' has changed in GCC 4.4"
# FIXME: This should not really be set using extra_cflags.
if test "x$OPENJDK_TARGET_CPU" = xarm; then
EXTRA_CFLAGS="$EXTRA_CFLAGS -Wno-psabi"
EXTRA_CXXFLAGS="$EXTRA_CXXFLAGS -Wno-psabi"
fi
# Also add JDK_ARCH_ABI_PROP_NAME define, but only to CFLAGS.
EXTRA_CFLAGS="$EXTRA_CFLAGS -DJDK_ARCH_ABI_PROP_NAME='\"\$(JDK_ARCH_ABI_PROP_NAME)\"'"
# And pass the architecture flags to the linker as well
EXTRA_LDFLAGS="$EXTRA_LDFLAGS $ARM_ARCH_TYPE_FLAGS $ARM_FLOAT_TYPE_FLAGS"
fi
# When building with an abi profile, the name of that profile is appended on the
# bundle platform, which is used in bundle names.
if test "x$OPENJDK_TARGET_ABI_PROFILE" != x; then
OPENJDK_TARGET_BUNDLE_PLATFORM="$OPENJDK_TARGET_OS_BUNDLE-$OPENJDK_TARGET_ABI_PROFILE"
fi
])
# Reset the global CFLAGS/LDFLAGS variables and initialize them with the
# corresponding configure arguments instead
AC_DEFUN_ONCE([FLAGS_SETUP_USER_SUPPLIED_FLAGS],
@ -306,9 +401,17 @@ AC_DEFUN([FLAGS_SETUP_COMPILER_FLAGS_FOR_LIBS],
PICFLAG='-fPIC'
SHARED_LIBRARY_FLAGS='-shared'
SET_EXECUTABLE_ORIGIN='-Wl,-rpath,\$$ORIGIN[$]1'
SET_SHARED_LIBRARY_ORIGIN="-Wl,-z,origin $SET_EXECUTABLE_ORIGIN"
SET_SHARED_LIBRARY_NAME='-Wl,-soname=[$]1'
SET_SHARED_LIBRARY_MAPFILE='-Wl,-version-script=[$]1'
# arm specific settings
if test "x$OPENJDK_TARGET_CPU" = "xarm"; then
# '-Wl,-z,origin' isn't used on arm.
SET_SHARED_LIBRARY_ORIGIN='-Wl,-rpath,\$$$$ORIGIN[$]1'
else
SET_SHARED_LIBRARY_ORIGIN="-Wl,-z,origin $SET_EXECUTABLE_ORIGIN"
fi
fi
elif test "x$TOOLCHAIN_TYPE" = xsolstudio; then
if test "x$OPENJDK_TARGET_CPU" = xsparcv9; then
@ -669,6 +772,7 @@ AC_DEFUN_ONCE([FLAGS_SETUP_COMPILER_FLAGS_FOR_OPTIMIZATION],
AC_DEFUN([FLAGS_SETUP_COMPILER_FLAGS_FOR_JDK],
[
FLAGS_SETUP_ABI_PROFILE
FLAGS_SETUP_COMPILER_FLAGS_FOR_JDK_HELPER([TARGET])
FLAGS_SETUP_COMPILER_FLAGS_FOR_JDK_HELPER([BUILD], [OPENJDK_BUILD_])
@ -758,6 +862,7 @@ AC_DEFUN([FLAGS_SETUP_COMPILER_FLAGS_FOR_JDK_HELPER],
arm )
# on arm we don't prevent gcc to omit frame pointer but do prevent strict aliasing
$2CFLAGS_JDK="${$2CFLAGS_JDK} -fno-strict-aliasing"
$2COMMON_CCXXFLAGS_JDK="${$2COMMON_CCXXFLAGS_JDK} -fsigned-char"
;;
ppc )
# on ppc we don't prevent gcc to omit frame pointer but do prevent strict aliasing
@ -1160,26 +1265,25 @@ AC_DEFUN([FLAGS_SETUP_COMPILER_FLAGS_FOR_JDK_HELPER],
$2JDKLIB_LIBS=""
else
$2JAVA_BASE_LDFLAGS="${$2JAVA_BASE_LDFLAGS} \
-L\$(SUPPORT_OUTPUTDIR)/modules_libs/java.base\$(OPENJDK_$1_CPU_LIBDIR)"
-L\$(SUPPORT_OUTPUTDIR)/modules_libs/java.base"
if test "x$1" = "xTARGET"; then
# On some platforms (mac) the linker warns about non existing -L dirs.
# Add server first if available. Linking aginst client does not always produce the same results.
# Only add client/minimal dir if client/minimal is being built.
# Default to server for other variants.
if HOTSPOT_CHECK_JVM_VARIANT(server); then
$2JAVA_BASE_LDFLAGS="${$2JAVA_BASE_LDFLAGS} -L\$(SUPPORT_OUTPUTDIR)/modules_libs/java.base\$(OPENJDK_$1_CPU_LIBDIR)/server"
elif HOTSPOT_CHECK_JVM_VARIANT(client); then
$2JAVA_BASE_LDFLAGS="${$2JAVA_BASE_LDFLAGS} -L\$(SUPPORT_OUTPUTDIR)/modules_libs/java.base\$(OPENJDK_$1_CPU_LIBDIR)/client"
elif HOTSPOT_CHECK_JVM_VARIANT(minimal); then
$2JAVA_BASE_LDFLAGS="${$2JAVA_BASE_LDFLAGS} -L\$(SUPPORT_OUTPUTDIR)/modules_libs/java.base\$(OPENJDK_$1_CPU_LIBDIR)/minimal"
else
$2JAVA_BASE_LDFLAGS="${$2JAVA_BASE_LDFLAGS} -L\$(SUPPORT_OUTPUTDIR)/modules_libs/java.base\$(OPENJDK_$1_CPU_LIBDIR)/server"
fi
# On some platforms (mac) the linker warns about non existing -L dirs.
# For any of the variants server, client or minimal, the dir matches the
# variant name. The "main" variant should be used for linking. For the
# rest, the dir is just server.
if HOTSPOT_CHECK_JVM_VARIANT(server) || HOTSPOT_CHECK_JVM_VARIANT(client) \
|| HOTSPOT_CHECK_JVM_VARIANT(minimal); then
$2JAVA_BASE_LDFLAGS="${$2JAVA_BASE_LDFLAGS} \
-L\$(SUPPORT_OUTPUTDIR)/modules_libs/java.base/$JVM_VARIANT_MAIN"
else
$2JAVA_BASE_LDFLAGS="${$2JAVA_BASE_LDFLAGS} \
-L\$(SUPPORT_OUTPUTDIR)/modules_libs/java.base/server"
fi
elif test "x$1" = "xBUILD"; then
# When building a buildjdk, it's always only the server variant
$2JAVA_BASE_LDFLAGS="${$2JAVA_BASE_LDFLAGS} \
-L\$(SUPPORT_OUTPUTDIR)/modules_libs/java.base\$(OPENJDK_$1_CPU_LIBDIR)/server"
-L\$(SUPPORT_OUTPUTDIR)/modules_libs/java.base/server"
fi
$2JDKLIB_LIBS="-ljava -ljvm"

File diff suppressed because it is too large Load Diff

View File

@ -121,6 +121,8 @@ apt_help() {
PKGHANDLER_COMMAND="sudo apt-get install ccache" ;;
dtrace)
PKGHANDLER_COMMAND="sudo apt-get install systemtap-sdt-dev" ;;
elf)
PKGHANDLER_COMMAND="sudo apt-get install libelf-dev" ;;
esac
}
@ -140,6 +142,8 @@ yum_help() {
PKGHANDLER_COMMAND="sudo yum install libXtst-devel libXt-devel libXrender-devel libXi-devel" ;;
ccache)
PKGHANDLER_COMMAND="sudo yum install ccache" ;;
elf)
PKGHANDLER_COMMAND="sudo yum install elfutils-libelf-devel" ;;
esac
}

View File

@ -25,7 +25,8 @@
# All valid JVM features, regardless of platform
VALID_JVM_FEATURES="compiler1 compiler2 zero shark minimal dtrace jvmti jvmci \
fprof vm-structs jni-check services management all-gcs nmt cds static-build"
graal fprof vm-structs jni-check services management all-gcs nmt cds \
static-build link-time-opt aot"
# All valid JVM variants
VALID_JVM_VARIANTS="server client minimal core zero zeroshark custom"
@ -69,6 +70,8 @@ AC_DEFUN_ONCE([HOTSPOT_SETUP_JVM_VARIANTS],
AC_ARG_WITH([jvm-variants], [AS_HELP_STRING([--with-jvm-variants],
[JVM variants (separated by commas) to build (server,client,minimal,core,zero,zeroshark,custom) @<:@server@:>@])])
SETUP_HOTSPOT_TARGET_CPU_PORT
if test "x$with_jvm_variants" = x; then
with_jvm_variants="server"
fi
@ -111,8 +114,23 @@ AC_DEFUN_ONCE([HOTSPOT_SETUP_JVM_VARIANTS],
AC_MSG_ERROR([You cannot build multiple variants with anything else than $VALID_MULTIPLE_JVM_VARIANTS.])
fi
# The "main" variant is the one used by other libs to link against during the
# build.
if test "x$BUILDING_MULTIPLE_JVM_VARIANTS" = "xtrue"; then
MAIN_VARIANT_PRIO_ORDER="server client minimal"
for variant in $MAIN_VARIANT_PRIO_ORDER; do
if HOTSPOT_CHECK_JVM_VARIANT($variant); then
JVM_VARIANT_MAIN="$variant"
break
fi
done
else
JVM_VARIANT_MAIN="$JVM_VARIANTS"
fi
AC_SUBST(JVM_VARIANTS)
AC_SUBST(VALID_JVM_VARIANTS)
AC_SUBST(JVM_VARIANT_MAIN)
if HOTSPOT_CHECK_JVM_VARIANT(zero) || HOTSPOT_CHECK_JVM_VARIANT(zeroshark); then
# zero behaves as a platform and rewrites these values. This is really weird. :(
@ -174,6 +192,55 @@ AC_DEFUN_ONCE([HOTSPOT_SETUP_DTRACE],
AC_SUBST(INCLUDE_DTRACE)
])
################################################################################
# Check if AOT should be enabled
#
AC_DEFUN_ONCE([HOTSPOT_ENABLE_DISABLE_AOT],
[
AC_ARG_ENABLE([aot], [AS_HELP_STRING([--enable-aot@<:@=yes/no/auto@:>@],
[enable ahead of time compilation feature. Default is auto, where aot is enabled if all dependencies are present.])])
if test "x$enable_aot" = "x" || test "x$enable_aot" = "xauto"; then
ENABLE_AOT="true"
elif test "x$enable_aot" = "xyes"; then
ENABLE_AOT="true"
elif test "x$enable_aot" = "xno"; then
ENABLE_AOT="false"
AC_MSG_CHECKING([if aot should be enabled])
AC_MSG_RESULT([no, forced])
else
AC_MSG_ERROR([Invalid value for --enable-aot: $enable_aot])
fi
if test "x$ENABLE_AOT" = "xtrue"; then
# Only enable AOT on linux-X64.
if test "x$OPENJDK_TARGET_OS-$OPENJDK_TARGET_CPU" = "xlinux-x86_64"; then
if test -e "$HOTSPOT_TOPDIR/src/jdk.aot"; then
if test -e "$HOTSPOT_TOPDIR/src/jdk.vm.compiler"; then
ENABLE_AOT="true"
else
ENABLE_AOT="false"
if test "x$enable_aot" = "xyes"; then
AC_MSG_ERROR([Cannot build AOT without hotspot/src/jdk.vm.compiler sources. Remove --enable-aot.])
fi
fi
else
ENABLE_AOT="false"
if test "x$enable_aot" = "xyes"; then
AC_MSG_ERROR([Cannot build AOT without hotspot/src/jdk.aot sources. Remove --enable-aot.])
fi
fi
else
ENABLE_AOT="false"
if test "x$enable_aot" = "xyes"; then
AC_MSG_ERROR([AOT is currently only supported on Linux-x86_64. Remove --enable-aot.])
fi
fi
fi
AC_SUBST(ENABLE_AOT)
])
###############################################################################
# Set up all JVM features for each JVM variant.
#
@ -189,6 +256,19 @@ AC_DEFUN_ONCE([HOTSPOT_SETUP_JVM_FEATURES],
AC_MSG_RESULT([$JVM_FEATURES])
fi
# Override hotspot cpu definitions for ARM platforms
if test "x$OPENJDK_TARGET_CPU" = xarm; then
HOTSPOT_TARGET_CPU=arm_32
HOTSPOT_TARGET_CPU_DEFINE="ARM32"
JVM_LDFLAGS="$JVM_LDFLAGS -fsigned-char"
JVM_CFLAGS="$JVM_CFLAGS -DARM -fsigned-char"
elif test "x$OPENJDK_TARGET_CPU" = xaarch64 && test "x$HOTSPOT_TARGET_CPU_PORT" = xarm64; then
HOTSPOT_TARGET_CPU=arm_64
HOTSPOT_TARGET_CPU_ARCH=arm
JVM_LDFLAGS="$JVM_LDFLAGS -fsigned-char"
JVM_CFLAGS="$JVM_CFLAGS -DARM -fsigned-char"
fi
# Verify that dependencies are met for explicitly set features.
if HOTSPOT_CHECK_JVM_FEATURE(jvmti) && ! HOTSPOT_CHECK_JVM_FEATURE(services); then
AC_MSG_ERROR([Specified JVM feature 'jvmti' requires feature 'services'])
@ -241,21 +321,67 @@ AC_DEFUN_ONCE([HOTSPOT_SETUP_JVM_FEATURES],
# Only enable jvmci on x86_64, sparcv9 and aarch64.
if test "x$OPENJDK_TARGET_CPU" = "xx86_64" || \
test "x$OPENJDK_TARGET_CPU" = "xsparcv9" || \
test "x$OPENJDK_TARGET_CPU" = "xaarch64" ; then
test "x$OPENJDK_TARGET_CPU" = "xsparcv9" || \
test "x$OPENJDK_TARGET_CPU" = "xaarch64" ; then
JVM_FEATURES_jvmci="jvmci"
else
JVM_FEATURES_jvmci=""
fi
AC_MSG_CHECKING([if jdk.vm.compiler should be built])
if HOTSPOT_CHECK_JVM_FEATURE(graal); then
AC_MSG_RESULT([yes, forced])
if test "x$JVM_FEATURES_jvmci" != "xjvmci" ; then
AC_MSG_ERROR([Specified JVM feature 'graal' requires feature 'jvmci'])
fi
INCLUDE_GRAAL="true"
else
# By default enable graal build where AOT is available
if test "x$ENABLE_AOT" = "xtrue"; then
AC_MSG_RESULT([yes])
JVM_FEATURES_graal="graal"
INCLUDE_GRAAL="true"
else
AC_MSG_RESULT([no])
JVM_FEATURES_graal=""
INCLUDE_GRAAL="false"
fi
fi
AC_SUBST(INCLUDE_GRAAL)
AC_MSG_CHECKING([if aot should be enabled])
if test "x$ENABLE_AOT" = "xtrue"; then
if test "x$enable_aot" = "xyes"; then
AC_MSG_RESULT([yes, forced])
else
AC_MSG_RESULT([yes])
fi
JVM_FEATURES_aot="aot"
else
if test "x$enable_aot" = "xno"; then
AC_MSG_RESULT([no, forced])
else
AC_MSG_RESULT([no])
fi
JVM_FEATURES_aot=""
fi
if test "x$OPENJDK_TARGET_CPU" = xarm ; then
# Default to use link time optimizations on minimal on arm
JVM_FEATURES_link_time_opt="link-time-opt"
else
JVM_FEATURES_link_time_opt=""
fi
# All variants but minimal (and custom) get these features
NON_MINIMAL_FEATURES="$NON_MINIMAL_FEATURES jvmti fprof vm-structs jni-check services management all-gcs nmt cds"
# Enable features depending on variant.
JVM_FEATURES_server="compiler1 compiler2 $NON_MINIMAL_FEATURES $JVM_FEATURES $JVM_FEATURES_jvmci"
JVM_FEATURES_server="compiler1 compiler2 $NON_MINIMAL_FEATURES $JVM_FEATURES $JVM_FEATURES_jvmci $JVM_FEATURES_aot $JVM_FEATURES_graal"
JVM_FEATURES_client="compiler1 $NON_MINIMAL_FEATURES $JVM_FEATURES $JVM_FEATURES_jvmci"
JVM_FEATURES_core="$NON_MINIMAL_FEATURES $JVM_FEATURES"
JVM_FEATURES_minimal="compiler1 minimal $JVM_FEATURES"
JVM_FEATURES_minimal="compiler1 minimal $JVM_FEATURES $JVM_FEATURES_link_time_opt"
JVM_FEATURES_zero="zero $NON_MINIMAL_FEATURES $JVM_FEATURES"
JVM_FEATURES_zeroshark="zero shark $NON_MINIMAL_FEATURES $JVM_FEATURES"
JVM_FEATURES_custom="$JVM_FEATURES"
@ -304,6 +430,31 @@ AC_DEFUN_ONCE([HOTSPOT_VALIDATE_JVM_FEATURES],
done
])
################################################################################
#
# Specify which sources will be used to build the 64-bit ARM port
#
# --with-cpu-port=arm64 will use hotspot/src/cpu/arm
# --with-cpu-port=aarch64 will use hotspot/src/cpu/aarch64
#
AC_DEFUN([SETUP_HOTSPOT_TARGET_CPU_PORT],
[
AC_ARG_WITH(cpu-port, [AS_HELP_STRING([--with-cpu-port],
[specify sources to use for Hotspot 64-bit ARM port (arm64,aarch64) @<:@aarch64@:>@ ])])
if test "x$with_cpu_port" != x; then
if test "x$OPENJDK_TARGET_CPU" != xaarch64; then
AC_MSG_ERROR([--with-cpu-port only available on aarch64])
fi
if test "x$with_cpu_port" != xarm64 && \
test "x$with_cpu_port" != xaarch64; then
AC_MSG_ERROR([--with-cpu-port must specify arm64 or aarch64])
fi
HOTSPOT_TARGET_CPU_PORT="$with_cpu_port"
fi
])
################################################################################
# Check if gtest should be built
#

129
common/autoconf/lib-elf.m4 Normal file
View File

@ -0,0 +1,129 @@
#
# Copyright (c) 2015, 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
# under the terms of the GNU General Public License version 2 only, as
# published by the Free Software Foundation. Oracle designates this
# particular file as subject to the "Classpath" exception as provided
# by Oracle in the LICENSE file that accompanied this code.
#
# This code is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
# version 2 for more details (a copy is included in the LICENSE file that
# accompanied this code).
#
# You should have received a copy of the GNU General Public License version
# 2 along with this work; if not, write to the Free Software Foundation,
# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
#
# 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.
#
################################################################################
# Setup libelf (ELF library)
################################################################################
AC_DEFUN_ONCE([LIB_SETUP_LIBELF],
[
AC_ARG_WITH(libelf, [AS_HELP_STRING([--with-libelf],
[specify prefix directory for the libelf package
(expecting the libraries under PATH/lib and the headers under PATH/include)])])
AC_ARG_WITH(libelf-include, [AS_HELP_STRING([--with-libelf-include],
[specify directory for the libelf include files])])
AC_ARG_WITH(libelf-lib, [AS_HELP_STRING([--with-libelf-lib],
[specify directory for the libelf library])])
if test "x$ENABLE_AOT" = xfalse; then
if (test "x${with_libelf}" != x && test "x${with_libelf}" != xno) || \
(test "x${with_libelf_include}" != x && test "x${with_libelf_include}" != xno) || \
(test "x${with_libelf_lib}" != x && test "x${with_libelf_lib}" != xno); then
AC_MSG_WARN([[libelf is not used, so --with-libelf[-*] is ignored]])
fi
LIBELF_CFLAGS=
LIBELF_LIBS=
else
LIBELF_FOUND=no
if test "x${with_libelf}" = xno || test "x${with_libelf_include}" = xno || test "x${with_libelf_lib}" = xno; then
ENABLE_AOT="false"
if test "x${enable_aot}" = xyes; then
AC_MSG_ERROR([libelf is explicitly disabled, cannot build AOT. Enable libelf or remove --enable-aot to disable AOT.])
fi
else
if test "x${with_libelf}" != x; then
ELF_LIBS="-L${with_libelf}/lib -lelf"
ELF_CFLAGS="-I${with_libelf}/include"
LIBELF_FOUND=yes
fi
if test "x${with_libelf_include}" != x; then
ELF_CFLAGS="-I${with_libelf_include}"
LIBELF_FOUND=yes
fi
if test "x${with_libelf_lib}" != x; then
ELF_LIBS="-L${with_libelf_lib} -lelf"
LIBELF_FOUND=yes
fi
# Do not try pkg-config if we have a sysroot set.
if test "x$SYSROOT" = x; then
if test "x$LIBELF_FOUND" = xno; then
# Figure out ELF_CFLAGS and ELF_LIBS
PKG_CHECK_MODULES([ELF], [libelf], [LIBELF_FOUND=yes], [LIBELF_FOUND=no])
fi
fi
if test "x$LIBELF_FOUND" = xno; then
AC_CHECK_HEADERS([libelf.h],
[
LIBELF_FOUND=yes
ELF_CFLAGS=
ELF_LIBS=-lelf
],
[LIBELF_FOUND=no]
)
fi
if test "x$LIBELF_FOUND" = xno; then
ENABLE_AOT="false"
HELP_MSG_MISSING_DEPENDENCY([elf])
if test "x${enable_aot}" = xyes; then
AC_MSG_ERROR([libelf not found, cannot build AOT. Remove --enable-aot to disable AOT or: $HELP_MSG])
else
AC_MSG_WARN([libelf not found, cannot build AOT. $HELP_MSG])
fi
else
AC_MSG_CHECKING([if libelf works])
AC_LANG_PUSH(C)
OLD_CFLAGS="$CFLAGS"
CFLAGS="$CFLAGS $ELF_CFLAGS"
OLD_LIBS="$LIBS"
LIBS="$LIBS $ELF_LIBS"
AC_LINK_IFELSE([AC_LANG_PROGRAM([#include <libelf.h>],
[
elf_version(0);
return 0;
])],
[LIBELF_WORKS=yes],
[LIBELF_WORKS=no]
)
CFLAGS="$OLD_CFLAGS"
LIBS="$OLD_LIBS"
AC_LANG_POP(C)
AC_MSG_RESULT([$LIBELF_WORKS])
if test "x$LIBELF_WORKS" = xno; then
ENABLE_AOT="false"
HELP_MSG_MISSING_DEPENDENCY([elf])
if test "x$enable_aot" = "xyes"; then
AC_MSG_ERROR([Found libelf but could not link and compile with it. Remove --enable-aot to disable AOT or: $HELP_MSG])
else
AC_MSG_WARN([Found libelf but could not link and compile with it. $HELP_MSG])
fi
fi
fi
fi
fi
AC_SUBST(ELF_CFLAGS)
AC_SUBST(ELF_LIBS)
])

View File

@ -31,6 +31,7 @@ m4_include([lib-ffi.m4])
m4_include([lib-freetype.m4])
m4_include([lib-std.m4])
m4_include([lib-x11.m4])
m4_include([lib-elf.m4])
################################################################################
# Determine which libraries are needed for this configuration
@ -90,6 +91,7 @@ AC_DEFUN_ONCE([LIB_SETUP_LIBRARIES],
LIB_SETUP_BUNDLED_LIBS
LIB_SETUP_MISC_LIBS
LIB_SETUP_SOLARIS_STLPORT
LIB_SETUP_LIBELF
])
################################################################################

View File

@ -308,15 +308,6 @@ AC_DEFUN([PLATFORM_SETUP_LEGACY_VARS_HELPER],
fi
AC_SUBST(OPENJDK_$1_CPU_LEGACY_LIB)
# This is the name of the cpu (but using i386 and amd64 instead of
# x86 and x86_64, respectively), preceeded by a /, to be used when
# locating libraries. On macosx, it's empty, though.
OPENJDK_$1_CPU_LIBDIR="/$OPENJDK_$1_CPU_LEGACY_LIB"
if test "x$OPENJDK_$1_OS" = xmacosx; then
OPENJDK_$1_CPU_LIBDIR=""
fi
AC_SUBST(OPENJDK_$1_CPU_LIBDIR)
# OPENJDK_$1_CPU_ISADIR is normally empty. On 64-bit Solaris systems, it is set to
# /amd64 or /sparcv9. This string is appended to some library paths, like this:
# /usr/lib${OPENJDK_$1_CPU_ISADIR}/libexample.so
@ -348,16 +339,6 @@ AC_DEFUN([PLATFORM_SETUP_LEGACY_VARS_HELPER],
# On all platforms except macosx, we replace x86_64 with amd64.
OPENJDK_$1_CPU_JLI="amd64"
fi
# Now setup the -D flags for building libjli.
OPENJDK_$1_CPU_JLI_CFLAGS="-DLIBARCHNAME='\"$OPENJDK_$1_CPU_JLI\"'"
if test "x$OPENJDK_$1_OS" = xsolaris; then
if test "x$OPENJDK_$1_CPU_ARCH" = xsparc; then
OPENJDK_$1_CPU_JLI_CFLAGS="$OPENJDK_$1_CPU_JLI_CFLAGS -DLIBARCH32NAME='\"sparc\"' -DLIBARCH64NAME='\"sparcv9\"'"
elif test "x$OPENJDK_$1_CPU_ARCH" = xx86; then
OPENJDK_$1_CPU_JLI_CFLAGS="$OPENJDK_$1_CPU_JLI_CFLAGS -DLIBARCH32NAME='\"i386\"' -DLIBARCH64NAME='\"amd64\"'"
fi
fi
AC_SUBST(OPENJDK_$1_CPU_JLI_CFLAGS)
if test "x$OPENJDK_$1_OS" = xmacosx; then
OPENJDK_$1_OS_EXPORT_DIR=macosx

View File

@ -62,27 +62,9 @@ AC_DEFUN_ONCE([SRCDIRS_SETUP_OUTPUT_DIRS],
[
BUILD_OUTPUT="$OUTPUT_ROOT"
AC_SUBST(BUILD_OUTPUT)
HOTSPOT_DIST="$OUTPUT_ROOT/hotspot/dist"
BUILD_HOTSPOT=true
AC_SUBST(HOTSPOT_DIST)
AC_SUBST(BUILD_HOTSPOT)
AC_ARG_WITH(import-hotspot, [AS_HELP_STRING([--with-import-hotspot],
[import hotspot binaries from this jdk image or hotspot build dist dir instead of building from source])])
if test "x$with_import_hotspot" != x; then
CURDIR="$PWD"
cd "$with_import_hotspot"
HOTSPOT_DIST="`pwd`"
cd "$CURDIR"
if ! (test -d $HOTSPOT_DIST/lib && test -d $HOTSPOT_DIST/jre/lib); then
AC_MSG_ERROR([You have to import hotspot from a full jdk image or hotspot build dist dir!])
fi
AC_MSG_CHECKING([if hotspot should be imported])
AC_MSG_RESULT([yes from $HOTSPOT_DIST])
BUILD_HOTSPOT=false
fi
JDK_OUTPUTDIR="$OUTPUT_ROOT/jdk"
BASIC_DEPRECATED_ARG_WITH(import_hotspot)
])
################################################################################
@ -123,6 +105,12 @@ AC_DEFUN_ONCE([SRCDIRS_SETUP_IMPORT_MODULES],
if test -d "$IMPORT_MODULES_TOPDIR/modules_conf"; then
IMPORT_MODULES_CONF="$IMPORT_MODULES_TOPDIR/modules_conf"
fi
if test -d "$IMPORT_MODULES_TOPDIR/modules_legal"; then
IMPORT_MODULES_LEGAL="$IMPORT_MODULES_TOPDIR/modules_legal"
fi
if test -d "$IMPORT_MODULES_TOPDIR/modules_man"; then
IMPORT_MODULES_MAN="$IMPORT_MODULES_TOPDIR/modules_man"
fi
if test -d "$IMPORT_MODULES_TOPDIR/modules_src"; then
IMPORT_MODULES_SRC="$IMPORT_MODULES_TOPDIR/modules_src"
fi
@ -140,6 +128,8 @@ AC_DEFUN_ONCE([SRCDIRS_SETUP_IMPORT_MODULES],
AC_SUBST(IMPORT_MODULES_CMDS)
AC_SUBST(IMPORT_MODULES_LIBS)
AC_SUBST(IMPORT_MODULES_CONF)
AC_SUBST(IMPORT_MODULES_LEGAL)
AC_SUBST(IMPORT_MODULES_MAN)
AC_SUBST(IMPORT_MODULES_SRC)
AC_SUBST(IMPORT_MODULES_MAKE)
])

View File

@ -75,11 +75,9 @@ COMPILE_TYPE:=@COMPILE_TYPE@
# Legacy support
OPENJDK_TARGET_CPU_ISADIR:=@OPENJDK_TARGET_CPU_ISADIR@
OPENJDK_TARGET_CPU_LIBDIR:=@OPENJDK_TARGET_CPU_LIBDIR@
OPENJDK_TARGET_CPU_LEGACY:=@OPENJDK_TARGET_CPU_LEGACY@
OPENJDK_TARGET_CPU_LEGACY_LIB:=@OPENJDK_TARGET_CPU_LEGACY_LIB@
OPENJDK_TARGET_CPU_OSARCH:=@OPENJDK_TARGET_CPU_OSARCH@
OPENJDK_TARGET_CPU_JLI_CFLAGS:=@OPENJDK_TARGET_CPU_JLI_CFLAGS@
OPENJDK_TARGET_OS_EXPORT_DIR:=@OPENJDK_TARGET_OS_EXPORT_DIR@
HOTSPOT_TARGET_OS := @HOTSPOT_TARGET_OS@
@ -145,6 +143,8 @@ IMPORT_MODULES_CLASSES:=@IMPORT_MODULES_CLASSES@
IMPORT_MODULES_CMDS:=@IMPORT_MODULES_CMDS@
IMPORT_MODULES_LIBS:=@IMPORT_MODULES_LIBS@
IMPORT_MODULES_CONF:=@IMPORT_MODULES_CONF@
IMPORT_MODULES_LEGAL:=@IMPORT_MODULES_LEGAL@
IMPORT_MODULES_MAN:=@IMPORT_MODULES_MAN@
IMPORT_MODULES_SRC:=@IMPORT_MODULES_SRC@
IMPORT_MODULES_MAKE:=@IMPORT_MODULES_MAKE@
@ -220,6 +220,7 @@ JDK_VARIANT:=@JDK_VARIANT@
# Which JVM variants to build (space-separated list)
JVM_VARIANTS := @JVM_VARIANTS@
JVM_VARIANT_MAIN := @JVM_VARIANT_MAIN@
# Lists of features per variant. Only relevant for the variants listed in
# JVM_VARIANTS.
@ -273,8 +274,6 @@ JAVADOC_OUTPUTDIR = $(DOCS_IMAGE_DIR)
CONFIGURESUPPORT_OUTPUTDIR:=@CONFIGURESUPPORT_OUTPUTDIR@
BUILDJDK_OUTPUTDIR=$(BUILD_OUTPUT)/buildjdk
HOTSPOT_DIST=@HOTSPOT_DIST@
BUILD_HOTSPOT=@BUILD_HOTSPOT@
BUILD_FAILURE_HANDLER := @BUILD_FAILURE_HANDLER@
@ -686,6 +685,7 @@ TAR_INCLUDE_PARAM:=@TAR_INCLUDE_PARAM@
TAR_SUPPORTS_TRANSFORM:=@TAR_SUPPORTS_TRANSFORM@
# Build setup
ENABLE_AOT:=@ENABLE_AOT@
ENABLE_JFR=@ENABLE_JFR@
ENABLE_INTREE_EC=@ENABLE_INTREE_EC@
USE_EXTERNAL_LIBJPEG:=@USE_EXTERNAL_LIBJPEG@
@ -760,6 +760,8 @@ USE_EXTERNAL_LIBPNG:=@USE_EXTERNAL_LIBPNG@
PNG_LIBS:=@PNG_LIBS@
PNG_CFLAGS:=@PNG_CFLAGS@
ELF_CFLAGS:=@ELF_CFLAGS@
ELF_LIBS:=@ELF_LIBS@
####################################################
#
@ -767,6 +769,7 @@ PNG_CFLAGS:=@PNG_CFLAGS@
#
INCLUDE_SA=@INCLUDE_SA@
INCLUDE_GRAAL=@INCLUDE_GRAAL@
OS_VERSION_MAJOR:=@OS_VERSION_MAJOR@
OS_VERSION_MINOR:=@OS_VERSION_MINOR@

View File

@ -509,30 +509,32 @@ compare_zip_file() {
| $CUT -f 2 -d ' ' | $SED "s|$OTHER_UNZIPDIR/||g")
fi
$RM -f $WORK_DIR/$ZIP_FILE.diffs
for file in $DIFFING_FILES; do
if [[ "$ACCEPTED_JARZIP_CONTENTS $EXCEPTIONS" != *"$file"* ]]; then
diff_text $OTHER_UNZIPDIR/$file $THIS_UNZIPDIR/$file >> $WORK_DIR/$ZIP_FILE.diffs
fi
done
if [ "$CMP_ZIPS_CONTENTS" = "true" ]; then
$RM -f $WORK_DIR/$ZIP_FILE.diffs
for file in $DIFFING_FILES; do
if [[ "$ACCEPTED_JARZIP_CONTENTS $EXCEPTIONS" != *"$file"* ]]; then
diff_text $OTHER_UNZIPDIR/$file $THIS_UNZIPDIR/$file >> $WORK_DIR/$ZIP_FILE.diffs
fi
done
if [ -s "$WORK_DIR/$ZIP_FILE.diffs" ]; then
return_value=1
echo " Differing files in $ZIP_FILE"
$CAT $WORK_DIR/$ZIP_FILE.diffs | $GREP 'differ$' | cut -f 2 -d ' ' | \
$SED "s|$OTHER_UNZIPDIR| |g" > $WORK_DIR/$ZIP_FILE.difflist
$CAT $WORK_DIR/$ZIP_FILE.difflist
if [ -s "$WORK_DIR/$ZIP_FILE.diffs" ]; then
return_value=1
echo " Differing files in $ZIP_FILE"
$CAT $WORK_DIR/$ZIP_FILE.diffs | $GREP 'differ$' | cut -f 2 -d ' ' | \
$SED "s|$OTHER_UNZIPDIR| |g" > $WORK_DIR/$ZIP_FILE.difflist
$CAT $WORK_DIR/$ZIP_FILE.difflist
if [ -n "$SHOW_DIFFS" ]; then
for i in $(cat $WORK_DIR/$ZIP_FILE.difflist) ; do
if [ -f "${OTHER_UNZIPDIR}/$i.javap" ]; then
LC_ALL=C $DIFF ${OTHER_UNZIPDIR}/$i.javap ${THIS_UNZIPDIR}/$i.javap
elif [ -f "${OTHER_UNZIPDIR}/$i.cleaned" ]; then
LC_ALL=C $DIFF ${OTHER_UNZIPDIR}/$i.cleaned ${THIS_UNZIPDIR}/$i
else
LC_ALL=C $DIFF ${OTHER_UNZIPDIR}/$i ${THIS_UNZIPDIR}/$i
fi
done
if [ -n "$SHOW_DIFFS" ]; then
for i in $(cat $WORK_DIR/$ZIP_FILE.difflist) ; do
if [ -f "${OTHER_UNZIPDIR}/$i.javap" ]; then
LC_ALL=C $DIFF ${OTHER_UNZIPDIR}/$i.javap ${THIS_UNZIPDIR}/$i.javap
elif [ -f "${OTHER_UNZIPDIR}/$i.cleaned" ]; then
LC_ALL=C $DIFF ${OTHER_UNZIPDIR}/$i.cleaned ${THIS_UNZIPDIR}/$i
else
LC_ALL=C $DIFF ${OTHER_UNZIPDIR}/$i ${THIS_UNZIPDIR}/$i
fi
done
fi
fi
fi
@ -1072,7 +1074,8 @@ if [ -z "$1" ] || [ "$1" = "-h" ] || [ "$1" = "-?" ] || [ "$1" = "/h" ] || [ "$1
echo "-perms Compare the permission bits on all files and directories"
echo "-types Compare the output of the file command on all files"
echo "-general Compare the files not convered by the specialized comparisons"
echo "-zips Compare the contents of all zip files"
echo "-zips Compare the contents of all zip files and files in them"
echo "-zips-names Compare the file names inside all zip files"
echo "-jars Compare the contents of all jar files"
echo "-libs Compare all native libraries"
echo "-execs Compare all executables"
@ -1100,6 +1103,7 @@ CMP_PERMS=false
CMP_TYPES=false
CMP_GENERAL=false
CMP_ZIPS=false
CMP_ZIPS_CONTENTS=true
CMP_JARS=false
CMP_LIBS=false
CMP_EXECS=false
@ -1143,6 +1147,11 @@ while [ -n "$1" ]; do
;;
-zips)
CMP_ZIPS=true
CMP_ZIPS_CONTENTS=true
;;
-zips-names)
CMP_ZIPS=true
CMP_ZIPS_CONTENTS=false
;;
-jars)
CMP_JARS=true

View File

@ -57,21 +57,21 @@ if [ "$OPENJDK_TARGET_OS" = "linux" ]; then
./demo/jvmti/mtrace/lib/libmtrace.so
./demo/jvmti/versionCheck/lib/libversionCheck.so
./demo/jvmti/waiters/lib/libwaiters.so
./lib$OPENJDK_TARGET_CPU_LIBDIR/client/libjsig.so
./lib$OPENJDK_TARGET_CPU_LIBDIR/client/libjvm.so
./lib$OPENJDK_TARGET_CPU_LIBDIR/libattach.so
./lib$OPENJDK_TARGET_CPU_LIBDIR/libdt_socket.so
./lib$OPENJDK_TARGET_CPU_LIBDIR/libinstrument.so
./lib$OPENJDK_TARGET_CPU_LIBDIR/libjsdt.so
./lib$OPENJDK_TARGET_CPU_LIBDIR/libjsig.so
./lib$OPENJDK_TARGET_CPU_LIBDIR/libmanagement.so
./lib$OPENJDK_TARGET_CPU_LIBDIR/libnet.so
./lib$OPENJDK_TARGET_CPU_LIBDIR/libnpt.so
./lib$OPENJDK_TARGET_CPU_LIBDIR/libverify.so
./lib$OPENJDK_TARGET_CPU_LIBDIR/minimal/libjsig.so
./lib$OPENJDK_TARGET_CPU_LIBDIR/minimal/libjvm.so
./lib$OPENJDK_TARGET_CPU_LIBDIR/server/libjsig.so
./lib$OPENJDK_TARGET_CPU_LIBDIR/server/libjvm.so
./lib/client/libjsig.so
./lib/client/libjvm.so
./lib/libattach.so
./lib/libdt_socket.so
./lib/libinstrument.so
./lib/libjsdt.so
./lib/libjsig.so
./lib/libmanagement.so
./lib/libnet.so
./lib/libnpt.so
./lib/libverify.so
./lib/minimal/libjsig.so
./lib/minimal/libjvm.so
./lib/server/libjsig.so
./lib/server/libjvm.so
./bin/appletviewer
./bin/idlj
./bin/jar
@ -122,12 +122,12 @@ if [ "$OPENJDK_TARGET_OS" = "linux" ]; then
# So for now, accept the difference but put a limit on the size. The
# different order of functions shouldn't result in a very big diff.
KNOWN_FULLDUMP_DIFF="
./lib$OPENJDK_TARGET_CPU_LIBDIR/minimal/libjvm.so
./lib/minimal/libjvm.so
"
# Link time optimization adds random numbers to symbol names
NEED_DIS_DIFF_FILTER="
./lib$OPENJDK_TARGET_CPU_LIBDIR/minimal/libjvm.so
./lib/minimal/libjvm.so
"
DIS_DIFF_FILTER="$SED -r \
-e 's/\.[0-9]+/.X/g' \
@ -135,12 +135,12 @@ if [ "$OPENJDK_TARGET_OS" = "linux" ]; then
-e 's/\t[0-9a-f]{5,} /\t<HEX> /' \
"
KNOWN_DIS_DIFF="
./lib$OPENJDK_TARGET_CPU_LIBDIR/minimal/libjvm.so
./lib/minimal/libjvm.so
"
MAX_KNOWN_DIS_DIFF_SIZE="3000"
NEED_SYMBOLS_DIFF_FILTER="
./lib$OPENJDK_TARGET_CPU_LIBDIR/minimal/libjvm.so
./lib/minimal/libjvm.so
"
SYMBOLS_DIFF_FILTER="$SED -r \
-e 's/\.[0-9]+/.X/g'
@ -163,11 +163,11 @@ if [ "$OPENJDK_TARGET_OS" = "solaris" ] && [ "$OPENJDK_TARGET_CPU" = "x86_64" ];
"
SORT_SYMBOLS="
./lib/amd64/server/libjvm.so
./lib/amd64/libfontmanager.so
./lib/amd64/libjimage.so
./lib/amd64/libsaproc.so
./lib/amd64/libunpack.so
./lib/server/libjvm.so
./lib/libfontmanager.so
./lib/libjimage.so
./lib/libsaproc.so
./lib/libunpack.so
./bin/unpack200
"
@ -183,48 +183,48 @@ if [ "$OPENJDK_TARGET_OS" = "solaris" ] && [ "$OPENJDK_TARGET_CPU" = "x86_64" ];
./demo/jvmti/mtrace/lib/libmtrace.so
./demo/jvmti/versionCheck/lib/libversionCheck.so
./demo/jvmti/waiters/lib/libwaiters.so
./lib/amd64/jli/libjli.so
./lib/amd64/jspawnhelper
./lib/amd64/libJdbcOdbc.so
./lib/amd64/libattach.so
./lib/amd64/libawt.so
./lib/amd64/libawt_headless.so
./lib/amd64/libawt_xawt.so
./lib/amd64/libdcpr.so
./lib/amd64/libdt_socket.so
./lib/amd64/libfontmanager.so
./lib/amd64/libinstrument.so
./lib/amd64/libj2gss.so
./lib/amd64/libj2pcsc.so
./lib/amd64/libj2pkcs11.so
./lib/amd64/libj2ucrypto.so
./lib/amd64/libjaas_unix.so
./lib/amd64/libjava.so
./lib/amd64/libjawt.so
./lib/amd64/libjdwp.so
./lib/amd64/libjpeg.so
./lib/amd64/libjsdt.so
./lib/amd64/libjsound.so
./lib/amd64/libkcms.so
./lib/amd64/liblcms.so
./lib/amd64/libmanagement.so
./lib/amd64/libmlib_image.so
./lib/amd64/libnet.so
./lib/amd64/libnio.so
./lib/amd64/libnpt.so
./lib/amd64/libsctp.so
./lib/amd64/libsplashscreen.so
./lib/amd64/libsunec.so
./lib/amd64/libsunwjdga.so
./lib/amd64/libt2k.so
./lib/amd64/libunpack.so
./lib/amd64/libverify.so
./lib/amd64/libzip.so
./lib/amd64/server/64/libjvm_db.so
./lib/amd64/server/64/libjvm_dtrace.so
./lib/amd64/server/libjvm.so
./lib/amd64/server/libjvm_db.so
./lib/amd64/server/libjvm_dtrace.so
./lib/jli/libjli.so
./lib/jspawnhelper
./lib/libJdbcOdbc.so
./lib/libattach.so
./lib/libawt.so
./lib/libawt_headless.so
./lib/libawt_xawt.so
./lib/libdcpr.so
./lib/libdt_socket.so
./lib/libfontmanager.so
./lib/libinstrument.so
./lib/libj2gss.so
./lib/libj2pcsc.so
./lib/libj2pkcs11.so
./lib/libj2ucrypto.so
./lib/libjaas_unix.so
./lib/libjava.so
./lib/libjawt.so
./lib/libjdwp.so
./lib/libjpeg.so
./lib/libjsdt.so
./lib/libjsound.so
./lib/libkcms.so
./lib/liblcms.so
./lib/libmanagement.so
./lib/libmlib_image.so
./lib/libnet.so
./lib/libnio.so
./lib/libnpt.so
./lib/libsctp.so
./lib/libsplashscreen.so
./lib/libsunec.so
./lib/libsunwjdga.so
./lib/libt2k.so
./lib/libunpack.so
./lib/libverify.so
./lib/libzip.so
./lib/server/64/libjvm_db.so
./lib/server/64/libjvm_dtrace.so
./lib/server/libjvm.so
./lib/server/libjvm_db.so
./lib/server/libjvm_dtrace.so
./bin/appletviewer
./bin/idlj
./bin/jar
@ -292,13 +292,13 @@ if [ "$OPENJDK_TARGET_OS" = "solaris" ] && [ "$OPENJDK_TARGET_CPU" = "sparcv9" ]
SORT_SYMBOLS="
./demo/jvmti/waiters/lib/libwaiters.so
./lib/sparcv9/libjsig.so
./lib/sparcv9/libfontmanager.so
./lib/sparcv9/libjimage.so
./lib/sparcv9/libsaproc.so
./lib/sparcv9/libunpack.so
./lib/sparcv9/server/libjvm.so
./lib/sparcv9/server/libjvm_dtrace.so
./lib/libjsig.so
./lib/libfontmanager.so
./lib/libjimage.so
./lib/libsaproc.so
./lib/libunpack.so
./lib/server/libjvm.so
./lib/server/libjvm_dtrace.so
./bin/unpack200
"
@ -314,46 +314,46 @@ if [ "$OPENJDK_TARGET_OS" = "solaris" ] && [ "$OPENJDK_TARGET_CPU" = "sparcv9" ]
./demo/jvmti/mtrace/lib/libmtrace.so
./demo/jvmti/versionCheck/lib/libversionCheck.so
./demo/jvmti/waiters/lib/libwaiters.so
./lib/sparcv9/client/libjvm.so
./lib/sparcv9/jli/libjli.so
./lib/sparcv9/jspawnhelper
./lib/sparcv9/libJdbcOdbc.so
./lib/sparcv9/libattach.so
./lib/sparcv9/libawt.so
./lib/sparcv9/libawt_headless.so
./lib/sparcv9/libawt_xawt.so
./lib/sparcv9/libdcpr.so
./lib/sparcv9/libdt_socket.so
./lib/sparcv9/libfontmanager.so
./lib/sparcv9/libinstrument.so
./lib/sparcv9/libj2gss.so
./lib/sparcv9/libj2pcsc.so
./lib/sparcv9/libj2pkcs11.so
./lib/sparcv9/libj2ucrypto.so
./lib/sparcv9/libjaas_unix.so
./lib/sparcv9/libjava.so
./lib/sparcv9/libjawt.so
./lib/sparcv9/libjdwp.so
./lib/sparcv9/libjpeg.so
./lib/sparcv9/libjsdt.so
./lib/sparcv9/libjsound.so
./lib/sparcv9/libkcms.so
./lib/sparcv9/liblcms.so
./lib/sparcv9/libmanagement.so
./lib/sparcv9/libmlib_image.so
./lib/sparcv9/libmlib_image_v.so
./lib/sparcv9/libnet.so
./lib/sparcv9/libnio.so
./lib/sparcv9/libnpt.so
./lib/sparcv9/libsctp.so
./lib/sparcv9/libsplashscreen.so
./lib/sparcv9/libsunec.so
./lib/sparcv9/libsunwjdga.so
./lib/sparcv9/libt2k.so
./lib/sparcv9/libunpack.so
./lib/sparcv9/libverify.so
./lib/sparcv9/libzip.so
./lib/sparcv9/server/libjvm.so
./lib/client/libjvm.so
./lib/jli/libjli.so
./lib/jspawnhelper
./lib/libJdbcOdbc.so
./lib/libattach.so
./lib/libawt.so
./lib/libawt_headless.so
./lib/libawt_xawt.so
./lib/libdcpr.so
./lib/libdt_socket.so
./lib/libfontmanager.so
./lib/libinstrument.so
./lib/libj2gss.so
./lib/libj2pcsc.so
./lib/libj2pkcs11.so
./lib/libj2ucrypto.so
./lib/libjaas_unix.so
./lib/libjava.so
./lib/libjawt.so
./lib/libjdwp.so
./lib/libjpeg.so
./lib/libjsdt.so
./lib/libjsound.so
./lib/libkcms.so
./lib/liblcms.so
./lib/libmanagement.so
./lib/libmlib_image.so
./lib/libmlib_image_v.so
./lib/libnet.so
./lib/libnio.so
./lib/libnpt.so
./lib/libsctp.so
./lib/libsplashscreen.so
./lib/libsunec.so
./lib/libsunwjdga.so
./lib/libt2k.so
./lib/libunpack.so
./lib/libverify.so
./lib/libzip.so
./lib/server/libjvm.so
./bin/appletviewer
./bin/idlj
./bin/jar
@ -409,7 +409,7 @@ if [ "$OPENJDK_TARGET_OS" = "solaris" ] && [ "$OPENJDK_TARGET_CPU" = "sparcv9" ]
"
KNOWN_DIS_DIFF="
./lib/sparcv9/libsaproc.so
./lib/libsaproc.so
"
MAX_KNOWN_DIS_DIFF_SIZE="3000"
@ -417,8 +417,8 @@ if [ "$OPENJDK_TARGET_OS" = "solaris" ] && [ "$OPENJDK_TARGET_CPU" = "sparcv9" ]
# On slowdebug the disassembly can differ randomly.
if [ "$DEBUG_LEVEL" = "slowdebug" ]; then
ACCEPTED_DIS_DIFF="
./lib/sparcv9/libfontmanager.so
./lib/sparcv9/server/libjvm.so
./lib/libfontmanager.so
./lib/server/libjvm.so
"
fi

View File

@ -28,6 +28,11 @@ corba/src/java.corba/share/classes/javax/activity : corba/src/share/classes/java
corba/src/java.corba/share/classes/javax/rmi : corba/src/share/classes/javax/rmi
corba/src/java.corba/share/classes/org/omg : corba/src/share/classes/org/omg
corba/src/java.corba/share/classes/sun/corba : corba/src/share/classes/sun/corba
corba/src/java.corba/share/classes/com/sun/jndi/cosnaming : jdk/src/share/classes/com/sun/jndi/cosnaming
corba/src/java.corba/share/classes/com/sun/jndi/toolkit/corba : jdk/src/share/classes/com/sun/jndi/toolkit/corba
corba/src/java.corba/share/classes/com/sun/jndi/url/corbaname : jdk/src/share/classes/com/sun/jndi/url/corbaname
corba/src/java.corba/share/classes/com/sun/jndi/url/iiop : jdk/src/share/classes/com/sun/jndi/url/iiop
corba/src/java.corba/share/classes/com/sun/jndi/url/iiopname : jdk/src/share/classes/com/sun/jndi/url/iiopname
corba/src/jdk.rmic/share/classes/sun/rmi/rmic/iiop : corba/src/share/classes/sun/rmi/rmic/iiop
jaxp/src/java.xml/share/classes/com/sun/java_cup/internal/runtime : jaxp/src/com/sun/java_cup/internal/runtime
jaxp/src/java.xml/share/classes/com/sun/org/apache/bcel/internal : jaxp/src/com/sun/org/apache/bcel/internal
@ -516,11 +521,6 @@ jdk/src/java.base/windows/native/libnet/TwoStacksPlainSocketImpl.c : jdk/src/win
jdk/src/java.base/windows/native/libnio/ch : jdk/src/windows/native/sun/nio/ch
jdk/src/java.base/windows/native/libnio/fs : jdk/src/windows/native/sun/nio/fs
jdk/src/java.base/windows/native/libnio/MappedByteBuffer.c : jdk/src/windows/native/java/nio/MappedByteBuffer.c
jdk/src/java.corba/share/classes/com/sun/jndi/cosnaming : jdk/src/share/classes/com/sun/jndi/cosnaming
jdk/src/java.corba/share/classes/com/sun/jndi/toolkit/corba : jdk/src/share/classes/com/sun/jndi/toolkit/corba
jdk/src/java.corba/share/classes/com/sun/jndi/url/corbaname : jdk/src/share/classes/com/sun/jndi/url/corbaname
jdk/src/java.corba/share/classes/com/sun/jndi/url/iiop : jdk/src/share/classes/com/sun/jndi/url/iiop
jdk/src/java.corba/share/classes/com/sun/jndi/url/iiopname : jdk/src/share/classes/com/sun/jndi/url/iiopname
jdk/src/java.desktop/aix/native/libawt : jdk/src/aix/porting
jdk/src/java.desktop/linux/conf/oblique-fonts/fonts.dir : jdk/src/solaris/classes/sun/awt/motif/java.oblique-fonts.dir
jdk/src/java.desktop/macosx/classes/com/apple/eawt/event/package.html : jdk/src/macosx/classes/com/apple/eawt/event/package.html
@ -1266,33 +1266,33 @@ jdk/src/jdk.crypto.ec/share/native/libsunec/ECC_JNI.cpp : jdk/src/share/native/s
jdk/src/jdk.crypto.ec/share/native/libsunec/impl : jdk/src/share/native/sun/security/ec/impl
jdk/src/jdk.crypto.mscapi/windows/classes/sun/security/mscapi : jdk/src/windows/classes/sun/security/mscapi
jdk/src/jdk.crypto.mscapi/windows/native/libsunmscapi : jdk/src/windows/native/sun/security/mscapi
jdk/src/jdk.crypto.pkcs11/share/classes/sun/security/pkcs11 : jdk/src/share/classes/sun/security/pkcs11
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/j2secmod.c : jdk/src/share/native/sun/security/pkcs11/j2secmod.c
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/j2secmod.h : jdk/src/share/native/sun/security/pkcs11/j2secmod.h
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_convert.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_convert.c
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_crypt.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_crypt.c
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_digest.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_digest.c
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_dual.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_dual.c
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_general.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_general.c
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_keymgmt.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_keymgmt.c
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_mutex.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_mutex.c
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_objmgmt.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_objmgmt.c
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_sessmgmt.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_sessmgmt.c
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_sign.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_sign.c
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_util.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_util.c
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/pkcs11f.h : jdk/src/share/native/sun/security/pkcs11/wrapper/pkcs11f.h
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/pkcs11.h : jdk/src/share/native/sun/security/pkcs11/wrapper/pkcs11.h
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/pkcs11t.h : jdk/src/share/native/sun/security/pkcs11/wrapper/pkcs11t.h
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/pkcs-11v2-20a3.h : jdk/src/share/native/sun/security/pkcs11/wrapper/pkcs-11v2-20a3.h
jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/pkcs11wrapper.h : jdk/src/share/native/sun/security/pkcs11/wrapper/pkcs11wrapper.h
jdk/src/jdk.crypto.pkcs11/unix/native/libj2pkcs11/j2secmod_md.c : jdk/src/solaris/native/sun/security/pkcs11/j2secmod_md.c
jdk/src/jdk.crypto.pkcs11/unix/native/libj2pkcs11/j2secmod_md.h : jdk/src/solaris/native/sun/security/pkcs11/j2secmod_md.h
jdk/src/jdk.crypto.pkcs11/unix/native/libj2pkcs11/p11_md.c : jdk/src/solaris/native/sun/security/pkcs11/wrapper/p11_md.c
jdk/src/jdk.crypto.pkcs11/unix/native/libj2pkcs11/p11_md.h : jdk/src/solaris/native/sun/security/pkcs11/wrapper/p11_md.h
jdk/src/jdk.crypto.pkcs11/windows/native/libj2pkcs11/j2secmod_md.c : jdk/src/windows/native/sun/security/pkcs11/j2secmod_md.c
jdk/src/jdk.crypto.pkcs11/windows/native/libj2pkcs11/j2secmod_md.h : jdk/src/windows/native/sun/security/pkcs11/j2secmod_md.h
jdk/src/jdk.crypto.pkcs11/windows/native/libj2pkcs11/p11_md.c : jdk/src/windows/native/sun/security/pkcs11/wrapper/p11_md.c
jdk/src/jdk.crypto.pkcs11/windows/native/libj2pkcs11/p11_md.h : jdk/src/windows/native/sun/security/pkcs11/wrapper/p11_md.h
jdk/src/jdk.crypto.token/share/classes/sun/security/pkcs11 : jdk/src/share/classes/sun/security/pkcs11
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/j2secmod.c : jdk/src/share/native/sun/security/pkcs11/j2secmod.c
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/j2secmod.h : jdk/src/share/native/sun/security/pkcs11/j2secmod.h
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_convert.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_convert.c
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_crypt.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_crypt.c
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_digest.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_digest.c
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_dual.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_dual.c
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_general.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_general.c
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_keymgmt.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_keymgmt.c
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_mutex.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_mutex.c
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_objmgmt.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_objmgmt.c
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_sessmgmt.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_sessmgmt.c
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_sign.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_sign.c
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_util.c : jdk/src/share/native/sun/security/pkcs11/wrapper/p11_util.c
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/pkcs11f.h : jdk/src/share/native/sun/security/pkcs11/wrapper/pkcs11f.h
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/pkcs11.h : jdk/src/share/native/sun/security/pkcs11/wrapper/pkcs11.h
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/pkcs11t.h : jdk/src/share/native/sun/security/pkcs11/wrapper/pkcs11t.h
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/pkcs-11v2-20a3.h : jdk/src/share/native/sun/security/pkcs11/wrapper/pkcs-11v2-20a3.h
jdk/src/jdk.crypto.token/share/native/libj2pkcs11/pkcs11wrapper.h : jdk/src/share/native/sun/security/pkcs11/wrapper/pkcs11wrapper.h
jdk/src/jdk.crypto.token/unix/native/libj2pkcs11/j2secmod_md.c : jdk/src/solaris/native/sun/security/pkcs11/j2secmod_md.c
jdk/src/jdk.crypto.token/unix/native/libj2pkcs11/j2secmod_md.h : jdk/src/solaris/native/sun/security/pkcs11/j2secmod_md.h
jdk/src/jdk.crypto.token/unix/native/libj2pkcs11/p11_md.c : jdk/src/solaris/native/sun/security/pkcs11/wrapper/p11_md.c
jdk/src/jdk.crypto.token/unix/native/libj2pkcs11/p11_md.h : jdk/src/solaris/native/sun/security/pkcs11/wrapper/p11_md.h
jdk/src/jdk.crypto.token/windows/native/libj2pkcs11/j2secmod_md.c : jdk/src/windows/native/sun/security/pkcs11/j2secmod_md.c
jdk/src/jdk.crypto.token/windows/native/libj2pkcs11/j2secmod_md.h : jdk/src/windows/native/sun/security/pkcs11/j2secmod_md.h
jdk/src/jdk.crypto.token/windows/native/libj2pkcs11/p11_md.c : jdk/src/windows/native/sun/security/pkcs11/wrapper/p11_md.c
jdk/src/jdk.crypto.token/windows/native/libj2pkcs11/p11_md.h : jdk/src/windows/native/sun/security/pkcs11/wrapper/p11_md.h
jdk/src/java.desktop/macosx/native/libosx/CFileManager.m : jdk/src/macosx/native/com/apple/eio/CFileManager.m
jdk/src/java.base/macosx/native/libosxsecurity/KeystoreImpl.m : jdk/src/macosx/native/apple/security/KeystoreImpl.m
jdk/src/jdk.hprof.agent/share/classes/com/sun/demo/jvmti/hprof : jdk/src/share/classes/com/sun/demo/jvmti/hprof
@ -1427,26 +1427,26 @@ jdk/src/jdk.naming.dns/share/classes/META-INF/services : jdk/src/share/classes/s
jdk/src/jdk.naming.dns/share/classes/sun/net/spi/nameservice/dns : jdk/src/share/classes/sun/net/spi/nameservice/dns
jdk/src/jdk.naming.rmi/share/classes/com/sun/jndi/rmi/registry : jdk/src/share/classes/com/sun/jndi/rmi/registry
jdk/src/jdk.naming.rmi/share/classes/com/sun/jndi/url/rmi : jdk/src/share/classes/com/sun/jndi/url/rmi
jdk/src/jdk.pack200/share/native/common-unpack/bands.cpp : jdk/src/share/native/com/sun/java/util/jar/pack/bands.cpp
jdk/src/jdk.pack200/share/native/common-unpack/bands.h : jdk/src/share/native/com/sun/java/util/jar/pack/bands.h
jdk/src/jdk.pack200/share/native/common-unpack/bytes.cpp : jdk/src/share/native/com/sun/java/util/jar/pack/bytes.cpp
jdk/src/jdk.pack200/share/native/common-unpack/bytes.h : jdk/src/share/native/com/sun/java/util/jar/pack/bytes.h
jdk/src/jdk.pack200/share/native/common-unpack/coding.cpp : jdk/src/share/native/com/sun/java/util/jar/pack/coding.cpp
jdk/src/jdk.pack200/share/native/common-unpack/coding.h : jdk/src/share/native/com/sun/java/util/jar/pack/coding.h
jdk/src/jdk.pack200/share/native/common-unpack/constants.h : jdk/src/share/native/com/sun/java/util/jar/pack/constants.h
jdk/src/jdk.pack200/share/native/common-unpack/defines.h : jdk/src/share/native/com/sun/java/util/jar/pack/defines.h
jdk/src/jdk.pack200/share/native/common-unpack/unpack.cpp : jdk/src/share/native/com/sun/java/util/jar/pack/unpack.cpp
jdk/src/jdk.pack200/share/native/common-unpack/unpack.h : jdk/src/share/native/com/sun/java/util/jar/pack/unpack.h
jdk/src/jdk.pack200/share/native/common-unpack/utils.cpp : jdk/src/share/native/com/sun/java/util/jar/pack/utils.cpp
jdk/src/jdk.pack200/share/native/common-unpack/utils.h : jdk/src/share/native/com/sun/java/util/jar/pack/utils.h
jdk/src/jdk.pack200/share/native/common-unpack/zip.cpp : jdk/src/share/native/com/sun/java/util/jar/pack/zip.cpp
jdk/src/jdk.pack200/share/native/common-unpack/zip.h : jdk/src/share/native/com/sun/java/util/jar/pack/zip.h
jdk/src/jdk.pack200/share/native/libjsdt : jdk/src/share/native/sun/tracing/dtrace
jdk/src/jdk.pack200/share/native/libunpack/jni.cpp : jdk/src/share/native/com/sun/java/util/jar/pack/jni.cpp
jdk/src/jdk.pack200/share/native/unpack200/main.cpp : jdk/src/share/native/com/sun/java/util/jar/pack/main.cpp
jdk/src/jdk.pack200/unix/native/libjsdt/jvm_symbols_md.c : jdk/src/solaris/native/sun/tracing/dtrace/jvm_symbols_md.c
jdk/src/jdk.pack200/windows/native/libjsdt/jvm_symbols_md.c : jdk/src/windows/native/sun/tracing/dtrace/jvm_symbols_md.c
jdk/src/jdk.pack200/windows/native/unpack200/unpack200_proto.exe.manifest : jdk/src/windows/resource/unpack200_proto.exe.manifest
jdk/src/jdk.pack/share/native/common-unpack/bands.cpp : jdk/src/share/native/com/sun/java/util/jar/pack/bands.cpp
jdk/src/jdk.pack/share/native/common-unpack/bands.h : jdk/src/share/native/com/sun/java/util/jar/pack/bands.h
jdk/src/jdk.pack/share/native/common-unpack/bytes.cpp : jdk/src/share/native/com/sun/java/util/jar/pack/bytes.cpp
jdk/src/jdk.pack/share/native/common-unpack/bytes.h : jdk/src/share/native/com/sun/java/util/jar/pack/bytes.h
jdk/src/jdk.pack/share/native/common-unpack/coding.cpp : jdk/src/share/native/com/sun/java/util/jar/pack/coding.cpp
jdk/src/jdk.pack/share/native/common-unpack/coding.h : jdk/src/share/native/com/sun/java/util/jar/pack/coding.h
jdk/src/jdk.pack/share/native/common-unpack/constants.h : jdk/src/share/native/com/sun/java/util/jar/pack/constants.h
jdk/src/jdk.pack/share/native/common-unpack/defines.h : jdk/src/share/native/com/sun/java/util/jar/pack/defines.h
jdk/src/jdk.pack/share/native/common-unpack/unpack.cpp : jdk/src/share/native/com/sun/java/util/jar/pack/unpack.cpp
jdk/src/jdk.pack/share/native/common-unpack/unpack.h : jdk/src/share/native/com/sun/java/util/jar/pack/unpack.h
jdk/src/jdk.pack/share/native/common-unpack/utils.cpp : jdk/src/share/native/com/sun/java/util/jar/pack/utils.cpp
jdk/src/jdk.pack/share/native/common-unpack/utils.h : jdk/src/share/native/com/sun/java/util/jar/pack/utils.h
jdk/src/jdk.pack/share/native/common-unpack/zip.cpp : jdk/src/share/native/com/sun/java/util/jar/pack/zip.cpp
jdk/src/jdk.pack/share/native/common-unpack/zip.h : jdk/src/share/native/com/sun/java/util/jar/pack/zip.h
jdk/src/jdk.pack/share/native/libjsdt : jdk/src/share/native/sun/tracing/dtrace
jdk/src/jdk.pack/share/native/libunpack/jni.cpp : jdk/src/share/native/com/sun/java/util/jar/pack/jni.cpp
jdk/src/jdk.pack/share/native/unpack200/main.cpp : jdk/src/share/native/com/sun/java/util/jar/pack/main.cpp
jdk/src/jdk.pack/unix/native/libjsdt/jvm_symbols_md.c : jdk/src/solaris/native/sun/tracing/dtrace/jvm_symbols_md.c
jdk/src/jdk.pack/windows/native/libjsdt/jvm_symbols_md.c : jdk/src/windows/native/sun/tracing/dtrace/jvm_symbols_md.c
jdk/src/jdk.pack/windows/native/unpack200/unpack200_proto.exe.manifest : jdk/src/windows/resource/unpack200_proto.exe.manifest
jdk/src/jdk.policytool/share/classes/sun/security/tools/policytool : jdk/src/share/classes/sun/security/tools/policytool
jdk/src/jdk.rmic/share/classes/sun/rmi/rmic : jdk/src/share/classes/sun/rmi/rmic
jdk/src/jdk.rmic/share/classes/sun/rmi/rmic/newrmic : jdk/src/share/classes/sun/rmi/rmic/newrmic

View File

@ -2166,7 +2166,7 @@
</df>
</df>
</df>
<df name="jdk.crypto.pkcs11">
<df name="jdk.crypto.token">
<df name="share">
<df name="native">
<df name="libj2pkcs11">
@ -2318,7 +2318,7 @@
</df>
</df>
</df>
<df name="jdk.pack200">
<df name="jdk.pack">
<df name="share">
<df name="native">
<df name="common-unpack">
@ -29422,35 +29422,35 @@
<cTool flags="5">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/j2secmod.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/j2secmod.c"
ex="false"
tool="0"
flavor2="3">
<cTool flags="5">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_convert.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_convert.c"
ex="false"
tool="0"
flavor2="3">
<cTool flags="5">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_crypt.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_crypt.c"
ex="false"
tool="0"
flavor2="3">
<cTool flags="5">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_digest.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_digest.c"
ex="false"
tool="0"
flavor2="3">
<cTool flags="5">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_dual.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_dual.c"
ex="false"
tool="0"
flavor2="2">
@ -29460,63 +29460,63 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_general.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_general.c"
ex="false"
tool="0"
flavor2="3">
<cTool flags="5">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_keymgmt.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_keymgmt.c"
ex="false"
tool="0"
flavor2="3">
<cTool flags="5">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_mutex.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_mutex.c"
ex="false"
tool="0"
flavor2="3">
<cTool flags="5">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_objmgmt.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_objmgmt.c"
ex="false"
tool="0"
flavor2="3">
<cTool flags="5">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_sessmgmt.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_sessmgmt.c"
ex="false"
tool="0"
flavor2="3">
<cTool flags="5">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_sign.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_sign.c"
ex="false"
tool="0"
flavor2="3">
<cTool flags="5">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_util.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_util.c"
ex="false"
tool="0"
flavor2="3">
<cTool flags="5">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/unix/native/libj2pkcs11/j2secmod_md.c"
<item path="../../jdk/src/jdk.crypto.token/unix/native/libj2pkcs11/j2secmod_md.c"
ex="false"
tool="0"
flavor2="3">
<cTool flags="5">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/unix/native/libj2pkcs11/p11_md.c"
<item path="../../jdk/src/jdk.crypto.token/unix/native/libj2pkcs11/p11_md.c"
ex="false"
tool="0"
flavor2="3">
@ -30022,12 +30022,12 @@
<cTool flags="2">
</cTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/bands.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/bands.cpp"
ex="false"
tool="1"
flavor2="4">
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/bytes.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/bytes.cpp"
ex="false"
tool="1"
flavor2="4">
@ -30037,7 +30037,7 @@
</preprocessorList>
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/coding.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/coding.cpp"
ex="false"
tool="1"
flavor2="4">
@ -30047,7 +30047,7 @@
</preprocessorList>
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/unpack.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/unpack.cpp"
ex="false"
tool="1"
flavor2="4">
@ -30057,7 +30057,7 @@
</preprocessorList>
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/utils.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/utils.cpp"
ex="false"
tool="1"
flavor2="4">
@ -30067,7 +30067,7 @@
</preprocessorList>
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/zip.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/zip.cpp"
ex="false"
tool="1"
flavor2="4">
@ -30077,12 +30077,12 @@
</preprocessorList>
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/libunpack/jni.cpp"
<item path="../../jdk/src/jdk.pack/share/native/libunpack/jni.cpp"
ex="false"
tool="1"
flavor2="4">
</item>
<item path="../../jdk/src/jdk.pack200/share/native/unpack200/main.cpp"
<item path="../../jdk/src/jdk.pack/share/native/unpack200/main.cpp"
ex="false"
tool="1"
flavor2="4">
@ -31752,7 +31752,7 @@
</preprocessorList>
</ccTool>
</folder>
<folder path="0/jdk/src/jdk.crypto.pkcs11">
<folder path="0/jdk/src/jdk.crypto.token">
<cTool>
<incDir>
<pElem>../../jdk/src/java.base/share/native/include</pElem>
@ -31760,10 +31760,10 @@
<pElem>../../jdk/src/java.base/unix/native/include</pElem>
<pElem>../../jdk/src/java.base/share/native/libjava</pElem>
<pElem>../../jdk/src/java.base/unix/native/libjava</pElem>
<pElem>../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11</pElem>
<pElem>../../jdk/src/jdk.crypto.pkcs11/unix/native/libj2pkcs11</pElem>
<pElem>../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11</pElem>
<pElem>../../jdk/src/jdk.crypto.token/unix/native/libj2pkcs11</pElem>
<pElem>../../jdk/src/java.base/macosx/native/libjava</pElem>
<pElem>../../build/support/headers/jdk.crypto.pkcs11</pElem>
<pElem>../../build/support/headers/jdk.crypto.token</pElem>
<pElem>../../make</pElem>
</incDir>
<preprocessorList>
@ -31772,7 +31772,7 @@
</preprocessorList>
</cTool>
</folder>
<folder path="0/jdk/src/jdk.crypto.pkcs11/unix">
<folder path="0/jdk/src/jdk.crypto.token/unix">
<cTool>
<preprocessorList>
<Elem>THIS_FILE="j2secmod_md.c"</Elem>
@ -31899,7 +31899,7 @@
</preprocessorList>
</cTool>
</folder>
<folder path="0/jdk/src/jdk.pack200">
<folder path="0/jdk/src/jdk.pack">
<ccTool>
<preprocessorList>
<Elem>DEBUG</Elem>
@ -31908,7 +31908,7 @@
</preprocessorList>
</ccTool>
</folder>
<folder path="0/jdk/src/jdk.pack200/share/native/common-unpack">
<folder path="0/jdk/src/jdk.pack/share/native/common-unpack">
<ccTool>
<incDir>
<pElem>../../jdk/src/java.base/share/native/include</pElem>
@ -31917,7 +31917,7 @@
<pElem>../../jdk/src/java.base/share/native/libjava</pElem>
<pElem>../../jdk/src/java.base/unix/native/libjava</pElem>
<pElem>../../build/support/headers/java.base</pElem>
<pElem>../../jdk/src/jdk.pack200/share/native/common-unpack</pElem>
<pElem>../../jdk/src/jdk.pack/share/native/common-unpack</pElem>
<pElem>../../jdk/src/java.base/macosx/native/libjava</pElem>
<pElem>../../make</pElem>
</incDir>
@ -31927,7 +31927,7 @@
</preprocessorList>
</ccTool>
</folder>
<folder path="0/jdk/src/jdk.pack200/share/native/libunpack">
<folder path="0/jdk/src/jdk.pack/share/native/libunpack">
<ccTool>
<incDir>
<pElem>../../jdk/src/java.base/share/native/include</pElem>
@ -31936,7 +31936,7 @@
<pElem>../../jdk/src/java.base/share/native/libjava</pElem>
<pElem>../../jdk/src/java.base/unix/native/libjava</pElem>
<pElem>../../build/support/headers/java.base</pElem>
<pElem>../../jdk/src/jdk.pack200/share/native/common-unpack</pElem>
<pElem>../../jdk/src/jdk.pack/share/native/common-unpack</pElem>
<pElem>../../jdk/src/java.base/macosx/native/libjava</pElem>
<pElem>../../make</pElem>
</incDir>
@ -31947,10 +31947,10 @@
</preprocessorList>
</ccTool>
</folder>
<folder path="0/jdk/src/jdk.pack200/share/native/unpack200">
<folder path="0/jdk/src/jdk.pack/share/native/unpack200">
<ccTool>
<incDir>
<pElem>../../jdk/src/jdk.pack200/share/native/common-unpack</pElem>
<pElem>../../jdk/src/jdk.pack/share/native/common-unpack</pElem>
<pElem>../../jdk/src/java.base/share/native/libjava</pElem>
<pElem>../../jdk/src/java.base/unix/native/libjava</pElem>
<pElem>../../jdk/src/java.base/share/native/include</pElem>
@ -44741,14 +44741,14 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/j2secmod.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/j2secmod.c"
ex="false"
tool="0"
flavor2="0">
<cTool flags="4">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_convert.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_convert.c"
ex="false"
tool="0"
flavor2="0">
@ -44758,7 +44758,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_crypt.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_crypt.c"
ex="false"
tool="0"
flavor2="0">
@ -44768,7 +44768,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_digest.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_digest.c"
ex="false"
tool="0"
flavor2="0">
@ -44778,7 +44778,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_dual.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_dual.c"
ex="false"
tool="0"
flavor2="0">
@ -44788,7 +44788,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_general.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_general.c"
ex="false"
tool="0"
flavor2="0">
@ -44798,7 +44798,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_keymgmt.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_keymgmt.c"
ex="false"
tool="0"
flavor2="0">
@ -44808,7 +44808,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_mutex.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_mutex.c"
ex="false"
tool="0"
flavor2="0">
@ -44818,7 +44818,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_objmgmt.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_objmgmt.c"
ex="false"
tool="0"
flavor2="0">
@ -44828,7 +44828,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_sessmgmt.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_sessmgmt.c"
ex="false"
tool="0"
flavor2="0">
@ -44838,7 +44838,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_sign.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_sign.c"
ex="false"
tool="0"
flavor2="0">
@ -44848,7 +44848,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_util.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_util.c"
ex="false"
tool="0"
flavor2="0">
@ -44858,14 +44858,14 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/unix/native/libj2pkcs11/j2secmod_md.c"
<item path="../../jdk/src/jdk.crypto.token/unix/native/libj2pkcs11/j2secmod_md.c"
ex="false"
tool="0"
flavor2="0">
<cTool flags="4">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/unix/native/libj2pkcs11/p11_md.c"
<item path="../../jdk/src/jdk.crypto.token/unix/native/libj2pkcs11/p11_md.c"
ex="false"
tool="0"
flavor2="0">
@ -45364,14 +45364,14 @@
<cTool flags="4">
</cTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/bands.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/bands.cpp"
ex="false"
tool="1"
flavor2="0">
<ccTool flags="2">
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/bytes.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/bytes.cpp"
ex="false"
tool="1"
flavor2="0">
@ -45381,7 +45381,7 @@
</preprocessorList>
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/coding.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/coding.cpp"
ex="false"
tool="1"
flavor2="0">
@ -45391,7 +45391,7 @@
</preprocessorList>
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/unpack.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/unpack.cpp"
ex="false"
tool="1"
flavor2="0">
@ -45401,7 +45401,7 @@
</preprocessorList>
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/utils.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/utils.cpp"
ex="false"
tool="1"
flavor2="0">
@ -45411,7 +45411,7 @@
</preprocessorList>
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/zip.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/zip.cpp"
ex="false"
tool="1"
flavor2="0">
@ -45421,14 +45421,14 @@
</preprocessorList>
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/libunpack/jni.cpp"
<item path="../../jdk/src/jdk.pack/share/native/libunpack/jni.cpp"
ex="false"
tool="1"
flavor2="0">
<ccTool flags="2">
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/unpack200/main.cpp"
<item path="../../jdk/src/jdk.pack/share/native/unpack200/main.cpp"
ex="false"
tool="1"
flavor2="0">
@ -47795,7 +47795,7 @@
</preprocessorList>
</ccTool>
</folder>
<folder path="0/jdk/src/jdk.crypto.pkcs11">
<folder path="0/jdk/src/jdk.crypto.token">
<cTool>
<incDir>
<pElem>../../jdk/src/java.base/share/native/include</pElem>
@ -47803,10 +47803,10 @@
<pElem>../../jdk/src/java.base/unix/native/include</pElem>
<pElem>../../jdk/src/java.base/share/native/libjava</pElem>
<pElem>../../jdk/src/java.base/unix/native/libjava</pElem>
<pElem>../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11</pElem>
<pElem>../../jdk/src/jdk.crypto.pkcs11/unix/native/libj2pkcs11</pElem>
<pElem>../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11</pElem>
<pElem>../../jdk/src/jdk.crypto.token/unix/native/libj2pkcs11</pElem>
<pElem>../../jdk/src/java.base/linux/native/libjava</pElem>
<pElem>../../build/support/headers/jdk.crypto.pkcs11</pElem>
<pElem>../../build/support/headers/jdk.crypto.token</pElem>
<pElem>../../make</pElem>
</incDir>
<preprocessorList>
@ -47815,7 +47815,7 @@
</preprocessorList>
</cTool>
</folder>
<folder path="0/jdk/src/jdk.crypto.pkcs11/unix">
<folder path="0/jdk/src/jdk.crypto.token/unix">
<cTool>
<preprocessorList>
<Elem>THIS_FILE="j2secmod_md.c"</Elem>
@ -47942,7 +47942,7 @@
</preprocessorList>
</cTool>
</folder>
<folder path="0/jdk/src/jdk.pack200">
<folder path="0/jdk/src/jdk.pack">
<ccTool>
<preprocessorList>
<Elem>DEBUG</Elem>
@ -47951,7 +47951,7 @@
</preprocessorList>
</ccTool>
</folder>
<folder path="0/jdk/src/jdk.pack200/share/native/common-unpack">
<folder path="0/jdk/src/jdk.pack/share/native/common-unpack">
<ccTool>
<incDir>
<pElem>../../jdk/src/java.base/share/native/include</pElem>
@ -47960,7 +47960,7 @@
<pElem>../../jdk/src/java.base/share/native/libjava</pElem>
<pElem>../../jdk/src/java.base/unix/native/libjava</pElem>
<pElem>../../build/support/headers/java.base</pElem>
<pElem>../../jdk/src/jdk.pack200/share/native/common-unpack</pElem>
<pElem>../../jdk/src/jdk.pack/share/native/common-unpack</pElem>
<pElem>../../jdk/src/java.base/linux/native/libjava</pElem>
<pElem>../../make</pElem>
</incDir>
@ -47970,7 +47970,7 @@
</preprocessorList>
</ccTool>
</folder>
<folder path="0/jdk/src/jdk.pack200/share/native/libunpack">
<folder path="0/jdk/src/jdk.pack/share/native/libunpack">
<ccTool>
<incDir>
<pElem>../../jdk/src/java.base/share/native/include</pElem>
@ -47979,7 +47979,7 @@
<pElem>../../jdk/src/java.base/share/native/libjava</pElem>
<pElem>../../jdk/src/java.base/unix/native/libjava</pElem>
<pElem>../../build/support/headers/java.base</pElem>
<pElem>../../jdk/src/jdk.pack200/share/native/common-unpack</pElem>
<pElem>../../jdk/src/jdk.pack/share/native/common-unpack</pElem>
<pElem>../../jdk/src/java.base/linux/native/libjava</pElem>
<pElem>../../make</pElem>
</incDir>
@ -47990,10 +47990,10 @@
</preprocessorList>
</ccTool>
</folder>
<folder path="0/jdk/src/jdk.pack200/share/native/unpack200">
<folder path="0/jdk/src/jdk.pack/share/native/unpack200">
<ccTool>
<incDir>
<pElem>../../jdk/src/jdk.pack200/share/native/common-unpack</pElem>
<pElem>../../jdk/src/jdk.pack/share/native/common-unpack</pElem>
<pElem>../../jdk/src/java.base/share/native/libjava</pElem>
<pElem>../../jdk/src/java.base/unix/native/libjava</pElem>
<pElem>../../jdk/src/java.base/share/native/libzip/zlib-1.2.8</pElem>
@ -62728,14 +62728,14 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/j2secmod.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/j2secmod.c"
ex="false"
tool="0"
flavor2="0">
<cTool flags="2">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_convert.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_convert.c"
ex="false"
tool="0"
flavor2="0">
@ -62745,7 +62745,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_crypt.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_crypt.c"
ex="false"
tool="0"
flavor2="0">
@ -62755,7 +62755,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_digest.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_digest.c"
ex="false"
tool="0"
flavor2="0">
@ -62765,7 +62765,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_dual.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_dual.c"
ex="false"
tool="0"
flavor2="0">
@ -62775,7 +62775,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_general.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_general.c"
ex="false"
tool="0"
flavor2="0">
@ -62785,7 +62785,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_keymgmt.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_keymgmt.c"
ex="false"
tool="0"
flavor2="0">
@ -62795,7 +62795,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_mutex.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_mutex.c"
ex="false"
tool="0"
flavor2="0">
@ -62805,7 +62805,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_objmgmt.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_objmgmt.c"
ex="false"
tool="0"
flavor2="0">
@ -62815,7 +62815,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_sessmgmt.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_sessmgmt.c"
ex="false"
tool="0"
flavor2="0">
@ -62825,7 +62825,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_sign.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_sign.c"
ex="false"
tool="0"
flavor2="0">
@ -62835,7 +62835,7 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11/p11_util.c"
<item path="../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11/p11_util.c"
ex="false"
tool="0"
flavor2="0">
@ -62845,14 +62845,14 @@
</preprocessorList>
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/unix/native/libj2pkcs11/j2secmod_md.c"
<item path="../../jdk/src/jdk.crypto.token/unix/native/libj2pkcs11/j2secmod_md.c"
ex="false"
tool="0"
flavor2="0">
<cTool flags="2">
</cTool>
</item>
<item path="../../jdk/src/jdk.crypto.pkcs11/unix/native/libj2pkcs11/p11_md.c"
<item path="../../jdk/src/jdk.crypto.token/unix/native/libj2pkcs11/p11_md.c"
ex="false"
tool="0"
flavor2="0">
@ -63395,14 +63395,14 @@
<cTool flags="2">
</cTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/bands.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/bands.cpp"
ex="false"
tool="1"
flavor2="0">
<ccTool flags="0">
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/bytes.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/bytes.cpp"
ex="false"
tool="1"
flavor2="0">
@ -63412,7 +63412,7 @@
</preprocessorList>
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/coding.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/coding.cpp"
ex="false"
tool="1"
flavor2="0">
@ -63422,7 +63422,7 @@
</preprocessorList>
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/unpack.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/unpack.cpp"
ex="false"
tool="1"
flavor2="0">
@ -63432,7 +63432,7 @@
</preprocessorList>
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/utils.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/utils.cpp"
ex="false"
tool="1"
flavor2="0">
@ -63442,7 +63442,7 @@
</preprocessorList>
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/common-unpack/zip.cpp"
<item path="../../jdk/src/jdk.pack/share/native/common-unpack/zip.cpp"
ex="false"
tool="1"
flavor2="0">
@ -63452,14 +63452,14 @@
</preprocessorList>
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/libunpack/jni.cpp"
<item path="../../jdk/src/jdk.pack/share/native/libunpack/jni.cpp"
ex="false"
tool="1"
flavor2="0">
<ccTool flags="0">
</ccTool>
</item>
<item path="../../jdk/src/jdk.pack200/share/native/unpack200/main.cpp"
<item path="../../jdk/src/jdk.pack/share/native/unpack200/main.cpp"
ex="false"
tool="1"
flavor2="0">
@ -66281,7 +66281,7 @@
</preprocessorList>
</ccTool>
</folder>
<folder path="0/jdk/src/jdk.crypto.pkcs11">
<folder path="0/jdk/src/jdk.crypto.token">
<cTool>
<incDir>
<pElem>../../jdk/src/java.base/share/native/include</pElem>
@ -66289,10 +66289,10 @@
<pElem>../../jdk/src/java.base/unix/native/include</pElem>
<pElem>../../jdk/src/java.base/share/native/libjava</pElem>
<pElem>../../jdk/src/java.base/unix/native/libjava</pElem>
<pElem>../../jdk/src/jdk.crypto.pkcs11/share/native/libj2pkcs11</pElem>
<pElem>../../jdk/src/jdk.crypto.pkcs11/unix/native/libj2pkcs11</pElem>
<pElem>../../jdk/src/jdk.crypto.token/share/native/libj2pkcs11</pElem>
<pElem>../../jdk/src/jdk.crypto.token/unix/native/libj2pkcs11</pElem>
<pElem>../../jdk/src/java.base/solaris/native/libjava</pElem>
<pElem>../../build/support/headers/jdk.crypto.pkcs11</pElem>
<pElem>../../build/support/headers/jdk.crypto.token</pElem>
<pElem>../../make</pElem>
</incDir>
<preprocessorList>
@ -66301,7 +66301,7 @@
</preprocessorList>
</cTool>
</folder>
<folder path="0/jdk/src/jdk.crypto.pkcs11/unix">
<folder path="0/jdk/src/jdk.crypto.token/unix">
<cTool>
<preprocessorList>
<Elem>THIS_FILE="j2secmod_md.c"</Elem>
@ -66462,7 +66462,7 @@
</preprocessorList>
</cTool>
</folder>
<folder path="0/jdk/src/jdk.pack200">
<folder path="0/jdk/src/jdk.pack">
<ccTool>
<preprocessorList>
<Elem>DEBUG</Elem>
@ -66471,11 +66471,11 @@
</preprocessorList>
</ccTool>
</folder>
<folder path="0/jdk/src/jdk.pack200/share/native/common-unpack">
<folder path="0/jdk/src/jdk.pack/share/native/common-unpack">
<ccTool>
<incDir>
<pElem>../../build/support/headers/java.base</pElem>
<pElem>../../jdk/src/jdk.pack200/share/native/common-unpack</pElem>
<pElem>../../jdk/src/jdk.pack/share/native/common-unpack</pElem>
<pElem>../../jdk/src/java.base/solaris/native/libjava</pElem>
<pElem>../../make</pElem>
</incDir>
@ -66485,11 +66485,11 @@
</preprocessorList>
</ccTool>
</folder>
<folder path="0/jdk/src/jdk.pack200/share/native/libunpack">
<folder path="0/jdk/src/jdk.pack/share/native/libunpack">
<ccTool>
<incDir>
<pElem>../../build/support/headers/java.base</pElem>
<pElem>../../jdk/src/jdk.pack200/share/native/common-unpack</pElem>
<pElem>../../jdk/src/jdk.pack/share/native/common-unpack</pElem>
<pElem>../../jdk/src/java.base/solaris/native/libjava</pElem>
<pElem>../../make</pElem>
</incDir>
@ -66500,10 +66500,10 @@
</preprocessorList>
</ccTool>
</folder>
<folder path="0/jdk/src/jdk.pack200/share/native/unpack200">
<folder path="0/jdk/src/jdk.pack/share/native/unpack200">
<ccTool>
<incDir>
<pElem>../../jdk/src/jdk.pack200/share/native/common-unpack</pElem>
<pElem>../../jdk/src/jdk.pack/share/native/common-unpack</pElem>
<pElem>../../make</pElem>
</incDir>
<preprocessorList>

View File

@ -23,3 +23,19 @@
^test/compiler/jvmci/\w[\w\.]*/.*\.iml
^test/compiler/jvmci/\w[\w\.]*/nbproject
^test/compiler/jvmci/\w[\w\.]*/\..*
^test/compiler/aot/\w[\w\.]*/.*\.xml
^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.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\.]*/\..*

View File

@ -551,3 +551,4 @@ d87d5d430c42342f0320ca7f5cbe0cbd1f9d62ba jdk-9+143
a82cb5350cad96a0b4de496afebe3ded89f27efa jdk-9+146
132a72c782071cc11ab25cc7c9ee167c3632fea4 jdk-9+147
5e4e893520ecdbd517c6ed6375f0885664fe62c4 jdk-9+148
30e1996bd55da36183434f24ed964adebf9ca71e jdk-9+149

View File

@ -0,0 +1,162 @@
#
# Copyright (c) 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
# under the terms of the GNU General Public License version 2 only, as
# published by the Free Software Foundation. Oracle designates this
# particular file as subject to the "Classpath" exception as provided
# by Oracle in the LICENSE file that accompanied this code.
#
# This code is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
# version 2 for more details (a copy is included in the LICENSE file that
# accompanied this code).
#
# You should have received a copy of the GNU General Public License version
# 2 along with this work; if not, write to the Free Software Foundation,
# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
#
# 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.
#
# This must be the first rule
default: all
include $(SPEC)
include MakeBase.gmk
include JavaCompilation.gmk
include SetupJavaCompilers.gmk
TARGETS :=
# Hook to include the corresponding custom file, if present.
$(eval $(call IncludeCustomExtension, hotspot, CompileTools.gmk))
ifeq ($(INCLUDE_GRAAL), true)
VM_CI_SRC_DIR := $(HOTSPOT_TOPDIR)/src/jdk.vm.ci/share/classes
SRC_DIR := $(HOTSPOT_TOPDIR)/src/jdk.vm.compiler/share/classes
##############################################################################
# Compile the annotation processors
$(eval $(call SetupJavaCompilation, BUILD_VM_COMPILER_MATCH_PROCESSOR, \
SETUP := GENERATE_OLDBYTECODE, \
SRC := \
$(SRC_DIR)/org.graalvm.compiler.common/src \
$(SRC_DIR)/org.graalvm.compiler.core/src \
$(SRC_DIR)/org.graalvm.compiler.core.common/src \
$(SRC_DIR)/org.graalvm.compiler.core.match.processor/src \
$(SRC_DIR)/org.graalvm.compiler.api.collections/src \
$(SRC_DIR)/org.graalvm.compiler.api.replacements/src \
$(SRC_DIR)/org.graalvm.compiler.asm/src \
$(SRC_DIR)/org.graalvm.compiler.bytecode/src \
$(SRC_DIR)/org.graalvm.compiler.code/src \
$(SRC_DIR)/org.graalvm.compiler.debug/src \
$(SRC_DIR)/org.graalvm.compiler.graph/src \
$(SRC_DIR)/org.graalvm.compiler.lir/src \
$(SRC_DIR)/org.graalvm.compiler.loop/src \
$(SRC_DIR)/org.graalvm.compiler.loop.phases/src \
$(SRC_DIR)/org.graalvm.compiler.nodeinfo/src \
$(SRC_DIR)/org.graalvm.compiler.nodes/src \
$(SRC_DIR)/org.graalvm.compiler.options/src \
$(SRC_DIR)/org.graalvm.compiler.phases/src \
$(SRC_DIR)/org.graalvm.compiler.phases.common/src \
$(SRC_DIR)/org.graalvm.compiler.serviceprovider/src \
$(SRC_DIR)/org.graalvm.compiler.virtual/src \
$(VM_CI_SRC_DIR)/jdk.vm.ci.code/src \
$(VM_CI_SRC_DIR)/jdk.vm.ci.common/src \
$(VM_CI_SRC_DIR)/jdk.vm.ci.meta/src \
$(VM_CI_SRC_DIR)/jdk.vm.ci.runtime/src \
$(VM_CI_SRC_DIR)/jdk.vm.ci.services/src \
, \
EXCLUDE_FILES := $(EXCLUDE_FILES), \
BIN := $(BUILDTOOLS_OUTPUTDIR)/jdk.vm.compiler.match.processor, \
JAR := $(BUILDTOOLS_OUTPUTDIR)/jdk.vm.compiler.match.processor.jar, \
))
TARGETS += $(BUILD_VM_COMPILER_MATCH_PROCESSOR)
##############################################################################
$(eval $(call SetupJavaCompilation, BUILD_VM_COMPILER_NODEINFO_PROCESSOR, \
SETUP := GENERATE_OLDBYTECODE, \
SRC := \
$(SRC_DIR)/org.graalvm.compiler.nodeinfo/src \
$(SRC_DIR)/org.graalvm.compiler.nodeinfo.processor/src \
, \
BIN := $(BUILDTOOLS_OUTPUTDIR)/jdk.vm.compiler.nodeinfo.processor, \
JAR := $(BUILDTOOLS_OUTPUTDIR)/jdk.vm.compiler.nodeinfo.processor.jar, \
))
TARGETS += $(BUILD_VM_COMPILER_NODEINFO_PROCESSOR)
##############################################################################
$(eval $(call SetupJavaCompilation, BUILD_VM_COMPILER_OPTIONS_PROCESSOR, \
SETUP := GENERATE_OLDBYTECODE, \
SRC := \
$(SRC_DIR)/org.graalvm.compiler.options/src \
$(SRC_DIR)/org.graalvm.compiler.options.processor/src \
, \
BIN := $(BUILDTOOLS_OUTPUTDIR)/jdk.vm.compiler.options.processor, \
JAR := $(BUILDTOOLS_OUTPUTDIR)/jdk.vm.compiler.options.processor.jar, \
))
TARGETS += $(BUILD_VM_COMPILER_OPTIONS_PROCESSOR)
##############################################################################
$(eval $(call SetupJavaCompilation, BUILD_VM_COMPILER_REPLACEMENTS_VERIFIER, \
SETUP := GENERATE_OLDBYTECODE, \
SRC := \
$(SRC_DIR)/org.graalvm.compiler.common/src \
$(SRC_DIR)/org.graalvm.compiler.replacements.verifier/src \
$(SRC_DIR)/org.graalvm.compiler.api.collections/src \
$(SRC_DIR)/org.graalvm.compiler.api.replacements/src \
$(SRC_DIR)/org.graalvm.compiler.code/src \
$(SRC_DIR)/org.graalvm.compiler.core.common/src \
$(SRC_DIR)/org.graalvm.compiler.debug/src \
$(SRC_DIR)/org.graalvm.compiler.graph/src \
$(SRC_DIR)/org.graalvm.compiler.nodeinfo/src \
$(SRC_DIR)/org.graalvm.compiler.options/src \
$(SRC_DIR)/org.graalvm.compiler.serviceprovider/src \
$(VM_CI_SRC_DIR)/jdk.vm.ci.code/src \
$(VM_CI_SRC_DIR)/jdk.vm.ci.common/src \
$(VM_CI_SRC_DIR)/jdk.vm.ci.meta/src \
$(VM_CI_SRC_DIR)/jdk.vm.ci.runtime/src \
$(VM_CI_SRC_DIR)/jdk.vm.ci.services/src \
, \
EXCLUDE_FILES := $(EXCLUDE_FILES), \
BIN := $(BUILDTOOLS_OUTPUTDIR)/jdk.vm.compiler.replacements.verifier, \
JAR := $(BUILDTOOLS_OUTPUTDIR)/jdk.vm.compiler.replacements.verifier.jar, \
))
TARGETS += $(BUILD_VM_COMPILER_REPLACEMENTS_VERIFIER)
##############################################################################
$(eval $(call SetupJavaCompilation, BUILD_VM_COMPILER_SERVICEPROVIDER_PROCESSOR, \
SETUP := GENERATE_OLDBYTECODE, \
SRC := \
$(SRC_DIR)/org.graalvm.compiler.serviceprovider/src \
$(SRC_DIR)/org.graalvm.compiler.serviceprovider.processor/src \
$(VM_CI_SRC_DIR)/jdk.vm.ci.services/src \
, \
EXCLUDE_FILES := $(EXCLUDE_FILES), \
BIN := $(BUILDTOOLS_OUTPUTDIR)/jdk.vm.compiler.serviceprovider.processor, \
JAR := $(BUILDTOOLS_OUTPUTDIR)/jdk.vm.compiler.serviceprovider.processor.jar, \
))
TARGETS += $(BUILD_VM_COMPILER_SERVICEPROVIDER_PROCESSOR)
##############################################################################
endif
all: $(TARGETS)
.PHONY: all

View File

@ -0,0 +1,152 @@
#
# Copyright (c) 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
# under the terms of the GNU General Public License version 2 only, as
# published by the Free Software Foundation. Oracle designates this
# particular file as subject to the "Classpath" exception as provided
# by Oracle in the LICENSE file that accompanied this code.
#
# This code is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
# version 2 for more details (a copy is included in the LICENSE file that
# accompanied this code).
#
# You should have received a copy of the GNU General Public License version
# 2 along with this work; if not, write to the Free Software Foundation,
# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
#
# 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.
#
default: all
include $(SPEC)
include MakeBase.gmk
$(eval $(call IncludeCustomExtension, hotspot, gensrc/Gensrc-jdk.vm.compiler.gmk))
GENSRC_DIR := $(SUPPORT_OUTPUTDIR)/gensrc/$(MODULE)
SRC_DIR := $(HOTSPOT_TOPDIR)/src/$(MODULE)/share/classes
################################################################################
PROC_SRC_SUBDIRS := \
org.graalvm.compiler.code \
org.graalvm.compiler.common \
org.graalvm.compiler.core \
org.graalvm.compiler.core.aarch64 \
org.graalvm.compiler.core.amd64 \
org.graalvm.compiler.core.common \
org.graalvm.compiler.core.sparc \
org.graalvm.compiler.debug \
org.graalvm.compiler.hotspot \
org.graalvm.compiler.hotspot.aarch64 \
org.graalvm.compiler.hotspot.amd64 \
org.graalvm.compiler.hotspot.sparc \
org.graalvm.compiler.graph \
org.graalvm.compiler.java \
org.graalvm.compiler.lir \
org.graalvm.compiler.lir.amd64 \
org.graalvm.compiler.loop \
org.graalvm.compiler.loop.phases \
org.graalvm.compiler.nodes \
org.graalvm.compiler.replacements \
org.graalvm.compiler.replacements.aarch64 \
org.graalvm.compiler.replacements.amd64 \
org.graalvm.compiler.phases \
org.graalvm.compiler.phases.common \
org.graalvm.compiler.printer \
org.graalvm.compiler.virtual \
#
PROC_SRC_DIRS := $(patsubst %, $(SRC_DIR)/%/src, $(PROC_SRC_SUBDIRS))
PROC_SRCS := $(filter %.java, $(call CacheFind, $(PROC_SRC_DIRS)))
ALL_SRC_DIRS := $(wildcard $(SRC_DIR)/*/src)
SOURCEPATH := $(call PathList, $(ALL_SRC_DIRS))
PROCESSOR_JARS := \
$(BUILDTOOLS_OUTPUTDIR)/jdk.vm.compiler.match.processor.jar \
$(BUILDTOOLS_OUTPUTDIR)/jdk.vm.compiler.nodeinfo.processor.jar \
$(BUILDTOOLS_OUTPUTDIR)/jdk.vm.compiler.options.processor.jar \
$(BUILDTOOLS_OUTPUTDIR)/jdk.vm.compiler.replacements.verifier.jar \
$(BUILDTOOLS_OUTPUTDIR)/jdk.vm.compiler.serviceprovider.processor.jar \
#
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 \
#
$(GENSRC_DIR)/_gensrc_proc_done: $(PROC_SRCS) $(PROCESSOR_JARS)
$(call MakeDir, $(@D))
$(eval $(call ListPathsSafely,PROC_SRCS,$(@D)/_gensrc_proc_files))
$(JAVA_SMALL) $(NEW_JAVAC) \
-XDignore.symbol.file \
--upgrade-module-path $(JDK_OUTPUTDIR)/modules --system none \
$(ADD_EXPORTS) \
-sourcepath $(SOURCEPATH) \
-implicit:none \
-proc:only \
-processorpath $(PROCESSOR_PATH) \
-d $(GENSRC_DIR) \
-s $(GENSRC_DIR) \
@$(@D)/_gensrc_proc_files
$(TOUCH) $@
TARGETS += $(GENSRC_DIR)/_gensrc_proc_done
################################################################################
$(GENSRC_DIR)/module-info.java.extra: $(GENSRC_DIR)/_gensrc_proc_done
($(CD) $(GENSRC_DIR)/META-INF/providers && \
p=""; \
for i in $$($(LS)); do \
c=$$($(CAT) $$i | $(TR) -d '\n\r'); \
if test x$$p != x$$c; then \
if test x$$p != x; then \
$(ECHO) " ;" >> $@; \
fi; \
$(ECHO) "provides $$c with" >> $@; \
p=$$c; \
fi; \
$(ECHO) " $$i," >> $@; \
done); \
$(ECHO) " ;" >> $@; \
$(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) '/' '.'); \
$(ECHO) " $$c," >> $@; \
done; \
$(ECHO) " ;" >> $@;
TARGETS += $(GENSRC_DIR)/module-info.java.extra
################################################################################
all: $(TARGETS)
.PHONY: default all

View File

@ -114,6 +114,10 @@ ifeq ($(call check-jvm-feature, compiler2), true)
ADLCFLAGS += -U_LP64
endif
ifeq ($(HOTSPOT_TARGET_CPU_ARCH), arm)
ADLCFLAGS += -DARM=1
endif
##############################################################################
# Concatenate all ad source files into a single file, which will be fed to
# adlc. Also include a #line directive at the start of every included file

View File

@ -124,15 +124,14 @@ fi
# We will set the LD_LIBRARY_PATH as follows:
# o $JVMPATH (directory portion only)
# o $JRE/lib/$ARCH
# o $JRE/lib
# followed by the user's previous effective LD_LIBRARY_PATH, if
# any.
JRE=$JDK
JAVA_HOME=$JDK
export JAVA_HOME
ARCH=@@LIBARCH@@
SBP=${MYDIR}:${JRE}/lib/${ARCH}
SBP=${MYDIR}:${JRE}/lib
# Set up a suitable LD_LIBRARY_PATH or DYLD_LIBRARY_PATH

View File

@ -107,6 +107,7 @@ $(eval $(call SetupNativeCompilation, BUILD_GTEST_LAUNCHER, \
LDFLAGS := $(LDFLAGS_JDKEXE), \
LDFLAGS_unix := -L$(JVM_OUTPUTDIR)/gtest $(call SET_SHARED_LIBRARY_ORIGIN), \
LDFLAGS_solaris := -library=stlport4, \
LIBS_linux := $(LIBCXX), \
LIBS_unix := -ljvm, \
LIBS_windows := $(JVM_OUTPUTDIR)/gtest/objs/jvm.lib, \
COPY_DEBUG_SYMBOLS := $(GTEST_COPY_DEBUG_SYMBOLS), \

View File

@ -63,8 +63,8 @@ JVM_CFLAGS_INCLUDES += \
# INCLUDE_SUFFIX_* is only meant for including the proper
# platform files. Don't use it to guard code. Use the value of
# HOTSPOT_TARGET_CPU_DEFINE etc. instead.
# Remaining TARGET_ARCH_* is needed to distinguish closed and open
# 64-bit ARM ports (also called AARCH64).
# Remaining TARGET_ARCH_* is needed to select the cpu specific
# sources for 64-bit ARM ports (arm versus aarch64).
JVM_CFLAGS_TARGET_DEFINES += \
-DTARGET_ARCH_$(HOTSPOT_TARGET_CPU_ARCH) \
-DINCLUDE_SUFFIX_OS=_$(HOTSPOT_TARGET_OS) \
@ -139,6 +139,20 @@ endif
################################################################################
# Platform specific setup
# ARM source selection
ifeq ($(OPENJDK_TARGET_OS)-$(OPENJDK_TARGET_CPU), linux-arm)
JVM_EXCLUDE_PATTERNS += arm_64
else ifeq ($(OPENJDK_TARGET_OS)-$(OPENJDK_TARGET_CPU), linux-aarch64)
# For 64-bit arm builds, we use the 64 bit hotspot/src/cpu/arm
# hotspot sources if HOTSPOT_TARGET_CPU_ARCH is set to arm.
# Exclude the aarch64 and 32 bit arm files for this build.
ifeq ($(HOTSPOT_TARGET_CPU_ARCH), arm)
JVM_EXCLUDE_PATTERNS += arm_32 aarch64
endif
endif
ifneq ($(filter $(OPENJDK_TARGET_OS), linux macosx windows), )
JVM_PRECOMPILED_HEADER := $(HOTSPOT_TOPDIR)/src/share/vm/precompiled/precompiled.hpp
endif

View File

@ -48,6 +48,12 @@ ifneq ($(OPENJDK_TARGET_OS), windows)
LIBJSIG_CPU_FLAGS := -m64
else ifeq ($(OPENJDK_TARGET_CPU), x86)
LIBJSIG_CPU_FLAGS := -m32 -march=i586
else ifeq ($(OPENJDK_TARGET_CPU), ppc64)
LIBJSIG_CPU_FLAGS := -mcpu=powerpc64 -mtune=power5
else ifeq ($(OPENJDK_TARGET_CPU), ppc64le)
LIBJSIG_CPU_FLAGS := -DABI_ELFv2 -mcpu=power8 -mtune=power8
else ifeq ($(OPENJDK_TARGET_CPU), s390x)
LIBJSIG_CPU_FLAGS := -mbackchain -march=z10
endif
else ifeq ($(OPENJDK_TARGET_OS), solaris)

View File

@ -146,3 +146,116 @@ ifneq ($(call check-jvm-feature, nmt), true)
memBaseline.cpp memReporter.cpp mallocTracker.cpp virtualMemoryTracker.cpp nmtCommon.cpp \
memTracker.cpp nmtDCmd.cpp mallocSiteTable.cpp
endif
ifeq ($(call check-jvm-feature, aot), true)
JVM_CFLAGS_FEATURES += -DINCLUDE_AOT
else
JVM_EXCLUDE_FILES += \
compiledIC_aot_x86_64.cpp compilerRuntime.cpp \
aotCodeHeap.cpp aotCompiledMethod.cpp aotLoader.cpp compiledIC_aot.cpp
endif
################################################################################
ifeq ($(call check-jvm-feature, link-time-opt), true)
# NOTE: Disable automatic opimization level and let the explicit cflag control
# optimization level instead. This activates O3 on slowdebug builds, just
# like the old build, but it's probably not right.
JVM_OPTIMIZATION :=
JVM_CFLAGS_FEATURES += -O3 -flto
JVM_LDFLAGS_FEATURES += -O3 -flto -fwhole-program -fno-strict-aliasing
endif
ifeq ($(call check-jvm-feature, minimal), true)
ifeq ($(call check-jvm-feature, link-time-opt), false)
JVM_OPTIMIZATION := SIZE
OPT_SPEED_SRC := \
allocation.cpp \
assembler.cpp \
assembler_linux_arm.cpp \
barrierSet.cpp \
basicLock.cpp \
biasedLocking.cpp \
bytecode.cpp \
bytecodeInterpreter.cpp \
bytecodeInterpreter_x86.cpp \
c1_Compilation.cpp \
c1_Compiler.cpp \
c1_GraphBuilder.cpp \
c1_LinearScan.cpp \
c1_LIR.cpp \
ciEnv.cpp \
ciObjectFactory.cpp \
codeBlob.cpp \
constantPool.cpp \
constMethod.cpp \
classLoader.cpp \
classLoaderData.cpp \
classFileParser.cpp \
classFileStream.cpp \
cpCache.cpp \
defNewGeneration.cpp \
frame_arm.cpp \
genCollectedHeap.cpp \
generation.cpp \
genMarkSweep.cpp \
growableArray.cpp \
handles.cpp \
hashtable.cpp \
heap.cpp \
icache.cpp \
icache_arm.cpp \
instanceKlass.cpp \
invocationCounter.cpp \
iterator.cpp \
javaCalls.cpp \
javaClasses.cpp \
jniFastGetField_arm.cpp \
jvm.cpp \
jvm_linux.cpp \
linkResolver.cpp \
klass.cpp \
klassVtable.cpp \
markSweep.cpp \
memRegion.cpp \
memoryPool.cpp \
method.cpp \
methodHandles.cpp \
methodHandles_arm.cpp \
methodLiveness.cpp \
metablock.cpp \
metaspace.cpp \
mutex.cpp \
mutex_linux.cpp \
mutexLocker.cpp \
nativeLookup.cpp \
objArrayKlass.cpp \
os_linux.cpp \
os_linux_arm.cpp \
placeHolders.cpp \
quickSort.cpp \
resourceArea.cpp \
rewriter.cpp \
sharedRuntime.cpp \
signature.cpp \
space.cpp \
stackMapTable.cpp \
symbolTable.cpp \
systemDictionary.cpp \
symbol.cpp \
synchronizer.cpp \
threadLS_bsd_x86.cpp \
threadLS_linux_arm.cpp \
threadLS_linux_x86.cpp \
timer.cpp \
typeArrayKlass.cpp \
unsafe.cpp \
utf8.cpp \
vmSymbols.cpp \
#
$(foreach s, $(OPT_SPEED_SRC), \
$(eval BUILD_LIBJVM_$s_OPTIMIZATION := HIGHEST_JVM))
BUILD_LIBJVM_systemDictionary.cpp_CXXFLAGS := -fno-optimize-sibling-calls
endif
endif

View File

@ -0,0 +1,53 @@
#
# Copyright (c) 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
# under the terms of the GNU General Public License version 2 only, as
# published by the Free Software Foundation. Oracle designates this
# particular file as subject to the "Classpath" exception as provided
# by Oracle in the LICENSE file that accompanied this code.
#
# This code is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
# version 2 for more details (a copy is included in the LICENSE file that
# accompanied this code).
#
# You should have received a copy of the GNU General Public License version
# 2 along with this work; if not, write to the Free Software Foundation,
# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
#
# 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 $(SPEC)
include NativeCompilation.gmk
$(eval $(call IncludeCustomExtension, hotspot, lib/Lib-jdk.aot.gmk))
##############################################################################
# Build libjelfshim only when AOT is enabled.
ifeq ($(ENABLE_AOT), true)
JELFSHIM_NAME := jelfshim
$(eval $(call SetupNativeCompilation, BUILD_LIBJELFSHIM, \
TOOLCHAIN := TOOLCHAIN_DEFAULT, \
OPTIMIZATION := LOW, \
LIBRARY := $(JELFSHIM_NAME), \
OUTPUT_DIR := $(call FindLibDirForModule, $(MODULE)), \
SRC := $(HOTSPOT_TOPDIR)/src/jdk.aot/unix/native/libjelfshim, \
CFLAGS := $(CFLAGS_JDKLIB) $(ELF_CFLAGS) \
-DAOT_VERSION_STRING='"$(VERSION_STRING)"' \
-I$(SUPPORT_OUTPUTDIR)/headers/$(MODULE), \
LDFLAGS := $(LDFLAGS_JDKLIB), \
OBJECT_DIR := $(SUPPORT_OUTPUTDIR)/native/$(MODULE)/lib$(JELFSHIM_NAME), \
LIBS := $(ELF_LIBS) $(LIBS_JDKLIB), \
))
TARGETS += $(BUILD_LIBJELFSHIM)
endif
##############################################################################

View File

@ -53,7 +53,6 @@ BUILD_HOTSPOT_JTREG_NATIVE_SRC := \
$(HOTSPOT_TOPDIR)/test/runtime/BoolReturn \
$(HOTSPOT_TOPDIR)/test/compiler/floatingpoint/ \
$(HOTSPOT_TOPDIR)/test/compiler/calls \
$(HOTSPOT_TOPDIR)/test/compiler/native \
$(HOTSPOT_TOPDIR)/test/serviceability/jvmti/GetNamedModule \
$(HOTSPOT_TOPDIR)/test/serviceability/jvmti/AddModuleReads \
$(HOTSPOT_TOPDIR)/test/serviceability/jvmti/AddModuleExportsAndOpens \
@ -97,7 +96,7 @@ ifeq ($(OPENJDK_TARGET_OS), linux)
BUILD_HOTSPOT_JTREG_LIBRARIES_LDFLAGS_libtest-rwx := -z execstack
BUILD_HOTSPOT_JTREG_EXECUTABLES_LIBS_exeinvoke := -ljvm -lpthread
BUILD_TEST_invoke_exeinvoke.c_OPTIMIZATION := NONE
BUILD_HOTSPOT_JTREG_EXECUTABLES_LDFLAGS_exeFPRegs := -ldl
BUILD_HOTSPOT_JTREG_EXECUTABLES_LIBS_exeFPRegs := -ldl
endif
ifeq ($(OPENJDK_TARGET_OS), windows)

View File

@ -9646,6 +9646,10 @@ instruct compareAndSwapNAcq(iRegINoSp res, indirect mem, iRegNNoSp oldval, iRegN
// ---------------------------------------------------------------------
// BEGIN This section of the file is automatically generated. Do not edit --------------
// Sundry CAS operations. Note that release is always true,
// regardless of the memory ordering of the CAS. This is because we
// need the volatile case to be sequentially consistent but there is
@ -9656,10 +9660,11 @@ instruct compareAndSwapNAcq(iRegINoSp res, indirect mem, iRegNNoSp oldval, iRegN
// This section is generated from aarch64_ad_cas.m4
instruct compareAndExchangeB(iRegI_R0 res, indirect mem, iRegI_R2 oldval, iRegI_R3 newval, rFlagsReg cr) %{
instruct compareAndExchangeB(iRegINoSp res, indirect mem, iRegI oldval, iRegI newval, rFlagsReg cr) %{
match(Set res (CompareAndExchangeB mem (Binary oldval newval)));
ins_cost(2 * VOLATILE_REF_COST);
effect(KILL cr);
effect(TEMP_DEF res, KILL cr);
format %{
"cmpxchg $res = $mem, $oldval, $newval\t# (byte, weak) if $mem == $oldval then $mem <-- $newval"
%}
@ -9673,10 +9678,10 @@ instruct compareAndExchangeB(iRegI_R0 res, indirect mem, iRegI_R2 oldval, iRegI_
ins_pipe(pipe_slow);
%}
instruct compareAndExchangeS(iRegI_R0 res, indirect mem, iRegI_R2 oldval, iRegI_R3 newval, rFlagsReg cr) %{
instruct compareAndExchangeS(iRegINoSp res, indirect mem, iRegI oldval, iRegI newval, rFlagsReg cr) %{
match(Set res (CompareAndExchangeS mem (Binary oldval newval)));
ins_cost(2 * VOLATILE_REF_COST);
effect(KILL cr);
effect(TEMP_DEF res, KILL cr);
format %{
"cmpxchg $res = $mem, $oldval, $newval\t# (short, weak) if $mem == $oldval then $mem <-- $newval"
%}
@ -9690,10 +9695,10 @@ instruct compareAndExchangeS(iRegI_R0 res, indirect mem, iRegI_R2 oldval, iRegI_
ins_pipe(pipe_slow);
%}
instruct compareAndExchangeI(iRegI_R0 res, indirect mem, iRegI_R2 oldval, iRegI_R3 newval, rFlagsReg cr) %{
instruct compareAndExchangeI(iRegINoSp res, indirect mem, iRegI oldval, iRegI newval, rFlagsReg cr) %{
match(Set res (CompareAndExchangeI mem (Binary oldval newval)));
ins_cost(2 * VOLATILE_REF_COST);
effect(KILL cr);
effect(TEMP_DEF res, KILL cr);
format %{
"cmpxchg $res = $mem, $oldval, $newval\t# (int, weak) if $mem == $oldval then $mem <-- $newval"
%}
@ -9705,10 +9710,10 @@ instruct compareAndExchangeI(iRegI_R0 res, indirect mem, iRegI_R2 oldval, iRegI_
ins_pipe(pipe_slow);
%}
instruct compareAndExchangeL(iRegL_R0 res, indirect mem, iRegL_R2 oldval, iRegL_R3 newval, rFlagsReg cr) %{
instruct compareAndExchangeL(iRegLNoSp res, indirect mem, iRegL oldval, iRegL newval, rFlagsReg cr) %{
match(Set res (CompareAndExchangeL mem (Binary oldval newval)));
ins_cost(2 * VOLATILE_REF_COST);
effect(KILL cr);
effect(TEMP_DEF res, KILL cr);
format %{
"cmpxchg $res = $mem, $oldval, $newval\t# (long, weak) if $mem == $oldval then $mem <-- $newval"
%}
@ -9720,10 +9725,10 @@ instruct compareAndExchangeL(iRegL_R0 res, indirect mem, iRegL_R2 oldval, iRegL_
ins_pipe(pipe_slow);
%}
instruct compareAndExchangeN(iRegN_R0 res, indirect mem, iRegN_R2 oldval, iRegN_R3 newval, rFlagsReg cr) %{
instruct compareAndExchangeN(iRegNNoSp res, indirect mem, iRegN oldval, iRegN newval, rFlagsReg cr) %{
match(Set res (CompareAndExchangeN mem (Binary oldval newval)));
ins_cost(2 * VOLATILE_REF_COST);
effect(KILL cr);
effect(TEMP_DEF res, KILL cr);
format %{
"cmpxchg $res = $mem, $oldval, $newval\t# (narrow oop, weak) if $mem == $oldval then $mem <-- $newval"
%}
@ -9735,10 +9740,10 @@ instruct compareAndExchangeN(iRegN_R0 res, indirect mem, iRegN_R2 oldval, iRegN_
ins_pipe(pipe_slow);
%}
instruct compareAndExchangeP(iRegP_R0 res, indirect mem, iRegP_R2 oldval, iRegP_R3 newval, rFlagsReg cr) %{
instruct compareAndExchangeP(iRegPNoSp res, indirect mem, iRegP oldval, iRegP newval, rFlagsReg cr) %{
match(Set res (CompareAndExchangeP mem (Binary oldval newval)));
ins_cost(2 * VOLATILE_REF_COST);
effect(KILL cr);
effect(TEMP_DEF res, KILL cr);
format %{
"cmpxchg $res = $mem, $oldval, $newval\t# (ptr, weak) if $mem == $oldval then $mem <-- $newval"
%}
@ -9853,6 +9858,8 @@ instruct weakCompareAndSwapP(iRegINoSp res, indirect mem, iRegP oldval, iRegP ne
%}
ins_pipe(pipe_slow);
%}
// END This section of the file is automatically generated. Do not edit --------------
// ---------------------------------------------------------------------
instruct get_and_setI(indirect mem, iRegINoSp newv, iRegI prev) %{
@ -12990,137 +12997,146 @@ instruct mulD_reg_reg(vRegD dst, vRegD src1, vRegD src2) %{
ins_pipe(fp_dop_reg_reg_d);
%}
// We cannot use these fused mul w add/sub ops because they don't
// produce the same result as the equivalent separated ops
// (essentially they don't round the intermediate result). that's a
// shame. leaving them here in case we can idenitfy cases where it is
// legitimate to use them
// src1 * src2 + src3
instruct maddF_reg_reg(vRegF dst, vRegF src1, vRegF src2, vRegF src3) %{
predicate(UseFMA);
match(Set dst (FmaF src3 (Binary src1 src2)));
format %{ "fmadds $dst, $src1, $src2, $src3" %}
// instruct maddF_reg_reg(vRegF dst, vRegF src1, vRegF src2, vRegF src3) %{
// match(Set dst (AddF (MulF src1 src2) src3));
ins_encode %{
__ fmadds(as_FloatRegister($dst$$reg),
as_FloatRegister($src1$$reg),
as_FloatRegister($src2$$reg),
as_FloatRegister($src3$$reg));
%}
// format %{ "fmadds $dst, $src1, $src2, $src3" %}
ins_pipe(pipe_class_default);
%}
// ins_encode %{
// __ fmadds(as_FloatRegister($dst$$reg),
// as_FloatRegister($src1$$reg),
// as_FloatRegister($src2$$reg),
// as_FloatRegister($src3$$reg));
// %}
// src1 * src2 + src3
instruct maddD_reg_reg(vRegD dst, vRegD src1, vRegD src2, vRegD src3) %{
predicate(UseFMA);
match(Set dst (FmaD src3 (Binary src1 src2)));
// ins_pipe(pipe_class_default);
// %}
format %{ "fmaddd $dst, $src1, $src2, $src3" %}
// instruct maddD_reg_reg(vRegD dst, vRegD src1, vRegD src2, vRegD src3) %{
// match(Set dst (AddD (MulD src1 src2) src3));
ins_encode %{
__ fmaddd(as_FloatRegister($dst$$reg),
as_FloatRegister($src1$$reg),
as_FloatRegister($src2$$reg),
as_FloatRegister($src3$$reg));
%}
// format %{ "fmaddd $dst, $src1, $src2, $src3" %}
ins_pipe(pipe_class_default);
%}
// ins_encode %{
// __ fmaddd(as_FloatRegister($dst$$reg),
// as_FloatRegister($src1$$reg),
// as_FloatRegister($src2$$reg),
// as_FloatRegister($src3$$reg));
// %}
// -src1 * src2 + src3
instruct msubF_reg_reg(vRegF dst, vRegF src1, vRegF src2, vRegF src3) %{
predicate(UseFMA);
match(Set dst (FmaF src3 (Binary (NegF src1) src2)));
match(Set dst (FmaF src3 (Binary src1 (NegF src2))));
// ins_pipe(pipe_class_default);
// %}
format %{ "fmsubs $dst, $src1, $src2, $src3" %}
// instruct msubF_reg_reg(vRegF dst, vRegF src1, vRegF src2, vRegF src3) %{
// match(Set dst (AddF (MulF (NegF src1) src2) src3));
// match(Set dst (AddF (NegF (MulF src1 src2)) src3));
ins_encode %{
__ fmsubs(as_FloatRegister($dst$$reg),
as_FloatRegister($src1$$reg),
as_FloatRegister($src2$$reg),
as_FloatRegister($src3$$reg));
%}
// format %{ "fmsubs $dst, $src1, $src2, $src3" %}
ins_pipe(pipe_class_default);
%}
// ins_encode %{
// __ fmsubs(as_FloatRegister($dst$$reg),
// as_FloatRegister($src1$$reg),
// as_FloatRegister($src2$$reg),
// as_FloatRegister($src3$$reg));
// %}
// -src1 * src2 + src3
instruct msubD_reg_reg(vRegD dst, vRegD src1, vRegD src2, vRegD src3) %{
predicate(UseFMA);
match(Set dst (FmaD src3 (Binary (NegD src1) src2)));
match(Set dst (FmaD src3 (Binary src1 (NegD src2))));
// ins_pipe(pipe_class_default);
// %}
format %{ "fmsubd $dst, $src1, $src2, $src3" %}
// instruct msubD_reg_reg(vRegD dst, vRegD src1, vRegD src2, vRegD src3) %{
// match(Set dst (AddD (MulD (NegD src1) src2) src3));
// match(Set dst (AddD (NegD (MulD src1 src2)) src3));
ins_encode %{
__ fmsubd(as_FloatRegister($dst$$reg),
as_FloatRegister($src1$$reg),
as_FloatRegister($src2$$reg),
as_FloatRegister($src3$$reg));
%}
// format %{ "fmsubd $dst, $src1, $src2, $src3" %}
ins_pipe(pipe_class_default);
%}
// ins_encode %{
// __ fmsubd(as_FloatRegister($dst$$reg),
// as_FloatRegister($src1$$reg),
// as_FloatRegister($src2$$reg),
// as_FloatRegister($src3$$reg));
// %}
// -src1 * src2 - src3
instruct mnaddF_reg_reg(vRegF dst, vRegF src1, vRegF src2, vRegF src3) %{
predicate(UseFMA);
match(Set dst (FmaF (NegF src3) (Binary (NegF src1) src2)));
match(Set dst (FmaF (NegF src3) (Binary src1 (NegF src2))));
// ins_pipe(pipe_class_default);
// %}
format %{ "fnmadds $dst, $src1, $src2, $src3" %}
// instruct mnaddF_reg_reg(vRegF dst, vRegF src1, vRegF src2, vRegF src3) %{
// match(Set dst (SubF (MulF (NegF src1) src2) src3));
// match(Set dst (SubF (NegF (MulF src1 src2)) src3));
ins_encode %{
__ fnmadds(as_FloatRegister($dst$$reg),
as_FloatRegister($src1$$reg),
as_FloatRegister($src2$$reg),
as_FloatRegister($src3$$reg));
%}
// format %{ "fnmadds $dst, $src1, $src2, $src3" %}
ins_pipe(pipe_class_default);
%}
// ins_encode %{
// __ fnmadds(as_FloatRegister($dst$$reg),
// as_FloatRegister($src1$$reg),
// as_FloatRegister($src2$$reg),
// as_FloatRegister($src3$$reg));
// %}
// -src1 * src2 - src3
instruct mnaddD_reg_reg(vRegD dst, vRegD src1, vRegD src2, vRegD src3) %{
predicate(UseFMA);
match(Set dst (FmaD (NegD src3) (Binary (NegD src1) src2)));
match(Set dst (FmaD (NegD src3) (Binary src1 (NegD src2))));
// ins_pipe(pipe_class_default);
// %}
format %{ "fnmaddd $dst, $src1, $src2, $src3" %}
// instruct mnaddD_reg_reg(vRegD dst, vRegD src1, vRegD src2, vRegD src3) %{
// match(Set dst (SubD (MulD (NegD src1) src2) src3));
// match(Set dst (SubD (NegD (MulD src1 src2)) src3));
ins_encode %{
__ fnmaddd(as_FloatRegister($dst$$reg),
as_FloatRegister($src1$$reg),
as_FloatRegister($src2$$reg),
as_FloatRegister($src3$$reg));
%}
// format %{ "fnmaddd $dst, $src1, $src2, $src3" %}
ins_pipe(pipe_class_default);
%}
// ins_encode %{
// __ fnmaddd(as_FloatRegister($dst$$reg),
// as_FloatRegister($src1$$reg),
// as_FloatRegister($src2$$reg),
// as_FloatRegister($src3$$reg));
// %}
// src1 * src2 - src3
instruct mnsubF_reg_reg(vRegF dst, vRegF src1, vRegF src2, vRegF src3, immF0 zero) %{
predicate(UseFMA);
match(Set dst (FmaF (NegF src3) (Binary src1 src2)));
// ins_pipe(pipe_class_default);
// %}
format %{ "fnmsubs $dst, $src1, $src2, $src3" %}
// instruct mnsubF_reg_reg(vRegF dst, vRegF src1, vRegF src2, vRegF src3, immF0 zero) %{
// match(Set dst (SubF (MulF src1 src2) src3));
ins_encode %{
__ fnmsubs(as_FloatRegister($dst$$reg),
as_FloatRegister($src1$$reg),
as_FloatRegister($src2$$reg),
as_FloatRegister($src3$$reg));
%}
// format %{ "fnmsubs $dst, $src1, $src2, $src3" %}
ins_pipe(pipe_class_default);
%}
// ins_encode %{
// __ fnmsubs(as_FloatRegister($dst$$reg),
// as_FloatRegister($src1$$reg),
// as_FloatRegister($src2$$reg),
// as_FloatRegister($src3$$reg));
// %}
// src1 * src2 - src3
instruct mnsubD_reg_reg(vRegD dst, vRegD src1, vRegD src2, vRegD src3, immD0 zero) %{
predicate(UseFMA);
match(Set dst (FmaD (NegD src3) (Binary src1 src2)));
// ins_pipe(pipe_class_default);
// %}
format %{ "fnmsubd $dst, $src1, $src2, $src3" %}
// instruct mnsubD_reg_reg(vRegD dst, vRegD src1, vRegD src2, vRegD src3, immD0 zero) %{
// match(Set dst (SubD (MulD src1 src2) src3));
ins_encode %{
// n.b. insn name should be fnmsubd
__ fnmsub(as_FloatRegister($dst$$reg),
as_FloatRegister($src1$$reg),
as_FloatRegister($src2$$reg),
as_FloatRegister($src3$$reg));
%}
// format %{ "fnmsubd $dst, $src1, $src2, $src3" %}
// ins_encode %{
// // n.b. insn name should be fnmsubd
// __ fnmsub(as_FloatRegister($dst$$reg),
// as_FloatRegister($src1$$reg),
// as_FloatRegister($src2$$reg),
// as_FloatRegister($src3$$reg));
// %}
// ins_pipe(pipe_class_default);
// %}
ins_pipe(pipe_class_default);
%}
instruct divF_reg_reg(vRegF dst, vRegF src1, vRegF src2) %{

View File

@ -65,7 +65,9 @@ bool AbstractInterpreter::can_be_compiled(methodHandle m) {
case Interpreter::java_lang_math_log10 : // fall thru
case Interpreter::java_lang_math_sqrt : // fall thru
case Interpreter::java_lang_math_pow : // fall thru
case Interpreter::java_lang_math_exp :
case Interpreter::java_lang_math_exp : // fall thru
case Interpreter::java_lang_math_fmaD : // fall thru
case Interpreter::java_lang_math_fmaF :
return false;
default:
return true;

View File

@ -848,7 +848,7 @@ public:
// architecture. In debug mode we shrink it in order to test
// trampolines, but not so small that branches in the interpreter
// are out of range.
static const unsigned long branch_range = NOT_DEBUG(128 * M) DEBUG_ONLY(2 * M);
static const unsigned long branch_range = INCLUDE_JVMCI ? 128 * M : NOT_DEBUG(128 * M) DEBUG_ONLY(2 * M);
static bool reachable_from_branch_at(address branch, address target) {
return uabs(target - branch) < branch_range;

View File

@ -375,7 +375,7 @@ int LIR_Assembler::emit_exception_handler() {
__ nop();
// generate code for exception handler
address handler_base = __ start_a_stub(exception_handler_size);
address handler_base = __ start_a_stub(exception_handler_size());
if (handler_base == NULL) {
// not enough space left for the handler
bailout("exception handler overflow");
@ -393,7 +393,7 @@ int LIR_Assembler::emit_exception_handler() {
// search an exception handler (r0: exception oop, r3: throwing pc)
__ far_call(RuntimeAddress(Runtime1::entry_for(Runtime1::handle_exception_from_callee_id))); __ should_not_reach_here();
guarantee(code_offset() - offset <= exception_handler_size, "overflow");
guarantee(code_offset() - offset <= exception_handler_size(), "overflow");
__ end_a_stub();
return offset;
@ -467,7 +467,7 @@ int LIR_Assembler::emit_deopt_handler() {
__ nop();
// generate code for exception handler
address handler_base = __ start_a_stub(deopt_handler_size);
address handler_base = __ start_a_stub(deopt_handler_size());
if (handler_base == NULL) {
// not enough space left for the handler
bailout("deopt handler overflow");
@ -478,7 +478,7 @@ int LIR_Assembler::emit_deopt_handler() {
__ adr(lr, pc());
__ far_jump(RuntimeAddress(SharedRuntime::deopt_blob()->unpack()));
guarantee(code_offset() - offset <= deopt_handler_size, "overflow");
guarantee(code_offset() - offset <= deopt_handler_size(), "overflow");
__ end_a_stub();
return offset;
@ -1055,7 +1055,7 @@ int LIR_Assembler::array_element_size(BasicType type) const {
return exact_log2(elem_size);
}
void LIR_Assembler::emit_op3(LIR_Op3* op) {
void LIR_Assembler::arithmetic_idiv(LIR_Op3* op, bool is_irem) {
Register Rdividend = op->in_opr1()->as_register();
Register Rdivisor = op->in_opr2()->as_register();
Register Rscratch = op->in_opr3()->as_register();
@ -1076,12 +1076,31 @@ void LIR_Assembler::emit_op3(LIR_Op3* op) {
// convert division by a power of two into some shifts and logical operations
}
if (op->code() == lir_irem) {
__ corrected_idivl(Rresult, Rdividend, Rdivisor, true, rscratch1);
} else if (op->code() == lir_idiv) {
__ corrected_idivl(Rresult, Rdividend, Rdivisor, false, rscratch1);
} else
ShouldNotReachHere();
__ corrected_idivl(Rresult, Rdividend, Rdivisor, is_irem, rscratch1);
}
void LIR_Assembler::emit_op3(LIR_Op3* op) {
switch (op->code()) {
case lir_idiv:
arithmetic_idiv(op, false);
break;
case lir_irem:
arithmetic_idiv(op, true);
break;
case lir_fmad:
__ fmaddd(op->result_opr()->as_double_reg(),
op->in_opr1()->as_double_reg(),
op->in_opr2()->as_double_reg(),
op->in_opr3()->as_double_reg());
break;
case lir_fmaf:
__ fmadds(op->result_opr()->as_float_reg(),
op->in_opr1()->as_float_reg(),
op->in_opr2()->as_float_reg(),
op->in_opr3()->as_float_reg());
break;
default: ShouldNotReachHere(); break;
}
}
void LIR_Assembler::emit_opBranch(LIR_OpBranch* op) {
@ -2001,7 +2020,7 @@ void LIR_Assembler::vtable_call(LIR_OpJavaCall* op) {
void LIR_Assembler::emit_static_call_stub() {
address call_pc = __ pc();
address stub = __ start_a_stub(call_stub_size);
address stub = __ start_a_stub(call_stub_size());
if (stub == NULL) {
bailout("static call stub overflow");
return;
@ -2014,7 +2033,7 @@ void LIR_Assembler::emit_static_call_stub() {
__ movptr(rscratch1, 0);
__ br(rscratch1);
assert(__ offset() - start <= call_stub_size, "stub too big");
assert(__ offset() - start <= call_stub_size(), "stub too big");
__ end_a_stub();
}
@ -2249,6 +2268,25 @@ void LIR_Assembler::emit_arraycopy(LIR_OpArrayCopy* op) {
__ cbz(dst, *stub->entry());
}
// If the compiler was not able to prove that exact type of the source or the destination
// of the arraycopy is an array type, check at runtime if the source or the destination is
// an instance type.
if (flags & LIR_OpArrayCopy::type_check) {
if (!(flags & LIR_OpArrayCopy::LIR_OpArrayCopy::dst_objarray)) {
__ load_klass(tmp, dst);
__ ldrw(rscratch1, Address(tmp, in_bytes(Klass::layout_helper_offset())));
__ cmpw(rscratch1, Klass::_lh_neutral_value);
__ br(Assembler::GE, *stub->entry());
}
if (!(flags & LIR_OpArrayCopy::LIR_OpArrayCopy::src_objarray)) {
__ load_klass(tmp, src);
__ ldrw(rscratch1, Address(tmp, in_bytes(Klass::layout_helper_offset())));
__ cmpw(rscratch1, Klass::_lh_neutral_value);
__ br(Assembler::GE, *stub->entry());
}
}
// check if negative
if (flags & LIR_OpArrayCopy::src_pos_positive_check) {
__ cmpw(src_pos, 0);

View File

@ -68,14 +68,19 @@ friend class ArrayCopyStub;
void deoptimize_trap(CodeEmitInfo *info);
enum {
_call_stub_size = 12 * NativeInstruction::instruction_size,
_call_aot_stub_size = 0,
_exception_handler_size = DEBUG_ONLY(1*K) NOT_DEBUG(175),
_deopt_handler_size = 7 * NativeInstruction::instruction_size
};
void arithmetic_idiv(LIR_Op3* op, bool is_irem);
public:
void store_parameter(Register r, int offset_from_esp_in_words);
void store_parameter(jint c, int offset_from_esp_in_words);
void store_parameter(jobject c, int offset_from_esp_in_words);
enum { call_stub_size = 12 * NativeInstruction::instruction_size,
exception_handler_size = DEBUG_ONLY(1*K) NOT_DEBUG(175),
deopt_handler_size = 7 * NativeInstruction::instruction_size };
#endif // CPU_AARCH64_VM_C1_LIRASSEMBLER_AARCH64_HPP

View File

@ -1034,7 +1034,26 @@ void LIRGenerator::do_update_CRC32C(Intrinsic* x) {
}
void LIRGenerator::do_FmaIntrinsic(Intrinsic* x) {
fatal("FMA intrinsic is not implemented on this platform");
assert(x->number_of_arguments() == 3, "wrong type");
assert(UseFMA, "Needs FMA instructions support.");
LIRItem value(x->argument_at(0), this);
LIRItem value1(x->argument_at(1), this);
LIRItem value2(x->argument_at(2), this);
value.load_item();
value1.load_item();
value2.load_item();
LIR_Opr calc_input = value.result();
LIR_Opr calc_input1 = value1.result();
LIR_Opr calc_input2 = value2.result();
LIR_Opr calc_result = rlock_result(x);
switch (x->id()) {
case vmIntrinsics::_fmaD: __ fmad(calc_input, calc_input1, calc_input2, calc_result); break;
case vmIntrinsics::_fmaF: __ fmaf(calc_input, calc_input1, calc_input2, calc_result); break;
default: ShouldNotReachHere();
}
}
void LIRGenerator::do_vectorizedMismatch(Intrinsic* x) {

View File

@ -1,3 +1,31 @@
dnl Copyright (c) 2016, Red Hat Inc. All rights reserved.
dnl DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
dnl
dnl This code is free software; you can redistribute it and/or modify it
dnl under the terms of the GNU General Public License version 2 only, as
dnl published by the Free Software Foundation.
dnl
dnl This code is distributed in the hope that it will be useful, but WITHOUT
dnl ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
dnl FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
dnl version 2 for more details (a copy is included in the LICENSE file that
dnl accompanied this code).
dnl
dnl You should have received a copy of the GNU General Public License version
dnl 2 along with this work; if not, write to the Free Software Foundation,
dnl Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
dnl
dnl Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
dnl or visit www.oracle.com if you need additional information or have any
dnl questions.
dnl
dnl
dnl Process this file with m4 cas.m4 to generate the CAE and wCAS
dnl instructions used in aarch64.ad.
dnl
// BEGIN This section of the file is automatically generated. Do not edit --------------
// Sundry CAS operations. Note that release is always true,
// regardless of the memory ordering of the CAS. This is because we
// need the volatile case to be sequentially consistent but there is
@ -5,13 +33,16 @@
// can't check the type of memory ordering here, so we always emit a
// STLXR.
// This section is generated from aarch64_ad_cas.m4
define(`CAS_INSN',
`
instruct compareAndExchange$1$5(iReg$2_R0 res, indirect mem, iReg$2_R2 oldval, iReg$2_R3 newval, rFlagsReg cr) %{
instruct compareAndExchange$1$5(iReg$2NoSp res, indirect mem, iReg$2 oldval, iReg$2 newval, rFlagsReg cr) %{
match(Set res (CompareAndExchange$1 mem (Binary oldval newval)));
ifelse($5,Acq,' predicate(needs_acquiring_load_exclusive(n));
ins_cost(VOLATILE_REF_COST);`,' ins_cost(2 * VOLATILE_REF_COST);`)
effect(KILL cr);
effect(TEMP_DEF res, KILL cr);
format %{
"cmpxchg $res = $mem, $oldval, $newval\t# ($3, weak) if $mem == $oldval then $mem <-- $newval"
%}
@ -24,11 +55,11 @@ instruct compareAndExchange$1$5(iReg$2_R0 res, indirect mem, iReg$2_R2 oldval, i
%}')dnl
define(`CAS_INSN4',
`
instruct compareAndExchange$1$7(iReg$2_R0 res, indirect mem, iReg$2_R2 oldval, iReg$2_R3 newval, rFlagsReg cr) %{
instruct compareAndExchange$1$7(iReg$2NoSp res, indirect mem, iReg$2 oldval, iReg$2 newval, rFlagsReg cr) %{
match(Set res (CompareAndExchange$1 mem (Binary oldval newval)));
ifelse($7,Acq,' predicate(needs_acquiring_load_exclusive(n));
ins_cost(VOLATILE_REF_COST);`,' ins_cost(2 * VOLATILE_REF_COST);`)
effect(KILL cr);
effect(TEMP_DEF res, KILL cr);
format %{
"cmpxchg $res = $mem, $oldval, $newval\t# ($3, weak) if $mem == $oldval then $mem <-- $newval"
%}
@ -107,3 +138,5 @@ dnl CAS_INSN3(L,L,long,xword,Acq)
dnl CAS_INSN3(N,N,narrow oop,word,Acq)
dnl CAS_INSN3(P,P,ptr,xword,Acq)
dnl
// END This section of the file is automatically generated. Do not edit --------------

View File

@ -76,13 +76,13 @@ int CompiledStaticCall::reloc_to_interp_stub() {
return 4; // 3 in emit_to_interp_stub + 1 in emit_call
}
void CompiledStaticCall::set_to_interpreted(methodHandle callee, address entry) {
address stub = find_stub();
void CompiledDirectStaticCall::set_to_interpreted(const methodHandle& callee, address entry) {
address stub = find_stub(false /* is_aot */);
guarantee(stub != NULL, "stub not found");
if (TraceICs) {
ResourceMark rm;
tty->print_cr("CompiledStaticCall@" INTPTR_FORMAT ": set_to_interpreted %s",
tty->print_cr("CompiledDirectStaticCall@" INTPTR_FORMAT ": set_to_interpreted %s",
p2i(instruction_address()),
callee->name_and_sig_as_C_string());
}
@ -107,7 +107,7 @@ void CompiledStaticCall::set_to_interpreted(methodHandle callee, address entry)
set_destination_mt_safe(stub);
}
void CompiledStaticCall::set_stub_to_clean(static_stub_Relocation* static_stub) {
void CompiledDirectStaticCall::set_stub_to_clean(static_stub_Relocation* static_stub) {
assert (CompiledIC_lock->is_locked() || SafepointSynchronize::is_at_safepoint(), "mt unsafe call");
// Reset stub.
address stub = static_stub->addr();
@ -121,15 +121,15 @@ void CompiledStaticCall::set_stub_to_clean(static_stub_Relocation* static_stub)
// Non-product mode code
#ifndef PRODUCT
void CompiledStaticCall::verify() {
void CompiledDirectStaticCall::verify() {
// Verify call.
NativeCall::verify();
_call->verify();
if (os::is_MP()) {
verify_alignment();
_call->verify_alignment();
}
// Verify stub.
address stub = find_stub();
address stub = find_stub(false /* is_aot */);
assert(stub != NULL, "no stub found for static call");
// Creation also verifies the object.
NativeMovConstReg* method_holder = nativeMovConstReg_at(stub);

View File

@ -407,10 +407,8 @@ void InterpreterMacroAssembler::jump_from_interpreted(Register method, Register
// JVMTI events, such as single-stepping, are implemented partly by avoiding running
// compiled code in threads for which the event is enabled. Check here for
// interp_only_mode if these events CAN be enabled.
// interp_only is an int, on little endian it is sufficient to test the byte only
// Is a cmpl faster?
ldr(rscratch1, Address(rthread, JavaThread::interp_only_mode_offset()));
cbz(rscratch1, run_compiled_code);
ldrw(rscratch1, Address(rthread, JavaThread::interp_only_mode_offset()));
cbzw(rscratch1, run_compiled_code);
ldr(rscratch1, Address(method, Method::interpreter_entry_offset()));
br(rscratch1);
bind(run_compiled_code);

View File

@ -41,28 +41,34 @@ jint CodeInstaller::pd_next_offset(NativeInstruction* inst, jint pc_offset, Hand
void CodeInstaller::pd_patch_OopConstant(int pc_offset, Handle constant, TRAPS) {
address pc = _instructions->start() + pc_offset;
#ifdef ASSERT
{
NativeInstruction *insn = nativeInstruction_at(pc);
if (HotSpotObjectConstantImpl::compressed(constant)) {
// Mov narrow constant: movz n << 16, movk
assert(Instruction_aarch64::extract(insn->encoding(), 31, 21) == 0b11010010101 &&
nativeInstruction_at(pc+4)->is_movk(), "wrong insn in patch");
} else {
// Move wide constant: movz n, movk, movk.
assert(nativeInstruction_at(pc+4)->is_movk()
&& nativeInstruction_at(pc+8)->is_movk(), "wrong insn in patch");
}
}
#endif // ASSERT
Handle obj = HotSpotObjectConstantImpl::object(constant);
jobject value = JNIHandles::make_local(obj());
if (HotSpotObjectConstantImpl::compressed(constant)) {
int oop_index = _oop_recorder->find_index(value);
RelocationHolder rspec = oop_Relocation::spec(oop_index);
_instructions->relocate(pc, rspec, 1);
Unimplemented();
} else {
NativeMovConstReg* move = nativeMovConstReg_at(pc);
move->set_data((intptr_t) value);
int oop_index = _oop_recorder->find_index(value);
RelocationHolder rspec = oop_Relocation::spec(oop_index);
_instructions->relocate(pc, rspec);
}
MacroAssembler::patch_oop(pc, (address)obj());
int oop_index = _oop_recorder->find_index(value);
RelocationHolder rspec = oop_Relocation::spec(oop_index);
_instructions->relocate(pc, rspec);
}
void CodeInstaller::pd_patch_MetaspaceConstant(int pc_offset, Handle constant, TRAPS) {
address pc = _instructions->start() + pc_offset;
if (HotSpotMetaspaceConstantImpl::compressed(constant)) {
narrowKlass narrowOop = record_narrow_metadata_reference(_instructions, pc, constant, CHECK);
MacroAssembler::patch_narrow_klass(pc, narrowOop);
TRACE_jvmci_3("relocating (narrow metaspace constant) at " PTR_FORMAT "/0x%x", p2i(pc), narrowOop);
Unimplemented();
} else {
NativeMovConstReg* move = nativeMovConstReg_at(pc);
void* reference = record_metadata_reference(_instructions, pc, constant, CHECK);
@ -167,8 +173,8 @@ VMReg CodeInstaller::get_hotspot_reg(jint jvmci_reg, TRAPS) {
if (jvmci_reg < RegisterImpl::number_of_registers) {
return as_Register(jvmci_reg)->as_VMReg();
} else {
jint floatRegisterNumber = jvmci_reg - RegisterImpl::number_of_registers;
if (floatRegisterNumber < FloatRegisterImpl::number_of_registers) {
jint floatRegisterNumber = jvmci_reg - RegisterImpl::number_of_registers_for_jvmci;
if (floatRegisterNumber >= 0 && floatRegisterNumber < FloatRegisterImpl::number_of_registers) {
return as_FloatRegister(floatRegisterNumber)->as_VMReg();
}
JVMCI_ERROR_NULL("invalid register number: %d", jvmci_reg);

View File

@ -185,6 +185,19 @@ int MacroAssembler::patch_oop(address insn_addr, address o) {
return instructions * NativeInstruction::instruction_size;
}
int MacroAssembler::patch_narrow_klass(address insn_addr, narrowKlass n) {
// Metatdata pointers are either narrow (32 bits) or wide (48 bits).
// We encode narrow ones by setting the upper 16 bits in the first
// instruction.
NativeInstruction *insn = nativeInstruction_at(insn_addr);
assert(Instruction_aarch64::extract(insn->encoding(), 31, 21) == 0b11010010101 &&
nativeInstruction_at(insn_addr+4)->is_movk(), "wrong insns in patch");
Instruction_aarch64::patch(insn_addr, 20, 5, n >> 16);
Instruction_aarch64::patch(insn_addr+4, 20, 5, n & 0xffff);
return 2 * NativeInstruction::instruction_size;
}
address MacroAssembler::target_addr_for_insn(address insn_addr, unsigned insn) {
long offset = 0;
if ((Instruction_aarch64::extract(insn, 29, 24) & 0b011011) == 0b00011000) {

View File

@ -590,6 +590,7 @@ public:
#endif
static int patch_oop(address insn_addr, address o);
static int patch_narrow_klass(address insn_addr, narrowKlass n);
address emit_trampoline_stub(int insts_call_instruction_offset, address target);

View File

@ -42,8 +42,9 @@ inline Register as_Register(int encoding) {
class RegisterImpl: public AbstractRegisterImpl {
public:
enum {
number_of_registers = 32,
number_of_byte_registers = 32
number_of_registers = 32,
number_of_byte_registers = 32,
number_of_registers_for_jvmci = 34 // Including SP and ZR.
};
// derived registers, offsets, and addresses
@ -103,6 +104,10 @@ CONSTANT_REGISTER_DECLARATION(Register, r28, (28));
CONSTANT_REGISTER_DECLARATION(Register, r29, (29));
CONSTANT_REGISTER_DECLARATION(Register, r30, (30));
// r31 is not a general purpose register, but represents either the
// stack pointer or the zero/discard register depending on the
// instruction.
CONSTANT_REGISTER_DECLARATION(Register, r31_sp, (31));
CONSTANT_REGISTER_DECLARATION(Register, zr, (32));
CONSTANT_REGISTER_DECLARATION(Register, sp, (33));

View File

@ -2388,6 +2388,7 @@ void SharedRuntime::generate_deopt_blob() {
__ movw(rcpool, (int32_t)Deoptimization::Unpack_reexecute);
__ mov(c_rarg0, rthread);
__ movw(c_rarg2, rcpool); // exec mode
__ lea(rscratch1,
RuntimeAddress(CAST_FROM_FN_PTR(address,
Deoptimization::uncommon_trap)));

View File

@ -2743,7 +2743,7 @@ class StubGenerator: public StubCodeGenerator {
__ align(CodeEntryAlignment);
StubCodeMark mark(this, "StubRoutines", "cipherBlockChaining_encryptAESCrypt");
Label L_loadkeys_44, L_loadkeys_52, L_aes_loop, L_rounds_44, L_rounds_52, _L_finish;
Label L_loadkeys_44, L_loadkeys_52, L_aes_loop, L_rounds_44, L_rounds_52;
const Register from = c_rarg0; // source array address
const Register to = c_rarg1; // destination array address
@ -2757,8 +2757,7 @@ class StubGenerator: public StubCodeGenerator {
__ enter();
__ subsw(rscratch2, len_reg, zr);
__ br(Assembler::LE, _L_finish);
__ movw(rscratch2, len_reg);
__ ldrw(keylen, Address(key, arrayOopDesc::length_offset_in_bytes() - arrayOopDesc::base_offset_in_bytes(T_INT)));
@ -2823,7 +2822,6 @@ class StubGenerator: public StubCodeGenerator {
__ st1(v0, __ T16B, rvec);
__ BIND(_L_finish);
__ mov(r0, rscratch2);
__ leave();
@ -2849,7 +2847,7 @@ class StubGenerator: public StubCodeGenerator {
__ align(CodeEntryAlignment);
StubCodeMark mark(this, "StubRoutines", "cipherBlockChaining_decryptAESCrypt");
Label L_loadkeys_44, L_loadkeys_52, L_aes_loop, L_rounds_44, L_rounds_52, _L_finish;
Label L_loadkeys_44, L_loadkeys_52, L_aes_loop, L_rounds_44, L_rounds_52;
const Register from = c_rarg0; // source array address
const Register to = c_rarg1; // destination array address
@ -2863,8 +2861,7 @@ class StubGenerator: public StubCodeGenerator {
__ enter();
__ subsw(rscratch2, len_reg, zr);
__ br(Assembler::LE, _L_finish);
__ movw(rscratch2, len_reg);
__ ldrw(keylen, Address(key, arrayOopDesc::length_offset_in_bytes() - arrayOopDesc::base_offset_in_bytes(T_INT)));
@ -2933,7 +2930,6 @@ class StubGenerator: public StubCodeGenerator {
__ st1(v2, __ T16B, rvec);
__ BIND(_L_finish);
__ mov(r0, rscratch2);
__ leave();

View File

@ -203,6 +203,26 @@ address TemplateInterpreterGenerator::generate_math_entry(AbstractInterpreter::M
__ mov(sp, r13);
generate_transcendental_entry(kind, 2);
break;
case Interpreter::java_lang_math_fmaD :
if (UseFMA) {
entry_point = __ pc();
__ ldrd(v0, Address(esp, 4 * Interpreter::stackElementSize));
__ ldrd(v1, Address(esp, 2 * Interpreter::stackElementSize));
__ ldrd(v2, Address(esp));
__ fmaddd(v0, v0, v1, v2);
__ mov(sp, r13); // Restore caller's SP
}
break;
case Interpreter::java_lang_math_fmaF :
if (UseFMA) {
entry_point = __ pc();
__ ldrs(v0, Address(esp, 2 * Interpreter::stackElementSize));
__ ldrs(v1, Address(esp, Interpreter::stackElementSize));
__ ldrs(v2, Address(esp));
__ fmadds(v0, v0, v1, v2);
__ mov(sp, r13); // Restore caller's SP
}
break;
default:
;
}
@ -883,7 +903,7 @@ address TemplateInterpreterGenerator::generate_Reference_get_entry(void) {
// and so we don't need to call the G1 pre-barrier. Thus we can use the
// regular method entry code to generate the NPE.
//
// This code is based on generate_accessor_enty.
// This code is based on generate_accessor_entry.
//
// rmethod: Method*
// r13: senderSP must preserve for slow path, set SP to it on fast path
@ -901,11 +921,11 @@ address TemplateInterpreterGenerator::generate_Reference_get_entry(void) {
__ ldr(local_0, Address(esp, 0));
__ cbz(local_0, slow_path);
// Load the value of the referent field.
const Address field_address(local_0, referent_offset);
__ load_heap_oop(local_0, field_address);
__ mov(r19, r13); // Move senderSP to a callee-saved register
// Generate the G1 pre-barrier code to log the value of
// the referent field in an SATB buffer.
__ enter(); // g1_write may call runtime
@ -917,7 +937,7 @@ address TemplateInterpreterGenerator::generate_Reference_get_entry(void) {
true /* expand_call */);
__ leave();
// areturn
__ andr(sp, r13, -16); // done with stack
__ andr(sp, r19, -16); // done with stack
__ ret(lr);
// generate a vanilla interpreter entry as the slow path

View File

@ -262,9 +262,8 @@ void VM_Version::get_processor_features() {
FLAG_SET_DEFAULT(UseCRC32CIntrinsics, false);
}
if (UseFMA) {
warning("FMA instructions are not available on this CPU");
FLAG_SET_DEFAULT(UseFMA, false);
if (FLAG_IS_DEFAULT(UseFMA)) {
FLAG_SET_DEFAULT(UseFMA, true);
}
if (auxv & (HWCAP_SHA1 | HWCAP_SHA2)) {

View File

@ -0,0 +1,270 @@
/*
* 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "asm/assembler.hpp"
#include "interpreter/bytecode.hpp"
#include "interpreter/interpreter.hpp"
#include "oops/constMethod.hpp"
#include "oops/method.hpp"
#include "prims/methodHandles.hpp"
#include "runtime/handles.inline.hpp"
#include "runtime/frame.inline.hpp"
#include "runtime/synchronizer.hpp"
#include "utilities/macros.hpp"
int AbstractInterpreter::BasicType_as_index(BasicType type) {
int i = 0;
switch (type) {
#ifdef AARCH64
case T_BOOLEAN: i = 0; break;
case T_CHAR : i = 1; break;
case T_BYTE : i = 2; break;
case T_SHORT : i = 3; break;
case T_INT : // fall through
case T_LONG : // fall through
case T_VOID : // fall through
case T_FLOAT : // fall through
case T_DOUBLE : i = 4; break;
case T_OBJECT : // fall through
case T_ARRAY : i = 5; break;
#else
case T_VOID : i = 0; break;
case T_BOOLEAN: i = 1; break;
case T_CHAR : i = 2; break;
case T_BYTE : i = 3; break;
case T_SHORT : i = 4; break;
case T_INT : i = 5; break;
case T_OBJECT : // fall through
case T_ARRAY : i = 6; break;
case T_LONG : i = 7; break;
case T_FLOAT : i = 8; break;
case T_DOUBLE : i = 9; break;
#endif // AARCH64
default : ShouldNotReachHere();
}
assert(0 <= i && i < AbstractInterpreter::number_of_result_handlers, "index out of bounds");
return i;
}
// These should never be compiled since the interpreter will prefer
// the compiled version to the intrinsic version.
bool AbstractInterpreter::can_be_compiled(methodHandle m) {
switch (method_kind(m)) {
case Interpreter::java_lang_math_sin : // fall thru
case Interpreter::java_lang_math_cos : // fall thru
case Interpreter::java_lang_math_tan : // fall thru
case Interpreter::java_lang_math_abs : // fall thru
case Interpreter::java_lang_math_log : // fall thru
case Interpreter::java_lang_math_log10 : // fall thru
case Interpreter::java_lang_math_sqrt :
return false;
default:
return true;
}
}
// How much stack a method activation needs in words.
int AbstractInterpreter::size_top_interpreter_activation(Method* method) {
const int stub_code = AARCH64_ONLY(24) NOT_AARCH64(12); // see generate_call_stub
// Save space for one monitor to get into the interpreted method in case
// the method is synchronized
int monitor_size = method->is_synchronized() ?
1*frame::interpreter_frame_monitor_size() : 0;
// total overhead size: monitor_size + (sender SP, thru expr stack bottom).
// be sure to change this if you add/subtract anything to/from the overhead area
const int overhead_size = monitor_size +
(frame::sender_sp_offset - frame::interpreter_frame_initial_sp_offset);
const int method_stack = (method->max_locals() + method->max_stack()) *
Interpreter::stackElementWords;
return overhead_size + method_stack + stub_code;
}
// asm based interpreter deoptimization helpers
int AbstractInterpreter::size_activation(int max_stack,
int tempcount,
int extra_args,
int moncount,
int callee_param_count,
int callee_locals,
bool is_top_frame) {
// Note: This calculation must exactly parallel the frame setup
// in TemplateInterpreterGenerator::generate_fixed_frame.
// fixed size of an interpreter frame:
int overhead = frame::sender_sp_offset - frame::interpreter_frame_initial_sp_offset;
// Our locals were accounted for by the caller (or last_frame_adjust on the transistion)
// Since the callee parameters already account for the callee's params we only need to account for
// the extra locals.
int size = overhead +
((callee_locals - callee_param_count)*Interpreter::stackElementWords) +
(moncount*frame::interpreter_frame_monitor_size()) +
tempcount*Interpreter::stackElementWords + extra_args;
#ifdef AARCH64
size = round_to(size, StackAlignmentInBytes/BytesPerWord);
#endif // AARCH64
return size;
}
void AbstractInterpreter::layout_activation(Method* method,
int tempcount,
int popframe_extra_args,
int moncount,
int caller_actual_parameters,
int callee_param_count,
int callee_locals,
frame* caller,
frame* interpreter_frame,
bool is_top_frame,
bool is_bottom_frame) {
// Set up the method, locals, and monitors.
// The frame interpreter_frame is guaranteed to be the right size,
// as determined by a previous call to the size_activation() method.
// It is also guaranteed to be walkable even though it is in a skeletal state
// NOTE: return size is in words not bytes
// fixed size of an interpreter frame:
int max_locals = method->max_locals() * Interpreter::stackElementWords;
int extra_locals = (method->max_locals() - method->size_of_parameters()) * Interpreter::stackElementWords;
#ifdef ASSERT
assert(caller->sp() == interpreter_frame->sender_sp(), "Frame not properly walkable");
#endif
interpreter_frame->interpreter_frame_set_method(method);
// NOTE the difference in using sender_sp and interpreter_frame_sender_sp
// interpreter_frame_sender_sp is the original sp of the caller (the unextended_sp)
// and sender_sp is (fp + sender_sp_offset*wordSize)
#ifdef AARCH64
intptr_t* locals;
if (caller->is_interpreted_frame()) {
// attach locals to the expression stack of caller interpreter frame
locals = caller->interpreter_frame_tos_address() + caller_actual_parameters*Interpreter::stackElementWords - 1;
} else {
assert (is_bottom_frame, "should be");
locals = interpreter_frame->fp() + frame::sender_sp_offset + method->max_locals() - 1;
}
if (TraceDeoptimization) {
tty->print_cr("layout_activation:");
if (caller->is_entry_frame()) {
tty->print("entry ");
}
if (caller->is_compiled_frame()) {
tty->print("compiled ");
}
if (caller->is_interpreted_frame()) {
tty->print("interpreted ");
}
tty->print_cr("caller: sp=%p, unextended_sp=%p, fp=%p, pc=%p", caller->sp(), caller->unextended_sp(), caller->fp(), caller->pc());
tty->print_cr("interpreter_frame: sp=%p, unextended_sp=%p, fp=%p, pc=%p", interpreter_frame->sp(), interpreter_frame->unextended_sp(), interpreter_frame->fp(), interpreter_frame->pc());
tty->print_cr("method: max_locals = %d, size_of_parameters = %d", method->max_locals(), method->size_of_parameters());
tty->print_cr("caller_actual_parameters = %d", caller_actual_parameters);
tty->print_cr("locals = %p", locals);
}
#ifdef ASSERT
if (caller_actual_parameters != method->size_of_parameters()) {
assert(caller->is_interpreted_frame(), "adjusted caller_actual_parameters, but caller is not interpreter frame");
Bytecode_invoke inv(caller->interpreter_frame_method(), caller->interpreter_frame_bci());
if (is_bottom_frame) {
assert(caller_actual_parameters == 0, "invalid adjusted caller_actual_parameters value for bottom frame");
assert(inv.is_invokedynamic() || inv.is_invokehandle(), "adjusted caller_actual_parameters for bottom frame, but not invokedynamic/invokehandle");
} else {
assert(caller_actual_parameters == method->size_of_parameters()+1, "invalid adjusted caller_actual_parameters value");
assert(!inv.is_invokedynamic() && MethodHandles::has_member_arg(inv.klass(), inv.name()), "adjusted caller_actual_parameters, but no member arg");
}
}
if (caller->is_interpreted_frame()) {
intptr_t* locals_base = (locals - method->max_locals()*Interpreter::stackElementWords + 1);
locals_base = (intptr_t*)round_down((intptr_t)locals_base, StackAlignmentInBytes);
assert(interpreter_frame->sender_sp() <= locals_base, "interpreter-to-interpreter frame chaining");
} else if (caller->is_compiled_frame()) {
assert(locals + 1 <= caller->unextended_sp(), "compiled-to-interpreter frame chaining");
} else {
assert(caller->is_entry_frame(), "should be");
assert(locals + 1 <= caller->fp(), "entry-to-interpreter frame chaining");
}
#endif // ASSERT
#else
intptr_t* locals = interpreter_frame->sender_sp() + max_locals - 1;
#endif // AARCH64
interpreter_frame->interpreter_frame_set_locals(locals);
BasicObjectLock* montop = interpreter_frame->interpreter_frame_monitor_begin();
BasicObjectLock* monbot = montop - moncount;
interpreter_frame->interpreter_frame_set_monitor_end(monbot);
// Set last_sp
intptr_t* stack_top = (intptr_t*) monbot -
tempcount*Interpreter::stackElementWords -
popframe_extra_args;
#ifdef AARCH64
interpreter_frame->interpreter_frame_set_stack_top(stack_top);
intptr_t* extended_sp = (intptr_t*) monbot -
(method->max_stack() + 1) * Interpreter::stackElementWords - // +1 is reserved slot for exception handler
popframe_extra_args;
extended_sp = (intptr_t*)round_down((intptr_t)extended_sp, StackAlignmentInBytes);
interpreter_frame->interpreter_frame_set_extended_sp(extended_sp);
#else
interpreter_frame->interpreter_frame_set_last_sp(stack_top);
#endif // AARCH64
// All frames but the initial (oldest) interpreter frame we fill in have a
// value for sender_sp that allows walking the stack but isn't
// truly correct. Correct the value here.
#ifdef AARCH64
if (caller->is_interpreted_frame()) {
intptr_t* sender_sp = (intptr_t*)round_down((intptr_t)caller->interpreter_frame_tos_address(), StackAlignmentInBytes);
interpreter_frame->set_interpreter_frame_sender_sp(sender_sp);
} else {
// in case of non-interpreter caller sender_sp of the oldest frame is already
// set to valid value
}
#else
if (extra_locals != 0 &&
interpreter_frame->sender_sp() == interpreter_frame->interpreter_frame_sender_sp() ) {
interpreter_frame->set_interpreter_frame_sender_sp(caller->sp() + extra_locals);
}
#endif // AARCH64
*interpreter_frame->interpreter_frame_cache_addr() =
method->constants()->cache();
*interpreter_frame->interpreter_frame_mirror_addr() =
method->method_holder()->java_mirror();
}

14428
hotspot/src/cpu/arm/vm/arm.ad Normal file

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,586 @@
//
// Copyright (c) 2008, 2013, 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
// under the terms of the GNU General Public License version 2 only, as
// published by the Free Software Foundation.
//
// This code is distributed in the hope that it will be useful, but WITHOUT
// ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
// FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
// version 2 for more details (a copy is included in the LICENSE file that
// accompanied this code).
//
// You should have received a copy of the GNU General Public License version
// 2 along with this work; if not, write to the Free Software Foundation,
// Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
//
// 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.
//
// ARM Architecture Description File
//----------REGISTER DEFINITION BLOCK------------------------------------------
// This information is used by the matcher and the register allocator to
// describe individual registers and classes of registers within the target
// archtecture.
register %{
//----------Architecture Description Register Definitions----------------------
// General Registers
// "reg_def" name ( register save type, C convention save type,
// ideal register type, encoding, vm name );
// Register Save Types:
//
// NS = No-Save: The register allocator assumes that these registers
// can be used without saving upon entry to the method, &
// that they do not need to be saved at call sites.
//
// SOC = Save-On-Call: The register allocator assumes that these registers
// can be used without saving upon entry to the method,
// but that they must be saved at call sites.
//
// SOE = Save-On-Entry: The register allocator assumes that these registers
// must be saved before using them upon entry to the
// method, but they do not need to be saved at call
// sites.
//
// AS = Always-Save: The register allocator assumes that these registers
// must be saved before using them upon entry to the
// method, & that they must be saved at call sites.
//
// Ideal Register Type is used to determine how to save & restore a
// register. Op_RegI will get spilled with LoadI/StoreI, Op_RegP will get
// spilled with LoadP/StoreP. If the register supports both, use Op_RegI.
//
// The encoding number is the actual bit-pattern placed into the opcodes.
// ----------------------------
// Integer/Long Registers
// ----------------------------
reg_def R_R0 (SOC, SOC, Op_RegI, 0, R(0)->as_VMReg());
reg_def R_R1 (SOC, SOC, Op_RegI, 1, R(1)->as_VMReg());
reg_def R_R2 (SOC, SOC, Op_RegI, 2, R(2)->as_VMReg());
reg_def R_R3 (SOC, SOC, Op_RegI, 3, R(3)->as_VMReg());
reg_def R_R4 (SOC, SOE, Op_RegI, 4, R(4)->as_VMReg());
reg_def R_R5 (SOC, SOE, Op_RegI, 5, R(5)->as_VMReg());
reg_def R_R6 (SOC, SOE, Op_RegI, 6, R(6)->as_VMReg());
reg_def R_R7 (SOC, SOE, Op_RegI, 7, R(7)->as_VMReg());
reg_def R_R8 (SOC, SOE, Op_RegI, 8, R(8)->as_VMReg());
reg_def R_R9 (SOC, SOE, Op_RegI, 9, R(9)->as_VMReg());
reg_def R_R10(NS, SOE, Op_RegI, 10, R(10)->as_VMReg());
reg_def R_R11(NS, SOE, Op_RegI, 11, R(11)->as_VMReg());
reg_def R_R12(SOC, SOC, Op_RegI, 12, R(12)->as_VMReg());
reg_def R_R13(NS, NS, Op_RegI, 13, R(13)->as_VMReg());
reg_def R_R14(SOC, SOC, Op_RegI, 14, R(14)->as_VMReg());
reg_def R_R15(NS, NS, Op_RegI, 15, R(15)->as_VMReg());
// ----------------------------
// Float/Double Registers
// ----------------------------
// Float Registers
reg_def R_S0 ( SOC, SOC, Op_RegF, 0, S0->as_VMReg());
reg_def R_S1 ( SOC, SOC, Op_RegF, 1, S1_reg->as_VMReg());
reg_def R_S2 ( SOC, SOC, Op_RegF, 2, S2_reg->as_VMReg());
reg_def R_S3 ( SOC, SOC, Op_RegF, 3, S3_reg->as_VMReg());
reg_def R_S4 ( SOC, SOC, Op_RegF, 4, S4_reg->as_VMReg());
reg_def R_S5 ( SOC, SOC, Op_RegF, 5, S5_reg->as_VMReg());
reg_def R_S6 ( SOC, SOC, Op_RegF, 6, S6_reg->as_VMReg());
reg_def R_S7 ( SOC, SOC, Op_RegF, 7, S7->as_VMReg());
reg_def R_S8 ( SOC, SOC, Op_RegF, 8, S8->as_VMReg());
reg_def R_S9 ( SOC, SOC, Op_RegF, 9, S9->as_VMReg());
reg_def R_S10( SOC, SOC, Op_RegF, 10,S10->as_VMReg());
reg_def R_S11( SOC, SOC, Op_RegF, 11,S11->as_VMReg());
reg_def R_S12( SOC, SOC, Op_RegF, 12,S12->as_VMReg());
reg_def R_S13( SOC, SOC, Op_RegF, 13,S13->as_VMReg());
reg_def R_S14( SOC, SOC, Op_RegF, 14,S14->as_VMReg());
reg_def R_S15( SOC, SOC, Op_RegF, 15,S15->as_VMReg());
reg_def R_S16( SOC, SOE, Op_RegF, 16,S16->as_VMReg());
reg_def R_S17( SOC, SOE, Op_RegF, 17,S17->as_VMReg());
reg_def R_S18( SOC, SOE, Op_RegF, 18,S18->as_VMReg());
reg_def R_S19( SOC, SOE, Op_RegF, 19,S19->as_VMReg());
reg_def R_S20( SOC, SOE, Op_RegF, 20,S20->as_VMReg());
reg_def R_S21( SOC, SOE, Op_RegF, 21,S21->as_VMReg());
reg_def R_S22( SOC, SOE, Op_RegF, 22,S22->as_VMReg());
reg_def R_S23( SOC, SOE, Op_RegF, 23,S23->as_VMReg());
reg_def R_S24( SOC, SOE, Op_RegF, 24,S24->as_VMReg());
reg_def R_S25( SOC, SOE, Op_RegF, 25,S25->as_VMReg());
reg_def R_S26( SOC, SOE, Op_RegF, 26,S26->as_VMReg());
reg_def R_S27( SOC, SOE, Op_RegF, 27,S27->as_VMReg());
reg_def R_S28( SOC, SOE, Op_RegF, 28,S28->as_VMReg());
reg_def R_S29( SOC, SOE, Op_RegF, 29,S29->as_VMReg());
reg_def R_S30( SOC, SOE, Op_RegF, 30,S30->as_VMReg());
reg_def R_S31( SOC, SOE, Op_RegF, 31,S31->as_VMReg());
// Double Registers
// The rules of ADL require that double registers be defined in pairs.
// Each pair must be two 32-bit values, but not necessarily a pair of
// single float registers. In each pair, ADLC-assigned register numbers
// must be adjacent, with the lower number even. Finally, when the
// CPU stores such a register pair to memory, the word associated with
// the lower ADLC-assigned number must be stored to the lower address.
reg_def R_D16 (SOC, SOC, Op_RegD, 32, D16->as_VMReg());
reg_def R_D16x(SOC, SOC, Op_RegD,255, D16->as_VMReg()->next());
reg_def R_D17 (SOC, SOC, Op_RegD, 34, D17->as_VMReg());
reg_def R_D17x(SOC, SOC, Op_RegD,255, D17->as_VMReg()->next());
reg_def R_D18 (SOC, SOC, Op_RegD, 36, D18->as_VMReg());
reg_def R_D18x(SOC, SOC, Op_RegD,255, D18->as_VMReg()->next());
reg_def R_D19 (SOC, SOC, Op_RegD, 38, D19->as_VMReg());
reg_def R_D19x(SOC, SOC, Op_RegD,255, D19->as_VMReg()->next());
reg_def R_D20 (SOC, SOC, Op_RegD, 40, D20->as_VMReg());
reg_def R_D20x(SOC, SOC, Op_RegD,255, D20->as_VMReg()->next());
reg_def R_D21 (SOC, SOC, Op_RegD, 42, D21->as_VMReg());
reg_def R_D21x(SOC, SOC, Op_RegD,255, D21->as_VMReg()->next());
reg_def R_D22 (SOC, SOC, Op_RegD, 44, D22->as_VMReg());
reg_def R_D22x(SOC, SOC, Op_RegD,255, D22->as_VMReg()->next());
reg_def R_D23 (SOC, SOC, Op_RegD, 46, D23->as_VMReg());
reg_def R_D23x(SOC, SOC, Op_RegD,255, D23->as_VMReg()->next());
reg_def R_D24 (SOC, SOC, Op_RegD, 48, D24->as_VMReg());
reg_def R_D24x(SOC, SOC, Op_RegD,255, D24->as_VMReg()->next());
reg_def R_D25 (SOC, SOC, Op_RegD, 50, D25->as_VMReg());
reg_def R_D25x(SOC, SOC, Op_RegD,255, D25->as_VMReg()->next());
reg_def R_D26 (SOC, SOC, Op_RegD, 52, D26->as_VMReg());
reg_def R_D26x(SOC, SOC, Op_RegD,255, D26->as_VMReg()->next());
reg_def R_D27 (SOC, SOC, Op_RegD, 54, D27->as_VMReg());
reg_def R_D27x(SOC, SOC, Op_RegD,255, D27->as_VMReg()->next());
reg_def R_D28 (SOC, SOC, Op_RegD, 56, D28->as_VMReg());
reg_def R_D28x(SOC, SOC, Op_RegD,255, D28->as_VMReg()->next());
reg_def R_D29 (SOC, SOC, Op_RegD, 58, D29->as_VMReg());
reg_def R_D29x(SOC, SOC, Op_RegD,255, D29->as_VMReg()->next());
reg_def R_D30 (SOC, SOC, Op_RegD, 60, D30->as_VMReg());
reg_def R_D30x(SOC, SOC, Op_RegD,255, D30->as_VMReg()->next());
reg_def R_D31 (SOC, SOC, Op_RegD, 62, D31->as_VMReg());
reg_def R_D31x(SOC, SOC, Op_RegD,255, D31->as_VMReg()->next());
// ----------------------------
// Special Registers
// Condition Codes Flag Registers
reg_def APSR (SOC, SOC, Op_RegFlags, 0, VMRegImpl::Bad());
reg_def FPSCR(SOC, SOC, Op_RegFlags, 0, VMRegImpl::Bad());
// ----------------------------
// Specify the enum values for the registers. These enums are only used by the
// OptoReg "class". We can convert these enum values at will to VMReg when needed
// for visibility to the rest of the vm. The order of this enum influences the
// register allocator so having the freedom to set this order and not be stuck
// with the order that is natural for the rest of the vm is worth it.
// registers in that order so that R11/R12 is an aligned pair that can be used for longs
alloc_class chunk0(
R_R4, R_R5, R_R6, R_R7, R_R8, R_R9, R_R11, R_R12, R_R10, R_R13, R_R14, R_R15, R_R0, R_R1, R_R2, R_R3);
// Note that a register is not allocatable unless it is also mentioned
// in a widely-used reg_class below.
alloc_class chunk1(
R_S16, R_S17, R_S18, R_S19, R_S20, R_S21, R_S22, R_S23,
R_S24, R_S25, R_S26, R_S27, R_S28, R_S29, R_S30, R_S31,
R_S0, R_S1, R_S2, R_S3, R_S4, R_S5, R_S6, R_S7,
R_S8, R_S9, R_S10, R_S11, R_S12, R_S13, R_S14, R_S15,
R_D16, R_D16x,R_D17, R_D17x,R_D18, R_D18x,R_D19, R_D19x,
R_D20, R_D20x,R_D21, R_D21x,R_D22, R_D22x,R_D23, R_D23x,
R_D24, R_D24x,R_D25, R_D25x,R_D26, R_D26x,R_D27, R_D27x,
R_D28, R_D28x,R_D29, R_D29x,R_D30, R_D30x,R_D31, R_D31x
);
alloc_class chunk2(APSR, FPSCR);
//----------Architecture Description Register Classes--------------------------
// Several register classes are automatically defined based upon information in
// this architecture description.
// 1) reg_class inline_cache_reg ( as defined in frame section )
// 2) reg_class interpreter_method_oop_reg ( as defined in frame section )
// 3) reg_class stack_slots( /* one chunk of stack-based "registers" */ )
//
// ----------------------------
// Integer Register Classes
// ----------------------------
// Exclusions from i_reg:
// SP (R13), PC (R15)
// R10: reserved by HotSpot to the TLS register (invariant within Java)
reg_class int_reg(R_R0, R_R1, R_R2, R_R3, R_R4, R_R5, R_R6, R_R7, R_R8, R_R9, R_R11, R_R12, R_R14);
reg_class R0_regI(R_R0);
reg_class R1_regI(R_R1);
reg_class R2_regI(R_R2);
reg_class R3_regI(R_R3);
reg_class R12_regI(R_R12);
// ----------------------------
// Pointer Register Classes
// ----------------------------
reg_class ptr_reg(R_R0, R_R1, R_R2, R_R3, R_R4, R_R5, R_R6, R_R7, R_R8, R_R9, R_R11, R_R12, R_R14);
// Special class for storeP instructions, which can store SP or RPC to TLS.
// It is also used for memory addressing, allowing direct TLS addressing.
reg_class sp_ptr_reg(R_R0, R_R1, R_R2, R_R3, R_R4, R_R5, R_R6, R_R7, R_R8, R_R9, R_R11, R_R12, R_R14, R_R10 /* TLS*/, R_R13 /* SP*/);
#define R_Ricklass R_R8
#define R_Rmethod R_R9
#define R_Rthread R_R10
#define R_Rexception_obj R_R4
// Other special pointer regs
reg_class R0_regP(R_R0);
reg_class R1_regP(R_R1);
reg_class R2_regP(R_R2);
reg_class R4_regP(R_R4);
reg_class Rexception_regP(R_Rexception_obj);
reg_class Ricklass_regP(R_Ricklass);
reg_class Rmethod_regP(R_Rmethod);
reg_class Rthread_regP(R_Rthread);
reg_class IP_regP(R_R12);
reg_class LR_regP(R_R14);
reg_class FP_regP(R_R11);
// ----------------------------
// Long Register Classes
// ----------------------------
reg_class long_reg ( R_R0,R_R1, R_R2,R_R3, R_R4,R_R5, R_R6,R_R7, R_R8,R_R9, R_R11,R_R12);
// for ldrexd, strexd: first reg of pair must be even
reg_class long_reg_align ( R_R0,R_R1, R_R2,R_R3, R_R4,R_R5, R_R6,R_R7, R_R8,R_R9);
reg_class R0R1_regL(R_R0,R_R1);
reg_class R2R3_regL(R_R2,R_R3);
// ----------------------------
// Special Class for Condition Code Flags Register
reg_class int_flags(APSR);
reg_class float_flags(FPSCR);
// ----------------------------
// Float Point Register Classes
// ----------------------------
// Skip S14/S15, they are reserved for mem-mem copies
reg_class sflt_reg(R_S0, R_S1, R_S2, R_S3, R_S4, R_S5, R_S6, R_S7, R_S8, R_S9, R_S10, R_S11, R_S12, R_S13,
R_S16, R_S17, R_S18, R_S19, R_S20, R_S21, R_S22, R_S23, R_S24, R_S25, R_S26, R_S27, R_S28, R_S29, R_S30, R_S31);
// Paired floating point registers--they show up in the same order as the floats,
// but they are used with the "Op_RegD" type, and always occur in even/odd pairs.
reg_class dflt_reg(R_S0,R_S1, R_S2,R_S3, R_S4,R_S5, R_S6,R_S7, R_S8,R_S9, R_S10,R_S11, R_S12,R_S13,
R_S16,R_S17, R_S18,R_S19, R_S20,R_S21, R_S22,R_S23, R_S24,R_S25, R_S26,R_S27, R_S28,R_S29, R_S30,R_S31,
R_D16,R_D16x, R_D17,R_D17x, R_D18,R_D18x, R_D19,R_D19x, R_D20,R_D20x, R_D21,R_D21x, R_D22,R_D22x,
R_D23,R_D23x, R_D24,R_D24x, R_D25,R_D25x, R_D26,R_D26x, R_D27,R_D27x, R_D28,R_D28x, R_D29,R_D29x,
R_D30,R_D30x, R_D31,R_D31x);
reg_class dflt_low_reg(R_S0,R_S1, R_S2,R_S3, R_S4,R_S5, R_S6,R_S7, R_S8,R_S9, R_S10,R_S11, R_S12,R_S13,
R_S16,R_S17, R_S18,R_S19, R_S20,R_S21, R_S22,R_S23, R_S24,R_S25, R_S26,R_S27, R_S28,R_S29, R_S30,R_S31);
reg_class actual_dflt_reg %{
if (VM_Version::has_vfp3_32()) {
return DFLT_REG_mask();
} else {
return DFLT_LOW_REG_mask();
}
%}
reg_class S0_regF(R_S0);
reg_class D0_regD(R_S0,R_S1);
reg_class D1_regD(R_S2,R_S3);
reg_class D2_regD(R_S4,R_S5);
reg_class D3_regD(R_S6,R_S7);
reg_class D4_regD(R_S8,R_S9);
reg_class D5_regD(R_S10,R_S11);
reg_class D6_regD(R_S12,R_S13);
reg_class D7_regD(R_S14,R_S15);
reg_class D16_regD(R_D16,R_D16x);
reg_class D17_regD(R_D17,R_D17x);
reg_class D18_regD(R_D18,R_D18x);
reg_class D19_regD(R_D19,R_D19x);
reg_class D20_regD(R_D20,R_D20x);
reg_class D21_regD(R_D21,R_D21x);
reg_class D22_regD(R_D22,R_D22x);
reg_class D23_regD(R_D23,R_D23x);
reg_class D24_regD(R_D24,R_D24x);
reg_class D25_regD(R_D25,R_D25x);
reg_class D26_regD(R_D26,R_D26x);
reg_class D27_regD(R_D27,R_D27x);
reg_class D28_regD(R_D28,R_D28x);
reg_class D29_regD(R_D29,R_D29x);
reg_class D30_regD(R_D30,R_D30x);
reg_class D31_regD(R_D31,R_D31x);
reg_class vectorx_reg(R_S0,R_S1,R_S2,R_S3, R_S4,R_S5,R_S6,R_S7,
R_S8,R_S9,R_S10,R_S11, /* skip S14/S15 */
R_S16,R_S17,R_S18,R_S19, R_S20,R_S21,R_S22,R_S23,
R_S24,R_S25,R_S26,R_S27, R_S28,R_S29,R_S30,R_S31,
R_D16,R_D16x,R_D17,R_D17x, R_D18,R_D18x,R_D19,R_D19x,
R_D20,R_D20x,R_D21,R_D21x, R_D22,R_D22x,R_D23,R_D23x,
R_D24,R_D24x,R_D25,R_D25x, R_D26,R_D26x,R_D27,R_D27x,
R_D28,R_D28x,R_D29,R_D29x, R_D30,R_D30x,R_D31,R_D31x);
%}
source_hpp %{
// FIXME
const MachRegisterNumbers R_mem_copy_lo_num = R_S14_num;
const MachRegisterNumbers R_mem_copy_hi_num = R_S15_num;
const FloatRegister Rmemcopy = S14;
const MachRegisterNumbers R_hf_ret_lo_num = R_S0_num;
const MachRegisterNumbers R_hf_ret_hi_num = R_S1_num;
const MachRegisterNumbers R_Ricklass_num = R_R8_num;
const MachRegisterNumbers R_Rmethod_num = R_R9_num;
#define LDR_DOUBLE "FLDD"
#define LDR_FLOAT "FLDS"
#define STR_DOUBLE "FSTD"
#define STR_FLOAT "FSTS"
#define LDR_64 "LDRD"
#define STR_64 "STRD"
#define LDR_32 "LDR"
#define STR_32 "STR"
#define MOV_DOUBLE "FCPYD"
#define MOV_FLOAT "FCPYS"
#define FMSR "FMSR"
#define FMRS "FMRS"
#define LDREX "ldrex "
#define STREX "strex "
#define str_64 strd
#define ldr_64 ldrd
#define ldr_32 ldr
#define ldrex ldrex
#define strex strex
static inline bool is_memoryD(int offset) {
return offset < 1024 && offset > -1024;
}
static inline bool is_memoryfp(int offset) {
return offset < 1024 && offset > -1024;
}
static inline bool is_memoryI(int offset) {
return offset < 4096 && offset > -4096;
}
static inline bool is_memoryP(int offset) {
return offset < 4096 && offset > -4096;
}
static inline bool is_memoryHD(int offset) {
return offset < 256 && offset > -256;
}
static inline bool is_aimm(int imm) {
return AsmOperand::is_rotated_imm(imm);
}
static inline bool is_limmI(jint imm) {
return AsmOperand::is_rotated_imm(imm);
}
static inline bool is_limmI_low(jint imm, int n) {
int imml = imm & right_n_bits(n);
return is_limmI(imml) || is_limmI(imm);
}
static inline int limmI_low(jint imm, int n) {
int imml = imm & right_n_bits(n);
return is_limmI(imml) ? imml : imm;
}
%}
source %{
// Given a register encoding, produce a Integer Register object
static Register reg_to_register_object(int register_encoding) {
assert(R0->encoding() == R_R0_enc && R15->encoding() == R_R15_enc, "right coding");
return as_Register(register_encoding);
}
// Given a register encoding, produce a single-precision Float Register object
static FloatRegister reg_to_FloatRegister_object(int register_encoding) {
assert(S0->encoding() == R_S0_enc && S31->encoding() == R_S31_enc, "right coding");
return as_FloatRegister(register_encoding);
}
void Compile::pd_compiler2_init() {
// Umimplemented
}
// Location of compiled Java return values. Same as C
OptoRegPair c2::return_value(int ideal_reg) {
assert( ideal_reg >= Op_RegI && ideal_reg <= Op_RegL, "only return normal values" );
#ifndef __ABI_HARD__
static int lo[Op_RegL+1] = { 0, 0, OptoReg::Bad, R_R0_num, R_R0_num, R_R0_num, R_R0_num, R_R0_num };
static int hi[Op_RegL+1] = { 0, 0, OptoReg::Bad, OptoReg::Bad, OptoReg::Bad, OptoReg::Bad, R_R1_num, R_R1_num };
#else
static int lo[Op_RegL+1] = { 0, 0, OptoReg::Bad, R_R0_num, R_R0_num, R_hf_ret_lo_num, R_hf_ret_lo_num, R_R0_num };
static int hi[Op_RegL+1] = { 0, 0, OptoReg::Bad, OptoReg::Bad, OptoReg::Bad, OptoReg::Bad, R_hf_ret_hi_num, R_R1_num };
#endif
return OptoRegPair( hi[ideal_reg], lo[ideal_reg]);
}
// !!!!! Special hack to get all type of calls to specify the byte offset
// from the start of the call to the point where the return address
// will point.
int MachCallStaticJavaNode::ret_addr_offset() {
bool far = (_method == NULL) ? maybe_far_call(this) : !cache_reachable();
return ((far ? 3 : 1) + (_method_handle_invoke ? 1 : 0)) *
NativeInstruction::instruction_size;
}
int MachCallDynamicJavaNode::ret_addr_offset() {
bool far = !cache_reachable();
// mov_oop is always 2 words
return (2 + (far ? 3 : 1)) * NativeInstruction::instruction_size;
}
int MachCallRuntimeNode::ret_addr_offset() {
// bl or movw; movt; blx
bool far = maybe_far_call(this);
return (far ? 3 : 1) * NativeInstruction::instruction_size;
}
%}
// The intptr_t operand types, defined by textual substitution.
// (Cf. opto/type.hpp. This lets us avoid many, many other ifdefs.)
#define immX immI
#define immXRot immIRot
#define iRegX iRegI
#define aimmX aimmI
#define limmX limmI
#define immX10x2 immI10x2
#define LShiftX LShiftI
#define shimmX immU5
// Compatibility interface
#define aimmP immPRot
#define immIMov immIRot
#define store_RegL iRegL
#define store_RegLd iRegLd
#define store_RegI iRegI
#define store_ptr_RegP iRegP
//----------ATTRIBUTES---------------------------------------------------------
//----------Operand Attributes-------------------------------------------------
op_attrib op_cost(1); // Required cost attribute
//----------OPERANDS-----------------------------------------------------------
// Operand definitions must precede instruction definitions for correct parsing
// in the ADLC because operands constitute user defined types which are used in
// instruction definitions.
//----------Simple Operands----------------------------------------------------
// Immediate Operands
operand immIRot() %{
predicate(AsmOperand::is_rotated_imm(n->get_int()));
match(ConI);
op_cost(0);
// formats are generated automatically for constants and base registers
format %{ %}
interface(CONST_INTER);
%}
operand immIRotn() %{
predicate(n->get_int() != 0 && AsmOperand::is_rotated_imm(~n->get_int()));
match(ConI);
op_cost(0);
// formats are generated automatically for constants and base registers
format %{ %}
interface(CONST_INTER);
%}
operand immIRotneg() %{
// if AsmOperand::is_rotated_imm() is true for this constant, it is
// a immIRot and an optimal instruction combination exists to handle the
// constant as an immIRot
predicate(!AsmOperand::is_rotated_imm(n->get_int()) && AsmOperand::is_rotated_imm(-n->get_int()));
match(ConI);
op_cost(0);
// formats are generated automatically for constants and base registers
format %{ %}
interface(CONST_INTER);
%}
// Non-negative integer immediate that is encodable using the rotation scheme,
// and that when expanded fits in 31 bits.
operand immU31Rot() %{
predicate((0 <= n->get_int()) && AsmOperand::is_rotated_imm(n->get_int()));
match(ConI);
op_cost(0);
// formats are generated automatically for constants and base registers
format %{ %}
interface(CONST_INTER);
%}
operand immPRot() %{
predicate(n->get_ptr() == 0 || (AsmOperand::is_rotated_imm(n->get_ptr()) && ((ConPNode*)n)->type()->reloc() == relocInfo::none));
match(ConP);
op_cost(0);
// formats are generated automatically for constants and base registers
format %{ %}
interface(CONST_INTER);
%}
operand immLlowRot() %{
predicate(n->get_long() >> 32 == 0 && AsmOperand::is_rotated_imm((int)n->get_long()));
match(ConL);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
operand immLRot2() %{
predicate(AsmOperand::is_rotated_imm((int)(n->get_long() >> 32)) &&
AsmOperand::is_rotated_imm((int)(n->get_long())));
match(ConL);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
// Integer Immediate: 12-bit - for addressing mode
operand immI12() %{
predicate((-4096 < n->get_int()) && (n->get_int() < 4096));
match(ConI);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
// Integer Immediate: 10-bit disp and disp+4 - for addressing float pair
operand immI10x2() %{
predicate((-1024 < n->get_int()) && (n->get_int() < 1024 - 4));
match(ConI);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
// Integer Immediate: 12-bit disp and disp+4 - for addressing word pair
operand immI12x2() %{
predicate((-4096 < n->get_int()) && (n->get_int() < 4096 - 4));
match(ConI);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}

View File

@ -0,0 +1,998 @@
//
// Copyright (c) 2008, 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
// under the terms of the GNU General Public License version 2 only, as
// published by the Free Software Foundation.
//
// This code is distributed in the hope that it will be useful, but WITHOUT
// ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
// FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
// version 2 for more details (a copy is included in the LICENSE file that
// accompanied this code).
//
// You should have received a copy of the GNU General Public License version
// 2 along with this work; if not, write to the Free Software Foundation,
// Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
//
// 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.
//
// ARM Architecture Description File
//----------REGISTER DEFINITION BLOCK------------------------------------------
// This information is used by the matcher and the register allocator to
// describe individual registers and classes of registers within the target
// archtecture.
register %{
//----------Architecture Description Register Definitions----------------------
// General Registers
// "reg_def" name ( register save type, C convention save type,
// ideal register type, encoding, vm name );
// Register Save Types:
//
// NS = No-Save: The register allocator assumes that these registers
// can be used without saving upon entry to the method, &
// that they do not need to be saved at call sites.
//
// SOC = Save-On-Call: The register allocator assumes that these registers
// can be used without saving upon entry to the method,
// but that they must be saved at call sites.
//
// SOE = Save-On-Entry: The register allocator assumes that these registers
// must be saved before using them upon entry to the
// method, but they do not need to be saved at call
// sites.
//
// AS = Always-Save: The register allocator assumes that these registers
// must be saved before using them upon entry to the
// method, & that they must be saved at call sites.
//
// Ideal Register Type is used to determine how to save & restore a
// register. Op_RegI will get spilled with LoadI/StoreI, Op_RegP will get
// spilled with LoadP/StoreP. If the register supports both, use Op_RegI.
// FIXME: above comment seems wrong. Spill done through MachSpillCopyNode
//
// The encoding number is the actual bit-pattern placed into the opcodes.
// ----------------------------
// Integer/Long Registers
// ----------------------------
// TODO: would be nice to keep track of high-word state:
// zeroRegI --> RegL
// signedRegI --> RegL
// junkRegI --> RegL
// how to tell C2 to treak RegI as RegL, or RegL as RegI?
reg_def R_R0 (SOC, SOC, Op_RegI, 0, R0->as_VMReg());
reg_def R_R0x (SOC, SOC, Op_RegI, 255, R0->as_VMReg()->next());
reg_def R_R1 (SOC, SOC, Op_RegI, 1, R1->as_VMReg());
reg_def R_R1x (SOC, SOC, Op_RegI, 255, R1->as_VMReg()->next());
reg_def R_R2 (SOC, SOC, Op_RegI, 2, R2->as_VMReg());
reg_def R_R2x (SOC, SOC, Op_RegI, 255, R2->as_VMReg()->next());
reg_def R_R3 (SOC, SOC, Op_RegI, 3, R3->as_VMReg());
reg_def R_R3x (SOC, SOC, Op_RegI, 255, R3->as_VMReg()->next());
reg_def R_R4 (SOC, SOC, Op_RegI, 4, R4->as_VMReg());
reg_def R_R4x (SOC, SOC, Op_RegI, 255, R4->as_VMReg()->next());
reg_def R_R5 (SOC, SOC, Op_RegI, 5, R5->as_VMReg());
reg_def R_R5x (SOC, SOC, Op_RegI, 255, R5->as_VMReg()->next());
reg_def R_R6 (SOC, SOC, Op_RegI, 6, R6->as_VMReg());
reg_def R_R6x (SOC, SOC, Op_RegI, 255, R6->as_VMReg()->next());
reg_def R_R7 (SOC, SOC, Op_RegI, 7, R7->as_VMReg());
reg_def R_R7x (SOC, SOC, Op_RegI, 255, R7->as_VMReg()->next());
reg_def R_R8 (SOC, SOC, Op_RegI, 8, R8->as_VMReg());
reg_def R_R8x (SOC, SOC, Op_RegI, 255, R8->as_VMReg()->next());
reg_def R_R9 (SOC, SOC, Op_RegI, 9, R9->as_VMReg());
reg_def R_R9x (SOC, SOC, Op_RegI, 255, R9->as_VMReg()->next());
reg_def R_R10 (SOC, SOC, Op_RegI, 10, R10->as_VMReg());
reg_def R_R10x(SOC, SOC, Op_RegI, 255, R10->as_VMReg()->next());
reg_def R_R11 (SOC, SOC, Op_RegI, 11, R11->as_VMReg());
reg_def R_R11x(SOC, SOC, Op_RegI, 255, R11->as_VMReg()->next());
reg_def R_R12 (SOC, SOC, Op_RegI, 12, R12->as_VMReg());
reg_def R_R12x(SOC, SOC, Op_RegI, 255, R12->as_VMReg()->next());
reg_def R_R13 (SOC, SOC, Op_RegI, 13, R13->as_VMReg());
reg_def R_R13x(SOC, SOC, Op_RegI, 255, R13->as_VMReg()->next());
reg_def R_R14 (SOC, SOC, Op_RegI, 14, R14->as_VMReg());
reg_def R_R14x(SOC, SOC, Op_RegI, 255, R14->as_VMReg()->next());
reg_def R_R15 (SOC, SOC, Op_RegI, 15, R15->as_VMReg());
reg_def R_R15x(SOC, SOC, Op_RegI, 255, R15->as_VMReg()->next());
reg_def R_R16 (SOC, SOC, Op_RegI, 16, R16->as_VMReg()); // IP0
reg_def R_R16x(SOC, SOC, Op_RegI, 255, R16->as_VMReg()->next());
reg_def R_R17 (SOC, SOC, Op_RegI, 17, R17->as_VMReg()); // IP1
reg_def R_R17x(SOC, SOC, Op_RegI, 255, R17->as_VMReg()->next());
reg_def R_R18 (SOC, SOC, Op_RegI, 18, R18->as_VMReg()); // Platform Register
reg_def R_R18x(SOC, SOC, Op_RegI, 255, R18->as_VMReg()->next());
reg_def R_R19 (SOC, SOE, Op_RegI, 19, R19->as_VMReg());
reg_def R_R19x(SOC, SOE, Op_RegI, 255, R19->as_VMReg()->next());
reg_def R_R20 (SOC, SOE, Op_RegI, 20, R20->as_VMReg());
reg_def R_R20x(SOC, SOE, Op_RegI, 255, R20->as_VMReg()->next());
reg_def R_R21 (SOC, SOE, Op_RegI, 21, R21->as_VMReg());
reg_def R_R21x(SOC, SOE, Op_RegI, 255, R21->as_VMReg()->next());
reg_def R_R22 (SOC, SOE, Op_RegI, 22, R22->as_VMReg());
reg_def R_R22x(SOC, SOE, Op_RegI, 255, R22->as_VMReg()->next());
reg_def R_R23 (SOC, SOE, Op_RegI, 23, R23->as_VMReg());
reg_def R_R23x(SOC, SOE, Op_RegI, 255, R23->as_VMReg()->next());
reg_def R_R24 (SOC, SOE, Op_RegI, 24, R24->as_VMReg());
reg_def R_R24x(SOC, SOE, Op_RegI, 255, R24->as_VMReg()->next());
reg_def R_R25 (SOC, SOE, Op_RegI, 25, R25->as_VMReg());
reg_def R_R25x(SOC, SOE, Op_RegI, 255, R25->as_VMReg()->next());
reg_def R_R26 (SOC, SOE, Op_RegI, 26, R26->as_VMReg());
reg_def R_R26x(SOC, SOE, Op_RegI, 255, R26->as_VMReg()->next());
reg_def R_R27 (SOC, SOE, Op_RegI, 27, R27->as_VMReg()); // Rheap_base
reg_def R_R27x(SOC, SOE, Op_RegI, 255, R27->as_VMReg()->next()); // Rheap_base
reg_def R_R28 ( NS, SOE, Op_RegI, 28, R28->as_VMReg()); // TLS
reg_def R_R28x( NS, SOE, Op_RegI, 255, R28->as_VMReg()->next()); // TLS
reg_def R_R29 ( NS, SOE, Op_RegI, 29, R29->as_VMReg()); // FP
reg_def R_R29x( NS, SOE, Op_RegI, 255, R29->as_VMReg()->next()); // FP
reg_def R_R30 (SOC, SOC, Op_RegI, 30, R30->as_VMReg()); // LR
reg_def R_R30x(SOC, SOC, Op_RegI, 255, R30->as_VMReg()->next()); // LR
reg_def R_ZR ( NS, NS, Op_RegI, 31, ZR->as_VMReg()); // ZR
reg_def R_ZRx( NS, NS, Op_RegI, 255, ZR->as_VMReg()->next()); // ZR
// FIXME
//reg_def R_SP ( NS, NS, Op_RegP, 32, SP->as_VMReg());
reg_def R_SP ( NS, NS, Op_RegI, 32, SP->as_VMReg());
//reg_def R_SPx( NS, NS, Op_RegP, 255, SP->as_VMReg()->next());
reg_def R_SPx( NS, NS, Op_RegI, 255, SP->as_VMReg()->next());
// ----------------------------
// Float/Double/Vector Registers
// ----------------------------
reg_def R_V0(SOC, SOC, Op_RegF, 0, V0->as_VMReg());
reg_def R_V1(SOC, SOC, Op_RegF, 1, V1->as_VMReg());
reg_def R_V2(SOC, SOC, Op_RegF, 2, V2->as_VMReg());
reg_def R_V3(SOC, SOC, Op_RegF, 3, V3->as_VMReg());
reg_def R_V4(SOC, SOC, Op_RegF, 4, V4->as_VMReg());
reg_def R_V5(SOC, SOC, Op_RegF, 5, V5->as_VMReg());
reg_def R_V6(SOC, SOC, Op_RegF, 6, V6->as_VMReg());
reg_def R_V7(SOC, SOC, Op_RegF, 7, V7->as_VMReg());
reg_def R_V8(SOC, SOC, Op_RegF, 8, V8->as_VMReg());
reg_def R_V9(SOC, SOC, Op_RegF, 9, V9->as_VMReg());
reg_def R_V10(SOC, SOC, Op_RegF, 10, V10->as_VMReg());
reg_def R_V11(SOC, SOC, Op_RegF, 11, V11->as_VMReg());
reg_def R_V12(SOC, SOC, Op_RegF, 12, V12->as_VMReg());
reg_def R_V13(SOC, SOC, Op_RegF, 13, V13->as_VMReg());
reg_def R_V14(SOC, SOC, Op_RegF, 14, V14->as_VMReg());
reg_def R_V15(SOC, SOC, Op_RegF, 15, V15->as_VMReg());
reg_def R_V16(SOC, SOC, Op_RegF, 16, V16->as_VMReg());
reg_def R_V17(SOC, SOC, Op_RegF, 17, V17->as_VMReg());
reg_def R_V18(SOC, SOC, Op_RegF, 18, V18->as_VMReg());
reg_def R_V19(SOC, SOC, Op_RegF, 19, V19->as_VMReg());
reg_def R_V20(SOC, SOC, Op_RegF, 20, V20->as_VMReg());
reg_def R_V21(SOC, SOC, Op_RegF, 21, V21->as_VMReg());
reg_def R_V22(SOC, SOC, Op_RegF, 22, V22->as_VMReg());
reg_def R_V23(SOC, SOC, Op_RegF, 23, V23->as_VMReg());
reg_def R_V24(SOC, SOC, Op_RegF, 24, V24->as_VMReg());
reg_def R_V25(SOC, SOC, Op_RegF, 25, V25->as_VMReg());
reg_def R_V26(SOC, SOC, Op_RegF, 26, V26->as_VMReg());
reg_def R_V27(SOC, SOC, Op_RegF, 27, V27->as_VMReg());
reg_def R_V28(SOC, SOC, Op_RegF, 28, V28->as_VMReg());
reg_def R_V29(SOC, SOC, Op_RegF, 29, V29->as_VMReg());
reg_def R_V30(SOC, SOC, Op_RegF, 30, V30->as_VMReg());
reg_def R_V31(SOC, SOC, Op_RegF, 31, V31->as_VMReg());
reg_def R_V0b(SOC, SOC, Op_RegF, 255, V0->as_VMReg()->next(1));
reg_def R_V1b(SOC, SOC, Op_RegF, 255, V1->as_VMReg()->next(1));
reg_def R_V2b(SOC, SOC, Op_RegF, 255, V2->as_VMReg()->next(1));
reg_def R_V3b(SOC, SOC, Op_RegF, 3, V3->as_VMReg()->next(1));
reg_def R_V4b(SOC, SOC, Op_RegF, 4, V4->as_VMReg()->next(1));
reg_def R_V5b(SOC, SOC, Op_RegF, 5, V5->as_VMReg()->next(1));
reg_def R_V6b(SOC, SOC, Op_RegF, 6, V6->as_VMReg()->next(1));
reg_def R_V7b(SOC, SOC, Op_RegF, 7, V7->as_VMReg()->next(1));
reg_def R_V8b(SOC, SOC, Op_RegF, 255, V8->as_VMReg()->next(1));
reg_def R_V9b(SOC, SOC, Op_RegF, 9, V9->as_VMReg()->next(1));
reg_def R_V10b(SOC, SOC, Op_RegF, 10, V10->as_VMReg()->next(1));
reg_def R_V11b(SOC, SOC, Op_RegF, 11, V11->as_VMReg()->next(1));
reg_def R_V12b(SOC, SOC, Op_RegF, 12, V12->as_VMReg()->next(1));
reg_def R_V13b(SOC, SOC, Op_RegF, 13, V13->as_VMReg()->next(1));
reg_def R_V14b(SOC, SOC, Op_RegF, 14, V14->as_VMReg()->next(1));
reg_def R_V15b(SOC, SOC, Op_RegF, 15, V15->as_VMReg()->next(1));
reg_def R_V16b(SOC, SOC, Op_RegF, 16, V16->as_VMReg()->next(1));
reg_def R_V17b(SOC, SOC, Op_RegF, 17, V17->as_VMReg()->next(1));
reg_def R_V18b(SOC, SOC, Op_RegF, 18, V18->as_VMReg()->next(1));
reg_def R_V19b(SOC, SOC, Op_RegF, 19, V19->as_VMReg()->next(1));
reg_def R_V20b(SOC, SOC, Op_RegF, 20, V20->as_VMReg()->next(1));
reg_def R_V21b(SOC, SOC, Op_RegF, 21, V21->as_VMReg()->next(1));
reg_def R_V22b(SOC, SOC, Op_RegF, 22, V22->as_VMReg()->next(1));
reg_def R_V23b(SOC, SOC, Op_RegF, 23, V23->as_VMReg()->next(1));
reg_def R_V24b(SOC, SOC, Op_RegF, 24, V24->as_VMReg()->next(1));
reg_def R_V25b(SOC, SOC, Op_RegF, 25, V25->as_VMReg()->next(1));
reg_def R_V26b(SOC, SOC, Op_RegF, 26, V26->as_VMReg()->next(1));
reg_def R_V27b(SOC, SOC, Op_RegF, 27, V27->as_VMReg()->next(1));
reg_def R_V28b(SOC, SOC, Op_RegF, 28, V28->as_VMReg()->next(1));
reg_def R_V29b(SOC, SOC, Op_RegF, 29, V29->as_VMReg()->next(1));
reg_def R_V30b(SOC, SOC, Op_RegD, 30, V30->as_VMReg()->next(1));
reg_def R_V31b(SOC, SOC, Op_RegF, 31, V31->as_VMReg()->next(1));
reg_def R_V0c(SOC, SOC, Op_RegF, 0, V0->as_VMReg()->next(2));
reg_def R_V1c(SOC, SOC, Op_RegF, 1, V1->as_VMReg()->next(2));
reg_def R_V2c(SOC, SOC, Op_RegF, 2, V2->as_VMReg()->next(2));
reg_def R_V3c(SOC, SOC, Op_RegF, 3, V3->as_VMReg()->next(2));
reg_def R_V4c(SOC, SOC, Op_RegF, 4, V4->as_VMReg()->next(2));
reg_def R_V5c(SOC, SOC, Op_RegF, 5, V5->as_VMReg()->next(2));
reg_def R_V6c(SOC, SOC, Op_RegF, 6, V6->as_VMReg()->next(2));
reg_def R_V7c(SOC, SOC, Op_RegF, 7, V7->as_VMReg()->next(2));
reg_def R_V8c(SOC, SOC, Op_RegF, 8, V8->as_VMReg()->next(2));
reg_def R_V9c(SOC, SOC, Op_RegF, 9, V9->as_VMReg()->next(2));
reg_def R_V10c(SOC, SOC, Op_RegF, 10, V10->as_VMReg()->next(2));
reg_def R_V11c(SOC, SOC, Op_RegF, 11, V11->as_VMReg()->next(2));
reg_def R_V12c(SOC, SOC, Op_RegF, 12, V12->as_VMReg()->next(2));
reg_def R_V13c(SOC, SOC, Op_RegF, 13, V13->as_VMReg()->next(2));
reg_def R_V14c(SOC, SOC, Op_RegF, 14, V14->as_VMReg()->next(2));
reg_def R_V15c(SOC, SOC, Op_RegF, 15, V15->as_VMReg()->next(2));
reg_def R_V16c(SOC, SOC, Op_RegF, 16, V16->as_VMReg()->next(2));
reg_def R_V17c(SOC, SOC, Op_RegF, 17, V17->as_VMReg()->next(2));
reg_def R_V18c(SOC, SOC, Op_RegF, 18, V18->as_VMReg()->next(2));
reg_def R_V19c(SOC, SOC, Op_RegF, 19, V19->as_VMReg()->next(2));
reg_def R_V20c(SOC, SOC, Op_RegF, 20, V20->as_VMReg()->next(2));
reg_def R_V21c(SOC, SOC, Op_RegF, 21, V21->as_VMReg()->next(2));
reg_def R_V22c(SOC, SOC, Op_RegF, 22, V22->as_VMReg()->next(2));
reg_def R_V23c(SOC, SOC, Op_RegF, 23, V23->as_VMReg()->next(2));
reg_def R_V24c(SOC, SOC, Op_RegF, 24, V24->as_VMReg()->next(2));
reg_def R_V25c(SOC, SOC, Op_RegF, 25, V25->as_VMReg()->next(2));
reg_def R_V26c(SOC, SOC, Op_RegF, 26, V26->as_VMReg()->next(2));
reg_def R_V27c(SOC, SOC, Op_RegF, 27, V27->as_VMReg()->next(2));
reg_def R_V28c(SOC, SOC, Op_RegF, 28, V28->as_VMReg()->next(2));
reg_def R_V29c(SOC, SOC, Op_RegF, 29, V29->as_VMReg()->next(2));
reg_def R_V30c(SOC, SOC, Op_RegF, 30, V30->as_VMReg()->next(2));
reg_def R_V31c(SOC, SOC, Op_RegF, 31, V31->as_VMReg()->next(2));
reg_def R_V0d(SOC, SOC, Op_RegF, 0, V0->as_VMReg()->next(3));
reg_def R_V1d(SOC, SOC, Op_RegF, 1, V1->as_VMReg()->next(3));
reg_def R_V2d(SOC, SOC, Op_RegF, 2, V2->as_VMReg()->next(3));
reg_def R_V3d(SOC, SOC, Op_RegF, 3, V3->as_VMReg()->next(3));
reg_def R_V4d(SOC, SOC, Op_RegF, 4, V4->as_VMReg()->next(3));
reg_def R_V5d(SOC, SOC, Op_RegF, 5, V5->as_VMReg()->next(3));
reg_def R_V6d(SOC, SOC, Op_RegF, 6, V6->as_VMReg()->next(3));
reg_def R_V7d(SOC, SOC, Op_RegF, 7, V7->as_VMReg()->next(3));
reg_def R_V8d(SOC, SOC, Op_RegF, 8, V8->as_VMReg()->next(3));
reg_def R_V9d(SOC, SOC, Op_RegF, 9, V9->as_VMReg()->next(3));
reg_def R_V10d(SOC, SOC, Op_RegF, 10, V10->as_VMReg()->next(3));
reg_def R_V11d(SOC, SOC, Op_RegF, 11, V11->as_VMReg()->next(3));
reg_def R_V12d(SOC, SOC, Op_RegF, 12, V12->as_VMReg()->next(3));
reg_def R_V13d(SOC, SOC, Op_RegF, 13, V13->as_VMReg()->next(3));
reg_def R_V14d(SOC, SOC, Op_RegF, 14, V14->as_VMReg()->next(3));
reg_def R_V15d(SOC, SOC, Op_RegF, 15, V15->as_VMReg()->next(3));
reg_def R_V16d(SOC, SOC, Op_RegF, 16, V16->as_VMReg()->next(3));
reg_def R_V17d(SOC, SOC, Op_RegF, 17, V17->as_VMReg()->next(3));
reg_def R_V18d(SOC, SOC, Op_RegF, 18, V18->as_VMReg()->next(3));
reg_def R_V19d(SOC, SOC, Op_RegF, 19, V19->as_VMReg()->next(3));
reg_def R_V20d(SOC, SOC, Op_RegF, 20, V20->as_VMReg()->next(3));
reg_def R_V21d(SOC, SOC, Op_RegF, 21, V21->as_VMReg()->next(3));
reg_def R_V22d(SOC, SOC, Op_RegF, 22, V22->as_VMReg()->next(3));
reg_def R_V23d(SOC, SOC, Op_RegF, 23, V23->as_VMReg()->next(3));
reg_def R_V24d(SOC, SOC, Op_RegF, 24, V24->as_VMReg()->next(3));
reg_def R_V25d(SOC, SOC, Op_RegF, 25, V25->as_VMReg()->next(3));
reg_def R_V26d(SOC, SOC, Op_RegF, 26, V26->as_VMReg()->next(3));
reg_def R_V27d(SOC, SOC, Op_RegF, 27, V27->as_VMReg()->next(3));
reg_def R_V28d(SOC, SOC, Op_RegF, 28, V28->as_VMReg()->next(3));
reg_def R_V29d(SOC, SOC, Op_RegF, 29, V29->as_VMReg()->next(3));
reg_def R_V30d(SOC, SOC, Op_RegF, 30, V30->as_VMReg()->next(3));
reg_def R_V31d(SOC, SOC, Op_RegF, 31, V31->as_VMReg()->next(3));
// ----------------------------
// Special Registers
// Condition Codes Flag Registers
reg_def APSR (SOC, SOC, Op_RegFlags, 255, VMRegImpl::Bad());
reg_def FPSCR(SOC, SOC, Op_RegFlags, 255, VMRegImpl::Bad());
// ----------------------------
// Specify the enum values for the registers. These enums are only used by the
// OptoReg "class". We can convert these enum values at will to VMReg when needed
// for visibility to the rest of the vm. The order of this enum influences the
// register allocator so having the freedom to set this order and not be stuck
// with the order that is natural for the rest of the vm is worth it.
// Quad vector must be aligned here, so list them first.
alloc_class fprs(
R_V8, R_V8b, R_V8c, R_V8d, R_V9, R_V9b, R_V9c, R_V9d,
R_V10, R_V10b, R_V10c, R_V10d, R_V11, R_V11b, R_V11c, R_V11d,
R_V12, R_V12b, R_V12c, R_V12d, R_V13, R_V13b, R_V13c, R_V13d,
R_V14, R_V14b, R_V14c, R_V14d, R_V15, R_V15b, R_V15c, R_V15d,
R_V16, R_V16b, R_V16c, R_V16d, R_V17, R_V17b, R_V17c, R_V17d,
R_V18, R_V18b, R_V18c, R_V18d, R_V19, R_V19b, R_V19c, R_V19d,
R_V20, R_V20b, R_V20c, R_V20d, R_V21, R_V21b, R_V21c, R_V21d,
R_V22, R_V22b, R_V22c, R_V22d, R_V23, R_V23b, R_V23c, R_V23d,
R_V24, R_V24b, R_V24c, R_V24d, R_V25, R_V25b, R_V25c, R_V25d,
R_V26, R_V26b, R_V26c, R_V26d, R_V27, R_V27b, R_V27c, R_V27d,
R_V28, R_V28b, R_V28c, R_V28d, R_V29, R_V29b, R_V29c, R_V29d,
R_V30, R_V30b, R_V30c, R_V30d, R_V31, R_V31b, R_V31c, R_V31d,
R_V0, R_V0b, R_V0c, R_V0d, R_V1, R_V1b, R_V1c, R_V1d,
R_V2, R_V2b, R_V2c, R_V2d, R_V3, R_V3b, R_V3c, R_V3d,
R_V4, R_V4b, R_V4c, R_V4d, R_V5, R_V5b, R_V5c, R_V5d,
R_V6, R_V6b, R_V6c, R_V6d, R_V7, R_V7b, R_V7c, R_V7d
);
// Need double-register alignment here.
// We are already quad-register aligned because of vectors above.
alloc_class gprs(
R_R0, R_R0x, R_R1, R_R1x, R_R2, R_R2x, R_R3, R_R3x,
R_R4, R_R4x, R_R5, R_R5x, R_R6, R_R6x, R_R7, R_R7x,
R_R8, R_R8x, R_R9, R_R9x, R_R10, R_R10x, R_R11, R_R11x,
R_R12, R_R12x, R_R13, R_R13x, R_R14, R_R14x, R_R15, R_R15x,
R_R16, R_R16x, R_R17, R_R17x, R_R18, R_R18x, R_R19, R_R19x,
R_R20, R_R20x, R_R21, R_R21x, R_R22, R_R22x, R_R23, R_R23x,
R_R24, R_R24x, R_R25, R_R25x, R_R26, R_R26x, R_R27, R_R27x,
R_R28, R_R28x, R_R29, R_R29x, R_R30, R_R30x
);
// Continuing with double-reigister alignment...
alloc_class chunk2(APSR, FPSCR);
alloc_class chunk3(R_SP, R_SPx);
alloc_class chunk4(R_ZR, R_ZRx);
//----------Architecture Description Register Classes--------------------------
// Several register classes are automatically defined based upon information in
// this architecture description.
// 1) reg_class inline_cache_reg ( as defined in frame section )
// 2) reg_class interpreter_method_oop_reg ( as defined in frame section )
// 3) reg_class stack_slots( /* one chunk of stack-based "registers" */ )
//
// ----------------------------
// Integer Register Classes
// ----------------------------
reg_class int_reg_all(R_R0, R_R1, R_R2, R_R3, R_R4, R_R5, R_R6, R_R7,
R_R8, R_R9, R_R10, R_R11, R_R12, R_R13, R_R14, R_R15,
R_R16, R_R17, R_R18, R_R19, R_R20, R_R21, R_R22, R_R23,
R_R24, R_R25, R_R26, R_R27, R_R28, R_R29, R_R30
);
// Exclusions from i_reg:
// SP (R31)
// Rthread/R28: reserved by HotSpot to the TLS register (invariant within Java)
reg_class int_reg %{
return _INT_REG_mask;
%}
reg_class ptr_reg %{
return _PTR_REG_mask;
%}
reg_class vectorx_reg %{
return _VECTORX_REG_mask;
%}
reg_class R0_regI(R_R0);
reg_class R1_regI(R_R1);
reg_class R2_regI(R_R2);
reg_class R3_regI(R_R3);
//reg_class R12_regI(R_R12);
// ----------------------------
// Pointer Register Classes
// ----------------------------
// Special class for storeP instructions, which can store SP or RPC to TLS.
// It is also used for memory addressing, allowing direct TLS addressing.
reg_class sp_ptr_reg %{
return _SP_PTR_REG_mask;
%}
reg_class store_reg %{
return _STR_REG_mask;
%}
reg_class store_ptr_reg %{
return _STR_PTR_REG_mask;
%}
reg_class spillP_reg %{
return _SPILLP_REG_mask;
%}
// Other special pointer regs
reg_class R0_regP(R_R0, R_R0x);
reg_class R1_regP(R_R1, R_R1x);
reg_class R2_regP(R_R2, R_R2x);
reg_class Rexception_regP(R_R19, R_R19x);
reg_class Ricklass_regP(R_R8, R_R8x);
reg_class Rmethod_regP(R_R27, R_R27x);
reg_class Rthread_regP(R_R28, R_R28x);
reg_class IP_regP(R_R16, R_R16x);
#define RtempRegP IPRegP
reg_class LR_regP(R_R30, R_R30x);
reg_class SP_regP(R_SP, R_SPx);
reg_class FP_regP(R_R29, R_R29x);
reg_class ZR_regP(R_ZR, R_ZRx);
reg_class ZR_regI(R_ZR);
// ----------------------------
// Long Register Classes
// ----------------------------
reg_class long_reg %{ return _PTR_REG_mask; %}
// for ldrexd, strexd: first reg of pair must be even
reg_class long_reg_align %{ return LONG_REG_mask(); %}
reg_class R0_regL(R_R0,R_R0x); // arg 1 or return value
// ----------------------------
// Special Class for Condition Code Flags Register
reg_class int_flags(APSR);
reg_class float_flags(FPSCR);
// ----------------------------
// Float Point Register Classes
// ----------------------------
reg_class sflt_reg_0(
R_V0, R_V1, R_V2, R_V3, R_V4, R_V5, R_V6, R_V7,
R_V8, R_V9, R_V10, R_V11, R_V12, R_V13, R_V14, R_V15,
R_V16, R_V17, R_V18, R_V19, R_V20, R_V21, R_V22, R_V23,
R_V24, R_V25, R_V26, R_V27, R_V28, R_V29, R_V30, R_V31);
reg_class sflt_reg %{
return _SFLT_REG_mask;
%}
reg_class dflt_low_reg %{
return _DFLT_REG_mask;
%}
reg_class actual_dflt_reg %{
return _DFLT_REG_mask;
%}
reg_class vectorx_reg_0(
R_V0, R_V1, R_V2, R_V3, R_V4, R_V5, R_V6, R_V7,
R_V8, R_V9, R_V10, R_V11, R_V12, R_V13, R_V14, R_V15,
R_V16, R_V17, R_V18, R_V19, R_V20, R_V21, R_V22, R_V23,
R_V24, R_V25, R_V26, R_V27, R_V28, R_V29, R_V30, /*R_V31,*/
R_V0b, R_V1b, R_V2b, R_V3b, R_V4b, R_V5b, R_V6b, R_V7b,
R_V8b, R_V9b, R_V10b, R_V11b, R_V12b, R_V13b, R_V14b, R_V15b,
R_V16b, R_V17b, R_V18b, R_V19b, R_V20b, R_V21b, R_V22b, R_V23b,
R_V24b, R_V25b, R_V26b, R_V27b, R_V28b, R_V29b, R_V30b, /*R_V31b,*/
R_V0c, R_V1c, R_V2c, R_V3c, R_V4c, R_V5c, R_V6c, R_V7c,
R_V8c, R_V9c, R_V10c, R_V11c, R_V12c, R_V13c, R_V14c, R_V15c,
R_V16c, R_V17c, R_V18c, R_V19c, R_V20c, R_V21c, R_V22c, R_V23c,
R_V24c, R_V25c, R_V26c, R_V27c, R_V28c, R_V29c, R_V30c, /*R_V31c,*/
R_V0d, R_V1d, R_V2d, R_V3d, R_V4d, R_V5d, R_V6d, R_V7d,
R_V8d, R_V9d, R_V10d, R_V11d, R_V12d, R_V13d, R_V14d, R_V15d,
R_V16d, R_V17d, R_V18d, R_V19d, R_V20d, R_V21d, R_V22d, R_V23d,
R_V24d, R_V25d, R_V26d, R_V27d, R_V28d, R_V29d, R_V30d, /*R_V31d*/);
reg_class Rmemcopy_reg %{
return _RMEMCOPY_REG_mask;
%}
%}
source_hpp %{
const MachRegisterNumbers R_mem_copy_lo_num = R_V31_num;
const MachRegisterNumbers R_mem_copy_hi_num = R_V31b_num;
const FloatRegister Rmemcopy = V31;
const MachRegisterNumbers R_hf_ret_lo_num = R_V0_num;
const MachRegisterNumbers R_hf_ret_hi_num = R_V0b_num;
const FloatRegister Rhfret = V0;
extern OptoReg::Name R_Ricklass_num;
extern OptoReg::Name R_Rmethod_num;
extern OptoReg::Name R_tls_num;
extern OptoReg::Name R_Rheap_base_num;
extern RegMask _INT_REG_mask;
extern RegMask _PTR_REG_mask;
extern RegMask _SFLT_REG_mask;
extern RegMask _DFLT_REG_mask;
extern RegMask _VECTORX_REG_mask;
extern RegMask _RMEMCOPY_REG_mask;
extern RegMask _SP_PTR_REG_mask;
extern RegMask _SPILLP_REG_mask;
extern RegMask _STR_REG_mask;
extern RegMask _STR_PTR_REG_mask;
#define LDR_DOUBLE "LDR_D"
#define LDR_FLOAT "LDR_S"
#define STR_DOUBLE "STR_D"
#define STR_FLOAT "STR_S"
#define STR_64 "STR"
#define LDR_64 "LDR"
#define STR_32 "STR_W"
#define LDR_32 "LDR_W"
#define MOV_DOUBLE "FMOV_D"
#define MOV_FLOAT "FMOV_S"
#define FMSR "FMOV_SW"
#define FMRS "FMOV_WS"
#define LDREX "ldxr "
#define STREX "stxr "
#define str_64 str
#define ldr_64 ldr
#define ldr_32 ldr_w
#define ldrex ldxr
#define strex stxr
#define fmsr fmov_sw
#define fmrs fmov_ws
#define fconsts fmov_s
#define fconstd fmov_d
static inline bool is_uimm12(jlong imm, int shift) {
return Assembler::is_unsigned_imm_in_range(imm, 12, shift);
}
static inline bool is_memoryD(int offset) {
int scale = 3; // LogBytesPerDouble
return is_uimm12(offset, scale);
}
static inline bool is_memoryfp(int offset) {
int scale = LogBytesPerInt; // include 32-bit word accesses
return is_uimm12(offset, scale);
}
static inline bool is_memoryI(int offset) {
int scale = LogBytesPerInt;
return is_uimm12(offset, scale);
}
static inline bool is_memoryP(int offset) {
int scale = LogBytesPerWord;
return is_uimm12(offset, scale);
}
static inline bool is_memoryHD(int offset) {
int scale = LogBytesPerInt; // include 32-bit word accesses
return is_uimm12(offset, scale);
}
uintx limmL_low(uintx imm, int n);
static inline bool Xis_aimm(int imm) {
return Assembler::ArithmeticImmediate(imm).is_encoded();
}
static inline bool is_aimm(intptr_t imm) {
return Assembler::ArithmeticImmediate(imm).is_encoded();
}
static inline bool is_limmL(uintptr_t imm) {
return Assembler::LogicalImmediate(imm).is_encoded();
}
static inline bool is_limmL_low(intptr_t imm, int n) {
return is_limmL(limmL_low(imm, n));
}
static inline bool is_limmI(jint imm) {
return Assembler::LogicalImmediate(imm, true).is_encoded();
}
static inline uintx limmI_low(jint imm, int n) {
return limmL_low(imm, n);
}
static inline bool is_limmI_low(jint imm, int n) {
return is_limmL_low(imm, n);
}
%}
source %{
// Given a register encoding, produce a Integer Register object
static Register reg_to_register_object(int register_encoding) {
assert(R0->encoding() == R_R0_enc && R30->encoding() == R_R30_enc, "right coding");
assert(Rthread->encoding() == R_R28_enc, "right coding");
assert(SP->encoding() == R_SP_enc, "right coding");
return as_Register(register_encoding);
}
// Given a register encoding, produce a single-precision Float Register object
static FloatRegister reg_to_FloatRegister_object(int register_encoding) {
assert(V0->encoding() == R_V0_enc && V31->encoding() == R_V31_enc, "right coding");
return as_FloatRegister(register_encoding);
}
RegMask _INT_REG_mask;
RegMask _PTR_REG_mask;
RegMask _SFLT_REG_mask;
RegMask _DFLT_REG_mask;
RegMask _VECTORX_REG_mask;
RegMask _RMEMCOPY_REG_mask;
RegMask _SP_PTR_REG_mask;
RegMask _SPILLP_REG_mask;
RegMask _STR_REG_mask;
RegMask _STR_PTR_REG_mask;
OptoReg::Name R_Ricklass_num = -1;
OptoReg::Name R_Rmethod_num = -1;
OptoReg::Name R_tls_num = -1;
OptoReg::Name R_Rtemp_num = -1;
OptoReg::Name R_Rheap_base_num = -1;
static int mov_oop_size = -1;
#ifdef ASSERT
static bool same_mask(const RegMask &a, const RegMask &b) {
RegMask a_sub_b = a; a_sub_b.SUBTRACT(b);
RegMask b_sub_a = b; b_sub_a.SUBTRACT(a);
return a_sub_b.Size() == 0 && b_sub_a.Size() == 0;
}
#endif
void Compile::pd_compiler2_init() {
R_Ricklass_num = OptoReg::as_OptoReg(Ricklass->as_VMReg());
R_Rmethod_num = OptoReg::as_OptoReg(Rmethod->as_VMReg());
R_tls_num = OptoReg::as_OptoReg(Rthread->as_VMReg());
R_Rtemp_num = OptoReg::as_OptoReg(Rtemp->as_VMReg());
R_Rheap_base_num = OptoReg::as_OptoReg(Rheap_base->as_VMReg());
_INT_REG_mask = _INT_REG_ALL_mask;
_INT_REG_mask.Remove(R_tls_num);
_INT_REG_mask.Remove(R_SP_num);
if (UseCompressedOops) {
_INT_REG_mask.Remove(R_Rheap_base_num);
}
// Remove Rtemp because safepoint poll can trash it
// (see SharedRuntime::generate_handler_blob)
_INT_REG_mask.Remove(R_Rtemp_num);
_PTR_REG_mask = _INT_REG_mask;
_PTR_REG_mask.smear_to_sets(2);
// STR_REG = INT_REG+ZR
// SPILLP_REG = INT_REG+SP
// SP_PTR_REG = INT_REG+SP+TLS
_STR_REG_mask = _INT_REG_mask;
_SP_PTR_REG_mask = _STR_REG_mask;
_STR_REG_mask.Insert(R_ZR_num);
_SP_PTR_REG_mask.Insert(R_SP_num);
_SPILLP_REG_mask = _SP_PTR_REG_mask;
_SP_PTR_REG_mask.Insert(R_tls_num);
_STR_PTR_REG_mask = _STR_REG_mask;
_STR_PTR_REG_mask.smear_to_sets(2);
_SP_PTR_REG_mask.smear_to_sets(2);
_SPILLP_REG_mask.smear_to_sets(2);
_RMEMCOPY_REG_mask = RegMask(R_mem_copy_lo_num);
assert(OptoReg::as_OptoReg(Rmemcopy->as_VMReg()) == R_mem_copy_lo_num, "!");
_SFLT_REG_mask = _SFLT_REG_0_mask;
_SFLT_REG_mask.SUBTRACT(_RMEMCOPY_REG_mask);
_DFLT_REG_mask = _SFLT_REG_mask;
_DFLT_REG_mask.smear_to_sets(2);
_VECTORX_REG_mask = _SFLT_REG_mask;
_VECTORX_REG_mask.smear_to_sets(4);
assert(same_mask(_VECTORX_REG_mask, _VECTORX_REG_0_mask), "!");
#ifdef ASSERT
RegMask r((RegMask *)&SFLT_REG_mask());
r.smear_to_sets(2);
assert(same_mask(r, _DFLT_REG_mask), "!");
#endif
if (VM_Version::prefer_moves_over_load_literal()) {
mov_oop_size = 4;
} else {
mov_oop_size = 1;
}
assert(Matcher::interpreter_method_oop_reg_encode() == Rmethod->encoding(), "should be");
}
uintx limmL_low(uintx imm, int n) {
// 1: try as is
if (is_limmL(imm)) {
return imm;
}
// 2: try low bits + all 0's
uintx imm0 = imm & right_n_bits(n);
if (is_limmL(imm0)) {
return imm0;
}
// 3: try low bits + all 1's
uintx imm1 = imm0 | left_n_bits(BitsPerWord - n);
if (is_limmL(imm1)) {
return imm1;
}
#if 0
// 4: try low bits replicated
int field = 1 << log2_intptr(n + n - 1);
assert(field >= n, "!");
assert(field / n == 1, "!");
intptr_t immr = immx;
while (field < BitsPerWord) {
intrptr_t bits = immr & right_n_bits(field);
immr = bits | (bits << field);
field = field << 1;
}
// replicate at power-of-2 boundary
if (is_limmL(immr)) {
return immr;
}
#endif
return imm;
}
// Convert the raw encoding form into the form expected by the
// constructor for Address.
Address Address::make_raw(int base, int index, int scale, int disp, relocInfo::relocType disp_reloc) {
RelocationHolder rspec;
if (disp_reloc != relocInfo::none) {
rspec = Relocation::spec_simple(disp_reloc);
}
Register rbase = (base == 0xff) ? SP : as_Register(base);
if (index != 0xff) {
Register rindex = as_Register(index);
if (disp == 0x7fffffff) { // special value to indicate sign-extend
Address madr(rbase, rindex, ex_sxtw, scale);
madr._rspec = rspec;
return madr;
} else {
assert(disp == 0, "unsupported");
Address madr(rbase, rindex, ex_lsl, scale);
madr._rspec = rspec;
return madr;
}
} else {
assert(scale == 0, "not supported");
Address madr(rbase, disp);
madr._rspec = rspec;
return madr;
}
}
// Location of compiled Java return values. Same as C
OptoRegPair c2::return_value(int ideal_reg) {
assert( ideal_reg >= Op_RegI && ideal_reg <= Op_RegL, "only return normal values" );
static int lo[Op_RegL+1] = { 0, 0, OptoReg::Bad, R_R0_num, R_R0_num, R_hf_ret_lo_num, R_hf_ret_lo_num, R_R0_num };
static int hi[Op_RegL+1] = { 0, 0, OptoReg::Bad, OptoReg::Bad, R_R0x_num, OptoReg::Bad, R_hf_ret_hi_num, R_R0x_num };
return OptoRegPair( hi[ideal_reg], lo[ideal_reg]);
}
// !!!!! Special hack to get all type of calls to specify the byte offset
// from the start of the call to the point where the return address
// will point.
int MachCallStaticJavaNode::ret_addr_offset() {
bool far = (_method == NULL) ? maybe_far_call(this) : !cache_reachable();
bool patchable = _method != NULL;
int call_size = MacroAssembler::call_size(entry_point(), far, patchable);
return (call_size + (_method_handle_invoke ? 1 : 0)) * NativeInstruction::instruction_size;
}
int MachCallDynamicJavaNode::ret_addr_offset() {
bool far = !cache_reachable();
int call_size = MacroAssembler::call_size(entry_point(), far, true);
return (mov_oop_size + call_size) * NativeInstruction::instruction_size;
}
int MachCallRuntimeNode::ret_addr_offset() {
int call_size = 0;
// TODO: check if Leaf nodes also need this
if (!is_MachCallLeaf()) {
// adr $temp, ret_addr
// str $temp, [SP + last_java_pc]
call_size += 2;
}
// bl or mov_slow; blr
bool far = maybe_far_call(this);
call_size += MacroAssembler::call_size(entry_point(), far, false);
return call_size * NativeInstruction::instruction_size;
}
%}
// The intptr_t operand types, defined by textual substitution.
// (Cf. opto/type.hpp. This lets us avoid many, many other ifdefs.)
#define immX immL
#define iRegX iRegL
#define aimmX aimmL
#define limmX limmL
#define immX9 immL9
#define LShiftX LShiftL
#define shimmX immU6
#define store_RegLd store_RegL
//----------ATTRIBUTES---------------------------------------------------------
//----------Operand Attributes-------------------------------------------------
op_attrib op_cost(1); // Required cost attribute
//----------OPERANDS-----------------------------------------------------------
// Operand definitions must precede instruction definitions for correct parsing
// in the ADLC because operands constitute user defined types which are used in
// instruction definitions.
//----------Simple Operands----------------------------------------------------
// Immediate Operands
// Integer Immediate: 9-bit (including sign bit), so same as immI8?
// FIXME: simm9 allows -256, but immI8 doesn't...
operand simm9() %{
predicate(Assembler::is_imm_in_range(n->get_int(), 9, 0));
match(ConI);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
operand uimm12() %{
predicate(Assembler::is_unsigned_imm_in_range(n->get_int(), 12, 0));
match(ConI);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
operand aimmP() %{
predicate(n->get_ptr() == 0 || (is_aimm(n->get_ptr()) && ((ConPNode*)n)->type()->reloc() == relocInfo::none));
match(ConP);
op_cost(0);
// formats are generated automatically for constants and base registers
format %{ %}
interface(CONST_INTER);
%}
// Long Immediate: 12-bit - for addressing mode
operand immL12() %{
predicate((-4096 < n->get_long()) && (n->get_long() < 4096));
match(ConL);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
// Long Immediate: 9-bit - for addressing mode
operand immL9() %{
predicate((-256 <= n->get_long()) && (n->get_long() < 256));
match(ConL);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
operand immIMov() %{
predicate(n->get_int() >> 16 == 0);
match(ConI);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
operand immLMov() %{
predicate(n->get_long() >> 16 == 0);
match(ConL);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
operand immUL12() %{
predicate(is_uimm12(n->get_long(), 0));
match(ConL);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
operand immUL12x2() %{
predicate(is_uimm12(n->get_long(), 1));
match(ConL);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
operand immUL12x4() %{
predicate(is_uimm12(n->get_long(), 2));
match(ConL);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
operand immUL12x8() %{
predicate(is_uimm12(n->get_long(), 3));
match(ConL);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
operand immUL12x16() %{
predicate(is_uimm12(n->get_long(), 4));
match(ConL);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
// Used for long shift
operand immU6() %{
predicate(0 <= n->get_int() && (n->get_int() <= 63));
match(ConI);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
// Used for register extended shift
operand immI_0_4() %{
predicate(0 <= n->get_int() && (n->get_int() <= 4));
match(ConI);
op_cost(0);
format %{ %}
interface(CONST_INTER);
%}
// Compressed Pointer Register
operand iRegN() %{
constraint(ALLOC_IN_RC(int_reg));
match(RegN);
match(ZRRegN);
format %{ %}
interface(REG_INTER);
%}
operand SPRegP() %{
constraint(ALLOC_IN_RC(SP_regP));
match(RegP);
format %{ %}
interface(REG_INTER);
%}
operand ZRRegP() %{
constraint(ALLOC_IN_RC(ZR_regP));
match(RegP);
format %{ %}
interface(REG_INTER);
%}
operand ZRRegL() %{
constraint(ALLOC_IN_RC(ZR_regP));
match(RegL);
format %{ %}
interface(REG_INTER);
%}
operand ZRRegI() %{
constraint(ALLOC_IN_RC(ZR_regI));
match(RegI);
format %{ %}
interface(REG_INTER);
%}
operand ZRRegN() %{
constraint(ALLOC_IN_RC(ZR_regI));
match(RegN);
format %{ %}
interface(REG_INTER);
%}

View File

@ -0,0 +1,57 @@
/*
* Copyright (c) 2008, 2015, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "asm/assembler.hpp"
#include "asm/assembler.inline.hpp"
#include "ci/ciEnv.hpp"
#include "gc/shared/cardTableModRefBS.hpp"
#include "gc/shared/collectedHeap.inline.hpp"
#include "interpreter/interpreter.hpp"
#include "interpreter/interpreterRuntime.hpp"
#include "interpreter/templateInterpreterGenerator.hpp"
#include "memory/resourceArea.hpp"
#include "prims/jvm_misc.hpp"
#include "prims/methodHandles.hpp"
#include "runtime/biasedLocking.hpp"
#include "runtime/interfaceSupport.hpp"
#include "runtime/objectMonitor.hpp"
#include "runtime/os.hpp"
#include "runtime/sharedRuntime.hpp"
#include "runtime/stubRoutines.hpp"
#include "utilities/hashtable.hpp"
#include "utilities/macros.hpp"
#if INCLUDE_ALL_GCS
#include "gc/g1/g1CollectedHeap.inline.hpp"
#include "gc/g1/g1SATBCardTableModRefBS.hpp"
#include "gc/g1/heapRegion.hpp"
#endif // INCLUDE_ALL_GCS
int AbstractAssembler::code_fill_byte() {
return 0xff; // illegal instruction 0xffffffff
}
#ifdef ASSERT
bool AbstractAssembler::pd_check_instruction_mark() { return false; }
#endif

View File

@ -0,0 +1,404 @@
/*
* Copyright (c) 2008, 2013, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_ASSEMBLER_ARM_HPP
#define CPU_ARM_VM_ASSEMBLER_ARM_HPP
#include "utilities/macros.hpp"
enum AsmCondition {
eq, ne, cs, cc, mi, pl, vs, vc,
hi, ls, ge, lt, gt, le, al, nv,
number_of_conditions,
// alternative names
hs = cs,
lo = cc
};
enum AsmShift {
lsl, lsr, asr, ror
};
#ifdef AARCH64
enum AsmExtendOp {
ex_uxtb, ex_uxth, ex_uxtw, ex_uxtx,
ex_sxtb, ex_sxth, ex_sxtw, ex_sxtx,
ex_lsl = ex_uxtx
};
#endif
enum AsmOffset {
#ifdef AARCH64
basic_offset = 0b00,
pre_indexed = 0b11,
post_indexed = 0b01
#else
basic_offset = 1 << 24,
pre_indexed = 1 << 24 | 1 << 21,
post_indexed = 0
#endif
};
#ifndef AARCH64
enum AsmWriteback {
no_writeback,
writeback
};
enum AsmOffsetOp {
sub_offset = 0,
add_offset = 1
};
#endif
// ARM Addressing Modes 2 and 3 - Load and store
class Address VALUE_OBJ_CLASS_SPEC {
private:
Register _base;
Register _index;
int _disp;
AsmOffset _mode;
RelocationHolder _rspec;
int _shift_imm;
#ifdef AARCH64
AsmExtendOp _extend;
#else
AsmShift _shift;
AsmOffsetOp _offset_op;
static inline int abs(int x) { return x < 0 ? -x : x; }
static inline int up (int x) { return x < 0 ? 0 : 1; }
#endif
#ifdef AARCH64
static const AsmExtendOp LSL = ex_lsl;
#else
static const AsmShift LSL = lsl;
#endif
public:
Address() : _base(noreg) {}
Address(Register rn, int offset = 0, AsmOffset mode = basic_offset) {
_base = rn;
_index = noreg;
_disp = offset;
_mode = mode;
_shift_imm = 0;
#ifdef AARCH64
_extend = ex_lsl;
#else
_shift = lsl;
_offset_op = add_offset;
#endif
}
#ifdef ASSERT
Address(Register rn, ByteSize offset, AsmOffset mode = basic_offset) {
_base = rn;
_index = noreg;
_disp = in_bytes(offset);
_mode = mode;
_shift_imm = 0;
#ifdef AARCH64
_extend = ex_lsl;
#else
_shift = lsl;
_offset_op = add_offset;
#endif
}
#endif
#ifdef AARCH64
Address(Register rn, Register rm, AsmExtendOp extend = ex_lsl, int shift_imm = 0) {
assert ((extend == ex_uxtw) || (extend == ex_lsl) || (extend == ex_sxtw) || (extend == ex_sxtx), "invalid extend for address mode");
assert ((0 <= shift_imm) && (shift_imm <= 4), "shift amount is out of range");
_base = rn;
_index = rm;
_disp = 0;
_mode = basic_offset;
_extend = extend;
_shift_imm = shift_imm;
}
#else
Address(Register rn, Register rm, AsmShift shift = lsl,
int shift_imm = 0, AsmOffset mode = basic_offset,
AsmOffsetOp offset_op = add_offset) {
_base = rn;
_index = rm;
_disp = 0;
_shift = shift;
_shift_imm = shift_imm;
_mode = mode;
_offset_op = offset_op;
}
Address(Register rn, RegisterOrConstant offset, AsmShift shift = lsl,
int shift_imm = 0) {
_base = rn;
if (offset.is_constant()) {
_index = noreg;
{
int off = (int) offset.as_constant();
if (shift_imm != 0) {
assert(shift == lsl,"shift not yet encoded");
off = off << shift_imm;
}
_disp = off;
}
_shift = lsl;
_shift_imm = 0;
} else {
_index = offset.as_register();
_disp = 0;
_shift = shift;
_shift_imm = shift_imm;
}
_mode = basic_offset;
_offset_op = add_offset;
}
#endif // AARCH64
// [base + index * wordSize]
static Address indexed_ptr(Register base, Register index) {
return Address(base, index, LSL, LogBytesPerWord);
}
// [base + index * BytesPerInt]
static Address indexed_32(Register base, Register index) {
return Address(base, index, LSL, LogBytesPerInt);
}
// [base + index * BytesPerHeapOop]
static Address indexed_oop(Register base, Register index) {
return Address(base, index, LSL, LogBytesPerHeapOop);
}
Address plus_disp(int disp) const {
assert((disp == 0) || (_index == noreg),"can't apply an offset to a register indexed address");
Address a = (*this);
a._disp += disp;
return a;
}
Address rebase(Register new_base) const {
Address a = (*this);
a._base = new_base;
return a;
}
#ifdef AARCH64
int encoding_simd() const {
assert(_index != SP, "encoding constraint");
assert(_disp == 0 || _mode == post_indexed, "encoding constraint");
assert(_index == noreg || _mode == basic_offset, "encoding constraint");
assert(_mode == basic_offset || _mode == post_indexed, "encoding constraint");
assert(_extend == ex_lsl, "encoding constraint");
int index;
if (_index == noreg) {
if (_mode == post_indexed)
index = 0b100 << 5 | 31;
else
index = 0;
} else {
index = 0b100 << 5 | _index->encoding();
}
return index << 16 | _base->encoding_with_sp() << 5;
}
#else /* !AARCH64 */
int encoding2() const {
assert(_mode == basic_offset || _base != PC, "unpredictable instruction");
if (_index == noreg) {
assert(-4096 < _disp && _disp < 4096, "encoding constraint");
return _mode | up(_disp) << 23 | _base->encoding() << 16 | abs(_disp);
} else {
assert(_index != PC && (_mode == basic_offset || _index != _base), "unpredictable instruction");
assert(_disp == 0 && (_shift_imm >> 5) == 0, "encoding constraint");
return 1 << 25 | _offset_op << 23 | _mode | _base->encoding() << 16 |
_shift_imm << 7 | _shift << 5 | _index->encoding();
}
}
int encoding3() const {
assert(_mode == basic_offset || _base != PC, "unpredictable instruction");
if (_index == noreg) {
assert(-256 < _disp && _disp < 256, "encoding constraint");
return _mode | up(_disp) << 23 | 1 << 22 | _base->encoding() << 16 |
(abs(_disp) & 0xf0) << 4 | abs(_disp) & 0x0f;
} else {
assert(_index != PC && (_mode == basic_offset || _index != _base), "unpredictable instruction");
assert(_disp == 0 && _shift == lsl && _shift_imm == 0, "encoding constraint");
return _mode | _offset_op << 23 | _base->encoding() << 16 | _index->encoding();
}
}
int encoding_ex() const {
assert(_index == noreg && _disp == 0 && _mode == basic_offset &&
_base != PC, "encoding constraint");
return _base->encoding() << 16;
}
int encoding_vfp() const {
assert(_index == noreg && _mode == basic_offset, "encoding constraint");
assert(-1024 < _disp && _disp < 1024 && (_disp & 3) == 0, "encoding constraint");
return _base->encoding() << 16 | up(_disp) << 23 | abs(_disp) >> 2;
}
int encoding_simd() const {
assert(_base != PC, "encoding constraint");
assert(_index != PC && _index != SP, "encoding constraint");
assert(_disp == 0, "encoding constraint");
assert(_shift == 0, "encoding constraint");
assert(_index == noreg || _mode == basic_offset, "encoding constraint");
assert(_mode == basic_offset || _mode == post_indexed, "encoding constraint");
int index;
if (_index == noreg) {
if (_mode == post_indexed)
index = 13;
else
index = 15;
} else {
index = _index->encoding();
}
return _base->encoding() << 16 | index;
}
#endif // !AARCH64
Register base() const {
return _base;
}
Register index() const {
return _index;
}
int disp() const {
return _disp;
}
AsmOffset mode() const {
return _mode;
}
int shift_imm() const {
return _shift_imm;
}
#ifdef AARCH64
AsmExtendOp extend() const {
return _extend;
}
#else
AsmShift shift() const {
return _shift;
}
AsmOffsetOp offset_op() const {
return _offset_op;
}
#endif
bool uses(Register reg) const { return _base == reg || _index == reg; }
const relocInfo::relocType rtype() { return _rspec.type(); }
const RelocationHolder& rspec() { return _rspec; }
// Convert the raw encoding form into the form expected by the
// constructor for Address.
static Address make_raw(int base, int index, int scale, int disp, relocInfo::relocType disp_reloc);
};
#ifdef COMPILER2
class VFP VALUE_OBJ_CLASS_SPEC {
// Helper classes to detect whether a floating point constant can be
// encoded in a fconstd or fconsts instruction
// The conversion from the imm8, 8 bit constant, to the floating
// point value encoding is done with either:
// for single precision: imm8<7>:NOT(imm8<6>):Replicate(imm8<6>,5):imm8<5:0>:Zeros(19)
// or
// for double precision: imm8<7>:NOT(imm8<6>):Replicate(imm8<6>,8):imm8<5:0>:Zeros(48)
private:
class fpnum {
public:
virtual unsigned int f_hi4() const = 0;
virtual bool f_lo_is_null() const = 0;
virtual int e() const = 0;
virtual unsigned int s() const = 0;
inline bool can_be_imm8() const { return e() >= -3 && e() <= 4 && f_lo_is_null(); }
inline unsigned char imm8() const { int v = (s() << 7) | (((e() - 1) & 0x7) << 4) | f_hi4(); assert((v >> 8) == 0, "overflow"); return v; }
};
public:
class float_num : public fpnum {
public:
float_num(float v) {
_num.val = v;
}
virtual unsigned int f_hi4() const { return (_num.bits << 9) >> (19+9); }
virtual bool f_lo_is_null() const { return (_num.bits & ((1 << 19) - 1)) == 0; }
virtual int e() const { return ((_num.bits << 1) >> (23+1)) - 127; }
virtual unsigned int s() const { return _num.bits >> 31; }
private:
union {
float val;
unsigned int bits;
} _num;
};
class double_num : public fpnum {
public:
double_num(double v) {
_num.val = v;
}
virtual unsigned int f_hi4() const { return (_num.bits << 12) >> (48+12); }
virtual bool f_lo_is_null() const { return (_num.bits & ((1LL << 48) - 1)) == 0; }
virtual int e() const { return ((_num.bits << 1) >> (52+1)) - 1023; }
virtual unsigned int s() const { return _num.bits >> 63; }
private:
union {
double val;
unsigned long long bits;
} _num;
};
};
#endif
#ifdef AARCH64
#include "assembler_arm_64.hpp"
#else
#include "assembler_arm_32.hpp"
#endif
#endif // CPU_ARM_VM_ASSEMBLER_ARM_HPP

View File

@ -0,0 +1,29 @@
/*
* Copyright (c) 2008, 2013, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_ASSEMBLER_ARM_INLINE_HPP
#define CPU_ARM_VM_ASSEMBLER_ARM_INLINE_HPP
#endif // CPU_ARM_VM_ASSEMBLER_ARM_INLINE_HPP

View File

@ -0,0 +1,99 @@
/*
* Copyright (c) 2008, 2015, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "asm/assembler.hpp"
#include "asm/assembler.inline.hpp"
#include "ci/ciEnv.hpp"
#include "gc/shared/cardTableModRefBS.hpp"
#include "gc/shared/collectedHeap.inline.hpp"
#include "interpreter/interpreter.hpp"
#include "interpreter/interpreterRuntime.hpp"
#include "interpreter/templateInterpreterGenerator.hpp"
#include "memory/resourceArea.hpp"
#include "prims/jvm_misc.hpp"
#include "prims/methodHandles.hpp"
#include "runtime/biasedLocking.hpp"
#include "runtime/interfaceSupport.hpp"
#include "runtime/objectMonitor.hpp"
#include "runtime/os.hpp"
#include "runtime/sharedRuntime.hpp"
#include "runtime/stubRoutines.hpp"
#include "utilities/hashtable.hpp"
#include "utilities/macros.hpp"
#if INCLUDE_ALL_GCS
#include "gc/g1/g1CollectedHeap.inline.hpp"
#include "gc/g1/g1SATBCardTableModRefBS.hpp"
#include "gc/g1/heapRegion.hpp"
#endif // INCLUDE_ALL_GCS
#ifdef COMPILER2
// Convert the raw encoding form into the form expected by the
// constructor for Address.
Address Address::make_raw(int base, int index, int scale, int disp, relocInfo::relocType disp_reloc) {
RelocationHolder rspec;
if (disp_reloc != relocInfo::none) {
rspec = Relocation::spec_simple(disp_reloc);
}
Register rindex = as_Register(index);
if (rindex != PC) {
assert(disp == 0, "unsupported");
Address madr(as_Register(base), rindex, lsl, scale);
madr._rspec = rspec;
return madr;
} else {
assert(scale == 0, "not supported");
Address madr(as_Register(base), disp);
madr._rspec = rspec;
return madr;
}
}
#endif
void AsmOperand::initialize_rotated_imm(unsigned int imm) {
for (int shift = 2; shift <= 24; shift += 2) {
if ((imm & ~(0xff << shift)) == 0) {
_encoding = 1 << 25 | (32 - shift) << 7 | imm >> shift;
return;
}
}
assert((imm & 0x0ffffff0) == 0, "too complicated constant: %d (%x)", imm, imm);
_encoding = 1 << 25 | 4 << 7 | imm >> 28 | imm << 4;
}
bool AsmOperand::is_rotated_imm(unsigned int imm) {
if ((imm >> 8) == 0) {
return true;
}
for (int shift = 2; shift <= 24; shift += 2) {
if ((imm & ~(0xff << shift)) == 0) {
return true;
}
}
if ((imm & 0x0ffffff0) == 0) {
return true;
}
return false;
}

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,191 @@
/*
* Copyright (c) 2008, 2015, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "asm/assembler.hpp"
#include "asm/assembler.inline.hpp"
#include "ci/ciEnv.hpp"
#include "gc/shared/cardTableModRefBS.hpp"
#include "gc/shared/collectedHeap.inline.hpp"
#include "interpreter/interpreter.hpp"
#include "interpreter/interpreterRuntime.hpp"
#include "interpreter/templateInterpreterGenerator.hpp"
#include "memory/resourceArea.hpp"
#include "prims/jvm_misc.hpp"
#include "prims/methodHandles.hpp"
#include "runtime/biasedLocking.hpp"
#include "runtime/interfaceSupport.hpp"
#include "runtime/objectMonitor.hpp"
#include "runtime/os.hpp"
#include "runtime/sharedRuntime.hpp"
#include "runtime/stubRoutines.hpp"
#include "utilities/hashtable.hpp"
#include "utilities/macros.hpp"
#if INCLUDE_ALL_GCS
#include "gc/g1/g1CollectedHeap.inline.hpp"
#include "gc/g1/g1SATBCardTableModRefBS.hpp"
#include "gc/g1/heapRegion.hpp"
#endif // INCLUDE_ALL_GCS
// Returns whether given imm has equal bit fields <0:size-1> and <size:2*size-1>.
inline bool Assembler::LogicalImmediate::has_equal_subpatterns(uintx imm, int size) {
uintx mask = right_n_bits(size);
uintx subpattern1 = mask_bits(imm, mask);
uintx subpattern2 = mask_bits(imm >> size, mask);
return subpattern1 == subpattern2;
}
// Returns least size that is a power of two from 2 to 64 with the proviso that given
// imm is composed of repeating patterns of this size.
inline int Assembler::LogicalImmediate::least_pattern_size(uintx imm) {
int size = BitsPerWord;
while (size > 2 && has_equal_subpatterns(imm, size >> 1)) {
size >>= 1;
}
return size;
}
// Returns count of set bits in given imm. Based on variable-precision SWAR algorithm.
inline int Assembler::LogicalImmediate::population_count(uintx x) {
x -= ((x >> 1) & 0x5555555555555555L);
x = (((x >> 2) & 0x3333333333333333L) + (x & 0x3333333333333333L));
x = (((x >> 4) + x) & 0x0f0f0f0f0f0f0f0fL);
x += (x >> 8);
x += (x >> 16);
x += (x >> 32);
return(x & 0x7f);
}
// Let given x be <A:B> where B = 0 and least bit of A = 1. Returns <A:C>, where C is B-size set bits.
inline uintx Assembler::LogicalImmediate::set_least_zeroes(uintx x) {
return x | (x - 1);
}
#ifdef ASSERT
// Restores immediate by encoded bit masks.
uintx Assembler::LogicalImmediate::decode() {
assert (_encoded, "should be");
int len_code = (_immN << 6) | ((~_imms) & 0x3f);
assert (len_code != 0, "should be");
int len = 6;
while (!is_set_nth_bit(len_code, len)) len--;
int esize = 1 << len;
assert (len > 0, "should be");
assert ((_is32bit ? 32 : 64) >= esize, "should be");
int levels = right_n_bits(len);
int S = _imms & levels;
int R = _immr & levels;
assert (S != levels, "should be");
uintx welem = right_n_bits(S + 1);
uintx wmask = (R == 0) ? welem : ((welem >> R) | (welem << (esize - R)));
for (int size = esize; size < 64; size <<= 1) {
wmask |= (wmask << size);
}
return wmask;
}
#endif
// Constructs LogicalImmediate by given imm. Figures out if given imm can be used in AArch64 logical
// instructions (AND, ANDS, EOR, ORR) and saves its encoding.
void Assembler::LogicalImmediate::construct(uintx imm, bool is32) {
_is32bit = is32;
if (is32) {
assert(((imm >> 32) == 0) || (((intx)imm >> 31) == -1), "32-bit immediate is out of range");
// Replicate low 32 bits.
imm &= 0xffffffff;
imm |= imm << 32;
}
// All-zeroes and all-ones can not be encoded.
if (imm != 0 && (~imm != 0)) {
// Let LPS (least pattern size) be the least size (power of two from 2 to 64) of repeating
// patterns in the immediate. If immediate value can be encoded, it is encoded by pattern
// of exactly LPS size (due to structure of valid patterns). In order to verify
// that immediate value can be encoded, LPS is calculated and <LPS-1:0> bits of immediate
// are verified to be valid pattern.
int lps = least_pattern_size(imm);
uintx lps_mask = right_n_bits(lps);
// A valid pattern has one of the following forms:
// | 0 x A | 1 x B | 0 x C |, where B > 0 and C > 0, or
// | 1 x A | 0 x B | 1 x C |, where B > 0 and C > 0.
// For simplicity, the second form of the pattern is inverted into the first form.
bool inverted = imm & 0x1;
uintx pattern = (inverted ? ~imm : imm) & lps_mask;
// | 0 x A | 1 x (B + C) |
uintx without_least_zeroes = set_least_zeroes(pattern);
// Pattern is valid iff without least zeroes it is a power of two - 1.
if ((without_least_zeroes & (without_least_zeroes + 1)) == 0) {
// Count B as population count of pattern.
int bits_count = population_count(pattern);
// Count B+C as population count of pattern without least zeroes
int left_range = population_count(without_least_zeroes);
// S-prefix is a part of imms field which encodes LPS.
// LPS | S prefix
// 64 | not defined
// 32 | 0b0
// 16 | 0b10
// 8 | 0b110
// 4 | 0b1110
// 2 | 0b11110
int s_prefix = (lps == 64) ? 0 : ~set_least_zeroes(lps) & 0x3f;
// immN bit is set iff LPS == 64.
_immN = (lps == 64) ? 1 : 0;
assert (!is32 || (_immN == 0), "32-bit immediate should be encoded with zero N-bit");
// immr is the rotation size.
_immr = lps + (inverted ? 0 : bits_count) - left_range;
// imms is the field that encodes bits count and S-prefix.
_imms = ((inverted ? (lps - bits_count) : bits_count) - 1) | s_prefix;
_encoded = true;
assert (decode() == imm, "illegal encoding");
return;
}
}
_encoded = false;
}

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,195 @@
/*
* 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_BYTES_ARM_HPP
#define CPU_ARM_VM_BYTES_ARM_HPP
#include "memory/allocation.hpp"
#include "utilities/macros.hpp"
#ifndef VM_LITTLE_ENDIAN
#define VM_LITTLE_ENDIAN 1
#endif
class Bytes: AllStatic {
public:
// Returns true if the byte ordering used by Java is different from the native byte ordering
// of the underlying machine.
static inline bool is_Java_byte_ordering_different() {
return VM_LITTLE_ENDIAN != 0;
}
static inline u2 get_Java_u2(address p) {
return (u2(p[0]) << 8) | u2(p[1]);
}
static inline u4 get_Java_u4(address p) {
return u4(p[0]) << 24 |
u4(p[1]) << 16 |
u4(p[2]) << 8 |
u4(p[3]);
}
static inline u8 get_Java_u8(address p) {
return u8(p[0]) << 56 |
u8(p[1]) << 48 |
u8(p[2]) << 40 |
u8(p[3]) << 32 |
u8(p[4]) << 24 |
u8(p[5]) << 16 |
u8(p[6]) << 8 |
u8(p[7]);
}
static inline void put_Java_u2(address p, u2 x) {
p[0] = x >> 8;
p[1] = x;
}
static inline void put_Java_u4(address p, u4 x) {
((u1*)p)[0] = x >> 24;
((u1*)p)[1] = x >> 16;
((u1*)p)[2] = x >> 8;
((u1*)p)[3] = x;
}
static inline void put_Java_u8(address p, u8 x) {
((u1*)p)[0] = x >> 56;
((u1*)p)[1] = x >> 48;
((u1*)p)[2] = x >> 40;
((u1*)p)[3] = x >> 32;
((u1*)p)[4] = x >> 24;
((u1*)p)[5] = x >> 16;
((u1*)p)[6] = x >> 8;
((u1*)p)[7] = x;
}
#ifdef VM_LITTLE_ENDIAN
static inline u2 get_native_u2(address p) {
return (intptr_t(p) & 1) == 0 ? *(u2*)p : u2(p[0]) | (u2(p[1]) << 8);
}
static inline u4 get_native_u4(address p) {
switch (intptr_t(p) & 3) {
case 0: return *(u4*)p;
case 2: return u4(((u2*)p)[0]) |
u4(((u2*)p)[1]) << 16;
default: return u4(p[0]) |
u4(p[1]) << 8 |
u4(p[2]) << 16 |
u4(p[3]) << 24;
}
}
static inline u8 get_native_u8(address p) {
switch (intptr_t(p) & 7) {
case 0: return *(u8*)p;
case 4: return u8(((u4*)p)[0]) |
u8(((u4*)p)[1]) << 32;
case 2: return u8(((u2*)p)[0]) |
u8(((u2*)p)[1]) << 16 |
u8(((u2*)p)[2]) << 32 |
u8(((u2*)p)[3]) << 48;
default: return u8(p[0]) |
u8(p[1]) << 8 |
u8(p[2]) << 16 |
u8(p[3]) << 24 |
u8(p[4]) << 32 |
u8(p[5]) << 40 |
u8(p[6]) << 48 |
u8(p[7]) << 56;
}
}
static inline void put_native_u2(address p, u2 x) {
if ((intptr_t(p) & 1) == 0) {
*(u2*)p = x;
} else {
p[0] = x;
p[1] = x >> 8;
}
}
static inline void put_native_u4(address p, u4 x) {
switch (intptr_t(p) & 3) {
case 0: *(u4*)p = x;
break;
case 2: ((u2*)p)[0] = x;
((u2*)p)[1] = x >> 16;
break;
default: ((u1*)p)[0] = x;
((u1*)p)[1] = x >> 8;
((u1*)p)[2] = x >> 16;
((u1*)p)[3] = x >> 24;
break;
}
}
static inline void put_native_u8(address p, u8 x) {
switch (intptr_t(p) & 7) {
case 0: *(u8*)p = x;
break;
case 4: ((u4*)p)[0] = x;
((u4*)p)[1] = x >> 32;
break;
case 2: ((u2*)p)[0] = x;
((u2*)p)[1] = x >> 16;
((u2*)p)[2] = x >> 32;
((u2*)p)[3] = x >> 48;
break;
default: ((u1*)p)[0] = x;
((u1*)p)[1] = x >> 8;
((u1*)p)[2] = x >> 16;
((u1*)p)[3] = x >> 24;
((u1*)p)[4] = x >> 32;
((u1*)p)[5] = x >> 40;
((u1*)p)[6] = x >> 48;
((u1*)p)[7] = x >> 56;
}
}
#else
static inline u2 get_native_u2(address p) { return get_Java_u2(p); }
static inline u4 get_native_u4(address p) { return get_Java_u4(p); }
static inline u8 get_native_u8(address p) { return get_Java_u8(p); }
static inline void put_native_u2(address p, u2 x) { put_Java_u2(p, x); }
static inline void put_native_u4(address p, u4 x) { put_Java_u4(p, x); }
static inline void put_native_u8(address p, u8 x) { put_Java_u8(p, x); }
#endif // VM_LITTLE_ENDIAN
// Efficient swapping of byte ordering
static inline u2 swap_u2(u2 x);
static inline u4 swap_u4(u4 x);
static inline u8 swap_u8(u8 x);
};
// The following header contains the implementations of swap_u2, swap_u4, and swap_u8
#include OS_CPU_HEADER_INLINE(bytes)
#endif // CPU_ARM_VM_BYTES_ARM_HPP

View File

@ -0,0 +1,510 @@
/*
* Copyright (c) 2008, 2015, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "asm/macroAssembler.hpp"
#include "c1/c1_CodeStubs.hpp"
#include "c1/c1_FrameMap.hpp"
#include "c1/c1_LIRAssembler.hpp"
#include "c1/c1_MacroAssembler.hpp"
#include "c1/c1_Runtime1.hpp"
#include "nativeInst_arm.hpp"
#include "runtime/sharedRuntime.hpp"
#include "utilities/macros.hpp"
#include "vmreg_arm.inline.hpp"
#if INCLUDE_ALL_GCS
#include "gc/g1/g1SATBCardTableModRefBS.hpp"
#endif // INCLUDE_ALL_GCS
#define __ ce->masm()->
void CounterOverflowStub::emit_code(LIR_Assembler* ce) {
__ bind(_entry);
ce->store_parameter(_bci, 0);
ce->store_parameter(_method->as_constant_ptr()->as_metadata(), 1);
__ call(Runtime1::entry_for(Runtime1::counter_overflow_id), relocInfo::runtime_call_type);
ce->add_call_info_here(_info);
ce->verify_oop_map(_info);
__ b(_continuation);
}
// TODO: ARM - is it possible to inline these stubs into the main code stream?
RangeCheckStub::RangeCheckStub(CodeEmitInfo* info, LIR_Opr index,
bool throw_index_out_of_bounds_exception)
: _throw_index_out_of_bounds_exception(throw_index_out_of_bounds_exception)
, _index(index)
{
_info = info == NULL ? NULL : new CodeEmitInfo(info);
}
void RangeCheckStub::emit_code(LIR_Assembler* ce) {
__ bind(_entry);
if (_info->deoptimize_on_exception()) {
#ifdef AARCH64
__ NOT_TESTED();
#endif
__ call(Runtime1::entry_for(Runtime1::predicate_failed_trap_id), relocInfo::runtime_call_type);
ce->add_call_info_here(_info);
ce->verify_oop_map(_info);
debug_only(__ should_not_reach_here());
return;
}
// Pass the array index on stack because all registers must be preserved
ce->verify_reserved_argument_area_size(1);
if (_index->is_cpu_register()) {
__ str_32(_index->as_register(), Address(SP));
} else {
__ mov_slow(Rtemp, _index->as_jint()); // Rtemp should be OK in C1
__ str_32(Rtemp, Address(SP));
}
if (_throw_index_out_of_bounds_exception) {
#ifdef AARCH64
__ NOT_TESTED();
#endif
__ call(Runtime1::entry_for(Runtime1::throw_index_exception_id), relocInfo::runtime_call_type);
} else {
__ call(Runtime1::entry_for(Runtime1::throw_range_check_failed_id), relocInfo::runtime_call_type);
}
ce->add_call_info_here(_info);
ce->verify_oop_map(_info);
DEBUG_ONLY(STOP("RangeCheck");)
}
PredicateFailedStub::PredicateFailedStub(CodeEmitInfo* info) {
_info = new CodeEmitInfo(info);
}
void PredicateFailedStub::emit_code(LIR_Assembler* ce) {
__ bind(_entry);
__ call(Runtime1::entry_for(Runtime1::predicate_failed_trap_id), relocInfo::runtime_call_type);
ce->add_call_info_here(_info);
ce->verify_oop_map(_info);
debug_only(__ should_not_reach_here());
}
void DivByZeroStub::emit_code(LIR_Assembler* ce) {
if (_offset != -1) {
ce->compilation()->implicit_exception_table()->append(_offset, __ offset());
}
__ bind(_entry);
__ call(Runtime1::entry_for(Runtime1::throw_div0_exception_id),
relocInfo::runtime_call_type);
ce->add_call_info_here(_info);
DEBUG_ONLY(STOP("DivByZero");)
}
// Implementation of NewInstanceStub
NewInstanceStub::NewInstanceStub(LIR_Opr klass_reg, LIR_Opr result, ciInstanceKlass* klass, CodeEmitInfo* info, Runtime1::StubID stub_id) {
_result = result;
_klass = klass;
_klass_reg = klass_reg;
_info = new CodeEmitInfo(info);
assert(stub_id == Runtime1::new_instance_id ||
stub_id == Runtime1::fast_new_instance_id ||
stub_id == Runtime1::fast_new_instance_init_check_id,
"need new_instance id");
_stub_id = stub_id;
}
void NewInstanceStub::emit_code(LIR_Assembler* ce) {
assert(_result->as_register() == R0, "runtime call setup");
assert(_klass_reg->as_register() == R1, "runtime call setup");
__ bind(_entry);
__ call(Runtime1::entry_for(_stub_id), relocInfo::runtime_call_type);
ce->add_call_info_here(_info);
ce->verify_oop_map(_info);
__ b(_continuation);
}
// Implementation of NewTypeArrayStub
NewTypeArrayStub::NewTypeArrayStub(LIR_Opr klass_reg, LIR_Opr length, LIR_Opr result, CodeEmitInfo* info) {
_klass_reg = klass_reg;
_length = length;
_result = result;
_info = new CodeEmitInfo(info);
}
void NewTypeArrayStub::emit_code(LIR_Assembler* ce) {
assert(_result->as_register() == R0, "runtime call setup");
assert(_klass_reg->as_register() == R1, "runtime call setup");
assert(_length->as_register() == R2, "runtime call setup");
__ bind(_entry);
__ call(Runtime1::entry_for(Runtime1::new_type_array_id), relocInfo::runtime_call_type);
ce->add_call_info_here(_info);
ce->verify_oop_map(_info);
__ b(_continuation);
}
// Implementation of NewObjectArrayStub
NewObjectArrayStub::NewObjectArrayStub(LIR_Opr klass_reg, LIR_Opr length, LIR_Opr result, CodeEmitInfo* info) {
_klass_reg = klass_reg;
_result = result;
_length = length;
_info = new CodeEmitInfo(info);
}
void NewObjectArrayStub::emit_code(LIR_Assembler* ce) {
assert(_result->as_register() == R0, "runtime call setup");
assert(_klass_reg->as_register() == R1, "runtime call setup");
assert(_length->as_register() == R2, "runtime call setup");
__ bind(_entry);
__ call(Runtime1::entry_for(Runtime1::new_object_array_id), relocInfo::runtime_call_type);
ce->add_call_info_here(_info);
ce->verify_oop_map(_info);
__ b(_continuation);
}
// Implementation of MonitorAccessStubs
MonitorEnterStub::MonitorEnterStub(LIR_Opr obj_reg, LIR_Opr lock_reg, CodeEmitInfo* info)
: MonitorAccessStub(obj_reg, lock_reg)
{
_info = new CodeEmitInfo(info);
}
void MonitorEnterStub::emit_code(LIR_Assembler* ce) {
__ bind(_entry);
const Register obj_reg = _obj_reg->as_pointer_register();
const Register lock_reg = _lock_reg->as_pointer_register();
ce->verify_reserved_argument_area_size(2);
#ifdef AARCH64
__ stp(obj_reg, lock_reg, Address(SP));
#else
if (obj_reg < lock_reg) {
__ stmia(SP, RegisterSet(obj_reg) | RegisterSet(lock_reg));
} else {
__ str(obj_reg, Address(SP));
__ str(lock_reg, Address(SP, BytesPerWord));
}
#endif // AARCH64
Runtime1::StubID enter_id = ce->compilation()->has_fpu_code() ?
Runtime1::monitorenter_id :
Runtime1::monitorenter_nofpu_id;
__ call(Runtime1::entry_for(enter_id), relocInfo::runtime_call_type);
ce->add_call_info_here(_info);
ce->verify_oop_map(_info);
__ b(_continuation);
}
void MonitorExitStub::emit_code(LIR_Assembler* ce) {
__ bind(_entry);
if (_compute_lock) {
ce->monitor_address(_monitor_ix, _lock_reg);
}
const Register lock_reg = _lock_reg->as_pointer_register();
ce->verify_reserved_argument_area_size(1);
__ str(lock_reg, Address(SP));
// Non-blocking leaf routine - no call info needed
Runtime1::StubID exit_id = ce->compilation()->has_fpu_code() ?
Runtime1::monitorexit_id :
Runtime1::monitorexit_nofpu_id;
__ call(Runtime1::entry_for(exit_id), relocInfo::runtime_call_type);
__ b(_continuation);
}
// Call return is directly after patch word
int PatchingStub::_patch_info_offset = 0;
void PatchingStub::align_patch_site(MacroAssembler* masm) {
#if 0
// TODO: investigate if we required to implement this
ShouldNotReachHere();
#endif
}
void PatchingStub::emit_code(LIR_Assembler* ce) {
const int patchable_instruction_offset = AARCH64_ONLY(NativeInstruction::instruction_size) NOT_AARCH64(0);
assert(NativeCall::instruction_size <= _bytes_to_copy && _bytes_to_copy <= 0xFF,
"not enough room for call");
assert((_bytes_to_copy & 3) == 0, "must copy a multiple of four bytes");
Label call_patch;
bool is_load = (_id == load_klass_id) || (_id == load_mirror_id) || (_id == load_appendix_id);
#ifdef AARCH64
assert(nativeInstruction_at(_pc_start)->is_nop(), "required for MT safe patching");
// Same alignment of reg2mem code and PatchingStub code. Required to make copied bind_literal() code properly aligned.
__ align(wordSize);
#endif // AARCH64
if (is_load NOT_AARCH64(&& !VM_Version::supports_movw())) {
address start = __ pc();
// The following sequence duplicates code provided in MacroAssembler::patchable_mov_oop()
// without creating relocation info entry.
#ifdef AARCH64
// Extra nop for MT safe patching
__ nop();
#endif // AARCH64
assert((__ pc() - start) == patchable_instruction_offset, "should be");
#ifdef AARCH64
__ ldr(_obj, __ pc());
#else
__ ldr(_obj, Address(PC));
// Extra nop to handle case of large offset of oop placeholder (see NativeMovConstReg::set_data).
__ nop();
#endif // AARCH64
#ifdef ASSERT
for (int i = 0; i < _bytes_to_copy; i++) {
assert(((address)_pc_start)[i] == start[i], "should be the same code");
}
#endif // ASSERT
}
address being_initialized_entry = __ pc();
if (CommentedAssembly) {
__ block_comment(" patch template");
}
if (is_load) {
address start = __ pc();
if (_id == load_mirror_id || _id == load_appendix_id) {
__ patchable_mov_oop(_obj, (jobject)Universe::non_oop_word(), _index);
} else {
__ patchable_mov_metadata(_obj, (Metadata*)Universe::non_oop_word(), _index);
}
#ifdef ASSERT
for (int i = 0; i < _bytes_to_copy; i++) {
assert(((address)_pc_start)[i] == start[i], "should be the same code");
}
#endif // ASSERT
} else {
int* start = (int*)_pc_start;
int* end = start + (_bytes_to_copy / BytesPerInt);
while (start < end) {
__ emit_int32(*start++);
}
}
address end_of_patch = __ pc();
int bytes_to_skip = 0;
if (_id == load_mirror_id) {
int offset = __ offset();
if (CommentedAssembly) {
__ block_comment(" being_initialized check");
}
assert(_obj != noreg, "must be a valid register");
// Rtemp should be OK in C1
__ ldr(Rtemp, Address(_obj, java_lang_Class::klass_offset_in_bytes()));
__ ldr(Rtemp, Address(Rtemp, InstanceKlass::init_thread_offset()));
__ cmp(Rtemp, Rthread);
__ b(call_patch, ne);
__ b(_patch_site_continuation);
bytes_to_skip += __ offset() - offset;
}
if (CommentedAssembly) {
__ block_comment("patch data - 3 high bytes of the word");
}
const int sizeof_patch_record = 4;
bytes_to_skip += sizeof_patch_record;
int being_initialized_entry_offset = __ pc() - being_initialized_entry + sizeof_patch_record;
__ emit_int32(0xff | being_initialized_entry_offset << 8 | bytes_to_skip << 16 | _bytes_to_copy << 24);
address patch_info_pc = __ pc();
assert(patch_info_pc - end_of_patch == bytes_to_skip, "incorrect patch info");
// runtime call will return here
Label call_return;
__ bind(call_return);
ce->add_call_info_here(_info);
assert(_patch_info_offset == (patch_info_pc - __ pc()), "must not change");
__ b(_patch_site_entry);
address entry = __ pc();
NativeGeneralJump::insert_unconditional((address)_pc_start, entry);
address target = NULL;
relocInfo::relocType reloc_type = relocInfo::none;
switch (_id) {
case access_field_id: target = Runtime1::entry_for(Runtime1::access_field_patching_id); break;
case load_klass_id: target = Runtime1::entry_for(Runtime1::load_klass_patching_id); reloc_type = relocInfo::metadata_type; break;
case load_mirror_id: target = Runtime1::entry_for(Runtime1::load_mirror_patching_id); reloc_type = relocInfo::oop_type; break;
case load_appendix_id: target = Runtime1::entry_for(Runtime1::load_appendix_patching_id); reloc_type = relocInfo::oop_type; break;
default: ShouldNotReachHere();
}
__ bind(call_patch);
if (CommentedAssembly) {
__ block_comment("patch entry point");
}
// arrange for call to return just after patch word
__ adr(LR, call_return);
__ jump(target, relocInfo::runtime_call_type, Rtemp);
if (is_load) {
CodeSection* cs = __ code_section();
address pc = (address)_pc_start;
RelocIterator iter(cs, pc, pc + 1);
relocInfo::change_reloc_info_for_address(&iter, pc, reloc_type, relocInfo::none);
}
}
void DeoptimizeStub::emit_code(LIR_Assembler* ce) {
__ bind(_entry);
__ mov_slow(Rtemp, _trap_request);
ce->verify_reserved_argument_area_size(1);
__ str(Rtemp, Address(SP));
__ call(Runtime1::entry_for(Runtime1::deoptimize_id), relocInfo::runtime_call_type);
ce->add_call_info_here(_info);
DEBUG_ONLY(__ should_not_reach_here());
}
void ImplicitNullCheckStub::emit_code(LIR_Assembler* ce) {
address a;
if (_info->deoptimize_on_exception()) {
// Deoptimize, do not throw the exception, because it is
// probably wrong to do it here.
a = Runtime1::entry_for(Runtime1::predicate_failed_trap_id);
} else {
a = Runtime1::entry_for(Runtime1::throw_null_pointer_exception_id);
}
ce->compilation()->implicit_exception_table()->append(_offset, __ offset());
__ bind(_entry);
__ call(a, relocInfo::runtime_call_type);
ce->add_call_info_here(_info);
ce->verify_oop_map(_info);
DEBUG_ONLY(STOP("ImplicitNullCheck");)
}
void SimpleExceptionStub::emit_code(LIR_Assembler* ce) {
__ bind(_entry);
// Pass the object on stack because all registers must be preserved
if (_obj->is_cpu_register()) {
ce->verify_reserved_argument_area_size(1);
__ str(_obj->as_pointer_register(), Address(SP));
} else {
assert(_obj->is_illegal(), "should be");
}
__ call(Runtime1::entry_for(_stub), relocInfo::runtime_call_type);
ce->add_call_info_here(_info);
DEBUG_ONLY(STOP("SimpleException");)
}
void ArrayCopyStub::emit_code(LIR_Assembler* ce) {
__ bind(_entry);
VMRegPair args[5];
BasicType signature[5] = { T_OBJECT, T_INT, T_OBJECT, T_INT, T_INT };
SharedRuntime::java_calling_convention(signature, args, 5, true);
Register r[5];
r[0] = src()->as_pointer_register();
r[1] = src_pos()->as_register();
r[2] = dst()->as_pointer_register();
r[3] = dst_pos()->as_register();
r[4] = length()->as_register();
for (int i = 0; i < 5; i++) {
VMReg arg = args[i].first();
if (arg->is_stack()) {
__ str(r[i], Address(SP, arg->reg2stack() * VMRegImpl::stack_slot_size));
} else {
assert(r[i] == arg->as_Register(), "Calling conventions must match");
}
}
ce->emit_static_call_stub();
if (ce->compilation()->bailed_out()) {
return; // CodeCache is full
}
int ret_addr_offset = __ patchable_call(SharedRuntime::get_resolve_static_call_stub(), relocInfo::static_call_type);
assert(ret_addr_offset == __ offset(), "embedded return address not allowed");
ce->add_call_info_here(info());
ce->verify_oop_map(info());
__ b(_continuation);
}
/////////////////////////////////////////////////////////////////////////////
#if INCLUDE_ALL_GCS
void G1PreBarrierStub::emit_code(LIR_Assembler* ce) {
// At this point we know that marking is in progress.
// If do_load() is true then we have to emit the
// load of the previous value; otherwise it has already
// been loaded into _pre_val.
__ bind(_entry);
assert(pre_val()->is_register(), "Precondition.");
Register pre_val_reg = pre_val()->as_register();
if (do_load()) {
ce->mem2reg(addr(), pre_val(), T_OBJECT, patch_code(), info(), false /*wide*/, false /*unaligned*/);
}
__ cbz(pre_val_reg, _continuation);
ce->verify_reserved_argument_area_size(1);
__ str(pre_val_reg, Address(SP));
__ call(Runtime1::entry_for(Runtime1::g1_pre_barrier_slow_id), relocInfo::runtime_call_type);
__ b(_continuation);
}
void G1PostBarrierStub::emit_code(LIR_Assembler* ce) {
__ bind(_entry);
assert(addr()->is_register(), "Precondition.");
assert(new_val()->is_register(), "Precondition.");
Register new_val_reg = new_val()->as_register();
__ cbz(new_val_reg, _continuation);
ce->verify_reserved_argument_area_size(1);
__ str(addr()->as_pointer_register(), Address(SP));
__ call(Runtime1::entry_for(Runtime1::g1_post_barrier_slow_id), relocInfo::runtime_call_type);
__ b(_continuation);
}
#endif // INCLUDE_ALL_GCS
/////////////////////////////////////////////////////////////////////////////
#undef __

View File

@ -0,0 +1,85 @@
/*
* Copyright (c) 2008, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_C1_DEFS_ARM_HPP
#define CPU_ARM_VM_C1_DEFS_ARM_HPP
// native word offsets from memory address (little endian)
enum {
pd_lo_word_offset_in_bytes = 0,
pd_hi_word_offset_in_bytes = BytesPerWord
};
// explicit rounding operations are required to implement the strictFP mode
enum {
pd_strict_fp_requires_explicit_rounding = false
};
#ifdef __SOFTFP__
#define SOFT(n) n
#define VFP(n)
#else // __SOFTFP__
#define SOFT(n)
#define VFP(n) n
#endif // __SOFTFP__
// registers
enum {
pd_nof_cpu_regs_frame_map = AARCH64_ONLY(33) NOT_AARCH64(16), // number of registers used during code emission
pd_nof_caller_save_cpu_regs_frame_map = AARCH64_ONLY(27) NOT_AARCH64(10), // number of registers killed by calls
pd_nof_cpu_regs_reg_alloc = AARCH64_ONLY(27) NOT_AARCH64(10), // number of registers that are visible to register allocator (including Rheap_base which is visible only if compressed pointers are not enabled)
pd_nof_cpu_regs_linearscan = pd_nof_cpu_regs_frame_map, // number of registers visible to linear scan
pd_nof_cpu_regs_processed_in_linearscan = pd_nof_cpu_regs_reg_alloc + 1, // number of registers processed in linear scan; includes LR as it is used as temporary register in c1_LIRGenerator_arm
pd_first_cpu_reg = 0,
pd_last_cpu_reg = pd_nof_cpu_regs_frame_map - 1,
pd_nof_fpu_regs_frame_map = VFP(32) SOFT(0), // number of float registers used during code emission
pd_nof_caller_save_fpu_regs_frame_map = VFP(32) SOFT(0), // number of float registers killed by calls
pd_nof_fpu_regs_reg_alloc = AARCH64_ONLY(32) NOT_AARCH64(VFP(30) SOFT(0)), // number of float registers that are visible to register allocator
pd_nof_fpu_regs_linearscan = pd_nof_fpu_regs_frame_map, // number of float registers visible to linear scan
pd_first_fpu_reg = pd_nof_cpu_regs_frame_map,
pd_last_fpu_reg = pd_first_fpu_reg + pd_nof_fpu_regs_frame_map - 1,
pd_nof_xmm_regs_linearscan = 0,
pd_nof_caller_save_xmm_regs = 0,
pd_first_xmm_reg = -1,
pd_last_xmm_reg = -1
};
// encoding of float value in debug info:
enum {
pd_float_saved_as_double = false
};
#ifdef AARCH64
#define PATCHED_ADDR 0xff8
#else
#define PATCHED_ADDR (204)
#endif
#define CARDTABLEMODREF_POST_BARRIER_HELPER
#define GENERATE_ADDRESS_IS_PREFERRED
#endif // CPU_ARM_VM_C1_DEFS_ARM_HPP

View File

@ -0,0 +1,31 @@
/*
* Copyright (c) 2008, 2011, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "c1/c1_FpuStackSim.hpp"
#include "c1/c1_FrameMap.hpp"
#include "utilities/array.hpp"
#include "utilities/ostream.hpp"
// Nothing needed here

View File

@ -0,0 +1,30 @@
/*
* Copyright (c) 2008, 2011, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_C1_FPUSTACKSIM_ARM_HPP
#define CPU_ARM_VM_C1_FPUSTACKSIM_ARM_HPP
// Nothing needed here
#endif // CPU_ARM_VM_C1_FPUSTACKSIM_ARM_HPP

View File

@ -0,0 +1,230 @@
/*
* Copyright (c) 2008, 2015, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "c1/c1_FrameMap.hpp"
#include "c1/c1_LIR.hpp"
#include "runtime/sharedRuntime.hpp"
#include "vmreg_arm.inline.hpp"
LIR_Opr FrameMap::R0_opr;
LIR_Opr FrameMap::R1_opr;
LIR_Opr FrameMap::R2_opr;
LIR_Opr FrameMap::R3_opr;
LIR_Opr FrameMap::R4_opr;
LIR_Opr FrameMap::R5_opr;
LIR_Opr FrameMap::R0_oop_opr;
LIR_Opr FrameMap::R1_oop_opr;
LIR_Opr FrameMap::R2_oop_opr;
LIR_Opr FrameMap::R3_oop_opr;
LIR_Opr FrameMap::R4_oop_opr;
LIR_Opr FrameMap::R5_oop_opr;
LIR_Opr FrameMap::R0_metadata_opr;
LIR_Opr FrameMap::R1_metadata_opr;
LIR_Opr FrameMap::R2_metadata_opr;
LIR_Opr FrameMap::R3_metadata_opr;
LIR_Opr FrameMap::R4_metadata_opr;
LIR_Opr FrameMap::R5_metadata_opr;
#ifdef AARCH64
LIR_Opr FrameMap::ZR_opr;
#endif // AARCH64
LIR_Opr FrameMap::LR_opr;
LIR_Opr FrameMap::LR_oop_opr;
LIR_Opr FrameMap::LR_ptr_opr;
LIR_Opr FrameMap::FP_opr;
LIR_Opr FrameMap::SP_opr;
LIR_Opr FrameMap::Rthread_opr;
LIR_Opr FrameMap::Int_result_opr;
LIR_Opr FrameMap::Long_result_opr;
LIR_Opr FrameMap::Object_result_opr;
LIR_Opr FrameMap::Float_result_opr;
LIR_Opr FrameMap::Double_result_opr;
LIR_Opr FrameMap::Exception_oop_opr;
LIR_Opr FrameMap::Exception_pc_opr;
LIR_Opr FrameMap::_caller_save_cpu_regs[] = { 0 };
LIR_Opr FrameMap::_caller_save_fpu_regs[]; // same as initialize to zero
LIR_Opr FrameMap::map_to_opr(BasicType type, VMRegPair* reg, bool) {
LIR_Opr opr = LIR_OprFact::illegalOpr;
VMReg r_1 = reg->first();
VMReg r_2 = reg->second();
if (r_1->is_stack()) {
int st_off = (r_1->reg2stack() + SharedRuntime::out_preserve_stack_slots()) * VMRegImpl::stack_slot_size;
opr = LIR_OprFact::address(new LIR_Address(SP_opr, st_off, type));
} else if (r_1->is_Register()) {
Register reg = r_1->as_Register();
if (r_2->is_Register() && (type == T_LONG || type == T_DOUBLE)) {
#ifdef AARCH64
assert(r_1->next() == r_2, "should be the same");
opr = as_long_opr(reg);
#else
opr = as_long_opr(reg, r_2->as_Register());
#endif
} else if (type == T_OBJECT || type == T_ARRAY) {
opr = as_oop_opr(reg);
} else if (type == T_METADATA) {
opr = as_metadata_opr(reg);
} else {
// PreferInterpreterNativeStubs should ensure we never need to
// handle a long opr passed as R3+stack_slot
assert(! r_2->is_stack(), "missing support for ALIGN_WIDE_ARGUMENTS==0");
opr = as_opr(reg);
}
} else if (r_1->is_FloatRegister()) {
FloatRegister reg = r_1->as_FloatRegister();
opr = type == T_FLOAT ? as_float_opr(reg) : as_double_opr(reg);
} else {
ShouldNotReachHere();
}
return opr;
}
void FrameMap::initialize() {
if (_init_done) return;
int i;
int rnum = 0;
// Registers used for allocation
#ifdef AARCH64
assert(Rthread == R28 && Rheap_base == R27 && Rtemp == R16, "change the code here");
for (i = 0; i < 16; i++) {
map_register(rnum++, as_Register(i));
}
for (i = 17; i < 28; i++) {
map_register(rnum++, as_Register(i));
}
#else
assert(Rthread == R10 && Rtemp == R12, "change the code here");
for (i = 0; i < 10; i++) {
map_register(rnum++, as_Register(i));
}
#endif // AARCH64
assert(rnum == pd_nof_cpu_regs_reg_alloc, "should be");
// Registers not used for allocation
map_register(rnum++, LR); // LR register should be listed first, see c1_LinearScan_arm.hpp::is_processed_reg_num.
assert(rnum == pd_nof_cpu_regs_processed_in_linearscan, "should be");
map_register(rnum++, Rtemp);
map_register(rnum++, Rthread);
map_register(rnum++, FP); // ARM32: R7 or R11
map_register(rnum++, SP);
#ifdef AARCH64
map_register(rnum++, ZR);
#else
map_register(rnum++, PC);
#endif
assert(rnum == pd_nof_cpu_regs_frame_map, "should be");
_init_done = true;
R0_opr = as_opr(R0); R0_oop_opr = as_oop_opr(R0); R0_metadata_opr = as_metadata_opr(R0);
R1_opr = as_opr(R1); R1_oop_opr = as_oop_opr(R1); R1_metadata_opr = as_metadata_opr(R1);
R2_opr = as_opr(R2); R2_oop_opr = as_oop_opr(R2); R2_metadata_opr = as_metadata_opr(R2);
R3_opr = as_opr(R3); R3_oop_opr = as_oop_opr(R3); R3_metadata_opr = as_metadata_opr(R3);
R4_opr = as_opr(R4); R4_oop_opr = as_oop_opr(R4); R4_metadata_opr = as_metadata_opr(R4);
R5_opr = as_opr(R5); R5_oop_opr = as_oop_opr(R5); R5_metadata_opr = as_metadata_opr(R5);
#ifdef AARCH64
ZR_opr = as_opr(ZR);
#endif // AARCH64
LR_opr = as_opr(LR);
LR_oop_opr = as_oop_opr(LR);
LR_ptr_opr = as_pointer_opr(LR);
FP_opr = as_pointer_opr(FP);
SP_opr = as_pointer_opr(SP);
Rthread_opr = as_pointer_opr(Rthread);
// LIR operands for result
Int_result_opr = R0_opr;
Object_result_opr = R0_oop_opr;
#ifdef AARCH64
Long_result_opr = as_long_opr(R0);
Float_result_opr = as_float_opr(S0);
Double_result_opr = as_double_opr(D0);
#else
Long_result_opr = as_long_opr(R0, R1);
#ifdef __ABI_HARD__
Float_result_opr = as_float_opr(S0);
Double_result_opr = as_double_opr(D0);
#else
Float_result_opr = LIR_OprFact::single_softfp(0);
Double_result_opr = LIR_OprFact::double_softfp(0, 1);
#endif // __ABI_HARD__
#endif // AARCH64
Exception_oop_opr = as_oop_opr(Rexception_obj);
Exception_pc_opr = as_opr(Rexception_pc);
for (i = 0; i < nof_caller_save_cpu_regs(); i++) {
_caller_save_cpu_regs[i] = LIR_OprFact::single_cpu(i);
}
for (i = 0; i < nof_caller_save_fpu_regs; i++) {
_caller_save_fpu_regs[i] = LIR_OprFact::single_fpu(i);
}
}
Address FrameMap::make_new_address(ByteSize sp_offset) const {
return Address(SP, sp_offset);
}
LIR_Opr FrameMap::stack_pointer() {
return FrameMap::SP_opr;
}
LIR_Opr FrameMap::method_handle_invoke_SP_save_opr() {
assert(Rmh_SP_save == FP, "Fix register used for saving SP for MethodHandle calls");
return FP_opr;
}
bool FrameMap::validate_frame() {
int max_offset = in_bytes(framesize_in_bytes());
int java_index = 0;
for (int i = 0; i < _incoming_arguments->length(); i++) {
LIR_Opr opr = _incoming_arguments->at(i);
if (opr->is_stack()) {
int arg_offset = _argument_locations->at(java_index);
if (arg_offset > max_offset) {
max_offset = arg_offset;
}
}
java_index += type2size[opr->type()];
}
return max_offset < AARCH64_ONLY(16384) NOT_AARCH64(4096); // TODO-AARCH64 check that LIRAssembler does not generate load/store of byte and half-word with SP as address base
}
VMReg FrameMap::fpu_regname(int n) {
return as_FloatRegister(n)->as_VMReg();
}

View File

@ -0,0 +1,128 @@
/*
* Copyright (c) 2008, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_C1_FRAMEMAP_ARM_HPP
#define CPU_ARM_VM_C1_FRAMEMAP_ARM_HPP
public:
enum {
first_available_sp_in_frame = 0,
frame_pad_in_bytes = 2*wordSize // Account for FP/LR saved at build_frame().
};
static LIR_Opr R0_opr;
static LIR_Opr R1_opr;
static LIR_Opr R2_opr;
static LIR_Opr R3_opr;
static LIR_Opr R4_opr;
static LIR_Opr R5_opr;
// add more predefined register oprs as needed
static LIR_Opr R0_oop_opr;
static LIR_Opr R1_oop_opr;
static LIR_Opr R2_oop_opr;
static LIR_Opr R3_oop_opr;
static LIR_Opr R4_oop_opr;
static LIR_Opr R5_oop_opr;
static LIR_Opr R0_metadata_opr;
static LIR_Opr R1_metadata_opr;
static LIR_Opr R2_metadata_opr;
static LIR_Opr R3_metadata_opr;
static LIR_Opr R4_metadata_opr;
static LIR_Opr R5_metadata_opr;
#ifdef AARCH64
static LIR_Opr ZR_opr;
#endif // AARCH64
static LIR_Opr LR_opr;
static LIR_Opr LR_oop_opr;
static LIR_Opr LR_ptr_opr;
static LIR_Opr FP_opr;
static LIR_Opr SP_opr;
static LIR_Opr Rthread_opr;
static LIR_Opr Int_result_opr;
static LIR_Opr Long_result_opr;
static LIR_Opr Object_result_opr;
static LIR_Opr Float_result_opr;
static LIR_Opr Double_result_opr;
static LIR_Opr Exception_oop_opr;
static LIR_Opr Exception_pc_opr;
#ifdef AARCH64
static LIR_Opr as_long_opr(Register r) {
return LIR_OprFact::double_cpu(cpu_reg2rnr(r), cpu_reg2rnr(r));
}
static LIR_Opr as_pointer_opr(Register r) {
return LIR_OprFact::double_cpu(cpu_reg2rnr(r), cpu_reg2rnr(r));
}
static LIR_Opr as_double_opr(FloatRegister r) {
return LIR_OprFact::double_fpu(r->encoding());
}
#else
static LIR_Opr as_long_opr(Register r, Register r2) {
return LIR_OprFact::double_cpu(cpu_reg2rnr(r), cpu_reg2rnr(r2));
}
static LIR_Opr as_pointer_opr(Register r) {
return LIR_OprFact::single_cpu(cpu_reg2rnr(r));
}
static LIR_Opr as_double_opr(FloatRegister r) {
return LIR_OprFact::double_fpu(r->encoding(), r->successor()->encoding());
}
#endif
static LIR_Opr as_float_opr(FloatRegister r) {
return LIR_OprFact::single_fpu(r->encoding());
}
static VMReg fpu_regname(int n);
static bool is_caller_save_register(LIR_Opr opr) {
return true;
}
static int adjust_reg_range(int range) {
// Reduce the number of available regs (to free Rheap_base) in case of compressed oops
if (UseCompressedOops || UseCompressedClassPointers) return range - 1;
return range;
}
static int nof_caller_save_cpu_regs() {
return adjust_reg_range(pd_nof_caller_save_cpu_regs_frame_map);
}
static int last_cpu_reg() {
return pd_last_cpu_reg;
}
#endif // CPU_ARM_VM_C1_FRAMEMAP_ARM_HPP

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,71 @@
/*
* Copyright (c) 2008, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_C1_LIRASSEMBLER_ARM_HPP
#define CPU_ARM_VM_C1_LIRASSEMBLER_ARM_HPP
private:
// Record the type of the receiver in ReceiverTypeData
void type_profile_helper(Register mdo, int mdo_offset_bias,
ciMethodData *md, ciProfileData *data,
Register recv, Register tmp1, Label* update_done);
// Setup pointers to MDO, MDO slot, also compute offset bias to access the slot.
void setup_md_access(ciMethod* method, int bci,
ciMethodData*& md, ciProfileData*& data, int& mdo_offset_bias);
void typecheck_profile_helper1(ciMethod* method, int bci,
ciMethodData*& md, ciProfileData*& data, int& mdo_offset_bias,
Register obj, Register mdo, Register data_val, Label* obj_is_null);
void typecheck_profile_helper2(ciMethodData* md, ciProfileData* data, int mdo_offset_bias,
Register mdo, Register recv, Register value, Register tmp1,
Label* profile_cast_success, Label* profile_cast_failure,
Label* success, Label* failure);
#ifdef AARCH64
void long_compare_helper(LIR_Opr opr1, LIR_Opr opr2);
#endif // AARCH64
// Saves 4 given registers in reserved argument area.
void save_in_reserved_area(Register r1, Register r2, Register r3, Register r4);
// Restores 4 given registers from reserved argument area.
void restore_from_reserved_area(Register r1, Register r2, Register r3, Register r4);
enum {
_call_stub_size = AARCH64_ONLY(32) NOT_AARCH64(16),
_call_aot_stub_size = 0,
_exception_handler_size = PRODUCT_ONLY(AARCH64_ONLY(256) NOT_AARCH64(68)) NOT_PRODUCT(AARCH64_ONLY(256+216) NOT_AARCH64(68+60)),
_deopt_handler_size = AARCH64_ONLY(32) NOT_AARCH64(16)
};
public:
void verify_reserved_argument_area_size(int args_count) PRODUCT_RETURN;
void store_parameter(jint c, int offset_from_sp_in_words);
void store_parameter(Metadata* m, int offset_from_sp_in_words);
#endif // CPU_ARM_VM_C1_LIRASSEMBLER_ARM_HPP

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,33 @@
/*
* Copyright (c) 2014, 2015, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
// Helper to set the card at the given address to the given value.
void set_card(LIR_Opr value, LIR_Address* card_addr);
void make_div_by_zero_check(LIR_Opr right_arg, BasicType type, CodeEmitInfo* info);
#ifdef AARCH64
// the helper for arithmetic
void add_constant(LIR_Opr src, jlong c, LIR_Opr dest);
#endif // AARCH64

View File

@ -0,0 +1,86 @@
/*
* Copyright (c) 2010, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "c1/c1_LIR.hpp"
FloatRegister LIR_OprDesc::as_float_reg() const {
return as_FloatRegister(fpu_regnr());
}
FloatRegister LIR_OprDesc::as_double_reg() const {
return as_FloatRegister(fpu_regnrLo());
}
#ifdef AARCH64
// Reg2 unused.
LIR_Opr LIR_OprFact::double_fpu(int reg1, int reg2) {
assert(as_FloatRegister(reg2) == fnoreg, "Not used on this platform");
return (LIR_Opr)(intptr_t)((reg1 << LIR_OprDesc::reg1_shift) |
(reg1 << LIR_OprDesc::reg2_shift) |
LIR_OprDesc::double_type |
LIR_OprDesc::fpu_register |
LIR_OprDesc::double_size);
}
#else
LIR_Opr LIR_OprFact::double_fpu(int reg1, int reg2) {
assert(as_FloatRegister(reg2) != fnoreg, "Arm32 holds double in two regs.");
return (LIR_Opr)(intptr_t)((reg1 << LIR_OprDesc::reg1_shift) |
(reg2 << LIR_OprDesc::reg2_shift) |
LIR_OprDesc::double_type |
LIR_OprDesc::fpu_register |
LIR_OprDesc::double_size);
}
#endif
#ifndef PRODUCT
void LIR_Address::verify() const {
#ifdef _LP64
assert(base()->is_cpu_register(), "wrong base operand");
#endif
#ifdef AARCH64
if (base()->type() == T_INT) {
assert(index()->is_single_cpu() && (index()->type() == T_INT), "wrong index operand");
} else {
assert(index()->is_illegal() || index()->is_double_cpu() ||
(index()->is_single_cpu() && (index()->is_oop_register() || index()->type() == T_INT)), "wrong index operand");
assert(base()->type() == T_OBJECT || base()->type() == T_LONG || base()->type() == T_METADATA, "wrong type for addresses");
}
#else
assert(disp() == 0 || index()->is_illegal(), "can't have both");
// Note: offsets higher than 4096 must not be rejected here. They can
// be handled by the back-end or will be rejected if not.
#ifdef _LP64
assert(index()->is_illegal() || index()->is_double_cpu(), "wrong index operand");
assert(base()->type() == T_OBJECT || base()->type() == T_LONG || base()->type() == T_METADATA,
"wrong type for addresses");
#else
assert(base()->is_single_cpu(), "wrong base operand");
assert(index()->is_illegal() || index()->is_single_cpu(), "wrong index operand");
assert(base()->type() == T_OBJECT || base()->type() == T_INT || base()->type() == T_METADATA,
"wrong type for addresses");
#endif
#endif // AARCH64
}
#endif // PRODUCT

View File

@ -0,0 +1,32 @@
/*
* Copyright (c) 2008, 2011, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "c1/c1_Instruction.hpp"
#include "c1/c1_LinearScan.hpp"
#include "utilities/bitMap.inline.hpp"
void LinearScan::allocate_fpu_stack() {
// No FPU stack on ARM
}

View File

@ -0,0 +1,78 @@
/*
* Copyright (c) 2008, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_C1_LINEARSCAN_ARM_HPP
#define CPU_ARM_VM_C1_LINEARSCAN_ARM_HPP
inline bool LinearScan::is_processed_reg_num(int reg_num) {
return reg_num < pd_nof_cpu_regs_processed_in_linearscan ||
reg_num >= pd_nof_cpu_regs_frame_map;
}
inline int LinearScan::num_physical_regs(BasicType type) {
#ifndef AARCH64
if (type == T_LONG || type == T_DOUBLE) return 2;
#endif // !AARCH64
return 1;
}
inline bool LinearScan::requires_adjacent_regs(BasicType type) {
#ifdef AARCH64
return false;
#else
return type == T_DOUBLE || type == T_LONG;
#endif // AARCH64
}
inline bool LinearScan::is_caller_save(int assigned_reg) {
assert(assigned_reg >= 0 && assigned_reg < nof_regs, "should call this only for registers");
// TODO-AARCH64 try to add callee-saved registers
return true;
}
inline void LinearScan::pd_add_temps(LIR_Op* op) {
// No extra temporals on ARM
}
// Implementation of LinearScanWalker
inline bool LinearScanWalker::pd_init_regs_for_alloc(Interval* cur) {
#ifndef __SOFTFP__
if (cur->type() == T_FLOAT || cur->type() == T_DOUBLE) {
_first_reg = pd_first_fpu_reg;
_last_reg = pd_first_fpu_reg + pd_nof_fpu_regs_reg_alloc - 1;
return true;
}
#endif // !__SOFTFP__
// Use allocatable CPU registers otherwise
_first_reg = pd_first_cpu_reg;
_last_reg = pd_first_cpu_reg + FrameMap::adjust_reg_range(pd_nof_cpu_regs_reg_alloc) - 1;
return true;
}
#endif // CPU_ARM_VM_C1_LINEARSCAN_ARM_HPP

View File

@ -0,0 +1,408 @@
/*
* Copyright (c) 2008, 2015, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "c1/c1_MacroAssembler.hpp"
#include "c1/c1_Runtime1.hpp"
#include "classfile/systemDictionary.hpp"
#include "gc/shared/collectedHeap.hpp"
#include "interpreter/interpreter.hpp"
#include "oops/arrayOop.hpp"
#include "oops/markOop.hpp"
#include "runtime/basicLock.hpp"
#include "runtime/biasedLocking.hpp"
#include "runtime/os.hpp"
#include "runtime/sharedRuntime.hpp"
#include "runtime/stubRoutines.hpp"
// Note: Rtemp usage is this file should not impact C2 and should be
// correct as long as it is not implicitly used in lower layers (the
// arm [macro]assembler) and used with care in the other C1 specific
// files.
void C1_MacroAssembler::inline_cache_check(Register receiver, Register iCache) {
Label verified;
load_klass(Rtemp, receiver);
cmp(Rtemp, iCache);
b(verified, eq); // jump over alignment no-ops
#ifdef AARCH64
jump(SharedRuntime::get_ic_miss_stub(), relocInfo::runtime_call_type, Rtemp);
#else
jump(SharedRuntime::get_ic_miss_stub(), relocInfo::runtime_call_type);
#endif
align(CodeEntryAlignment);
bind(verified);
}
void C1_MacroAssembler::build_frame(int frame_size_in_bytes, int bang_size_in_bytes) {
assert(bang_size_in_bytes >= frame_size_in_bytes, "stack bang size incorrect");
assert((frame_size_in_bytes % StackAlignmentInBytes) == 0, "frame size should be aligned");
#ifdef AARCH64
// Extra nop for MT-safe patching in NativeJump::patch_verified_entry
nop();
#endif // AARCH64
arm_stack_overflow_check(bang_size_in_bytes, Rtemp);
// FP can no longer be used to memorize SP. It may be modified
// if this method contains a methodHandle call site
raw_push(FP, LR);
sub_slow(SP, SP, frame_size_in_bytes);
}
void C1_MacroAssembler::remove_frame(int frame_size_in_bytes) {
add_slow(SP, SP, frame_size_in_bytes);
raw_pop(FP, LR);
}
void C1_MacroAssembler::verified_entry() {
if (C1Breakpoint) {
breakpoint();
}
}
// Puts address of allocated object into register `obj` and end of allocated object into register `obj_end`.
void C1_MacroAssembler::try_allocate(Register obj, Register obj_end, Register tmp1, Register tmp2,
RegisterOrConstant size_expression, Label& slow_case) {
if (UseTLAB) {
tlab_allocate(obj, obj_end, tmp1, size_expression, slow_case);
} else {
eden_allocate(obj, obj_end, tmp1, tmp2, size_expression, slow_case);
incr_allocated_bytes(size_expression, tmp1);
}
}
void C1_MacroAssembler::initialize_header(Register obj, Register klass, Register len, Register tmp) {
assert_different_registers(obj, klass, len, tmp);
if(UseBiasedLocking && !len->is_valid()) {
ldr(tmp, Address(klass, Klass::prototype_header_offset()));
} else {
mov(tmp, (intptr_t)markOopDesc::prototype());
}
#ifdef AARCH64
if (UseCompressedClassPointers) {
str(tmp, Address(obj, oopDesc::mark_offset_in_bytes()));
encode_klass_not_null(tmp, klass); // Take care not to kill klass
str_w(tmp, Address(obj, oopDesc::klass_offset_in_bytes()));
} else {
assert(oopDesc::mark_offset_in_bytes() + wordSize == oopDesc::klass_offset_in_bytes(), "adjust this code");
stp(tmp, klass, Address(obj, oopDesc::mark_offset_in_bytes()));
}
#else
str(tmp, Address(obj, oopDesc::mark_offset_in_bytes()));
str(klass, Address(obj, oopDesc::klass_offset_in_bytes()));
#endif // AARCH64
if (len->is_valid()) {
str_32(len, Address(obj, arrayOopDesc::length_offset_in_bytes()));
}
#ifdef AARCH64
else if (UseCompressedClassPointers) {
store_klass_gap(obj);
}
#endif // AARCH64
}
// Cleans object body [base..obj_end]. Clobbers `base` and `tmp` registers.
void C1_MacroAssembler::initialize_body(Register base, Register obj_end, Register tmp) {
zero_memory(base, obj_end, tmp);
}
void C1_MacroAssembler::initialize_object(Register obj, Register obj_end, Register klass,
Register len, Register tmp1, Register tmp2,
RegisterOrConstant header_size, int obj_size_in_bytes,
bool is_tlab_allocated)
{
assert_different_registers(obj, obj_end, klass, len, tmp1, tmp2);
initialize_header(obj, klass, len, tmp1);
const Register ptr = tmp2;
if (!(UseTLAB && ZeroTLAB && is_tlab_allocated)) {
#ifdef AARCH64
if (obj_size_in_bytes < 0) {
add_rc(ptr, obj, header_size);
initialize_body(ptr, obj_end, tmp1);
} else {
int base = instanceOopDesc::header_size() * HeapWordSize;
assert(obj_size_in_bytes >= base, "should be");
const int zero_bytes = obj_size_in_bytes - base;
assert((zero_bytes % wordSize) == 0, "should be");
if ((zero_bytes % (2*wordSize)) != 0) {
str(ZR, Address(obj, base));
base += wordSize;
}
const int stp_count = zero_bytes / (2*wordSize);
if (zero_bytes > 8 * wordSize) {
Label loop;
add(ptr, obj, base);
mov(tmp1, stp_count);
bind(loop);
subs(tmp1, tmp1, 1);
stp(ZR, ZR, Address(ptr, 2*wordSize, post_indexed));
b(loop, gt);
} else {
for (int i = 0; i < stp_count; i++) {
stp(ZR, ZR, Address(obj, base + i * 2 * wordSize));
}
}
}
#else
if (obj_size_in_bytes >= 0 && obj_size_in_bytes <= 8 * BytesPerWord) {
mov(tmp1, 0);
const int base = instanceOopDesc::header_size() * HeapWordSize;
for (int i = base; i < obj_size_in_bytes; i += wordSize) {
str(tmp1, Address(obj, i));
}
} else {
assert(header_size.is_constant() || header_size.as_register() == ptr, "code assumption");
add(ptr, obj, header_size);
initialize_body(ptr, obj_end, tmp1);
}
#endif // AARCH64
}
// StoreStore barrier required after complete initialization
// (headers + content zeroing), before the object may escape.
membar(MacroAssembler::StoreStore, tmp1);
}
void C1_MacroAssembler::allocate_object(Register obj, Register tmp1, Register tmp2, Register tmp3,
int header_size, int object_size,
Register klass, Label& slow_case) {
assert_different_registers(obj, tmp1, tmp2, tmp3, klass, Rtemp);
assert(header_size >= 0 && object_size >= header_size, "illegal sizes");
const int object_size_in_bytes = object_size * BytesPerWord;
const Register obj_end = tmp1;
const Register len = noreg;
if (Assembler::is_arith_imm_in_range(object_size_in_bytes)) {
try_allocate(obj, obj_end, tmp2, tmp3, object_size_in_bytes, slow_case);
} else {
// Rtemp should be free at c1 LIR level
mov_slow(Rtemp, object_size_in_bytes);
try_allocate(obj, obj_end, tmp2, tmp3, Rtemp, slow_case);
}
initialize_object(obj, obj_end, klass, len, tmp2, tmp3, instanceOopDesc::header_size() * HeapWordSize, object_size_in_bytes, /* is_tlab_allocated */ UseTLAB);
}
void C1_MacroAssembler::allocate_array(Register obj, Register len,
Register tmp1, Register tmp2, Register tmp3,
int header_size, int element_size,
Register klass, Label& slow_case) {
assert_different_registers(obj, len, tmp1, tmp2, tmp3, klass, Rtemp);
const int header_size_in_bytes = header_size * BytesPerWord;
const int scale_shift = exact_log2(element_size);
const Register obj_size = Rtemp; // Rtemp should be free at c1 LIR level
#ifdef AARCH64
mov_slow(Rtemp, max_array_allocation_length);
cmp_32(len, Rtemp);
#else
cmp_32(len, max_array_allocation_length);
#endif // AARCH64
b(slow_case, hs);
bool align_header = ((header_size_in_bytes | element_size) & MinObjAlignmentInBytesMask) != 0;
assert(align_header || ((header_size_in_bytes & MinObjAlignmentInBytesMask) == 0), "must be");
assert(align_header || ((element_size & MinObjAlignmentInBytesMask) == 0), "must be");
mov(obj_size, header_size_in_bytes + (align_header ? (MinObjAlignmentInBytes - 1) : 0));
add_ptr_scaled_int32(obj_size, obj_size, len, scale_shift);
if (align_header) {
align_reg(obj_size, obj_size, MinObjAlignmentInBytes);
}
try_allocate(obj, tmp1, tmp2, tmp3, obj_size, slow_case);
initialize_object(obj, tmp1, klass, len, tmp2, tmp3, header_size_in_bytes, -1, /* is_tlab_allocated */ UseTLAB);
}
int C1_MacroAssembler::lock_object(Register hdr, Register obj,
Register disp_hdr, Register tmp1,
Label& slow_case) {
Label done, fast_lock, fast_lock_done;
int null_check_offset = 0;
const Register tmp2 = Rtemp; // Rtemp should be free at c1 LIR level
assert_different_registers(hdr, obj, disp_hdr, tmp1, tmp2);
assert(BasicObjectLock::lock_offset_in_bytes() == 0, "ajust this code");
const int obj_offset = BasicObjectLock::obj_offset_in_bytes();
const int mark_offset = BasicLock::displaced_header_offset_in_bytes();
if (UseBiasedLocking) {
// load object
str(obj, Address(disp_hdr, obj_offset));
null_check_offset = biased_locking_enter(obj, hdr/*scratched*/, tmp1, false, tmp2, done, slow_case);
}
assert(oopDesc::mark_offset_in_bytes() == 0, "Required by atomic instructions");
#ifdef AARCH64
str(obj, Address(disp_hdr, obj_offset));
if (!UseBiasedLocking) {
null_check_offset = offset();
}
ldr(hdr, obj);
// Test if object is already locked
assert(markOopDesc::unlocked_value == 1, "adjust this code");
tbnz(hdr, exact_log2(markOopDesc::unlocked_value), fast_lock);
// Check for recursive locking
// See comments in InterpreterMacroAssembler::lock_object for
// explanations on the fast recursive locking check.
intptr_t mask = ((intptr_t)3) - ((intptr_t)os::vm_page_size());
Assembler::LogicalImmediate imm(mask, false);
mov(tmp2, SP);
sub(tmp2, hdr, tmp2);
ands(tmp2, tmp2, imm);
b(slow_case, ne);
// Recursive locking: store 0 into a lock record
str(ZR, Address(disp_hdr, mark_offset));
b(fast_lock_done);
#else // AARCH64
if (!UseBiasedLocking) {
null_check_offset = offset();
}
// On MP platforms the next load could return a 'stale' value if the memory location has been modified by another thread.
// That would be acceptable as ether CAS or slow case path is taken in that case.
// Must be the first instruction here, because implicit null check relies on it
ldr(hdr, Address(obj, oopDesc::mark_offset_in_bytes()));
str(obj, Address(disp_hdr, obj_offset));
tst(hdr, markOopDesc::unlocked_value);
b(fast_lock, ne);
// Check for recursive locking
// See comments in InterpreterMacroAssembler::lock_object for
// explanations on the fast recursive locking check.
// -1- test low 2 bits
movs(tmp2, AsmOperand(hdr, lsl, 30));
// -2- test (hdr - SP) if the low two bits are 0
sub(tmp2, hdr, SP, eq);
movs(tmp2, AsmOperand(tmp2, lsr, exact_log2(os::vm_page_size())), eq);
// If 'eq' then OK for recursive fast locking: store 0 into a lock record.
str(tmp2, Address(disp_hdr, mark_offset), eq);
b(fast_lock_done, eq);
// else need slow case
b(slow_case);
#endif // AARCH64
bind(fast_lock);
// Save previous object header in BasicLock structure and update the header
str(hdr, Address(disp_hdr, mark_offset));
cas_for_lock_acquire(hdr, disp_hdr, obj, tmp2, slow_case);
bind(fast_lock_done);
#ifndef PRODUCT
if (PrintBiasedLockingStatistics) {
cond_atomic_inc32(al, BiasedLocking::fast_path_entry_count_addr());
}
#endif // !PRODUCT
bind(done);
return null_check_offset;
}
void C1_MacroAssembler::unlock_object(Register hdr, Register obj,
Register disp_hdr, Register tmp,
Label& slow_case) {
// Note: this method is not using its 'tmp' argument
assert_different_registers(hdr, obj, disp_hdr, Rtemp);
Register tmp2 = Rtemp;
assert(BasicObjectLock::lock_offset_in_bytes() == 0, "ajust this code");
const int obj_offset = BasicObjectLock::obj_offset_in_bytes();
const int mark_offset = BasicLock::displaced_header_offset_in_bytes();
Label done;
if (UseBiasedLocking) {
// load object
ldr(obj, Address(disp_hdr, obj_offset));
biased_locking_exit(obj, hdr, done);
}
assert(oopDesc::mark_offset_in_bytes() == 0, "Required by atomic instructions");
Label retry;
// Load displaced header and object from the lock
ldr(hdr, Address(disp_hdr, mark_offset));
// If hdr is NULL, we've got recursive locking and there's nothing more to do
cbz(hdr, done);
if(!UseBiasedLocking) {
// load object
ldr(obj, Address(disp_hdr, obj_offset));
}
// Restore the object header
cas_for_lock_release(disp_hdr, hdr, obj, tmp2, slow_case);
bind(done);
}
#ifndef PRODUCT
void C1_MacroAssembler::verify_stack_oop(int stack_offset) {
if (!VerifyOops) return;
verify_oop_addr(Address(SP, stack_offset));
}
void C1_MacroAssembler::verify_not_null_oop(Register r) {
Label not_null;
cbnz(r, not_null);
stop("non-null oop required");
bind(not_null);
if (!VerifyOops) return;
verify_oop(r);
}
#endif // !PRODUCT

View File

@ -0,0 +1,69 @@
/*
* Copyright (c) 2008, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_C1_MACROASSEMBLER_ARM_HPP
#define CPU_ARM_VM_C1_MACROASSEMBLER_ARM_HPP
private:
void pd_init() { /* not used */ }
public:
// Puts address of allocated object into register `obj` and end of allocated object into register `obj_end`.
// `size_expression` should be a register or constant which can be used as immediate in "add" instruction.
void try_allocate(Register obj, Register obj_end, Register tmp1, Register tmp2,
RegisterOrConstant size_expression, Label& slow_case);
void initialize_header(Register obj, Register klass, Register len, Register tmp);
// Cleans object body [base..obj_end]. Clobbers `base` and `tmp` registers.
void initialize_body(Register base, Register obj_end, Register tmp);
void initialize_object(Register obj, Register obj_end, Register klass,
Register len, Register tmp1, Register tmp2,
RegisterOrConstant header_size_expression, int obj_size_in_bytes,
bool is_tlab_allocated);
void allocate_object(Register obj, Register tmp1, Register tmp2, Register tmp3,
int header_size, int object_size,
Register klass, Label& slow_case);
void allocate_array(Register obj, Register len,
Register tmp1, Register tmp2, Register tmp3,
int header_size, int element_size,
Register klass, Label& slow_case);
enum {
max_array_allocation_length = 0x01000000
};
int lock_object(Register hdr, Register obj, Register disp_hdr, Register tmp, Label& slow_case);
void unlock_object(Register hdr, Register obj, Register disp_hdr, Register tmp, Label& slow_case);
// This platform only uses signal-based null checks. The Label is not needed.
void null_check(Register r, Label *Lnull = NULL) { MacroAssembler::null_check(r); }
#endif // CPU_ARM_VM_C1_MACROASSEMBLER_ARM_HPP

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,73 @@
/*
* Copyright (c) 2008, 2015, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_C1_GLOBALS_ARM_HPP
#define CPU_ARM_VM_C1_GLOBALS_ARM_HPP
#include "utilities/globalDefinitions.hpp"
#include "utilities/macros.hpp"
//
// Sets the default values for platform dependent flags used by the client compiler.
// (see c1_globals.hpp)
//
#ifndef COMPILER2 // avoid duplicated definitions, favoring C2 version
define_pd_global(bool, BackgroundCompilation, true );
define_pd_global(bool, UseTLAB, true );
define_pd_global(bool, ResizeTLAB, true );
define_pd_global(bool, InlineIntrinsics, false); // TODO: ARM
define_pd_global(bool, PreferInterpreterNativeStubs, false);
define_pd_global(bool, ProfileTraps, false);
define_pd_global(bool, UseOnStackReplacement, true );
define_pd_global(bool, TieredCompilation, false);
define_pd_global(intx, CompileThreshold, 1500 );
define_pd_global(intx, OnStackReplacePercentage, 933 );
define_pd_global(intx, FreqInlineSize, 325 );
define_pd_global(size_t, NewSizeThreadIncrease, 4*K );
define_pd_global(size_t, InitialCodeCacheSize, 160*K);
define_pd_global(size_t, ReservedCodeCacheSize, 32*M );
define_pd_global(size_t, NonProfiledCodeHeapSize, 13*M );
define_pd_global(size_t, ProfiledCodeHeapSize, 14*M );
define_pd_global(size_t, NonNMethodCodeHeapSize, 5*M );
define_pd_global(bool, ProfileInterpreter, false);
define_pd_global(size_t, CodeCacheExpansionSize, 32*K );
define_pd_global(uintx, CodeCacheMinBlockLength, 1);
define_pd_global(size_t, CodeCacheMinimumUseSpace, 400*K);
define_pd_global(size_t, MetaspaceSize, 12*M );
define_pd_global(bool, NeverActAsServerClassMachine, true);
define_pd_global(uint64_t, MaxRAM, 1ULL*G);
define_pd_global(bool, CICompileOSR, true );
#endif // COMPILER2
define_pd_global(bool, UseTypeProfile, false);
define_pd_global(bool, RoundFPResults, false);
define_pd_global(bool, LIRFillDelaySlots, false);
define_pd_global(bool, OptimizeSinglePrecision, true);
define_pd_global(bool, CSEArrayLength, true);
define_pd_global(bool, TwoOperandLIRForm, false);
#endif // CPU_ARM_VM_C1_GLOBALS_ARM_HPP

View File

@ -0,0 +1,124 @@
/*
* Copyright (c) 2008, 2015, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_C2_GLOBALS_ARM_HPP
#define CPU_ARM_VM_C2_GLOBALS_ARM_HPP
#include "utilities/globalDefinitions.hpp"
#include "utilities/macros.hpp"
//
// Sets the default values for platform dependent flags used by the server compiler.
// (see c2_globals.hpp). Alpha-sorted.
define_pd_global(bool, BackgroundCompilation, true);
define_pd_global(bool, CICompileOSR, true);
define_pd_global(bool, InlineIntrinsics, false);
define_pd_global(bool, PreferInterpreterNativeStubs, false);
define_pd_global(bool, ProfileTraps, true);
define_pd_global(bool, UseOnStackReplacement, true);
define_pd_global(bool, ProfileInterpreter, true);
#ifdef AARCH64
define_pd_global(bool, TieredCompilation, trueInTiered);
#else
define_pd_global(bool, TieredCompilation, false);
#endif
define_pd_global(intx, CompileThreshold, 10000);
define_pd_global(intx, OnStackReplacePercentage, 140);
define_pd_global(intx, ConditionalMoveLimit, 4);
// C2 gets to use all the float/double registers
#ifdef AARCH64
define_pd_global(intx, FLOATPRESSURE, 31);
#else
define_pd_global(intx, FLOATPRESSURE, 30);
#endif
define_pd_global(intx, FreqInlineSize, 175);
#ifdef AARCH64
define_pd_global(intx, INTPRESSURE, 27);
#else
define_pd_global(intx, INTPRESSURE, 12);
#endif
define_pd_global(intx, InteriorEntryAlignment, 16); // = CodeEntryAlignment
define_pd_global(size_t, NewSizeThreadIncrease, ScaleForWordSize(4*K));
// The default setting 16/16 seems to work best.
// (For _228_jack 16/16 is 2% better than 4/4, 16/4, 32/32, 32/16, or 16/32.)
//define_pd_global(intx, OptoLoopAlignment, 16); // = 4*wordSize
define_pd_global(intx, RegisterCostAreaRatio, 16000);
define_pd_global(bool, UseTLAB, true);
define_pd_global(bool, ResizeTLAB, true);
define_pd_global(intx, LoopUnrollLimit, 60); // Design center runs on 1.3.1
define_pd_global(intx, LoopPercentProfileLimit, 10);
define_pd_global(intx, PostLoopMultiversioning, false);
define_pd_global(intx, MinJumpTableSize, 16);
// Peephole and CISC spilling both break the graph, and so makes the
// scheduler sick.
define_pd_global(bool, OptoPeephole, false);
define_pd_global(bool, UseCISCSpill, false);
define_pd_global(bool, OptoBundling, false);
define_pd_global(bool, OptoScheduling, true);
define_pd_global(bool, OptoRegScheduling, false);
define_pd_global(bool, SuperWordLoopUnrollAnalysis, false);
define_pd_global(bool, IdealizeClearArrayNode, true);
#ifdef _LP64
// We need to make sure that all generated code is within
// 2 gigs of the libjvm.so runtime routines so we can use
// the faster "call" instruction rather than the expensive
// sequence of instructions to load a 64 bit pointer.
//
// InitialCodeCacheSize derived from specjbb2000 run.
define_pd_global(size_t, InitialCodeCacheSize, 2048*K); // Integral multiple of CodeCacheExpansionSize
define_pd_global(size_t, ReservedCodeCacheSize, 48*M);
define_pd_global(size_t, NonProfiledCodeHeapSize, 21*M);
define_pd_global(size_t, ProfiledCodeHeapSize, 22*M);
define_pd_global(size_t, NonNMethodCodeHeapSize, 5*M );
define_pd_global(size_t, CodeCacheExpansionSize, 64*K);
// Ergonomics related flags
define_pd_global(uint64_t, MaxRAM, 128ULL*G);
#else
// InitialCodeCacheSize derived from specjbb2000 run.
define_pd_global(size_t, InitialCodeCacheSize, 1536*K); // Integral multiple of CodeCacheExpansionSize
define_pd_global(size_t, ReservedCodeCacheSize, 32*M);
define_pd_global(size_t, NonProfiledCodeHeapSize, 13*M);
define_pd_global(size_t, ProfiledCodeHeapSize, 14*M);
define_pd_global(size_t, NonNMethodCodeHeapSize, 5*M );
define_pd_global(size_t, CodeCacheExpansionSize, 32*K);
// Ergonomics related flags
define_pd_global(uint64_t, MaxRAM, 4ULL*G);
#endif
define_pd_global(uintx, CodeCacheMinBlockLength, 4);
define_pd_global(size_t, CodeCacheMinimumUseSpace, 400*K);
define_pd_global(bool, TrapBasedRangeChecks, false); // Not needed
// Heap related flags
define_pd_global(size_t, MetaspaceSize, ScaleForWordSize(16*M));
// Ergonomics related flags
define_pd_global(bool, NeverActAsServerClassMachine, false);
#endif // CPU_ARM_VM_C2_GLOBALS_ARM_HPP

View File

@ -0,0 +1,34 @@
/*
* Copyright (c) 2008, 2011, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_CODEBUFFER_ARM_HPP
#define CPU_ARM_VM_CODEBUFFER_ARM_HPP
private:
void pd_initialize() {}
public:
void flush_bundle(bool start_new_bundle) {}
#endif // CPU_ARM_VM_CODEBUFFER_ARM_HPP

View File

@ -0,0 +1,166 @@
/*
* Copyright (c) 1997, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "asm/macroAssembler.inline.hpp"
#include "code/compiledIC.hpp"
#include "code/icBuffer.hpp"
#include "code/nativeInst.hpp"
#include "code/nmethod.hpp"
#include "memory/resourceArea.hpp"
#include "runtime/mutexLocker.hpp"
#include "runtime/safepoint.hpp"
// ----------------------------------------------------------------------------
#if defined(COMPILER2) || INCLUDE_JVMCI
#define __ _masm.
// emit call stub, compiled java to interpreter
address CompiledStaticCall::emit_to_interp_stub(CodeBuffer &cbuf, address mark) {
// Stub is fixed up when the corresponding call is converted from calling
// compiled code to calling interpreted code.
// set (empty), R9
// b -1
if (mark == NULL) {
mark = cbuf.insts_mark(); // get mark within main instrs section
}
MacroAssembler _masm(&cbuf);
address base = __ start_a_stub(to_interp_stub_size());
if (base == NULL) {
return NULL; // CodeBuffer::expand failed
}
// static stub relocation stores the instruction address of the call
__ relocate(static_stub_Relocation::spec(mark));
InlinedMetadata object_literal(NULL);
// single instruction, see NativeMovConstReg::next_instruction_address() in
// CompiledStaticCall::set_to_interpreted()
__ ldr_literal(Rmethod, object_literal);
__ set_inst_mark(); // Who uses this?
bool near_range = __ cache_fully_reachable();
InlinedAddress dest((address)-1);
address branch_site = __ pc();
if (near_range) {
__ b(branch_site); // special NativeJump -1 destination
} else {
// Can't trash LR, FP, or argument registers
__ indirect_jump(dest, Rtemp);
}
__ bind_literal(object_literal); // includes spec_for_immediate reloc
if (!near_range) {
__ bind_literal(dest); // special NativeJump -1 destination
}
assert(__ pc() - base <= to_interp_stub_size(), "wrong stub size");
// Update current stubs pointer and restore code_end.
__ end_a_stub();
return base;
}
#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
void CompiledDirectStaticCall::set_to_interpreted(const methodHandle& callee, address entry) {
address stub = find_stub(/*is_aot*/ false);
guarantee(stub != NULL, "stub not found");
if (TraceICs) {
ResourceMark rm;
tty->print_cr("CompiledDirectStaticCall@" INTPTR_FORMAT ": set_to_interpreted %s",
p2i(instruction_address()),
callee->name_and_sig_as_C_string());
}
// Creation also verifies the object.
NativeMovConstReg* method_holder = nativeMovConstReg_at(stub);
NativeJump* jump = nativeJump_at(method_holder->next_instruction_address());
#ifdef ASSERT
// read the value once
volatile intptr_t data = method_holder->data();
volatile address destination = jump->jump_destination();
assert(data == 0 || data == (intptr_t)callee(),
"a) MT-unsafe modification of inline cache");
assert(destination == (address)-1 || destination == entry,
"b) MT-unsafe modification of inline cache");
#endif
// Update stub.
method_holder->set_data((intptr_t)callee());
jump->set_jump_destination(entry);
// Update jump to call.
set_destination_mt_safe(stub);
}
void CompiledDirectStaticCall::set_stub_to_clean(static_stub_Relocation* static_stub) {
assert (CompiledIC_lock->is_locked() || SafepointSynchronize::is_at_safepoint(), "mt unsafe call");
// Reset stub.
address stub = static_stub->addr();
assert(stub != NULL, "stub not found");
// Creation also verifies the object.
NativeMovConstReg* method_holder = nativeMovConstReg_at(stub);
NativeJump* jump = nativeJump_at(method_holder->next_instruction_address());
method_holder->set_data(0);
jump->set_jump_destination((address)-1);
}
//-----------------------------------------------------------------------------
// Non-product mode code
#ifndef PRODUCT
void CompiledDirectStaticCall::verify() {
// Verify call.
_call->verify();
if (os::is_MP()) {
_call->verify_alignment();
}
// Verify stub.
address stub = find_stub(/*is_aot*/ false);
assert(stub != NULL, "no stub found for static call");
// Creation also verifies the object.
NativeMovConstReg* method_holder = nativeMovConstReg_at(stub);
NativeJump* jump = nativeJump_at(method_holder->next_instruction_address());
// Verify state.
assert(is_clean() || is_call_to_compiled() || is_call_to_interpreted(), "sanity check");
}
#endif // !PRODUCT

View File

@ -0,0 +1,59 @@
/*
* 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_COPY_ARM_HPP
#define CPU_ARM_VM_COPY_ARM_HPP
#include "utilities/macros.hpp"
// Inline functions for memory copy and fill.
// Contains inline asm implementations
#include OS_CPU_HEADER_INLINE(copy)
static void pd_fill_to_words(HeapWord* tohw, size_t count, juint value) {
juint* to = (juint*)tohw;
count *= HeapWordSize / BytesPerInt;
while (count-- > 0) {
*to++ = value;
}
}
static void pd_fill_to_aligned_words(HeapWord* tohw, size_t count, juint value) {
pd_fill_to_words(tohw, count, value);
}
static void pd_fill_to_bytes(void* to, size_t count, jubyte value) {
memset(to, value, count);
}
static void pd_zero_to_words(HeapWord* tohw, size_t count) {
pd_fill_to_words(tohw, count, 0);
}
static void pd_zero_to_bytes(void* to, size_t count) {
memset(to, 0, count);
}
#endif // CPU_ARM_VM_COPY_ARM_HPP

View File

@ -0,0 +1,33 @@
/*
* Copyright (c) 2008, 2011, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "code/codeCache.hpp"
#include "code/nmethod.hpp"
#include "runtime/frame.hpp"
#include "runtime/init.hpp"
#include "runtime/os.hpp"
#include "utilities/debug.hpp"
void pd_ps(frame f) {}

View File

@ -0,0 +1,29 @@
/*
* Copyright (c) 2008, 2011, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "compiler/disassembler.hpp"
#include "depChecker_arm.hpp"
// Nothing to do

View File

@ -0,0 +1,30 @@
/*
* Copyright (c) 2008, 2011, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_DEPCHECKER_ARM_HPP
#define CPU_ARM_VM_DEPCHECKER_ARM_HPP
// Nothing to do
#endif // CPU_ARM_VM_DEPCHECKER_ARM_HPP

View File

@ -0,0 +1,36 @@
/*
* Copyright (c) 2008, 2011, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_DISASSEMBLER_ARM_HPP
#define CPU_ARM_VM_DISASSEMBLER_ARM_HPP
static int pd_instruction_alignment() {
return sizeof(int);
}
static const char* pd_cpu_opts() {
return "";
}
#endif // CPU_ARM_VM_DISASSEMBLER_ARM_HPP

View File

@ -0,0 +1,655 @@
/*
* 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "interpreter/interpreter.hpp"
#include "memory/resourceArea.hpp"
#include "oops/markOop.hpp"
#include "oops/method.hpp"
#include "oops/oop.inline.hpp"
#include "runtime/frame.inline.hpp"
#include "runtime/handles.inline.hpp"
#include "runtime/javaCalls.hpp"
#include "runtime/monitorChunk.hpp"
#include "runtime/signature.hpp"
#include "runtime/stubCodeGenerator.hpp"
#include "runtime/stubRoutines.hpp"
#include "vmreg_arm.inline.hpp"
#ifdef COMPILER1
#include "c1/c1_Runtime1.hpp"
#include "runtime/vframeArray.hpp"
#endif
#include "prims/methodHandles.hpp"
#ifdef ASSERT
void RegisterMap::check_location_valid() {
}
#endif
// Profiling/safepoint support
bool frame::safe_for_sender(JavaThread *thread) {
address sp = (address)_sp;
address fp = (address)_fp;
address unextended_sp = (address)_unextended_sp;
static size_t stack_guard_size = os::uses_stack_guard_pages() ?
(JavaThread::stack_red_zone_size() + JavaThread::stack_yellow_zone_size()) : 0;
size_t usable_stack_size = thread->stack_size() - stack_guard_size;
// sp must be within the usable part of the stack (not in guards)
bool sp_safe = (sp != NULL &&
(sp <= thread->stack_base()) &&
(sp >= thread->stack_base() - usable_stack_size));
if (!sp_safe) {
return false;
}
bool unextended_sp_safe = (unextended_sp != NULL &&
(unextended_sp <= thread->stack_base()) &&
(unextended_sp >= sp));
if (!unextended_sp_safe) {
return false;
}
// We know sp/unextended_sp are safe. Only fp is questionable here.
bool fp_safe = (fp != NULL &&
(fp <= thread->stack_base()) &&
fp >= sp);
if (_cb != NULL ) {
// First check if frame is complete and tester is reliable
// Unfortunately we can only check frame complete for runtime stubs and nmethod
// other generic buffer blobs are more problematic so we just assume they are
// ok. adapter blobs never have a frame complete and are never ok.
if (!_cb->is_frame_complete_at(_pc)) {
if (_cb->is_compiled() || _cb->is_adapter_blob() || _cb->is_runtime_stub()) {
return false;
}
}
// Could just be some random pointer within the codeBlob
if (!_cb->code_contains(_pc)) {
return false;
}
// Entry frame checks
if (is_entry_frame()) {
// an entry frame must have a valid fp.
return fp_safe && is_entry_frame_valid(thread);
}
intptr_t* sender_sp = NULL;
address sender_pc = NULL;
if (is_interpreted_frame()) {
// fp must be safe
if (!fp_safe) {
return false;
}
sender_pc = (address) this->fp()[return_addr_offset];
sender_sp = (intptr_t*) addr_at(sender_sp_offset);
} else {
// must be some sort of compiled/runtime frame
// fp does not have to be safe (although it could be check for c1?)
sender_sp = _unextended_sp + _cb->frame_size();
// Is sender_sp safe?
if ((address)sender_sp >= thread->stack_base()) {
return false;
}
// With our calling conventions, the return_address should
// end up being the word on the stack
sender_pc = (address) *(sender_sp - sender_sp_offset + return_addr_offset);
}
// We must always be able to find a recognizable pc
CodeBlob* sender_blob = CodeCache::find_blob_unsafe(sender_pc);
if (sender_pc == NULL || sender_blob == NULL) {
return false;
}
// If the potential sender is the interpreter then we can do some more checking
if (Interpreter::contains(sender_pc)) {
// FP is always saved in a recognizable place in any code we generate. However
// only if the sender is interpreted/call_stub (c1 too?) are we certain that the saved FP
// is really a frame pointer.
intptr_t *saved_fp = (intptr_t*)*(sender_sp - frame::sender_sp_offset + link_offset);
bool saved_fp_safe = ((address)saved_fp <= thread->stack_base()) && (saved_fp > sender_sp);
if (!saved_fp_safe) {
return false;
}
// construct the potential sender
frame sender(sender_sp, saved_fp, sender_pc);
return sender.is_interpreted_frame_valid(thread);
}
if (sender_blob->is_zombie() || sender_blob->is_unloaded()) {
return false;
}
// Could just be some random pointer within the codeBlob
if (!sender_blob->code_contains(sender_pc)) {
return false;
}
// We should never be able to see an adapter if the current frame is something from code cache
if (sender_blob->is_adapter_blob()) {
return false;
}
// Could be the call_stub
if (StubRoutines::returns_to_call_stub(sender_pc)) {
intptr_t *saved_fp = (intptr_t*)*(sender_sp - frame::sender_sp_offset + link_offset);
bool saved_fp_safe = ((address)saved_fp <= thread->stack_base()) && (saved_fp >= sender_sp);
if (!saved_fp_safe) {
return false;
}
// construct the potential sender
frame sender(sender_sp, saved_fp, sender_pc);
// Validate the JavaCallWrapper an entry frame must have
address jcw = (address)sender.entry_frame_call_wrapper();
bool jcw_safe = (jcw <= thread->stack_base()) && (jcw > (address)sender.fp());
return jcw_safe;
}
// If the frame size is 0 something (or less) is bad because every nmethod has a non-zero frame size
// because the return address counts against the callee's frame.
if (sender_blob->frame_size() <= 0) {
assert(!sender_blob->is_compiled(), "should count return address at least");
return false;
}
// We should never be able to see anything here except an nmethod. If something in the
// code cache (current frame) is called by an entity within the code cache that entity
// should not be anything but the call stub (already covered), the interpreter (already covered)
// or an nmethod.
if (!sender_blob->is_compiled()) {
return false;
}
// Could put some more validation for the potential non-interpreted sender
// frame we'd create by calling sender if I could think of any. Wait for next crash in forte...
// One idea is seeing if the sender_pc we have is one that we'd expect to call to current cb
// We've validated the potential sender that would be created
return true;
}
// Must be native-compiled frame. Since sender will try and use fp to find
// linkages it must be safe
if (!fp_safe) {
return false;
}
// Will the pc we fetch be non-zero (which we'll find at the oldest frame)
if ((address) this->fp()[return_addr_offset] == NULL) return false;
// could try and do some more potential verification of native frame if we could think of some...
return true;
}
void frame::patch_pc(Thread* thread, address pc) {
address* pc_addr = &((address *)sp())[-sender_sp_offset+return_addr_offset];
if (TracePcPatching) {
tty->print_cr("patch_pc at address" INTPTR_FORMAT " [" INTPTR_FORMAT " -> " INTPTR_FORMAT "] ",
p2i(pc_addr), p2i(*pc_addr), p2i(pc));
}
*pc_addr = pc;
_cb = CodeCache::find_blob(pc);
address original_pc = CompiledMethod::get_deopt_original_pc(this);
if (original_pc != NULL) {
assert(original_pc == _pc, "expected original PC to be stored before patching");
_deopt_state = is_deoptimized;
// leave _pc as is
} else {
_deopt_state = not_deoptimized;
_pc = pc;
}
}
bool frame::is_interpreted_frame() const {
return Interpreter::contains(pc());
}
int frame::frame_size(RegisterMap* map) const {
frame sender = this->sender(map);
return sender.sp() - sp();
}
intptr_t* frame::entry_frame_argument_at(int offset) const {
assert(is_entry_frame(), "entry frame expected");
// convert offset to index to deal with tsi
int index = (Interpreter::expr_offset_in_bytes(offset)/wordSize);
// Entry frame's arguments are always in relation to unextended_sp()
return &unextended_sp()[index];
}
// sender_sp
intptr_t* frame::interpreter_frame_sender_sp() const {
assert(is_interpreted_frame(), "interpreted frame expected");
return (intptr_t*) at(interpreter_frame_sender_sp_offset);
}
void frame::set_interpreter_frame_sender_sp(intptr_t* sender_sp) {
assert(is_interpreted_frame(), "interpreted frame expected");
ptr_at_put(interpreter_frame_sender_sp_offset, (intptr_t) sender_sp);
}
// monitor elements
BasicObjectLock* frame::interpreter_frame_monitor_begin() const {
return (BasicObjectLock*) addr_at(interpreter_frame_monitor_block_bottom_offset);
}
BasicObjectLock* frame::interpreter_frame_monitor_end() const {
BasicObjectLock* result = (BasicObjectLock*) *addr_at(interpreter_frame_monitor_block_top_offset);
// make sure the pointer points inside the frame
assert((intptr_t) fp() > (intptr_t) result, "result must < than frame pointer");
assert((intptr_t) sp() <= (intptr_t) result, "result must >= than stack pointer");
return result;
}
void frame::interpreter_frame_set_monitor_end(BasicObjectLock* value) {
*((BasicObjectLock**)addr_at(interpreter_frame_monitor_block_top_offset)) = value;
}
#ifdef AARCH64
// Used by template based interpreter deoptimization
void frame::interpreter_frame_set_stack_top(intptr_t* stack_top) {
*((intptr_t**)addr_at(interpreter_frame_stack_top_offset)) = stack_top;
}
// Used by template based interpreter deoptimization
void frame::interpreter_frame_set_extended_sp(intptr_t* sp) {
*((intptr_t**)addr_at(interpreter_frame_extended_sp_offset)) = sp;
}
#else
// Used by template based interpreter deoptimization
void frame::interpreter_frame_set_last_sp(intptr_t* sp) {
*((intptr_t**)addr_at(interpreter_frame_last_sp_offset)) = sp;
}
#endif // AARCH64
frame frame::sender_for_entry_frame(RegisterMap* map) const {
assert(map != NULL, "map must be set");
// Java frame called from C; skip all C frames and return top C
// frame of that chunk as the sender
JavaFrameAnchor* jfa = entry_frame_call_wrapper()->anchor();
assert(!entry_frame_is_first(), "next Java fp must be non zero");
assert(jfa->last_Java_sp() > sp(), "must be above this frame on stack");
map->clear();
assert(map->include_argument_oops(), "should be set by clear");
#ifdef AARCH64
assert (jfa->last_Java_pc() != NULL, "pc should be stored");
frame fr(jfa->last_Java_sp(), jfa->last_Java_fp(), jfa->last_Java_pc());
return fr;
#else
if (jfa->last_Java_pc() != NULL) {
frame fr(jfa->last_Java_sp(), jfa->last_Java_fp(), jfa->last_Java_pc());
return fr;
}
frame fr(jfa->last_Java_sp(), jfa->last_Java_fp());
return fr;
#endif // AARCH64
}
//------------------------------------------------------------------------------
// frame::verify_deopt_original_pc
//
// Verifies the calculated original PC of a deoptimization PC for the
// given unextended SP. The unextended SP might also be the saved SP
// for MethodHandle call sites.
#ifdef ASSERT
void frame::verify_deopt_original_pc(CompiledMethod* nm, intptr_t* unextended_sp, bool is_method_handle_return) {
frame fr;
// This is ugly but it's better than to change {get,set}_original_pc
// to take an SP value as argument. And it's only a debugging
// method anyway.
fr._unextended_sp = unextended_sp;
address original_pc = nm->get_original_pc(&fr);
assert(nm->insts_contains(original_pc), "original PC must be in nmethod");
assert(nm->is_method_handle_return(original_pc) == is_method_handle_return, "must be");
}
#endif
//------------------------------------------------------------------------------
// frame::adjust_unextended_sp
void frame::adjust_unextended_sp() {
// same as on x86
// If we are returning to a compiled MethodHandle call site, the
// saved_fp will in fact be a saved value of the unextended SP. The
// simplest way to tell whether we are returning to such a call site
// is as follows:
CompiledMethod* sender_cm = (_cb == NULL) ? NULL : _cb->as_compiled_method_or_null();
if (sender_cm != NULL) {
// If the sender PC is a deoptimization point, get the original
// PC. For MethodHandle call site the unextended_sp is stored in
// saved_fp.
if (sender_cm->is_deopt_mh_entry(_pc)) {
DEBUG_ONLY(verify_deopt_mh_original_pc(sender_cm, _fp));
_unextended_sp = _fp;
}
else if (sender_cm->is_deopt_entry(_pc)) {
DEBUG_ONLY(verify_deopt_original_pc(sender_cm, _unextended_sp));
}
else if (sender_cm->is_method_handle_return(_pc)) {
_unextended_sp = _fp;
}
}
}
//------------------------------------------------------------------------------
// frame::update_map_with_saved_link
void frame::update_map_with_saved_link(RegisterMap* map, intptr_t** link_addr) {
// see x86 for comments
map->set_location(FP->as_VMReg(), (address) link_addr);
#ifdef AARCH64
// also adjust a high part of register
map->set_location(FP->as_VMReg()->next(), (address) link_addr);
#endif // AARCH64
}
frame frame::sender_for_interpreter_frame(RegisterMap* map) const {
// SP is the raw SP from the sender after adapter or interpreter
// extension.
intptr_t* sender_sp = this->sender_sp();
// This is the sp before any possible extension (adapter/locals).
intptr_t* unextended_sp = interpreter_frame_sender_sp();
#ifdef COMPILER2
if (map->update_map()) {
update_map_with_saved_link(map, (intptr_t**) addr_at(link_offset));
}
#endif // COMPILER2
return frame(sender_sp, unextended_sp, link(), sender_pc());
}
frame frame::sender_for_compiled_frame(RegisterMap* map) const {
assert(map != NULL, "map must be set");
// frame owned by optimizing compiler
assert(_cb->frame_size() >= 0, "must have non-zero frame size");
intptr_t* sender_sp = unextended_sp() + _cb->frame_size();
intptr_t* unextended_sp = sender_sp;
address sender_pc = (address) *(sender_sp - sender_sp_offset + return_addr_offset);
// This is the saved value of FP which may or may not really be an FP.
// It is only an FP if the sender is an interpreter frame (or C1?).
intptr_t** saved_fp_addr = (intptr_t**) (sender_sp - sender_sp_offset + link_offset);
if (map->update_map()) {
// Tell GC to use argument oopmaps for some runtime stubs that need it.
// For C1, the runtime stub might not have oop maps, so set this flag
// outside of update_register_map.
map->set_include_argument_oops(_cb->caller_must_gc_arguments(map->thread()));
if (_cb->oop_maps() != NULL) {
OopMapSet::update_register_map(this, map);
}
// Since the prolog does the save and restore of FP there is no oopmap
// for it so we must fill in its location as if there was an oopmap entry
// since if our caller was compiled code there could be live jvm state in it.
update_map_with_saved_link(map, saved_fp_addr);
}
assert(sender_sp != sp(), "must have changed");
return frame(sender_sp, unextended_sp, *saved_fp_addr, sender_pc);
}
frame frame::sender(RegisterMap* map) const {
// Default is we done have to follow them. The sender_for_xxx will
// update it accordingly
map->set_include_argument_oops(false);
if (is_entry_frame()) return sender_for_entry_frame(map);
if (is_interpreted_frame()) return sender_for_interpreter_frame(map);
assert(_cb == CodeCache::find_blob(pc()),"Must be the same");
if (_cb != NULL) {
return sender_for_compiled_frame(map);
}
assert(false, "should not be called for a C frame");
return frame();
}
bool frame::is_interpreted_frame_valid(JavaThread* thread) const {
assert(is_interpreted_frame(), "Not an interpreted frame");
// These are reasonable sanity checks
if (fp() == 0 || (intptr_t(fp()) & (wordSize-1)) != 0) {
return false;
}
if (sp() == 0 || (intptr_t(sp()) & (wordSize-1)) != 0) {
return false;
}
if (fp() + interpreter_frame_initial_sp_offset < sp()) {
return false;
}
// These are hacks to keep us out of trouble.
// The problem with these is that they mask other problems
if (fp() <= sp()) { // this attempts to deal with unsigned comparison above
return false;
}
// do some validation of frame elements
// first the method
Method* m = *interpreter_frame_method_addr();
// validate the method we'd find in this potential sender
if (!m->is_valid_method()) return false;
// stack frames shouldn't be much larger than max_stack elements
if (fp() - sp() > 1024 + m->max_stack()*Interpreter::stackElementSize) {
return false;
}
// validate bci/bcp
address bcp = interpreter_frame_bcp();
if (m->validate_bci_from_bcp(bcp) < 0) {
return false;
}
// validate ConstantPoolCache*
ConstantPoolCache* cp = *interpreter_frame_cache_addr();
if (cp == NULL || !cp->is_metaspace_object()) return false;
// validate locals
address locals = (address) *interpreter_frame_locals_addr();
if (locals > thread->stack_base() || locals < (address) fp()) return false;
// We'd have to be pretty unlucky to be mislead at this point
return true;
}
BasicType frame::interpreter_frame_result(oop* oop_result, jvalue* value_result) {
assert(is_interpreted_frame(), "interpreted frame expected");
Method* method = interpreter_frame_method();
BasicType type = method->result_type();
intptr_t* res_addr;
if (method->is_native()) {
// Prior to calling into the runtime to report the method_exit both of
// the possible return value registers are saved.
#ifdef AARCH64
// Return value registers are saved into the frame
if (type == T_FLOAT || type == T_DOUBLE) {
res_addr = addr_at(interpreter_frame_fp_saved_result_offset);
} else {
res_addr = addr_at(interpreter_frame_gp_saved_result_offset);
}
#else
// Return value registers are pushed to the native stack
res_addr = (intptr_t*)sp();
#ifdef __ABI_HARD__
// FP result is pushed onto a stack along with integer result registers
if (type == T_FLOAT || type == T_DOUBLE) {
res_addr += 2;
}
#endif // __ABI_HARD__
#endif // AARCH64
} else {
res_addr = (intptr_t*)interpreter_frame_tos_address();
}
switch (type) {
case T_OBJECT :
case T_ARRAY : {
oop obj;
if (method->is_native()) {
obj = cast_to_oop(at(interpreter_frame_oop_temp_offset));
} else {
obj = *(oop*)res_addr;
}
assert(obj == NULL || Universe::heap()->is_in(obj), "sanity check");
*oop_result = obj;
break;
}
case T_BOOLEAN : value_result->z = *(jboolean*)res_addr; break;
case T_BYTE : value_result->b = *(jbyte*)res_addr; break;
case T_CHAR : value_result->c = *(jchar*)res_addr; break;
case T_SHORT : value_result->s = *(jshort*)res_addr; break;
case T_INT : value_result->i = *(jint*)res_addr; break;
case T_LONG : value_result->j = *(jlong*)res_addr; break;
case T_FLOAT : value_result->f = *(jfloat*)res_addr; break;
case T_DOUBLE : value_result->d = *(jdouble*)res_addr; break;
case T_VOID : /* Nothing to do */ break;
default : ShouldNotReachHere();
}
return type;
}
intptr_t* frame::interpreter_frame_tos_at(jint offset) const {
int index = (Interpreter::expr_offset_in_bytes(offset)/wordSize);
return &interpreter_frame_tos_address()[index];
}
#ifndef PRODUCT
#define DESCRIBE_FP_OFFSET(name) \
values.describe(frame_no, fp() + frame::name##_offset, #name)
void frame::describe_pd(FrameValues& values, int frame_no) {
if (is_interpreted_frame()) {
DESCRIBE_FP_OFFSET(interpreter_frame_sender_sp);
#ifdef AARCH64
DESCRIBE_FP_OFFSET(interpreter_frame_stack_top);
DESCRIBE_FP_OFFSET(interpreter_frame_extended_sp);
#else
DESCRIBE_FP_OFFSET(interpreter_frame_last_sp);
#endif // AARCH64
DESCRIBE_FP_OFFSET(interpreter_frame_method);
DESCRIBE_FP_OFFSET(interpreter_frame_mdp);
DESCRIBE_FP_OFFSET(interpreter_frame_cache);
DESCRIBE_FP_OFFSET(interpreter_frame_locals);
DESCRIBE_FP_OFFSET(interpreter_frame_bcp);
DESCRIBE_FP_OFFSET(interpreter_frame_initial_sp);
}
}
// This is a generic constructor which is only used by pns() in debug.cpp.
frame::frame(void* sp, void* fp, void* pc) {
init((intptr_t*)sp, (intptr_t*)fp, (address)pc);
}
#endif
intptr_t *frame::initial_deoptimization_info() {
// used to reset the saved FP
return fp();
}
intptr_t* frame::real_fp() const {
#ifndef AARCH64
if (is_entry_frame()) {
// Work-around: FP (currently) does not conform to the ABI for entry
// frames (see generate_call_stub). Might be worth fixing as another CR.
// Following code assumes (and asserts) this has not yet been fixed.
assert(frame::entry_frame_call_wrapper_offset == 0, "adjust this code");
intptr_t* new_fp = fp();
new_fp += 5; // saved R0,R1,R2,R4,R10
#ifndef __SOFTFP__
new_fp += 8*2; // saved D8..D15
#endif
return new_fp;
}
#endif // !AARCH64
if (_cb != NULL) {
// use the frame size if valid
int size = _cb->frame_size();
if (size > 0) {
return unextended_sp() + size;
}
}
// else rely on fp()
assert(! is_compiled_frame(), "unknown compiled frame size");
return fp();
}

View File

@ -0,0 +1,138 @@
/*
* 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_FRAME_ARM_HPP
#define CPU_ARM_VM_FRAME_ARM_HPP
#include "runtime/synchronizer.hpp"
public:
enum {
pc_return_offset = 0,
// All frames
link_offset = 0,
return_addr_offset = 1,
// non-interpreter frames
sender_sp_offset = 2,
// Interpreter frames
#ifdef AARCH64
interpreter_frame_gp_saved_result_offset = 4, // for native calls only
interpreter_frame_fp_saved_result_offset = 3, // for native calls only
#endif
interpreter_frame_oop_temp_offset = 2, // for native calls only
interpreter_frame_sender_sp_offset = -1,
#ifdef AARCH64
interpreter_frame_stack_top_offset = interpreter_frame_sender_sp_offset - 1,
interpreter_frame_extended_sp_offset = interpreter_frame_stack_top_offset - 1,
interpreter_frame_method_offset = interpreter_frame_extended_sp_offset - 1,
#else
// outgoing sp before a call to an invoked method
interpreter_frame_last_sp_offset = interpreter_frame_sender_sp_offset - 1,
interpreter_frame_method_offset = interpreter_frame_last_sp_offset - 1,
#endif // AARCH64
interpreter_frame_mirror_offset = interpreter_frame_method_offset - 1,
interpreter_frame_mdp_offset = interpreter_frame_mirror_offset - 1,
interpreter_frame_cache_offset = interpreter_frame_mdp_offset - 1,
interpreter_frame_locals_offset = interpreter_frame_cache_offset - 1,
interpreter_frame_bcp_offset = interpreter_frame_locals_offset - 1,
interpreter_frame_initial_sp_offset = interpreter_frame_bcp_offset - 1,
interpreter_frame_monitor_block_top_offset = interpreter_frame_initial_sp_offset,
interpreter_frame_monitor_block_bottom_offset = interpreter_frame_initial_sp_offset,
// Entry frames
entry_frame_call_wrapper_offset = AARCH64_ONLY(2) NOT_AARCH64(0)
};
intptr_t ptr_at(int offset) const {
return *ptr_at_addr(offset);
}
void ptr_at_put(int offset, intptr_t value) {
*ptr_at_addr(offset) = value;
}
private:
// an additional field beyond _sp and _pc:
intptr_t* _fp; // frame pointer
// The interpreter and adapters will extend the frame of the caller.
// Since oopMaps are based on the sp of the caller before extension
// we need to know that value. However in order to compute the address
// of the return address we need the real "raw" sp. Since sparc already
// uses sp() to mean "raw" sp and unextended_sp() to mean the caller's
// original sp we use that convention.
intptr_t* _unextended_sp;
void adjust_unextended_sp();
intptr_t* ptr_at_addr(int offset) const {
return (intptr_t*) addr_at(offset);
}
#ifdef ASSERT
// Used in frame::sender_for_{interpreter,compiled}_frame
static void verify_deopt_original_pc( CompiledMethod* nm, intptr_t* unextended_sp, bool is_method_handle_return = false);
static void verify_deopt_mh_original_pc(CompiledMethod* nm, intptr_t* unextended_sp) {
verify_deopt_original_pc(nm, unextended_sp, true);
}
#endif
public:
// Constructors
frame(intptr_t* sp, intptr_t* fp, address pc);
frame(intptr_t* sp, intptr_t* unextended_sp, intptr_t* fp, address pc);
#ifndef AARCH64
frame(intptr_t* sp, intptr_t* fp);
#endif // !AARCH64
void init(intptr_t* sp, intptr_t* fp, address pc);
// accessors for the instance variables
// Note: not necessarily the real 'frame pointer' (see real_fp)
intptr_t* fp() const { return _fp; }
inline address* sender_pc_addr() const;
#ifdef AARCH64
// Used by template based interpreter deoptimization
void interpreter_frame_set_stack_top(intptr_t* stack_top);
void interpreter_frame_set_extended_sp(intptr_t* sp);
#else
// expression stack tos if we are nested in a java call
intptr_t* interpreter_frame_last_sp() const;
// deoptimization support
void interpreter_frame_set_last_sp(intptr_t* sp);
#endif // AARCH64
// helper to update a map with callee-saved FP
static void update_map_with_saved_link(RegisterMap* map, intptr_t** link_addr);
#endif // CPU_ARM_VM_FRAME_ARM_HPP

View File

@ -0,0 +1,248 @@
/*
* 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_FRAME_ARM_INLINE_HPP
#define CPU_ARM_VM_FRAME_ARM_INLINE_HPP
#include "code/codeCache.hpp"
#include "code/vmreg.inline.hpp"
// Inline functions for ARM frames:
// Constructors:
inline frame::frame() {
_pc = NULL;
_sp = NULL;
_unextended_sp = NULL;
_fp = NULL;
_cb = NULL;
_deopt_state = unknown;
}
inline void frame::init(intptr_t* sp, intptr_t* fp, address pc) {
_sp = sp;
_unextended_sp = sp;
_fp = fp;
_pc = pc;
assert(pc != NULL, "no pc?");
_cb = CodeCache::find_blob(pc);
adjust_unextended_sp();
address original_pc = CompiledMethod::get_deopt_original_pc(this);
if (original_pc != NULL) {
_pc = original_pc;
_deopt_state = is_deoptimized;
} else {
_deopt_state = not_deoptimized;
}
}
inline frame::frame(intptr_t* sp, intptr_t* fp, address pc) {
init(sp, fp, pc);
}
inline frame::frame(intptr_t* sp, intptr_t* unextended_sp, intptr_t* fp, address pc) {
_sp = sp;
_unextended_sp = unextended_sp;
_fp = fp;
_pc = pc;
assert(pc != NULL, "no pc?");
_cb = CodeCache::find_blob(pc);
adjust_unextended_sp();
address original_pc = CompiledMethod::get_deopt_original_pc(this);
if (original_pc != NULL) {
_pc = original_pc;
assert(_cb->as_compiled_method()->insts_contains(_pc), "original PC must be in CompiledMethod");
_deopt_state = is_deoptimized;
} else {
_deopt_state = not_deoptimized;
}
}
#ifndef AARCH64
inline frame::frame(intptr_t* sp, intptr_t* fp) {
_sp = sp;
_unextended_sp = sp;
_fp = fp;
assert(sp != NULL,"null SP ?");
_pc = (address)(sp[-1]);
// assert(_pc != NULL, "no pc?"); // see comments in x86
_cb = CodeCache::find_blob(_pc);
adjust_unextended_sp();
address original_pc = CompiledMethod::get_deopt_original_pc(this);
if (original_pc != NULL) {
_pc = original_pc;
_deopt_state = is_deoptimized;
} else {
_deopt_state = not_deoptimized;
}
}
#endif // !AARCH64
// Accessors
inline bool frame::equal(frame other) const {
bool ret = sp() == other.sp()
&& unextended_sp() == other.unextended_sp()
&& fp() == other.fp()
&& pc() == other.pc();
assert(!ret || ret && cb() == other.cb() && _deopt_state == other._deopt_state, "inconsistent construction");
return ret;
}
// Return unique id for this frame. The id must have a value where we can distinguish
// identity and younger/older relationship. NULL represents an invalid (incomparable)
// frame.
inline intptr_t* frame::id(void) const { return unextended_sp(); }
// Relationals on frames based
// Return true if the frame is younger (more recent activation) than the frame represented by id
inline bool frame::is_younger(intptr_t* id) const { assert(this->id() != NULL && id != NULL, "NULL frame id");
return this->id() < id ; }
// Return true if the frame is older (less recent activation) than the frame represented by id
inline bool frame::is_older(intptr_t* id) const { assert(this->id() != NULL && id != NULL, "NULL frame id");
return this->id() > id ; }
inline intptr_t* frame::link() const { return (intptr_t*) *(intptr_t **)addr_at(link_offset); }
inline intptr_t* frame::unextended_sp() const { return _unextended_sp; }
// Return address:
inline address* frame::sender_pc_addr() const { return (address*) addr_at(return_addr_offset); }
inline address frame::sender_pc() const { return *sender_pc_addr(); }
inline intptr_t* frame::sender_sp() const { return addr_at(sender_sp_offset); }
inline intptr_t** frame::interpreter_frame_locals_addr() const {
return (intptr_t**)addr_at(interpreter_frame_locals_offset);
}
#ifndef AARCH64
inline intptr_t* frame::interpreter_frame_last_sp() const {
return *(intptr_t**)addr_at(interpreter_frame_last_sp_offset);
}
#endif // !AARCH64
inline intptr_t* frame::interpreter_frame_bcp_addr() const {
return (intptr_t*)addr_at(interpreter_frame_bcp_offset);
}
inline intptr_t* frame::interpreter_frame_mdp_addr() const {
return (intptr_t*)addr_at(interpreter_frame_mdp_offset);
}
// Constant pool cache
inline ConstantPoolCache** frame::interpreter_frame_cache_addr() const {
return (ConstantPoolCache**)addr_at(interpreter_frame_cache_offset);
}
// Method
inline Method** frame::interpreter_frame_method_addr() const {
return (Method**)addr_at(interpreter_frame_method_offset);
}
inline oop* frame::interpreter_frame_mirror_addr() const {
return (oop*)addr_at(interpreter_frame_mirror_offset);
}
// top of expression stack
inline intptr_t* frame::interpreter_frame_tos_address() const {
#ifdef AARCH64
intptr_t* stack_top = (intptr_t*)*addr_at(interpreter_frame_stack_top_offset);
assert(stack_top != NULL, "should be stored before call");
assert(stack_top <= (intptr_t*) interpreter_frame_monitor_end(), "bad tos");
return stack_top;
#else
intptr_t* last_sp = interpreter_frame_last_sp();
if (last_sp == NULL ) {
return sp();
} else {
// sp() may have been extended or shrunk by an adapter. At least
// check that we don't fall behind the legal region.
// For top deoptimized frame last_sp == interpreter_frame_monitor_end.
assert(last_sp <= (intptr_t*) interpreter_frame_monitor_end(), "bad tos");
return last_sp;
}
#endif // AARCH64
}
inline oop* frame::interpreter_frame_temp_oop_addr() const {
return (oop *)(fp() + interpreter_frame_oop_temp_offset);
}
inline int frame::interpreter_frame_monitor_size() {
return BasicObjectLock::size();
}
// expression stack
// (the max_stack arguments are used by the GC; see class FrameClosure)
inline intptr_t* frame::interpreter_frame_expression_stack() const {
intptr_t* monitor_end = (intptr_t*) interpreter_frame_monitor_end();
return monitor_end-1;
}
inline jint frame::interpreter_frame_expression_stack_direction() { return -1; }
// Entry frames
inline JavaCallWrapper** frame::entry_frame_call_wrapper_addr() const {
return (JavaCallWrapper**)addr_at(entry_frame_call_wrapper_offset);
}
// Compiled frames
inline bool frame::volatile_across_calls(Register reg) {
return true;
}
inline oop frame::saved_oop_result(RegisterMap* map) const {
oop* result_adr = (oop*) map->location(R0->as_VMReg());
guarantee(result_adr != NULL, "bad register save location");
return (*result_adr);
}
inline void frame::set_saved_oop_result(RegisterMap* map, oop obj) {
oop* result_adr = (oop*) map->location(R0->as_VMReg());
guarantee(result_adr != NULL, "bad register save location");
*result_adr = obj;
}
#endif // CPU_ARM_VM_FRAME_ARM_INLINE_HPP

View File

@ -0,0 +1,79 @@
/*
* 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_GLOBALDEFINITIONS_ARM_HPP
#define CPU_ARM_VM_GLOBALDEFINITIONS_ARM_HPP
#ifdef AARCH64
#define AARCH64_ONLY(code) code
#define AARCH64_ONLY_ARG(arg) , arg
#define NOT_AARCH64(code)
#define NOT_AARCH64_ARG(arg)
#else
#define AARCH64_ONLY(code)
#define AARCH64_ONLY_ARG(arg)
#define NOT_AARCH64(code) code
#define NOT_AARCH64_ARG(arg) , arg
#endif
const int StackAlignmentInBytes = AARCH64_ONLY(16) NOT_AARCH64(8);
// Indicates whether the C calling conventions require that
// 32-bit integer argument values are extended to 64 bits.
const bool CCallingConventionRequiresIntsAsLongs = false;
#ifdef __SOFTFP__
const bool HaveVFP = false;
#else
const bool HaveVFP = true;
#endif
#if defined(__ARM_PCS_VFP) || defined(AARCH64)
#define __ABI_HARD__
#endif
#if defined(__ARM_ARCH_7A__) || defined(AARCH64)
#define SUPPORTS_NATIVE_CX8
#endif
#define STUBROUTINES_MD_HPP "stubRoutines_arm.hpp"
#define INTERP_MASM_MD_HPP "interp_masm_arm.hpp"
#define TEMPLATETABLE_MD_HPP "templateTable_arm.hpp"
#ifdef AARCH64
#define ADGLOBALS_MD_HPP "adfiles/adGlobals_arm_64.hpp"
#define AD_MD_HPP "adfiles/ad_arm_64.hpp"
#else
#define ADGLOBALS_MD_HPP "adfiles/adGlobals_arm_32.hpp"
#define AD_MD_HPP "adfiles/ad_arm_32.hpp"
#endif
#define C1_LIRGENERATOR_MD_HPP "c1_LIRGenerator_arm.hpp"
#ifdef TARGET_COMPILER_gcc
#ifdef ARM32
#undef BREAKPOINT
#define BREAKPOINT __asm__ volatile ("bkpt")
#endif
#endif
#endif // CPU_ARM_VM_GLOBALDEFINITIONS_ARM_HPP

View File

@ -0,0 +1,98 @@
/*
* 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_GLOBALS_ARM_HPP
#define CPU_ARM_VM_GLOBALS_ARM_HPP
//
// Sets the default values for platform dependent flags used by the runtime system.
// (see globals.hpp)
//
define_pd_global(bool, ShareVtableStubs, true);
define_pd_global(bool, ImplicitNullChecks, true); // Generate code for implicit null checks
define_pd_global(bool, UncommonNullCast, true); // Uncommon-trap NULLs past to check cast
define_pd_global(bool, TrapBasedNullChecks, false); // Not needed
define_pd_global(uintx, CodeCacheSegmentSize, 64 TIERED_ONLY(+64)); // Tiered compilation has large code-entry alignment.
define_pd_global(intx, CodeEntryAlignment, 16);
define_pd_global(intx, OptoLoopAlignment, 16);
define_pd_global(bool, NeedsDeoptSuspend, false); // only register window machines need this
#define DEFAULT_STACK_YELLOW_PAGES (2)
#define DEFAULT_STACK_RED_PAGES (1)
#define DEFAULT_STACK_SHADOW_PAGES (5 DEBUG_ONLY(+1))
#define DEFAULT_STACK_RESERVED_PAGES (0)
#define MIN_STACK_YELLOW_PAGES DEFAULT_STACK_YELLOW_PAGES
#define MIN_STACK_RED_PAGES DEFAULT_STACK_RED_PAGES
#define MIN_STACK_SHADOW_PAGES DEFAULT_STACK_SHADOW_PAGES
#define MIN_STACK_RESERVED_PAGES (0)
define_pd_global(intx, StackYellowPages, DEFAULT_STACK_YELLOW_PAGES);
define_pd_global(intx, StackRedPages, DEFAULT_STACK_RED_PAGES);
define_pd_global(intx, StackShadowPages, DEFAULT_STACK_SHADOW_PAGES);
define_pd_global(intx, StackReservedPages, DEFAULT_STACK_RESERVED_PAGES);
define_pd_global(intx, InlineFrequencyCount, 50);
#if defined(COMPILER1) || defined(COMPILER2)
define_pd_global(intx, InlineSmallCode, 1500);
#endif
define_pd_global(bool, RewriteBytecodes, true);
define_pd_global(bool, RewriteFrequentPairs, true);
define_pd_global(bool, UseMembar, true);
define_pd_global(bool, PreserveFramePointer, false);
// GC Ergo Flags
define_pd_global(size_t, CMSYoungGenPerWorker, 16*M); // default max size of CMS young gen, per GC worker thread
define_pd_global(uintx, TypeProfileLevel, 0);
// No performance work done here yet.
define_pd_global(bool, CompactStrings, false);
define_pd_global(intx, InitArrayShortSize, 8*BytesPerLong);
#define ARCH_FLAGS(develop, \
product, \
diagnostic, \
experimental, \
notproduct, \
range, \
constraint, \
writeable) \
\
develop(bool, VerifyInterpreterStackTop, false, \
"Verify interpreter stack top at every stack expansion (AArch64 only)") \
\
develop(bool, ZapHighNonSignificantBits, false, \
"Zap high non-significant bits of values (AArch64 only)") \
\
#endif // CPU_ARM_VM_GLOBALS_ARM_HPP

View File

@ -0,0 +1,66 @@
/*
* 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "asm/assembler.hpp"
#include "assembler_arm.inline.hpp"
#include "code/icBuffer.hpp"
#include "gc/shared/collectedHeap.inline.hpp"
#include "interpreter/bytecodes.hpp"
#include "memory/resourceArea.hpp"
#include "nativeInst_arm.hpp"
#include "oops/oop.inline.hpp"
#define __ masm->
int InlineCacheBuffer::ic_stub_code_size() {
return (AARCH64_ONLY(8) NOT_AARCH64(4)) * Assembler::InstructionSize;
}
void InlineCacheBuffer::assemble_ic_buffer_code(address code_begin, void* cached_value, address entry_point) {
ResourceMark rm;
CodeBuffer code(code_begin, ic_stub_code_size());
MacroAssembler* masm = new MacroAssembler(&code);
InlinedAddress oop_literal((address) cached_value);
__ ldr_literal(Ricklass, oop_literal);
// FIXME: OK to remove reloc here?
__ patchable_jump(entry_point, relocInfo::runtime_call_type, Rtemp);
__ bind_literal(oop_literal);
__ flush();
}
address InlineCacheBuffer::ic_buffer_entry_point(address code_begin) {
address jump_address;
jump_address = code_begin + NativeInstruction::instruction_size;
NativeJump* jump = nativeJump_at(jump_address);
return jump->jump_destination();
}
void* InlineCacheBuffer::ic_buffer_cached_value(address code_begin) {
NativeMovConstReg* move = nativeMovConstReg_at(code_begin);
return (void*)move->data();
}
#undef __

View File

@ -0,0 +1,94 @@
/*
* 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "asm/macroAssembler.hpp"
#include "assembler_arm.inline.hpp"
#include "runtime/icache.hpp"
#define __ _masm->
#ifdef AARCH64
static int icache_flush(address addr, int lines, int magic) {
// TODO-AARCH64 Figure out actual cache line size (mrs Xt, CTR_EL0)
address p = addr;
for (int i = 0; i < lines; i++, p += ICache::line_size) {
__asm__ volatile(
" dc cvau, %[p]"
:
: [p] "r" (p)
: "memory");
}
__asm__ volatile(
" dsb ish"
: : : "memory");
p = addr;
for (int i = 0; i < lines; i++, p += ICache::line_size) {
__asm__ volatile(
" ic ivau, %[p]"
:
: [p] "r" (p)
: "memory");
}
__asm__ volatile(
" dsb ish\n\t"
" isb\n\t"
: : : "memory");
return magic;
}
#else
static int icache_flush(address addr, int lines, int magic) {
__builtin___clear_cache(addr, addr + (lines << ICache::log2_line_size));
return magic;
}
#endif // AARCH64
void ICacheStubGenerator::generate_icache_flush(ICache::flush_icache_stub_t* flush_icache_stub) {
address start = (address)icache_flush;
*flush_icache_stub = (ICache::flush_icache_stub_t)start;
// ICache::invalidate_range() contains explicit condition that the first
// call is invoked on the generated icache flush stub code range.
ICache::invalidate_range(start, 0);
{
// dummy code mark to make the shared code happy
// (fields that would need to be modified to emulate the correct
// mark are not accessible)
StubCodeMark mark(this, "ICache", "fake_stub_for_inlined_icache_flush");
__ ret();
}
}
#undef __

View File

@ -0,0 +1,40 @@
/*
* Copyright (c) 2008, 2011, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_ICACHE_ARM_HPP
#define CPU_ARM_VM_ICACHE_ARM_HPP
// Interface for updating the instruction cache. Whenever the VM modifies
// code, part of the processor instruction cache potentially has to be flushed.
class ICache : public AbstractICache {
public:
enum {
stub_size = 32, // Size of the icache flush stub in bytes
line_size = BytesPerWord, // conservative
log2_line_size = LogBytesPerWord // log2(line_size)
};
};
#endif // CPU_ARM_VM_ICACHE_ARM_HPP

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,355 @@
/*
* 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_INTERP_MASM_ARM_HPP
#define CPU_ARM_VM_INTERP_MASM_ARM_HPP
#include "asm/macroAssembler.hpp"
#include "asm/macroAssembler.inline.hpp"
#include "interpreter/invocationCounter.hpp"
#include "runtime/frame.hpp"
#include "prims/jvmtiExport.hpp"
// This file specializes the assember with interpreter-specific macros
class InterpreterMacroAssembler: public MacroAssembler {
public:
// allow JvmtiExport checks to be extended
bool can_force_early_return() { return JvmtiExport::can_force_early_return(); }
bool can_post_interpreter_events() { return JvmtiExport::can_post_interpreter_events(); }
bool can_pop_frame() { return JvmtiExport::can_pop_frame(); }
bool can_post_breakpoint() { return JvmtiExport::can_post_breakpoint(); }
bool can_post_field_access() { return JvmtiExport::can_post_field_access(); }
bool can_post_field_modification() { return JvmtiExport::can_post_field_modification(); }
// flags controlled by JVMTI settings
bool rewrite_frequent_pairs() { return RewriteFrequentPairs; }
protected:
// Template interpreter specific version of call_VM_helper
virtual void call_VM_helper(Register oop_result, address entry_point, int number_of_arguments, bool check_exceptions);
virtual void check_and_handle_popframe();
virtual void check_and_handle_earlyret();
// base routine for all dispatches
typedef enum { DispatchDefault, DispatchNormal } DispatchTableMode;
void dispatch_base(TosState state, DispatchTableMode table_mode, bool verifyoop = true);
public:
InterpreterMacroAssembler(CodeBuffer* code);
// Interpreter-specific registers
#if defined(AARCH64) && defined(ASSERT)
#define check_stack_top() _check_stack_top("invalid Rstack_top at " __FILE__ ":" XSTR(__LINE__))
#define check_stack_top_on_expansion() _check_stack_top("invalid Rstack_top at " __FILE__ ":" XSTR(__LINE__), VerifyInterpreterStackTop)
#define check_extended_sp(tmp) _check_extended_sp(tmp, "SP does not match extended SP in frame at " __FILE__ ":" XSTR(__LINE__))
#define check_no_cached_stack_top(tmp) _check_no_cached_stack_top(tmp, "stack_top is already cached in frame at " __FILE__ ":" XSTR(__LINE__))
void _check_stack_top(const char* msg, bool enabled = true) {
if (enabled) {
Label L;
cmp(SP, Rstack_top);
b(L, ls);
stop(msg);
bind(L);
}
}
void _check_extended_sp(Register tmp, const char* msg) {
Label L;
ldr(tmp, Address(FP, frame::interpreter_frame_extended_sp_offset * wordSize));
cmp(SP, tmp);
b(L, eq);
stop(msg);
bind(L);
}
void _check_no_cached_stack_top(Register tmp, const char* msg) {
Label L;
ldr(tmp, Address(FP, frame::interpreter_frame_stack_top_offset * wordSize));
cbz(tmp, L);
stop(msg);
bind(L);
}
#else
inline void check_stack_top() {}
inline void check_stack_top_on_expansion() {}
inline void check_extended_sp(Register tmp) {}
inline void check_no_cached_stack_top(Register tmp) {}
#endif // AARCH64 && ASSERT
void save_bcp() { str(Rbcp, Address(FP, frame::interpreter_frame_bcp_offset * wordSize)); }
void restore_bcp() { ldr(Rbcp, Address(FP, frame::interpreter_frame_bcp_offset * wordSize)); }
void restore_locals() { ldr(Rlocals, Address(FP, frame::interpreter_frame_locals_offset * wordSize)); }
void restore_method() { ldr(Rmethod, Address(FP, frame::interpreter_frame_method_offset * wordSize)); }
void restore_dispatch();
#ifdef AARCH64
void save_stack_top() { check_stack_top(); str(Rstack_top, Address(FP, frame::interpreter_frame_stack_top_offset * wordSize)); }
void clear_cached_stack_top() { str(ZR, Address(FP, frame::interpreter_frame_stack_top_offset * wordSize)); }
void restore_stack_top() { ldr(Rstack_top, Address(FP, frame::interpreter_frame_stack_top_offset * wordSize)); clear_cached_stack_top(); check_stack_top(); }
void cut_sp_before_call() { align_reg(SP, Rstack_top, StackAlignmentInBytes); }
void restore_sp_after_call(Register tmp) { ldr(tmp, Address(FP, frame::interpreter_frame_extended_sp_offset * wordSize)); mov(SP, tmp); }
#endif
// Helpers for runtime call arguments/results
void get_const(Register reg) { ldr(reg, Address(Rmethod, Method::const_offset())); }
void get_constant_pool(Register reg) { get_const(reg); ldr(reg, Address(reg, ConstMethod::constants_offset())); }
void get_constant_pool_cache(Register reg) { get_constant_pool(reg); ldr(reg, Address(reg, ConstantPool::cache_offset_in_bytes())); }
void get_cpool_and_tags(Register cpool, Register tags) { get_constant_pool(cpool); ldr(tags, Address(cpool, ConstantPool::tags_offset_in_bytes())); }
// Sets reg. Blows Rtemp.
void get_unsigned_2_byte_index_at_bcp(Register reg, int bcp_offset);
// Sets index. Blows reg_tmp.
void get_index_at_bcp(Register index, int bcp_offset, Register reg_tmp, size_t index_size = sizeof(u2));
// Sets cache, index.
void get_cache_and_index_at_bcp(Register cache, Register index, int bcp_offset, size_t index_size = sizeof(u2));
void get_cache_and_index_and_bytecode_at_bcp(Register cache, Register index, Register bytecode, int byte_no, int bcp_offset, size_t index_size = sizeof(u2));
// Sets cache. Blows reg_tmp.
void get_cache_entry_pointer_at_bcp(Register cache, Register reg_tmp, int bcp_offset, size_t index_size = sizeof(u2));
// Load object from cpool->resolved_references(*bcp+1)
void load_resolved_reference_at_index(Register result, Register tmp);
void store_check_part1(Register card_table_base); // Sets card_table_base register.
void store_check_part2(Register obj, Register card_table_base, Register tmp);
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
void pop_l(Register r = R0_tos);
#else
void pop_l(Register lo = R0_tos_lo, Register hi = R1_tos_hi);
#endif
void pop_f(FloatRegister fd);
void pop_d(FloatRegister fd);
void push_ptr(Register r);
void push_i(Register r = R0_tos);
#ifdef AARCH64
void push_l(Register r = R0_tos);
#else
void push_l(Register lo = R0_tos_lo, Register hi = R1_tos_hi);
#endif
void push_f();
void push_d();
// Transition vtos -> state. Blows R0, R1. Sets TOS cached value.
void pop(TosState state);
// Transition state -> vtos. Blows Rtemp.
void push(TosState state);
#ifndef AARCH64
// The following methods are overridden to allow overloaded calls to
// MacroAssembler::push/pop(Register)
// MacroAssembler::push/pop(RegisterSet)
// InterpreterMacroAssembler::push/pop(TosState)
void push(Register rd, AsmCondition cond = al) { MacroAssembler::push(rd, cond); }
void pop(Register rd, AsmCondition cond = al) { MacroAssembler::pop(rd, cond); }
void push(RegisterSet reg_set, AsmCondition cond = al) { MacroAssembler::push(reg_set, cond); }
void pop(RegisterSet reg_set, AsmCondition cond = al) { MacroAssembler::pop(reg_set, cond); }
// Converts return value in R0/R1 (interpreter calling conventions) to TOS cached value.
void convert_retval_to_tos(TosState state);
// Converts TOS cached value to return value in R0/R1 (according to interpreter calling conventions).
void convert_tos_to_retval(TosState state);
#endif
// JVMTI ForceEarlyReturn support
void load_earlyret_value(TosState state);
void jump_to_entry(address entry);
// Blows Rtemp.
void empty_expression_stack() {
ldr(Rstack_top, Address(FP, frame::interpreter_frame_monitor_block_top_offset * wordSize));
check_stack_top();
#ifdef AARCH64
clear_cached_stack_top();
#else
// NULL last_sp until next java call
str(zero_register(Rtemp), Address(FP, frame::interpreter_frame_last_sp_offset * wordSize));
#endif // AARCH64
}
// Helpers for swap and dup
void load_ptr(int n, Register val);
void store_ptr(int n, Register val);
// Generate a subtype check: branch to not_subtype if sub_klass is
// not a subtype of super_klass.
// Profiling code for the subtype check failure (profile_typecheck_failed)
// should be explicitly generated by the caller in the not_subtype case.
// Blows Rtemp, tmp1, tmp2.
void gen_subtype_check(Register Rsub_klass, Register Rsuper_klass,
Label &not_subtype, Register tmp1, Register tmp2);
// Dispatching
void dispatch_prolog(TosState state, int step = 0);
void dispatch_epilog(TosState state, int step = 0);
void dispatch_only(TosState state); // dispatch by R3_bytecode
void dispatch_only_normal(TosState state); // dispatch normal table by R3_bytecode
void dispatch_only_noverify(TosState state);
void dispatch_next(TosState state, int step = 0); // load R3_bytecode from [Rbcp + step] and dispatch by R3_bytecode
// jump to an invoked target
void prepare_to_jump_from_interpreted();
void jump_from_interpreted(Register method);
void narrow(Register result);
// Returning from interpreted functions
//
// Removes the current activation (incl. unlocking of monitors)
// and sets up the return address. This code is also used for
// exception unwindwing. In that case, we do not want to throw
// IllegalMonitorStateExceptions, since that might get us into an
// infinite rethrow exception loop.
// Additionally this code is used for popFrame and earlyReturn.
// In popFrame case we want to skip throwing an exception,
// installing an exception, and notifying jvmdi.
// In earlyReturn case we only want to skip throwing an exception
// and installing an exception.
void remove_activation(TosState state, Register ret_addr,
bool throw_monitor_exception = true,
bool install_monitor_exception = true,
bool notify_jvmdi = true);
// At certain points in the method invocation the monitor of
// synchronized methods hasn't been entered yet.
// To correctly handle exceptions at these points, we set the thread local
// variable _do_not_unlock_if_synchronized to true. The remove_activation will
// check this flag.
void set_do_not_unlock_if_synchronized(bool flag, Register tmp);
// Debugging
void interp_verify_oop(Register reg, TosState state, const char* file, int line); // only if +VerifyOops && state == atos
void verify_FPU(int stack_depth, TosState state = ftos) {
// No VFP state verification is required for ARM
}
// Object locking
void lock_object (Register lock_reg);
void unlock_object(Register lock_reg);
// Interpreter profiling operations
void set_method_data_pointer_for_bcp(); // Blows R0-R3/R0-R18, Rtemp, LR
void test_method_data_pointer(Register mdp, Label& zero_continue);
void verify_method_data_pointer();
void set_mdp_data_at(Register mdp_in, int offset, Register value);
// Increments mdp data. Sets bumped_count register to adjusted counter.
void increment_mdp_data_at(Address data, Register bumped_count, bool decrement = false);
// Increments mdp data. Sets bumped_count register to adjusted counter.
void increment_mdp_data_at(Register mdp_in, int offset, Register bumped_count, bool decrement = false);
void increment_mask_and_jump(Address counter_addr,
int increment, Address mask_addr,
Register scratch, Register scratch2,
AsmCondition cond, Label* where);
void set_mdp_flag_at(Register mdp_in, int flag_constant);
void test_mdp_data_at(Register mdp_in, int offset, Register value,
Register test_value_out,
Label& not_equal_continue);
void record_klass_in_profile(Register receiver, Register mdp,
Register reg_tmp, bool is_virtual_call);
void record_klass_in_profile_helper(Register receiver, Register mdp,
Register reg_tmp,
int start_row, Label& done, bool is_virtual_call);
void update_mdp_by_offset(Register mdp_in, int offset_of_offset, Register reg_tmp);
void update_mdp_by_offset(Register mdp_in, Register reg_offset, Register reg_tmp);
void update_mdp_by_constant(Register mdp_in, int constant);
void update_mdp_for_ret(Register return_bci); // Blows R0-R3/R0-R18, Rtemp, LR
void profile_taken_branch(Register mdp, Register bumped_count); // Sets mdp, bumped_count registers, blows Rtemp.
void profile_not_taken_branch(Register mdp); // Sets mdp, blows Rtemp.
void profile_call(Register mdp); // Sets mdp, blows Rtemp.
void profile_final_call(Register mdp); // Sets mdp, blows Rtemp.
void profile_virtual_call(Register mdp, Register receiver, // Sets mdp, blows Rtemp.
bool receiver_can_be_null = false);
void profile_ret(Register mdp, Register return_bci); // Sets mdp, blows R0-R3/R0-R18, Rtemp, LR
void profile_null_seen(Register mdp); // Sets mdp.
void profile_typecheck(Register mdp, Register klass); // Sets mdp, blows Rtemp.
void profile_typecheck_failed(Register mdp); // Sets mdp, blows Rtemp.
void profile_switch_default(Register mdp); // Sets mdp, blows Rtemp.
// Sets mdp. Blows reg_tmp1, reg_tmp2. Index could be the same as reg_tmp2.
void profile_switch_case(Register mdp, Register index, Register reg_tmp1, Register reg_tmp2);
void byteswap_u32(Register r, Register rtmp1, Register rtmp2);
void inc_global_counter(address address_of_counter, int offset_in_bytes, Register tmp1, Register tmp2, bool avoid_overflow);
typedef enum { NotifyJVMTI, SkipNotifyJVMTI } NotifyMethodExitMode;
// support for jvmti
void notify_method_entry();
void notify_method_exit(TosState state, NotifyMethodExitMode mode,
bool native = false, Register result_lo = noreg, Register result_hi = noreg, FloatRegister result_fp = fnoreg);
void trace_state(const char* msg) PRODUCT_RETURN;
void get_method_counters(Register method, Register Rcounters, Label& skip);
};
#endif // CPU_ARM_VM_INTERP_MASM_ARM_HPP

View File

@ -0,0 +1,449 @@
/*
* Copyright (c) 2008, 2015, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "interpreter/interpreter.hpp"
#include "interpreter/interpreterRuntime.hpp"
#include "memory/allocation.inline.hpp"
#include "memory/universe.inline.hpp"
#include "oops/method.hpp"
#include "oops/oop.inline.hpp"
#include "runtime/handles.inline.hpp"
#include "runtime/icache.hpp"
#include "runtime/interfaceSupport.hpp"
#include "runtime/signature.hpp"
#define __ _masm->
#ifdef SHARING_FAST_NATIVE_FINGERPRINTS
// mapping from SignatureIterator param to (common) type of parsing
static const u1 shared_type[] = {
(u1) SignatureIterator::int_parm, // bool
(u1) SignatureIterator::int_parm, // byte
(u1) SignatureIterator::int_parm, // char
(u1) SignatureIterator::int_parm, // short
(u1) SignatureIterator::int_parm, // int
(u1) SignatureIterator::long_parm, // long
#ifndef __ABI_HARD__
(u1) SignatureIterator::int_parm, // float, passed as int
(u1) SignatureIterator::long_parm, // double, passed as long
#else
(u1) SignatureIterator::float_parm, // float
(u1) SignatureIterator::double_parm, // double
#endif
(u1) SignatureIterator::obj_parm, // obj
(u1) SignatureIterator::done_parm // done
};
uint64_t InterpreterRuntime::normalize_fast_native_fingerprint(uint64_t fingerprint) {
if (fingerprint == UCONST64(-1)) {
// special signature used when the argument list cannot be encoded in a 64 bits value
return fingerprint;
}
int shift = SignatureIterator::static_feature_size;
uint64_t result = fingerprint & ((1 << shift) - 1);
fingerprint >>= shift;
BasicType ret_type = (BasicType) (fingerprint & SignatureIterator::result_feature_mask);
// For ARM, the fast signature handler only needs to know whether
// the return value must be unboxed. T_OBJECT and T_ARRAY need not
// be distinguished from each other and all other return values
// behave like integers with respect to the handler.
bool unbox = (ret_type == T_OBJECT) || (ret_type == T_ARRAY);
if (unbox) {
ret_type = T_OBJECT;
} else {
ret_type = T_INT;
}
result |= ((uint64_t) ret_type) << shift;
shift += SignatureIterator::result_feature_size;
fingerprint >>= SignatureIterator::result_feature_size;
while (true) {
uint32_t type = (uint32_t) (fingerprint & SignatureIterator::parameter_feature_mask);
if (type == SignatureIterator::done_parm) {
result |= ((uint64_t) SignatureIterator::done_parm) << shift;
return result;
}
assert((type >= SignatureIterator::bool_parm) && (type <= SignatureIterator::obj_parm), "check fingerprint encoding");
int shared = shared_type[type - SignatureIterator::bool_parm];
result |= ((uint64_t) shared) << shift;
shift += SignatureIterator::parameter_feature_size;
fingerprint >>= SignatureIterator::parameter_feature_size;
}
}
#endif // SHARING_FAST_NATIVE_FINGERPRINTS
// Implementation of SignatureHandlerGenerator
void InterpreterRuntime::SignatureHandlerGenerator::pass_int() {
if (_ireg < GPR_PARAMS) {
Register dst = as_Register(_ireg);
__ ldr_s32(dst, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));
_ireg++;
} else {
__ ldr_s32(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));
__ str_32(Rtemp, Address(SP, _abi_offset * wordSize));
_abi_offset++;
}
}
void InterpreterRuntime::SignatureHandlerGenerator::pass_long() {
#ifdef AARCH64
if (_ireg < GPR_PARAMS) {
Register dst = as_Register(_ireg);
__ ldr(dst, Address(Rlocals, Interpreter::local_offset_in_bytes(offset() + 1)));
_ireg++;
} else {
__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset() + 1)));
__ str(Rtemp, Address(SP, _abi_offset * wordSize));
_abi_offset++;
}
#else
if (_ireg <= 2) {
#if (ALIGN_WIDE_ARGUMENTS == 1)
if ((_ireg & 1) != 0) {
// 64-bit values should be 8-byte aligned
_ireg++;
}
#endif
Register dst1 = as_Register(_ireg);
Register dst2 = as_Register(_ireg+1);
__ ldr(dst1, Address(Rlocals, Interpreter::local_offset_in_bytes(offset()+1)));
__ ldr(dst2, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));
_ireg += 2;
#if (ALIGN_WIDE_ARGUMENTS == 0)
} else if (_ireg == 3) {
// uses R3 + one stack slot
Register dst1 = as_Register(_ireg);
__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));
__ ldr(dst1, Address(Rlocals, Interpreter::local_offset_in_bytes(offset()+1)));
__ str(Rtemp, Address(SP, _abi_offset * wordSize));
_ireg += 1;
_abi_offset += 1;
#endif
} else {
#if (ALIGN_WIDE_ARGUMENTS == 1)
if(_abi_offset & 1) _abi_offset++;
#endif
__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset()+1)));
__ str(Rtemp, Address(SP, (_abi_offset) * wordSize));
__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));
__ str(Rtemp, Address(SP, (_abi_offset+1) * wordSize));
_abi_offset += 2;
_ireg = 4;
}
#endif // AARCH64
}
void InterpreterRuntime::SignatureHandlerGenerator::pass_object() {
#ifdef AARCH64
__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));
__ cmp(Rtemp, 0);
__ sub(Rtemp, Rlocals, -Interpreter::local_offset_in_bytes(offset()));
if (_ireg < GPR_PARAMS) {
Register dst = as_Register(_ireg);
__ csel(dst, ZR, Rtemp, eq);
_ireg++;
} else {
__ csel(Rtemp, ZR, Rtemp, eq);
__ str(Rtemp, Address(SP, _abi_offset * wordSize));
_abi_offset++;
}
#else
if (_ireg < 4) {
Register dst = as_Register(_ireg);
__ ldr(dst, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));
__ cmp(dst, 0);
__ sub(dst, Rlocals, -Interpreter::local_offset_in_bytes(offset()), ne);
_ireg++;
} else {
__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));
__ cmp(Rtemp, 0);
__ sub(Rtemp, Rlocals, -Interpreter::local_offset_in_bytes(offset()), ne);
__ str(Rtemp, Address(SP, _abi_offset * wordSize));
_abi_offset++;
}
#endif // AARCH64
}
#ifndef __ABI_HARD__
void InterpreterRuntime::SignatureHandlerGenerator::pass_float() {
if (_ireg < 4) {
Register dst = as_Register(_ireg);
__ ldr(dst, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));
_ireg++;
} else {
__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));
__ str(Rtemp, Address(SP, _abi_offset * wordSize));
_abi_offset++;
}
}
#else
#ifndef __SOFTFP__
void InterpreterRuntime::SignatureHandlerGenerator::pass_float() {
#ifdef AARCH64
if (_freg < FPR_PARAMS) {
FloatRegister dst = as_FloatRegister(_freg);
__ ldr_s(dst, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));
_freg++;
} else {
__ ldr_u32(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));
__ str_32(Rtemp, Address(SP, _abi_offset * wordSize));
_abi_offset++;
}
#else
if((_fp_slot < 16) || (_single_fpr_slot & 1)) {
if ((_single_fpr_slot & 1) == 0) {
_single_fpr_slot = _fp_slot;
_fp_slot += 2;
}
__ flds(as_FloatRegister(_single_fpr_slot), Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));
_single_fpr_slot++;
} else {
__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));
__ str(Rtemp, Address(SP, _abi_offset * wordSize));
_abi_offset++;
}
#endif // AARCH64
}
void InterpreterRuntime::SignatureHandlerGenerator::pass_double() {
#ifdef AARCH64
if (_freg < FPR_PARAMS) {
FloatRegister dst = as_FloatRegister(_freg);
__ ldr_d(dst, Address(Rlocals, Interpreter::local_offset_in_bytes(offset() + 1)));
_freg++;
} else {
__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset() + 1)));
__ str(Rtemp, Address(SP, _abi_offset * wordSize));
_abi_offset++;
}
#else
if(_fp_slot <= 14) {
__ fldd(as_FloatRegister(_fp_slot), Address(Rlocals, Interpreter::local_offset_in_bytes(offset()+1)));
_fp_slot += 2;
} else {
__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset()+1)));
__ str(Rtemp, Address(SP, (_abi_offset) * wordSize));
__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));
__ str(Rtemp, Address(SP, (_abi_offset+1) * wordSize));
_abi_offset += 2;
_single_fpr_slot = 16;
}
#endif // AARCH64
}
#endif // __SOFTFP__
#endif // __ABI_HARD__
void InterpreterRuntime::SignatureHandlerGenerator::generate(uint64_t fingerprint) {
iterate(fingerprint);
BasicType result_type = SignatureIterator::return_type(fingerprint);
address result_handler = Interpreter::result_handler(result_type);
#ifdef AARCH64
__ mov_slow(R0, (address)result_handler);
#else
// Check that result handlers are not real handler on ARM (0 or -1).
// This ensures the signature handlers do not need symbolic information.
assert((result_handler == NULL)||(result_handler==(address)0xffffffff),"");
__ mov_slow(R0, (intptr_t)result_handler);
#endif
__ ret();
}
// Implementation of SignatureHandlerLibrary
void SignatureHandlerLibrary::pd_set_handler(address handler) {}
class SlowSignatureHandler: public NativeSignatureIterator {
private:
address _from;
intptr_t* _to;
#ifndef __ABI_HARD__
virtual void pass_int() {
*_to++ = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));
_from -= Interpreter::stackElementSize;
}
virtual void pass_float() {
*_to++ = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));
_from -= Interpreter::stackElementSize;
}
virtual void pass_long() {
#if (ALIGN_WIDE_ARGUMENTS == 1)
if (((intptr_t)_to & 7) != 0) {
// 64-bit values should be 8-byte aligned
_to++;
}
#endif
_to[0] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(1));
_to[1] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(0));
_to += 2;
_from -= 2*Interpreter::stackElementSize;
}
virtual void pass_object() {
intptr_t from_addr = (intptr_t)(_from + Interpreter::local_offset_in_bytes(0));
*_to++ = (*(intptr_t*)from_addr == 0) ? (intptr_t)NULL : from_addr;
_from -= Interpreter::stackElementSize;
}
#else
intptr_t* _toFP;
intptr_t* _toGP;
int _last_gp;
int _last_fp;
#ifndef AARCH64
int _last_single_fp;
#endif // !AARCH64
virtual void pass_int() {
if(_last_gp < GPR_PARAMS) {
_toGP[_last_gp++] = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));
} else {
*_to++ = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));
}
_from -= Interpreter::stackElementSize;
}
virtual void pass_long() {
#ifdef AARCH64
if(_last_gp < GPR_PARAMS) {
_toGP[_last_gp++] = *(jlong *)(_from+Interpreter::local_offset_in_bytes(1));
} else {
*_to++ = *(jlong *)(_from+Interpreter::local_offset_in_bytes(1));
}
#else
assert(ALIGN_WIDE_ARGUMENTS == 1, "ABI_HARD not supported with unaligned wide arguments");
if (_last_gp <= 2) {
if(_last_gp & 1) _last_gp++;
_toGP[_last_gp++] = *(jint *)(_from+Interpreter::local_offset_in_bytes(1));
_toGP[_last_gp++] = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));
} else {
if (((intptr_t)_to & 7) != 0) {
// 64-bit values should be 8-byte aligned
_to++;
}
_to[0] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(1));
_to[1] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(0));
_to += 2;
_last_gp = 4;
}
#endif // AARCH64
_from -= 2*Interpreter::stackElementSize;
}
virtual void pass_object() {
intptr_t from_addr = (intptr_t)(_from + Interpreter::local_offset_in_bytes(0));
if(_last_gp < GPR_PARAMS) {
_toGP[_last_gp++] = (*(intptr_t*)from_addr == 0) ? NULL : from_addr;
} else {
*_to++ = (*(intptr_t*)from_addr == 0) ? NULL : from_addr;
}
_from -= Interpreter::stackElementSize;
}
virtual void pass_float() {
#ifdef AARCH64
if(_last_fp < FPR_PARAMS) {
_toFP[_last_fp++] = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));
} else {
*_to++ = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));
}
#else
if((_last_fp < 16) || (_last_single_fp & 1)) {
if ((_last_single_fp & 1) == 0) {
_last_single_fp = _last_fp;
_last_fp += 2;
}
_toFP[_last_single_fp++] = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));
} else {
*_to++ = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));
}
#endif // AARCH64
_from -= Interpreter::stackElementSize;
}
virtual void pass_double() {
#ifdef AARCH64
if(_last_fp < FPR_PARAMS) {
_toFP[_last_fp++] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(1));
} else {
*_to++ = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(1));
}
#else
assert(ALIGN_WIDE_ARGUMENTS == 1, "ABI_HARD not supported with unaligned wide arguments");
if(_last_fp <= 14) {
_toFP[_last_fp++] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(1));
_toFP[_last_fp++] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(0));
} else {
if (((intptr_t)_to & 7) != 0) { // 64-bit values should be 8-byte aligned
_to++;
}
_to[0] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(1));
_to[1] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(0));
_to += 2;
_last_single_fp = 16;
}
#endif // AARCH64
_from -= 2*Interpreter::stackElementSize;
}
#endif // !__ABI_HARD__
public:
SlowSignatureHandler(methodHandle method, address from, intptr_t* to) :
NativeSignatureIterator(method) {
_from = from;
#ifdef __ABI_HARD__
_toGP = to;
_toFP = _toGP + GPR_PARAMS;
_to = _toFP + AARCH64_ONLY(FPR_PARAMS) NOT_AARCH64(8*2);
_last_gp = (is_static() ? 2 : 1);
_last_fp = 0;
#ifndef AARCH64
_last_single_fp = 0;
#endif // !AARCH64
#else
_to = to + (is_static() ? 2 : 1);
#endif // __ABI_HARD__
}
};
IRT_ENTRY(address, InterpreterRuntime::slow_signature_handler(JavaThread* thread, Method* method, intptr_t* from, intptr_t* to))
methodHandle m(thread, (Method*)method);
assert(m->is_native(), "sanity check");
SlowSignatureHandler(m, (address)from, to).iterate(UCONST64(-1));
return Interpreter::result_handler(m->result_type());
IRT_END

View File

@ -0,0 +1,84 @@
/*
* Copyright (c) 2008, 2013, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_INTERPRETERRT_ARM_HPP
#define CPU_ARM_VM_INTERPRETERRT_ARM_HPP
#include "memory/allocation.hpp"
// native method calls
class SignatureHandlerGenerator: public NativeSignatureIterator {
private:
MacroAssembler* _masm;
int _abi_offset;
int _ireg;
#ifdef __ABI_HARD__
#ifdef AARCH64
int _freg;
#else
int _fp_slot; // number of FPR's with arguments loaded
int _single_fpr_slot;
#endif
#endif
void move(int from_offset, int to_offset);
void box(int from_offset, int to_offset);
void pass_int();
void pass_long();
void pass_float();
void pass_object();
#ifdef __ABI_HARD__
void pass_double();
#endif
public:
// Creation
SignatureHandlerGenerator(methodHandle method, CodeBuffer* buffer) : NativeSignatureIterator(method) {
_masm = new MacroAssembler(buffer);
_abi_offset = 0;
_ireg = is_static() ? 2 : 1;
#ifdef __ABI_HARD__
#ifdef AARCH64
_freg = 0;
#else
_fp_slot = 0;
_single_fpr_slot = 0;
#endif
#endif
}
// Code generation
void generate(uint64_t fingerprint);
};
#ifndef AARCH64
// ARM provides a normalized fingerprint for native calls (to increase
// sharing). See normalize_fast_native_fingerprint
#define SHARING_FAST_NATIVE_FINGERPRINTS
#endif
#endif // CPU_ARM_VM_INTERPRETERRT_ARM_HPP

View File

@ -0,0 +1,86 @@
/*
* Copyright (c) 2008, 2011, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_JAVAFRAMEANCHOR_ARM_HPP
#define CPU_ARM_VM_JAVAFRAMEANCHOR_ARM_HPP
private:
// FP value associated with _last_Java_sp:
intptr_t* volatile _last_Java_fp; // pointer is volatile not what it points to
public:
// Each arch must define reset, save, restore
// These are used by objects that only care about:
// 1 - initializing a new state (thread creation, javaCalls)
// 2 - saving a current state (javaCalls)
// 3 - restoring an old state (javaCalls)
void clear(void) {
// clearing _last_Java_sp must be first
_last_Java_sp = NULL;
// fence?
_last_Java_fp = NULL;
_last_Java_pc = NULL;
}
void copy(JavaFrameAnchor* src) {
// In order to make sure the transition state is valid for "this"
// We must clear _last_Java_sp before copying the rest of the new data
//
// Hack Alert: Temporary bugfix for 4717480/4721647
// To act like previous version (pd_cache_state) don't NULL _last_Java_sp
// unless the value is changing
//
if (_last_Java_sp != src->_last_Java_sp)
_last_Java_sp = NULL;
_last_Java_fp = src->_last_Java_fp;
_last_Java_pc = src->_last_Java_pc;
// Must be last so profiler will always see valid frame if has_last_frame() is true
_last_Java_sp = src->_last_Java_sp;
}
// Always walkable
bool walkable(void) { return true; }
// Never any thing to do since we are always walkable and can find address of return addresses
void make_walkable(JavaThread* thread) { }
intptr_t* last_Java_sp(void) const { return _last_Java_sp; }
address last_Java_pc(void) { return _last_Java_pc; }
private:
static ByteSize last_Java_fp_offset() { return byte_offset_of(JavaFrameAnchor, _last_Java_fp); }
public:
void set_last_Java_sp(intptr_t* sp) { _last_Java_sp = sp; }
intptr_t* last_Java_fp(void) { return _last_Java_fp; }
// Assert (last_Java_sp == NULL || fp == NULL)
void set_last_Java_fp(intptr_t* fp) { _last_Java_fp = fp; }
#endif // CPU_ARM_VM_JAVAFRAMEANCHOR_ARM_HPP

View File

@ -0,0 +1,277 @@
/*
* 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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 "precompiled.hpp"
#include "asm/macroAssembler.hpp"
#include "assembler_arm.inline.hpp"
#include "memory/resourceArea.hpp"
#include "prims/jniFastGetField.hpp"
#include "prims/jvm_misc.hpp"
#include "runtime/safepoint.hpp"
#define __ masm->
#define BUFFER_SIZE 96
address JNI_FastGetField::generate_fast_get_int_field0(BasicType type) {
const char* name = NULL;
address slow_case_addr = NULL;
switch (type) {
case T_BOOLEAN:
name = "jni_fast_GetBooleanField";
slow_case_addr = jni_GetBooleanField_addr();
break;
case T_BYTE:
name = "jni_fast_GetByteField";
slow_case_addr = jni_GetByteField_addr();
break;
case T_CHAR:
name = "jni_fast_GetCharField";
slow_case_addr = jni_GetCharField_addr();
break;
case T_SHORT:
name = "jni_fast_GetShortField";
slow_case_addr = jni_GetShortField_addr();
break;
case T_INT:
name = "jni_fast_GetIntField";
slow_case_addr = jni_GetIntField_addr();
break;
case T_LONG:
name = "jni_fast_GetLongField";
slow_case_addr = jni_GetLongField_addr();
break;
case T_FLOAT:
name = "jni_fast_GetFloatField";
slow_case_addr = jni_GetFloatField_addr();
break;
case T_DOUBLE:
name = "jni_fast_GetDoubleField";
slow_case_addr = jni_GetDoubleField_addr();
break;
default:
ShouldNotReachHere();
}
// R0 - jni env
// R1 - object handle
// R2 - jfieldID
const Register Rsafepoint_counter_addr = AARCH64_ONLY(R4) NOT_AARCH64(R3);
const Register Robj = AARCH64_ONLY(R5) NOT_AARCH64(R1);
const Register Rres = AARCH64_ONLY(R6) NOT_AARCH64(R0);
#ifndef AARCH64
const Register Rres_hi = R1;
#endif // !AARCH64
const Register Rsafept_cnt = Rtemp;
const Register Rsafept_cnt2 = Rsafepoint_counter_addr;
const Register Rtmp1 = AARCH64_ONLY(R7) NOT_AARCH64(R3); // same as Rsafepoint_counter_addr on 32-bit ARM
const Register Rtmp2 = AARCH64_ONLY(R8) NOT_AARCH64(R2); // same as jfieldID on 32-bit ARM
#ifdef AARCH64
assert_different_registers(Rsafepoint_counter_addr, Rsafept_cnt, Robj, Rres, Rtmp1, Rtmp2, R0, R1, R2, LR);
assert_different_registers(Rsafept_cnt2, Rsafept_cnt, Rres, R0, R1, R2, LR);
#else
assert_different_registers(Rsafepoint_counter_addr, Rsafept_cnt, Robj, Rres, LR);
assert_different_registers(Rsafept_cnt, R1, R2, Rtmp1, LR);
assert_different_registers(Rsafepoint_counter_addr, Rsafept_cnt, Rres, Rres_hi, Rtmp2, LR);
assert_different_registers(Rsafept_cnt2, Rsafept_cnt, Rres, Rres_hi, LR);
#endif // AARCH64
address fast_entry;
ResourceMark rm;
BufferBlob* blob = BufferBlob::create(name, BUFFER_SIZE);
CodeBuffer cbuf(blob);
MacroAssembler* masm = new MacroAssembler(&cbuf);
fast_entry = __ pc();
// Safepoint check
InlinedAddress safepoint_counter_addr(SafepointSynchronize::safepoint_counter_addr());
Label slow_case;
__ ldr_literal(Rsafepoint_counter_addr, safepoint_counter_addr);
#ifndef AARCH64
__ push(RegisterSet(R0, R3)); // save incoming arguments for slow case
#endif // !AARCH64
__ ldr_s32(Rsafept_cnt, Address(Rsafepoint_counter_addr));
__ tbnz(Rsafept_cnt, 0, slow_case);
if (os::is_MP()) {
// Address dependency restricts memory access ordering. It's cheaper than explicit LoadLoad barrier
__ andr(Rtmp1, Rsafept_cnt, (unsigned)1);
__ ldr(Robj, Address(R1, Rtmp1));
} else {
__ ldr(Robj, Address(R1));
}
#ifdef AARCH64
__ add(Robj, Robj, AsmOperand(R2, lsr, 2));
Address field_addr = Address(Robj);
#else
Address field_addr;
if (type != T_BOOLEAN
&& type != T_INT
#ifndef __ABI_HARD__
&& type != T_FLOAT
#endif // !__ABI_HARD__
) {
// Only ldr and ldrb support embedded shift, other loads do not
__ add(Robj, Robj, AsmOperand(R2, lsr, 2));
field_addr = Address(Robj);
} else {
field_addr = Address(Robj, R2, lsr, 2);
}
#endif // AARCH64
assert(count < LIST_CAPACITY, "LIST_CAPACITY too small");
speculative_load_pclist[count] = __ pc();
switch (type) {
case T_BOOLEAN:
__ ldrb(Rres, field_addr);
break;
case T_BYTE:
__ ldrsb(Rres, field_addr);
break;
case T_CHAR:
__ ldrh(Rres, field_addr);
break;
case T_SHORT:
__ ldrsh(Rres, field_addr);
break;
case T_INT:
#ifndef __ABI_HARD__
case T_FLOAT:
#endif
__ ldr_s32(Rres, field_addr);
break;
case T_LONG:
#ifndef __ABI_HARD__
case T_DOUBLE:
#endif
#ifdef AARCH64
__ ldr(Rres, field_addr);
#else
// Safe to use ldrd since long and double fields are 8-byte aligned
__ ldrd(Rres, field_addr);
#endif // AARCH64
break;
#ifdef __ABI_HARD__
case T_FLOAT:
__ ldr_float(S0, field_addr);
break;
case T_DOUBLE:
__ ldr_double(D0, field_addr);
break;
#endif // __ABI_HARD__
default:
ShouldNotReachHere();
}
if(os::is_MP()) {
// Address dependency restricts memory access ordering. It's cheaper than explicit LoadLoad barrier
#if defined(__ABI_HARD__) && !defined(AARCH64)
if (type == T_FLOAT || type == T_DOUBLE) {
__ ldr_literal(Rsafepoint_counter_addr, safepoint_counter_addr);
__ fmrrd(Rres, Rres_hi, D0);
__ eor(Rtmp2, Rres, Rres);
__ ldr_s32(Rsafept_cnt2, Address(Rsafepoint_counter_addr, Rtmp2));
} else
#endif // __ABI_HARD__ && !AARCH64
{
#ifndef AARCH64
__ ldr_literal(Rsafepoint_counter_addr, safepoint_counter_addr);
#endif // !AARCH64
__ eor(Rtmp2, Rres, Rres);
__ ldr_s32(Rsafept_cnt2, Address(Rsafepoint_counter_addr, Rtmp2));
}
} else {
__ ldr_s32(Rsafept_cnt2, Address(Rsafepoint_counter_addr));
}
__ cmp(Rsafept_cnt2, Rsafept_cnt);
#ifdef AARCH64
__ b(slow_case, ne);
__ mov(R0, Rres);
__ ret();
#else
// discards saved R0 R1 R2 R3
__ add(SP, SP, 4 * wordSize, eq);
__ bx(LR, eq);
#endif // AARCH64
slowcase_entry_pclist[count++] = __ pc();
__ bind(slow_case);
#ifndef AARCH64
__ pop(RegisterSet(R0, R3));
#endif // !AARCH64
// thumb mode switch handled by MacroAssembler::jump if needed
__ jump(slow_case_addr, relocInfo::none, Rtemp);
__ bind_literal(safepoint_counter_addr);
__ flush();
guarantee((__ pc() - fast_entry) <= BUFFER_SIZE, "BUFFER_SIZE too small");
return fast_entry;
}
address JNI_FastGetField::generate_fast_get_float_field0(BasicType type) {
ShouldNotReachHere();
return NULL;
}
address JNI_FastGetField::generate_fast_get_boolean_field() {
return generate_fast_get_int_field0(T_BOOLEAN);
}
address JNI_FastGetField::generate_fast_get_byte_field() {
return generate_fast_get_int_field0(T_BYTE);
}
address JNI_FastGetField::generate_fast_get_char_field() {
return generate_fast_get_int_field0(T_CHAR);
}
address JNI_FastGetField::generate_fast_get_short_field() {
return generate_fast_get_int_field0(T_SHORT);
}
address JNI_FastGetField::generate_fast_get_int_field() {
return generate_fast_get_int_field0(T_INT);
}
address JNI_FastGetField::generate_fast_get_long_field() {
return generate_fast_get_int_field0(T_LONG);
}
address JNI_FastGetField::generate_fast_get_float_field() {
return generate_fast_get_int_field0(T_FLOAT);
}
address JNI_FastGetField::generate_fast_get_double_field() {
return generate_fast_get_int_field0(T_DOUBLE);
}

View File

@ -0,0 +1,98 @@
/*
* Copyright (c) 2008, 2013, 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
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* 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.
*
*/
#ifndef CPU_ARM_VM_JNITYPES_ARM_HPP
#define CPU_ARM_VM_JNITYPES_ARM_HPP
#include "memory/allocation.hpp"
#include "oops/oop.hpp"
#include "prims/jni.h"
// This file holds platform-dependent routines used to write primitive jni
// types to the array of arguments passed into JavaCalls::call
class JNITypes : AllStatic {
// These functions write a java primitive type (in native format)
// to a java stack slot array to be passed as an argument to JavaCalls:calls.
// I.e., they are functionally 'push' operations if they have a 'pos'
// formal parameter. Note that jlong's and jdouble's are written
// _in reverse_ of the order in which they appear in the interpreter
// stack. This is because call stubs (see stubGenerator_arm.cpp)
// reverse the argument list constructed by JavaCallArguments (see
// javaCalls.hpp).
private:
#ifndef AARCH64
// 32bit Helper routines.
static inline void put_int2r(jint *from, intptr_t *to) { *(jint *)(to++) = from[1];
*(jint *)(to ) = from[0]; }
static inline void put_int2r(jint *from, intptr_t *to, int& pos) { put_int2r(from, to + pos); pos += 2; }
#endif
public:
// Ints are stored in native format in one JavaCallArgument slot at *to.
static inline void put_int(jint from, intptr_t *to) { *(jint *)(to + 0 ) = from; }
static inline void put_int(jint from, intptr_t *to, int& pos) { *(jint *)(to + pos++) = from; }
static inline void put_int(jint *from, intptr_t *to, int& pos) { *(jint *)(to + pos++) = *from; }
#ifdef AARCH64
// Longs are stored in native format in one JavaCallArgument slot at *(to+1).
static inline void put_long(jlong from, intptr_t *to) { *(jlong *)(to + 1 + 0) = from; }
static inline void put_long(jlong from, intptr_t *to, int& pos) { *(jlong *)(to + 1 + pos) = from; pos += 2; }
static inline void put_long(jlong *from, intptr_t *to, int& pos) { *(jlong *)(to + 1 + pos) = *from; pos += 2; }
#else
// Longs are stored in big-endian word format in two JavaCallArgument slots at *to.
// The high half is in *to and the low half in *(to+1).
static inline void put_long(jlong from, intptr_t *to) { put_int2r((jint *)&from, to); }
static inline void put_long(jlong from, intptr_t *to, int& pos) { put_int2r((jint *)&from, to, pos); }
static inline void put_long(jlong *from, intptr_t *to, int& pos) { put_int2r((jint *) from, to, pos); }
#endif
// Oops are stored in native format in one JavaCallArgument slot at *to.
static inline void put_obj(oop from, intptr_t *to) { *(oop *)(to + 0 ) = from; }
static inline void put_obj(oop from, intptr_t *to, int& pos) { *(oop *)(to + pos++) = from; }
static inline void put_obj(oop *from, intptr_t *to, int& pos) { *(oop *)(to + pos++) = *from; }
// Floats are stored in native format in one JavaCallArgument slot at *to.
static inline void put_float(jfloat from, intptr_t *to) { *(jfloat *)(to + 0 ) = from; }
static inline void put_float(jfloat from, intptr_t *to, int& pos) { *(jfloat *)(to + pos++) = from; }
static inline void put_float(jfloat *from, intptr_t *to, int& pos) { *(jfloat *)(to + pos++) = *from; }
#ifdef AARCH64
// Doubles are stored in native word format in one JavaCallArgument slot at *(to+1).
static inline void put_double(jdouble from, intptr_t *to) { *(jdouble *)(to + 1 + 0) = from; }
static inline void put_double(jdouble from, intptr_t *to, int& pos) { *(jdouble *)(to + 1 + pos) = from; pos += 2; }
static inline void put_double(jdouble *from, intptr_t *to, int& pos) { *(jdouble *)(to + 1 + pos) = *from; pos += 2; }
#else
// Doubles are stored in big-endian word format in two JavaCallArgument slots at *to.
// The high half is in *to and the low half in *(to+1).
static inline void put_double(jdouble from, intptr_t *to) { put_int2r((jint *)&from, to); }
static inline void put_double(jdouble from, intptr_t *to, int& pos) { put_int2r((jint *)&from, to, pos); }
static inline void put_double(jdouble *from, intptr_t *to, int& pos) { put_int2r((jint *) from, to, pos); }
#endif
};
#endif // CPU_ARM_VM_JNITYPES_ARM_HPP

Some files were not shown because too many files have changed in this diff Show More