8024344: PPC64 (part 112): C argument in register AND stack slot.
Summary: On PPC, the first 13 floating point arguments to C calls are passed in floating point registers. Also, all but the first 8 arguments are passed on the stack. So there can be floating point arguments that are passed on the stack and in a register. We duplicate the regs datastructure in c_calling_convention() to represent this.
Reviewed-by: kvn, cjplummer
--- a/hotspot/src/cpu/sparc/vm/sharedRuntime_sparc.cpp Fri Sep 06 20:16:09 2013 +0200
+++ b/hotspot/src/cpu/sparc/vm/sharedRuntime_sparc.cpp Thu Sep 12 13:51:13 2013 -0700
@@ -1118,7 +1118,9 @@
int SharedRuntime::c_calling_convention(const BasicType *sig_bt,
VMRegPair *regs,
+ VMRegPair *regs2,
int total_args_passed) {
+ assert(regs2 == NULL, "not needed on sparc");
// Return the number of VMReg stack_slots needed for the args.
// This value does not include an abi space (like register window
@@ -2096,7 +2098,7 @@
// the 1st six register arguments). It's weird see int_stk_helper.
//
int out_arg_slots;
- out_arg_slots = c_calling_convention(out_sig_bt, out_regs, total_c_args);
+ out_arg_slots = c_calling_convention(out_sig_bt, out_regs, NULL, total_c_args);
if (is_critical_native) {
// Critical natives may have to call out so they need a save area
@@ -2843,7 +2845,7 @@
// the 1st six register arguments). It's weird see int_stk_helper.
//
int out_arg_slots;
- out_arg_slots = c_calling_convention(out_sig_bt, out_regs, total_c_args);
+ out_arg_slots = c_calling_convention(out_sig_bt, out_regs, NULL, total_c_args);
// Calculate the total number of stack slots we will need.
--- a/hotspot/src/cpu/sparc/vm/sparc.ad Fri Sep 06 20:16:09 2013 +0200
+++ b/hotspot/src/cpu/sparc/vm/sparc.ad Thu Sep 12 13:51:13 2013 -0700
@@ -3218,7 +3218,7 @@
// C.
c_calling_convention %{
// This is obviously always outgoing
- (void) SharedRuntime::c_calling_convention(sig_bt, regs, length);
+ (void) SharedRuntime::c_calling_convention(sig_bt, regs, /*regs2=*/NULL, length);
%}
// Location of native (C/C++) and interpreter return values. This is specified to
@@ -9118,7 +9118,7 @@
size(4);
ins_cost(BRANCH_COST);
format %{ "BA $labl\t! short branch" %}
- ins_encode %{
+ ins_encode %{
Label* L = $labl$$label;
assert(__ use_cbcond(*L), "back to back cbcond");
__ ba_short(*L);
--- a/hotspot/src/cpu/x86/vm/sharedRuntime_x86_32.cpp Fri Sep 06 20:16:09 2013 +0200
+++ b/hotspot/src/cpu/x86/vm/sharedRuntime_x86_32.cpp Thu Sep 12 13:51:13 2013 -0700
@@ -977,7 +977,9 @@
int SharedRuntime::c_calling_convention(const BasicType *sig_bt,
VMRegPair *regs,
+ VMRegPair *regs2,
int total_args_passed) {
+ assert(regs2 == NULL, "not needed on x86");
// We return the amount of VMRegImpl stack slots we need to reserve for all
// the arguments NOT counting out_preserve_stack_slots.
@@ -1624,7 +1626,7 @@
// Now figure out where the args must be stored and how much stack space
// they require.
int out_arg_slots;
- out_arg_slots = c_calling_convention(out_sig_bt, out_regs, total_c_args);
+ out_arg_slots = c_calling_convention(out_sig_bt, out_regs, NULL, total_c_args);
// Compute framesize for the wrapper. We need to handlize all oops in
// registers a max of 2 on x86.
@@ -2495,7 +2497,7 @@
// they require (neglecting out_preserve_stack_slots).
int out_arg_slots;
- out_arg_slots = c_calling_convention(out_sig_bt, out_regs, total_c_args);
+ out_arg_slots = c_calling_convention(out_sig_bt, out_regs, NULL, total_c_args);
// Calculate the total number of stack slots we will need.
--- a/hotspot/src/cpu/x86/vm/sharedRuntime_x86_64.cpp Fri Sep 06 20:16:09 2013 +0200
+++ b/hotspot/src/cpu/x86/vm/sharedRuntime_x86_64.cpp Thu Sep 12 13:51:13 2013 -0700
@@ -889,7 +889,9 @@
int SharedRuntime::c_calling_convention(const BasicType *sig_bt,
VMRegPair *regs,
+ VMRegPair *regs2,
int total_args_passed) {
+ assert(regs2 == NULL, "not needed on x86");
// We return the amount of VMRegImpl stack slots we need to reserve for all
// the arguments NOT counting out_preserve_stack_slots.
@@ -1857,7 +1859,7 @@
// Now figure out where the args must be stored and how much stack space
// they require.
int out_arg_slots;
- out_arg_slots = c_calling_convention(out_sig_bt, out_regs, total_c_args);
+ out_arg_slots = c_calling_convention(out_sig_bt, out_regs, NULL, total_c_args);
// Compute framesize for the wrapper. We need to handlize all oops in
// incoming registers
@@ -2761,7 +2763,7 @@
// the 1st six register arguments). It's weird see int_stk_helper.
int out_arg_slots;
- out_arg_slots = c_calling_convention(out_sig_bt, out_regs, total_c_args);
+ out_arg_slots = c_calling_convention(out_sig_bt, out_regs, NULL, total_c_args);
// Calculate the total number of stack slots we will need.
--- a/hotspot/src/cpu/x86/vm/x86_32.ad Fri Sep 06 20:16:09 2013 +0200
+++ b/hotspot/src/cpu/x86/vm/x86_32.ad Thu Sep 12 13:51:13 2013 -0700
@@ -3755,7 +3755,7 @@
// automatically biased by the preserve_stack_slots field above.
c_calling_convention %{
// This is obviously always outgoing
- (void) SharedRuntime::c_calling_convention(sig_bt, regs, length);
+ (void) SharedRuntime::c_calling_convention(sig_bt, regs, /*regs2=*/NULL, length);
%}
// Location of C & interpreter return values
--- a/hotspot/src/cpu/x86/vm/x86_64.ad Fri Sep 06 20:16:09 2013 +0200
+++ b/hotspot/src/cpu/x86/vm/x86_64.ad Thu Sep 12 13:51:13 2013 -0700
@@ -2941,7 +2941,7 @@
c_calling_convention
%{
// This is obviously always outgoing
- (void) SharedRuntime::c_calling_convention(sig_bt, regs, length);
+ (void) SharedRuntime::c_calling_convention(sig_bt, regs, /*regs2=*/NULL, length);
%}
// Location of compiled Java return values. Same as C for now.
--- a/hotspot/src/cpu/zero/vm/globals_zero.hpp Fri Sep 06 20:16:09 2013 +0200
+++ b/hotspot/src/cpu/zero/vm/globals_zero.hpp Thu Sep 12 13:51:13 2013 -0700
@@ -43,6 +43,7 @@
define_pd_global(intx, CodeEntryAlignment, 32);
define_pd_global(intx, OptoLoopAlignment, 16);
define_pd_global(intx, InlineFrequencyCount, 100);
+define_pd_global(intx, InlineSmallCode, 1000 );
define_pd_global(intx, PreInflateSpin, 10);
define_pd_global(intx, StackYellowPages, 2);
--- a/hotspot/src/cpu/zero/vm/sharedRuntime_zero.cpp Fri Sep 06 20:16:09 2013 +0200
+++ b/hotspot/src/cpu/zero/vm/sharedRuntime_zero.cpp Thu Sep 12 13:51:13 2013 -0700
@@ -135,6 +135,7 @@
int SharedRuntime::c_calling_convention(const BasicType *sig_bt,
VMRegPair *regs,
+ VMRegPair *regs2,
int total_args_passed) {
ShouldNotCallThis();
return 0;
--- a/hotspot/src/cpu/zero/vm/shark_globals_zero.hpp Fri Sep 06 20:16:09 2013 +0200
+++ b/hotspot/src/cpu/zero/vm/shark_globals_zero.hpp Thu Sep 12 13:51:13 2013 -0700
@@ -50,7 +50,6 @@
define_pd_global(intx, OnStackReplacePercentage, 933 );
define_pd_global(intx, FreqInlineSize, 325 );
-define_pd_global(intx, InlineSmallCode, 1000 );
define_pd_global(uintx, NewRatio, 12 );
define_pd_global(intx, NewSizeThreadIncrease, 4*K );
define_pd_global(intx, InitialCodeCacheSize, 160*K);
--- a/hotspot/src/share/vm/c1/c1_FrameMap.cpp Fri Sep 06 20:16:09 2013 +0200
+++ b/hotspot/src/share/vm/c1/c1_FrameMap.cpp Thu Sep 12 13:51:13 2013 -0700
@@ -133,7 +133,7 @@
}
}
- intptr_t out_preserve = SharedRuntime::c_calling_convention(sig_bt, regs, sizeargs);
+ intptr_t out_preserve = SharedRuntime::c_calling_convention(sig_bt, regs, NULL, sizeargs);
LIR_OprList* args = new LIR_OprList(signature->length());
for (i = 0; i < sizeargs;) {
BasicType t = sig_bt[i];
--- a/hotspot/src/share/vm/runtime/sharedRuntime.hpp Fri Sep 06 20:16:09 2013 +0200
+++ b/hotspot/src/share/vm/runtime/sharedRuntime.hpp Thu Sep 12 13:51:13 2013 -0700
@@ -356,7 +356,15 @@
const VMRegPair* regs) NOT_DEBUG_RETURN;
// Ditto except for calling C
- static int c_calling_convention(const BasicType *sig_bt, VMRegPair *regs, int total_args_passed);
+ //
+ // C argument in register AND stack slot.
+ // Some architectures require that an argument must be passed in a register
+ // AND in a stack slot. These architectures provide a second VMRegPair array
+ // to be filled by the c_calling_convention method. On other architectures,
+ // NULL is being passed as the second VMRegPair array, so arguments are either
+ // passed in a register OR in a stack slot.
+ static int c_calling_convention(const BasicType *sig_bt, VMRegPair *regs, VMRegPair *regs2,
+ int total_args_passed);
// Generate I2C and C2I adapters. These adapters are simple argument marshalling
// blobs. Unlike adapters in the tiger and earlier releases the code in these