varasm.c (output_constant_def): Split out two new static functions...

* varasm.c (output_constant_def): Split out two new static
	functions, build_constant_desc and maybe_output_constant_def_contents.
	Restructure for comprehensibility.  Don't call
	output_addressed_constants.  Treat defstr being non-NULL for
	STRING_POOL_ADDRESS_P constants as an invariant.
	(struct deferred_string): Remove labelno field.
	(output_constant_def_contents): Kill labelno argument.  Call
	output_addressed_constants here.  Use ASM_OUTPUT_LABEL, not
	asm_out.internal_label.
	(mark_constant): Update call to output_constant_def_contents.
	Treat defstr being non-NULL for STRING_POOL_ADDRESS_P
	constants as an invariant.

From-SVN: r66129
This commit is contained in:
Zack Weinberg 2003-04-27 03:50:27 +00:00
parent 12969f45d3
commit 293107d161
2 changed files with 191 additions and 165 deletions

View File

@ -1,3 +1,18 @@
2003-04-26 Zack Weinberg <zack@codesourcery.com>
* varasm.c (output_constant_def): Split out two new static
functions, build_constant_desc and maybe_output_constant_def_contents.
Restructure for comprehensibility. Don't call
output_addressed_constants. Treat defstr being non-NULL for
STRING_POOL_ADDRESS_P constants as an invariant.
(struct deferred_string): Remove labelno field.
(output_constant_def_contents): Kill labelno argument. Call
output_addressed_constants here. Use ASM_OUTPUT_LABEL, not
asm_out.internal_label.
(mark_constant): Update call to output_constant_def_contents.
Treat defstr being non-NULL for STRING_POOL_ADDRESS_P
constants as an invariant.
2003-04-26 Richard Henderson <rth@redhat.com>
* config/i386/i386.c (output_pic_addr_const): Use SYMBOL_REF_LOCAL_P.
@ -88,9 +103,9 @@
2003-04-25 Richard Henderson <rth@redhat.com>
PR opt/10315
* config/rs6000/rs6000.c (rs6000_emit_move): Only elide proper
checks during reload; use validize_mem instead of adjust_address.
PR opt/10315
* config/rs6000/rs6000.c (rs6000_emit_move): Only elide proper
checks during reload; use validize_mem instead of adjust_address.
2003-04-26 Ben Elliston <bje@wasabisystems.com>
@ -115,14 +130,14 @@
2003-04-24 Alexander Kabaev <kan@FreeBSD.ORG>
* config/sparc/sparc.md (umulsidi3, mulsidi3): Avoid using
const_umulsidi3_sp32 and const_mulsidi3_sp32 on 64bit targets
const_umulsidi3_sp32 and const_mulsidi3_sp32 on 64bit targets
where they might be not present. Use their _sp64 equivalent
instead.
Thu Apr 24 20:42:12 CEST 2003 Jan Hubicka <jh@suse.cz>
* i386.md (cvtsi2sdq): Fix typo in previous patch.
2003-04-24 Krister Walfridsson <cato@df.lth.se>
* configure.in: Check whether mbstowcs works.
@ -156,7 +171,7 @@ Thu Apr 24 16:55:26 CEST 2003 Jan Hubicka <jh@suse.cz>
PR c/10308
* reload.c (find_reloads_address_1): Reload plus at the place of
index register.
2003-04-24 Nathan Sidwell <nathan@codesourcery.com>
New GCOV_TAG_FUNCTION layout
@ -334,14 +349,14 @@ Thu Apr 24 16:55:26 CEST 2003 Jan Hubicka <jh@suse.cz>
2003-04-22 Richard Henderson <rth@redhat.com>
PR 8866
* rtl.h (MEM_NOTRAP_P): New.
(MEM_COPY_ATTRIBUTES): Copy it.
* rtlanal.c (may_trap_p): Check it.
* expr.c (do_tablejump): Set it.
PR 8866
* rtl.h (MEM_NOTRAP_P): New.
(MEM_COPY_ATTRIBUTES): Copy it.
* rtlanal.c (may_trap_p): Check it.
* expr.c (do_tablejump): Set it.
* doc/rtl.texi (Flags): Document it.
* cfgrtl.c (try_redirect_by_replacing_jump): Revert last three changes.
* cfgrtl.c (try_redirect_by_replacing_jump): Revert last three changes.
2003-04-22 Olivier Hainque <hainque@act-europe.fr>
@ -350,12 +365,12 @@ Thu Apr 24 16:55:26 CEST 2003 Jan Hubicka <jh@suse.cz>
2003-04-22 Vincent Celier <celier@gnat.com>
* gthr-gnat.h, gthr-gnat.c: new sources for implementation of
--enable-threads=gnat.
* Makefile.in: Add gthr-gnat.c to LIB2ADDEH.
* configure.in: Add gnat to the list of thread packages
* configure: Rebuild.
* config/t-linux: Add gthr-gnat.c to LIB2ADDEH and LIB2ADDEHDEP
* gthr-gnat.h, gthr-gnat.c: new sources for implementation of
--enable-threads=gnat.
* Makefile.in: Add gthr-gnat.c to LIB2ADDEH.
* configure.in: Add gnat to the list of thread packages
* configure: Rebuild.
* config/t-linux: Add gthr-gnat.c to LIB2ADDEH and LIB2ADDEHDEP
2003-04-22 Neil Booth <neil@daikokuya.co.uk>
@ -366,7 +381,7 @@ Thu Apr 24 16:55:26 CEST 2003 Jan Hubicka <jh@suse.cz>
* cpptrad.c (_cpp_replacement_text_len): Add check for macro
parameter count.
(_cpp_copy_replacement_text): Same.
2003-04-22 Neil Booth <neil@daikokuya.co.uk>
* c-lex.c (c_lex): Handle CPP_OTHER differently.
@ -397,9 +412,9 @@ Thu Apr 24 16:55:26 CEST 2003 Jan Hubicka <jh@suse.cz>
2003-04-22 Aldy Hernandez <aldyh@redhat.com>
* config/rs6000/t-spe: Merge in t-fprules into file.
* config/rs6000/t-spe: Merge in t-fprules into file.
* config.gcc: Add t-spe to powerpc-eabispe.
* config.gcc: Add t-spe to powerpc-eabispe.
2003-04-22 Kean Johnston <jkj@sco.com>
@ -433,8 +448,8 @@ Thu Apr 24 16:55:26 CEST 2003 Jan Hubicka <jh@suse.cz>
2003-04-21 Aldy Hernandez <aldyh@redhat.com>
* config/rs6000/rs6000.c (rs6000_override_options): No SPE means
64-bit long doubles.
* config/rs6000/rs6000.c (rs6000_override_options): No SPE means
64-bit long doubles.
2003-04-21 Olivier Hainque <hainque@act-europe.fr>
@ -446,7 +461,7 @@ Thu Apr 24 16:55:26 CEST 2003 Jan Hubicka <jh@suse.cz>
nested subprograms.
* expmed.c (extract_bit_field): Reverse operands of && condition to
prevent a potential division by zero in the previously first branch.
prevent a potential division by zero in the previously first branch.
* config/pa/pa.md (extv, extzv): FAIL if the bitfield length is zero.
2003-04-21 Joel Brobecker <brobecker@gnat.com>
@ -458,34 +473,34 @@ Thu Apr 24 16:55:26 CEST 2003 Jan Hubicka <jh@suse.cz>
2003-04-21 Nathan Sidwell <nathan@codesourcery.com>
Break out coverage routines to new file.
* Makefile.in (COVERAGE_H): New variable
(C_OBJS): Add coverage.o
(coverage.o): New target.
(profile.o, loop-init.o, sched-ebb.o, predict.o, tracer.o): Adjust
dependencies.
(GTFILES): Adjust.
(gt-coverage.h): New target.
(gt-profile.h): Remove.
* profile.h: Remove. Move to ...
* coverage.h: ... here. New. #include gcov-io.h.
* gcov-io.h: Move function definitions to ...
* gcov-io.c: ... here. New.
* profile.c: Move coverage routines to coverage.c.
(instrument_edges, get_exec_counts, branch_prob, init_branch_prob,
end_branch_prob): Adjust.
* coverage.c: New. Coverage routines from profile.c
(coverage_counter_ref, coverage_init, coverage_finish,
coverage_end_function, coverage_begin_output,
coverage_counter_ref, get_coverage_counts): Define.
* gcov-dump.c, gcov.c: #include gcov-io.c.
* libgcov.c: Likewise. Adjust.
* loop-init.c: Don't #include profile.h
* tracer.c, predict.c, sched-ebb.c: Adjust #includes.
* rtl.h: Add coverage prototypes.
* toplev.c (compile_file): Init coverage, not branch_prob.
Always call coverage_finish.
(rest_of_compilation): Call coverage_end_function.
Break out coverage routines to new file.
* Makefile.in (COVERAGE_H): New variable
(C_OBJS): Add coverage.o
(coverage.o): New target.
(profile.o, loop-init.o, sched-ebb.o, predict.o, tracer.o): Adjust
dependencies.
(GTFILES): Adjust.
(gt-coverage.h): New target.
(gt-profile.h): Remove.
* profile.h: Remove. Move to ...
* coverage.h: ... here. New. #include gcov-io.h.
* gcov-io.h: Move function definitions to ...
* gcov-io.c: ... here. New.
* profile.c: Move coverage routines to coverage.c.
(instrument_edges, get_exec_counts, branch_prob, init_branch_prob,
end_branch_prob): Adjust.
* coverage.c: New. Coverage routines from profile.c
(coverage_counter_ref, coverage_init, coverage_finish,
coverage_end_function, coverage_begin_output,
coverage_counter_ref, get_coverage_counts): Define.
* gcov-dump.c, gcov.c: #include gcov-io.c.
* libgcov.c: Likewise. Adjust.
* loop-init.c: Don't #include profile.h
* tracer.c, predict.c, sched-ebb.c: Adjust #includes.
* rtl.h: Add coverage prototypes.
* toplev.c (compile_file): Init coverage, not branch_prob.
Always call coverage_finish.
(rest_of_compilation): Call coverage_end_function.
2003-04-21 Matt Kraai <kraai@alumni.cmu.edu>
@ -506,10 +521,10 @@ Thu Apr 24 16:55:26 CEST 2003 Jan Hubicka <jh@suse.cz>
* cpplib.h (struct cpp_callbacks): Change prototype of include.
2003-04-21 Richard Kenner <kenner@vlsi1.ultra.nyu.edu>
* doc/rtl.texi (RTX_UNCHANGING_P): Point to true_dependence for
details of conflict handling.
* fold-const.c (extract_muldiv, case CONVERT_EXPR): Detect case
when conversion overflows.
@ -525,7 +540,7 @@ Thu Apr 24 16:55:26 CEST 2003 Jan Hubicka <jh@suse.cz>
2003-04-21 Andreas Jaeger <aj@suse.de>
* cppcharset.c (_cpp_valid_ucn): Cast field precision to int.
* cppcharset.c (_cpp_valid_ucn): Cast field precision to int.
2003-04-20 Chris Lattner <sabre@nondot.org>
Zack Weinberg <zack@codesourcery.com>
@ -921,7 +936,7 @@ Fri Apr 18 01:28:51 CEST 2003 Jan Hubicka <jh@suse.cz>
* emit-rtl.c (subreg_hard_regno): Check that register is
representable.
* reload.c (reload_inner_reg_of_subreg): When register is not
representable, reload the whole thing.
(find_reloads): Likewsie.

