/* `Q' means address register indirect addressing mode.
`S' is for operands that satisfy 'm' when -mpcrel is in effect.
`T' is for operands that satisfy 's' when -mpcrel is not in effect.
- `U' is for register offset addressing. */
+ `U' is for register offset addressing.
+ `W' is for const_call_operands. */
#define EXTRA_CONSTRAINT(OP,CODE) \
- (((CODE) == 'S') \
+ ((CODE) == 'S' \
? (TARGET_PCREL \
&& GET_CODE (OP) == MEM \
&& (GET_CODE (XEXP (OP, 0)) == SYMBOL_REF \
|| GET_CODE (XEXP (OP, 0)) == LABEL_REF \
|| GET_CODE (XEXP (OP, 0)) == CONST)) \
: \
- (((CODE) == 'T') \
+ (CODE) == 'T' \
? ( !TARGET_PCREL \
&& (GET_CODE (OP) == SYMBOL_REF \
|| GET_CODE (OP) == LABEL_REF \
|| GET_CODE (OP) == CONST)) \
: \
- (((CODE) == 'Q') \
+ (CODE) == 'Q' \
? (GET_CODE (OP) == MEM \
&& GET_CODE (XEXP (OP, 0)) == REG) \
: \
- (((CODE) == 'U') \
+ (CODE) == 'U' \
? (GET_CODE (OP) == MEM \
&& GET_CODE (XEXP (OP, 0)) == PLUS \
&& GET_CODE (XEXP (XEXP (OP, 0), 0)) == REG \
&& GET_CODE (XEXP (XEXP (OP, 0), 1)) == CONST_INT) \
: \
- 0))))
+ (CODE) == 'W' \
+ ? const_call_operand (OP, VOIDmode) \
+ : 0)
/* On the m68k, use a data reg if possible when the
value is a constant in the range where moveq could be used
/* Moves between fp regs and other regs are two insns. */
#define REGISTER_MOVE_COST(MODE, CLASS1, CLASS2) \
- (((CLASS1) == FP_REGS && (CLASS2) != FP_REGS) \
- || ((CLASS2) == FP_REGS && (CLASS1) != FP_REGS) \
- ? 4 : 2)
+ ((((CLASS1) == FP_REGS) != ((CLASS2) == FP_REGS)) ? 4 : 2)
\f
/* Stack layout; function entry, exit and calling. */
-#define STACK_GROWS_DOWNWARD
+#define STACK_GROWS_DOWNWARD 1
#define FRAME_GROWS_DOWNWARD 1
#define STARTING_FRAME_OFFSET 0
== void_type_node))) \
? (SIZE) : 0)
-/* On the m68k the return value is always in D0. */
+/* On the m68k the return value defaults to D0. */
#define FUNCTION_VALUE(VALTYPE, FUNC) \
gen_rtx_REG (TYPE_MODE (VALTYPE), 0)
-/* On the m68k the return value is always in D0. */
+/* On the m68k the return value defaults to D0. */
#define LIBCALL_VALUE(MODE) gen_rtx_REG (MODE, 0)
-/* On the m68k, D0 is the only register used. */
+/* On the m68k, D0 is usually the only register used. */
#define FUNCTION_VALUE_REGNO_P(N) ((N) == 0)
/* Define this to be true when FUNCTION_VALUE_REGNO_P is true for
/* Macros to check register numbers against specific register classes. */
-#define REGNO_OK_FOR_INDEX_P(REGNO) \
-((REGNO) < 16 || (unsigned) reg_renumber[REGNO] < 16)
-#define REGNO_OK_FOR_BASE_P(REGNO) \
-(((REGNO) ^ 010) < 8 || (unsigned) (reg_renumber[REGNO] ^ 010) < 8)
-#define REGNO_OK_FOR_DATA_P(REGNO) \
-((REGNO) < 8 || (unsigned) reg_renumber[REGNO] < 8)
-#define REGNO_OK_FOR_FP_P(REGNO) \
-(((REGNO) ^ 020) < 8 || (unsigned) (reg_renumber[REGNO] ^ 020) < 8)
+/* True for data registers, D0 through D7. */
+#define DATA_REGNO_P(REGNO) ((unsigned int) (REGNO) < 8)
+
+/* True for address registers, A0 through A7. */
+#define ADDRESS_REGNO_P(REGNO) (((unsigned int) (REGNO) - 8) < 8)
+
+/* True for integer registers, D0 through D7 and A0 through A7. */
+#define INT_REGNO_P(REGNO) ((unsigned int) (REGNO) < 16)
+
+/* True for floating point registers, FP0 through FP7. */
+#define FP_REGNO_P(REGNO) (((unsigned int) (REGNO) - 16) < 8)
+
+#define REGNO_OK_FOR_INDEX_P(REGNO) \
+ (INT_REGNO_P (REGNO) \
+ || INT_REGNO_P (reg_renumber[REGNO]))
+
+#define REGNO_OK_FOR_BASE_P(REGNO) \
+ (ADDRESS_REGNO_P (REGNO) \
+ || ADDRESS_REGNO_P (reg_renumber[REGNO]))
+
+#define REGNO_OK_FOR_DATA_P(REGNO) \
+ (DATA_REGNO_P (REGNO) \
+ || DATA_REGNO_P (reg_renumber[REGNO]))
+
+#define REGNO_OK_FOR_FP_P(REGNO) \
+ (FP_REGNO_P (REGNO) \
+ || FP_REGNO_P (reg_renumber[REGNO]))
/* Now macros that check whether X is a register and also,
strictly, whether it is in a specified class.
#define LEGITIMATE_PIC_OPERAND_P(X) \
(! symbolic_operand (X, VOIDmode) \
- || (GET_CODE (X) == SYMBOL_REF && SYMBOL_REF_FLAG (X)) \
|| PCREL_GENERAL_OPERAND_OK)
#ifndef REG_OK_STRICT
/* Nonzero if X is a hard reg that can be used as an index
or if it is a pseudo reg. */
-#define REG_OK_FOR_INDEX_P(X) ((REGNO (X) ^ 020) >= 8)
+#define REG_OK_FOR_INDEX_P(X) !FP_REGNO_P (REGNO (X))
/* Nonzero if X is a hard reg that can be used as a base reg
or if it is a pseudo reg. */
-#define REG_OK_FOR_BASE_P(X) ((REGNO (X) & ~027) != 0)
+#define REG_OK_FOR_BASE_P(X) \
+ (!DATA_REGNO_P (REGNO (X)) && !FP_REGNO_P (REGNO (X)))
#else
/* Describe how we implement __builtin_eh_return. */
#define EH_RETURN_DATA_REGNO(N) \
((N) < 2 ? (N) : INVALID_REGNUM)
-#define EH_RETURN_STACKADJ_RTX gen_rtx_REG (Pmode, 8)
+#define EH_RETURN_STACKADJ_RTX gen_rtx_REG (Pmode, A0_REG)
#define EH_RETURN_HANDLER_RTX \
gen_rtx_MEM (Pmode, \
gen_rtx_PLUS (Pmode, arg_pointer_rtx, \
'b' for byte insn (no effect, on the Sun; this is for the ISI).
'd' to force memory addressing to be absolute, not relative.
'f' for float insn (print a CONST_DOUBLE as a float rather than in hex)
- 'o' for operands to go directly to output_operand_address (bypassing
- print_operand_address--used only for SYMBOL_REFs under TARGET_PCREL)
'x' for float insn (print a CONST_DOUBLE as a float rather than in hex),
or print pair of registers as rx:ry. */
extern enum uarch_type m68k_tune;
extern enum fpu_type m68k_fpu;
extern unsigned int m68k_cpu_flags;
+extern const char *m68k_symbolic_call;
+extern const char *m68k_symbolic_jump;