From patchwork Mon Nov 11 14:40:48 2013 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Ulrich Weigand X-Patchwork-Id: 290329 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from sourceware.org (server1.sourceware.org [209.132.180.131]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (Client did not present a certificate) by ozlabs.org (Postfix) with ESMTPS id D5F822C00AB for ; Tue, 12 Nov 2013 01:49:11 +1100 (EST) DomainKey-Signature: a=rsa-sha1; c=nofws; d=gcc.gnu.org; h=list-id :list-unsubscribe:list-archive:list-post:list-help:sender :message-id:subject:to:date:from:mime-version:content-type :content-transfer-encoding; q=dns; s=default; b=TQqsBT3beKeTxix/ CPCyJ0JYZ3SD0QgVHDSMPJC3C/MUX2uMwzbUh6SVmp8BWyHzC3nQGuUqKeRfQuVt HEZYZoH3w/a6JQYBqQyTn4iNNLjZzHHMaKTR8oAgvvigfOlv8eMcpYiB2GY62fk9 tyAVr2NABFysj4ogOnrocKjkI0g= DKIM-Signature: v=1; a=rsa-sha1; c=relaxed; d=gcc.gnu.org; h=list-id :list-unsubscribe:list-archive:list-post:list-help:sender :message-id:subject:to:date:from:mime-version:content-type :content-transfer-encoding; s=default; bh=uNmano5u/MjdE3MwnCZn6V 7pdm0=; b=CFCsvnCq19NDmy1fTYlBlqHjy01Nb6GdgOMmpFPWoYdnsXFEVy7DXp NbcpIeG4HBXLvvQ+3muokYUf4k7urloCFYRzUNZx1nnUWeFaQM2NMwL46pDt9n5+ sYMYqr7OmVZ5NdG9Uji/08g58GACz/FrG2alikicpptEWen8Sglzs= Received: (qmail 8905 invoked by alias); 11 Nov 2013 14:43:44 -0000 Mailing-List: contact gcc-patches-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Id: List-Unsubscribe: List-Archive: List-Post: List-Help: Sender: gcc-patches-owner@gcc.gnu.org Delivered-To: mailing list gcc-patches@gcc.gnu.org Received: (qmail 8877 invoked by uid 89); 11 Nov 2013 14:43:43 -0000 Authentication-Results: sourceware.org; auth=none X-Virus-Found: No X-Spam-SWARE-Status: No, score=0.7 required=5.0 tests=AWL, BAYES_50, KAM_STOCKGEN, MSGID_FROM_MTA_HEADER, RDNS_NONE, SPF_PASS, URIBL_BLOCKED autolearn=no version=3.3.2 X-HELO: e06smtp15.uk.ibm.com Received: from Unknown (HELO e06smtp15.uk.ibm.com) (195.75.94.111) by sourceware.org (qpsmtpd/0.93/v0.84-503-g423c35a) with (AES256-SHA encrypted) ESMTPS; Mon, 11 Nov 2013 14:42:16 +0000 Received: from /spool/local by e06smtp15.uk.ibm.com with IBM ESMTP SMTP Gateway: Authorized Use Only! Violators will be prosecuted for from ; Mon, 11 Nov 2013 14:42:06 -0000 Received: from d06dlp02.portsmouth.uk.ibm.com (9.149.20.14) by e06smtp15.uk.ibm.com (192.168.101.145) with IBM ESMTP SMTP Gateway: Authorized Use Only! Violators will be prosecuted; Mon, 11 Nov 2013 14:42:05 -0000 Received: from b06cxnps3075.portsmouth.uk.ibm.com (d06relay10.portsmouth.uk.ibm.com [9.149.109.195]) by d06dlp02.portsmouth.uk.ibm.com (Postfix) with ESMTP id 5162A2190063 for ; Mon, 11 Nov 2013 14:42:05 +0000 (GMT) Received: from d06av02.portsmouth.uk.ibm.com (d06av02.portsmouth.uk.ibm.com [9.149.37.228]) by b06cxnps3075.portsmouth.uk.ibm.com (8.13.8/8.13.8/NCO v10.0) with ESMTP id rABEebdU65142878 for ; Mon, 11 Nov 2013 14:40:37 GMT Received: from d06av02.portsmouth.uk.ibm.com (localhost [127.0.0.1]) by d06av02.portsmouth.uk.ibm.com (8.14.4/8.14.4/NCO v10.0 AVout) with ESMTP id rABEen3t003934 for ; Mon, 11 Nov 2013 07:40:49 -0700 Received: from tuxmaker.boeblingen.de.ibm.com (tuxmaker.boeblingen.de.ibm.com [9.152.85.9]) by d06av02.portsmouth.uk.ibm.com (8.14.4/8.14.4/NCO v10.0 AVin) with SMTP id rABEem5T003872 for ; Mon, 11 Nov 2013 07:40:48 -0700 Message-Id: <201311111440.rABEem5T003872@d06av02.portsmouth.uk.ibm.com> Received: by tuxmaker.boeblingen.de.ibm.com (sSMTP sendmail emulation); Mon, 11 Nov 2013 15:40:48 +0100 Subject: [PATCH, rs6000] ELFv2 ABI 1/8: Add options and infrastructure To: gcc-patches@gcc.gnu.org Date: Mon, 11 Nov 2013 15:40:48 +0100 (CET) From: "Ulrich Weigand" MIME-Version: 1.0 X-TM-AS-MML: disable X-Content-Scanned: Fidelis XPS MAILER x-cbid: 13111114-0342-0000-0000-000006D2CBF3 Hello, this is the first patch in the series to add support for the ELFv2 ABI. The ELFv2 ABI is the intended ABI for the new powerpc64le-linux port. However, it is not inherently tied to the byte order; it it possible in principle to use the ELFv2 ABI in big-endian mode too. Therefore, it is introduces via a new pair of options -mabi=elfv1 / -mabi=elfv2 where -mabi=elfv1 select the current Linux ABI, and -mabi=elfv2 selects the new one. If neither option is given, the compiler defaults to whatever ABI was specified at configure time using the --with-abi=elfv1 / --with-abi=elfv2 configure option. If this was not specified either, every subtarget can provide a master default by defining (or not) the LINUX64_DEFAULT_ABI_ELFv2 macro. The patch series is structured as follows: - This first patch adds the new enum rs6000_abi value ABI_ELFv2 and all the configure logic needed to set it. It is treated just like ABI_AIX (on a modern system) at this point; no change in generated code is expected yet. - A series of follow on patches will add the various features defining the ELFv2 ABI. Note that they will still not be active by default anywhere. - The final patch will simply turn the switch to make ELFv2 the default ABI on powerpc64le-linux. The whole series was tested on: - powerpc64-linux with no regression, including no regression in an ALT_CC_UNDER_TEST/ALT_CXX_UNDER_TEST run of compat.exp and struct-layout-1.exp against a current compiler. - powerpc64-linux --with-abi=elfv2 in mock-up big-endian ELFv2 environment running with some hacks on an existing system. - powerpc64le-linux, using the new default ELFv2 in a rebuilt small OS image using the new ABI everywhere. (Of course, patches to binutils, glibc, and libffi to support the new ELFv2 ABI are also required.) The tests were using all languages (including Java, Go, and Objective-C++; on powerpc64le-linux also Ada), and all target libraries except libsanitizer (which currently seems broken on mainline). There is a small number of regressions on powerpc64le-linux which seem to be due to unrelated issues: - FAIL: g++.dg/cpp1y/vla-initlist1.C execution test This is an invalid assumption in the test case - FAIL: go.test/test/fixedbugs/bug296.go execution, -O2 -g The ELFv2 ABI seems to be exposing a Go frontend bug here - FAIL: runtime/pprof (in libgo) This is due to a glibc problem with unwinding through a context created via makecontext I'll address those separately. (Of course, there are also other pre-existing regressions on powerpc64le-linux simply due to little-endian issues. Those are unaffected by ELFv2.) I'll add more detailed descriptions of the actual ABI features with the various follow-on patches that implement those. This patch specifically only adds the options as described above. ABI_ELFv2 is implemented to be equivalent to ABI_AIX on a modern system; since the ABI is new, there is no need to continue to support legacy features. This means specifically: - DOT_SYMBOLS is assumed to be false - rs6000_compat_align_parm is assumed to be false - code in linux-unwind.h that handles old kernels/linkers is removed The patch also adds two new pre-defined macros: - _CALL_ELF is set to 1 or 2 to denote the ELFv1 / ELFv2 ABI - __STRUCT_PARM_ALIGN__ is set to 16 if aggregates passed by value are aligned to 16 if their native alignment requires that (this is necessary to implement libffi, for example) In addition, the patch adds a testsuite effective target check for the ELFv2 ABI, and disables the pr57949 tests (these verify the operation of the -mcompat-align-parm option, which is no longer useful in the ELFv2 ABI). To avoid having a partial ABI implementation in tree, it seems best to commit this whole patch series as a single commit. Is the series OK for mainline? Bye, Ulrich gcc/ChangeLog: 2013-11-11 Ulrich Weigand * config.gcc [powerpc*-*-* | rs6000-*-*]: Support --with-abi=elfv1 and --with-abi=elfv2. * config/rs6000/option-defaults.h (OPTION_DEFAULT_SPECS): Add "abi". * config/rs6000/rs6000.opt (mabi=elfv1): New option. (mabi=elfv2): Likewise. * config/rs6000/rs6000-opts.h (enum rs6000_abi): Add ABI_ELFv2. * config/rs6000/linux64.h (DEFAULT_ABI): Do not hard-code to AIX_ABI if !RS6000_BI_ARCH. (ELFv2_ABI_CHECK): New macro. (SUBSUBTARGET_OVERRIDE_OPTIONS): Use it to decide whether to set rs6000_current_abi to ABI_AIX or ABI_ELFv2. (GLIBC_DYNAMIC_LINKER64): Support ELFv2 ld.so version. * config/rs6000/rs6000-c.c (rs6000_cpu_cpp_builtins): Predefine _CALL_ELF and __STRUCT_PARM_ALIGN__ if appropriate. * config/rs6000/rs6000.c (rs6000_debug_reg_global): Handle ABI_ELFv2. (debug_stack_info): Likewise. (rs6000_file_start): Treat ABI_ELFv2 the same as ABI_AIX. (rs6000_legitimize_tls_address): Likewise. (rs6000_conditional_register_usage): Likewise. (rs6000_emit_move): Likewise. (init_cumulative_args): Likewise. (rs6000_function_arg_advance_1): Likewise. (rs6000_function_arg): Likewise. (rs6000_arg_partial_bytes): Likewise. (rs6000_output_function_entry): Likewise. (rs6000_assemble_integer): Likewise. (rs6000_savres_strategy): Likewise. (rs6000_stack_info): Likewise. (rs6000_function_ok_for_sibcall): Likewise. (rs6000_emit_load_toc_table): Likewise. (rs6000_savres_routine_name): Likewise. (ptr_regno_for_savres): Likewise. (rs6000_emit_prologue): Likewise. (rs6000_emit_epilogue): Likewise. (rs6000_output_function_epilogue): Likewise. (output_profile_hook): Likewise. (output_function_profiler): Likewise. (rs6000_trampoline_size): Likewise. (rs6000_trampoline_init): Likewise. (rs6000_elf_output_toc_section_asm_op): Likewise. (rs6000_elf_encode_section_info): Likewise. (rs6000_elf_reloc_rw_mask): Likewise. (rs6000_elf_declare_function_name): Likewise. (rs6000_function_arg_boundary): Treat ABI_ELFv2 the same as ABI_AIX, except that rs6000_compat_align_parm is always assumed false. (rs6000_gimplify_va_arg): Likewise. (rs6000_call_aix): Update comment. (rs6000_sibcall_aix): Likewise. * config/rs6000/rs6000.md ("tls_gd_aix"): Treat ABI_ELFv2 the same as ABI_AIX. ("*tls_gd_call_aix"): Likewise. ("tls_ld_aix"): Likewise. ("*tls_ld_call_aix"): Likewise. ("load_toc_aix_si"): Likewise. ("load_toc_aix_di"): Likewise. ("call"): Likewise. ("call_value"): Likewise. ("*call_local_aix"): Likewise. ("*call_value_local_aix"): Likewise. ("*call_nonlocal_aix"): Likewise. ("*call_value_nonlocal_aix"): Likewise. ("*call_indirect_aix"): Likewise. ("*call_value_indirect_aix"): Likewise. ("sibcall"): Likewise. ("sibcall_value"): Likewise. ("*sibcall_aix"): Likewise. ("*sibcall_value_aix"): Likewise. * config/rs6000/predicates.md ("symbol_ref_operand"): Likewise. ("current_file_function_operand"): Likewise. libgcc/ChangeLog: 2013-11-11 Ulrich Weigand Alan Modra * config/rs6000/linux-unwind.h (get_regs): Do not support old kernel versions if _CALL_ELF == 2. (frob_update_context): Do not support PLT stub variants only generated by old linkers if _CALL_ELF == 2. gcc/testsuite/ChangeLog: 2013-11-11 Ulrich Weigand * lib/target-supports.exp (check_effective_target_powerpc_elfv2): New function. * gcc.target/powerpc/pr57949-1.c: Disable for powerpc_elfv2. * gcc.target/powerpc/pr57949-2.c: Likewise. Index: gcc/gcc/config.gcc =================================================================== --- gcc.orig/gcc/config.gcc +++ gcc/gcc/config.gcc @@ -3805,7 +3805,7 @@ case "${target}" in ;; powerpc*-*-* | rs6000-*-*) - supported_defaults="cpu cpu_32 cpu_64 float tune tune_32 tune_64" + supported_defaults="abi cpu cpu_32 cpu_64 float tune tune_32 tune_64" for which in cpu cpu_32 cpu_64 tune tune_32 tune_64; do eval "val=\$with_$which" @@ -3842,6 +3842,16 @@ case "${target}" in ;; esac done + + case "$with_abi" in + "" | elfv1 | elfv2 ) + #OK + ;; + *) + echo "Unknown ABI used in --with-abi=$with_abi" + exit 1 + ;; + esac ;; s390*-*-*) Index: gcc/gcc/config/rs6000/option-defaults.h =================================================================== --- gcc.orig/gcc/config/rs6000/option-defaults.h +++ gcc/gcc/config/rs6000/option-defaults.h @@ -54,6 +54,7 @@ --with-float is ignored if -mhard-float or -msoft-float are specified. */ #define OPTION_DEFAULT_SPECS \ + {"abi", "%{!mabi=elfv*:-mabi=%(VALUE)}" }, \ {"tune", "%{!mtune=*:%{!mcpu=*:-mtune=%(VALUE)}}" }, \ {"tune_32", "%{" OPT_ARCH32 ":%{!mtune=*:%{!mcpu=*:-mtune=%(VALUE)}}}" }, \ {"tune_64", "%{" OPT_ARCH64 ":%{!mtune=*:%{!mcpu=*:-mtune=%(VALUE)}}}" }, \ Index: gcc/gcc/config/rs6000/rs6000.opt =================================================================== --- gcc.orig/gcc/config/rs6000/rs6000.opt +++ gcc/gcc/config/rs6000/rs6000.opt @@ -369,6 +369,14 @@ mabi=no-spe Target RejectNegative Var(rs6000_spe_abi, 0) Do not use the SPE ABI extensions +mabi=elfv1 +Target RejectNegative Var(rs6000_elf_abi, 1) Save +Use the ELFv1 ABI + +mabi=elfv2 +Target RejectNegative Var(rs6000_elf_abi, 2) +Use the ELFv2 ABI + ; These are here for testing during development only, do not document ; in the manual please. Index: gcc/gcc/config/rs6000/rs6000-opts.h =================================================================== --- gcc.orig/gcc/config/rs6000/rs6000-opts.h +++ gcc/gcc/config/rs6000/rs6000-opts.h @@ -107,7 +107,8 @@ enum group_termination /* Enumeration to give which calling sequence to use. */ enum rs6000_abi { ABI_NONE, - ABI_AIX, /* IBM's AIX */ + ABI_AIX, /* IBM's AIX, or Linux ELFv1 */ + ABI_ELFv2, /* Linux ELFv2 ABI */ ABI_V4, /* System V.4/eabi */ ABI_DARWIN /* Apple's Darwin (OS X kernel) */ }; Index: gcc/gcc/config/rs6000/linux64.h =================================================================== --- gcc.orig/gcc/config/rs6000/linux64.h +++ gcc/gcc/config/rs6000/linux64.h @@ -25,9 +25,6 @@ #ifndef RS6000_BI_ARCH -#undef DEFAULT_ABI -#define DEFAULT_ABI ABI_AIX - #undef TARGET_64BIT #define TARGET_64BIT 1 @@ -88,6 +85,12 @@ extern int dot_symbols; #define INVALID_64BIT "-m%s not supported in this configuration" #define INVALID_32BIT INVALID_64BIT +#ifdef LINUX64_DEFAULT_ABI_ELFv2 +#define ELFv2_ABI_CHECK (rs6000_elf_abi != 1) +#else +#define ELFv2_ABI_CHECK (rs6000_elf_abi == 2) +#endif + #undef SUBSUBTARGET_OVERRIDE_OPTIONS #define SUBSUBTARGET_OVERRIDE_OPTIONS \ do \ @@ -102,6 +105,12 @@ extern int dot_symbols; error (INVALID_64BIT, "call"); \ } \ dot_symbols = !strcmp (rs6000_abi_name, "aixdesc"); \ + if (ELFv2_ABI_CHECK) \ + { \ + rs6000_current_abi = ABI_ELFv2; \ + if (dot_symbols) \ + error ("-mcall-aixdesc incompatible with -mabi=elfv2"); \ + } \ if (rs6000_isa_flags & OPTION_MASK_RELOCATABLE) \ { \ rs6000_isa_flags &= ~OPTION_MASK_RELOCATABLE; \ @@ -355,7 +364,11 @@ extern int dot_symbols; #define LINK_OS_DEFAULT_SPEC "%(link_os_linux)" #define GLIBC_DYNAMIC_LINKER32 "/lib/ld.so.1" -#define GLIBC_DYNAMIC_LINKER64 "/lib64/ld64.so.1" +#ifdef LINUX64_DEFAULT_ABI_ELFv2 +#define GLIBC_DYNAMIC_LINKER64 "%{mabi=elfv1:/lib64/ld64.so.1;:/lib64/ld64.so.2}" +#else +#define GLIBC_DYNAMIC_LINKER64 "%{mabi=elfv2:/lib64/ld64.so.2;:/lib64/ld64.so.1}" +#endif #define UCLIBC_DYNAMIC_LINKER32 "/lib/ld-uClibc.so.0" #define UCLIBC_DYNAMIC_LINKER64 "/lib/ld64-uClibc.so.0" #if DEFAULT_LIBC == LIBC_UCLIBC Index: gcc/gcc/config/rs6000/rs6000-c.c =================================================================== --- gcc.orig/gcc/config/rs6000/rs6000-c.c +++ gcc/gcc/config/rs6000/rs6000-c.c @@ -461,6 +461,10 @@ rs6000_cpu_cpp_builtins (cpp_reader *pfi case ABI_AIX: builtin_define ("_CALL_AIXDESC"); builtin_define ("_CALL_AIX"); + builtin_define ("_CALL_ELF=1"); + break; + case ABI_ELFv2: + builtin_define ("_CALL_ELF=2"); break; case ABI_DARWIN: builtin_define ("_CALL_DARWIN"); @@ -473,6 +477,13 @@ rs6000_cpu_cpp_builtins (cpp_reader *pfi if (TARGET_SOFT_FLOAT || !TARGET_FPRS) builtin_define ("__NO_FPRS__"); + /* Whether aggregates passed by value are aligned to a 16 byte boundary + if their alignment is 16 bytes or larger. */ + if ((TARGET_MACHO && rs6000_darwin64_abi) + || DEFAULT_ABI == ABI_ELFv2 + || (DEFAULT_ABI == ABI_AIX && !rs6000_compat_align_parm)) + builtin_define ("__STRUCT_PARM_ALIGN__=16"); + /* Generate defines for Xilinx FPU. */ if (rs6000_xilinx_fpu) { Index: gcc/gcc/config/rs6000/rs6000.c =================================================================== --- gcc.orig/gcc/config/rs6000/rs6000.c +++ gcc/gcc/config/rs6000/rs6000.c @@ -2231,6 +2231,7 @@ rs6000_debug_reg_global (void) { case ABI_NONE: abi_str = "none"; break; case ABI_AIX: abi_str = "aix"; break; + case ABI_ELFv2: abi_str = "ELFv2"; break; case ABI_V4: abi_str = "V4"; break; case ABI_DARWIN: abi_str = "darwin"; break; default: abi_str = "unknown"; break; @@ -4761,7 +4762,8 @@ rs6000_file_start (void) putc ('\n', file); } - if (DEFAULT_ABI == ABI_AIX || (TARGET_ELF && flag_pic == 2)) + if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2 + || (TARGET_ELF && flag_pic == 2)) { switch_to_section (toc_section); switch_to_section (text_section); @@ -6971,10 +6973,13 @@ rs6000_legitimize_tls_address (rtx addr, 1, const0_rtx, Pmode); r3 = gen_rtx_REG (Pmode, 3); - if (DEFAULT_ABI == ABI_AIX && TARGET_64BIT) - insn = gen_tls_gd_aix64 (r3, got, addr, tga, const0_rtx); - else if (DEFAULT_ABI == ABI_AIX && !TARGET_64BIT) - insn = gen_tls_gd_aix32 (r3, got, addr, tga, const0_rtx); + if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) + { + if (TARGET_64BIT) + insn = gen_tls_gd_aix64 (r3, got, addr, tga, const0_rtx); + else + insn = gen_tls_gd_aix32 (r3, got, addr, tga, const0_rtx); + } else if (DEFAULT_ABI == ABI_V4) insn = gen_tls_gd_sysvsi (r3, got, addr, tga, const0_rtx); else @@ -6993,10 +6998,13 @@ rs6000_legitimize_tls_address (rtx addr, 1, const0_rtx, Pmode); r3 = gen_rtx_REG (Pmode, 3); - if (DEFAULT_ABI == ABI_AIX && TARGET_64BIT) - insn = gen_tls_ld_aix64 (r3, got, tga, const0_rtx); - else if (DEFAULT_ABI == ABI_AIX && !TARGET_64BIT) - insn = gen_tls_ld_aix32 (r3, got, tga, const0_rtx); + if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) + { + if (TARGET_64BIT) + insn = gen_tls_ld_aix64 (r3, got, tga, const0_rtx); + else + insn = gen_tls_ld_aix32 (r3, got, tga, const0_rtx); + } else if (DEFAULT_ABI == ABI_V4) insn = gen_tls_ld_sysvsi (r3, got, tga, const0_rtx); else @@ -7623,7 +7631,7 @@ rs6000_conditional_register_usage (void) /* The TOC register is not killed across calls in a way that is visible to the compiler. */ - if (DEFAULT_ABI == ABI_AIX) + if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) call_really_used_regs[2] = 0; if (DEFAULT_ABI == ABI_V4 @@ -8274,7 +8282,7 @@ rs6000_emit_move (rtx dest, rtx source, /* If this is a function address on -mcall-aixdesc, convert it to the address of the descriptor. */ - if (DEFAULT_ABI == ABI_AIX + if ((DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) && GET_CODE (operands[1]) == SYMBOL_REF && XSTR (operands[1], 0)[0] == '.') { @@ -8665,7 +8673,7 @@ init_cumulative_args (CUMULATIVE_ARGS *c static bool rs6000_must_pass_in_stack (enum machine_mode mode, const_tree type) { - if (DEFAULT_ABI == ABI_AIX || TARGET_64BIT) + if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2 || TARGET_64BIT) return must_pass_in_stack_var_size (mode, type); else return must_pass_in_stack_var_size_or_pad (mode, type); @@ -8762,6 +8770,7 @@ rs6000_function_arg_boundary (enum machi && int_size_in_bytes (type) >= 16)) return 128; else if (((TARGET_MACHO && rs6000_darwin64_abi) + || DEFAULT_ABI == ABI_ELFv2 || (DEFAULT_ABI == ABI_AIX && !rs6000_compat_align_parm)) && mode == BLKmode && type && TYPE_ALIGN (type) > 64) @@ -9004,7 +9013,8 @@ rs6000_function_arg_advance_1 (CUMULATIV /* PowerPC64 Linux and AIX allocate GPRs for a vector argument even if it is going to be passed in a vector register. Darwin does the same for variable-argument functions. */ - if ((DEFAULT_ABI == ABI_AIX && TARGET_64BIT) + if (((DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) + && TARGET_64BIT) || (cum->stdarg && DEFAULT_ABI != ABI_V4)) stack = true; } @@ -9787,7 +9797,7 @@ rs6000_function_arg (cumulative_args_t c /* Do we also need to pass this argument in the parameter save area? */ if (type && (cum->nargs_prototype <= 0 - || (DEFAULT_ABI == ABI_AIX + || ((DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) && TARGET_XL_COMPAT && align_words >= GP_ARG_NUM_REG))) k = rs6000_psave_function_arg (mode, type, align_words, rvec); @@ -9871,7 +9881,7 @@ rs6000_arg_partial_bytes (cumulative_arg PARALLEL including a memory element as necessary. */ if (type && (cum->nargs_prototype <= 0 - || (DEFAULT_ABI == ABI_AIX + || ((DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) && TARGET_XL_COMPAT && align_words >= GP_ARG_NUM_REG))) return 0; @@ -10343,6 +10353,7 @@ rs6000_gimplify_va_arg (tree valist, tre if (((TARGET_MACHO && rs6000_darwin64_abi) + || DEFAULT_ABI == ABI_ELFv2 || (DEFAULT_ABI == ABI_AIX && !rs6000_compat_align_parm)) && integer_zerop (TYPE_SIZE (type))) { @@ -16667,6 +16678,7 @@ rs6000_output_function_entry (FILE *file gcc_unreachable (); case ABI_AIX: + case ABI_ELFv2: if (DOT_SYMBOLS) putc ('.', file); else @@ -17470,7 +17482,7 @@ rs6000_assemble_integer (rtx x, unsigned itself. */ else if (GET_CODE (x) == SYMBOL_REF && XSTR (x, 0)[0] == '.' - && DEFAULT_ABI == ABI_AIX) + && (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2)) { const char *name = XSTR (x, 0); while (*name == '.') @@ -19625,7 +19637,7 @@ rs6000_savres_strategy (rs6000_stack_t * } else { - gcc_checking_assert (DEFAULT_ABI == ABI_AIX); + gcc_checking_assert (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2); if (info->first_fp_reg_save > 61) strategy |= SAVE_INLINE_FPRS | REST_INLINE_FPRS; strategy |= SAVE_INLINE_GPRS | REST_INLINE_GPRS; @@ -19962,6 +19974,7 @@ rs6000_stack_info (void) gcc_unreachable (); case ABI_AIX: + case ABI_ELFv2: case ABI_DARWIN: info_ptr->fp_save_offset = - info_ptr->fp_size; info_ptr->gp_save_offset = info_ptr->fp_save_offset - info_ptr->gp_size; @@ -20066,7 +20079,7 @@ rs6000_stack_info (void) /* Determine if we need to save the link register. */ if (info_ptr->calls_p - || (DEFAULT_ABI == ABI_AIX + || ((DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) && crtl->profile && !TARGET_PROFILE_KERNEL) || (DEFAULT_ABI == ABI_V4 && cfun->calls_alloca) @@ -20212,6 +20225,7 @@ debug_stack_info (rs6000_stack_t *info) default: abi_string = "Unknown"; break; case ABI_NONE: abi_string = "NONE"; break; case ABI_AIX: abi_string = "AIX"; break; + case ABI_ELFv2: abi_string = "ELFv2"; break; case ABI_DARWIN: abi_string = "Darwin"; break; case ABI_V4: abi_string = "V.4"; break; } @@ -20393,13 +20407,13 @@ rs6000_function_ok_for_sibcall (tree dec return false; } - /* Under the AIX ABI we can't allow calls to non-local functions, - because the callee may have a different TOC pointer to the - caller and there's no way to ensure we restore the TOC when we - return. With the secure-plt SYSV ABI we can't make non-local + /* Under the AIX or ELFv2 ABIs we can't allow calls to non-local + functions, because the callee may have a different TOC pointer to + the caller and there's no way to ensure we restore the TOC when + we return. With the secure-plt SYSV ABI we can't make non-local calls when -fpic/PIC because the plt call stubs use r30. */ if (DEFAULT_ABI == ABI_DARWIN - || (DEFAULT_ABI == ABI_AIX + || ((DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) && decl && !DECL_EXTERNAL (decl) && (*targetm.binds_local_p) (decl)) @@ -20558,7 +20572,7 @@ rs6000_emit_load_toc_table (int fromprol } else { - gcc_assert (DEFAULT_ABI == ABI_AIX); + gcc_assert (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2); if (TARGET_32BIT) emit_insn (gen_load_toc_aix_si (dest)); @@ -21277,7 +21291,7 @@ rs6000_savres_routine_name (rs6000_stack if ((sel & SAVRES_LR)) suffix = "_x"; } - else if (DEFAULT_ABI == ABI_AIX) + else if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) { #if !defined (POWERPC_LINUX) && !defined (POWERPC_FREEBSD) /* No out-of-line save/restore routines for GPRs on AIX. */ @@ -21418,7 +21432,7 @@ rs6000_emit_stack_reset (rs6000_stack_t static inline unsigned ptr_regno_for_savres (int sel) { - if (DEFAULT_ABI == ABI_AIX) + if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) return (sel & SAVRES_REG) == SAVRES_FPR || (sel & SAVRES_LR) ? 1 : 12; return DEFAULT_ABI == ABI_DARWIN && (sel & SAVRES_REG) == SAVRES_FPR ? 1 : 11; } @@ -21785,7 +21799,7 @@ rs6000_emit_prologue (void) /* If we need to save CR, put it into r12 or r11. Choose r12 except when r12 will be needed by out-of-line gpr restore. */ - cr_save_regno = (DEFAULT_ABI == ABI_AIX + cr_save_regno = ((DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) && !(strategy & (SAVE_INLINE_GPRS | SAVE_NOINLINE_GPRS_SAVES_LR)) ? 11 : 12); @@ -22301,7 +22315,8 @@ rs6000_emit_prologue (void) be using r12 as frame_reg_rtx and r11 as the static chain pointer for nested functions. */ save_regno = 12; - if (DEFAULT_ABI == ABI_AIX && !using_static_chain_p) + if ((DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) + && !using_static_chain_p) save_regno = 11; else if (REGNO (frame_reg_rtx) == 12) { @@ -23392,6 +23407,7 @@ rs6000_emit_epilogue (int sibcall) if (! restoring_FPRs_inline) { int i; + int reg; rtx sym; if (flag_shrink_wrap) @@ -23400,10 +23416,9 @@ rs6000_emit_epilogue (int sibcall) sym = rs6000_savres_routine_sym (info, SAVRES_FPR | (lr ? SAVRES_LR : 0)); RTVEC_ELT (p, 2) = gen_rtx_USE (VOIDmode, sym); - RTVEC_ELT (p, 3) = gen_rtx_USE (VOIDmode, - gen_rtx_REG (Pmode, - DEFAULT_ABI == ABI_AIX - ? 1 : 11)); + reg = (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2)? 1 : 11; + RTVEC_ELT (p, 3) = gen_rtx_USE (VOIDmode, gen_rtx_REG (Pmode, reg)); + for (i = 0; i < 64 - info->first_fp_reg_save; i++) { rtx reg = gen_rtx_REG (DFmode, info->first_fp_reg_save + i); @@ -23481,7 +23496,8 @@ rs6000_output_function_epilogue (FILE *f System V.4 Powerpc's (and the embedded ABI derived from it) use a different traceback table. */ - if (DEFAULT_ABI == ABI_AIX && ! flag_inhibit_size_directive + if ((DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) + && ! flag_inhibit_size_directive && rs6000_traceback != traceback_none && !cfun->is_thunk) { const char *fname = NULL; @@ -24484,7 +24500,7 @@ output_profile_hook (int labelno ATTRIBU if (TARGET_PROFILE_KERNEL) return; - if (DEFAULT_ABI == ABI_AIX) + if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) { #ifndef NO_PROFILE_COUNTERS # define NO_PROFILE_COUNTERS 0 @@ -24628,6 +24644,7 @@ output_function_profiler (FILE *file, in break; case ABI_AIX: + case ABI_ELFv2: case ABI_DARWIN: if (!TARGET_PROFILE_KERNEL) { @@ -26583,6 +26600,7 @@ rs6000_trampoline_size (void) gcc_unreachable (); case ABI_AIX: + case ABI_ELFv2: ret = (TARGET_32BIT) ? 12 : 24; break; @@ -26614,6 +26632,7 @@ rs6000_trampoline_init (rtx m_tramp, tre /* Under AIX, just build the 3 word function descriptor */ case ABI_AIX: + case ABI_ELFv2: { rtx fnmem, fn_reg, toc_reg; @@ -26935,7 +26954,7 @@ rs6000_ms_bitfield_layout_p (const_tree static void rs6000_elf_output_toc_section_asm_op (const void *data ATTRIBUTE_UNUSED) { - if (DEFAULT_ABI == ABI_AIX + if ((DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) && TARGET_MINIMAL_TOC && !TARGET_RELOCATABLE) { @@ -26956,7 +26975,8 @@ rs6000_elf_output_toc_section_asm_op (co else fprintf (asm_out_file, "%s\n", MINIMAL_TOC_SECTION_ASM_OP); } - else if (DEFAULT_ABI == ABI_AIX && !TARGET_RELOCATABLE) + else if ((DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) + && !TARGET_RELOCATABLE) fprintf (asm_out_file, "%s\n", TOC_SECTION_ASM_OP); else { @@ -27012,7 +27032,7 @@ rs6000_elf_encode_section_info (tree dec if (first && TREE_CODE (decl) == FUNCTION_DECL && !TARGET_AIX - && DEFAULT_ABI == ABI_AIX) + && (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2)) { rtx sym_ref = XEXP (rtl, 0); size_t len = strlen (XSTR (sym_ref, 0)); @@ -27506,7 +27526,7 @@ rs6000_elf_reloc_rw_mask (void) { if (flag_pic) return 3; - else if (DEFAULT_ABI == ABI_AIX) + else if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) return 2; else return 0; @@ -27632,7 +27652,7 @@ rs6000_elf_declare_function_name (FILE * ASM_OUTPUT_TYPE_DIRECTIVE (file, name, "function"); ASM_DECLARE_RESULT (file, DECL_RESULT (decl)); - if (DEFAULT_ABI == ABI_AIX) + if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) { const char *desc_name, *orig_name; @@ -30632,7 +30652,7 @@ rs6000_legitimate_constant_p (enum machi -/* Expand code to perform a call under the AIX ABI. */ +/* Expand code to perform a call under the AIX or ELFv2 ABI. */ void rs6000_call_aix (rtx value, rtx func_desc, rtx flag, rtx cookie) @@ -30738,7 +30758,7 @@ rs6000_call_aix (rtx value, rtx func_des use_reg (&CALL_INSN_FUNCTION_USAGE (insn), abi_reg); } -/* Expand code to perform a sibling call under the AIX ABI. */ +/* Expand code to perform a sibling call under the AIX or ELFv2 ABI. */ void rs6000_sibcall_aix (rtx value, rtx func_desc, rtx flag, rtx cookie) Index: gcc/gcc/config/rs6000/rs6000.md =================================================================== --- gcc.orig/gcc/config/rs6000/rs6000.md +++ gcc/gcc/config/rs6000/rs6000.md @@ -11201,7 +11201,7 @@ (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")] UNSPEC_TLSGD) (clobber (reg:SI LR_REGNO))] - "HAVE_AS_TLS && DEFAULT_ABI == ABI_AIX" + "HAVE_AS_TLS && (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2)" { if (TARGET_CMODEL != CMODEL_SMALL) return "addis %0,%1,%2@got@tlsgd@ha\;addi %0,%0,%2@got@tlsgd@l\;" @@ -11310,7 +11310,8 @@ (unspec:TLSmode [(match_operand:TLSmode 3 "rs6000_tls_symbol_ref" "")] UNSPEC_TLSGD) (clobber (reg:SI LR_REGNO))] - "HAVE_AS_TLS && DEFAULT_ABI == ABI_AIX && TARGET_TLS_MARKERS" + "HAVE_AS_TLS && TARGET_TLS_MARKERS + && (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2)" "bl %z1(%3@tlsgd)\;nop" [(set_attr "type" "branch") (set_attr "length" "8")]) @@ -11342,7 +11343,7 @@ (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")] UNSPEC_TLSLD) (clobber (reg:SI LR_REGNO))] - "HAVE_AS_TLS && DEFAULT_ABI == ABI_AIX" + "HAVE_AS_TLS && (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2)" { if (TARGET_CMODEL != CMODEL_SMALL) return "addis %0,%1,%&@got@tlsld@ha\;addi %0,%0,%&@got@tlsld@l\;" @@ -11445,7 +11446,8 @@ (match_operand 2 "" "g"))) (unspec:TLSmode [(const_int 0)] UNSPEC_TLSLD) (clobber (reg:SI LR_REGNO))] - "HAVE_AS_TLS && DEFAULT_ABI == ABI_AIX && TARGET_TLS_MARKERS" + "HAVE_AS_TLS && TARGET_TLS_MARKERS + && (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2)" "bl %z1(%&@tlsld)\;nop" [(set_attr "type" "branch") (set_attr "length" "8")]) @@ -11816,7 +11818,7 @@ [(parallel [(set (match_operand:SI 0 "gpc_reg_operand" "=r") (unspec:SI [(const_int 0)] UNSPEC_TOC)) (use (reg:SI 2))])] - "DEFAULT_ABI == ABI_AIX && TARGET_32BIT" + "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) && TARGET_32BIT" "* { char buf[30]; @@ -11831,7 +11833,7 @@ [(parallel [(set (match_operand:DI 0 "gpc_reg_operand" "=r") (unspec:DI [(const_int 0)] UNSPEC_TOC)) (use (reg:DI 2))])] - "DEFAULT_ABI == ABI_AIX && TARGET_64BIT" + "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) && TARGET_64BIT" "* { char buf[30]; @@ -12097,7 +12099,7 @@ operands[0] = XEXP (operands[0], 0); - if (DEFAULT_ABI == ABI_AIX) + if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) { rs6000_call_aix (NULL_RTX, operands[0], operands[1], operands[2]); DONE; @@ -12141,7 +12143,7 @@ operands[1] = XEXP (operands[1], 0); - if (DEFAULT_ABI == ABI_AIX) + if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) { rs6000_call_aix (operands[0], operands[1], operands[2], operands[3]); DONE; @@ -12440,7 +12442,7 @@ [(call (mem:SI (match_operand:P 0 "current_file_function_operand" "s")) (match_operand 1 "" "g")) (clobber (reg:P LR_REGNO))] - "DEFAULT_ABI == ABI_AIX" + "DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2" "bl %z0" [(set_attr "type" "branch") (set_attr "length" "4")]) @@ -12450,7 +12452,7 @@ (call (mem:SI (match_operand:P 1 "current_file_function_operand" "s")) (match_operand 2 "" "g"))) (clobber (reg:P LR_REGNO))] - "DEFAULT_ABI == ABI_AIX" + "DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2" "bl %z1" [(set_attr "type" "branch") (set_attr "length" "4")]) @@ -12462,7 +12464,7 @@ [(call (mem:SI (match_operand:P 0 "symbol_ref_operand" "s")) (match_operand 1 "" "g")) (clobber (reg:P LR_REGNO))] - "DEFAULT_ABI == ABI_AIX" + "DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2" "bl %z0\;nop" [(set_attr "type" "branch") (set_attr "length" "8")]) @@ -12472,7 +12474,7 @@ (call (mem:SI (match_operand:P 1 "symbol_ref_operand" "s")) (match_operand 2 "" "g"))) (clobber (reg:P LR_REGNO))] - "DEFAULT_ABI == ABI_AIX" + "DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2" "bl %z1\;nop" [(set_attr "type" "branch") (set_attr "length" "8")]) @@ -12488,7 +12490,7 @@ (use (match_operand:P 2 "memory_operand" ",")) (set (reg:P TOC_REGNUM) (match_operand:P 3 "memory_operand" ",")) (clobber (reg:P LR_REGNO))] - "DEFAULT_ABI == ABI_AIX" + "DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2" " 2,%2\;b%T0l\; 2,%3" [(set_attr "type" "jmpreg") (set_attr "length" "12")]) @@ -12500,7 +12502,7 @@ (use (match_operand:P 3 "memory_operand" ",")) (set (reg:P TOC_REGNUM) (match_operand:P 4 "memory_operand" ",")) (clobber (reg:P LR_REGNO))] - "DEFAULT_ABI == ABI_AIX" + "DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2" " 2,%3\;b%T1l\; 2,%4" [(set_attr "type" "jmpreg") (set_attr "length" "12")]) @@ -12554,7 +12556,7 @@ operands[0] = XEXP (operands[0], 0); - if (DEFAULT_ABI == ABI_AIX) + if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) { rs6000_sibcall_aix (NULL_RTX, operands[0], operands[1], operands[2]); DONE; @@ -12581,7 +12583,7 @@ operands[1] = XEXP (operands[1], 0); - if (DEFAULT_ABI == ABI_AIX) + if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) { rs6000_sibcall_aix (operands[0], operands[1], operands[2], operands[3]); DONE; @@ -12741,7 +12743,7 @@ [(call (mem:SI (match_operand:P 0 "call_operand" "s,c")) (match_operand 1 "" "g,g")) (simple_return)] - "DEFAULT_ABI == ABI_AIX" + "DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2" "@ b %z0 b%T0" @@ -12753,7 +12755,7 @@ (call (mem:SI (match_operand:P 1 "call_operand" "s,c")) (match_operand 2 "" "g,g"))) (simple_return)] - "DEFAULT_ABI == ABI_AIX" + "DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2" "@ b %z1 b%T1" Index: gcc/gcc/config/rs6000/predicates.md =================================================================== --- gcc.orig/gcc/config/rs6000/predicates.md +++ gcc/gcc/config/rs6000/predicates.md @@ -1018,7 +1018,8 @@ (define_predicate "symbol_ref_operand" (and (match_code "symbol_ref") (match_test "(mode == VOIDmode || GET_MODE (op) == mode) - && (DEFAULT_ABI != ABI_AIX || SYMBOL_REF_FUNCTION_P (op))"))) + && ((DEFAULT_ABI != ABI_AIX && DEFAULT_ABI != ABI_ELFv2) + || SYMBOL_REF_FUNCTION_P (op))"))) ;; Return 1 if op is an operand that can be loaded via the GOT. ;; or non-special register register field no cr0 @@ -1048,9 +1049,11 @@ ;; this file. (define_predicate "current_file_function_operand" (and (match_code "symbol_ref") - (match_test "(DEFAULT_ABI != ABI_AIX || SYMBOL_REF_FUNCTION_P (op)) + (match_test "((DEFAULT_ABI != ABI_AIX && DEFAULT_ABI != ABI_ELFv2) + || SYMBOL_REF_FUNCTION_P (op)) && ((SYMBOL_REF_LOCAL_P (op) - && (DEFAULT_ABI != ABI_AIX + && ((DEFAULT_ABI != ABI_AIX + && DEFAULT_ABI != ABI_ELFv2) || !SYMBOL_REF_EXTERNAL_P (op))) || (op == XEXP (DECL_RTL (current_function_decl), 0)))"))) Index: gcc/libgcc/config/rs6000/linux-unwind.h =================================================================== --- gcc.orig/libgcc/config/rs6000/linux-unwind.h +++ gcc/libgcc/config/rs6000/linux-unwind.h @@ -107,6 +107,8 @@ get_regs (struct _Unwind_Context *contex } else if (pc[1] == 0x380000AC) { +#if _CALL_ELF != 2 + /* These old kernel versions never supported ELFv2. */ /* This works for 2.4 kernels, but not for 2.6 kernels with vdso because pc isn't pointing into the stack. Can be removed when no one is running 2.4.19 or 2.4.20, the first two ppc64 @@ -121,6 +123,7 @@ get_regs (struct _Unwind_Context *contex if ((long) frame24->puc != -21 * 8) return frame24->puc->regs; else +#endif { /* This works for 2.4.21 and later kernels. */ struct rt_sigframe { @@ -298,8 +301,12 @@ frob_update_context (struct _Unwind_Cont code that does the save/restore is generated by the linker, so we have no good way to determine at compile time what to do. */ if (pc[0] == 0xF8410028 +#if _CALL_ELF != 2 + /* The ELFv2 linker never generates the old PLT stub form. */ || ((pc[0] & 0xFFFF0000) == 0x3D820000 - && pc[1] == 0xF8410028)) + && pc[1] == 0xF8410028) +#endif + ) { /* We are in a plt call stub or r2 adjusting long branch stub, before r2 has been saved. Keep REG_UNSAVED. */ Index: gcc/gcc/testsuite/lib/target-supports.exp =================================================================== --- gcc.orig/gcc/testsuite/lib/target-supports.exp +++ gcc/gcc/testsuite/lib/target-supports.exp @@ -3019,6 +3019,22 @@ proc check_effective_target_powerpc_405_ } } +# Return 1 if this is a PowerPC target using the ELFv2 ABI. + +proc check_effective_target_powerpc_elfv2 { } { + if { [istarget powerpc*-*-*] } { + return [check_no_compiler_messages powerpc_elfv2 object { + #if _CALL_ELF != 2 + #error not ELF v2 ABI + #else + int dummy; + #endif + }] + } else { + return 0 + } +} + # Return 1 if this is a SPU target with a toolchain that # supports automatic overlay generation. Index: gcc/gcc/testsuite/gcc.target/powerpc/pr57949-1.c =================================================================== --- gcc.orig/gcc/testsuite/gcc.target/powerpc/pr57949-1.c +++ gcc/gcc/testsuite/gcc.target/powerpc/pr57949-1.c @@ -1,5 +1,6 @@ /* { dg-do compile { target { powerpc64*-*-* && lp64 } } } */ /* { dg-skip-if "" { powerpc*-*-darwin* } { "*" } { "" } } */ +/* { dg-skip-if "" { powerpc_elfv2 } { "*" } { "" } } */ /* { dg-options "-O2 -mcpu=power7" } */ /* Verify that vs is 16-byte aligned in the absence of -mcompat-align-parm. */ Index: gcc/gcc/testsuite/gcc.target/powerpc/pr57949-2.c =================================================================== --- gcc.orig/gcc/testsuite/gcc.target/powerpc/pr57949-2.c +++ gcc/gcc/testsuite/gcc.target/powerpc/pr57949-2.c @@ -1,5 +1,6 @@ /* { dg-do compile { target { powerpc64*-*-* && lp64 } } } */ /* { dg-skip-if "" { powerpc*-*-darwin* } { "*" } { "" } } */ +/* { dg-skip-if "" { powerpc_elfv2 } { "*" } { "" } } */ /* { dg-options "-O2 -mcpu=power7 -mcompat-align-parm" } */ /* Verify that vs is not 16-byte aligned with -mcompat-align-parm. */