Commit c9250371 by Richard Sandiford Committed by Richard Sandiford

Remove global call sets: DF (EH edges)

The DF dense_invalidated_by_call and sparse_invalidated_by_call
sets are actually only used on EH edges, and so are more the set
of registers that are invalidated by a taken EH edge.  Under the
new order, that means that they describe eh_edge_abi.

2019-09-30  Richard Sandiford  <richard.sandiford@arm.com>

gcc/
	* df-problems.c: Include regs.h and function-abi.h.
	(df_rd_problem_data): Rename sparse_invalidated_by_call to
	sparse_invalidated_by_eh and dense_invalidated_by_call to
	dense_invalidated_by_eh.
	(df_print_bb_index): Update accordingly.
	(df_rd_alloc, df_rd_start_dump, df_rd_confluence_n): Likewise.
	(df_lr_confluence_n): Use eh_edge_abi to get the set of registers
	that are clobbered by an EH edge.  Clobber partially-clobbered
	registers as well as fully-clobbered ones.
	(df_md_confluence_n): Likewise.
	(df_rd_local_compute): Likewise.  Update for changes to
	df_rd_problem_data.
	* df-scan.c (df_scan_start_dump): Use eh_edge_abi to get the set
	of registers that are clobbered by an EH edge.  Includde partially-
	clobbered registers as well as fully-clobbered ones.

