mirror of
git://gcc.gnu.org/git/gcc.git
synced 2025-03-09 20:27:19 +08:00
cselib.c (cselib_subst_to_values, [...]): Remove reference to CONST_DOUBLE_MEM in comment.
* cselib.c (cselib_subst_to_values, case CONST_DOUBLE): Remove reference to CONST_DOUBLE_MEM in comment. * emit-rtl.c (gen_rtx_CONST_DOUBLE): Remove one operand. (gen_rtx, case CONST_DOUBLE): Call it with one less operand. (init_emit_once): Don't clear CONST_DOUBLE_MEM. * function.c (pop_function_context_from): Don't call restore_varasm_status. * function.h (restore_varasm_status): Delete declaration. * gengenrtl.c (CONST_DOUBLE_FORMAT): Delete CONST_DOUBLE_MEM slot. * rtl.c: Likewise. * rtl.def (CONST_DOUBLE): Update comment. * rtl.h (CONST_DOUBLE_HIGH, CONST_DOUBLE_LOW): Update operand number. (CONST_DOUBLE_CHAIN): Likewise. (CONST_DOUBLE_MEM): Delete. (gen_rtx_CONST_DOUBLE): Update parameters. * varasm.c (struct varasm_status): x_pool_offset now HOST_WIDE_INT. Remove reference to CONST_DOUBLE_MEM. (const_alias_set): New variable. (immed_double_const): Change call to gen_rtx_CONST_DOUBLE. (immed_real_const_1): Adjust tests for 0, 1, and 2. Don't set CONST_DOUBLE_MEM. (clear_const_double_mem): Don't do anything with const_tiny_rtx. (output_constant_def): Don't look at TREE_CST_RTL if INTEGER_CST. Put constant in const_alias_set. (struct pool_constant): ALIGN now unsigned. OFFSET now HOST_WIDE_INT. Delete LABEL. (restore_varasm_status): Deleted. (mark_pool_constant): Mark desc->rtl. (force_const_mem): Rework to store rtl in hash table, not CONST_DOUBLE_MEM. Put constant in const_alias_set. (find_pool_constant): Check desc->rtl. (mark_constants, mark_constant): Don't special-case CONST_DOUBLE. (init_varasm_once): Initialize const_alias_set. From-SVN: r46736
This commit is contained in:
parent
d6b6783b3f
commit
a79e3a4591
@ -1,5 +1,41 @@
|
||||
Sat Nov 3 10:37:56 2001 Richard Kenner <kenner@vlsi1.ultra.nyu.edu>
|
||||
|
||||
* cselib.c (cselib_subst_to_values, case CONST_DOUBLE): Remove
|
||||
reference to CONST_DOUBLE_MEM in comment.
|
||||
* emit-rtl.c (gen_rtx_CONST_DOUBLE): Remove one operand.
|
||||
(gen_rtx, case CONST_DOUBLE): Call it with one less operand.
|
||||
(init_emit_once): Don't clear CONST_DOUBLE_MEM.
|
||||
* function.c (pop_function_context_from): Don't call
|
||||
restore_varasm_status.
|
||||
* function.h (restore_varasm_status): Delete declaration.
|
||||
* gengenrtl.c (CONST_DOUBLE_FORMAT): Delete CONST_DOUBLE_MEM slot.
|
||||
* rtl.c: Likewise.
|
||||
* rtl.def (CONST_DOUBLE): Update comment.
|
||||
* rtl.h (CONST_DOUBLE_HIGH, CONST_DOUBLE_LOW): Update operand number.
|
||||
(CONST_DOUBLE_CHAIN): Likewise.
|
||||
(CONST_DOUBLE_MEM): Delete.
|
||||
(gen_rtx_CONST_DOUBLE): Update parameters.
|
||||
* varasm.c (struct varasm_status): x_pool_offset now HOST_WIDE_INT.
|
||||
Remove reference to CONST_DOUBLE_MEM.
|
||||
(const_alias_set): New variable.
|
||||
(immed_double_const): Change call to gen_rtx_CONST_DOUBLE.
|
||||
(immed_real_const_1): Adjust tests for 0, 1, and 2.
|
||||
Don't set CONST_DOUBLE_MEM.
|
||||
(clear_const_double_mem): Don't do anything with const_tiny_rtx.
|
||||
(output_constant_def): Don't look at TREE_CST_RTL if INTEGER_CST.
|
||||
Put constant in const_alias_set.
|
||||
(struct pool_constant): ALIGN now unsigned.
|
||||
OFFSET now HOST_WIDE_INT.
|
||||
Delete LABEL.
|
||||
(restore_varasm_status): Deleted.
|
||||
(mark_pool_constant): Mark desc->rtl.
|
||||
(force_const_mem): Rework to store rtl in hash table,
|
||||
not CONST_DOUBLE_MEM.
|
||||
Put constant in const_alias_set.
|
||||
(find_pool_constant): Check desc->rtl.
|
||||
(mark_constants, mark_constant): Don't special-case CONST_DOUBLE.
|
||||
(init_varasm_once): Initialize const_alias_set.
|
||||
|
||||
* expr.c (expand_expr, case ADDDR_EXPR): If at top level, don't call
|
||||
force_const_mem.
|
||||
|
||||
|
@ -793,8 +793,6 @@ cselib_subst_to_values (x)
|
||||
}
|
||||
return e->u.val_rtx;
|
||||
|
||||
/* CONST_DOUBLEs must be special-cased here so that we won't try to
|
||||
look up the CONST_DOUBLE_MEM inside. */
|
||||
case CONST_DOUBLE:
|
||||
case CONST_INT:
|
||||
return x;
|
||||
|
@ -355,21 +355,19 @@ gen_rtx_CONST_INT (mode, arg)
|
||||
only at run-time. */
|
||||
|
||||
rtx
|
||||
gen_rtx_CONST_DOUBLE (mode, arg0, arg1, arg2)
|
||||
gen_rtx_CONST_DOUBLE (mode, arg0, arg1)
|
||||
enum machine_mode mode;
|
||||
rtx arg0;
|
||||
HOST_WIDE_INT arg1, arg2;
|
||||
HOST_WIDE_INT arg0, arg1;
|
||||
{
|
||||
rtx r = rtx_alloc (CONST_DOUBLE);
|
||||
int i;
|
||||
|
||||
PUT_MODE (r, mode);
|
||||
XEXP (r, 0) = arg0;
|
||||
X0EXP (r, 1) = NULL_RTX;
|
||||
X0EXP (r, 0) = NULL_RTX;
|
||||
XWINT (r, 1) = arg0;
|
||||
XWINT (r, 2) = arg1;
|
||||
XWINT (r, 3) = arg2;
|
||||
|
||||
for (i = GET_RTX_LENGTH (CONST_DOUBLE) - 1; i > 3; --i)
|
||||
for (i = GET_RTX_LENGTH (CONST_DOUBLE) - 1; i > 2; --i)
|
||||
XWINT (r, i) = 0;
|
||||
|
||||
return r;
|
||||
@ -516,10 +514,10 @@ gen_rtx VPARAMS ((enum rtx_code code, enum machine_mode mode, ...))
|
||||
|
||||
case CONST_DOUBLE:
|
||||
{
|
||||
rtx arg0 = va_arg (p, rtx);
|
||||
HOST_WIDE_INT arg0 = va_arg (p, HOST_WIDE_INT);
|
||||
HOST_WIDE_INT arg1 = va_arg (p, HOST_WIDE_INT);
|
||||
HOST_WIDE_INT arg2 = va_arg (p, HOST_WIDE_INT);
|
||||
rt_val = gen_rtx_CONST_DOUBLE (mode, arg0, arg1, arg2);
|
||||
|
||||
rt_val = gen_rtx_CONST_DOUBLE (mode, arg0, arg1);
|
||||
}
|
||||
break;
|
||||
|
||||
@ -4683,7 +4681,6 @@ init_emit_once (line_numbers)
|
||||
CONST_DOUBLE_HIGH (tem) = 0;
|
||||
|
||||
memcpy (&CONST_DOUBLE_LOW (tem), &u, sizeof u);
|
||||
CONST_DOUBLE_MEM (tem) = cc0_rtx;
|
||||
CONST_DOUBLE_CHAIN (tem) = NULL_RTX;
|
||||
PUT_MODE (tem, mode);
|
||||
|
||||
|
@ -386,7 +386,6 @@ pop_function_context_from (context)
|
||||
reg_renumber = 0;
|
||||
|
||||
restore_emit_status (p);
|
||||
restore_varasm_status (p);
|
||||
|
||||
if (restore_lang_status)
|
||||
(*restore_lang_status) (p);
|
||||
|
@ -597,7 +597,6 @@ extern void free_after_parsing PARAMS ((struct function *));
|
||||
extern void free_after_compilation PARAMS ((struct function *));
|
||||
|
||||
extern void init_varasm_status PARAMS ((struct function *));
|
||||
extern void restore_varasm_status PARAMS ((struct function *));
|
||||
extern void free_varasm_status PARAMS ((struct function *));
|
||||
extern void free_emit_status PARAMS ((struct function *));
|
||||
extern void free_stmt_status PARAMS ((struct function *));
|
||||
|
@ -71,19 +71,19 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
|
||||
#endif /* REAL_WIDTH */
|
||||
|
||||
#if REAL_WIDTH == 1
|
||||
# define CONST_DOUBLE_FORMAT "e0ww"
|
||||
# define CONST_DOUBLE_FORMAT "0ww"
|
||||
#else
|
||||
# if REAL_WIDTH == 2
|
||||
# define CONST_DOUBLE_FORMAT "e0ww"
|
||||
# define CONST_DOUBLE_FORMAT "0ww"
|
||||
# else
|
||||
# if REAL_WIDTH == 3
|
||||
# define CONST_DOUBLE_FORMAT "e0www"
|
||||
# define CONST_DOUBLE_FORMAT "0www"
|
||||
# else
|
||||
# if REAL_WIDTH == 4
|
||||
# define CONST_DOUBLE_FORMAT "e0wwww"
|
||||
# define CONST_DOUBLE_FORMAT "0wwww"
|
||||
# else
|
||||
# if REAL_WIDTH == 5
|
||||
# define CONST_DOUBLE_FORMAT "e0wwwww"
|
||||
# define CONST_DOUBLE_FORMAT "0wwwww"
|
||||
# else
|
||||
# define CONST_DOUBLE_FORMAT /* nothing - will cause syntax error */
|
||||
# endif
|
||||
|
12
gcc/rtl.c
12
gcc/rtl.c
@ -30,7 +30,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
|
||||
/* Calculate the format for CONST_DOUBLE. This depends on the relative
|
||||
widths of HOST_WIDE_INT and REAL_VALUE_TYPE.
|
||||
|
||||
We need to go out to e0wwwww, since REAL_ARITHMETIC assumes 16-bits
|
||||
We need to go out to 0wwwww, since REAL_ARITHMETIC assumes 16-bits
|
||||
per element in REAL_VALUE_TYPE.
|
||||
|
||||
This is duplicated in gengenrtl.c.
|
||||
@ -70,19 +70,19 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
|
||||
#endif /* REAL_WIDTH */
|
||||
|
||||
#if REAL_WIDTH == 1
|
||||
# define CONST_DOUBLE_FORMAT "e0ww"
|
||||
# define CONST_DOUBLE_FORMAT "0ww"
|
||||
#else
|
||||
# if REAL_WIDTH == 2
|
||||
# define CONST_DOUBLE_FORMAT "e0ww"
|
||||
# define CONST_DOUBLE_FORMAT "0ww"
|
||||
# else
|
||||
# if REAL_WIDTH == 3
|
||||
# define CONST_DOUBLE_FORMAT "e0www"
|
||||
# define CONST_DOUBLE_FORMAT "0www"
|
||||
# else
|
||||
# if REAL_WIDTH == 4
|
||||
# define CONST_DOUBLE_FORMAT "e0wwww"
|
||||
# define CONST_DOUBLE_FORMAT "0wwww"
|
||||
# else
|
||||
# if REAL_WIDTH == 5
|
||||
# define CONST_DOUBLE_FORMAT "e0wwwww"
|
||||
# define CONST_DOUBLE_FORMAT "0wwwww"
|
||||
# else
|
||||
# define CONST_DOUBLE_FORMAT /* nothing - will cause syntax error */
|
||||
# endif
|
||||
|
@ -560,10 +560,7 @@ DEF_RTL_EXPR(RESX, "resx", "i", 'x')
|
||||
DEF_RTL_EXPR(CONST_INT, "const_int", "w", 'o')
|
||||
|
||||
/* numeric floating point constant.
|
||||
Operand 0 ('e') is the MEM that stores this constant in memory, or
|
||||
various other things (see comments at immed_double_const in
|
||||
varasm.c).
|
||||
Operand 1 ('0') is a chain of all CONST_DOUBLEs in use in the
|
||||
Operand 0 ('0') is a chain of all CONST_DOUBLEs in use in the
|
||||
current function.
|
||||
Remaining operands hold the actual value. They are all 'w' and
|
||||
there may be from 1 to 4; see rtl.c. */
|
||||
|
12
gcc/rtl.h
12
gcc/rtl.h
@ -804,15 +804,11 @@ extern const char * const note_insn_name[NOTE_INSN_MAX - NOTE_INSN_BIAS];
|
||||
For a float, the number of ints varies,
|
||||
and CONST_DOUBLE_LOW is the one that should come first *in memory*.
|
||||
So use &CONST_DOUBLE_LOW(r) as the address of an array of ints. */
|
||||
#define CONST_DOUBLE_LOW(r) XCWINT (r, 2, CONST_DOUBLE)
|
||||
#define CONST_DOUBLE_HIGH(r) XCWINT (r, 3, CONST_DOUBLE)
|
||||
#define CONST_DOUBLE_LOW(r) XCWINT (r, 1, CONST_DOUBLE)
|
||||
#define CONST_DOUBLE_HIGH(r) XCWINT (r, 2, CONST_DOUBLE)
|
||||
|
||||
/* Link for chain of all CONST_DOUBLEs in use in current function. */
|
||||
#define CONST_DOUBLE_CHAIN(r) XCEXP (r, 1, CONST_DOUBLE)
|
||||
/* The MEM which represents this CONST_DOUBLE's value in memory,
|
||||
or const0_rtx if no MEM has been made for it yet,
|
||||
or cc0_rtx if it is not on the chain. */
|
||||
#define CONST_DOUBLE_MEM(r) XCEXP (r, 0, CONST_DOUBLE)
|
||||
#define CONST_DOUBLE_CHAIN(r) XCEXP (r, 0, CONST_DOUBLE)
|
||||
|
||||
/* For a SUBREG rtx, SUBREG_REG extracts the value we want a subreg of.
|
||||
SUBREG_BYTE extracts the byte-number. */
|
||||
@ -1619,7 +1615,7 @@ extern rtx return_address_pointer_rtx;
|
||||
add to this list, modify special_rtx in gengenrtl.c as well. You
|
||||
should also modify gen_rtx to use the special function. */
|
||||
|
||||
extern rtx gen_rtx_CONST_DOUBLE PARAMS ((enum machine_mode, rtx,
|
||||
extern rtx gen_rtx_CONST_DOUBLE PARAMS ((enum machine_mode,
|
||||
HOST_WIDE_INT, HOST_WIDE_INT));
|
||||
extern rtx gen_rtx_CONST_INT PARAMS ((enum machine_mode, HOST_WIDE_INT));
|
||||
extern rtx gen_raw_REG PARAMS ((enum machine_mode, int));
|
||||
|
265
gcc/varasm.c
265
gcc/varasm.c
@ -96,13 +96,10 @@ struct varasm_status
|
||||
|
||||
/* Current offset in constant pool (does not include any machine-specific
|
||||
header). */
|
||||
int x_pool_offset;
|
||||
HOST_WIDE_INT x_pool_offset;
|
||||
|
||||
/* Chain of all CONST_DOUBLE rtx's constructed for the current function.
|
||||
They are chained through the CONST_DOUBLE_CHAIN.
|
||||
A CONST_DOUBLE rtx has CONST_DOUBLE_MEM != cc0_rtx iff it is on this chain.
|
||||
In that case, CONST_DOUBLE_MEM is either a MEM,
|
||||
or const0_rtx if no MEM has been made for this CONST_DOUBLE yet. */
|
||||
They are chained through the CONST_DOUBLE_CHAIN. */
|
||||
rtx x_const_double_chain;
|
||||
};
|
||||
|
||||
@ -135,6 +132,15 @@ int size_directive_output;
|
||||
|
||||
tree last_assemble_variable_decl;
|
||||
|
||||
/* RTX_UNCHANGING_P in a MEM can mean it is stored into, for initialization.
|
||||
So giving constant the alias set for the type will allow such
|
||||
initializations to appear to conflict with the load of the constant. We
|
||||
avoid this by giving all constants an alias set for just constants.
|
||||
Since there will be no stores to that a alias set, nothing will ever
|
||||
conflict with them. */
|
||||
|
||||
static HOST_WIDE_INT const_alias_set;
|
||||
|
||||
static const char *strip_reg_name PARAMS ((const char *));
|
||||
static int contains_pointers_p PARAMS ((tree));
|
||||
static void assemble_real_1 PARAMS ((PTR));
|
||||
@ -2249,7 +2255,7 @@ immed_double_const (i0, i1, mode)
|
||||
return r;
|
||||
|
||||
/* No; make a new one and add it to the chain. */
|
||||
r = gen_rtx_CONST_DOUBLE (mode, const0_rtx, i0, i1);
|
||||
r = gen_rtx_CONST_DOUBLE (mode, i0, i1);
|
||||
|
||||
/* Don't touch const_double_chain if not inside any function. */
|
||||
if (current_function_decl != 0)
|
||||
@ -2277,16 +2283,16 @@ immed_real_const_1 (d, mode)
|
||||
|
||||
u.d = d;
|
||||
|
||||
/* Detect special cases. */
|
||||
if (REAL_VALUES_IDENTICAL (dconst0, d))
|
||||
/* Detect special cases. Check for NaN first, because some ports
|
||||
(specifically the i386) do not emit correct ieee-fp code by default, and
|
||||
thus will generate a core dump here if we pass a NaN to REAL_VALUES_EQUAL
|
||||
and if REAL_VALUES_EQUAL does a floating point comparison. */
|
||||
if (! REAL_VALUE_ISNAN (d) && REAL_VALUES_IDENTICAL (dconst0, d))
|
||||
return CONST0_RTX (mode);
|
||||
|
||||
/* Check for NaN first, because some ports (specifically the i386) do not
|
||||
emit correct ieee-fp code by default, and thus will generate a core
|
||||
dump here if we pass a NaN to REAL_VALUES_EQUAL and if REAL_VALUES_EQUAL
|
||||
does a floating point comparison. */
|
||||
else if (! REAL_VALUE_ISNAN (d) && REAL_VALUES_EQUAL (dconst1, d))
|
||||
return CONST1_RTX (mode);
|
||||
else if (! REAL_VALUE_ISNAN (d) && REAL_VALUES_EQUAL (dconst2, d))
|
||||
return CONST2_RTX (mode);
|
||||
|
||||
if (sizeof u == sizeof (HOST_WIDE_INT))
|
||||
return immed_double_const (u.i[0], 0, mode);
|
||||
@ -2325,12 +2331,6 @@ immed_real_const_1 (d, mode)
|
||||
else
|
||||
CONST_DOUBLE_CHAIN (r) = NULL_RTX;
|
||||
|
||||
/* Store const0_rtx in CONST_DOUBLE_MEM since this CONST_DOUBLE is on the
|
||||
chain, but has not been allocated memory. Actual use of CONST_DOUBLE_MEM
|
||||
is only through force_const_mem. */
|
||||
|
||||
CONST_DOUBLE_MEM (r) = const0_rtx;
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
@ -2352,25 +2352,13 @@ void
|
||||
clear_const_double_mem ()
|
||||
{
|
||||
rtx r, next;
|
||||
enum machine_mode mode;
|
||||
int i;
|
||||
|
||||
for (r = const_double_chain; r; r = next)
|
||||
{
|
||||
next = CONST_DOUBLE_CHAIN (r);
|
||||
CONST_DOUBLE_CHAIN (r) = 0;
|
||||
CONST_DOUBLE_MEM (r) = cc0_rtx;
|
||||
}
|
||||
const_double_chain = 0;
|
||||
|
||||
for (i = 0; i <= 2; i++)
|
||||
for (mode = GET_CLASS_NARROWEST_MODE (MODE_FLOAT); mode != VOIDmode;
|
||||
mode = GET_MODE_WIDER_MODE (mode))
|
||||
{
|
||||
r = const_tiny_rtx[i][(int) mode];
|
||||
CONST_DOUBLE_CHAIN (r) = 0;
|
||||
CONST_DOUBLE_MEM (r) = cc0_rtx;
|
||||
}
|
||||
}
|
||||
|
||||
/* Given an expression EXP with a constant value,
|
||||
@ -3292,8 +3280,9 @@ output_constant_def (exp, defer)
|
||||
int found = 1;
|
||||
int after_function = 0;
|
||||
int labelno = -1;
|
||||
rtx rtl;
|
||||
|
||||
if (TREE_CST_RTL (exp))
|
||||
if (TREE_CODE (exp) != INTEGER_CST && TREE_CST_RTL (exp))
|
||||
return TREE_CST_RTL (exp);
|
||||
|
||||
/* Make sure any other constants whose addresses appear in EXP
|
||||
@ -3328,16 +3317,21 @@ output_constant_def (exp, defer)
|
||||
const_hash_table[hash] = desc;
|
||||
|
||||
/* We have a symbol name; construct the SYMBOL_REF and the MEM. */
|
||||
desc->rtl
|
||||
rtl = desc->rtl
|
||||
= gen_rtx_MEM (TYPE_MODE (TREE_TYPE (exp)),
|
||||
gen_rtx_SYMBOL_REF (Pmode, desc->label));
|
||||
|
||||
set_mem_attributes (desc->rtl, exp, 1);
|
||||
set_mem_attributes (rtl, exp, 1);
|
||||
set_mem_alias_set (rtl, 0);
|
||||
set_mem_alias_set (rtl, const_alias_set);
|
||||
|
||||
found = 0;
|
||||
}
|
||||
else
|
||||
rtl = desc->rtl;
|
||||
|
||||
TREE_CST_RTL (exp) = desc->rtl;
|
||||
if (TREE_CODE (exp) != INTEGER_CST)
|
||||
TREE_CST_RTL (exp) = rtl;
|
||||
|
||||
/* Optionally set flags or add text to the name to record information
|
||||
such as that it is a function name. If the name is changed, the macro
|
||||
@ -3348,7 +3342,7 @@ output_constant_def (exp, defer)
|
||||
if (! found)
|
||||
{
|
||||
ENCODE_SECTION_INFO (exp);
|
||||
desc->rtl = TREE_CST_RTL (exp);
|
||||
desc->rtl = rtl;
|
||||
desc->label = XSTR (XEXP (desc->rtl, 0), 0);
|
||||
}
|
||||
#endif
|
||||
@ -3360,7 +3354,7 @@ output_constant_def (exp, defer)
|
||||
#endif
|
||||
|
||||
if (found
|
||||
&& STRING_POOL_ADDRESS_P (XEXP (desc->rtl, 0))
|
||||
&& STRING_POOL_ADDRESS_P (XEXP (rtl, 0))
|
||||
&& (!defer || defer_addressed_constants_flag || after_function))
|
||||
{
|
||||
defstr = (struct deferred_string **)
|
||||
@ -3372,7 +3366,7 @@ output_constant_def (exp, defer)
|
||||
remove it from deferred string hash table. */
|
||||
found = 0;
|
||||
labelno = (*defstr)->labelno;
|
||||
STRING_POOL_ADDRESS_P (XEXP (desc->rtl, 0)) = 0;
|
||||
STRING_POOL_ADDRESS_P (XEXP (rtl, 0)) = 0;
|
||||
htab_clear_slot (const_str_htab, (void **) defstr);
|
||||
}
|
||||
}
|
||||
@ -3383,8 +3377,9 @@ output_constant_def (exp, defer)
|
||||
{
|
||||
if (defer_addressed_constants_flag || after_function)
|
||||
{
|
||||
struct deferred_constant *p;
|
||||
p = (struct deferred_constant *) xmalloc (sizeof (struct deferred_constant));
|
||||
struct deferred_constant *p
|
||||
= (struct deferred_constant *)
|
||||
xmalloc (sizeof (struct deferred_constant));
|
||||
|
||||
p->exp = copy_constant (exp);
|
||||
p->reloc = reloc;
|
||||
@ -3425,13 +3420,13 @@ output_constant_def (exp, defer)
|
||||
p->label = desc->label;
|
||||
p->labelno = labelno;
|
||||
*defstr = p;
|
||||
STRING_POOL_ADDRESS_P (XEXP (desc->rtl, 0)) = 1;
|
||||
STRING_POOL_ADDRESS_P (XEXP (rtl, 0)) = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return TREE_CST_RTL (exp);
|
||||
return rtl;
|
||||
}
|
||||
|
||||
/* Now output assembler code to define the label for EXP,
|
||||
@ -3494,12 +3489,11 @@ struct pool_constant
|
||||
{
|
||||
struct constant_descriptor *desc;
|
||||
struct pool_constant *next, *next_sym;
|
||||
const char *label;
|
||||
rtx constant;
|
||||
enum machine_mode mode;
|
||||
int labelno;
|
||||
int align;
|
||||
int offset;
|
||||
unsigned int align;
|
||||
HOST_WIDE_INT offset;
|
||||
int mark;
|
||||
};
|
||||
|
||||
@ -3530,23 +3524,6 @@ init_varasm_status (f)
|
||||
p->x_const_double_chain = 0;
|
||||
}
|
||||
|
||||
/* Nested functions diddle with our const_double_chain via
|
||||
clear_const_double_mem and const_tiny_rtx. Remove these
|
||||
entries from our const_double_chain. */
|
||||
|
||||
void
|
||||
restore_varasm_status (f)
|
||||
struct function *f;
|
||||
{
|
||||
rtx *p = &f->varasm->x_const_double_chain;
|
||||
|
||||
while (*p)
|
||||
if (CONST_DOUBLE_MEM (*p) == cc0_rtx)
|
||||
*p = CONST_DOUBLE_CHAIN (*p);
|
||||
else
|
||||
p = &CONST_DOUBLE_CHAIN (*p);
|
||||
}
|
||||
|
||||
/* Mark PC for GC. */
|
||||
|
||||
static void
|
||||
@ -3557,6 +3534,7 @@ mark_pool_constant (pc)
|
||||
{
|
||||
ggc_mark (pc);
|
||||
ggc_mark_rtx (pc->constant);
|
||||
ggc_mark_rtx (pc->desc->rtl);
|
||||
pc = pc->next;
|
||||
}
|
||||
}
|
||||
@ -3590,19 +3568,22 @@ free_varasm_status (f)
|
||||
/* Clear out the hash tables. */
|
||||
for (i = 0; i < MAX_RTX_HASH_TABLE; ++i)
|
||||
{
|
||||
struct constant_descriptor* cd;
|
||||
struct constant_descriptor *cd;
|
||||
|
||||
cd = p->x_const_rtx_hash_table[i];
|
||||
while (cd) {
|
||||
struct constant_descriptor* next = cd->next;
|
||||
free (cd);
|
||||
cd = next;
|
||||
}
|
||||
while (cd)
|
||||
{
|
||||
struct constant_descriptor *next = cd->next;
|
||||
|
||||
free (cd);
|
||||
cd = next;
|
||||
}
|
||||
}
|
||||
|
||||
free (p->x_const_rtx_hash_table);
|
||||
free (p->x_const_rtx_sym_hash_table);
|
||||
free (p);
|
||||
|
||||
f->varasm = NULL;
|
||||
}
|
||||
|
||||
@ -3786,116 +3767,77 @@ force_const_mem (mode, x)
|
||||
int hash;
|
||||
struct constant_descriptor *desc;
|
||||
char label[256];
|
||||
const char *found = 0;
|
||||
rtx def;
|
||||
|
||||
/* If we want this CONST_DOUBLE in the same mode as it is in memory
|
||||
(this will always be true for floating CONST_DOUBLEs that have been
|
||||
placed in memory, but not for VOIDmode (integer) CONST_DOUBLEs),
|
||||
use the previous copy. Otherwise, make a new one. Note that in
|
||||
the unlikely event that this same CONST_DOUBLE is used in two different
|
||||
modes in an alternating fashion, we will allocate a lot of different
|
||||
memory locations, but this should be extremely rare. */
|
||||
|
||||
if (GET_CODE (x) == CONST_DOUBLE
|
||||
&& GET_CODE (CONST_DOUBLE_MEM (x)) == MEM
|
||||
&& GET_MODE (CONST_DOUBLE_MEM (x)) == mode)
|
||||
return CONST_DOUBLE_MEM (x);
|
||||
struct pool_constant *pool;
|
||||
unsigned int align;
|
||||
|
||||
/* Compute hash code of X. Search the descriptors for that hash code
|
||||
to see if any of them describes X. If yes, the descriptor records
|
||||
the label number already assigned. */
|
||||
|
||||
to see if any of them describes X. If yes, we have an rtx to use. */
|
||||
hash = const_hash_rtx (mode, x);
|
||||
|
||||
for (desc = const_rtx_hash_table[hash]; desc; desc = desc->next)
|
||||
if (compare_constant_rtx (mode, x, desc))
|
||||
{
|
||||
found = desc->label;
|
||||
break;
|
||||
}
|
||||
return desc->rtl;
|
||||
|
||||
if (found == 0)
|
||||
{
|
||||
struct pool_constant *pool;
|
||||
int align;
|
||||
|
||||
/* No constant equal to X is known to have been output.
|
||||
Make a constant descriptor to enter X in the hash table.
|
||||
Assign the label number and record it in the descriptor for
|
||||
future calls to this function to find. */
|
||||
|
||||
desc = record_constant_rtx (mode, x);
|
||||
desc->next = const_rtx_hash_table[hash];
|
||||
const_rtx_hash_table[hash] = desc;
|
||||
|
||||
/* Align the location counter as required by EXP's data type. */
|
||||
align = GET_MODE_ALIGNMENT (mode == VOIDmode ? word_mode : mode);
|
||||
/* No constant equal to X is known to have been output.
|
||||
Make a constant descriptor to enter X in the hash table
|
||||
and make a MEM for it. */
|
||||
desc = record_constant_rtx (mode, x);
|
||||
desc->next = const_rtx_hash_table[hash];
|
||||
const_rtx_hash_table[hash] = desc;
|
||||
|
||||
/* Align the location counter as required by EXP's data type. */
|
||||
align = GET_MODE_ALIGNMENT (mode == VOIDmode ? word_mode : mode);
|
||||
#ifdef CONSTANT_ALIGNMENT
|
||||
align = CONSTANT_ALIGNMENT (make_tree (type_for_mode (mode, 0), x),
|
||||
align);
|
||||
align = CONSTANT_ALIGNMENT (make_tree (type_for_mode (mode, 0), x), align);
|
||||
#endif
|
||||
|
||||
pool_offset += (align / BITS_PER_UNIT) - 1;
|
||||
pool_offset &= ~ ((align / BITS_PER_UNIT) - 1);
|
||||
pool_offset += (align / BITS_PER_UNIT) - 1;
|
||||
pool_offset &= ~ ((align / BITS_PER_UNIT) - 1);
|
||||
|
||||
if (GET_CODE (x) == LABEL_REF)
|
||||
LABEL_PRESERVE_P (XEXP (x, 0)) = 1;
|
||||
if (GET_CODE (x) == LABEL_REF)
|
||||
LABEL_PRESERVE_P (XEXP (x, 0)) = 1;
|
||||
|
||||
/* Allocate a pool constant descriptor, fill it in, and chain it in. */
|
||||
/* Allocate a pool constant descriptor, fill it in, and chain it in. */
|
||||
pool = (struct pool_constant *) ggc_alloc (sizeof (struct pool_constant));
|
||||
pool->desc = desc;
|
||||
pool->constant = x;
|
||||
pool->mode = mode;
|
||||
pool->labelno = const_labelno;
|
||||
pool->align = align;
|
||||
pool->offset = pool_offset;
|
||||
pool->mark = 1;
|
||||
pool->next = 0;
|
||||
|
||||
pool = (struct pool_constant *) ggc_alloc (sizeof (struct pool_constant));
|
||||
pool->desc = desc;
|
||||
pool->constant = x;
|
||||
pool->mode = mode;
|
||||
pool->labelno = const_labelno;
|
||||
pool->align = align;
|
||||
pool->offset = pool_offset;
|
||||
pool->mark = 1;
|
||||
pool->next = 0;
|
||||
if (last_pool == 0)
|
||||
first_pool = pool;
|
||||
else
|
||||
last_pool->next = pool;
|
||||
|
||||
last_pool = pool;
|
||||
pool_offset += GET_MODE_SIZE (mode);
|
||||
|
||||
if (last_pool == 0)
|
||||
first_pool = pool;
|
||||
else
|
||||
last_pool->next = pool;
|
||||
/* Create a string containing the label name, in LABEL. */
|
||||
ASM_GENERATE_INTERNAL_LABEL (label, "LC", const_labelno);
|
||||
|
||||
last_pool = pool;
|
||||
pool_offset += GET_MODE_SIZE (mode);
|
||||
++const_labelno;
|
||||
|
||||
/* Create a string containing the label name, in LABEL. */
|
||||
ASM_GENERATE_INTERNAL_LABEL (label, "LC", const_labelno);
|
||||
/* Construct the SYMBOL_REF and the MEM. */
|
||||
|
||||
++const_labelno;
|
||||
|
||||
desc->label = found = ggc_strdup (label);
|
||||
|
||||
/* Add label to symbol hash table. */
|
||||
hash = SYMHASH (found);
|
||||
pool->label = found;
|
||||
pool->next_sym = const_rtx_sym_hash_table[hash];
|
||||
const_rtx_sym_hash_table[hash] = pool;
|
||||
}
|
||||
|
||||
/* We have a symbol name; construct the SYMBOL_REF and the MEM. */
|
||||
|
||||
def = gen_rtx_MEM (mode, gen_rtx_SYMBOL_REF (Pmode, found));
|
||||
pool->desc->rtl = def
|
||||
= gen_rtx_MEM (mode, gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (label)));
|
||||
set_mem_alias_set (def, const_alias_set);
|
||||
set_mem_attributes (def, type_for_mode (mode, 0), 1);
|
||||
RTX_UNCHANGING_P (def) = 1;
|
||||
|
||||
/* Add label to symbol hash table. */
|
||||
hash = SYMHASH (XSTR (XEXP (def, 0), 0));
|
||||
pool->next_sym = const_rtx_sym_hash_table[hash];
|
||||
const_rtx_sym_hash_table[hash] = pool;
|
||||
|
||||
/* Mark the symbol_ref as belonging to this constants pool. */
|
||||
CONSTANT_POOL_ADDRESS_P (XEXP (def, 0)) = 1;
|
||||
current_function_uses_const_pool = 1;
|
||||
|
||||
if (GET_CODE (x) == CONST_DOUBLE)
|
||||
{
|
||||
if (CONST_DOUBLE_MEM (x) == cc0_rtx)
|
||||
{
|
||||
CONST_DOUBLE_CHAIN (x) = const_double_chain;
|
||||
const_double_chain = x;
|
||||
}
|
||||
CONST_DOUBLE_MEM (x) = def;
|
||||
}
|
||||
|
||||
return def;
|
||||
}
|
||||
|
||||
@ -3912,7 +3854,7 @@ find_pool_constant (f, addr)
|
||||
|
||||
for (pool = f->varasm->x_const_rtx_sym_hash_table[SYMHASH (label)]; pool;
|
||||
pool = pool->next_sym)
|
||||
if (pool->label == label)
|
||||
if (XSTR (XEXP (pool->desc->rtl, 0), 0) == label)
|
||||
return pool;
|
||||
|
||||
abort ();
|
||||
@ -4131,10 +4073,6 @@ mark_constants (x)
|
||||
mark_constant (&x, NULL);
|
||||
return;
|
||||
}
|
||||
/* Never search inside a CONST_DOUBLE, because CONST_DOUBLE_MEM may be
|
||||
a MEM, but does not constitute a use of that MEM. */
|
||||
else if (GET_CODE (x) == CONST_DOUBLE)
|
||||
return;
|
||||
|
||||
/* Insns may appear inside a SEQUENCE. Only check the patterns of
|
||||
insns, not any notes that may be attached. We don't want to mark
|
||||
@ -4182,7 +4120,7 @@ mark_constants (x)
|
||||
|
||||
/* Given a SYMBOL_REF CURRENT_RTX, mark it and all constants it refers
|
||||
to as used. Emit referenced deferred strings. This function can
|
||||
be used with for_each_rtx () to mark all SYMBOL_REFs in an rtx. */
|
||||
be used with for_each_rtx to mark all SYMBOL_REFs in an rtx. */
|
||||
|
||||
static int
|
||||
mark_constant (current_rtx, data)
|
||||
@ -4193,10 +4131,7 @@ mark_constant (current_rtx, data)
|
||||
|
||||
if (x == NULL_RTX)
|
||||
return 0;
|
||||
else if (GET_CODE(x) == CONST_DOUBLE)
|
||||
/* Never search inside a CONST_DOUBLE because CONST_DOUBLE_MEM may
|
||||
be a MEM but does not constitute a use of that MEM. */
|
||||
return -1;
|
||||
|
||||
else if (GET_CODE (x) == SYMBOL_REF)
|
||||
{
|
||||
if (CONSTANT_POOL_ADDRESS_P (x))
|
||||
@ -5185,6 +5120,8 @@ init_varasm_once ()
|
||||
mark_const_hash_entry);
|
||||
ggc_add_root (&const_str_htab, 1, sizeof const_str_htab,
|
||||
mark_const_str_htab);
|
||||
|
||||
const_alias_set = new_alias_set ();
|
||||
}
|
||||
|
||||
/* Select a set of attributes for section NAME based on the properties
|
||||
|
Loading…
Reference in New Issue
Block a user