From patchwork Sun Jan 6 22:56:45 2013 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?J=C3=BCrgen_Urban?= X-Patchwork-Id: 209842 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]) by ozlabs.org (Postfix) with SMTP id 50BAD2C0079 for ; Mon, 7 Jan 2013 09:57:05 +1100 (EST) Comment: DKIM? See http://www.dkim.org DKIM-Signature: v=1; a=rsa-sha1; c=relaxed/relaxed; d=gcc.gnu.org; s=default; x=1358117826; h=Comment: DomainKey-Signature:Received:Received:Received:Received:Received: Received:Content-Type:Date:From:Message-ID:MIME-Version:Subject: To:Mailing-List:Precedence:List-Id:List-Unsubscribe:List-Archive: List-Post:List-Help:Sender:Delivered-To; bh=PCmhWKW5e6bdu69ZJl4F k+14Bks=; b=wgobf8m+dQsLAu9GTAFoRCQL2pg2y1JE+CpWwMjs64vQOLBPOpgX yleTlnLfpjzMVcYhtLR7kZ/jh4rI7dnvq0Sr6R6eI0iKnUVSom2rPYUpJ4y52hM+ 5Y/kt07ac9pr7av7GABIf5gAR2TnpEvY9iDUhZ6T705tRlZZD41YWsQ= Comment: DomainKeys? See http://antispam.yahoo.com/domainkeys DomainKey-Signature: a=rsa-sha1; q=dns; c=nofws; s=default; d=gcc.gnu.org; h=Received:Received:X-SWARE-Spam-Status:X-Spam-Check-By:Received:Received:Received:Received:Content-Type:Date:From:Message-ID:MIME-Version:Subject:To:X-IsSubscribed:Mailing-List:Precedence:List-Id:List-Unsubscribe:List-Archive:List-Post:List-Help:Sender:Delivered-To; b=KRRbwwz6rM/nJhgO0O6yE5Pg/+WTAOYDYyVujlcE/TyzeXRXUs6oYYivKQJrkS adqKpUYwN6uSjp8pGy5Wb5nUQRGtXiTzJi7eeLW8ia0is/bzICUQmsN2FZtJ4HEE gQtw2u92+EkIbxhk6aUz5f8u7JSwR3mg7NZv0q7gPrWVU=; Received: (qmail 17977 invoked by alias); 6 Jan 2013 22:57:00 -0000 Received: (qmail 17968 invoked by uid 22791); 6 Jan 2013 22:56:59 -0000 X-SWARE-Spam-Status: No, hits=2.3 required=5.0 tests=AWL, BAYES_50, FREEMAIL_FROM, RCVD_IN_DNSWL_NONE, RCVD_IN_HOSTKARMA_NO, RCVD_IN_HOSTKARMA_YE, SARE_BAYES_5x8, SARE_BAYES_6x8, SARE_BAYES_7x8, TW_BV, TW_CL, TW_EG, TW_GV, TW_IV, TW_LZ, TW_SV, TW_UC X-Spam-Check-By: sourceware.org Received: from mout.gmx.net (HELO mout.gmx.net) (212.227.15.19) by sourceware.org (qpsmtpd/0.43rc1) with ESMTP; Sun, 06 Jan 2013 22:56:49 +0000 Received: from mailout-de.gmx.net ([10.1.76.32]) by mrigmx.server.lan (mrigmx001) with ESMTP (Nemesis) id 0M5aK6-1T3ca00aHg-00xaJS for ; Sun, 06 Jan 2013 23:56:48 +0100 Received: (qmail 6582 invoked by uid 0); 6 Jan 2013 22:56:48 -0000 Received: from 84.178.45.201 by www044.gmx.net with HTTP; Sun, 06 Jan 2013 23:56:45 +0100 (CET) Date: Sun, 06 Jan 2013 23:56:45 +0100 From: =?iso-8859-1?Q?=22J=FCrgen_Urban=22?= Message-ID: <20130106225645.190700@gmx.net> MIME-Version: 1.0 Subject: Support for MIPS r5900 To: gcc-patches@gcc.gnu.org X-IsSubscribed: yes 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 Hello, I created a patch from scratch to support MIPS r5900 used in the Playstation 2, but I have some problems with it. The attached patch only works with the latest binutils from CVS. The binutils forces the compiler to use r5900 compatible instructions which is good to find errors in the GCC. Later I will try to submit a patch here, but first I need some help. The MIPS r5900 supports 32 bit, 64 bit and 128 bit data accesses on a 32 Bit address bus. It supports instructions from MIPS ISA I, II, III, IV and has additional instructions, but none of them are complete. On each ISA level there are instructions missing. It can run MIPS ABI o32, n32 and o64 code, as long as unsupported instructions are not used or emulated by the operating system and the addresses keep in the first 32 bit. My patch adds support for r5900 and tries to disable the following unsupported instructions: ll, sc, dmult, ddiv, cvt.w.s, 64 bit FPU instructions. ll and sc is disabled with "-mno-llsc" and works. cvt.w.s is replaced by trunc.w.s. This seems to work. I disabled 64 bit FPU instructions by "-msoft-float". This works, but using "-msingle-float" fails. This would be the better configuration. There are still 64 bit FPU instructions used (e.g. "dmfc1 $2,$f0" when using "long double" multiplication). So "-msingle-float" doesn't seem to work on generic mips64-linux-gnu. I tried to disable dmult and ddiv (see mips.md). Disabling worked, but now muldi3 calls itself in libgcc2. I thought this should work, because I got this working with GCC 4.3, but the latest GCC version is a problem. multi3 is calling muldi3, so that muldi3 should be able to use mulsi3, because it is the same C code in libgcc2. Can someone get me some hints or comments? How can this be debugged? Does someone know how to enable TImode in MIPS ABI o32 (this doesn't need to use the 128 bit instructions at the moment)? There is some old code for the Playstation 2 which needs this. I know that TImode is supported in ABI n32, but some code uses also the 32 bit FPU and FPU registers are not available with "-msoft-float" in inline assembler. What is the best way to change the alignment to 128 bit for all structures and stack in any MIPS ABI? Much old code for the Playstation 2 expects this. Best regards Jürgen Urban diff -Nurp '--exclude=build01' ../gcc-svn-20130105.orig/config.sub gcc-svn-20130105-mips64r5900el-linux-patched/config.sub --- ../gcc-svn-20130105.orig/config.sub 2013-01-05 20:06:32.859960482 +0100 +++ gcc-svn-20130105-mips64r5900el-linux-patched/config.sub 2013-01-06 19:11:56.332755480 +0100 @@ -284,6 +284,8 @@ case $basic_machine in | mips64vr4300 | mips64vr4300el \ | mips64vr5000 | mips64vr5000el \ | mips64vr5900 | mips64vr5900el \ + | mips64r5900 | mips64r5900el \ + | mipsr5900 | mipsr5900el \ | mipsisa32 | mipsisa32el \ | mipsisa32r2 | mipsisa32r2el \ | mipsisa64 | mipsisa64el \ @@ -401,6 +403,8 @@ case $basic_machine in | mips64vr4300-* | mips64vr4300el-* \ | mips64vr5000-* | mips64vr5000el-* \ | mips64vr5900-* | mips64vr5900el-* \ + | mips64r5900-* | mips64r5900el-* \ + | mipsr5900-* | mipsr5900el-* \ | mipsisa32-* | mipsisa32el-* \ | mipsisa32r2-* | mipsisa32r2el-* \ | mipsisa64-* | mipsisa64el-* \ diff -Nurp '--exclude=build01' ../gcc-svn-20130105.orig/gcc/config/mips/mips.c gcc-svn-20130105-mips64r5900el-linux-patched/gcc/config/mips/mips.c --- ../gcc-svn-20130105.orig/gcc/config/mips/mips.c 2013-01-05 20:03:24.231962472 +0100 +++ gcc-svn-20130105-mips64r5900el-linux-patched/gcc/config/mips/mips.c 2013-01-06 19:11:56.336755480 +0100 @@ -1025,6 +1025,19 @@ static const struct mips_rtx_cost_data 1, /* branch_cost */ 4 /* memory_latency */ }, + { /* R5900 */ + COSTS_N_INSNS (4), /* fp_add */ + COSTS_N_INSNS (4), /* fp_mult_sf */ + COSTS_N_INSNS (256), /* fp_mult_df */ + COSTS_N_INSNS (8), /* fp_div_sf */ + COSTS_N_INSNS (256), /* fp_div_df */ + COSTS_N_INSNS (4), /* int_mult_si */ + COSTS_N_INSNS (256), /* int_mult_di */ + COSTS_N_INSNS (37), /* int_div_si */ + COSTS_N_INSNS (256), /* int_div_di */ + 1, /* branch_cost */ + 4 /* memory_latency */ + }, { /* R7000 */ /* The only costs that are changed here are integer multiplication. */ @@ -12793,6 +12806,7 @@ mips_issue_rate (void) case PROCESSOR_R4130: case PROCESSOR_R5400: case PROCESSOR_R5500: + case PROCESSOR_R5900: case PROCESSOR_R7000: case PROCESSOR_R9000: case PROCESSOR_OCTEON: @@ -15573,6 +15587,7 @@ vr4130_align_insns (void) } dfa_finish (); } + /* This structure records that the current function has a LO_SUM involving SYMBOL_REF or LABEL_REF BASE and that MAX_OFFSET is @@ -15801,6 +15816,11 @@ mips_reorg_process_insns (void) if (TARGET_FIX_VR4120 || TARGET_FIX_24K) cfun->machine->all_noreorder_p = false; + /* Code compiled for R5900 can't be all noreorder because + we rely on the assembler to work around some errata. */ + if (TARGET_MIPS5900) + cfun->machine->all_noreorder_p = false; + /* The same is true for -mfix-vr4130 if we might generate MFLO or MFHI instructions. Note that we avoid using MFLO and MFHI if the VR4130 MACC and DMACC instructions are available instead; diff -Nurp '--exclude=build01' ../gcc-svn-20130105.orig/gcc/config/mips/mips-cpus.def gcc-svn-20130105-mips64r5900el-linux-patched/gcc/config/mips/mips-cpus.def --- ../gcc-svn-20130105.orig/gcc/config/mips/mips-cpus.def 2013-01-05 20:03:24.227962471 +0100 +++ gcc-svn-20130105-mips64r5900el-linux-patched/gcc/config/mips/mips-cpus.def 2013-01-06 19:11:56.336755480 +0100 @@ -71,6 +71,7 @@ MIPS_CPU ("r4600", PROCESSOR_R4600, 3, 0 MIPS_CPU ("orion", PROCESSOR_R4600, 3, 0) MIPS_CPU ("r4650", PROCESSOR_R4650, 3, 0) MIPS_CPU ("r4700", PROCESSOR_R4700, 3, 0) +MIPS_CPU ("r5900", PROCESSOR_R5900, 3, 0) /* ST Loongson 2E/2F processors. */ MIPS_CPU ("loongson2e", PROCESSOR_LOONGSON_2E, 3, PTF_AVOID_BRANCHLIKELY) MIPS_CPU ("loongson2f", PROCESSOR_LOONGSON_2F, 3, PTF_AVOID_BRANCHLIKELY) diff -Nurp '--exclude=build01' ../gcc-svn-20130105.orig/gcc/config/mips/mips.h gcc-svn-20130105-mips64r5900el-linux-patched/gcc/config/mips/mips.h --- ../gcc-svn-20130105.orig/gcc/config/mips/mips.h 2013-01-05 20:03:24.231962472 +0100 +++ gcc-svn-20130105-mips64r5900el-linux-patched/gcc/config/mips/mips.h 2013-01-06 19:11:56.336755480 +0100 @@ -215,6 +215,7 @@ struct mips_cpu_info { #define TARGET_MIPS4130 (mips_arch == PROCESSOR_R4130) #define TARGET_MIPS5400 (mips_arch == PROCESSOR_R5400) #define TARGET_MIPS5500 (mips_arch == PROCESSOR_R5500) +#define TARGET_MIPS5900 (mips_arch == PROCESSOR_R5900) #define TARGET_MIPS7000 (mips_arch == PROCESSOR_R7000) #define TARGET_MIPS9000 (mips_arch == PROCESSOR_R9000) #define TARGET_OCTEON (mips_arch == PROCESSOR_OCTEON \ @@ -245,6 +246,7 @@ struct mips_cpu_info { #define TUNE_MIPS5000 (mips_tune == PROCESSOR_R5000) #define TUNE_MIPS5400 (mips_tune == PROCESSOR_R5400) #define TUNE_MIPS5500 (mips_tune == PROCESSOR_R5500) +#define TUNE_MIPS5900 (mips_tune == PROCESSOR_R5900) #define TUNE_MIPS6000 (mips_tune == PROCESSOR_R6000) #define TUNE_MIPS7000 (mips_tune == PROCESSOR_R7000) #define TUNE_MIPS9000 (mips_tune == PROCESSOR_R9000) @@ -815,6 +817,7 @@ struct mips_cpu_info { #define ISA_HAS_MUL3 ((TARGET_MIPS3900 \ || TARGET_MIPS5400 \ || TARGET_MIPS5500 \ + || TARGET_MIPS5900 \ || TARGET_MIPS7000 \ || TARGET_MIPS9000 \ || TARGET_MAD \ @@ -829,6 +832,21 @@ struct mips_cpu_info { && TARGET_OCTEON \ && !TARGET_MIPS16) +/* Target supports instructions dmult and dmultu (integer). */ +#define TARGET_HAS_DMULT (TARGET_64BIT \ + && !TARGET_MIPS5900) + +/* Target supports instructions mult and multu in 32 bit mode (integer). */ +#define TARGET_HAS_MULT (mips_isa >= 1) + +/* Target supports instructions dmult and dmultu (integer). */ +#define TARGET_HAS_DDIV (TARGET_64BIT \ + && !TARGET_MIPS5900) + +/* Target supports instructions mult and multu in 32 bit mode (integer). */ +#define TARGET_HAS_DIV (mips_isa >= 1) + + /* ISA has the floating-point conditional move instructions introduced in mips4. */ #define ISA_HAS_FP_CONDMOVE ((ISA_MIPS4 \ @@ -841,10 +859,10 @@ struct mips_cpu_info { /* ISA has the integer conditional move instructions introduced in mips4 and ST Loongson 2E/2F. */ -#define ISA_HAS_CONDMOVE (ISA_HAS_FP_CONDMOVE || TARGET_LOONGSON_2EF) +#define ISA_HAS_CONDMOVE (ISA_HAS_FP_CONDMOVE || TARGET_LOONGSON_2EF || TARGET_MIPS5900) /* ISA has LDC1 and SDC1. */ -#define ISA_HAS_LDC1_SDC1 (!ISA_MIPS1 && !TARGET_MIPS16) +#define ISA_HAS_LDC1_SDC1 (!ISA_MIPS1 && !TARGET_MIPS16 && !TARGET_MIPS5900) /* ISA has the mips4 FP condition code instructions: FP-compare to CC, branch on CC, and move (both FP and non-FP) on CC. */ @@ -884,7 +902,7 @@ struct mips_cpu_info { #define ISA_HAS_FP_MADD4_MSUB4 ISA_HAS_FP4 /* ISA has floating-point madd and msub instructions 'c = a * b [+-] c'. */ -#define ISA_HAS_FP_MADD3_MSUB3 TARGET_LOONGSON_2EF +#define ISA_HAS_FP_MADD3_MSUB3 (TARGET_LOONGSON_2EF || TARGET_MIPS5900) /* ISA has floating-point nmadd and nmsub instructions 'd = -((a * b) [+-] c)'. */ @@ -955,6 +973,7 @@ struct mips_cpu_info { /* ISA has data prefetch instructions. This controls use of 'pref'. */ #define ISA_HAS_PREFETCH ((ISA_MIPS4 \ || TARGET_LOONGSON_2EF \ + || TARGET_MIPS5900 \ || ISA_MIPS32 \ || ISA_MIPS32R2 \ || ISA_MIPS64 \ @@ -974,7 +993,11 @@ struct mips_cpu_info { /* True if trunc.w.s and trunc.w.d are real (not synthetic) instructions. Both require TARGET_HARD_FLOAT, and trunc.w.d also requires TARGET_DOUBLE_FLOAT. */ -#define ISA_HAS_TRUNC_W (!ISA_MIPS1) +#define ISA_HAS_TRUNC_W_D (!ISA_MIPS1) + +/* True if trunc.w.s is real (not synthetic) instructions. + Requires TARGET_HARD_FLOAT. */ +#define ISA_HAS_TRUNC_W_S (ISA_HAS_TRUNC_W_D || TARGET_MIPS5900) /* ISA includes the MIPS32r2 seb and seh instructions. */ #define ISA_HAS_SEB_SEH ((ISA_MIPS32R2 \ @@ -1015,15 +1038,18 @@ struct mips_cpu_info { and "addiu $4,$4,1". */ #define ISA_HAS_LOAD_DELAY (ISA_MIPS1 \ && !TARGET_MIPS3900 \ - && !TARGET_MIPS16) + && !TARGET_MIPS16 \ + && !TARGET_MIPS5900) /* Likewise mtc1 and mfc1. */ #define ISA_HAS_XFER_DELAY (mips_isa <= 3 \ - && !TARGET_LOONGSON_2EF) + && !TARGET_LOONGSON_2EF \ + && !TARGET_MIPS5900) /* Likewise floating-point comparisons. */ #define ISA_HAS_FCMP_DELAY (mips_isa <= 3 \ - && !TARGET_LOONGSON_2EF) + && !TARGET_LOONGSON_2EF \ + && !TARGET_MIPS5900) /* True if mflo and mfhi can be immediately followed by instructions which write to the HI and LO registers. @@ -1042,6 +1068,7 @@ struct mips_cpu_info { || ISA_MIPS64 \ || ISA_MIPS64R2 \ || TARGET_MIPS5500 \ + || TARGET_MIPS5900 \ || TARGET_LOONGSON_2EF) /* ISA includes synci, jr.hb and jalr.hb. */ diff -Nurp '--exclude=build01' ../gcc-svn-20130105.orig/gcc/config/mips/mips.md gcc-svn-20130105-mips64r5900el-linux-patched/gcc/config/mips/mips.md --- ../gcc-svn-20130105.orig/gcc/config/mips/mips.md 2013-01-05 20:03:24.227962471 +0100 +++ gcc-svn-20130105-mips64r5900el-linux-patched/gcc/config/mips/mips.md 2013-01-06 20:08:35.056750990 +0100 @@ -58,6 +58,7 @@ r5000 r5400 r5500 + r5900 r7000 r8000 r9000 @@ -726,7 +727,7 @@ ;; This mode iterator allows :MOVECC to be used anywhere that a ;; conditional-move-type condition is needed. (define_mode_iterator MOVECC [SI (DI "TARGET_64BIT") - (CC "TARGET_HARD_FLOAT && !TARGET_LOONGSON_2EF")]) + (CC "TARGET_HARD_FLOAT && !TARGET_LOONGSON_2EF && !TARGET_MIPS5900")]) ;; 32-bit integer moves for which we provide move patterns. (define_mode_iterator IMOVE32 @@ -1448,7 +1449,7 @@ [(set (match_operand:GPR 0 "register_operand") (mult:GPR (match_operand:GPR 1 "register_operand") (match_operand:GPR 2 "register_operand")))] - "" + "TARGET_HAS_MULT" { rtx lo; @@ -1490,11 +1491,11 @@ (mult:GPR (match_operand:GPR 1 "register_operand" "d,d") (match_operand:GPR 2 "register_operand" "d,d"))) (clobber (match_scratch:GPR 3 "=l,X"))] - "ISA_HAS_MUL3" + "ISA_HAS_MUL3 && TARGET_HAS_MULT" { if (which_alternative == 1) return "mult\t%1,%2"; - if (mode == SImode && TARGET_MIPS3900) + if (mode == SImode && (TARGET_MIPS3900 || TARGET_MIPS5900)) return "mult\t%0,%1,%2"; return "mul\t%0,%1,%2"; } @@ -1528,7 +1529,7 @@ [(set (match_operand:GPR 0 "muldiv_target_operand" "=l") (mult:GPR (match_operand:GPR 1 "register_operand" "d") (match_operand:GPR 2 "register_operand" "d")))] - "!TARGET_FIX_R4000" + "!TARGET_FIX_R4000 && TARGET_HAS_MULT" "mult\t%1,%2" [(set_attr "type" "imul") (set_attr "mode" "")]) @@ -1538,7 +1539,7 @@ (mult:GPR (match_operand:GPR 1 "register_operand" "d") (match_operand:GPR 2 "register_operand" "d"))) (clobber (match_scratch:GPR 3 "=l"))] - "TARGET_FIX_R4000" + "TARGET_FIX_R4000 && TARGET_HAS_MULT" "mult\t%1,%2\;mflo\t%0" [(set_attr "type" "imul") (set_attr "mode" "") @@ -1872,7 +1873,7 @@ [(set (match_operand:DI 0 "register_operand") (mult:DI (any_extend:DI (match_operand:SI 1 "register_operand")) (any_extend:DI (match_operand:SI 2 "register_operand"))))] - "mips_mulsidi3_gen_fn () != NULL" + "mips_mulsidi3_gen_fn () != NULL && TARGET_HAS_DMULT" { mulsidi3_gen_fn fn = mips_mulsidi3_gen_fn (); emit_insn (fn (operands[0], operands[1], operands[2])); @@ -1900,7 +1901,7 @@ [(set (match_operand:DI 0 "muldiv_target_operand" "=ka") (mult:DI (any_extend:DI (match_operand:SI 1 "register_operand" "d")) (any_extend:DI (match_operand:SI 2 "register_operand" "d"))))] - "!TARGET_64BIT && (!TARGET_FIX_R4000 || ISA_HAS_DSP)" + "(!TARGET_64BIT || (TARGET_64BIT && !TARGET_HAS_DMULT)) && (!TARGET_FIX_R4000 || ISA_HAS_DSP)" { if (ISA_HAS_DSP_MULT) return "mult\t%q0,%1,%2"; @@ -1927,7 +1928,7 @@ (any_extend:DI (match_operand:SI 2 "register_operand" "d")))) (clobber (match_scratch:TI 3 "=x")) (clobber (match_scratch:DI 4 "=d"))] - "TARGET_64BIT && !TARGET_FIX_R4000 && !ISA_HAS_DMUL3 && !TARGET_MIPS16" + "TARGET_64BIT && !TARGET_FIX_R4000 && !ISA_HAS_DMUL3 && !TARGET_MIPS16 && TARGET_HAS_DMULT" "#" "&& reload_completed" [(const_int 0)] @@ -2105,7 +2106,7 @@ { rtx hilo; - if (TARGET_64BIT) + if (TARGET_64BIT && TARGET_HAS_DMULT) { hilo = gen_rtx_REG (TImode, MD_REG_FIRST); emit_insn (gen_mulsidi3_64bit_hilo (hilo, operands[1], operands[2])); @@ -2159,7 +2160,7 @@ (mult:TI (any_extend:TI (match_operand:DI 1 "register_operand")) (any_extend:TI (match_operand:DI 2 "register_operand"))) (const_int 64))))] - "TARGET_64BIT && !( == ZERO_EXTEND && TARGET_FIX_VR4120)" + "TARGET_64BIT && TARGET_HAS_DMULT && !( == ZERO_EXTEND && TARGET_FIX_VR4120)" { if (TARGET_MIPS16) emit_insn (gen_muldi3_highpart_split (operands[0], operands[1], @@ -2180,6 +2181,7 @@ (clobber (match_scratch:DI 3 "=l"))] "TARGET_64BIT && !TARGET_MIPS16 + && TARGET_HAS_DMULT && !( == ZERO_EXTEND && TARGET_FIX_VR4120)" { return TARGET_FIX_R4000 ? "dmult\t%1,%2\n\tmfhi\t%0" : "#"; } "&& reload_completed && !TARGET_FIX_R4000" @@ -2200,7 +2202,7 @@ (mult:TI (any_extend:TI (match_operand:DI 1 "register_operand")) (any_extend:TI (match_operand:DI 2 "register_operand"))) (const_int 64))))] - "" + "TARGET_HAS_DMULT" { rtx hilo; @@ -2214,7 +2216,7 @@ [(set (match_operand:TI 0 "register_operand") (mult:TI (any_extend:TI (match_operand:DI 1 "register_operand")) (any_extend:TI (match_operand:DI 2 "register_operand"))))] - "TARGET_64BIT && !( == ZERO_EXTEND && TARGET_FIX_VR4120)" + "TARGET_64BIT && !( == ZERO_EXTEND && TARGET_FIX_VR4120) && TARGET_HAS_DMULT" { rtx hilo; @@ -2237,6 +2239,7 @@ (mult:TI (any_extend:TI (match_operand:DI 1 "register_operand" "d")) (any_extend:TI (match_operand:DI 2 "register_operand" "d"))))] "TARGET_64BIT + && TARGET_HAS_DMULT && !TARGET_FIX_R4000 && !( == ZERO_EXTEND && TARGET_FIX_VR4120)" "dmult\t%1,%2" @@ -2250,6 +2253,7 @@ (clobber (match_scratch:TI 3 "=x"))] "TARGET_64BIT && TARGET_FIX_R4000 + && TARGET_HAS_DMULT && !( == ZERO_EXTEND && TARGET_FIX_VR4120)" "dmult\t%1,%2\;mflo\t%L0\;mfhi\t%M0" [(set_attr "type" "imul") @@ -2537,7 +2541,7 @@ (set (match_operand:GPR 3 "register_operand") (mod:GPR (match_dup 1) (match_dup 2)))] - "!TARGET_FIX_VR4120" + "!TARGET_FIX_VR4120 && TARGET_HAS_DIV" { if (TARGET_MIPS16) { @@ -2558,7 +2562,7 @@ (set (match_operand:GPR 3 "register_operand" "=d") (mod:GPR (match_dup 1) (match_dup 2)))] - "!TARGET_FIX_VR4120 && !TARGET_MIPS16" + "!TARGET_FIX_VR4120 && !TARGET_MIPS16 && TARGET_HAS_DIV" "#" "&& reload_completed" [(const_int 0)] @@ -2577,7 +2581,7 @@ (set (match_operand:GPR 3 "register_operand") (umod:GPR (match_dup 1) (match_dup 2)))] - "" + "TARGET_HAS_DIV" { if (TARGET_MIPS16) { @@ -2598,7 +2602,7 @@ (set (match_operand:GPR 3 "register_operand" "=d") (umod:GPR (match_dup 1) (match_dup 2)))] - "!TARGET_MIPS16" + "!TARGET_MIPS16 && TARGET_HAS_DIV" "#" "reload_completed" [(const_int 0)] @@ -2614,7 +2618,7 @@ [(set (match_operand:GPR 0 "register_operand") (any_mod:GPR (match_operand:GPR 1 "register_operand") (match_operand:GPR 2 "register_operand")))] - "" + "TARGET_HAS_DIV" { rtx hilo; @@ -2641,7 +2645,7 @@ [(any_div:GPR (match_operand:GPR 1 "register_operand" "d") (match_operand:GPR 2 "register_operand" "d"))] UNSPEC_SET_HILO))] - "" + "TARGET_HAS_DIV" { return mips_output_division ("div\t%.,%1,%2", operands); } [(set_attr "type" "idiv") (set_attr "mode" "")]) @@ -3464,7 +3468,7 @@ (fix:SI (match_operand:DF 1 "register_operand")))] "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT" { - if (!ISA_HAS_TRUNC_W) + if (!ISA_HAS_TRUNC_W_D) { emit_insn (gen_fix_truncdfsi2_macro (operands[0], operands[1])); DONE; @@ -3474,7 +3478,7 @@ (define_insn "fix_truncdfsi2_insn" [(set (match_operand:SI 0 "register_operand" "=f") (fix:SI (match_operand:DF 1 "register_operand" "f")))] - "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && ISA_HAS_TRUNC_W" + "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && ISA_HAS_TRUNC_W_D" "trunc.w.d %0,%1" [(set_attr "type" "fcvt") (set_attr "mode" "DF") @@ -3484,7 +3488,7 @@ [(set (match_operand:SI 0 "register_operand" "=f") (fix:SI (match_operand:DF 1 "register_operand" "f"))) (clobber (match_scratch:DF 2 "=d"))] - "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !ISA_HAS_TRUNC_W" + "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !ISA_HAS_TRUNC_W_D" { if (mips_nomacro.nesting_level > 0) return ".set\tmacro\;trunc.w.d %0,%1,%2\;.set\tnomacro"; @@ -3501,7 +3505,7 @@ (fix:SI (match_operand:SF 1 "register_operand")))] "TARGET_HARD_FLOAT" { - if (!ISA_HAS_TRUNC_W) + if (!ISA_HAS_TRUNC_W_S) { emit_insn (gen_fix_truncsfsi2_macro (operands[0], operands[1])); DONE; @@ -3511,7 +3515,7 @@ (define_insn "fix_truncsfsi2_insn" [(set (match_operand:SI 0 "register_operand" "=f") (fix:SI (match_operand:SF 1 "register_operand" "f")))] - "TARGET_HARD_FLOAT && ISA_HAS_TRUNC_W" + "TARGET_HARD_FLOAT && ISA_HAS_TRUNC_W_S" "trunc.w.s %0,%1" [(set_attr "type" "fcvt") (set_attr "mode" "SF") @@ -3521,7 +3525,7 @@ [(set (match_operand:SI 0 "register_operand" "=f") (fix:SI (match_operand:SF 1 "register_operand" "f"))) (clobber (match_scratch:SF 2 "=d"))] - "TARGET_HARD_FLOAT && !ISA_HAS_TRUNC_W" + "TARGET_HARD_FLOAT && !ISA_HAS_TRUNC_W_S" { if (mips_nomacro.nesting_level > 0) return ".set\tmacro\;trunc.w.s %0,%1,%2\;.set\tnomacro"; diff -Nurp '--exclude=build01' ../gcc-svn-20130105.orig/gcc/config.gcc gcc-svn-20130105-mips64r5900el-linux-patched/gcc/config.gcc --- ../gcc-svn-20130105.orig/gcc/config.gcc 2013-01-05 20:03:33.659962367 +0100 +++ gcc-svn-20130105-mips64r5900el-linux-patched/gcc/config.gcc 2013-01-06 19:11:56.340755480 +0100 @@ -1881,11 +1881,17 @@ mipsisa64sb1-*-elf* | mipsisa64sb1el-*-e target_cpu_default="MASK_64BIT|MASK_FLOAT64" tm_defines="${tm_defines} MIPS_ISA_DEFAULT=64 MIPS_CPU_STRING_DEFAULT=\\\"sb1\\\" MIPS_ABI_DEFAULT=ABI_O64" ;; -mips-*-elf* | mipsel-*-elf*) +mips-*-elf* | mipsel-*-elf* | mipsr5900-*-elf* | mipsr5900el-*-elf*) tm_file="elfos.h newlib-stdint.h ${tm_file} mips/elf.h" tmake_file="mips/t-elf" ;; -mips64-*-elf* | mips64el-*-elf*) +mips64r5900-*-elf* | mips64r5900el-*-elf*) + tm_file="elfos.h newlib-stdint.h ${tm_file} mips/elf.h" + tmake_file="mips/t-elf" + target_cpu_default="MASK_64BIT" + tm_defines="${tm_defines} MIPS_ISA_DEFAULT=3 MIPS_ABI_DEFAULT=ABI_N32" + ;; +mips64-*-elf* | mips64el-*-elf* | mips64r5900-*-elf* | mips64r5900el-*-elf*) tm_file="elfos.h newlib-stdint.h ${tm_file} mips/elf.h" tmake_file="mips/t-elf" target_cpu_default="MASK_64BIT|MASK_FLOAT64" @@ -2910,6 +2916,26 @@ if test x$with_cpu = x ; then ;; esac ;; + mips64r5900-*-*|mips64r5900el-*-*) + with_arch=r5900 + with_tune=r5900 + if test x$with_llsc = x; then + # R5900 doesn't support ll, sc, lld and scd instructions: + with_llsc=no + fi + if test x$with_float = x; then + # R5900 doesn't support 64 bit float: + with_float=soft + fi + ;; + mipsr5900-*-*|mipsr5900el-*-*) + with_arch=r5900 + with_tune=r5900 + if test x$with_llsc = x; then + # R5900 doesn't support ll, sc, lld and scd instructions: + with_llsc=no + fi + ;; mips*-*-vxworks) with_arch=mips2 ;; @@ -3374,7 +3400,7 @@ case "${target}" in supported_defaults="abi arch arch_32 arch_64 float tune tune_32 tune_64 divide llsc mips-plt synci" case ${with_float} in - "" | soft | hard) + "" | soft | hard | single | double) # OK ;; *) diff -Nurp '--exclude=build01' ../gcc-svn-20130105.orig/libgcc/config.host gcc-svn-20130105-mips64r5900el-linux-patched/libgcc/config.host --- ../gcc-svn-20130105.orig/libgcc/config.host 2013-01-05 19:28:43.695984006 +0100 +++ gcc-svn-20130105-mips64r5900el-linux-patched/libgcc/config.host 2013-01-06 19:11:56.340755480 +0100 @@ -761,10 +761,18 @@ mips-*-elf* | mipsel-*-elf*) tmake_file="$tmake_file mips/t-elf mips/t-crtstuff mips/t-mips16" extra_parts="$extra_parts crti.o crtn.o" ;; +mipsr5900-*-elf* | mipsr5900el-*-elf*) + tmake_file="$tmake_file mips/t-elf mips/t-crtstuff" + extra_parts="$extra_parts crti.o crtn.o" + ;; mips64-*-elf* | mips64el-*-elf*) tmake_file="$tmake_file mips/t-elf mips/t-crtstuff mips/t-mips16" extra_parts="$extra_parts crti.o crtn.o" ;; +mips64r5900-*-elf* | mips64r5900el-*-elf*) + tmake_file="$tmake_file mips/t-elf mips/t-crtstuff" + extra_parts="$extra_parts crti.o crtn.o" + ;; mips64vr-*-elf* | mips64vrel-*-elf*) tmake_file="$tmake_file mips/t-elf mips/t-vr mips/t-crtstuff" extra_parts="$extra_parts crti.o crtn.o" diff -Nurp '--exclude=build01' ../gcc-svn-20130105.orig/libgcc/Makefile.in gcc-svn-20130105-mips64r5900el-linux-patched/libgcc/Makefile.in --- ../gcc-svn-20130105.orig/libgcc/Makefile.in 2013-01-05 19:28:43.695984006 +0100 +++ gcc-svn-20130105-mips64r5900el-linux-patched/libgcc/Makefile.in 2013-01-06 19:51:13.488752493 +0100 @@ -293,6 +293,9 @@ MULTIOSSUBDIR := $(shell if test $(MULTI inst_libdir = $(libsubdir)$(MULTISUBDIR) inst_slibdir = $(slibdir)$(MULTIOSSUBDIR) +# Get mips type: __mips or __mips64 is defined as GCC macro: +MIPSTYPE := $(shell $(CC) $(CFLAGS) -dM -E - < /dev/null | grep -e "\<__mips\>" -e "\<__mips64\>" | (read define type value; echo $$type)) + gcc_compile_bare = $(CC) $(INTERNAL_CFLAGS) compile_deps = -MT $@ -MD -MP -MF $(basename $@).dep gcc_compile = $(gcc_compile_bare) -o $@ $(compile_deps) @@ -401,7 +404,8 @@ LIB2ADDEHSTATIC += $(srcdir)/emutls.c LIB2ADDEHSHARED += $(srcdir)/emutls.c # Library members defined in libgcc2.c. -lib2funcs = _muldi3 _negdi2 _lshrdi3 _ashldi3 _ashrdi3 _cmpdi2 _ucmpdi2 \ +lib2difuncs = _muldi3 +lib2funcs = $(lib2difuncs) _negdi2 _lshrdi3 _ashldi3 _ashrdi3 _cmpdi2 _ucmpdi2 \ _clear_cache _trampoline __main _absvsi2 \ _absvdi2 _addvsi3 _addvdi3 _subvsi3 _subvdi3 _mulvsi3 _mulvdi3 \ _negvsi2 _negvdi2 _ctors _ffssi2 _ffsdi2 _clz _clzsi2 _clzdi2 \ @@ -427,7 +431,8 @@ endif # These might cause a divide overflow trap and so are compiled with # unwinder info. -LIB2_DIVMOD_FUNCS = _divdi3 _moddi3 _udivdi3 _umoddi3 _udiv_w_sdiv _udivmoddi4 +LIB2_DIVMODDI_FUNCS = _divdi3 _moddi3 _udivdi3 _umoddi3 _udivmoddi4 +LIB2_DIVMOD_FUNCS = $(LIB2_DIVMODDI_FUNCS) _udiv_w_sdiv # Remove any objects from lib2funcs and LIB2_DIVMOD_FUNCS that are # defined as optimized assembly code in LIB1ASMFUNCS or as C code @@ -459,12 +464,26 @@ lib2funcs-o = $(patsubst %,%$(objext),$( $(lib2funcs-o): %$(objext): $(srcdir)/libgcc2.c $(gcc_compile) -DL$* -c $< $(vis_hide) libgcc-objects += $(lib2funcs-o) +ifeq ($(MIPSTYPE),__mips64) +# Build functions needed by MIPS r5900. +lib2difuncs-o = $(patsubst %,%$(objext),$(addsuffix _32bit,$(lib2difuncs))) +$(lib2difuncs-o): %$(objext): $(srcdir)/libgcc2.c + $(gcc_compile) -DL$(subst _32bit,,$*) -DLIBGCC2_UNITS_PER_WORD=4 -c $< $(vis_hide) +libgcc-objects += $(lib2difuncs-o) +endif ifeq ($(enable_shared),yes) lib2funcs-s-o = $(patsubst %,%_s$(objext),$(lib2funcs)) $(lib2funcs-s-o): %_s$(objext): $(srcdir)/libgcc2.c $(gcc_s_compile) -DL$* -c $< libgcc-s-objects += $(lib2funcs-s-o) +ifeq ($(MIPSTYPE),__mips64) +# Build functions needed by MIPS r5900. +lib2difuncs-s-o = $(patsubst %,%_s$(objext),$(addsuffix _32bit,$(lib2difuncs))) +$(lib2difuncs-s-o): %_s$(objext): $(srcdir)/libgcc2.c + $(gcc_s_compile) -DL$(subst _32bit,,$*) -DLIBGCC2_UNITS_PER_WORD=4 -c $< +libgcc-s-objects += $(lib2difuncs-s-o) +endif endif ifneq ($(LIB2_SIDITI_CONV_FUNCS),) @@ -501,6 +520,14 @@ $(lib2-divmod-o): %$(objext): $(srcdir)/ $(gcc_compile) -DL$* -c $< \ $(LIB2_DIVMOD_EXCEPTION_FLAGS) $(vis_hide) libgcc-objects += $(lib2-divmod-o) +ifeq ($(MIPSTYPE),__mips64) +# Build functions needed by MIPS r5900. +lib2-divmoddi-o = $(patsubst %,%$(objext),$(addsuffix _32bit,$(LIB2_DIVMODDI_FUNCS))) +$(lib2-divmoddi-o): %$(objext): $(srcdir)/libgcc2.c + $(gcc_compile) -DL$(subst _32bit,,$*) -DLIBGCC2_UNITS_PER_WORD=4 -c $< \ + $(LIB2_DIVMOD_EXCEPTION_FLAGS) $(vis_hide) +libgcc-objects += $(lib2-divmoddi-o) +endif ifeq ($(enable_shared),yes) lib2-divmod-s-o = $(patsubst %,%_s$(objext),$(LIB2_DIVMOD_FUNCS)) @@ -508,6 +535,14 @@ $(lib2-divmod-s-o): %_s$(objext): $(srcd $(gcc_s_compile) -DL$* -c $< \ $(LIB2_DIVMOD_EXCEPTION_FLAGS) libgcc-s-objects += $(lib2-divmod-s-o) +ifeq ($(MIPSTYPE),__mips64) +# Build functions needed by MIPS r5900. +lib2-divmoddi-s-o = $(patsubst %,%_s$(objext),$(addsuffix _32bit,$(LIB2_DIVMODDI_FUNCS))) +$(lib2-divmoddi-s-o): %_s$(objext): $(srcdir)/libgcc2.c + $(gcc_s_compile) -DL$(subst _32bit,,$*) -DLIBGCC2_UNITS_PER_WORD=4 -c $< \ + $(LIB2_DIVMOD_EXCEPTION_FLAGS) +libgcc-s-objects += $(lib2-divmoddi-s-o) +endif endif ifeq ($(TPBIT),) diff -Nurp '--exclude=build01' ../gcc-svn-20130105.orig/libstdc++-v3/configure.host gcc-svn-20130105-mips64r5900el-linux-patched/libstdc++-v3/configure.host --- ../gcc-svn-20130105.orig/libstdc++-v3/configure.host 2013-01-05 19:09:50.603996241 +0100 +++ gcc-svn-20130105-mips64r5900el-linux-patched/libstdc++-v3/configure.host 2013-01-06 19:11:56.340755480 +0100 @@ -322,6 +322,11 @@ esac # Set any OS-dependent and CPU-dependent bits. # THIS TABLE IS SORTED. KEEP IT THAT WAY. case "${host}" in + mips*) + atomicity_dir="cpu/generic" + ;; +esac +case "${host}" in *-*-linux*) case "${host_cpu}" in i[567]86)