diff options
author | H.J. Lu <hongjiu.lu@intel.com> | 2009-03-27 22:22:30 +0000 |
---|---|---|
committer | H.J. Lu <hjl@gcc.gnu.org> | 2009-03-27 15:22:30 -0700 |
commit | 51212b321b1c143c36e54d68e9a29d1a1125f954 (patch) | |
tree | fec28a074b7f4d51805408c4567ef1b4dfc755dc /gcc | |
parent | 9027c95aba77aa51f6c8777e918e6c4db3063169 (diff) | |
download | gcc-51212b321b1c143c36e54d68e9a29d1a1125f954.zip gcc-51212b321b1c143c36e54d68e9a29d1a1125f954.tar.gz gcc-51212b321b1c143c36e54d68e9a29d1a1125f954.tar.bz2 |
re PR target/39472 (Add -mabi=[ms|sysv])
gcc/
2009-03-27 H.J. Lu <hongjiu.lu@intel.com>
PR target/39472
* config/i386/i386.c (ix86_abi): New.
(override_options): Handle -mabi=.
(ix86_function_arg_regno_p): Replace DEFAULT_ABI with
ix86_abi.
(ix86_call_abi_override): Likewise.
(init_cumulative_args): Likewise.
(function_arg_advance): Likewise.
(function_arg_64): Likewise.
(function_arg): Likewise.
(ix86_pass_by_reference): Likewise.
(ix86_function_value_regno_p): Likewise.
(ix86_build_builtin_va_list_abi): Likewise.
(setup_incoming_varargs_64): Likewise.
(is_va_list_char_pointer): Likewise.
(ix86_init_machine_status): Likewise.
(ix86_reg_parm_stack_space): Use enum calling_abi on
call_abi.
(ix86_function_type_abi): Return enum calling_abi. Rewrite
for 64bit. Replace DEFAULT_ABI with ix86_abi.
(ix86_function_abi): Make it static and return enum
calling_abi.
(ix86_cfun_abi): Return enum calling_abi. Replace DEFAULT_ABI
with ix86_abi.
(ix86_fn_abi_va_list): Updated.
* config/i386/i386.h (ix86_abi): New.
(STACK_BOUNDARY): Replace DEFAULT_ABI with ix86_abi.
(CONDITIONAL_REGISTER_USAGE): Likewise.
(CUMULATIVE_ARGS): Change call_abi type to enum calling_abi.
(machine_function): Likewise.
* config/i386/i386.md (untyped_call): Replace DEFAULT_ABI
with ix86_abi.
* config/i386/cygming.h (TARGET_64BIT_MS_ABI): Likewise.
(STACK_BOUNDARY): Likewise.
* config/i386/mingw32.h (EXTRA_OS_CPP_BUILTINS): Likewise.
* config/i386/i386.opt (mabi=): New.
* config/i386/i386-protos.h (ix86_cfun_abi): Changed to
return enum calling_abi.
(ix86_function_type_abi): Likewise.
(ix86_function_abi): Removed.
* doc/invoke.texi: Document -mabi= option for x86.
gcc/testsuite/
2009-03-27 H.J. Lu <hongjiu.lu@intel.com>
PR target/39472
* gcc.target/x86_64/abi/callabi/func-2a.c: New.
* gcc.target/x86_64/abi/callabi/func-2b.c: Likewise.
* gcc.target/x86_64/abi/callabi/func-indirect-2a.c: Likewise.
* gcc.target/x86_64/abi/callabi/func-indirect-2b.c: Likewise.
* gcc.target/x86_64/abi/callabi/vaarg-4a.c: Likewise.
* gcc.target/x86_64/abi/callabi/vaarg-4b.c: Likewise.
* gcc.target/x86_64/abi/callabi/vaarg-5a.c: Likewise.
* gcc.target/x86_64/abi/callabi/vaarg-5b.c: Likewise.
From-SVN: r145133
Diffstat (limited to 'gcc')
-rw-r--r-- | gcc/ChangeLog | 49 | ||||
-rw-r--r-- | gcc/config/i386/cygming.h | 4 | ||||
-rw-r--r-- | gcc/config/i386/i386-protos.h | 5 | ||||
-rw-r--r-- | gcc/config/i386/i386.c | 92 | ||||
-rw-r--r-- | gcc/config/i386/i386.h | 13 | ||||
-rw-r--r-- | gcc/config/i386/i386.md | 2 | ||||
-rw-r--r-- | gcc/config/i386/i386.opt | 4 | ||||
-rw-r--r-- | gcc/config/i386/mingw32.h | 2 | ||||
-rw-r--r-- | gcc/doc/invoke.texi | 12 | ||||
-rw-r--r-- | gcc/testsuite/ChangeLog | 12 | ||||
-rw-r--r-- | gcc/testsuite/gcc.target/x86_64/abi/callabi/func-2a.c | 27 | ||||
-rw-r--r-- | gcc/testsuite/gcc.target/x86_64/abi/callabi/func-2b.c | 13 | ||||
-rw-r--r-- | gcc/testsuite/gcc.target/x86_64/abi/callabi/func-indirect-2a.c | 17 | ||||
-rw-r--r-- | gcc/testsuite/gcc.target/x86_64/abi/callabi/func-indirect-2b.c | 24 | ||||
-rw-r--r-- | gcc/testsuite/gcc.target/x86_64/abi/callabi/vaarg-4a.c | 24 | ||||
-rw-r--r-- | gcc/testsuite/gcc.target/x86_64/abi/callabi/vaarg-4b.c | 31 | ||||
-rw-r--r-- | gcc/testsuite/gcc.target/x86_64/abi/callabi/vaarg-5a.c | 17 | ||||
-rw-r--r-- | gcc/testsuite/gcc.target/x86_64/abi/callabi/vaarg-5b.c | 37 |
18 files changed, 334 insertions, 51 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 3c58c26..d874d24 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,52 @@ +2009-03-27 H.J. Lu <hongjiu.lu@intel.com> + + PR target/39472 + * config/i386/i386.c (ix86_abi): New. + (override_options): Handle -mabi=. + (ix86_function_arg_regno_p): Replace DEFAULT_ABI with + ix86_abi. + (ix86_call_abi_override): Likewise. + (init_cumulative_args): Likewise. + (function_arg_advance): Likewise. + (function_arg_64): Likewise. + (function_arg): Likewise. + (ix86_pass_by_reference): Likewise. + (ix86_function_value_regno_p): Likewise. + (ix86_build_builtin_va_list_abi): Likewise. + (setup_incoming_varargs_64): Likewise. + (is_va_list_char_pointer): Likewise. + (ix86_init_machine_status): Likewise. + (ix86_reg_parm_stack_space): Use enum calling_abi on + call_abi. + (ix86_function_type_abi): Return enum calling_abi. Rewrite + for 64bit. Replace DEFAULT_ABI with ix86_abi. + (ix86_function_abi): Make it static and return enum + calling_abi. + (ix86_cfun_abi): Return enum calling_abi. Replace DEFAULT_ABI + with ix86_abi. + (ix86_fn_abi_va_list): Updated. + + * config/i386/i386.h (ix86_abi): New. + (STACK_BOUNDARY): Replace DEFAULT_ABI with ix86_abi. + (CONDITIONAL_REGISTER_USAGE): Likewise. + (CUMULATIVE_ARGS): Change call_abi type to enum calling_abi. + (machine_function): Likewise. + + * config/i386/i386.md (untyped_call): Replace DEFAULT_ABI + with ix86_abi. + * config/i386/cygming.h (TARGET_64BIT_MS_ABI): Likewise. + (STACK_BOUNDARY): Likewise. + * config/i386/mingw32.h (EXTRA_OS_CPP_BUILTINS): Likewise. + + * config/i386/i386.opt (mabi=): New. + + * config/i386/i386-protos.h (ix86_cfun_abi): Changed to + return enum calling_abi. + (ix86_function_type_abi): Likewise. + (ix86_function_abi): Removed. + + * doc/invoke.texi: Document -mabi= option for x86. + 2009-03-27 Kaveh R. Ghazi <ghazi@caip.rutgers.edu> * builtins.c (real_dconstp): Delete. diff --git a/gcc/config/i386/cygming.h b/gcc/config/i386/cygming.h index db43ffd..431e926 100644 --- a/gcc/config/i386/cygming.h +++ b/gcc/config/i386/cygming.h @@ -34,7 +34,7 @@ along with GCC; see the file COPYING3. If not see #endif #undef TARGET_64BIT_MS_ABI -#define TARGET_64BIT_MS_ABI (!cfun ? DEFAULT_ABI == MS_ABI : TARGET_64BIT && cfun->machine->call_abi == MS_ABI) +#define TARGET_64BIT_MS_ABI (!cfun ? ix86_abi == MS_ABI : TARGET_64BIT && cfun->machine->call_abi == MS_ABI) #undef DEFAULT_ABI #define DEFAULT_ABI (TARGET_64BIT ? MS_ABI : SYSV_ABI) @@ -202,7 +202,7 @@ do { \ #define CHECK_STACK_LIMIT 4000 #undef STACK_BOUNDARY -#define STACK_BOUNDARY (DEFAULT_ABI == MS_ABI ? 128 : BITS_PER_WORD) +#define STACK_BOUNDARY (ix86_abi == MS_ABI ? 128 : BITS_PER_WORD) /* By default, target has a 80387, uses IEEE compatible arithmetic, returns float values in the 387 and needs stack probes. diff --git a/gcc/config/i386/i386-protos.h b/gcc/config/i386/i386-protos.h index 23936a8..d6f5e5a 100644 --- a/gcc/config/i386/i386-protos.h +++ b/gcc/config/i386/i386-protos.h @@ -139,9 +139,8 @@ extern int ix86_function_arg_boundary (enum machine_mode, tree); extern bool ix86_sol10_return_in_memory (const_tree,const_tree); extern rtx ix86_force_to_memory (enum machine_mode, rtx); extern void ix86_free_from_memory (enum machine_mode); -extern int ix86_cfun_abi (void); -extern int ix86_function_abi (const_tree); -extern int ix86_function_type_abi (const_tree); +extern enum calling_abi ix86_cfun_abi (void); +extern enum calling_abi ix86_function_type_abi (const_tree); extern void ix86_call_abi_override (const_tree); extern tree ix86_fn_abi_va_list (tree); extern tree ix86_canonical_va_list_type (tree); diff --git a/gcc/config/i386/i386.c b/gcc/config/i386/i386.c index 18063e6..5f36ec3 100644 --- a/gcc/config/i386/i386.c +++ b/gcc/config/i386/i386.c @@ -1743,6 +1743,9 @@ static unsigned int ix86_default_incoming_stack_boundary; /* Alignment for incoming stack boundary in bits. */ unsigned int ix86_incoming_stack_boundary; +/* The abi used by target. */ +enum calling_abi ix86_abi = DEFAULT_ABI; + /* Values 1-5: see jump.c */ int ix86_branch_cost; @@ -1819,6 +1822,8 @@ static bool ix86_valid_target_attribute_inner_p (tree, char *[]); static bool ix86_can_inline_p (tree, tree); static void ix86_set_current_function (tree); +static enum calling_abi ix86_function_abi (const_tree); + /* The svr4 ABI for the i386 says that records and unions are returned in memory. */ @@ -2716,6 +2721,18 @@ override_options (bool main_args_p) error ("bad value (%s) for %sarch=%s %s", ix86_arch_string, prefix, suffix, sw); + /* Validate -mabi= value. */ + if (ix86_abi_string) + { + if (strcmp (ix86_abi_string, "sysv") == 0) + ix86_abi = SYSV_ABI; + else if (strcmp (ix86_abi_string, "ms") == 0) + ix86_abi = MS_ABI; + else + error ("unknown ABI (%s) for %sabi=%s %s", + ix86_abi_string, prefix, suffix, sw); + } + if (ix86_cmodel_string != 0) { if (!strcmp (ix86_cmodel_string, "small")) @@ -4515,14 +4532,14 @@ ix86_function_arg_regno_p (int regno) default ABI. */ /* RAX is used as hidden argument to va_arg functions. */ - if (DEFAULT_ABI == SYSV_ABI && regno == AX_REG) + if (ix86_abi == SYSV_ABI && regno == AX_REG) return true; - if (DEFAULT_ABI == MS_ABI) + if (ix86_abi == MS_ABI) parm_regs = x86_64_ms_abi_int_parameter_registers; else parm_regs = x86_64_int_parameter_registers; - for (i = 0; i < (DEFAULT_ABI == MS_ABI ? X64_REGPARM_MAX + for (i = 0; i < (ix86_abi == MS_ABI ? X64_REGPARM_MAX : X86_64_REGPARM_MAX); i++) if (regno == parm_regs[i]) return true; @@ -4550,7 +4567,7 @@ ix86_must_pass_in_stack (enum machine_mode mode, const_tree type) int ix86_reg_parm_stack_space (const_tree fndecl) { - int call_abi = SYSV_ABI; + enum calling_abi call_abi = SYSV_ABI; if (fndecl != NULL_TREE && TREE_CODE (fndecl) == FUNCTION_DECL) call_abi = ix86_function_abi (fndecl); else @@ -4562,37 +4579,39 @@ ix86_reg_parm_stack_space (const_tree fndecl) /* Returns value SYSV_ABI, MS_ABI dependent on fntype, specifying the call abi used. */ -int +enum calling_abi ix86_function_type_abi (const_tree fntype) { if (TARGET_64BIT && fntype != NULL) { - int abi; - if (DEFAULT_ABI == SYSV_ABI) - abi = lookup_attribute ("ms_abi", TYPE_ATTRIBUTES (fntype)) ? MS_ABI : SYSV_ABI; - else - abi = lookup_attribute ("sysv_abi", TYPE_ATTRIBUTES (fntype)) ? SYSV_ABI : MS_ABI; - + enum calling_abi abi = ix86_abi; + if (abi == SYSV_ABI) + { + if (lookup_attribute ("ms_abi", TYPE_ATTRIBUTES (fntype))) + abi = MS_ABI; + } + else if (lookup_attribute ("sysv_abi", TYPE_ATTRIBUTES (fntype))) + abi = SYSV_ABI; return abi; } - return DEFAULT_ABI; + return ix86_abi; } -int +static enum calling_abi ix86_function_abi (const_tree fndecl) { if (! fndecl) - return DEFAULT_ABI; + return ix86_abi; return ix86_function_type_abi (TREE_TYPE (fndecl)); } /* Returns value SYSV_ABI, MS_ABI dependent on cfun, specifying the call abi used. */ -int +enum calling_abi ix86_cfun_abi (void) { if (! cfun || ! TARGET_64BIT) - return DEFAULT_ABI; + return ix86_abi; return cfun->machine->call_abi; } @@ -4606,7 +4625,7 @@ void ix86_call_abi_override (const_tree fndecl) { if (fndecl == NULL_TREE) - cfun->machine->call_abi = DEFAULT_ABI; + cfun->machine->call_abi = ix86_abi; else cfun->machine->call_abi = ix86_function_type_abi (TREE_TYPE (fndecl)); } @@ -4646,8 +4665,8 @@ init_cumulative_args (CUMULATIVE_ARGS *cum, /* Argument info to initialize */ cum->nregs = ix86_regparm; if (TARGET_64BIT) { - if (cum->call_abi != DEFAULT_ABI) - cum->nregs = DEFAULT_ABI != SYSV_ABI ? X86_64_REGPARM_MAX + if (cum->call_abi != ix86_abi) + cum->nregs = ix86_abi != SYSV_ABI ? X86_64_REGPARM_MAX : X64_REGPARM_MAX; } if (TARGET_SSE) @@ -4655,8 +4674,8 @@ init_cumulative_args (CUMULATIVE_ARGS *cum, /* Argument info to initialize */ cum->sse_nregs = SSE_REGPARM_MAX; if (TARGET_64BIT) { - if (cum->call_abi != DEFAULT_ABI) - cum->sse_nregs = DEFAULT_ABI != SYSV_ABI ? X86_64_SSE_REGPARM_MAX + if (cum->call_abi != ix86_abi) + cum->sse_nregs = ix86_abi != SYSV_ABI ? X86_64_SSE_REGPARM_MAX : X64_SSE_REGPARM_MAX; } } @@ -5582,7 +5601,7 @@ function_arg_advance (CUMULATIVE_ARGS *cum, enum machine_mode mode, if (type) mode = type_natural_mode (type, NULL); - if (TARGET_64BIT && (cum ? cum->call_abi : DEFAULT_ABI) == MS_ABI) + if (TARGET_64BIT && (cum ? cum->call_abi : ix86_abi) == MS_ABI) function_arg_advance_ms_64 (cum, bytes, words); else if (TARGET_64BIT) function_arg_advance_64 (cum, mode, type, words, named); @@ -5728,9 +5747,9 @@ function_arg_64 (CUMULATIVE_ARGS *cum, enum machine_mode mode, if (mode == VOIDmode) return GEN_INT (cum->maybe_vaarg ? (cum->sse_nregs < 0 - ? (cum->call_abi == DEFAULT_ABI + ? (cum->call_abi == ix86_abi ? SSE_REGPARM_MAX - : (DEFAULT_ABI != SYSV_ABI ? X86_64_SSE_REGPARM_MAX + : (ix86_abi != SYSV_ABI ? X86_64_SSE_REGPARM_MAX : X64_SSE_REGPARM_MAX)) : cum->sse_regno) : -1); @@ -5824,7 +5843,7 @@ function_arg (CUMULATIVE_ARGS *cum, enum machine_mode omode, if (type && TREE_CODE (type) == VECTOR_TYPE) mode = type_natural_mode (type, cum); - if (TARGET_64BIT && (cum ? cum->call_abi : DEFAULT_ABI) == MS_ABI) + if (TARGET_64BIT && (cum ? cum->call_abi : ix86_abi) == MS_ABI) return function_arg_ms_64 (cum, mode, omode, named, bytes); else if (TARGET_64BIT) return function_arg_64 (cum, mode, omode, type, named); @@ -5844,7 +5863,7 @@ ix86_pass_by_reference (CUMULATIVE_ARGS *cum ATTRIBUTE_UNUSED, const_tree type, bool named ATTRIBUTE_UNUSED) { /* See Windows x64 Software Convention. */ - if (TARGET_64BIT && (cum ? cum->call_abi : DEFAULT_ABI) == MS_ABI) + if (TARGET_64BIT && (cum ? cum->call_abi : ix86_abi) == MS_ABI) { int msize = (int) GET_MODE_SIZE (mode); if (type) @@ -5984,7 +6003,7 @@ ix86_function_value_regno_p (int regno) /* TODO: The function should depend on current function ABI but builtins.c would need updating then. Therefore we use the default ABI. */ - if (TARGET_64BIT && DEFAULT_ABI == MS_ABI) + if (TARGET_64BIT && ix86_abi == MS_ABI) return false; return TARGET_FLOAT_RETURNS_IN_80387; @@ -6380,13 +6399,13 @@ ix86_build_builtin_va_list_abi (enum calling_abi abi) static tree ix86_build_builtin_va_list (void) { - tree ret = ix86_build_builtin_va_list_abi (DEFAULT_ABI); + tree ret = ix86_build_builtin_va_list_abi (ix86_abi); /* Initialize abi specific va_list builtin types. */ if (TARGET_64BIT) { tree t; - if (DEFAULT_ABI == MS_ABI) + if (ix86_abi == MS_ABI) { t = ix86_build_builtin_va_list_abi (SYSV_ABI); if (TREE_CODE (t) != RECORD_TYPE) @@ -6400,7 +6419,7 @@ ix86_build_builtin_va_list (void) t = build_variant_type_copy (t); sysv_va_list_type_node = t; } - if (DEFAULT_ABI != MS_ABI) + if (ix86_abi != MS_ABI) { t = ix86_build_builtin_va_list_abi (MS_ABI); if (TREE_CODE (t) != RECORD_TYPE) @@ -6433,8 +6452,8 @@ setup_incoming_varargs_64 (CUMULATIVE_ARGS *cum) int i; int regparm = ix86_regparm; - if (cum->call_abi != DEFAULT_ABI) - regparm = DEFAULT_ABI != SYSV_ABI ? X86_64_REGPARM_MAX : X64_REGPARM_MAX; + if (cum->call_abi != ix86_abi) + regparm = ix86_abi != SYSV_ABI ? X86_64_REGPARM_MAX : X64_REGPARM_MAX; /* GPR size of varargs save area. */ if (cfun->va_list_gpr_size) @@ -6587,7 +6606,7 @@ is_va_list_char_pointer (tree type) return true; canonic = ix86_canonical_va_list_type (type); return (canonic == ms_va_list_type_node - || (DEFAULT_ABI == MS_ABI && canonic == va_list_type_node)); + || (ix86_abi == MS_ABI && canonic == va_list_type_node)); } /* Implement va_start. */ @@ -18724,7 +18743,7 @@ ix86_init_machine_status (void) f = GGC_CNEW (struct machine_function); f->use_fast_prologue_epilogue_nregs = -1; f->tls_descriptor_call_expanded_p = 0; - f->call_abi = DEFAULT_ABI; + f->call_abi = ix86_abi; return f; } @@ -29443,14 +29462,11 @@ x86_builtin_vectorization_cost (bool runtime_test) tree ix86_fn_abi_va_list (tree fndecl) { - int abi; - if (!TARGET_64BIT) return va_list_type_node; gcc_assert (fndecl != NULL_TREE); - abi = ix86_function_abi ((const_tree) fndecl); - if (abi == MS_ABI) + if (ix86_function_abi ((const_tree) fndecl) == MS_ABI) return ms_va_list_type_node; else return sysv_va_list_type_node; diff --git a/gcc/config/i386/i386.h b/gcc/config/i386/i386.h index 8035e84..e4d4463 100644 --- a/gcc/config/i386/i386.h +++ b/gcc/config/i386/i386.h @@ -465,7 +465,10 @@ enum calling_abi MS_ABI = 1 }; -/* The default abi form used by target. */ +/* The abi used by target. */ +extern enum calling_abi ix86_abi; + +/* The default abi used by target. */ #define DEFAULT_ABI SYSV_ABI /* Subtargets may reset this to 1 in order to enable 96-bit long double @@ -653,7 +656,7 @@ enum target_cpu_default /* Boundary (in *bits*) on which stack pointer should be aligned. */ #define STACK_BOUNDARY \ - (TARGET_64BIT && DEFAULT_ABI == MS_ABI ? 128 : BITS_PER_WORD) + (TARGET_64BIT && ix86_abi == MS_ABI ? 128 : BITS_PER_WORD) /* Stack boundary of the main function guaranteed by OS. */ #define MAIN_STACK_BOUNDARY (TARGET_64BIT ? 128 : 32) @@ -949,7 +952,7 @@ do { \ fixed_regs[j] = call_used_regs[j] = 1; \ if (TARGET_64BIT \ && ((cfun && cfun->machine->call_abi == MS_ABI) \ - || (!cfun && DEFAULT_ABI == MS_ABI))) \ + || (!cfun && ix86_abi == MS_ABI))) \ { \ call_used_regs[SI_REG] = 0; \ call_used_regs[DI_REG] = 0; \ @@ -1609,7 +1612,7 @@ typedef struct ix86_args { int maybe_vaarg; /* true for calls to possibly vardic fncts. */ int float_in_sse; /* 1 if in 32-bit mode SFmode (2 for DFmode) should be passed in SSE registers. Otherwise 0. */ - int call_abi; /* Set to SYSV_ABI for sysv abi. Otherwise + enum calling_abi call_abi; /* Set to SYSV_ABI for sysv abi. Otherwise MS_ABI for ms abi. */ } CUMULATIVE_ARGS; @@ -2428,7 +2431,7 @@ struct machine_function GTY(()) int tls_descriptor_call_expanded_p; /* This value is used for amd64 targets and specifies the current abi to be used. MS_ABI means ms abi. Otherwise SYSV_ABI means sysv abi. */ - int call_abi; + enum calling_abi call_abi; }; #define ix86_stack_locals (cfun->machine->stack_locals) diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md index 39e62fb..a112198 100644 --- a/gcc/config/i386/i386.md +++ b/gcc/config/i386/i386.md @@ -15164,7 +15164,7 @@ ? gen_rtx_REG (XCmode, FIRST_FLOAT_REG) : NULL), operands[0], const0_rtx, GEN_INT ((TARGET_64BIT - ? (DEFAULT_ABI == SYSV_ABI + ? (ix86_abi == SYSV_ABI ? X86_64_SSE_REGPARM_MAX : X64_SSE_REGPARM_MAX) : X86_32_SSE_REGPARM_MAX) diff --git a/gcc/config/i386/i386.opt b/gcc/config/i386/i386.opt index 8530590..6fd218f 100644 --- a/gcc/config/i386/i386.opt +++ b/gcc/config/i386/i386.opt @@ -228,6 +228,10 @@ mtune= Target RejectNegative Joined Var(ix86_tune_string) Schedule code for given CPU +mabi= +Target RejectNegative Joined Var(ix86_abi_string) +Generate code that conforms to the given ABI + mveclibabi= Target RejectNegative Joined Var(ix86_veclibabi_string) Vector library ABI to use diff --git a/gcc/config/i386/mingw32.h b/gcc/config/i386/mingw32.h index f3fbe8c..746d7d1 100644 --- a/gcc/config/i386/mingw32.h +++ b/gcc/config/i386/mingw32.h @@ -38,7 +38,7 @@ along with GCC; see the file COPYING3. If not see builtin_define_std ("WINNT"); \ builtin_define_with_int_value ("_INTEGRAL_MAX_BITS", \ TYPE_PRECISION (intmax_type_node));\ - if (TARGET_64BIT && DEFAULT_ABI == MS_ABI) \ + if (TARGET_64BIT && ix86_abi == MS_ABI) \ { \ builtin_define ("__MINGW64__"); \ builtin_define_std ("WIN64"); \ diff --git a/gcc/doc/invoke.texi b/gcc/doc/invoke.texi index 1d58f06..ac5b2c8 100644 --- a/gcc/doc/invoke.texi +++ b/gcc/doc/invoke.texi @@ -585,7 +585,7 @@ Objective-C and Objective-C++ Dialects}. -m96bit-long-double -mregparm=@var{num} -msseregparm @gol -mveclibabi=@var{type} -mpc32 -mpc64 -mpc80 -mstackrealign @gol -momit-leaf-frame-pointer -mno-red-zone -mno-tls-direct-seg-refs @gol --mcmodel=@var{code-model} @gol +-mcmodel=@var{code-model} -mabi=@var{name} @gol -m32 -m64 -mlarge-data-threshold=@var{num} @gol -mfused-madd -mno-fused-madd -msse2avx} @@ -11393,6 +11393,16 @@ when @option{-mveclibabi=acml} is used. Both @option{-ftree-vectorize} and @option{-funsafe-math-optimizations} have to be enabled. A SVML or ACML ABI compatible library will have to be specified at link time. +@item -mabi=@var{name} +@opindex mabi +Generate code for the specified calling convention. Permissible values +are: @samp{sysv} for the ABI used on GNU/Linux and other systems and +@samp{ms} for the Microsoft ABI. The default is to use the Microsoft +ABI when targeting Windows. On all other systems, the default is the +SYSV ABI. You can control this behavior for a specific function by +using the function attribute @samp{ms_abi}/@samp{sysv_abi}. +@xref{Function Attributes}. + @item -mpush-args @itemx -mno-push-args @opindex mpush-args diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 2f1903a..a67ad29 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,15 @@ +2009-03-27 H.J. Lu <hongjiu.lu@intel.com> + + PR target/39472 + * gcc.target/x86_64/abi/callabi/func-2a.c: New. + * gcc.target/x86_64/abi/callabi/func-2b.c: Likewise. + * gcc.target/x86_64/abi/callabi/func-indirect-2a.c: Likewise. + * gcc.target/x86_64/abi/callabi/func-indirect-2b.c: Likewise. + * gcc.target/x86_64/abi/callabi/vaarg-4a.c: Likewise. + * gcc.target/x86_64/abi/callabi/vaarg-4b.c: Likewise. + * gcc.target/x86_64/abi/callabi/vaarg-5a.c: Likewise. + * gcc.target/x86_64/abi/callabi/vaarg-5b.c: Likewise. + 2009-03-27 Kaveh R. Ghazi <ghazi@caip.rutgers.edu> * gcc.dg/torture/builtin-explog-1.c: Remove tests that aren't true diff --git a/gcc/testsuite/gcc.target/x86_64/abi/callabi/func-2a.c b/gcc/testsuite/gcc.target/x86_64/abi/callabi/func-2a.c new file mode 100644 index 0000000..048da6e --- /dev/null +++ b/gcc/testsuite/gcc.target/x86_64/abi/callabi/func-2a.c @@ -0,0 +1,27 @@ +/* Test for cross x86_64<->w64 abi standard calls. */ +/* { dg-do run { target i?86-*-linux* x86_64-*-linux* } } */ +/* { dg-options "-O2 -mabi=ms -std=gnu99 -ffast-math -fno-builtin" } */ +/* { dg-additional-sources "func-2b.c" } */ + +extern void __attribute__ ((sysv_abi)) abort (void); +long double func_cross (long double, double, float, long, int, char); + +long double __attribute__ ((sysv_abi)) +func_native (long double a, double b, float c, long d, int e, char f) +{ + long double ret; + ret = a + (long double) b + (long double) c; + ret *= (long double) (d + (long) e); + if (f>0) + ret += func_native (a,b,c,d,e,-f); + return ret; +} + +int __attribute__ ((sysv_abi)) +main () +{ + if (func_cross (1.0,2.0,3.0,1,2,3) + != func_native (1.0,2.0,3.0,1,2,3)) + abort (); + return 0; +} diff --git a/gcc/testsuite/gcc.target/x86_64/abi/callabi/func-2b.c b/gcc/testsuite/gcc.target/x86_64/abi/callabi/func-2b.c new file mode 100644 index 0000000..fe85dd1 --- /dev/null +++ b/gcc/testsuite/gcc.target/x86_64/abi/callabi/func-2b.c @@ -0,0 +1,13 @@ +/* Test for cross x86_64<->w64 abi standard calls. */ +/* { dg-options "-mabi=ms -std=gnu99 -ffast-math -fno-builtin" } */ + +long double func_cross (long double a, double b, float c, long d, int e, + char f) +{ + long double ret; + ret = a + (long double) b + (long double) c; + ret *= (long double) (d + (long) e); + if (f>0) + ret += func_cross (a,b,c,d,e,-f); + return ret; +} diff --git a/gcc/testsuite/gcc.target/x86_64/abi/callabi/func-indirect-2a.c b/gcc/testsuite/gcc.target/x86_64/abi/callabi/func-indirect-2a.c new file mode 100644 index 0000000..730b8db --- /dev/null +++ b/gcc/testsuite/gcc.target/x86_64/abi/callabi/func-indirect-2a.c @@ -0,0 +1,17 @@ +/* Test for cross x86_64<->w64 abi standard calls via variable. */ +/* { dg-do run { target i?86-*-linux* x86_64-*-linux* } } */ +/* { dg-options "-O2 -mabi=ms -std=gnu99 -ffast-math -fno-builtin" } */ +/* { dg-additional-sources "func-indirect-2b.c" } */ + +extern void __attribute__ ((sysv_abi)) abort (void); +typedef int (*func)(void *, char *, char *, short, long long); +extern func get_callback (void); + +int __attribute__ ((sysv_abi)) +main () +{ + func callme = get_callback (); + if (callme (0, 0, 0, 0x1234, 0x1234567890abcdefLL)) + abort (); + return 0; +} diff --git a/gcc/testsuite/gcc.target/x86_64/abi/callabi/func-indirect-2b.c b/gcc/testsuite/gcc.target/x86_64/abi/callabi/func-indirect-2b.c new file mode 100644 index 0000000..1a9fccd --- /dev/null +++ b/gcc/testsuite/gcc.target/x86_64/abi/callabi/func-indirect-2b.c @@ -0,0 +1,24 @@ +/* Test for cross x86_64<->w64 abi standard calls via variable. */ +/* { dg-options "-O2 -mabi=ms -std=gnu99 -ffast-math -fno-builtin" } */ + +typedef int (*func)(void *, char *, char *, short, long long); + +static int +callback (void *ptr, char *string1, char *string2, short number, + long long rand) +{ + if (ptr != 0 + || string1 != 0 + || string2 != 0 + || number != 0x1234 + || rand != 0x1234567890abcdefLL) + return 1; + else + return 0; +} + +func +get_callback (void) +{ + return callback; +} diff --git a/gcc/testsuite/gcc.target/x86_64/abi/callabi/vaarg-4a.c b/gcc/testsuite/gcc.target/x86_64/abi/callabi/vaarg-4a.c new file mode 100644 index 0000000..a444704 --- /dev/null +++ b/gcc/testsuite/gcc.target/x86_64/abi/callabi/vaarg-4a.c @@ -0,0 +1,24 @@ +/* Test for cross x86_64<->w64 abi va_list calls. */ +/* { dg-do run { target i?86-*-linux* x86_64-*-linux* } } */ +/* { dg-options "-O2 -mabi=ms -std=gnu99 -fno-builtin" } */ +/* { dg-additional-sources "vaarg-4b.c" } */ + +extern __SIZE_TYPE__ __attribute__ ((sysv_abi)) strlen (const char *); +extern int __attribute__ ((sysv_abi)) sprintf (char *,const char *, ...); +extern void __attribute__ ((sysv_abi)) abort (void); + +extern void do_cpy (char *, ...); + +int __attribute__ ((sysv_abi)) +main () +{ + char s[256]; + + do_cpy (s, "1","2","3","4", "5", "6", "7", ""); + + if (s[0] != '1' || s[1] !='2' || s[2] != '3' || s[3] != '4' + || s[4] != '5' || s[5] != '6' || s[6] != '7' || s[7] != 0) + abort (); + + return 0; +} diff --git a/gcc/testsuite/gcc.target/x86_64/abi/callabi/vaarg-4b.c b/gcc/testsuite/gcc.target/x86_64/abi/callabi/vaarg-4b.c new file mode 100644 index 0000000..f33906b --- /dev/null +++ b/gcc/testsuite/gcc.target/x86_64/abi/callabi/vaarg-4b.c @@ -0,0 +1,31 @@ +/* Test for cross x86_64<->w64 abi va_list calls. */ +/* { dg-options "-O2 -mabi=ms -std=gnu99 -fno-builtin" } */ + +#include <stdarg.h> + +extern __SIZE_TYPE__ __attribute__ ((sysv_abi)) strlen (const char *); +extern int __attribute__ ((sysv_abi)) sprintf (char *, const char *, ...); + +static void +vdo_cpy (char *s, va_list argp) +{ + __SIZE_TYPE__ len; + char *r = s; + char *e; + *r = 0; + for (;;) { + e = va_arg (argp, char *); + if (*e == 0) break; + sprintf (r,"%s", e); + r += strlen (r); + } +} + +void +do_cpy (char *s, ...) +{ + va_list argp; + va_start (argp, s); + vdo_cpy (s, argp); + va_end (argp); +} diff --git a/gcc/testsuite/gcc.target/x86_64/abi/callabi/vaarg-5a.c b/gcc/testsuite/gcc.target/x86_64/abi/callabi/vaarg-5a.c new file mode 100644 index 0000000..e991295 --- /dev/null +++ b/gcc/testsuite/gcc.target/x86_64/abi/callabi/vaarg-5a.c @@ -0,0 +1,17 @@ +/* Test for cross x86_64<->w64 abi va_list calls. */ +/* { dg-do run { target i?86-*-linux* x86_64-*-linux* } } */ +/* { dg-options "-O2 -mabi=ms -std=gnu99 -fno-builtin" } */ +/* { dg-additional-sources "vaarg-5b.c" } */ + +extern void __attribute__ ((sysv_abi)) abort (void); +extern int fct2 (int, ...); + +#define SZ_ARGS 1ll,2ll,3ll,4ll,5ll,6ll,7ll,0ll + +int __attribute__ ((sysv_abi)) +main() +{ + if (fct2 (-1, SZ_ARGS) != 0) + abort (); + return 0; +} diff --git a/gcc/testsuite/gcc.target/x86_64/abi/callabi/vaarg-5b.c b/gcc/testsuite/gcc.target/x86_64/abi/callabi/vaarg-5b.c new file mode 100644 index 0000000..e5dd472 --- /dev/null +++ b/gcc/testsuite/gcc.target/x86_64/abi/callabi/vaarg-5b.c @@ -0,0 +1,37 @@ +/* Test for cross x86_64<->w64 abi va_list calls. */ +/* { dg-options "-O2 -mabi=ms -std=gnu99 -fno-builtin" } */ + +#include <stdarg.h> + +#define SZ_ARGS 1ll,2ll,3ll,4ll,5ll,6ll,7ll,0ll + +static int __attribute__ ((sysv_abi)) +fct1 (va_list argp, ...) +{ + long long p1,p2; + int ret = 1; + __builtin_sysv_va_list argp_2; + + __builtin_sysv_va_start (argp_2, argp); + do { + p1 = va_arg (argp_2, long long); + p2 = va_arg (argp, long long); + if (p1 != p2) + ret = 0; + } while (ret && p1 != 0); + __builtin_sysv_va_end (argp_2); + + return ret; +} + +int +fct2 (int dummy, ...) +{ + va_list argp; + int ret = dummy; + + va_start (argp, dummy); + ret += fct1 (argp, SZ_ARGS); + va_end (argp); + return ret; +} |