From patchwork Mon Aug 31 14:09:18 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: "Maciej W. Rozycki" X-Patchwork-Id: 1354343 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=gcc.gnu.org (client-ip=8.43.85.97; helo=sourceware.org; envelope-from=gcc-patches-bounces@gcc.gnu.org; receiver=) Authentication-Results: ozlabs.org; dmarc=none (p=none dis=none) header.from=gcc.gnu.org Authentication-Results: ozlabs.org; dkim=pass (1024-bit key; unprotected) header.d=gcc.gnu.org header.i=@gcc.gnu.org header.a=rsa-sha256 header.s=default header.b=lEEstQ0y; dkim-atps=neutral Received: from sourceware.org (server2.sourceware.org [8.43.85.97]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 4BgBsQ6p8lz9sSJ for ; Tue, 1 Sep 2020 00:09:29 +1000 (AEST) Received: from server2.sourceware.org (localhost [IPv6:::1]) by sourceware.org (Postfix) with ESMTP id E77A63951C2B; Mon, 31 Aug 2020 14:09:25 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org E77A63951C2B DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gcc.gnu.org; s=default; t=1598882966; bh=z7ZRAz2Wb4LYQ7sNnO9DE106wGFhyMyp2SxHfAcpiEU=; h=Date:To:Subject:List-Id:List-Unsubscribe:List-Archive:List-Post: List-Help:List-Subscribe:From:Reply-To:Cc:From; b=lEEstQ0ybWr/aMf4Kk/Hznr7ytg1t2ssBrUI/KFCK+HqSm72/WeN5DWYM1XcnC9VB 8WWUxunTwiIqtzR8ePFk0tm4uXVZFUP06MQGIr059V3DUnWuS+CTGhFdDO7fkom3+U 57fPWlM3z+Hh5RmhEdaLH0jq34H6FTsFsXtkPcy8= X-Original-To: gcc-patches@gcc.gnu.org Delivered-To: gcc-patches@gcc.gnu.org Received: from esa2.hgst.iphmx.com (esa2.hgst.iphmx.com [68.232.143.124]) by sourceware.org (Postfix) with ESMTPS id 39673386EC2D for ; Mon, 31 Aug 2020 14:09:23 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.3.2 sourceware.org 39673386EC2D IronPort-SDR: BN0pn/K4xH2y5eTJ0kqV548+keBDmxtIRLtURVPZ4ti4+pg+EqJvgRJU/X/P1bM87HOYO6AUIt g7AlaaRJ/wIWWbgTk+RUYRPRykVqfogxpSVnGotqFoGp300HsZmndIiIcV8bS0FSH/yjA2wa5i kLLwKVH0HV42QcVvvOwMpCvfK+zmrgjeuVpwXvTM7epGD0goa9KTeAdXcG00bPaLF/2ZszxtlC C81jfl2ILFbAa8YNYytHYXSGw/qyYbIbm5o6Est/YslzbFso05FKM29AMvaCb/sG2p49yAdoa/ ea0= X-IronPort-AV: E=Sophos;i="5.76,375,1592841600"; d="scan'208";a="249479543" Received: from h199-255-45-15.hgst.com (HELO uls-op-cesaep02.wdc.com) ([199.255.45.15]) by ob1.hgst.iphmx.com with ESMTP; 31 Aug 2020 22:10:05 +0800 IronPort-SDR: YmlI6jTUCxPwjor4rDzux74aDI7mdZDELIqTVlRVzoAPjpUamsxlMwt3h2CJz/Rk4rtuGOr27f +G4R4UiIezcQ== Received: from uls-op-cesaip01.wdc.com ([10.248.3.36]) by uls-op-cesaep02.wdc.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 31 Aug 2020 06:56:01 -0700 IronPort-SDR: qreE2q6DaZqodDR0jOJ+RYwDtPg9uOQ8FKx6PbZ5vARi4DjYA3vG9x/OGk8ykfoVKCeUlPwWvv XPAM7jfGbARQ== WDCIronportException: Internal Received: from unknown (HELO redsun52) ([10.149.66.28]) by uls-op-cesaip01.wdc.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 31 Aug 2020 07:09:21 -0700 Date: Mon, 31 Aug 2020 15:09:18 +0100 (BST) To: gcc-patches@gcc.gnu.org Subject: [WIP][PATCH] RISC-V: Add `-mgprel' option for GP-relative addressing Message-ID: User-Agent: Alpine 2.21 (LFD 202 2017-01-01) MIME-Version: 1.0 X-Spam-Status: No, score=-4.6 required=5.0 tests=BAYES_00, DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, DKIM_VALID_EF, KAM_ASCII_DIVIDERS, KAM_STOCKGEN, SPF_HELO_PASS, SPF_PASS, TXREP autolearn=no autolearn_force=no version=3.4.2 X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on server2.sourceware.org X-BeenThere: gcc-patches@gcc.gnu.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Gcc-patches mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: "Maciej W. Rozycki via Gcc-patches" From: "Maciej W. Rozycki" Reply-To: "Maciej W. Rozycki" Cc: Alistair Francis Errors-To: gcc-patches-bounces@gcc.gnu.org Sender: "Gcc-patches" Implement `-mgprel', forcing `-mexplicit-relocs' whenever the option is active due to the lack of GAS macro support for GP-relative addressing. gcc/ * riscv/riscv-protos.h (riscv_symbol_type): Add SYMBOL_GPREL enumeration constant. * config/riscv/riscv.c (riscv_classify_symbol) (riscv_symbolic_constant_p, riscv_symbol_insns) (riscv_split_symbol_type, riscv_split_symbol, riscv_output_move) (riscv_print_operand_reloc, riscv_option_override): Handle GP-relative addressing. * config/riscv/riscv.md (unspec): Add UNSPEC_GPREL enumeration constant. * config/riscv/riscv.opt (mgprel): New option. --- Hi, This is very early stage really, just implementing basic GP-relative relocation support, in preparation for FDPIC support discussed here: I planned adding support to GAS macros such as LA next so that we don't have to force explicit relocations with `-mgprel' for this option to work, but I won't be able to continue with this effort now as I am leaving Western Digital today, so I am posting this in case someone finds it useful or wishes to continue the effort. No regressions in `riscv64-linux-gnu' testing, RV32/ilp32d ABI with QEMU in the Linux user emulation mode across all GCC frontends and libraries, except for an odd ICE with one of the Fortran test cases and a couple timeouts with GNAT test cases, which I put all on the version difference between the test runs (10.0.1 20200426 vs 11.0.0 20200827). Unfortunately I lost several hours, because 11.0.0 20200829 has regressed enough compared to 11.0.0 20200827 for testing not to progress well enough in 15 hours where it usually completes in ~10 hours. So I had to restart with an older snapshot and wouldn't get reference results in time (I only had libgo results with 11.0.0 20200827). I think my assumption as to the nature of the regressions is right though. A corresponding binutils change has also been posted. Maciej --- gcc/config/riscv/riscv-protos.h | 1 + gcc/config/riscv/riscv.c | 32 +++++++++++++++++++++++++++++--- gcc/config/riscv/riscv.md | 1 + gcc/config/riscv/riscv.opt | 4 ++++ 4 files changed, 35 insertions(+), 3 deletions(-) gcc-riscv-gprel.diff Index: gcc/gcc/config/riscv/riscv-protos.h =================================================================== --- gcc.orig/gcc/config/riscv/riscv-protos.h +++ gcc/gcc/config/riscv/riscv-protos.h @@ -28,6 +28,7 @@ enum riscv_symbol_type { SYMBOL_ABSOLUTE, SYMBOL_PCREL, SYMBOL_GOT_DISP, + SYMBOL_GPREL, SYMBOL_TLS, SYMBOL_TLS_LE, SYMBOL_TLS_IE, Index: gcc/gcc/config/riscv/riscv.c =================================================================== --- gcc.orig/gcc/config/riscv/riscv.c +++ gcc/gcc/config/riscv/riscv.c @@ -559,7 +559,13 @@ riscv_classify_symbol (const_rtx x) if (GET_CODE (x) == SYMBOL_REF && flag_pic && !riscv_symbol_binds_local_p (x)) return SYMBOL_GOT_DISP; - return riscv_cmodel == CM_MEDLOW ? SYMBOL_ABSOLUTE : SYMBOL_PCREL; + if (riscv_cmodel == CM_MEDLOW) + return SYMBOL_ABSOLUTE; + + if (LABEL_REF_P (x) || (SYMBOL_REF_P (x) && SYMBOL_REF_FUNCTION_P (x))) + return SYMBOL_PCREL; + + return TARGET_GPREL ? SYMBOL_GPREL : SYMBOL_PCREL; } /* Classify the base of symbolic expression X. */ @@ -604,6 +610,7 @@ riscv_symbolic_constant_p (rtx x, enum r case SYMBOL_ABSOLUTE: case SYMBOL_PCREL: case SYMBOL_TLS_LE: + case SYMBOL_GPREL: /* GAS rejects offsets outside the range [-2^31, 2^31-1]. */ return sext_hwi (INTVAL (offset), 32) == INTVAL (offset); @@ -622,6 +629,7 @@ static int riscv_symbol_insns (enum risc case SYMBOL_ABSOLUTE: return 2; /* LUI + the reference. */ case SYMBOL_PCREL: return 2; /* AUIPC + the reference. */ case SYMBOL_TLS_LE: return 3; /* LUI + ADD TP + the reference. */ + case SYMBOL_GPREL: return 3; /* LUI + ADD GP + the reference. */ case SYMBOL_GOT_DISP: return 3; /* AUIPC + LD GOT + the reference. */ default: gcc_unreachable (); } @@ -735,7 +743,9 @@ riscv_split_symbol_type (enum riscv_symb if (!TARGET_EXPLICIT_RELOCS) return false; - return symbol_type == SYMBOL_ABSOLUTE || symbol_type == SYMBOL_PCREL; + return (symbol_type == SYMBOL_ABSOLUTE + || symbol_type == SYMBOL_PCREL + || symbol_type == SYMBOL_GPREL); } /* Return true if a LO_SUM can address a value of mode MODE when the @@ -1241,6 +1251,17 @@ riscv_split_symbol (rtx temp, rtx addr, } break; + case SYMBOL_GPREL: + { + rtx high = gen_rtx_HIGH (Pmode, copy_rtx (addr)); + rtx gp = gen_rtx_REG (Pmode, GP_REGNUM); + high = riscv_force_temporary (temp, high, in_splitter); + rtx reg = gen_rtx_PLUS (Pmode, high, gp); + reg = riscv_force_temporary (temp, reg, in_splitter); + *low_out = gen_rtx_LO_SUM (Pmode, reg, addr); + } + break; + default: gcc_unreachable (); } @@ -2030,6 +2051,7 @@ riscv_output_move (rtx dest, rtx src) case SYMBOL_GOT_DISP: return "la\t%0,%1"; case SYMBOL_ABSOLUTE: return "lla\t%0,%1"; case SYMBOL_PCREL: return "lla\t%0,%1"; + case SYMBOL_GPREL: return "la\t%0,%1"; default: gcc_unreachable (); } } @@ -3290,6 +3312,10 @@ riscv_print_operand_reloc (FILE *file, r reloc = hi_reloc ? "%tprel_hi" : "%tprel_lo"; break; + case SYMBOL_GPREL: + reloc = hi_reloc ? "%gprel_hi" : "%gprel_lo"; + break; + default: output_operand_lossage ("invalid use of '%%%c'", hi_reloc ? 'h' : 'R'); return; @@ -4735,7 +4761,7 @@ riscv_option_override (void) /* We get better code with explicit relocs for CM_MEDLOW, but worse code for the others (for now). Pick the best default. */ if ((target_flags_explicit & MASK_EXPLICIT_RELOCS) == 0) - if (riscv_cmodel == CM_MEDLOW) + if (riscv_cmodel == CM_MEDLOW || TARGET_GPREL) target_flags |= MASK_EXPLICIT_RELOCS; /* Require that the ISA supports the requested floating-point ABI. */ Index: gcc/gcc/config/riscv/riscv.md =================================================================== --- gcc.orig/gcc/config/riscv/riscv.md +++ gcc/gcc/config/riscv/riscv.md @@ -28,6 +28,7 @@ UNSPEC_ADDRESS_FIRST UNSPEC_PCREL UNSPEC_LOAD_GOT + UNSPEC_GPREL UNSPEC_TLS UNSPEC_TLS_LE UNSPEC_TLS_IE Index: gcc/gcc/config/riscv/riscv.opt =================================================================== --- gcc.orig/gcc/config/riscv/riscv.opt +++ gcc/gcc/config/riscv/riscv.opt @@ -179,3 +179,7 @@ Use the given offset for addressing the TargetVariable long riscv_stack_protector_guard_offset = 0 + +mgprel +Target Report Mask(GPREL) +Use GP-relative sequences for data accesses.