predicates.md (mcore_general_movesrc_operand): Accept CONSTs.
* config/mcore/predicates.md (mcore_general_movesrc_operand): Accept CONSTs. (mcore_general_movdst_operand): Do not accept CONST_INTs. (mcore_arith_K_S_operand): Run the test for the S constraint not the test for the M constraint. (mcore_addsub_operand): Do not accept integer values that are larger than 32 bits. * config/mcore/mcore.md: Remove unused constraints from split. (andsi3): Use HOST_WIDE_INT instead of int to hold an INTVAL. (addsi3): Likewise. (allocate_stack): Likewise. * config/mcore/mcore.c (mcore_print_operand): Restrict output of P operands to 32 bits. (mcore_const_costs): Use HOST_WIDE_INT instead of int to hold an INTVAL. (mcore_and_cost, mcore_modify_comparison, const_ok_for_mcore, mcore_const_ok_for_inline, mcore_const_trick_uses_not, try_constant_tricks, mcore_num_ones, mcore_num_zeros, mcore_output_bclri, mcore_output_andn, output_inline_const, mcore_output_move, mcore_output_movedouble): Likewise. (mcore_output_cmov): Use CONST_OK_FOR_M and CONST_OK_FOR_N. (output_inline_const): Likewise. (output_inline_const): Fix format strings used in sprintf statements. * config/mcore/mcore-protos.h: Update prototypes for changed functions in mcore.c. * config/mcore/mcore.h (CONST_OK_FOR_I): Cast values to HOST_WIDE_INT and not int. (CONST_OK_FOR_J, CONST_OK_FOR_K, CONST_OK_FOR_L, CONST_OK_FOR_M, CONST_OK_FOR_N): Likewise. (LEGITIMATE_CONSTANT_P): Also check CONSTANT_P. (GO_IF_LEGITIMATE_INDEX): Use HOST_WIDE_INT instead of int to hold an INTVAL. From-SVN: r120669
This commit is contained in:
parent
4d499824ed
commit
6e3a343d88
@ -1,3 +1,39 @@
|
||||
2007-01-11 Nick Clifton <nickc@redhat.com>
|
||||
|
||||
* config/mcore/predicates.md (mcore_general_movesrc_operand):
|
||||
Accept CONSTs.
|
||||
(mcore_general_movdst_operand): Do not accept CONST_INTs.
|
||||
(mcore_arith_K_S_operand): Run the test for the S constraint not
|
||||
the test for the M constraint.
|
||||
(mcore_addsub_operand): Do not accept integer values that are
|
||||
larger than 32 bits.
|
||||
* config/mcore/mcore.md: Remove unused constraints from split.
|
||||
(andsi3): Use HOST_WIDE_INT instead of int to hold an INTVAL.
|
||||
(addsi3): Likewise.
|
||||
(allocate_stack): Likewise.
|
||||
* config/mcore/mcore.c (mcore_print_operand): Restrict output of P
|
||||
operands to 32 bits.
|
||||
(mcore_const_costs): Use HOST_WIDE_INT instead of int to hold an
|
||||
INTVAL.
|
||||
(mcore_and_cost, mcore_modify_comparison, const_ok_for_mcore,
|
||||
mcore_const_ok_for_inline, mcore_const_trick_uses_not,
|
||||
try_constant_tricks, mcore_num_ones, mcore_num_zeros,
|
||||
mcore_output_bclri, mcore_output_andn, output_inline_const,
|
||||
mcore_output_move, mcore_output_movedouble): Likewise.
|
||||
(mcore_output_cmov): Use CONST_OK_FOR_M and CONST_OK_FOR_N.
|
||||
(output_inline_const): Likewise.
|
||||
(output_inline_const): Fix format strings used in sprintf
|
||||
statements.
|
||||
* config/mcore/mcore-protos.h: Update prototypes for changed
|
||||
functions in mcore.c.
|
||||
* config/mcore/mcore.h (CONST_OK_FOR_I): Cast values to
|
||||
HOST_WIDE_INT and not int.
|
||||
(CONST_OK_FOR_J, CONST_OK_FOR_K, CONST_OK_FOR_L, CONST_OK_FOR_M,
|
||||
CONST_OK_FOR_N): Likewise.
|
||||
(LEGITIMATE_CONSTANT_P): Also check CONSTANT_P.
|
||||
(GO_IF_LEGITIMATE_INDEX): Use HOST_WIDE_INT instead of int to hold
|
||||
an INTVAL.
|
||||
|
||||
2007-01-10 Jan Hubicka <jh@suse.cz>
|
||||
|
||||
* tree-vrp.c (remove_range_assertions): Release defs.
|
||||
|
@ -1,5 +1,5 @@
|
||||
/* Prototypes for exported functions defined in mcore.c
|
||||
Copyright (C) 2000, 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
|
||||
Copyright (C) 2000, 2002, 2003, 2004, 2005, 2007 Free Software Foundation, Inc.
|
||||
Contributed by Nick Clifton (nickc@redhat.com)
|
||||
|
||||
This file is part of GCC.
|
||||
@ -22,13 +22,13 @@
|
||||
extern const char * mcore_output_jump_label_table (void);
|
||||
extern void mcore_expand_prolog (void);
|
||||
extern void mcore_expand_epilog (void);
|
||||
extern int mcore_const_ok_for_inline (long);
|
||||
extern int mcore_num_ones (int);
|
||||
extern int mcore_num_zeros (int);
|
||||
extern int mcore_const_ok_for_inline (HOST_WIDE_INT);
|
||||
extern int mcore_num_ones (HOST_WIDE_INT);
|
||||
extern int mcore_num_zeros (HOST_WIDE_INT);
|
||||
extern int mcore_initial_elimination_offset (int, int);
|
||||
extern int mcore_byte_offset (unsigned int);
|
||||
extern int mcore_halfword_offset (unsigned int);
|
||||
extern int mcore_const_trick_uses_not (long);
|
||||
extern int mcore_const_trick_uses_not (HOST_WIDE_INT);
|
||||
extern void mcore_override_options (void);
|
||||
extern int mcore_dllexport_name_p (const char *);
|
||||
extern int mcore_dllimport_name_p (const char *);
|
||||
@ -71,7 +71,7 @@ extern int mcore_arith_S_operand (rtx);
|
||||
#ifdef HAVE_MACHINE_MODES
|
||||
extern const char * mcore_output_move (rtx, rtx *, enum machine_mode);
|
||||
extern const char * mcore_output_movedouble (rtx *, enum machine_mode);
|
||||
extern int const_ok_for_mcore (int);
|
||||
extern int const_ok_for_mcore (HOST_WIDE_INT);
|
||||
#ifdef TREE_CODE
|
||||
extern rtx mcore_function_arg (CUMULATIVE_ARGS, enum machine_mode, tree, int);
|
||||
#endif /* TREE_CODE */
|
||||
|
@ -1,5 +1,5 @@
|
||||
/* Output routines for Motorola MCore processor
|
||||
Copyright (C) 1993, 1999, 2000, 2001, 2002, 2003, 2004, 2005
|
||||
Copyright (C) 1993, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2007
|
||||
Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GCC.
|
||||
@ -118,7 +118,7 @@ cond_type;
|
||||
|
||||
static void output_stack_adjust (int, int);
|
||||
static int calc_live_regs (int *);
|
||||
static int try_constant_tricks (long, int *, int *);
|
||||
static int try_constant_tricks (long, HOST_WIDE_INT *, HOST_WIDE_INT *);
|
||||
static const char * output_inline_const (enum machine_mode, rtx *);
|
||||
static void layout_mcore_frame (struct mcore_frame *);
|
||||
static void mcore_setup_incoming_varargs (CUMULATIVE_ARGS *, enum machine_mode, tree, int *, int);
|
||||
@ -345,7 +345,7 @@ mcore_print_operand (FILE * stream, rtx x, int code)
|
||||
fprintf (asm_out_file, "%d", exact_log2 (INTVAL (x) + 1));
|
||||
break;
|
||||
case 'P':
|
||||
fprintf (asm_out_file, "%d", exact_log2 (INTVAL (x)));
|
||||
fprintf (asm_out_file, "%d", exact_log2 (INTVAL (x) & 0xffffffff));
|
||||
break;
|
||||
case 'Q':
|
||||
fprintf (asm_out_file, "%d", exact_log2 (~INTVAL (x)));
|
||||
@ -404,7 +404,7 @@ mcore_print_operand (FILE * stream, rtx x, int code)
|
||||
static int
|
||||
mcore_const_costs (rtx exp, enum rtx_code code)
|
||||
{
|
||||
int val = INTVAL (exp);
|
||||
HOST_WIDE_INT val = INTVAL (exp);
|
||||
|
||||
/* Easy constants. */
|
||||
if ( CONST_OK_FOR_I (val)
|
||||
@ -432,7 +432,7 @@ mcore_const_costs (rtx exp, enum rtx_code code)
|
||||
static int
|
||||
mcore_and_cost (rtx x)
|
||||
{
|
||||
int val;
|
||||
HOST_WIDE_INT val;
|
||||
|
||||
if (GET_CODE (XEXP (x, 1)) != CONST_INT)
|
||||
return 2;
|
||||
@ -458,7 +458,7 @@ mcore_and_cost (rtx x)
|
||||
static int
|
||||
mcore_ior_cost (rtx x)
|
||||
{
|
||||
int val;
|
||||
HOST_WIDE_INT val;
|
||||
|
||||
if (GET_CODE (XEXP (x, 1)) != CONST_INT)
|
||||
return 2;
|
||||
@ -529,7 +529,7 @@ mcore_modify_comparison (enum rtx_code code)
|
||||
|
||||
if (GET_CODE (op1) == CONST_INT)
|
||||
{
|
||||
int val = INTVAL (op1);
|
||||
HOST_WIDE_INT val = INTVAL (op1);
|
||||
|
||||
switch (code)
|
||||
{
|
||||
@ -686,17 +686,17 @@ mcore_output_call (rtx operands[], int index)
|
||||
/* Can we load a constant with a single instruction ? */
|
||||
|
||||
int
|
||||
const_ok_for_mcore (int value)
|
||||
const_ok_for_mcore (HOST_WIDE_INT value)
|
||||
{
|
||||
if (value >= 0 && value <= 127)
|
||||
return 1;
|
||||
|
||||
/* Try exact power of two. */
|
||||
if ((value & (value - 1)) == 0)
|
||||
if (CONST_OK_FOR_M (value))
|
||||
return 1;
|
||||
|
||||
/* Try exact power of two - 1. */
|
||||
if ((value & (value + 1)) == 0)
|
||||
if (CONST_OK_FOR_N (value) && value != -1)
|
||||
return 1;
|
||||
|
||||
return 0;
|
||||
@ -705,9 +705,9 @@ const_ok_for_mcore (int value)
|
||||
/* Can we load a constant inline with up to 2 instructions ? */
|
||||
|
||||
int
|
||||
mcore_const_ok_for_inline (long value)
|
||||
mcore_const_ok_for_inline (HOST_WIDE_INT value)
|
||||
{
|
||||
int x, y;
|
||||
HOST_WIDE_INT x, y;
|
||||
|
||||
return try_constant_tricks (value, & x, & y) > 0;
|
||||
}
|
||||
@ -715,9 +715,9 @@ mcore_const_ok_for_inline (long value)
|
||||
/* Are we loading the constant using a not ? */
|
||||
|
||||
int
|
||||
mcore_const_trick_uses_not (long value)
|
||||
mcore_const_trick_uses_not (HOST_WIDE_INT value)
|
||||
{
|
||||
int x, y;
|
||||
HOST_WIDE_INT x, y;
|
||||
|
||||
return try_constant_tricks (value, & x, & y) == 2;
|
||||
}
|
||||
@ -739,120 +739,119 @@ mcore_const_trick_uses_not (long value)
|
||||
11: single insn followed by ixw. */
|
||||
|
||||
static int
|
||||
try_constant_tricks (long value, int * x, int * y)
|
||||
try_constant_tricks (HOST_WIDE_INT value, HOST_WIDE_INT * x, HOST_WIDE_INT * y)
|
||||
{
|
||||
int i;
|
||||
unsigned bit, shf, rot;
|
||||
HOST_WIDE_INT i;
|
||||
unsigned HOST_WIDE_INT bit, shf, rot;
|
||||
|
||||
if (const_ok_for_mcore (value))
|
||||
return 1; /* Do the usual thing. */
|
||||
|
||||
if (TARGET_HARDLIT)
|
||||
if (! TARGET_HARDLIT)
|
||||
return 0;
|
||||
|
||||
if (const_ok_for_mcore (~value))
|
||||
{
|
||||
if (const_ok_for_mcore (~value))
|
||||
*x = ~value;
|
||||
return 2;
|
||||
}
|
||||
|
||||
for (i = 1; i <= 32; i++)
|
||||
{
|
||||
if (const_ok_for_mcore (value - i))
|
||||
{
|
||||
*x = ~value;
|
||||
return 2;
|
||||
*x = value - i;
|
||||
*y = i;
|
||||
|
||||
return 3;
|
||||
}
|
||||
|
||||
for (i = 1; i <= 32; i++)
|
||||
|
||||
if (const_ok_for_mcore (value + i))
|
||||
{
|
||||
if (const_ok_for_mcore (value - i))
|
||||
{
|
||||
*x = value - i;
|
||||
*y = i;
|
||||
|
||||
return 3;
|
||||
}
|
||||
|
||||
if (const_ok_for_mcore (value + i))
|
||||
{
|
||||
*x = value + i;
|
||||
*y = i;
|
||||
|
||||
return 4;
|
||||
}
|
||||
*x = value + i;
|
||||
*y = i;
|
||||
|
||||
return 4;
|
||||
}
|
||||
|
||||
bit = 0x80000000L;
|
||||
|
||||
for (i = 0; i <= 31; i++)
|
||||
}
|
||||
|
||||
bit = 0x80000000ULL;
|
||||
|
||||
for (i = 0; i <= 31; i++)
|
||||
{
|
||||
if (const_ok_for_mcore (i - value))
|
||||
{
|
||||
if (const_ok_for_mcore (i - value))
|
||||
{
|
||||
*x = i - value;
|
||||
*y = i;
|
||||
|
||||
return 5;
|
||||
}
|
||||
|
||||
if (const_ok_for_mcore (value & ~bit))
|
||||
{
|
||||
*y = bit;
|
||||
*x = value & ~bit;
|
||||
|
||||
return 6;
|
||||
}
|
||||
|
||||
if (const_ok_for_mcore (value | bit))
|
||||
{
|
||||
*y = ~bit;
|
||||
*x = value | bit;
|
||||
|
||||
return 7;
|
||||
}
|
||||
|
||||
bit >>= 1;
|
||||
*x = i - value;
|
||||
*y = i;
|
||||
|
||||
return 5;
|
||||
}
|
||||
|
||||
shf = value;
|
||||
rot = value;
|
||||
|
||||
for (i = 1; i < 31; i++)
|
||||
|
||||
if (const_ok_for_mcore (value & ~bit))
|
||||
{
|
||||
int c;
|
||||
|
||||
/* MCore has rotate left. */
|
||||
c = rot << 31;
|
||||
rot >>= 1;
|
||||
rot &= 0x7FFFFFFF;
|
||||
rot |= c; /* Simulate rotate. */
|
||||
|
||||
if (const_ok_for_mcore (rot))
|
||||
{
|
||||
*y = i;
|
||||
*x = rot;
|
||||
|
||||
return 8;
|
||||
}
|
||||
|
||||
if (shf & 1)
|
||||
shf = 0; /* Can't use logical shift, low order bit is one. */
|
||||
|
||||
shf >>= 1;
|
||||
|
||||
if (shf != 0 && const_ok_for_mcore (shf))
|
||||
{
|
||||
*y = i;
|
||||
*x = shf;
|
||||
|
||||
return 9;
|
||||
}
|
||||
*y = bit;
|
||||
*x = value & ~bit;
|
||||
return 6;
|
||||
}
|
||||
|
||||
if ((value % 3) == 0 && const_ok_for_mcore (value / 3))
|
||||
|
||||
if (const_ok_for_mcore (value | bit))
|
||||
{
|
||||
*x = value / 3;
|
||||
|
||||
return 10;
|
||||
*y = ~bit;
|
||||
*x = value | bit;
|
||||
|
||||
return 7;
|
||||
}
|
||||
|
||||
if ((value % 5) == 0 && const_ok_for_mcore (value / 5))
|
||||
|
||||
bit >>= 1;
|
||||
}
|
||||
|
||||
shf = value;
|
||||
rot = value;
|
||||
|
||||
for (i = 1; i < 31; i++)
|
||||
{
|
||||
int c;
|
||||
|
||||
/* MCore has rotate left. */
|
||||
c = rot << 31;
|
||||
rot >>= 1;
|
||||
rot &= 0x7FFFFFFF;
|
||||
rot |= c; /* Simulate rotate. */
|
||||
|
||||
if (const_ok_for_mcore (rot))
|
||||
{
|
||||
*x = value / 5;
|
||||
|
||||
return 11;
|
||||
*y = i;
|
||||
*x = rot;
|
||||
|
||||
return 8;
|
||||
}
|
||||
|
||||
if (shf & 1)
|
||||
shf = 0; /* Can't use logical shift, low order bit is one. */
|
||||
|
||||
shf >>= 1;
|
||||
|
||||
if (shf != 0 && const_ok_for_mcore (shf))
|
||||
{
|
||||
*y = i;
|
||||
*x = shf;
|
||||
|
||||
return 9;
|
||||
}
|
||||
}
|
||||
|
||||
if ((value % 3) == 0 && const_ok_for_mcore (value / 3))
|
||||
{
|
||||
*x = value / 3;
|
||||
|
||||
return 10;
|
||||
}
|
||||
|
||||
if ((value % 5) == 0 && const_ok_for_mcore (value / 5))
|
||||
{
|
||||
*x = value / 5;
|
||||
|
||||
return 11;
|
||||
}
|
||||
|
||||
return 0;
|
||||
@ -910,7 +909,7 @@ mcore_is_dead (rtx first, rtx reg)
|
||||
/* Count the number of ones in mask. */
|
||||
|
||||
int
|
||||
mcore_num_ones (int mask)
|
||||
mcore_num_ones (HOST_WIDE_INT mask)
|
||||
{
|
||||
/* A trick to count set bits recently posted on comp.compilers. */
|
||||
mask = (mask >> 1 & 0x55555555) + (mask & 0x55555555);
|
||||
@ -924,7 +923,7 @@ mcore_num_ones (int mask)
|
||||
/* Count the number of zeros in mask. */
|
||||
|
||||
int
|
||||
mcore_num_zeros (int mask)
|
||||
mcore_num_zeros (HOST_WIDE_INT mask)
|
||||
{
|
||||
return 32 - mcore_num_ones (mask);
|
||||
}
|
||||
@ -1015,8 +1014,8 @@ mcore_output_bclri (rtx dst, int mask)
|
||||
const char *
|
||||
mcore_output_cmov (rtx operands[], int cmp_t, const char * test)
|
||||
{
|
||||
int load_value;
|
||||
int adjust_value;
|
||||
HOST_WIDE_INT load_value;
|
||||
HOST_WIDE_INT adjust_value;
|
||||
rtx out_operands[4];
|
||||
|
||||
out_operands[0] = operands[0];
|
||||
@ -1049,9 +1048,9 @@ mcore_output_cmov (rtx operands[], int cmp_t, const char * test)
|
||||
instruction sequence has a different length attribute). */
|
||||
if (load_value >= 0 && load_value <= 127)
|
||||
output_asm_insn ("movi\t%0,%1", out_operands);
|
||||
else if ((load_value & (load_value - 1)) == 0)
|
||||
else if (CONST_OK_FOR_M (load_value))
|
||||
output_asm_insn ("bgeni\t%0,%P1", out_operands);
|
||||
else if ((load_value & (load_value + 1)) == 0)
|
||||
else if (CONST_OK_FOR_N (load_value))
|
||||
output_asm_insn ("bmaski\t%0,%N1", out_operands);
|
||||
|
||||
/* Output the constant adjustment. */
|
||||
@ -1079,7 +1078,7 @@ mcore_output_cmov (rtx operands[], int cmp_t, const char * test)
|
||||
const char *
|
||||
mcore_output_andn (rtx insn ATTRIBUTE_UNUSED, rtx operands[])
|
||||
{
|
||||
int x, y;
|
||||
HOST_WIDE_INT x, y;
|
||||
rtx out_operands[3];
|
||||
const char * load_op;
|
||||
char buf[256];
|
||||
@ -1089,22 +1088,25 @@ mcore_output_andn (rtx insn ATTRIBUTE_UNUSED, rtx operands[])
|
||||
gcc_assert (trick_no == 2);
|
||||
|
||||
out_operands[0] = operands[0];
|
||||
out_operands[1] = GEN_INT(x);
|
||||
out_operands[1] = GEN_INT (x);
|
||||
out_operands[2] = operands[2];
|
||||
|
||||
if (x >= 0 && x <= 127)
|
||||
load_op = "movi\t%0,%1";
|
||||
|
||||
/* Try exact power of two. */
|
||||
else if ((x & (x - 1)) == 0)
|
||||
else if (CONST_OK_FOR_M (x))
|
||||
load_op = "bgeni\t%0,%P1";
|
||||
|
||||
/* Try exact power of two - 1. */
|
||||
else if ((x & (x + 1)) == 0)
|
||||
else if (CONST_OK_FOR_N (x))
|
||||
load_op = "bmaski\t%0,%N1";
|
||||
|
||||
else
|
||||
load_op = "BADMOVI\t%0,%1";
|
||||
else
|
||||
{
|
||||
load_op = "BADMOVI-andn\t%0, %1";
|
||||
gcc_unreachable ();
|
||||
}
|
||||
|
||||
sprintf (buf, "%s\n\tandn\t%%2,%%0", load_op);
|
||||
output_asm_insn (buf, out_operands);
|
||||
@ -1117,13 +1119,13 @@ mcore_output_andn (rtx insn ATTRIBUTE_UNUSED, rtx operands[])
|
||||
static const char *
|
||||
output_inline_const (enum machine_mode mode, rtx operands[])
|
||||
{
|
||||
int x = 0, y = 0;
|
||||
HOST_WIDE_INT x = 0, y = 0;
|
||||
int trick_no;
|
||||
rtx out_operands[3];
|
||||
char buf[256];
|
||||
char load_op[256];
|
||||
const char *dst_fmt;
|
||||
int value;
|
||||
HOST_WIDE_INT value;
|
||||
|
||||
value = INTVAL (operands[1]);
|
||||
|
||||
@ -1153,15 +1155,18 @@ output_inline_const (enum machine_mode mode, rtx operands[])
|
||||
sprintf (load_op, "movi\t%s,%%1", dst_fmt);
|
||||
|
||||
/* Try exact power of two. */
|
||||
else if ((x & (x - 1)) == 0)
|
||||
else if (CONST_OK_FOR_M (x))
|
||||
sprintf (load_op, "bgeni\t%s,%%P1", dst_fmt);
|
||||
|
||||
/* Try exact power of two - 1. */
|
||||
else if ((x & (x + 1)) == 0)
|
||||
else if (CONST_OK_FOR_N (x))
|
||||
sprintf (load_op, "bmaski\t%s,%%N1", dst_fmt);
|
||||
|
||||
else
|
||||
sprintf (load_op, "BADMOVI\t%s,%%1", dst_fmt);
|
||||
else
|
||||
{
|
||||
sprintf (load_op, "BADMOVI-inline_const %s, %%1", dst_fmt);
|
||||
gcc_unreachable ();
|
||||
}
|
||||
|
||||
switch (trick_no)
|
||||
{
|
||||
@ -1169,35 +1174,35 @@ output_inline_const (enum machine_mode mode, rtx operands[])
|
||||
strcpy (buf, load_op);
|
||||
break;
|
||||
case 2: /* not */
|
||||
sprintf (buf, "%s\n\tnot\t%s\t// %d 0x%x", load_op, dst_fmt, value, value);
|
||||
sprintf (buf, "%s\n\tnot\t%s\t// %ld 0x%lx", load_op, dst_fmt, value, value);
|
||||
break;
|
||||
case 3: /* add */
|
||||
sprintf (buf, "%s\n\taddi\t%s,%%2\t// %d 0x%x", load_op, dst_fmt, value, value);
|
||||
sprintf (buf, "%s\n\taddi\t%s,%%2\t// %ld 0x%lx", load_op, dst_fmt, value, value);
|
||||
break;
|
||||
case 4: /* sub */
|
||||
sprintf (buf, "%s\n\tsubi\t%s,%%2\t// %d 0x%x", load_op, dst_fmt, value, value);
|
||||
sprintf (buf, "%s\n\tsubi\t%s,%%2\t// %ld 0x%lx", load_op, dst_fmt, value, value);
|
||||
break;
|
||||
case 5: /* rsub */
|
||||
/* Never happens unless -mrsubi, see try_constant_tricks(). */
|
||||
sprintf (buf, "%s\n\trsubi\t%s,%%2\t// %d 0x%x", load_op, dst_fmt, value, value);
|
||||
sprintf (buf, "%s\n\trsubi\t%s,%%2\t// %ld 0x%lx", load_op, dst_fmt, value, value);
|
||||
break;
|
||||
case 6: /* bset */
|
||||
sprintf (buf, "%s\n\tbseti\t%s,%%P2\t// %d 0x%x", load_op, dst_fmt, value, value);
|
||||
case 6: /* bseti */
|
||||
sprintf (buf, "%s\n\tbseti\t%s,%%P2\t// %ld 0x%lx", load_op, dst_fmt, value, value);
|
||||
break;
|
||||
case 7: /* bclr */
|
||||
sprintf (buf, "%s\n\tbclri\t%s,%%Q2\t// %d 0x%x", load_op, dst_fmt, value, value);
|
||||
sprintf (buf, "%s\n\tbclri\t%s,%%Q2\t// %ld 0x%lx", load_op, dst_fmt, value, value);
|
||||
break;
|
||||
case 8: /* rotl */
|
||||
sprintf (buf, "%s\n\trotli\t%s,%%2\t// %d 0x%x", load_op, dst_fmt, value, value);
|
||||
sprintf (buf, "%s\n\trotli\t%s,%%2\t// %ld 0x%lx", load_op, dst_fmt, value, value);
|
||||
break;
|
||||
case 9: /* lsl */
|
||||
sprintf (buf, "%s\n\tlsli\t%s,%%2\t// %d 0x%x", load_op, dst_fmt, value, value);
|
||||
sprintf (buf, "%s\n\tlsli\t%s,%%2\t// %ld 0x%lx", load_op, dst_fmt, value, value);
|
||||
break;
|
||||
case 10: /* ixh */
|
||||
sprintf (buf, "%s\n\tixh\t%s,%s\t// %d 0x%x", load_op, dst_fmt, dst_fmt, value, value);
|
||||
sprintf (buf, "%s\n\tixh\t%s,%s\t// %ld 0x%lx", load_op, dst_fmt, dst_fmt, value, value);
|
||||
break;
|
||||
case 11: /* ixw */
|
||||
sprintf (buf, "%s\n\tixw\t%s,%s\t// %d 0x%x", load_op, dst_fmt, dst_fmt, value, value);
|
||||
sprintf (buf, "%s\n\tixw\t%s,%s\t// %ld 0x%lx", load_op, dst_fmt, dst_fmt, value, value);
|
||||
break;
|
||||
default:
|
||||
return "";
|
||||
@ -1245,7 +1250,7 @@ mcore_output_move (rtx insn ATTRIBUTE_UNUSED, rtx operands[],
|
||||
}
|
||||
else if (GET_CODE (src) == CONST_INT)
|
||||
{
|
||||
int x, y;
|
||||
HOST_WIDE_INT x, y;
|
||||
|
||||
if (CONST_OK_FOR_I (INTVAL (src))) /* r-I */
|
||||
return "movi\t%0,%1";
|
||||
@ -1342,8 +1347,6 @@ mcore_output_movedouble (rtx operands[], enum machine_mode mode ATTRIBUTE_UNUSED
|
||||
output_asm_insn ("movi %0,%1", operands);
|
||||
else if (CONST_OK_FOR_M (INTVAL (src)))
|
||||
output_asm_insn ("bgeni %0,%P1", operands);
|
||||
else if (INTVAL (src) == -1)
|
||||
output_asm_insn ("bmaski %0,32", operands);
|
||||
else if (CONST_OK_FOR_N (INTVAL (src)))
|
||||
output_asm_insn ("bmaski %0,%N1", operands);
|
||||
else
|
||||
@ -1360,13 +1363,11 @@ mcore_output_movedouble (rtx operands[], enum machine_mode mode ATTRIBUTE_UNUSED
|
||||
output_asm_insn ("movi %R0,%1", operands);
|
||||
else if (CONST_OK_FOR_M (INTVAL (src)))
|
||||
output_asm_insn ("bgeni %R0,%P1", operands);
|
||||
else if (INTVAL (src) == -1)
|
||||
output_asm_insn ("bmaski %R0,32", operands);
|
||||
else if (CONST_OK_FOR_N (INTVAL (src)))
|
||||
output_asm_insn ("bmaski %R0,%N1", operands);
|
||||
else
|
||||
gcc_unreachable ();
|
||||
|
||||
|
||||
if (INTVAL (src) < 0)
|
||||
return "bmaski %0,32";
|
||||
else
|
||||
@ -1410,7 +1411,7 @@ mcore_expand_insv (rtx operands[])
|
||||
{
|
||||
/* Do directly with bseti or bclri. */
|
||||
/* RBE: 2/97 consider only low bit of constant. */
|
||||
if ((INTVAL(operands[3])&1) == 0)
|
||||
if ((INTVAL (operands[3]) & 1) == 0)
|
||||
{
|
||||
mask = ~(1 << posn);
|
||||
emit_insn (gen_rtx_SET (SImode, operands[0],
|
||||
@ -1445,8 +1446,8 @@ mcore_expand_insv (rtx operands[])
|
||||
immediates. */
|
||||
|
||||
/* If setting the entire field, do it directly. */
|
||||
if (GET_CODE (operands[3]) == CONST_INT &&
|
||||
INTVAL (operands[3]) == ((1 << width) - 1))
|
||||
if (GET_CODE (operands[3]) == CONST_INT
|
||||
&& INTVAL (operands[3]) == ((1 << width) - 1))
|
||||
{
|
||||
mreg = force_reg (SImode, GEN_INT (INTVAL (operands[3]) << posn));
|
||||
emit_insn (gen_rtx_SET (SImode, operands[0],
|
||||
|
@ -1,6 +1,6 @@
|
||||
/* Definitions of target machine for GNU compiler,
|
||||
for Motorola M*CORE Processor.
|
||||
Copyright (C) 1993, 1999, 2000, 2001, 2002, 2003, 2004, 2005
|
||||
Copyright (C) 1993, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2007
|
||||
Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GCC.
|
||||
@ -452,17 +452,17 @@ extern const enum reg_class reg_class_from_letter[];
|
||||
U: constant 0
|
||||
xxxS: 1 cleared bit out of 32 (complement of power of 2). for bclri
|
||||
xxxT: 2 cleared bits out of 32. for pairs of bclris. */
|
||||
#define CONST_OK_FOR_I(VALUE) (((int)(VALUE)) >= 0 && ((int)(VALUE)) <= 0x7f)
|
||||
#define CONST_OK_FOR_J(VALUE) (((int)(VALUE)) > 0 && ((int)(VALUE)) <= 32)
|
||||
#define CONST_OK_FOR_L(VALUE) (((int)(VALUE)) < 0 && ((int)(VALUE)) >= -32)
|
||||
#define CONST_OK_FOR_K(VALUE) (((int)(VALUE)) >= 0 && ((int)(VALUE)) <= 31)
|
||||
#define CONST_OK_FOR_M(VALUE) (exact_log2 (VALUE) >= 0)
|
||||
#define CONST_OK_FOR_N(VALUE) (((int)(VALUE)) == -1 || exact_log2 ((VALUE) + 1) >= 0)
|
||||
#define CONST_OK_FOR_I(VALUE) (((HOST_WIDE_INT)(VALUE)) >= 0 && ((HOST_WIDE_INT)(VALUE)) <= 0x7f)
|
||||
#define CONST_OK_FOR_J(VALUE) (((HOST_WIDE_INT)(VALUE)) > 0 && ((HOST_WIDE_INT)(VALUE)) <= 32)
|
||||
#define CONST_OK_FOR_L(VALUE) (((HOST_WIDE_INT)(VALUE)) < 0 && ((HOST_WIDE_INT)(VALUE)) >= -32)
|
||||
#define CONST_OK_FOR_K(VALUE) (((HOST_WIDE_INT)(VALUE)) >= 0 && ((HOST_WIDE_INT)(VALUE)) <= 31)
|
||||
#define CONST_OK_FOR_M(VALUE) (exact_log2 (VALUE) >= 0 && exact_log2 (VALUE) <= 30)
|
||||
#define CONST_OK_FOR_N(VALUE) (((HOST_WIDE_INT)(VALUE)) == -1 || (exact_log2 ((VALUE) + 1) >= 0 && exact_log2 ((VALUE) + 1) <= 30))
|
||||
#define CONST_OK_FOR_O(VALUE) (CONST_OK_FOR_I(VALUE) || \
|
||||
CONST_OK_FOR_M(VALUE) || \
|
||||
CONST_OK_FOR_N(VALUE) || \
|
||||
CONST_OK_FOR_M((int)(VALUE) - 1) || \
|
||||
CONST_OK_FOR_N((int)(VALUE) + 1))
|
||||
CONST_OK_FOR_M((HOST_WIDE_INT)(VALUE) - 1) || \
|
||||
CONST_OK_FOR_N((HOST_WIDE_INT)(VALUE) + 1))
|
||||
|
||||
#define CONST_OK_FOR_P(VALUE) (mcore_const_ok_for_inline (VALUE))
|
||||
|
||||
@ -698,7 +698,8 @@ extern const enum reg_class reg_class_from_letter[];
|
||||
It is given that X satisfies CONSTANT_P or is a CONST_DOUBLE.
|
||||
|
||||
On the MCore, allow anything but a double. */
|
||||
#define LEGITIMATE_CONSTANT_P(X) (GET_CODE(X) != CONST_DOUBLE)
|
||||
#define LEGITIMATE_CONSTANT_P(X) (GET_CODE(X) != CONST_DOUBLE \
|
||||
&& CONSTANT_P (X))
|
||||
|
||||
/* The macros REG_OK_FOR..._P assume that the arg is a REG rtx
|
||||
and check its validity for a certain class.
|
||||
@ -755,15 +756,15 @@ extern const enum reg_class reg_class_from_letter[];
|
||||
if (GET_CODE (OP) == CONST_INT) \
|
||||
{ \
|
||||
if (GET_MODE_SIZE (MODE) >= 4 \
|
||||
&& (((unsigned)INTVAL (OP)) % 4) == 0 \
|
||||
&& ((unsigned)INTVAL (OP)) <= 64 - GET_MODE_SIZE (MODE)) \
|
||||
&& (((unsigned HOST_WIDE_INT) INTVAL (OP)) % 4) == 0 \
|
||||
&& ((unsigned HOST_WIDE_INT) INTVAL (OP)) <= 64 - GET_MODE_SIZE (MODE)) \
|
||||
goto LABEL; \
|
||||
if (GET_MODE_SIZE (MODE) == 2 \
|
||||
&& (((unsigned)INTVAL (OP)) % 2) == 0 \
|
||||
&& ((unsigned)INTVAL (OP)) <= 30) \
|
||||
&& (((unsigned HOST_WIDE_INT) INTVAL (OP)) % 2) == 0 \
|
||||
&& ((unsigned HOST_WIDE_INT) INTVAL (OP)) <= 30) \
|
||||
goto LABEL; \
|
||||
if (GET_MODE_SIZE (MODE) == 1 \
|
||||
&& ((unsigned)INTVAL (OP)) <= 15) \
|
||||
&& ((unsigned HOST_WIDE_INT) INTVAL (OP)) <= 15) \
|
||||
goto LABEL; \
|
||||
} \
|
||||
} \
|
||||
@ -853,7 +854,7 @@ extern const enum reg_class reg_class_from_letter[];
|
||||
#define DATA_SECTION_ASM_OP "\t.data"
|
||||
|
||||
/* Switch into a generic section. */
|
||||
#undef TARGET_ASM_NAMED_SECTION
|
||||
#undef TARGET_ASM_NAMED_SECTION
|
||||
#define TARGET_ASM_NAMED_SECTION mcore_asm_named_section
|
||||
|
||||
/* This is how to output an insn to push a register on the stack.
|
||||
|
@ -1,5 +1,5 @@
|
||||
;; Machine description the Motorola MCore
|
||||
;; Copyright (C) 1993, 1999, 2000, 2004, 2005
|
||||
;; Copyright (C) 1993, 1999, 2000, 2004, 2005, 2007
|
||||
;; Free Software Foundation, Inc.
|
||||
;; Contributed by Motorola.
|
||||
|
||||
@ -192,11 +192,11 @@
|
||||
(define_split
|
||||
[(parallel[
|
||||
(set (reg:CC 17)
|
||||
(ne:CC (ne:SI (leu:CC (match_operand:SI 0 "mcore_arith_reg_operand" "r")
|
||||
(match_operand:SI 1 "mcore_arith_reg_operand" "r"))
|
||||
(ne:CC (ne:SI (leu:CC (match_operand:SI 0 "mcore_arith_reg_operand" "")
|
||||
(match_operand:SI 1 "mcore_arith_reg_operand" ""))
|
||||
(const_int 0))
|
||||
(const_int 0)))
|
||||
(clobber (match_operand:CC 2 "mcore_arith_reg_operand" "=r"))])]
|
||||
(clobber (match_operand:CC 2 "mcore_arith_reg_operand" ""))])]
|
||||
""
|
||||
[(set (reg:CC 17) (ne:SI (match_dup 0) (const_int 0)))
|
||||
(set (reg:CC 17) (leu:CC (match_dup 0) (match_dup 1)))])
|
||||
@ -355,7 +355,8 @@
|
||||
if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0
|
||||
&& ! mcore_arith_S_operand (operands[2]))
|
||||
{
|
||||
int not_value = ~ INTVAL (operands[2]);
|
||||
HOST_WIDE_INT not_value = ~ INTVAL (operands[2]);
|
||||
|
||||
if ( CONST_OK_FOR_I (not_value)
|
||||
|| CONST_OK_FOR_M (not_value)
|
||||
|| CONST_OK_FOR_N (not_value))
|
||||
@ -730,9 +731,11 @@
|
||||
/* Convert adds to subtracts if this makes loading the constant cheaper.
|
||||
But only if we are allowed to generate new pseudos. */
|
||||
if (! (reload_in_progress || reload_completed)
|
||||
&& GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < -32)
|
||||
&& GET_CODE (operands[2]) == CONST_INT
|
||||
&& INTVAL (operands[2]) < -32)
|
||||
{
|
||||
int neg_value = - INTVAL (operands[2]);
|
||||
HOST_WIDE_INT neg_value = - INTVAL (operands[2]);
|
||||
|
||||
if ( CONST_OK_FOR_I (neg_value)
|
||||
|| CONST_OK_FOR_M (neg_value)
|
||||
|| CONST_OK_FOR_N (neg_value))
|
||||
@ -764,7 +767,7 @@
|
||||
;; || (INTVAL (operands[2]) < -32 && INTVAL(operands[2]) >= -64))"
|
||||
;; "*
|
||||
;; {
|
||||
;; int n = INTVAL(operands[2]);
|
||||
;; HOST_WIDE_INT n = INTVAL(operands[2]);
|
||||
;; if (n > 0)
|
||||
;; {
|
||||
;; operands[2] = GEN_INT(n - 32);
|
||||
@ -822,7 +825,7 @@
|
||||
;; || (INTVAL (operands[2]) < -32 && INTVAL(operands[2]) >= -64))"
|
||||
;; "*
|
||||
;; {
|
||||
;; int n = INTVAL(operands[2]);
|
||||
;; HOST_WIDE_INT n = INTVAL(operands[2]);
|
||||
;; if ( n > 0)
|
||||
;; {
|
||||
;; operands[2] = GEN_INT( n - 32);
|
||||
@ -2976,8 +2979,9 @@
|
||||
(match_operand:SI 1 "const_int_operand" ""))
|
||||
(set (match_operand:SI 2 "mcore_arith_reg_operand" "")
|
||||
(ior:SI (match_dup 2) (match_dup 0)))]
|
||||
"TARGET_HARDLIT && mcore_num_ones (INTVAL (operands[1])) == 2 &&
|
||||
mcore_is_dead (insn, operands[0])"
|
||||
"TARGET_HARDLIT
|
||||
&& mcore_num_ones (INTVAL (operands[1])) == 2
|
||||
&& mcore_is_dead (insn, operands[0])"
|
||||
"* return mcore_output_bseti (operands[2], INTVAL (operands[1]));")
|
||||
|
||||
(define_peephole
|
||||
@ -3276,7 +3280,7 @@
|
||||
if (GET_CODE (operands[1]) == CONST_INT
|
||||
&& INTVAL (operands[1]) < 8 * STACK_UNITS_MAXSTEP)
|
||||
{
|
||||
int left = INTVAL(operands[1]);
|
||||
HOST_WIDE_INT left = INTVAL(operands[1]);
|
||||
|
||||
/* If it's a long way, get close enough for a last shot. */
|
||||
if (left >= STACK_UNITS_MAXSTEP)
|
||||
@ -3295,7 +3299,7 @@
|
||||
while (left > STACK_UNITS_MAXSTEP);
|
||||
}
|
||||
/* Perform the final adjustment. */
|
||||
emit_insn (gen_addsi3 (stack_pointer_rtx,stack_pointer_rtx,GEN_INT(-left)));
|
||||
emit_insn (gen_addsi3 (stack_pointer_rtx, stack_pointer_rtx, GEN_INT (-left)));
|
||||
;; emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
|
||||
DONE;
|
||||
}
|
||||
@ -3309,7 +3313,7 @@
|
||||
|
||||
#if 1
|
||||
emit_insn (gen_movsi (tmp, operands[1]));
|
||||
emit_insn (gen_movsi (step, GEN_INT(STACK_UNITS_MAXSTEP)));
|
||||
emit_insn (gen_movsi (step, GEN_INT (STACK_UNITS_MAXSTEP)));
|
||||
|
||||
if (GET_CODE (operands[1]) != CONST_INT)
|
||||
{
|
||||
|
@ -1,5 +1,5 @@
|
||||
;; Predicate definitions for Motorola MCore.
|
||||
;; Copyright (C) 2005 Free Software Foundation, Inc.
|
||||
;; Copyright (C) 2005, 2007 Free Software Foundation, Inc.
|
||||
;;
|
||||
;; This file is part of GCC.
|
||||
;;
|
||||
@ -38,7 +38,7 @@
|
||||
;; Nonzero if OP can be source of a simple move operation.
|
||||
|
||||
(define_predicate "mcore_general_movsrc_operand"
|
||||
(match_code "mem,const_int,reg,subreg,symbol_ref,label_ref")
|
||||
(match_code "mem,const_int,reg,subreg,symbol_ref,label_ref,const")
|
||||
{
|
||||
/* Any (MEM LABEL_REF) is OK. That is a pc-relative load. */
|
||||
if (GET_CODE (op) == MEM && GET_CODE (XEXP (op, 0)) == LABEL_REF)
|
||||
@ -50,7 +50,7 @@
|
||||
;; Nonzero if OP can be destination of a simple move operation.
|
||||
|
||||
(define_predicate "mcore_general_movdst_operand"
|
||||
(match_code "mem,const_int,reg,subreg")
|
||||
(match_code "mem,reg,subreg")
|
||||
{
|
||||
if (GET_CODE (op) == REG && REGNO (op) == CC_REG)
|
||||
return 0;
|
||||
@ -141,7 +141,7 @@
|
||||
|
||||
if (GET_CODE (op) == CONST_INT)
|
||||
{
|
||||
if (CONST_OK_FOR_K (INTVAL (op)) || CONST_OK_FOR_M (~INTVAL (op)))
|
||||
if (CONST_OK_FOR_K (INTVAL (op)) || (mcore_num_zeros (INTVAL (op)) <= 2))
|
||||
return 1;
|
||||
}
|
||||
|
||||
@ -212,18 +212,24 @@
|
||||
|
||||
if (GET_CODE (op) == CONST_INT)
|
||||
{
|
||||
return 1;
|
||||
|
||||
/* The following is removed because it precludes large constants from being
|
||||
/* The following has been removed because it precludes large constants from being
|
||||
returned as valid source operands for and add/sub insn. While large
|
||||
constants may not directly be used in an add/sub, they may if first loaded
|
||||
into a register. Thus, this predicate should indicate that they are valid,
|
||||
and the constraint in mcore.md should control whether an additional load to
|
||||
register is needed. (see mcore.md, addsi). -- DAC 4/2/1998 */
|
||||
/*
|
||||
if (CONST_OK_FOR_J(INTVAL(op)) || CONST_OK_FOR_L(INTVAL(op)))
|
||||
return 1;
|
||||
*/
|
||||
register is needed. (see mcore.md, addsi). -- DAC 4/2/1998
|
||||
|
||||
if (CONST_OK_FOR_J (INTVAL (op)) || CONST_OK_FOR_L (INTVAL (op)))
|
||||
return 1;
|
||||
|
||||
However we do still need to check to make sure that the constant is not too
|
||||
big, especially if we are running on a 64-bit OS... Nickc 8/1/07. */
|
||||
|
||||
if (trunc_int_for_mode (INTVAL (op), mode) != INTVAL (op))
|
||||
return 0;
|
||||
|
||||
return 1;
|
||||
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
Loading…
Reference in New Issue
Block a user