From patchwork Mon Jul 22 21:34:29 2013 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Eric Botcazou X-Patchwork-Id: 260817 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 with cipher DHE-RSA-AES256-SHA (256/256 bits)) (Client CN "localhost", Issuer "www.qmailtoaster.com" (not verified)) by ozlabs.org (Postfix) with ESMTPS id B09A32C0097 for ; Tue, 23 Jul 2013 07:42:40 +1000 (EST) DomainKey-Signature: a=rsa-sha1; c=nofws; d=gcc.gnu.org; h=list-id :list-unsubscribe:list-archive:list-post:list-help:sender:from :to:subject:date:mime-version:message-id:content-type; q=dns; s= default; b=e9gMv7JEggOsW/MhHa4tQX8+TKp5a/i0cqaMFSmSw9QM0rvS+Cz/z RReqTIyvESepmVZ614jomy35pX0tPHDH8996ye/GKsyl4Sg/YTFEAIFpWiDw3mRf QpYJr/Dnum2ULXoVUsVibu+zmcWUyZ8EyW6aqzDTxYO0Ucpvfc+poY= 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:from :to:subject:date:mime-version:message-id:content-type; s= default; bh=SLQZhXITAQnLpQaLKa/0Rxqh7PQ=; b=xAUH4TupTPIEqhTGiipD dhd/1AolDgd0Z0/WPV+GgBl8OJk/bB87Gjq5hsu5uVed2c6DtzNZhhF8LMaHrnZn LJDtvu0hmli5hupAQN72YC/IKMVe0fE+GJO4ztrok0TCeTbKuwxiQ/p4xUJQNzmU GU4M3U2G//jNBZDvBc4aDDA= Received: (qmail 2006 invoked by alias); 22 Jul 2013 21:42:34 -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 1996 invoked by uid 89); 22 Jul 2013 21:42:33 -0000 X-Spam-SWARE-Status: No, score=-0.2 required=5.0 tests=AWL, BAYES_50, RDNS_NONE, TW_FC autolearn=no version=3.3.1 Received: from Unknown (HELO smtp.eu.adacore.com) (194.98.77.210) by sourceware.org (qpsmtpd/0.84/v0.84-167-ge50287c) with ESMTP; Mon, 22 Jul 2013 21:42:31 +0000 Received: from localhost (localhost [127.0.0.1]) by filtered-smtp.eu.adacore.com (Postfix) with ESMTP id D434A265619E for ; Mon, 22 Jul 2013 23:42:23 +0200 (CEST) Received: from smtp.eu.adacore.com ([127.0.0.1]) by localhost (smtp.eu.adacore.com [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id VH5Jd6qfWbf3 for ; Mon, 22 Jul 2013 23:42:23 +0200 (CEST) Received: from hermes.site (ADijon-552-1-125-231.w92-148.abo.wanadoo.fr [92.148.188.231]) (using TLSv1 with cipher ECDHE-RSA-AES256-SHA (256/256 bits)) (No client certificate requested) by smtp.eu.adacore.com (Postfix) with ESMTPSA id 9C6212654D4D for ; Mon, 22 Jul 2013 23:42:23 +0200 (CEST) From: Eric Botcazou To: gcc-patches@gcc.gnu.org Subject: [SPARC] Work around data cache nullify issues on LEON3 Date: Mon, 22 Jul 2013 23:34:29 +0200 User-Agent: KMail/1.13.5 (Linux/2.6.34.10-0.6-desktop; KDE/4.4.4; x86_64; ; ) MIME-Version: 1.0 Message-Id: <201307222334.29651.ebotcazou@adacore.com> X-Virus-Found: No This enhances -mfix-ut699 to work around the data cache nullify issues recently uncovered on the LEON3 processor, as documented in the relevant errata sheet. Tested on SPARC/Solaris, applied on the mainline. 2013-07-22 Eric Botcazou * config.gcc (sparc*-*-*): Accept leon3 processor. (sparc-leon*-*): Merge with sparc*-*-* and add leon3 support. * doc/invoke.texi (SPARC Options): Adjust -mfix-ut699 entry. * config/sparc/sparc-opts.h (enum processor_type): Add PROCESSOR_LEON3. * config/sparc/sparc.opt (enum processor_type): Add leon3. (mfix-ut699): Adjust comment. * config/sparc/sparc.h (TARGET_CPU_leon3): New define. (CPP_CPU32_DEFAULT_SPEC): Add leon3 support. (CPP_CPU_SPEC): Likewise. (ASM_CPU_SPEC): Likewise. * config/sparc/sparc.c (leon3_cost): New constant. (sparc_option_override): Add leon3 support. (mem_ref): New function. (sparc_gate_work_around_errata): Return true if -mfix-ut699 is enabled. (sparc_do_work_around_errata): Look into the instruction in the delay slot and adjust accordingly. Add fix for the data cache nullify issues of the UT699. Change insertion position for the NOP. * config/sparc/leon.md (leon_fpalu, leon_fpmds, write_buf): Delete. (leon3_load): New reservation. (leon_store): Bump latency to 2. (grfpu): New automaton. (grfpu_alu): New unit. (grfpu_ds): Likewise. (leon_fp_alu): Adjust. (leon_fp_mult): Delete. (leon_fp_div): Split into leon_fp_divs and leon_fp_divd. (leon_fp_sqrt): Split into leon_fp_sqrts and leon_fp_sqrtd. * config/sparc/sparc.md (cpu): Add leon3. * config/sparc/sync.md (atomic_exchangesi): Disable if -mfix-ut699. (swapsi): Likewise. (atomic_test_and_set): Likewise. (ldstub): Likewise. Index: config.gcc =================================================================== --- config.gcc (revision 201053) +++ config.gcc (working copy) @@ -3642,7 +3642,7 @@ case "${target}" in case ${val} in "" | sparc | sparcv9 | sparc64 \ | v7 | cypress \ - | v8 | supersparc | hypersparc | leon \ + | v8 | supersparc | hypersparc | leon | leon3 \ | sparclite | f930 | f934 | sparclite86x \ | sparclet | tsc701 \ | v9 | ultrasparc | ultrasparc3 | niagara | niagara2 \ @@ -3799,15 +3799,6 @@ case ${target} in cxx_target_objs="${cxx_target_objs} sh-c.o" ;; - sparc-leon*-*) - if test x$with_tune = x ; then - with_tune=leon; - fi - - # The SPARC port checks this value at compile-time. - target_cpu_default2="TARGET_CPU_$with_cpu" - ;; - sparc*-*-*) # Some standard aliases. case x$with_cpu in @@ -3819,6 +3810,17 @@ case ${target} in ;; esac + if test x$with_tune = x ; then + case ${target} in + *-leon-*) + with_tune=leon + ;; + *-leon[3-9]*) + with_tune=leon3 + ;; + esac + fi + # The SPARC port checks this value at compile-time. target_cpu_default2="TARGET_CPU_$with_cpu" ;; Index: doc/invoke.texi =================================================================== --- doc/invoke.texi (revision 201053) +++ doc/invoke.texi (working copy) @@ -19491,8 +19491,8 @@ processor (which corresponds to erratum @item -mfix-ut699 @opindex mfix-ut699 -Enable the documented workarounds for the floating-point errata of the UT699 -processor. +Enable the documented workarounds for the floating-point errata and the data +cache nullify errata of the UT699 processor. @end table These @samp{-m} options are supported in addition to the above Index: config/sparc/sparc.md =================================================================== --- config/sparc/sparc.md (revision 201053) +++ config/sparc/sparc.md (working copy) @@ -206,7 +206,7 @@ (define_mode_iterator F [SF DF TF]) ;; 'f' for all DF/TFmode values, including those that are specific to the v8. ;; Attribute for cpu type. -;; These must match the values for enum processor_type in sparc.h. +;; These must match the values of the enum processor_type in sparc-opts.h. (define_attr "cpu" "v7, cypress, @@ -214,6 +214,7 @@ (define_attr "cpu" supersparc, hypersparc, leon, + leon3, sparclite, f930, f934, Index: config/sparc/sparc.opt =================================================================== --- config/sparc/sparc.opt (revision 201053) +++ config/sparc/sparc.opt (working copy) @@ -146,6 +146,9 @@ EnumValue Enum(sparc_processor_type) String(leon) Value(PROCESSOR_LEON) EnumValue +Enum(sparc_processor_type) String(leon3) Value(PROCESSOR_LEON3) + +EnumValue Enum(sparc_processor_type) String(sparclite) Value(PROCESSOR_SPARCLITE) EnumValue @@ -203,7 +206,7 @@ Enable workaround for single erratum of mfix-ut699 Target Report RejectNegative Var(sparc_fix_ut699) -Enable workarounds for the FP errata of the UT699 processor +Enable workarounds for the errata of the UT699 processor Mask(LONG_DOUBLE_128) ;; Use 128-bit long double Index: config/sparc/sync.md =================================================================== --- config/sparc/sync.md (revision 201053) +++ config/sparc/sync.md (working copy) @@ -220,7 +220,7 @@ (define_expand "atomic_exchangesi" (match_operand:SI 1 "memory_operand" "") (match_operand:SI 2 "register_operand" "") (match_operand:SI 3 "const_int_operand" "")] - "TARGET_V8 || TARGET_V9" + "(TARGET_V8 || TARGET_V9) && !sparc_fix_ut699" { enum memmodel model = (enum memmodel) INTVAL (operands[3]); @@ -236,7 +236,7 @@ (define_insn "swapsi" UNSPECV_SWAP)) (set (match_dup 1) (match_operand:SI 2 "register_operand" "0"))] - "TARGET_V8 || TARGET_V9" + "(TARGET_V8 || TARGET_V9) && !sparc_fix_ut699" "swap\t%1, %0" [(set_attr "type" "multi")]) @@ -244,7 +244,7 @@ (define_expand "atomic_test_and_set" [(match_operand:QI 0 "register_operand" "") (match_operand:QI 1 "memory_operand" "") (match_operand:SI 2 "const_int_operand" "")] - "" + "!sparc_fix_ut699" { enum memmodel model = (enum memmodel) INTVAL (operands[2]); rtx ret; @@ -268,6 +268,6 @@ (define_insn "ldstub" (unspec_volatile:QI [(match_operand:QI 1 "memory_operand" "+m")] UNSPECV_LDSTUB)) (set (match_dup 1) (const_int -1))] - "" + "!sparc_fix_ut699" "ldstub\t%1, %0" [(set_attr "type" "multi")]) Index: config/sparc/sparc-opts.h =================================================================== --- config/sparc/sparc-opts.h (revision 201053) +++ config/sparc/sparc-opts.h (working copy) @@ -30,6 +30,7 @@ enum processor_type { PROCESSOR_SUPERSPARC, PROCESSOR_HYPERSPARC, PROCESSOR_LEON, + PROCESSOR_LEON3, PROCESSOR_SPARCLITE, PROCESSOR_F930, PROCESSOR_F934, Index: config/sparc/sparc.c =================================================================== --- config/sparc/sparc.c (revision 201053) +++ config/sparc/sparc.c (working copy) @@ -227,6 +227,30 @@ struct processor_costs leon_costs = { }; static const +struct processor_costs leon3_costs = { + COSTS_N_INSNS (1), /* int load */ + COSTS_N_INSNS (1), /* int signed load */ + COSTS_N_INSNS (1), /* int zeroed load */ + COSTS_N_INSNS (1), /* float load */ + COSTS_N_INSNS (1), /* fmov, fneg, fabs */ + COSTS_N_INSNS (1), /* fadd, fsub */ + COSTS_N_INSNS (1), /* fcmp */ + COSTS_N_INSNS (1), /* fmov, fmovr */ + COSTS_N_INSNS (1), /* fmul */ + COSTS_N_INSNS (14), /* fdivs */ + COSTS_N_INSNS (15), /* fdivd */ + COSTS_N_INSNS (22), /* fsqrts */ + COSTS_N_INSNS (23), /* fsqrtd */ + COSTS_N_INSNS (5), /* imul */ + COSTS_N_INSNS (5), /* imulX */ + 0, /* imul bit factor */ + COSTS_N_INSNS (35), /* idiv */ + COSTS_N_INSNS (35), /* idivX */ + COSTS_N_INSNS (1), /* movcc/movr */ + 0, /* shift penalty */ +}; + +static const struct processor_costs sparclet_costs = { COSTS_N_INSNS (3), /* int load */ COSTS_N_INSNS (3), /* int signed load */ @@ -805,17 +829,31 @@ char sparc_hard_reg_printed[8]; struct gcc_target targetm = TARGET_INITIALIZER; +/* Return the memory reference contained in X if any, zero otherwise. */ + +static rtx +mem_ref (rtx x) +{ + if (GET_CODE (x) == SIGN_EXTEND || GET_CODE (x) == ZERO_EXTEND) + x = XEXP (x, 0); + + if (MEM_P (x)) + return x; + + return NULL_RTX; +} + /* We use a machine specific pass to enable workarounds for errata. We need to have the (essentially) final form of the insn stream in order to properly detect the various hazards. Therefore, this machine specific pass runs as late as possible. The pass is inserted in the pass pipeline - at the end of sparc_options_override. */ + at the end of sparc_option_override. */ static bool sparc_gate_work_around_errata (void) { - /* The only erratum we handle for now is that of the AT697F processor. */ - return sparc_fix_at697f != 0; + /* The only errata we handle are those of the AT697F and UT699. */ + return sparc_fix_at697f != 0 || sparc_fix_ut699 != 0; } static unsigned int @@ -823,14 +861,22 @@ sparc_do_work_around_errata (void) { rtx insn, next; + /* Force all instructions to be split into their final form. */ + split_all_insns_noflow (); + /* Now look for specific patterns in the insn stream. */ for (insn = get_insns (); insn; insn = next) { bool insert_nop = false; rtx set; + /* Look into the instruction in a delay slot. */ + if (NONJUMP_INSN_P (insn) && GET_CODE (PATTERN (insn)) == SEQUENCE) + insn = XVECEXP (PATTERN (insn), 0, 1); + /* Look for a single-word load into an odd-numbered FP register. */ - if (NONJUMP_INSN_P (insn) + if (sparc_fix_at697f + && NONJUMP_INSN_P (insn) && (set = single_set (insn)) != NULL_RTX && GET_MODE_SIZE (GET_MODE (SET_SRC (set))) == 4 && MEM_P (SET_SRC (set)) @@ -845,13 +891,13 @@ sparc_do_work_around_errata (void) /* If the insn has a delay slot, then it cannot be problematic. */ next = next_active_insn (insn); + if (!next) + break; if (NONJUMP_INSN_P (next) && GET_CODE (PATTERN (next)) == SEQUENCE) - code = -1; - else - { - extract_insn (next); - code = INSN_CODE (next); - } + continue; + + extract_insn (next); + code = INSN_CODE (next); switch (code) { @@ -897,12 +943,60 @@ sparc_do_work_around_errata (void) break; } } + + /* Look for a single-word load into an integer register. */ + else if (sparc_fix_ut699 + && NONJUMP_INSN_P (insn) + && (set = single_set (insn)) != NULL_RTX + && GET_MODE_SIZE (GET_MODE (SET_SRC (set))) <= 4 + && mem_ref (SET_SRC (set)) != NULL_RTX + && REG_P (SET_DEST (set)) + && REGNO (SET_DEST (set)) < 32) + { + /* There is no problem if the second memory access has a data + dependency on the first single-cycle load. */ + rtx x = SET_DEST (set); + + /* If the insn has a delay slot, then it cannot be problematic. */ + next = next_active_insn (insn); + if (!next) + break; + if (NONJUMP_INSN_P (next) && GET_CODE (PATTERN (next)) == SEQUENCE) + continue; + + /* Look for a second memory access to/from an integer register. */ + if ((set = single_set (next)) != NULL_RTX) + { + rtx src = SET_SRC (set); + rtx dest = SET_DEST (set); + rtx mem; + + /* LDD is affected. */ + if ((mem = mem_ref (src)) != NULL_RTX + && REG_P (dest) + && REGNO (dest) < 32 + && !reg_mentioned_p (x, XEXP (mem, 0))) + insert_nop = true; + + /* STD is *not* affected. */ + else if ((mem = mem_ref (dest)) != NULL_RTX + && GET_MODE_SIZE (GET_MODE (mem)) <= 4 + && (src == const0_rtx + || (REG_P (src) + && REGNO (src) < 32 + && REGNO (src) != REGNO (x))) + && !reg_mentioned_p (x, XEXP (mem, 0))) + insert_nop = true; + } + } + else next = NEXT_INSN (insn); if (insert_nop) - emit_insn_after (gen_nop (), insn); + emit_insn_before (gen_nop (), next); } + return 0; } @@ -1019,6 +1113,7 @@ sparc_option_override (void) { TARGET_CPU_supersparc, PROCESSOR_SUPERSPARC }, { TARGET_CPU_hypersparc, PROCESSOR_HYPERSPARC }, { TARGET_CPU_leon, PROCESSOR_LEON }, + { TARGET_CPU_leon3, PROCESSOR_LEON3 }, { TARGET_CPU_sparclite, PROCESSOR_F930 }, { TARGET_CPU_sparclite86x, PROCESSOR_SPARCLITE86X }, { TARGET_CPU_sparclet, PROCESSOR_TSC701 }, @@ -1033,7 +1128,7 @@ sparc_option_override (void) }; const struct cpu_default *def; /* Table of values for -m{cpu,tune}=. This must match the order of - the PROCESSOR_* enumeration. */ + the enum processor_type in sparc-opts.h. */ static struct cpu_table { const char *const name; const int disable; @@ -1047,6 +1142,7 @@ sparc_option_override (void) { "hypersparc", MASK_ISA, MASK_V8|MASK_FPU }, /* LEON */ { "leon", MASK_ISA, MASK_V8|MASK_FPU }, + { "leon3", MASK_ISA, MASK_V8|MASK_FPU }, { "sparclite", MASK_ISA, MASK_SPARCLITE }, /* The Fujitsu MB86930 is the original sparclite chip, with no FPU. */ { "f930", MASK_ISA|MASK_FPU, MASK_SPARCLITE }, @@ -1295,6 +1391,9 @@ sparc_option_override (void) case PROCESSOR_LEON: sparc_costs = &leon_costs; break; + case PROCESSOR_LEON3: + sparc_costs = &leon3_costs; + break; case PROCESSOR_SPARCLET: case PROCESSOR_TSC701: sparc_costs = &sparclet_costs; Index: config/sparc/leon.md =================================================================== --- config/sparc/leon.md (revision 201053) +++ config/sparc/leon.md (working copy) @@ -17,40 +17,48 @@ ;; along with GCC; see the file COPYING3. If not see ;; . +;; Leon is a single-issue processor. (define_automaton "leon") -(define_cpu_unit "leon_memory, leon_fpalu" "leon") -(define_cpu_unit "leon_fpmds" "leon") -(define_cpu_unit "write_buf" "leon") +(define_cpu_unit "leon_memory" "leon") (define_insn_reservation "leon_load" 1 - (and (eq_attr "cpu" "leon") - (eq_attr "type" "load,sload,fpload")) + (and (eq_attr "cpu" "leon") (eq_attr "type" "load,sload")) "leon_memory") -(define_insn_reservation "leon_store" 1 - (and (eq_attr "cpu" "leon") - (eq_attr "type" "store,fpstore")) - "leon_memory+write_buf") - -(define_insn_reservation "leon_fp_alu" 1 - (and (eq_attr "cpu" "leon") - (eq_attr "type" "fp,fpmove")) - "leon_fpalu, nothing") - -(define_insn_reservation "leon_fp_mult" 1 - (and (eq_attr "cpu" "leon") - (eq_attr "type" "fpmul")) - "leon_fpmds, nothing") - -(define_insn_reservation "leon_fp_div" 16 - (and (eq_attr "cpu" "leon") - (eq_attr "type" "fpdivs,fpdivd")) - "leon_fpmds, nothing*15") - -(define_insn_reservation "leon_fp_sqrt" 23 - (and (eq_attr "cpu" "leon") - (eq_attr "type" "fpsqrts,fpsqrtd")) - "leon_fpmds, nothing*21") +;; Use a double reservation to work around the load pipeline hazard on UT699. +(define_insn_reservation "leon3_load" 1 + (and (eq_attr "cpu" "leon3") (eq_attr "type" "load,sload")) + "leon_memory*2") +(define_insn_reservation "leon_store" 2 + (and (eq_attr "cpu" "leon,leon3") (eq_attr "type" "store")) + "leon_memory*2") + +;; This describes Gaisler Research's FPU + +(define_automaton "grfpu") + +(define_cpu_unit "grfpu_alu" "grfpu") +(define_cpu_unit "grfpu_ds" "grfpu") + +(define_insn_reservation "leon_fp_alu" 4 + (and (eq_attr "cpu" "leon,leon3") (eq_attr "type" "fp,fpcmp,fpmul")) + "grfpu_alu, nothing*3") + +(define_insn_reservation "leon_fp_divs" 16 + (and (eq_attr "cpu" "leon,leon3") (eq_attr "type" "fpdivs")) + "grfpu_ds*14, nothing*2") + +(define_insn_reservation "leon_fp_divd" 17 + (and (eq_attr "cpu" "leon,leon3") (eq_attr "type" "fpdivd")) + "grfpu_ds*15, nothing*2") + +(define_insn_reservation "leon_fp_sqrts" 24 + (and (eq_attr "cpu" "leon,leon3") (eq_attr "type" "fpsqrts")) + "grfpu_ds*22, nothing*2") + +(define_insn_reservation "leon_fp_sqrtd" 25 + (and (eq_attr "cpu" "leon,leon3") (eq_attr "type" "fpsqrtd")) + "grfpu_ds*23, nothing*2") Index: config/sparc/sparc.h =================================================================== --- config/sparc/sparc.h (revision 201053) +++ config/sparc/sparc.h (working copy) @@ -136,21 +136,22 @@ extern enum cmodel sparc_cmodel; #define TARGET_CPU_supersparc 2 #define TARGET_CPU_hypersparc 3 #define TARGET_CPU_leon 4 -#define TARGET_CPU_sparclite 5 -#define TARGET_CPU_f930 5 /* alias */ -#define TARGET_CPU_f934 5 /* alias */ -#define TARGET_CPU_sparclite86x 6 -#define TARGET_CPU_sparclet 7 -#define TARGET_CPU_tsc701 7 /* alias */ -#define TARGET_CPU_v9 8 /* generic v9 implementation */ -#define TARGET_CPU_sparcv9 8 /* alias */ -#define TARGET_CPU_sparc64 8 /* alias */ -#define TARGET_CPU_ultrasparc 9 -#define TARGET_CPU_ultrasparc3 10 -#define TARGET_CPU_niagara 11 -#define TARGET_CPU_niagara2 12 -#define TARGET_CPU_niagara3 13 -#define TARGET_CPU_niagara4 14 +#define TARGET_CPU_leon3 5 +#define TARGET_CPU_sparclite 6 +#define TARGET_CPU_f930 6 /* alias */ +#define TARGET_CPU_f934 6 /* alias */ +#define TARGET_CPU_sparclite86x 7 +#define TARGET_CPU_sparclet 8 +#define TARGET_CPU_tsc701 8 /* alias */ +#define TARGET_CPU_v9 9 /* generic v9 implementation */ +#define TARGET_CPU_sparcv9 9 /* alias */ +#define TARGET_CPU_sparc64 9 /* alias */ +#define TARGET_CPU_ultrasparc 10 +#define TARGET_CPU_ultrasparc3 11 +#define TARGET_CPU_niagara 12 +#define TARGET_CPU_niagara2 13 +#define TARGET_CPU_niagara3 14 +#define TARGET_CPU_niagara4 15 #if TARGET_CPU_DEFAULT == TARGET_CPU_v9 \ || TARGET_CPU_DEFAULT == TARGET_CPU_ultrasparc \ @@ -232,7 +233,8 @@ extern enum cmodel sparc_cmodel; #define ASM_CPU32_DEFAULT_SPEC "" #endif -#if TARGET_CPU_DEFAULT == TARGET_CPU_leon +#if TARGET_CPU_DEFAULT == TARGET_CPU_leon \ + || TARGET_CPU_DEFAULT == TARGET_CPU_leon3 #define CPP_CPU32_DEFAULT_SPEC "-D__leon__ -D__sparc_v8__" #define ASM_CPU32_DEFAULT_SPEC "" #endif @@ -282,6 +284,7 @@ extern enum cmodel sparc_cmodel; %{mcpu=supersparc:-D__supersparc__ -D__sparc_v8__} \ %{mcpu=hypersparc:-D__hypersparc__ -D__sparc_v8__} \ %{mcpu=leon:-D__leon__ -D__sparc_v8__} \ +%{mcpu=leon3:-D__leon__ -D__sparc_v8__} \ %{mcpu=v9:-D__sparc_v9__} \ %{mcpu=ultrasparc:-D__sparc_v9__} \ %{mcpu=ultrasparc3:-D__sparc_v9__} \ @@ -330,6 +333,7 @@ extern enum cmodel sparc_cmodel; %{mcpu=supersparc:-Av8} \ %{mcpu=hypersparc:-Av8} \ %{mcpu=leon:-Av8} \ +%{mcpu=leon3:-Av8} \ %{mv8plus:-Av8plus} \ %{mcpu=v9:-Av9} \ %{mcpu=ultrasparc:%{!mv8plus:-Av9a}} \