From-SVN: r276319
parent 3bd29185
2019-09-30 Richard Sandiford <richard.sandiford@arm.com> 2019-09-30 Richard Sandiford <richard.sandiford@arm.com>
* df-problems.c: Include regs.h and function-abi.h.
(df_rd_problem_data): Rename sparse_invalidated_by_call to
sparse_invalidated_by_eh and dense_invalidated_by_call to
dense_invalidated_by_eh.
(df_print_bb_index): Update accordingly.
(df_rd_alloc, df_rd_start_dump, df_rd_confluence_n): Likewise.
(df_lr_confluence_n): Use eh_edge_abi to get the set of registers
that are clobbered by an EH edge. Clobber partially-clobbered
registers as well as fully-clobbered ones.
(df_md_confluence_n): Likewise.
(df_rd_local_compute): Likewise. Update for changes to
df_rd_problem_data.
* df-scan.c (df_scan_start_dump): Use eh_edge_abi to get the set
of registers that are clobbered by an EH edge. Includde partially-
clobbered registers as well as fully-clobbered ones.
2019-09-30 Richard Sandiford <richard.sandiford@arm.com>
* cselib.c (cselib_process_insn): If we know what mode a * cselib.c (cselib_process_insn): If we know what mode a
register was set in, check whether it is clobbered in that register was set in, check whether it is clobbered in that
mode by a call. Only fall back to reg_raw_mode if that fails. mode by a call. Only fall back to reg_raw_mode if that fails.
......
...@@ -36,6 +36,8 @@ along with GCC; see the file COPYING3. If not see ...@@ -36,6 +36,8 @@ along with GCC; see the file COPYING3. If not see
#include "valtrack.h" #include "valtrack.h"
#include "dumpfile.h" #include "dumpfile.h"
#include "rtl-iter.h" #include "rtl-iter.h"
#include "regs.h"
#include "function-abi.h"
/* Note that turning REG_DEAD_DEBUGGING on will cause /* Note that turning REG_DEAD_DEBUGGING on will cause
gcc.c-torture/unsorted/dump-noaddr.c to fail because it prints gcc.c-torture/unsorted/dump-noaddr.c to fail because it prints
...@@ -139,18 +141,17 @@ df_print_bb_index (basic_block bb, FILE *file) ...@@ -139,18 +141,17 @@ df_print_bb_index (basic_block bb, FILE *file)
these along with the bitmap_clear_range call to remove ranges of these along with the bitmap_clear_range call to remove ranges of
bits without actually generating a knockout vector. bits without actually generating a knockout vector.
The kill and sparse_kill and the dense_invalidated_by_call and The kill and sparse_kill and the dense_invalidated_by_eh and
sparse_invalidated_by_call both play this game. */ sparse_invalidated_by_eh both play this game. */
/* Private data used to compute the solution for this problem. These /* Private data used to compute the solution for this problem. These
data structures are not accessible outside of this module. */ data structures are not accessible outside of this module. */
class df_rd_problem_data class df_rd_problem_data
{ {
public: public:
/* The set of defs to regs invalidated by call. */ /* The set of defs to regs invalidated by EH edges. */
bitmap_head sparse_invalidated_by_call; bitmap_head sparse_invalidated_by_eh;
/* The set of defs to regs invalidate by call for rd. */ bitmap_head dense_invalidated_by_eh;
bitmap_head dense_invalidated_by_call;
/* An obstack for the bitmaps we need for this problem. */ /* An obstack for the bitmaps we need for this problem. */
bitmap_obstack rd_bitmaps; bitmap_obstack rd_bitmaps;
}; };
...@@ -187,8 +188,8 @@ df_rd_alloc (bitmap all_blocks) ...@@ -187,8 +188,8 @@ df_rd_alloc (bitmap all_blocks)
if (df_rd->problem_data) if (df_rd->problem_data)
{ {
problem_data = (class df_rd_problem_data *) df_rd->problem_data; problem_data = (class df_rd_problem_data *) df_rd->problem_data;
bitmap_clear (&problem_data->sparse_invalidated_by_call); bitmap_clear (&problem_data->sparse_invalidated_by_eh);
bitmap_clear (&problem_data->dense_invalidated_by_call); bitmap_clear (&problem_data->dense_invalidated_by_eh);
} }
else else
{ {
...@@ -196,9 +197,9 @@ df_rd_alloc (bitmap all_blocks) ...@@ -196,9 +197,9 @@ df_rd_alloc (bitmap all_blocks)
df_rd->problem_data = problem_data; df_rd->problem_data = problem_data;
bitmap_obstack_initialize (&problem_data->rd_bitmaps); bitmap_obstack_initialize (&problem_data->rd_bitmaps);
bitmap_initialize (&problem_data->sparse_invalidated_by_call, bitmap_initialize (&problem_data->sparse_invalidated_by_eh,
&problem_data->rd_bitmaps); &problem_data->rd_bitmaps);
bitmap_initialize (&problem_data->dense_invalidated_by_call, bitmap_initialize (&problem_data->dense_invalidated_by_eh,
&problem_data->rd_bitmaps); &problem_data->rd_bitmaps);
} }
...@@ -391,8 +392,8 @@ df_rd_local_compute (bitmap all_blocks) ...@@ -391,8 +392,8 @@ df_rd_local_compute (bitmap all_blocks)
bitmap_iterator bi; bitmap_iterator bi;
class df_rd_problem_data *problem_data class df_rd_problem_data *problem_data
= (class df_rd_problem_data *) df_rd->problem_data; = (class df_rd_problem_data *) df_rd->problem_data;
bitmap sparse_invalidated = &problem_data->sparse_invalidated_by_call; bitmap sparse_invalidated = &problem_data->sparse_invalidated_by_eh;
bitmap dense_invalidated = &problem_data->dense_invalidated_by_call; bitmap dense_invalidated = &problem_data->dense_invalidated_by_eh;
bitmap_initialize (&seen_in_block, &df_bitmap_obstack); bitmap_initialize (&seen_in_block, &df_bitmap_obstack);
bitmap_initialize (&seen_in_insn, &df_bitmap_obstack); bitmap_initialize (&seen_in_insn, &df_bitmap_obstack);
...@@ -404,10 +405,13 @@ df_rd_local_compute (bitmap all_blocks) ...@@ -404,10 +405,13 @@ df_rd_local_compute (bitmap all_blocks)
df_rd_bb_local_compute (bb_index); df_rd_bb_local_compute (bb_index);
} }
/* Set up the knockout bit vectors to be applied across EH_EDGES. */ /* Set up the knockout bit vectors to be applied across EH_EDGES.
Conservatively treat partially-clobbered registers as surviving
across the EH edge, i.e. assume that definitions before the edge
is taken *might* reach uses after it has been taken. */
if (!(df->changeable_flags & DF_NO_HARD_REGS)) if (!(df->changeable_flags & DF_NO_HARD_REGS))
for (unsigned int regno = 0; regno < FIRST_PSEUDO_REGISTER; ++regno) for (unsigned int regno = 0; regno < FIRST_PSEUDO_REGISTER; ++regno)
if (TEST_HARD_REG_BIT (regs_invalidated_by_call, regno)) if (eh_edge_abi.clobbers_full_reg_p (regno))
{ {
if (DF_DEFS_COUNT (regno) > DF_SPARSE_THRESHOLD) if (DF_DEFS_COUNT (regno) > DF_SPARSE_THRESHOLD)
bitmap_set_bit (sparse_invalidated, regno); bitmap_set_bit (sparse_invalidated, regno);
...@@ -455,8 +459,8 @@ df_rd_confluence_n (edge e) ...@@ -455,8 +459,8 @@ df_rd_confluence_n (edge e)
{ {
class df_rd_problem_data *problem_data class df_rd_problem_data *problem_data
= (class df_rd_problem_data *) df_rd->problem_data; = (class df_rd_problem_data *) df_rd->problem_data;
bitmap sparse_invalidated = &problem_data->sparse_invalidated_by_call; bitmap sparse_invalidated = &problem_data->sparse_invalidated_by_eh;
bitmap dense_invalidated = &problem_data->dense_invalidated_by_call; bitmap dense_invalidated = &problem_data->dense_invalidated_by_eh;
bitmap_iterator bi; bitmap_iterator bi;
unsigned int regno; unsigned int regno;
...@@ -579,9 +583,9 @@ df_rd_start_dump (FILE *file) ...@@ -579,9 +583,9 @@ df_rd_start_dump (FILE *file)
fprintf (file, ";; Reaching defs:\n"); fprintf (file, ";; Reaching defs:\n");
fprintf (file, ";; sparse invalidated \t"); fprintf (file, ";; sparse invalidated \t");
dump_bitmap (file, &problem_data->sparse_invalidated_by_call); dump_bitmap (file, &problem_data->sparse_invalidated_by_eh);
fprintf (file, ";; dense invalidated \t"); fprintf (file, ";; dense invalidated \t");
dump_bitmap (file, &problem_data->dense_invalidated_by_call); dump_bitmap (file, &problem_data->dense_invalidated_by_eh);
fprintf (file, ";; reg->defs[] map:\t"); fprintf (file, ";; reg->defs[] map:\t");
for (regno = 0; regno < m; regno++) for (regno = 0; regno < m; regno++)
...@@ -976,12 +980,15 @@ df_lr_confluence_n (edge e) ...@@ -976,12 +980,15 @@ df_lr_confluence_n (edge e)
bitmap op2 = &df_lr_get_bb_info (e->dest->index)->in; bitmap op2 = &df_lr_get_bb_info (e->dest->index)->in;
bool changed = false; bool changed = false;
/* Call-clobbered registers die across exception and call edges. */ /* Call-clobbered registers die across exception and call edges.
Conservatively treat partially-clobbered registers as surviving
across the edges; they might or might not, depending on what
mode they have. */
/* ??? Abnormal call edges ignored for the moment, as this gets /* ??? Abnormal call edges ignored for the moment, as this gets
confused by sibling call edges, which crashes reg-stack. */ confused by sibling call edges, which crashes reg-stack. */
if (e->flags & EDGE_EH) if (e->flags & EDGE_EH)
{ {
bitmap_view<HARD_REG_SET> eh_kills (regs_invalidated_by_call); bitmap_view<HARD_REG_SET> eh_kills (eh_edge_abi.full_reg_clobbers ());
changed = bitmap_ior_and_compl_into (op1, op2, eh_kills); changed = bitmap_ior_and_compl_into (op1, op2, eh_kills);
} }
else else
...@@ -4636,7 +4643,10 @@ df_md_confluence_n (edge e) ...@@ -4636,7 +4643,10 @@ df_md_confluence_n (edge e)
if (e->flags & EDGE_EH) if (e->flags & EDGE_EH)
{ {
bitmap_view<HARD_REG_SET> eh_kills (regs_invalidated_by_call); /* Conservatively treat partially-clobbered registers as surviving
across the edge; they might or might not, depending on what mode
they have. */
bitmap_view<HARD_REG_SET> eh_kills (eh_edge_abi.full_reg_clobbers ());
return bitmap_ior_and_compl_into (op1, op2, eh_kills); return bitmap_ior_and_compl_into (op1, op2, eh_kills);
} }
else else
......
...@@ -312,8 +312,9 @@ df_scan_start_dump (FILE *file ATTRIBUTE_UNUSED) ...@@ -312,8 +312,9 @@ df_scan_start_dump (FILE *file ATTRIBUTE_UNUSED)
basic_block bb; basic_block bb;
rtx_insn *insn; rtx_insn *insn;
fprintf (file, ";; invalidated by call \t"); fprintf (file, ";; fully invalidated by EH \t");
df_print_regset (file, bitmap_view<HARD_REG_SET> (regs_invalidated_by_call)); df_print_regset
(file, bitmap_view<HARD_REG_SET> (eh_edge_abi.full_reg_clobbers ()));
fprintf (file, ";; hardware regs used \t"); fprintf (file, ";; hardware regs used \t");
df_print_regset (file, &df->hardware_regs_used); df_print_regset (file, &df->hardware_regs_used);
fprintf (file, ";; regular block artificial uses \t"); fprintf (file, ";; regular block artificial uses \t");
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment