From: Richard Sandiford Date: Sat, 14 Aug 2004 20:55:56 +0000 (+0000) Subject: * config/mips/mips-protos.h (mips_symbolic_constant_p) X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=96a30b18264771ab63790ae9976105745c2cec66;p=gcc.git * config/mips/mips-protos.h (mips_symbolic_constant_p) (mips_atomic_symbolic_constant_p, mips_stack_address_p) (mips_small_data_pattern_p): Declare. * config/mips/mips.h (CONST_GP_P): Moved from mips.c. (PREDICATE_CODES, SPECIAL_MODE_PREDICATES): Delete. * config/mips/mips.c (mips_symbolic_constant_p): Make global. (mips_atomic_symbolic_constant_p, mips_stack_address_p): New functions. (uns_arith_operand, const_arith_operand, arith_operand, sle_operand) (sleu_operand, small_int, reg_or_0_operand, const_float_1_operand) (reg_or_const_float_1_operand, hilo_operand, extend_operator) (macc_msac_operand, equality_op, cmp_op, trap_cmp_op) (pc_or_label_operand, call_insn_operand, move_operand) (consttable_operand, symbolic_operand, general_symbolic_operand) (global_got_operand, local_got_operand, stack_operand) (fp_register_operand, lo_operand, fcc_register_operand): Delete. (mips_small_data_pattern_1): Renamed from small_data_pattern_1. (mips_small_data_pattern_p): Replace previous small_data_pattern predicate. Turn into a bool () (rtx) function. * config/mips/predicates.md: New file. * config/mips/mips.md: Include it. Use the target-independent comparison_operator instead of cmp_op. Rename trap_cmp_op to trap_comparison_operator and equality_op to equality_operator. Replace uses of small_int with the equivalent const_arith_operand. Rename reg_or_const_float_1_operand to reg_or_1_operand. Rename const_float_1_operand to const_1_operand. Rename fcc_register_operand to fcc_reload_operand. * config/mips/sb1.md: Rename fp_register_operand to fpr_operand. From-SVN: r86006 --- diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 35e5623c91b..e2402b3fc51 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,33 @@ +2004-08-14 Richard Sandiford + + * config/mips/mips-protos.h (mips_symbolic_constant_p) + (mips_atomic_symbolic_constant_p, mips_stack_address_p) + (mips_small_data_pattern_p): Declare. + * config/mips/mips.h (CONST_GP_P): Moved from mips.c. + (PREDICATE_CODES, SPECIAL_MODE_PREDICATES): Delete. + * config/mips/mips.c (mips_symbolic_constant_p): Make global. + (mips_atomic_symbolic_constant_p, mips_stack_address_p): New functions. + (uns_arith_operand, const_arith_operand, arith_operand, sle_operand) + (sleu_operand, small_int, reg_or_0_operand, const_float_1_operand) + (reg_or_const_float_1_operand, hilo_operand, extend_operator) + (macc_msac_operand, equality_op, cmp_op, trap_cmp_op) + (pc_or_label_operand, call_insn_operand, move_operand) + (consttable_operand, symbolic_operand, general_symbolic_operand) + (global_got_operand, local_got_operand, stack_operand) + (fp_register_operand, lo_operand, fcc_register_operand): Delete. + (mips_small_data_pattern_1): Renamed from small_data_pattern_1. + (mips_small_data_pattern_p): Replace previous small_data_pattern + predicate. Turn into a bool () (rtx) function. + * config/mips/predicates.md: New file. + * config/mips/mips.md: Include it. Use the target-independent + comparison_operator instead of cmp_op. Rename trap_cmp_op to + trap_comparison_operator and equality_op to equality_operator. + Replace uses of small_int with the equivalent const_arith_operand. + Rename reg_or_const_float_1_operand to reg_or_1_operand. Rename + const_float_1_operand to const_1_operand. Rename fcc_register_operand + to fcc_reload_operand. + * config/mips/sb1.md: Rename fp_register_operand to fpr_operand. + 2004-08-14 John David Anglin PR libstdc++/17005 partial fix. diff --git a/gcc/config/mips/mips-protos.h b/gcc/config/mips/mips-protos.h index f09d704b862..eec42fce72d 100644 --- a/gcc/config/mips/mips-protos.h +++ b/gcc/config/mips/mips-protos.h @@ -88,7 +88,10 @@ enum mips_symbol_type { }; #define NUM_SYMBOL_TYPES (SYMBOL_64_LOW + 1) +extern bool mips_symbolic_constant_p (rtx, enum mips_symbol_type *); +extern bool mips_atomic_symbolic_constant_p (rtx); extern int mips_regno_mode_ok_for_base_p (int, enum machine_mode, int); +extern bool mips_stack_address_p (rtx, enum machine_mode); extern int mips_address_insns (rtx, enum machine_mode); extern int mips_const_insns (rtx); extern int mips_fetch_insns (rtx); @@ -173,6 +176,7 @@ extern void mips_declare_object (FILE *, const char *, const char *, extern void mips_declare_object_name (FILE *, const char *, tree); extern void mips_finish_declare_object (FILE *, tree, int, int); +extern bool mips_small_data_pattern_p (rtx); extern rtx mips_rewrite_small_data (rtx); extern HOST_WIDE_INT compute_frame_size (HOST_WIDE_INT); extern HOST_WIDE_INT mips_initial_elimination_offset (int, int); diff --git a/gcc/config/mips/mips.c b/gcc/config/mips/mips.c index 3fe9d4d24d7..3ded7410176 100644 --- a/gcc/config/mips/mips.c +++ b/gcc/config/mips/mips.c @@ -71,13 +71,6 @@ Boston, MA 02111-1307, USA. */ #define UNSPEC_ADDRESS_TYPE(X) \ ((enum mips_symbol_type) (XINT (X, 1) - UNSPEC_ADDRESS_FIRST)) -/* True if X is (const (unspec [(const_int 0)] UNSPEC_GP)). This is used - to initialize the mips16 gp pseudo register. */ -#define CONST_GP_P(X) \ - (GET_CODE (X) == CONST \ - && GET_CODE (XEXP (X, 0)) == UNSPEC \ - && XINT (XEXP (X, 0), 1) == UNSPEC_GP) - /* The maximum distance between the top of the stack frame and the value $sp has when we save & restore registers. @@ -154,7 +147,6 @@ struct mips_sim; static enum mips_symbol_type mips_classify_symbol (rtx); static void mips_split_const (rtx, rtx *, HOST_WIDE_INT *); static bool mips_offset_within_object_p (rtx, HOST_WIDE_INT); -static bool mips_symbolic_constant_p (rtx, enum mips_symbol_type *); static bool mips_valid_base_register_p (rtx, enum machine_mode, int); static bool mips_symbolic_address_p (enum mips_symbol_type, enum machine_mode); static bool mips_classify_address (struct mips_address_info *, rtx, @@ -192,7 +184,7 @@ static bool mips_assemble_integer (rtx, unsigned int, int); static void mips_file_start (void); static void mips_file_end (void); static bool mips_rewrite_small_data_p (rtx); -static int small_data_pattern_1 (rtx *, void *); +static int mips_small_data_pattern_1 (rtx *, void *); static int mips_rewrite_small_data_1 (rtx *, void *); static bool mips_function_has_gp_insn (void); static unsigned int mips_global_pointer (void); @@ -841,7 +833,7 @@ mips_offset_within_object_p (rtx symbol, HOST_WIDE_INT offset) the same way as a bare symbol. If it is, store the type of the symbol in *SYMBOL_TYPE. */ -static bool +bool mips_symbolic_constant_p (rtx x, enum mips_symbol_type *symbol_type) { HOST_WIDE_INT offset; @@ -906,6 +898,17 @@ mips_symbolic_constant_p (rtx x, enum mips_symbol_type *symbol_type) } +/* Return true if X is a symbolic constant whose value is not split + into separate relocations. */ + +bool +mips_atomic_symbolic_constant_p (rtx x) +{ + enum mips_symbol_type type; + return mips_symbolic_constant_p (x, &type) && !mips_split_p[type]; +} + + /* This function is used to implement REG_MODE_OK_FOR_BASE_P. */ int @@ -1125,6 +1128,17 @@ mips_symbol_insns (enum mips_symbol_type type) abort (); } +/* Return true if X is a legitimate $sp-based address for mode MDOE. */ + +bool +mips_stack_address_p (rtx x, enum machine_mode mode) +{ + struct mips_address_info addr; + + return (mips_classify_address (&addr, x, mode, false) + && addr.type == ADDRESS_REG + && addr.reg == stack_pointer_rtx); +} /* Return true if a value at OFFSET bytes from BASE can be accessed using an unextended mips16 instruction. MODE is the mode of the @@ -1289,377 +1303,7 @@ mips_idiv_insns (void) count++; return count; } - - -/* Return truth value of whether OP can be used as an operands - where a register or 16 bit unsigned integer is needed. */ - -int -uns_arith_operand (rtx op, enum machine_mode mode) -{ - if (GET_CODE (op) == CONST_INT && SMALL_INT_UNSIGNED (op)) - return 1; - - return register_operand (op, mode); -} - - -/* True if OP can be treated as a signed 16-bit constant. */ - -int -const_arith_operand (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED) -{ - return GET_CODE (op) == CONST_INT && SMALL_INT (op); -} - - -/* Return true if OP is a register operand or a signed 16-bit constant. */ - -int -arith_operand (rtx op, enum machine_mode mode) -{ - return const_arith_operand (op, mode) || register_operand (op, mode); -} - -/* Return true if OP can be used as the second argument to an LE operation. */ - -int -sle_operand (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED) -{ - return GET_CODE (op) == CONST_INT && SMALL_OPERAND (INTVAL (op) + 1); -} - -/* Likewise LEU. */ - -int -sleu_operand (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED) -{ - return (GET_CODE (op) == CONST_INT - && INTVAL (op) + 1 != 0 - && SMALL_OPERAND (INTVAL (op) + 1)); -} - -/* Return truth value of whether OP is an integer which fits in 16 bits. */ - -int -small_int (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED) -{ - return (GET_CODE (op) == CONST_INT && SMALL_INT (op)); -} - -/* Return truth value of whether OP is a register or the constant 0. - Do not accept 0 in mips16 mode since $0 is not one of the core 8 - registers. */ - -int -reg_or_0_operand (rtx op, enum machine_mode mode) -{ - switch (GET_CODE (op)) - { - case CONST_INT: - if (TARGET_MIPS16) - return 0; - return INTVAL (op) == 0; - - case CONST_DOUBLE: - if (TARGET_MIPS16) - return 0; - return op == CONST0_RTX (mode); - - default: - return register_operand (op, mode); - } -} - -/* Accept a register or the floating point constant 1 in the - appropriate mode. */ - -int -reg_or_const_float_1_operand (rtx op, enum machine_mode mode) -{ - return const_float_1_operand (op, mode) || register_operand (op, mode); -} - -/* Accept the floating point constant 1 in the appropriate mode. */ - -int -const_float_1_operand (rtx op, enum machine_mode mode) -{ - REAL_VALUE_TYPE d; - - if (GET_CODE (op) != CONST_DOUBLE - || mode != GET_MODE (op) - || (mode != DFmode && mode != SFmode)) - return 0; - - REAL_VALUE_FROM_CONST_DOUBLE (d, op); - - return REAL_VALUES_EQUAL (d, dconst1); -} - -/* Return true if OP is either the HI or LO register. */ - -int -hilo_operand (rtx op, enum machine_mode mode) -{ - return ((mode == VOIDmode || mode == GET_MODE (op)) - && REG_P (op) && MD_REG_P (REGNO (op))); -} - -/* Return true if OP is an extension operator. */ - -int -extend_operator (rtx op, enum machine_mode mode) -{ - return ((mode == VOIDmode || mode == GET_MODE (op)) - && (GET_CODE (op) == ZERO_EXTEND || GET_CODE (op) == SIGN_EXTEND)); -} - -/* Return true if X is the right hand side of a "macc" or "msac" instruction. - This predicate is intended for use in peephole optimizations. */ - -int -macc_msac_operand (rtx x, enum machine_mode mode ATTRIBUTE_UNUSED) -{ - if (ISA_HAS_MACC && GET_CODE (x) == PLUS && REG_P (XEXP (x, 1))) - x = XEXP (x, 0); - else if (ISA_HAS_MSAC && GET_CODE (x) == MINUS && REG_P (XEXP (x, 0))) - x = XEXP (x, 1); - else - return false; - - return GET_CODE (x) == MULT && REG_P (XEXP (x, 0)) && REG_P (XEXP (x, 1)); -} - -/* Return nonzero if the code of this rtx pattern is EQ or NE. */ - -int -equality_op (rtx op, enum machine_mode mode) -{ - if (mode != GET_MODE (op)) - return 0; - - return GET_CODE (op) == EQ || GET_CODE (op) == NE; -} - -/* Return nonzero if the code is a relational operations (EQ, LE, etc.) */ - -int -cmp_op (rtx op, enum machine_mode mode) -{ - if (mode != GET_MODE (op)) - return 0; - - return COMPARISON_P (op); -} - -/* Return nonzero if the code is a relational operation suitable for a - conditional trap instruction (only EQ, NE, LT, LTU, GE, GEU). - We need this in the insn that expands `trap_if' in order to prevent - combine from erroneously altering the condition. */ - -int -trap_cmp_op (rtx op, enum machine_mode mode) -{ - if (mode != GET_MODE (op)) - return 0; - - switch (GET_CODE (op)) - { - case EQ: - case NE: - case LT: - case LTU: - case GE: - case GEU: - return 1; - - default: - return 0; - } -} - -/* Return nonzero if the operand is either the PC or a label_ref. */ - -int -pc_or_label_operand (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED) -{ - if (op == pc_rtx) - return 1; - - if (GET_CODE (op) == LABEL_REF) - return 1; - - return 0; -} - -/* Test for a valid call address. */ - -int -call_insn_operand (rtx op, enum machine_mode mode) -{ - enum mips_symbol_type symbol_type; - - if (mips_symbolic_constant_p (op, &symbol_type)) - switch (symbol_type) - { - case SYMBOL_GENERAL: - /* If -mlong-calls, force all calls to use register addressing. */ - return !TARGET_LONG_CALLS; - - case SYMBOL_GOT_GLOBAL: - /* Without explicit relocs, there is no special syntax for - loading the address of a call destination into a register. - Using "la $25,foo; jal $25" would prevent the lazy binding - of "foo", so keep the address of global symbols with the - jal macro. */ - return !TARGET_EXPLICIT_RELOCS; - - default: - return false; - } - return register_operand (op, mode); -} - - -/* Return nonzero if OP is valid as a source operand for a move - instruction. */ - -int -move_operand (rtx op, enum machine_mode mode) -{ - enum mips_symbol_type symbol_type; - - if (!general_operand (op, mode)) - return false; - - switch (GET_CODE (op)) - { - case CONST_INT: - /* When generating mips16 code, LEGITIMATE_CONSTANT_P rejects - CONST_INTs that can't be loaded using simple insns. */ - if (TARGET_MIPS16) - return true; - - /* When generating 32-bit code, allow DImode move_operands to - match arbitrary constants. We split them after reload. */ - if (!TARGET_64BIT && mode == DImode) - return true; - - /* Otherwise check whether the constant can be loaded in a single - instruction. */ - return LUI_INT (op) || SMALL_INT (op) || SMALL_INT_UNSIGNED (op); - - case CONST: - case SYMBOL_REF: - case LABEL_REF: - if (CONST_GP_P (op)) - return true; - - return (mips_symbolic_constant_p (op, &symbol_type) - && !mips_split_p[symbol_type]); - - default: - return true; - } -} - - -/* Accept any operand that can appear in a mips16 constant table - instruction. We can't use any of the standard operand functions - because for these instructions we accept values that are not - accepted by LEGITIMATE_CONSTANT, such as arbitrary SYMBOL_REFs. */ - -int -consttable_operand (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED) -{ - return CONSTANT_P (op); -} - -/* Return 1 if OP is a symbolic operand, i.e. a symbol_ref or a label_ref, - possibly with an offset. */ - -int -symbolic_operand (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED) -{ - enum mips_symbol_type symbol_type; - - return mips_symbolic_constant_p (op, &symbol_type); -} - - -/* Return true if OP is a symbolic constant of type SYMBOL_GENERAL. */ - -int -general_symbolic_operand (rtx op, enum machine_mode mode) -{ - enum mips_symbol_type symbol_type; - - return ((mode == VOIDmode || mode == GET_MODE (op)) - && mips_symbolic_constant_p (op, &symbol_type) - && symbol_type == SYMBOL_GENERAL); -} - - -/* Return true if we're generating PIC and OP is a global symbol. */ - -int -global_got_operand (rtx op, enum machine_mode mode) -{ - enum mips_symbol_type symbol_type; - - return ((mode == VOIDmode || mode == GET_MODE (op)) - && mips_symbolic_constant_p (op, &symbol_type) - && symbol_type == SYMBOL_GOT_GLOBAL); -} - - -/* Likewise for local symbols. */ - -int -local_got_operand (rtx op, enum machine_mode mode) -{ - enum mips_symbol_type symbol_type; - - return ((mode == VOIDmode || mode == GET_MODE (op)) - && mips_symbolic_constant_p (op, &symbol_type) - && symbol_type == SYMBOL_GOT_LOCAL); -} - - -/* Return true if OP is a memory reference that uses the stack pointer - as a base register. */ - -int -stack_operand (rtx op, enum machine_mode mode) -{ - struct mips_address_info addr; - - return ((mode == VOIDmode || mode == GET_MODE (op)) - && GET_CODE (op) == MEM - && mips_classify_address (&addr, XEXP (op, 0), GET_MODE (op), false) - && addr.type == ADDRESS_REG - && addr.reg == stack_pointer_rtx); -} - -/* Helper function for DFA schedulers. Return true if OP is a floating - point register. */ - -int -fp_register_operand (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED) -{ - return REG_P (op) && FP_REG_P (REGNO (op)); -} - -/* Helper function for DFA schedulers. Return true if OP is a LO reg. */ - -int -lo_operand (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED) -{ - return REG_P (op) && REGNO (op) == LO_REGNUM; -} - /* This function is used to implement GO_IF_LEGITIMATE_ADDRESS. It returns a nonzero value if X is a legitimate address for a memory operand of the indicated MODE. STRICT is nonzero if this function @@ -3070,18 +2714,6 @@ mips_function_ok_for_sibcall (tree decl ATTRIBUTE_UNUSED, return TARGET_SIBCALLS; } -/* Return true if operand OP is a condition code register. - Only for use during or after reload. */ - -int -fcc_register_operand (rtx op, enum machine_mode mode) -{ - return ((mode == VOIDmode || mode == GET_MODE (op)) - && (reload_in_progress || reload_completed) - && (GET_CODE (op) == REG || GET_CODE (op) == SUBREG) - && ST_REG_P (true_regnum (op))); -} - /* Emit code to move general operand SRC into condition-code register DEST. SCRATCH is a scratch TFmode float register. The sequence is: @@ -5741,10 +5373,10 @@ mips_rewrite_small_data_p (rtx x) } -/* A for_each_rtx callback for small_data_pattern. */ +/* A for_each_rtx callback for mips_small_data_pattern_p. */ static int -small_data_pattern_1 (rtx *loc, void *data ATTRIBUTE_UNUSED) +mips_small_data_pattern_1 (rtx *loc, void *data ATTRIBUTE_UNUSED) { if (GET_CODE (*loc) == LO_SUM) return -1; @@ -5755,11 +5387,10 @@ small_data_pattern_1 (rtx *loc, void *data ATTRIBUTE_UNUSED) /* Return true if OP refers to small data symbols directly, not through a LO_SUM. */ -int -small_data_pattern (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED) +bool +mips_small_data_pattern_p (rtx op) { - return (GET_CODE (op) != SEQUENCE - && for_each_rtx (&op, small_data_pattern_1, 0)); + return for_each_rtx (&op, mips_small_data_pattern_1, 0); } /* A for_each_rtx callback, used by mips_rewrite_small_data. */ diff --git a/gcc/config/mips/mips.h b/gcc/config/mips/mips.h index f0f06ada15c..e1e45af477d 100644 --- a/gcc/config/mips/mips.h +++ b/gcc/config/mips/mips.h @@ -1653,6 +1653,13 @@ extern const struct mips_cpu_info *mips_tune_info; #define FP_REG_RTX_P(X) (GET_CODE (X) == REG && FP_REG_P (REGNO (X))) +/* True if X is (const (unspec [(const_int 0)] UNSPEC_GP)). This is used + to initialize the mips16 gp pseudo register. */ +#define CONST_GP_P(X) \ + (GET_CODE (X) == CONST \ + && GET_CODE (XEXP (X, 0)) == UNSPEC \ + && XINT (XEXP (X, 0), 1) == UNSPEC_GP) + /* Return coprocessor number from register number. */ #define COPNUM_AS_CHAR_FROM_REGNUM(REGNO) \ @@ -2693,67 +2700,6 @@ typedef struct mips_args { be updated with the correct length of the insn. */ #define ADJUST_INSN_LENGTH(INSN, LENGTH) \ ((LENGTH) = mips_adjust_insn_length ((INSN), (LENGTH))) - - -/* Optionally define this if you have added predicates to - `MACHINE.c'. This macro is called within an initializer of an - array of structures. The first field in the structure is the - name of a predicate and the second field is an array of rtl - codes. For each predicate, list all rtl codes that can be in - expressions matched by the predicate. The list should have a - trailing comma. Here is an example of two entries in the list - for a typical RISC machine: - - #define PREDICATE_CODES \ - {"gen_reg_rtx_operand", {SUBREG, REG}}, \ - {"reg_or_short_cint_operand", {SUBREG, REG, CONST_INT}}, - - Defining this macro does not affect the generated code (however, - incorrect definitions that omit an rtl code that may be matched - by the predicate can cause the compiler to malfunction). - Instead, it allows the table built by `genrecog' to be more - compact and efficient, thus speeding up the compiler. The most - important predicates to include in the list specified by this - macro are thoses used in the most insn patterns. */ - -#define PREDICATE_CODES \ - {"uns_arith_operand", { REG, CONST_INT, SUBREG }}, \ - {"symbolic_operand", { CONST, SYMBOL_REF, LABEL_REF }}, \ - {"general_symbolic_operand", { CONST, SYMBOL_REF, LABEL_REF }}, \ - {"global_got_operand", { CONST, SYMBOL_REF, LABEL_REF }}, \ - {"local_got_operand", { CONST, SYMBOL_REF, LABEL_REF }}, \ - {"const_arith_operand", { CONST_INT }}, \ - {"small_data_pattern", { SET, PARALLEL, UNSPEC, \ - UNSPEC_VOLATILE }}, \ - {"arith_operand", { REG, CONST_INT, CONST, SUBREG }}, \ - {"reg_or_0_operand", { REG, CONST_INT, CONST_DOUBLE, SUBREG }}, \ - {"sle_operand", { CONST_INT }}, \ - {"sleu_operand", { CONST_INT }}, \ - {"small_int", { CONST_INT }}, \ - {"const_float_1_operand", { CONST_DOUBLE }}, \ - {"reg_or_const_float_1_operand", { CONST_DOUBLE, REG}}, \ - {"equality_op", { EQ, NE }}, \ - {"cmp_op", { EQ, NE, GT, GE, GTU, GEU, LT, LE, \ - LTU, LEU }}, \ - {"trap_cmp_op", { EQ, NE, GE, GEU, LT, LTU }}, \ - {"pc_or_label_operand", { PC, LABEL_REF }}, \ - {"call_insn_operand", { CONST, SYMBOL_REF, LABEL_REF, REG }}, \ - {"move_operand", { CONST_INT, CONST_DOUBLE, CONST, \ - SYMBOL_REF, LABEL_REF, SUBREG, \ - REG, MEM}}, \ - {"stack_operand", { MEM }}, \ - {"consttable_operand", { LABEL_REF, SYMBOL_REF, CONST_INT, \ - CONST_DOUBLE, CONST }}, \ - {"fcc_register_operand", { REG, SUBREG }}, \ - {"hilo_operand", { REG }}, \ - {"macc_msac_operand", { PLUS, MINUS }}, \ - {"extend_operator", { ZERO_EXTEND, SIGN_EXTEND }}, - -/* A list of predicates that do special things with modes, and so - should not elicit warnings for VOIDmode match_operand. */ - -#define SPECIAL_MODE_PREDICATES \ - "pc_or_label_operand", /* Control the assembler format that we output. */ diff --git a/gcc/config/mips/mips.md b/gcc/config/mips/mips.md index ac4c4b9473e..38b38de90c3 100644 --- a/gcc/config/mips/mips.md +++ b/gcc/config/mips/mips.md @@ -53,6 +53,8 @@ (UNSPEC_ADDRESS_FIRST 100) (FAKE_CALL_REGNO 79)]) + +(include "predicates.md") ;; .................... ;; @@ -364,7 +366,7 @@ [(set_attr "type" "trap")]) (define_expand "conditional_trap" - [(trap_if (match_operator 0 "cmp_op" + [(trap_if (match_operator 0 "comparison_operator" [(match_dup 2) (match_dup 3)]) (match_operand 1 "const_int_operand"))] "ISA_HAS_COND_TRAP" @@ -379,7 +381,7 @@ }) (define_insn "" - [(trap_if (match_operator 0 "trap_cmp_op" + [(trap_if (match_operator 0 "trap_comparison_operator" [(match_operand:SI 1 "reg_or_0_operand" "dJ") (match_operand:SI 2 "arith_operand" "dI")]) (const_int 0))] @@ -388,7 +390,7 @@ [(set_attr "type" "trap")]) (define_insn "" - [(trap_if (match_operator 0 "trap_cmp_op" + [(trap_if (match_operator 0 "trap_comparison_operator" [(match_operand:DI 1 "reg_or_0_operand" "dJ") (match_operand:DI 2 "arith_operand" "dI")]) (const_int 0))] @@ -446,7 +448,7 @@ (define_insn "" [(set (reg:SI 29) (plus:SI (reg:SI 29) - (match_operand:SI 0 "small_int" "I")))] + (match_operand:SI 0 "const_arith_operand" "")))] "TARGET_MIPS16" "addu\t%$,%$,%0" [(set_attr "type" "arith") @@ -458,7 +460,7 @@ (define_insn "" [(set (match_operand:SI 0 "register_operand" "=d") (plus:SI (reg:SI 29) - (match_operand:SI 1 "small_int" "I")))] + (match_operand:SI 1 "const_arith_operand" "")))] "TARGET_MIPS16" "addu\t%0,%$,%1" [(set_attr "type" "arith") @@ -581,7 +583,7 @@ (define_insn "" [(set (reg:DI 29) (plus:DI (reg:DI 29) - (match_operand:DI 0 "small_int" "I")))] + (match_operand:DI 0 "const_arith_operand" "")))] "TARGET_MIPS16 && TARGET_64BIT" "daddu\t%$,%$,%0" [(set_attr "type" "arith") @@ -593,7 +595,7 @@ (define_insn "" [(set (match_operand:DI 0 "register_operand" "=d") (plus:DI (reg:DI 29) - (match_operand:DI 1 "small_int" "I")))] + (match_operand:DI 1 "const_arith_operand" "")))] "TARGET_MIPS16 && TARGET_64BIT" "daddu\t%0,%$,%1" [(set_attr "type" "arith") @@ -1947,11 +1949,11 @@ (define_expand "divdf3" [(set (match_operand:DF 0 "register_operand") - (div:DF (match_operand:DF 1 "reg_or_const_float_1_operand") + (div:DF (match_operand:DF 1 "reg_or_1_operand") (match_operand:DF 2 "register_operand")))] "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT" { - if (const_float_1_operand (operands[1], DFmode)) + if (const_1_operand (operands[1], DFmode)) if (!(ISA_HAS_FP4 && flag_unsafe_math_optimizations)) operands[1] = force_reg (DFmode, operands[1]); }) @@ -1997,11 +1999,11 @@ ;; precision is OK (i.e., flag_unsafe_math_optimizations is set). (define_expand "divsf3" [(set (match_operand:SF 0 "register_operand") - (div:SF (match_operand:SF 1 "reg_or_const_float_1_operand") + (div:SF (match_operand:SF 1 "reg_or_1_operand") (match_operand:SF 2 "register_operand")))] "TARGET_HARD_FLOAT && (!TARGET_FIX_SB1 || flag_unsafe_math_optimizations)" { - if (const_float_1_operand (operands[1], SFmode)) + if (const_1_operand (operands[1], SFmode)) if (!(ISA_HAS_FP4 && flag_unsafe_math_optimizations)) operands[1] = force_reg (SFmode, operands[1]); }) @@ -2033,7 +2035,7 @@ ;; "divdf3" comment for details). (define_insn "" [(set (match_operand:DF 0 "register_operand" "=f") - (div:DF (match_operand:DF 1 "const_float_1_operand" "") + (div:DF (match_operand:DF 1 "const_1_operand" "") (match_operand:DF 2 "register_operand" "f")))] "ISA_HAS_FP4 && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && flag_unsafe_math_optimizations" { @@ -2053,7 +2055,7 @@ ;; "divdf3" comment for details). (define_insn "" [(set (match_operand:SF 0 "register_operand" "=f") - (div:SF (match_operand:SF 1 "const_float_1_operand" "") + (div:SF (match_operand:SF 1 "const_1_operand" "") (match_operand:SF 2 "register_operand" "f")))] "ISA_HAS_FP4 && TARGET_HARD_FLOAT && flag_unsafe_math_optimizations" { @@ -2168,7 +2170,7 @@ ;; "divdf3" comment for details). (define_insn "" [(set (match_operand:DF 0 "register_operand" "=f") - (div:DF (match_operand:DF 1 "const_float_1_operand" "") + (div:DF (match_operand:DF 1 "const_1_operand" "") (sqrt:DF (match_operand:DF 2 "register_operand" "f"))))] "ISA_HAS_FP4 && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && flag_unsafe_math_optimizations" { @@ -2188,7 +2190,7 @@ ;; "divdf3" comment for details). (define_insn "" [(set (match_operand:SF 0 "register_operand" "=f") - (div:SF (match_operand:SF 1 "const_float_1_operand" "") + (div:SF (match_operand:SF 1 "const_1_operand" "") (sqrt:SF (match_operand:SF 2 "register_operand" "f"))))] "ISA_HAS_FP4 && TARGET_HARD_FLOAT && flag_unsafe_math_optimizations" { @@ -2208,7 +2210,7 @@ ;; "divdf3" comment for details). (define_insn "" [(set (match_operand:DF 0 "register_operand" "=f") - (sqrt:DF (div:DF (match_operand:DF 1 "const_float_1_operand" "") + (sqrt:DF (div:DF (match_operand:DF 1 "const_1_operand" "") (match_operand:DF 2 "register_operand" "f"))))] "ISA_HAS_FP4 && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && flag_unsafe_math_optimizations" { @@ -2228,7 +2230,7 @@ ;; "divdf3" comment for details). (define_insn "" [(set (match_operand:SF 0 "register_operand" "=f") - (sqrt:SF (div:SF (match_operand:SF 1 "const_float_1_operand" "") + (sqrt:SF (div:SF (match_operand:SF 1 "const_1_operand" "") (match_operand:SF 2 "register_operand" "f"))))] "ISA_HAS_FP4 && TARGET_HARD_FLOAT && flag_unsafe_math_optimizations" { @@ -2783,8 +2785,9 @@ dsrl\t%3,%3,1\n\ (define_insn "" [(set (match_operand:SI 0 "register_operand" "=d") - (truncate:SI (ashiftrt:DI (match_operand:DI 1 "register_operand" "d") - (match_operand:DI 2 "small_int" "I"))))] + (truncate:SI + (ashiftrt:DI (match_operand:DI 1 "register_operand" "d") + (match_operand:DI 2 "const_arith_operand" ""))))] "TARGET_64BIT && !TARGET_MIPS16 && INTVAL (operands[2]) >= 32" "dsra\t%0,%1,%2" [(set_attr "type" "shift") @@ -4285,7 +4288,7 @@ dsrl\t%3,%3,1\n\ ;; into a GPR takes a single movcc, moving elsewhere takes ;; two. We can leave these cases to the generic reload code. (define_expand "reload_incc" - [(set (match_operand:CC 0 "fcc_register_operand" "=z") + [(set (match_operand:CC 0 "fcc_reload_operand" "=z") (match_operand:CC 1 "general_operand" "")) (clobber (match_operand:TF 2 "register_operand" "=&f"))] "ISA_HAS_8CC && TARGET_HARD_FLOAT" @@ -4295,7 +4298,7 @@ dsrl\t%3,%3,1\n\ }) (define_expand "reload_outcc" - [(set (match_operand:CC 0 "fcc_register_operand" "=z") + [(set (match_operand:CC 0 "fcc_reload_operand" "=z") (match_operand:CC 1 "register_operand" "")) (clobber (match_operand:TF 2 "register_operand" "=&f"))] "ISA_HAS_8CC && TARGET_HARD_FLOAT" @@ -5497,7 +5500,7 @@ dsrl\t%3,%3,1\n\ (define_insn "branch_fp" [(set (pc) (if_then_else - (match_operator:CC 0 "cmp_op" + (match_operator:CC 0 "comparison_operator" [(match_operand:CC 2 "register_operand" "z") (const_int 0)]) (label_ref (match_operand 1 "" "")) @@ -5517,7 +5520,7 @@ dsrl\t%3,%3,1\n\ (define_insn "branch_fp_inverted" [(set (pc) (if_then_else - (match_operator:CC 0 "cmp_op" + (match_operator:CC 0 "comparison_operator" [(match_operand:CC 2 "register_operand" "z") (const_int 0)]) (pc) @@ -5539,7 +5542,7 @@ dsrl\t%3,%3,1\n\ (define_insn "branch_zero" [(set (pc) (if_then_else - (match_operator:SI 0 "cmp_op" + (match_operator:SI 0 "comparison_operator" [(match_operand:SI 2 "register_operand" "d") (const_int 0)]) (label_ref (match_operand 1 "" "")) @@ -5559,7 +5562,7 @@ dsrl\t%3,%3,1\n\ (define_insn "branch_zero_inverted" [(set (pc) (if_then_else - (match_operator:SI 0 "cmp_op" + (match_operator:SI 0 "comparison_operator" [(match_operand:SI 2 "register_operand" "d") (const_int 0)]) (pc) @@ -5579,7 +5582,7 @@ dsrl\t%3,%3,1\n\ (define_insn "branch_zero_di" [(set (pc) (if_then_else - (match_operator:DI 0 "cmp_op" + (match_operator:DI 0 "comparison_operator" [(match_operand:DI 2 "register_operand" "d") (const_int 0)]) (label_ref (match_operand 1 "" "")) @@ -5599,7 +5602,7 @@ dsrl\t%3,%3,1\n\ (define_insn "branch_zero_di_inverted" [(set (pc) (if_then_else - (match_operator:DI 0 "cmp_op" + (match_operator:DI 0 "comparison_operator" [(match_operand:DI 2 "register_operand" "d") (const_int 0)]) (pc) @@ -5621,7 +5624,7 @@ dsrl\t%3,%3,1\n\ (define_insn "branch_equality" [(set (pc) (if_then_else - (match_operator:SI 0 "equality_op" + (match_operator:SI 0 "equality_operator" [(match_operand:SI 2 "register_operand" "d") (match_operand:SI 3 "register_operand" "d")]) (label_ref (match_operand 1 "" "")) @@ -5641,7 +5644,7 @@ dsrl\t%3,%3,1\n\ (define_insn "branch_equality_di" [(set (pc) (if_then_else - (match_operator:DI 0 "equality_op" + (match_operator:DI 0 "equality_operator" [(match_operand:DI 2 "register_operand" "d") (match_operand:DI 3 "register_operand" "d")]) (label_ref (match_operand 1 "" "")) @@ -5661,7 +5664,7 @@ dsrl\t%3,%3,1\n\ (define_insn "branch_equality_inverted" [(set (pc) (if_then_else - (match_operator:SI 0 "equality_op" + (match_operator:SI 0 "equality_operator" [(match_operand:SI 2 "register_operand" "d") (match_operand:SI 3 "register_operand" "d")]) (pc) @@ -5681,7 +5684,7 @@ dsrl\t%3,%3,1\n\ (define_insn "branch_equality_di_inverted" [(set (pc) (if_then_else - (match_operator:DI 0 "equality_op" + (match_operator:DI 0 "equality_operator" [(match_operand:DI 2 "register_operand" "d") (match_operand:DI 3 "register_operand" "d")]) (pc) @@ -5702,9 +5705,10 @@ dsrl\t%3,%3,1\n\ (define_insn "" [(set (pc) - (if_then_else (match_operator:SI 0 "equality_op" - [(match_operand:SI 1 "register_operand" "d,t") - (const_int 0)]) + (if_then_else + (match_operator:SI 0 "equality_operator" + [(match_operand:SI 1 "register_operand" "d,t") + (const_int 0)]) (match_operand 2 "pc_or_label_operand" "") (match_operand 3 "pc_or_label_operand" "")))] "TARGET_MIPS16" @@ -5730,9 +5734,10 @@ dsrl\t%3,%3,1\n\ (define_insn "" [(set (pc) - (if_then_else (match_operator:DI 0 "equality_op" - [(match_operand:DI 1 "register_operand" "d,t") - (const_int 0)]) + (if_then_else + (match_operator:DI 0 "equality_operator" + [(match_operand:DI 1 "register_operand" "d,t") + (const_int 0)]) (match_operand 2 "pc_or_label_operand" "") (match_operand 3 "pc_or_label_operand" "")))] "TARGET_MIPS16" @@ -7305,7 +7310,7 @@ dsrl\t%3,%3,1\n\ (define_insn "" [(set (match_operand:SI 0 "register_operand" "=d,d") (if_then_else:SI - (match_operator 4 "equality_op" + (match_operator 4 "equality_operator" [(match_operand:SI 1 "register_operand" "d,d") (const_int 0)]) (match_operand:SI 2 "reg_or_0_operand" "dJ,0") @@ -7320,7 +7325,7 @@ dsrl\t%3,%3,1\n\ (define_insn "" [(set (match_operand:SI 0 "register_operand" "=d,d") (if_then_else:SI - (match_operator 4 "equality_op" + (match_operator 4 "equality_operator" [(match_operand:DI 1 "register_operand" "d,d") (const_int 0)]) (match_operand:SI 2 "reg_or_0_operand" "dJ,0") @@ -7335,10 +7340,9 @@ dsrl\t%3,%3,1\n\ (define_insn "" [(set (match_operand:SI 0 "register_operand" "=d,d") (if_then_else:SI - (match_operator 3 "equality_op" [(match_operand:CC 4 - "register_operand" - "z,z") - (const_int 0)]) + (match_operator 3 "equality_operator" + [(match_operand:CC 4 "register_operand" "z,z") + (const_int 0)]) (match_operand:SI 1 "reg_or_0_operand" "dJ,0") (match_operand:SI 2 "reg_or_0_operand" "0,dJ")))] "ISA_HAS_CONDMOVE && TARGET_HARD_FLOAT" @@ -7351,7 +7355,7 @@ dsrl\t%3,%3,1\n\ (define_insn "" [(set (match_operand:DI 0 "register_operand" "=d,d") (if_then_else:DI - (match_operator 4 "equality_op" + (match_operator 4 "equality_operator" [(match_operand:SI 1 "register_operand" "d,d") (const_int 0)]) (match_operand:DI 2 "reg_or_0_operand" "dJ,0") @@ -7366,7 +7370,7 @@ dsrl\t%3,%3,1\n\ (define_insn "" [(set (match_operand:DI 0 "register_operand" "=d,d") (if_then_else:DI - (match_operator 4 "equality_op" + (match_operator 4 "equality_operator" [(match_operand:DI 1 "register_operand" "d,d") (const_int 0)]) (match_operand:DI 2 "reg_or_0_operand" "dJ,0") @@ -7381,10 +7385,9 @@ dsrl\t%3,%3,1\n\ (define_insn "" [(set (match_operand:DI 0 "register_operand" "=d,d") (if_then_else:DI - (match_operator 3 "equality_op" [(match_operand:CC 4 - "register_operand" - "z,z") - (const_int 0)]) + (match_operator 3 "equality_operator" + [(match_operand:CC 4 "register_operand" "z,z") + (const_int 0)]) (match_operand:DI 1 "reg_or_0_operand" "dJ,0") (match_operand:DI 2 "reg_or_0_operand" "0,dJ")))] "ISA_HAS_CONDMOVE && TARGET_HARD_FLOAT && TARGET_64BIT" @@ -7397,7 +7400,7 @@ dsrl\t%3,%3,1\n\ (define_insn "" [(set (match_operand:SF 0 "register_operand" "=f,f") (if_then_else:SF - (match_operator 4 "equality_op" + (match_operator 4 "equality_operator" [(match_operand:SI 1 "register_operand" "d,d") (const_int 0)]) (match_operand:SF 2 "register_operand" "f,0") @@ -7412,7 +7415,7 @@ dsrl\t%3,%3,1\n\ (define_insn "" [(set (match_operand:SF 0 "register_operand" "=f,f") (if_then_else:SF - (match_operator 4 "equality_op" + (match_operator 4 "equality_operator" [(match_operand:DI 1 "register_operand" "d,d") (const_int 0)]) (match_operand:SF 2 "register_operand" "f,0") @@ -7427,10 +7430,9 @@ dsrl\t%3,%3,1\n\ (define_insn "" [(set (match_operand:SF 0 "register_operand" "=f,f") (if_then_else:SF - (match_operator 3 "equality_op" [(match_operand:CC 4 - "register_operand" - "z,z") - (const_int 0)]) + (match_operator 3 "equality_operator" + [(match_operand:CC 4 "register_operand" "z,z") + (const_int 0)]) (match_operand:SF 1 "register_operand" "f,0") (match_operand:SF 2 "register_operand" "0,f")))] "ISA_HAS_CONDMOVE && TARGET_HARD_FLOAT" @@ -7443,7 +7445,7 @@ dsrl\t%3,%3,1\n\ (define_insn "" [(set (match_operand:DF 0 "register_operand" "=f,f") (if_then_else:DF - (match_operator 4 "equality_op" + (match_operator 4 "equality_operator" [(match_operand:SI 1 "register_operand" "d,d") (const_int 0)]) (match_operand:DF 2 "register_operand" "f,0") @@ -7458,7 +7460,7 @@ dsrl\t%3,%3,1\n\ (define_insn "" [(set (match_operand:DF 0 "register_operand" "=f,f") (if_then_else:DF - (match_operator 4 "equality_op" + (match_operator 4 "equality_operator" [(match_operand:DI 1 "register_operand" "d,d") (const_int 0)]) (match_operand:DF 2 "register_operand" "f,0") @@ -7473,10 +7475,9 @@ dsrl\t%3,%3,1\n\ (define_insn "" [(set (match_operand:DF 0 "register_operand" "=f,f") (if_then_else:DF - (match_operator 3 "equality_op" [(match_operand:CC 4 - "register_operand" - "z,z") - (const_int 0)]) + (match_operator 3 "equality_operator" + [(match_operand:CC 4 "register_operand" "z,z") + (const_int 0)]) (match_operand:DF 1 "register_operand" "f,0") (match_operand:DF 2 "register_operand" "0,f")))] "ISA_HAS_CONDMOVE && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT" diff --git a/gcc/config/mips/predicates.md b/gcc/config/mips/predicates.md new file mode 100644 index 00000000000..dfc68875205 --- /dev/null +++ b/gcc/config/mips/predicates.md @@ -0,0 +1,202 @@ +;; Predicate definitions for MIPS. +;; Copyright (C) 2004 Free Software Foundation, Inc. +;; +;; This file is part of GCC. +;; +;; GCC is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation; either version 2, or (at your option) +;; any later version. +;; +;; GCC is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. +;; +;; You should have received a copy of the GNU General Public License +;; along with GCC; see the file COPYING. If not, write to +;; the Free Software Foundation, 59 Temple Place - Suite 330, +;; Boston, MA 02111-1307, USA. + +(define_predicate "const_uns_arith_operand" + (and (match_code "const_int") + (match_test "SMALL_OPERAND_UNSIGNED (INTVAL (op))"))) + +(define_predicate "uns_arith_operand" + (ior (match_operand 0 "const_uns_arith_operand") + (match_operand 0 "register_operand"))) + +(define_predicate "const_arith_operand" + (and (match_code "const_int") + (match_test "SMALL_OPERAND (INTVAL (op))"))) + +(define_predicate "arith_operand" + (ior (match_operand 0 "const_arith_operand") + (match_operand 0 "register_operand"))) + +(define_predicate "sle_operand" + (and (match_code "const_int") + (match_test "SMALL_OPERAND (INTVAL (op) + 1)"))) + +(define_predicate "sleu_operand" + (and (match_operand 0 "sle_operand") + (match_test "INTVAL (op) + 1 != 0"))) + +(define_predicate "const_0_operand" + (and (match_code "const_int,const_double") + (match_test "op == CONST0_RTX (GET_MODE (op))"))) + +(define_predicate "reg_or_0_operand" + (ior (and (match_operand 0 "const_0_operand") + (match_test "!TARGET_MIPS16")) + (match_operand 0 "register_operand"))) + +(define_predicate "const_1_operand" + (and (match_code "const_int,const_double") + (match_test "op == CONST1_RTX (GET_MODE (op))"))) + +(define_predicate "reg_or_1_operand" + (ior (match_operand 0 "const_1_operand") + (match_operand 0 "register_operand"))) + +(define_predicate "fpr_operand" + (and (match_code "reg") + (match_test "FP_REG_P (REGNO (op))"))) + +(define_predicate "hilo_operand" + (and (match_code "reg") + (match_test "MD_REG_P (REGNO (op))"))) + +(define_predicate "lo_operand" + (and (match_code "reg") + (match_test "REGNO (op) == LO_REGNUM"))) + +(define_predicate "fcc_reload_operand" + (and (match_code "reg,subreg") + (match_test "ST_REG_P (true_regnum (op))"))) + +(define_special_predicate "pc_or_label_operand" + (match_code "pc,label_ref")) + +(define_predicate "const_call_insn_operand" + (match_code "const,symbol_ref,label_ref") +{ + enum mips_symbol_type symbol_type; + + if (!mips_symbolic_constant_p (op, &symbol_type)) + return false; + + switch (symbol_type) + { + case SYMBOL_GENERAL: + /* If -mlong-calls, force all calls to use register addressing. */ + return !TARGET_LONG_CALLS; + + case SYMBOL_GOT_GLOBAL: + /* Without explicit relocs, there is no special syntax for + loading the address of a call destination into a register. + Using "la $25,foo; jal $25" would prevent the lazy binding + of "foo", so keep the address of global symbols with the + jal macro. */ + return !TARGET_EXPLICIT_RELOCS; + + default: + return false; + } +}) + +(define_predicate "call_insn_operand" + (ior (match_operand 0 "const_call_insn_operand") + (match_operand 0 "register_operand"))) + +(define_predicate "move_operand" + (match_operand 0 "general_operand") +{ + switch (GET_CODE (op)) + { + case CONST_INT: + /* When generating mips16 code, LEGITIMATE_CONSTANT_P rejects + CONST_INTs that can't be loaded using simple insns. */ + if (TARGET_MIPS16) + return true; + + /* When generating 32-bit code, allow DImode move_operands to + match arbitrary constants. We split them after reload. */ + if (!TARGET_64BIT && mode == DImode) + return true; + + /* Otherwise check whether the constant can be loaded in a single + instruction. */ + return LUI_INT (op) || SMALL_INT (op) || SMALL_INT_UNSIGNED (op); + + case CONST: + case SYMBOL_REF: + case LABEL_REF: + return CONST_GP_P (op) || mips_atomic_symbolic_constant_p (op); + + default: + return true; + } +}) + +(define_predicate "consttable_operand" + (match_test "CONSTANT_P (op)")) + +(define_predicate "symbolic_operand" + (match_code "const,symbol_ref,label_ref") +{ + enum mips_symbol_type type; + return mips_symbolic_constant_p (op, &type); +}) + +(define_predicate "general_symbolic_operand" + (match_code "const,symbol_ref,label_ref") +{ + enum mips_symbol_type type; + return mips_symbolic_constant_p (op, &type) && type == SYMBOL_GENERAL; +}) + +(define_predicate "global_got_operand" + (match_code "const,symbol_ref,label_ref") +{ + enum mips_symbol_type type; + return mips_symbolic_constant_p (op, &type) && type == SYMBOL_GOT_GLOBAL; +}) + +(define_predicate "local_got_operand" + (match_code "const,symbol_ref,label_ref") +{ + enum mips_symbol_type type; + return mips_symbolic_constant_p (op, &type) && type == SYMBOL_GOT_LOCAL; +}) + +(define_predicate "stack_operand" + (and (match_code "mem") + (match_test "mips_stack_address_p (XEXP (op, 0), GET_MODE (op))"))) + +(define_predicate "macc_msac_operand" + (ior (and (match_code "plus") (match_test "ISA_HAS_MACC")) + (and (match_code "minus") (match_test "ISA_HAS_MSAC"))) +{ + rtx mult = XEXP (op, GET_CODE (op) == PLUS ? 0 : 1); + rtx accum = XEXP (op, GET_CODE (op) == PLUS ? 1 : 0); + return (GET_CODE (mult) == MULT + && REG_P (XEXP (mult, 0)) + && REG_P (XEXP (mult, 1)) + && REG_P (accum)); +}) + + +(define_predicate "equality_operator" + (match_code "eq,ne")) + +(define_predicate "extend_operator" + (match_code "zero_extend,sign_extend")) + +(define_predicate "trap_comparison_operator" + (match_code "eq,ne,lt,ltu,ge,geu")) + + +(define_predicate "small_data_pattern" + (and (match_code "set,parallel,unspec,unspec_volatile") + (match_test "mips_small_data_pattern_p (op)"))) diff --git a/gcc/config/mips/sb1.md b/gcc/config/mips/sb1.md index de5f168e387..620de13d62e 100644 --- a/gcc/config/mips/sb1.md +++ b/gcc/config/mips/sb1.md @@ -390,7 +390,7 @@ (define_insn_reservation "ir_sb1_mtxfer" 5 (and (eq_attr "cpu" "sb1") (and (eq_attr "type" "xfer") - (match_operand 0 "fp_register_operand"))) + (match_operand 0 "fpr_operand"))) "sb1_fp0") ;; mfc1 latency 1 cycle. @@ -398,7 +398,7 @@ (define_insn_reservation "ir_sb1_mfxfer" 1 (and (eq_attr "cpu" "sb1") (and (eq_attr "type" "xfer") - (not (match_operand 0 "fp_register_operand")))) + (not (match_operand 0 "fpr_operand")))) "sb1_fp0") ;; ??? Can deliver at most 1 result per every 6 cycles because of issue