View File

@ -142,7 +142,8 @@ static unsigned int const_hash PARAMS ((tree));
static unsigned int const_hash_1 PARAMS ((tree));
static int compare_constant PARAMS ((tree, tree));
static tree copy_constant PARAMS ((tree));
static void output_constant_def_contents PARAMS ((tree, int, int));
static void maybe_output_constant_def_contents PARAMS ((tree, rtx, int));
static void output_constant_def_contents PARAMS ((tree, const char *));
static void decode_rtx_const PARAMS ((enum machine_mode, rtx,
struct rtx_const *));
static unsigned int const_hash_rtx PARAMS ((enum machine_mode, rtx));
@ -2164,6 +2165,8 @@ struct constant_descriptor_tree GTY(())
static GTY(()) struct constant_descriptor_tree *
const_hash_table[MAX_HASH_TABLE];
static struct constant_descriptor_tree * build_constant_desc PARAMS ((tree));
/* We maintain a hash table of STRING_CST values. Unless we are asked to force
out a string constant, we defer output of the constants until we know
they are actually used. This will be if something takes its address or if
@ -2175,7 +2178,6 @@ struct deferred_string GTY(())
{
const char *label;
tree exp;
int labelno;
};
static GTY ((param_is (struct deferred_string))) htab_t const_str_htab;
@ -2533,6 +2535,51 @@ copy_constant (exp)
}
}
/* Subroutine of output_constant_def:
No constant equal to EXP is known to have been output.
Make a constant descriptor to enter EXP in the hash table.
Assign the label number and construct RTL to refer to the
constant's location in memory.
Caller is responsible for updating the hash table. */
static struct constant_descriptor_tree *
build_constant_desc (exp)
tree exp;
{
rtx symbol;
rtx rtl;
char label[256];
int labelno;
struct constant_descriptor_tree *desc;
desc = ggc_alloc (sizeof (*desc));
desc->value = copy_constant (exp);
/* Create a string containing the label name, in LABEL. */
labelno = const_labelno++;
ASM_GENERATE_INTERNAL_LABEL (label, "LC", labelno);
/* We have a symbol name; construct the SYMBOL_REF and the MEM. */
symbol = gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (label));
SYMBOL_REF_FLAGS (symbol) = SYMBOL_FLAG_LOCAL;
rtl = gen_rtx_MEM (TYPE_MODE (TREE_TYPE (exp)), symbol);
set_mem_attributes (rtl, exp, 1);
set_mem_alias_set (rtl, 0);
set_mem_alias_set (rtl, const_alias_set);
/* Set flags or add text to the name to record information, such as
that it is a local symbol. If the name is changed, the macro
ASM_OUTPUT_LABELREF will have to know how to strip this
information. */
(*targetm.encode_section_info) (exp, rtl, true);
desc->rtl = rtl;
desc->label = XSTR (XEXP (desc->rtl, 0), 0);
return desc;
}
/* Return an rtx representing a reference to constant data in memory
for the constant expression EXP.
@ -2554,12 +2601,6 @@ output_constant_def (exp, defer)
{
int hash;
struct constant_descriptor_tree *desc;
struct deferred_string **defstr;
char label[256];
int reloc;
int found = 1;
int labelno = -1;
rtx rtl;
/* We can't just use the saved RTL if this is a deferred string constant
and we are not to defer anymore. */
@ -2567,133 +2608,102 @@ output_constant_def (exp, defer)
&& (defer || !STRING_POOL_ADDRESS_P (XEXP (TREE_CST_RTL (exp), 0))))
return TREE_CST_RTL (exp);
/* Make sure any other constants whose addresses appear in EXP
are assigned label numbers. */
reloc = output_addressed_constants (exp);
/* Compute hash code of EXP. Search the descriptors for that hash code
to see if any of them describes EXP. If yes, the descriptor records
the label number already assigned. */
hash = const_hash (exp);
for (desc = const_hash_table[hash]; desc; desc = desc->next)
if (compare_constant (exp, desc->value))
break;
if (desc == 0)
{
rtx symbol;
/* No constant equal to EXP is known to have been output.
Make a constant descriptor to enter EXP in the hash table.
Assign the label number and record it in the descriptor for
future calls to this function to find. */
/* Create a string containing the label name, in LABEL. */
labelno = const_labelno++;
ASM_GENERATE_INTERNAL_LABEL (label, "LC", labelno);
desc = ggc_alloc (sizeof (*desc));
desc = build_constant_desc (exp);
desc->next = const_hash_table[hash];
desc->label = ggc_strdup (label);
desc->value = copy_constant (exp);
const_hash_table[hash] = desc;
/* We have a symbol name; construct the SYMBOL_REF and the MEM. */
symbol = gen_rtx_SYMBOL_REF (Pmode, desc->label);
SYMBOL_REF_FLAGS (symbol) = SYMBOL_FLAG_LOCAL;
rtl = desc->rtl = gen_rtx_MEM (TYPE_MODE (TREE_TYPE (exp)), symbol);
set_mem_attributes (rtl, exp, 1);
set_mem_alias_set (rtl, 0);
set_mem_alias_set (rtl, const_alias_set);
found = 0;
maybe_output_constant_def_contents (exp, desc->rtl, defer);
}
else
rtl = 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
ASM_OUTPUT_LABELREF will have to know how to strip this information. */
/* A previously-processed constant would already have section info
encoded in it. */
if (! found)
else if (!defer && STRING_POOL_ADDRESS_P (XEXP (desc->rtl, 0)))
{
(*targetm.encode_section_info) (exp, rtl, true);
/* If the string is currently deferred but we need to output it
now, remove it from the deferred string hash table. */
struct deferred_string **defstr;
desc->rtl = rtl;
desc->label = XSTR (XEXP (desc->rtl, 0), 0);
}
if (found && !defer && STRING_POOL_ADDRESS_P (XEXP (rtl, 0)))
{
defstr = (struct deferred_string **)
htab_find_slot_with_hash (const_str_htab, desc->label,
STRHASH (desc->label), NO_INSERT);
#ifdef ENABLE_CHECKING
if (!defstr)
abort ();
#endif
STRING_POOL_ADDRESS_P (XEXP (desc->rtl, 0)) = 0;
htab_clear_slot (const_str_htab, (void **) defstr);
maybe_output_constant_def_contents (exp, desc->rtl, 0);
}
TREE_CST_RTL (exp) = desc->rtl;
return desc->rtl;
}
/* Subroutine of output_constant_def:
Decide whether or not to defer the output of EXP, which can be
accesed through rtl RTL, and either do the output or record EXP in
the table of deferred strings. */
static void
maybe_output_constant_def_contents (exp, rtl, defer)
tree exp;
rtx rtl;
int defer;
{
const char *label;
if (flag_syntax_only)
return;
label = XSTR (XEXP (rtl, 0), 0);
if (defer && TREE_CODE (exp) == STRING_CST && !flag_writable_strings)
{
struct deferred_string **defstr;
defstr = (struct deferred_string **)
htab_find_slot_with_hash (const_str_htab, label,
STRHASH (label), INSERT);
if (defstr)
{
/* If the string is currently deferred but we need to output it now,
remove it from deferred string hash table. */
found = 0;
labelno = (*defstr)->labelno;
STRING_POOL_ADDRESS_P (XEXP (rtl, 0)) = 0;
htab_clear_slot (const_str_htab, (void **) defstr);
struct deferred_string *p;
p = (struct deferred_string *)
ggc_alloc (sizeof (struct deferred_string));
p->exp = exp;
p->label = label;
*defstr = p;
STRING_POOL_ADDRESS_P (XEXP (rtl, 0)) = 1;
return;
}
}
/* If this is the first time we've seen this particular constant,
output it. Do no output if -fsyntax-only. */
if (! found && ! flag_syntax_only)
{
if (!defer || TREE_CODE (exp) != STRING_CST
|| flag_writable_strings)
output_constant_def_contents (exp, reloc, labelno);
else
{
defstr = (struct deferred_string **)
htab_find_slot_with_hash (const_str_htab, desc->label,
STRHASH (desc->label), INSERT);
if (!defstr)
output_constant_def_contents (exp, reloc, labelno);
else
{
struct deferred_string *p;
p = (struct deferred_string *)
ggc_alloc (sizeof (struct deferred_string));
p->exp = desc->value;
p->label = desc->label;
p->labelno = labelno;
*defstr = p;
STRING_POOL_ADDRESS_P (XEXP (rtl, 0)) = 1;
}
}
}
return rtl;
output_constant_def_contents (exp, label);
}
/* Now output assembler code to define the label for EXP,
and follow it with the data of EXP. */
static void
output_constant_def_contents (exp, reloc, labelno)
output_constant_def_contents (exp, label)
tree exp;
int reloc;
int labelno;
const char *label;
{
int align;
/* Make sure any other constants whose addresses appear in EXP
are assigned label numbers. */
int reloc = output_addressed_constants (exp);
/* Align the location counter as required by EXP's data type. */
align = TYPE_ALIGN (TREE_TYPE (exp));
int align = TYPE_ALIGN (TREE_TYPE (exp));
#ifdef CONSTANT_ALIGNMENT
align = CONSTANT_ALIGNMENT (exp, align);
#endif
@ -2709,7 +2719,7 @@ output_constant_def_contents (exp, reloc, labelno)
}
/* Output the label itself. */
(*targetm.asm_out.internal_label) (asm_out_file, "LC", labelno);
ASM_OUTPUT_LABEL (asm_out_file, label);
/* Output the value of EXP. */
output_constant (exp,
@ -3521,19 +3531,20 @@ mark_constant (current_rtx, data)
}
else if (STRING_POOL_ADDRESS_P (x))
{
struct deferred_string **defstr;
struct deferred_string *p, **defstr;
defstr = (struct deferred_string **)
htab_find_slot_with_hash (const_str_htab, XSTR (x, 0),
STRHASH (XSTR (x, 0)), NO_INSERT);
if (defstr)
{
struct deferred_string *p = *defstr;
#ifdef ENABLE_CHECKING
if (!defstr)
abort ();
#endif
STRING_POOL_ADDRESS_P (x) = 0;
output_constant_def_contents (p->exp, 0, p->labelno);
htab_clear_slot (const_str_htab, (void **) defstr);
}
p = *defstr;
STRING_POOL_ADDRESS_P (x) = 0;
output_constant_def_contents (p->exp, p->label);
htab_clear_slot (const_str_htab, (void **) defstr);
}
}
return 0;