Commit 9ddb66ca by Jan Hubicka Committed by Jan Hubicka

alias.c: Invlude varray.h

	* alias.c:  Invlude varray.h
	(alias_sets): Turn into varray.
	(get_alias_set_entry): Use VARRAY; mark inline.
	(mems_in_disjoint_alias_sets_p): Mark inline.
	(record_alias_subset): Use varray.
	(init_alias_once): Initialize varray.
	(new_alias_set): Grow array.
	* varray.c: Make VARRAY_GENERIC_PTR non GTYized.

From-SVN: r75711
parent c65ecebc
2004-01-12 Jan Hubicka <jh@suse.cz> 2004-01-12 Jan Hubicka <jh@suse.cz>
Partial fox for PR opt/10776 II * alias.c: Invlude varray.h
(alias_sets): Turn into varray.
(get_alias_set_entry): Use VARRAY; mark inline.
(mems_in_disjoint_alias_sets_p): Mark inline.
(record_alias_subset): Use varray.
(init_alias_once): Initialize varray.
(new_alias_set): Grow array.
* varray.c: Make VARRAY_GENERIC_PTR non GTYized.
2004-01-12 Jan Hubicka <jh@suse.cz>
Partial fix for PR opt/10776 II
* cselib.c: Include params.h * cselib.c: Include params.h
(cselib_invalidate_mem): Limit amount of nonconflicting memory (cselib_invalidate_mem): Limit amount of nonconflicting memory
locations. locations.
......
...@@ -1653,7 +1653,7 @@ web.o : web.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) $(REGS_H) \ ...@@ -1653,7 +1653,7 @@ web.o : web.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) $(REGS_H) \
gcse.o : gcse.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) $(REGS_H) \ gcse.o : gcse.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) $(REGS_H) \
hard-reg-set.h flags.h real.h insn-config.h $(GGC_H) $(RECOG_H) $(EXPR_H) \ hard-reg-set.h flags.h real.h insn-config.h $(GGC_H) $(RECOG_H) $(EXPR_H) \
$(BASIC_BLOCK_H) function.h output.h toplev.h $(TM_P_H) $(PARAMS_H) \ $(BASIC_BLOCK_H) function.h output.h toplev.h $(TM_P_H) $(PARAMS_H) \
except.h gt-gcse.h $(TREE_H) except.h gt-gcse.h $(TREE_H) cselib.h
sibcall.o : sibcall.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) $(REGS_H) \ sibcall.o : sibcall.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) $(REGS_H) \
function.h hard-reg-set.h flags.h insn-config.h $(RECOG_H) $(BASIC_BLOCK_H) function.h hard-reg-set.h flags.h insn-config.h $(RECOG_H) $(BASIC_BLOCK_H)
resource.o : resource.c $(CONFIG_H) $(RTL_H) hard-reg-set.h $(SYSTEM_H) coretypes.h \ resource.o : resource.c $(CONFIG_H) $(RTL_H) hard-reg-set.h $(SYSTEM_H) coretypes.h \
......
...@@ -42,6 +42,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA ...@@ -42,6 +42,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
#include "timevar.h" #include "timevar.h"
#include "target.h" #include "target.h"
#include "cgraph.h" #include "cgraph.h"
#include "varray.h"
/* The alias sets assigned to MEMs assist the back-end in determining /* The alias sets assigned to MEMs assist the back-end in determining
which MEMs can alias which other MEMs. In general, two MEMs in which MEMs can alias which other MEMs. In general, two MEMs in
...@@ -205,24 +206,21 @@ char *reg_known_equiv_p; ...@@ -205,24 +206,21 @@ char *reg_known_equiv_p;
static bool copying_arguments; static bool copying_arguments;
/* The splay-tree used to store the various alias set entries. */ /* The splay-tree used to store the various alias set entries. */
static splay_tree alias_sets; varray_type alias_sets;
/* Returns a pointer to the alias set entry for ALIAS_SET, if there is /* Returns a pointer to the alias set entry for ALIAS_SET, if there is
such an entry, or NULL otherwise. */ such an entry, or NULL otherwise. */
static alias_set_entry static inline alias_set_entry
get_alias_set_entry (HOST_WIDE_INT alias_set) get_alias_set_entry (HOST_WIDE_INT alias_set)
{ {
splay_tree_node sn return (alias_set_entry)VARRAY_GENERIC_PTR (alias_sets, alias_set);
= splay_tree_lookup (alias_sets, (splay_tree_key) alias_set);
return sn != 0 ? ((alias_set_entry) sn->value) : 0;
} }
/* Returns nonzero if the alias sets for MEM1 and MEM2 are such that /* Returns nonzero if the alias sets for MEM1 and MEM2 are such that
the two MEMs cannot alias each other. */ the two MEMs cannot alias each other. */
static int static inline int
mems_in_disjoint_alias_sets_p (rtx mem1, rtx mem2) mems_in_disjoint_alias_sets_p (rtx mem1, rtx mem2)
{ {
#ifdef ENABLE_CHECKING #ifdef ENABLE_CHECKING
...@@ -599,7 +597,10 @@ new_alias_set (void) ...@@ -599,7 +597,10 @@ new_alias_set (void)
static HOST_WIDE_INT last_alias_set; static HOST_WIDE_INT last_alias_set;
if (flag_strict_aliasing) if (flag_strict_aliasing)
return ++last_alias_set; {
VARRAY_GROW (alias_sets, last_alias_set + 2);
return ++last_alias_set;
}
else else
return 0; return 0;
} }
...@@ -641,8 +642,7 @@ record_alias_subset (HOST_WIDE_INT superset, HOST_WIDE_INT subset) ...@@ -641,8 +642,7 @@ record_alias_subset (HOST_WIDE_INT superset, HOST_WIDE_INT subset)
superset_entry->children superset_entry->children
= splay_tree_new (splay_tree_compare_ints, 0, 0); = splay_tree_new (splay_tree_compare_ints, 0, 0);
superset_entry->has_zero_child = 0; superset_entry->has_zero_child = 0;
splay_tree_insert (alias_sets, (splay_tree_key) superset, VARRAY_GENERIC_PTR (alias_sets, superset) = superset_entry;
(splay_tree_value) superset_entry);
} }
if (subset == 0) if (subset == 0)
...@@ -2673,7 +2673,7 @@ init_alias_once (void) ...@@ -2673,7 +2673,7 @@ init_alias_once (void)
= gen_rtx_ADDRESS (Pmode, hard_frame_pointer_rtx); = gen_rtx_ADDRESS (Pmode, hard_frame_pointer_rtx);
#endif #endif
alias_sets = splay_tree_new (splay_tree_compare_ints, 0, 0); VARRAY_GENERIC_PTR_INIT (alias_sets, 10, "alias sets");
} }
/* Set MEMORY_MODIFIED when X modifies DATA (that is assumed /* Set MEMORY_MODIFIED when X modifies DATA (that is assumed
......
...@@ -1768,6 +1768,7 @@ struct check_dependence_data ...@@ -1768,6 +1768,7 @@ struct check_dependence_data
{ {
enum machine_mode mode; enum machine_mode mode;
rtx exp; rtx exp;
rtx addr;
}; };
static int static int
...@@ -1775,7 +1776,8 @@ check_dependence (rtx *x, void *data) ...@@ -1775,7 +1776,8 @@ check_dependence (rtx *x, void *data)
{ {
struct check_dependence_data *d = (struct check_dependence_data *) data; struct check_dependence_data *d = (struct check_dependence_data *) data;
if (*x && GET_CODE (*x) == MEM) if (*x && GET_CODE (*x) == MEM)
return true_dependence (d->exp, d->mode, *x, cse_rtx_varies_p); return canon_true_dependence (d->exp, d->mode, d->addr, *x,
cse_rtx_varies_p);
else else
return 0; return 0;
} }
...@@ -1797,6 +1799,7 @@ invalidate (rtx x, enum machine_mode full_mode) ...@@ -1797,6 +1799,7 @@ invalidate (rtx x, enum machine_mode full_mode)
{ {
int i; int i;
struct table_elt *p; struct table_elt *p;
rtx addr;
switch (GET_CODE (x)) switch (GET_CODE (x))
{ {
...@@ -1887,6 +1890,7 @@ invalidate (rtx x, enum machine_mode full_mode) ...@@ -1887,6 +1890,7 @@ invalidate (rtx x, enum machine_mode full_mode)
return; return;
case MEM: case MEM:
addr = canon_rtx (get_addr (XEXP (x, 0)));
/* Calculate the canonical version of X here so that /* Calculate the canonical version of X here so that
true_dependence doesn't generate new RTL for X on each call. */ true_dependence doesn't generate new RTL for X on each call. */
x = canon_rtx (x); x = canon_rtx (x);
...@@ -1914,6 +1918,7 @@ invalidate (rtx x, enum machine_mode full_mode) ...@@ -1914,6 +1918,7 @@ invalidate (rtx x, enum machine_mode full_mode)
if (!p->canon_exp) if (!p->canon_exp)
p->canon_exp = canon_rtx (p->exp); p->canon_exp = canon_rtx (p->exp);
d.exp = x; d.exp = x;
d.addr = addr;
d.mode = full_mode; d.mode = full_mode;
if (for_each_rtx (&p->canon_exp, check_dependence, &d)) if (for_each_rtx (&p->canon_exp, check_dependence, &d))
remove_from_table (p, i); remove_from_table (p, i);
......
...@@ -58,7 +58,6 @@ static cselib_val *new_cselib_val (unsigned int, enum machine_mode); ...@@ -58,7 +58,6 @@ static cselib_val *new_cselib_val (unsigned int, enum machine_mode);
static void add_mem_for_addr (cselib_val *, cselib_val *, rtx); static void add_mem_for_addr (cselib_val *, cselib_val *, rtx);
static cselib_val *cselib_lookup_mem (rtx, int); static cselib_val *cselib_lookup_mem (rtx, int);
static void cselib_invalidate_regno (unsigned int, enum machine_mode); static void cselib_invalidate_regno (unsigned int, enum machine_mode);
static int cselib_mem_conflict_p (rtx, rtx);
static void cselib_invalidate_mem (rtx); static void cselib_invalidate_mem (rtx);
static void cselib_invalidate_rtx (rtx, rtx, void *); static void cselib_invalidate_rtx (rtx, rtx, void *);
static void cselib_record_set (rtx, cselib_val *, cselib_val *); static void cselib_record_set (rtx, cselib_val *, cselib_val *);
...@@ -168,6 +167,7 @@ new_elt_loc_list (struct elt_loc_list *next, rtx loc) ...@@ -168,6 +167,7 @@ new_elt_loc_list (struct elt_loc_list *next, rtx loc)
el = ggc_alloc (sizeof (struct elt_loc_list)); el = ggc_alloc (sizeof (struct elt_loc_list));
el->next = next; el->next = next;
el->loc = loc; el->loc = loc;
el->canon_loc = NULL;
el->setting_insn = cselib_current_insn; el->setting_insn = cselib_current_insn;
el->in_libcall = cselib_current_insn_in_libcall; el->in_libcall = cselib_current_insn_in_libcall;
return el; return el;
...@@ -1050,60 +1050,18 @@ cselib_invalidate_regno (unsigned int regno, enum machine_mode mode) ...@@ -1050,60 +1050,18 @@ cselib_invalidate_regno (unsigned int regno, enum machine_mode mode)
} }
} }
} }
/* The memory at address MEM_BASE is being changed. /* Return 1 if X has a value that can vary even between two
Return whether this change will invalidate VAL. */ executions of the program. 0 means X can be compared reliably
against certain constants or near-constants. */
static int static int
cselib_mem_conflict_p (rtx mem_base, rtx val) cselib_rtx_varies_p (rtx x ATTRIBUTE_UNUSED, int from_alias ATTRIBUTE_UNUSED)
{ {
enum rtx_code code; /* We actually don't need to verify very hard. This is because
const char *fmt; if X has actually changed, we invalidate the memory anyway,
int i, j; so assume that all common memory addresses are
invariant. */
code = GET_CODE (val);
switch (code)
{
/* Get rid of a few simple cases quickly. */
case REG:
case PC:
case CC0:
case SCRATCH:
case CONST:
case CONST_INT:
case CONST_DOUBLE:
case CONST_VECTOR:
case SYMBOL_REF:
case LABEL_REF:
return 0;
case MEM:
if (GET_MODE (mem_base) == BLKmode
|| GET_MODE (val) == BLKmode
|| anti_dependence (val, mem_base))
return 1;
/* The address may contain nested MEMs. */
break;
default:
break;
}
fmt = GET_RTX_FORMAT (code);
for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
{
if (fmt[i] == 'e')
{
if (cselib_mem_conflict_p (mem_base, XEXP (val, i)))
return 1;
}
else if (fmt[i] == 'E')
for (j = 0; j < XVECLEN (val, i); j++)
if (cselib_mem_conflict_p (mem_base, XVECEXP (val, i, j)))
return 1;
}
return 0; return 0;
} }
...@@ -1116,6 +1074,10 @@ cselib_invalidate_mem (rtx mem_rtx) ...@@ -1116,6 +1074,10 @@ cselib_invalidate_mem (rtx mem_rtx)
{ {
cselib_val **vp, *v, *next; cselib_val **vp, *v, *next;
int num_mems = 0; int num_mems = 0;
rtx mem_addr;
mem_addr = canon_rtx (get_addr (XEXP (mem_rtx, 0)));
mem_rtx = canon_rtx (mem_rtx);
vp = &first_containing_mem; vp = &first_containing_mem;
for (v = *vp; v != &dummy_val; v = next) for (v = *vp; v != &dummy_val; v = next)
...@@ -1127,6 +1089,7 @@ cselib_invalidate_mem (rtx mem_rtx) ...@@ -1127,6 +1089,7 @@ cselib_invalidate_mem (rtx mem_rtx)
while (*p) while (*p)
{ {
rtx x = (*p)->loc; rtx x = (*p)->loc;
rtx canon_x = (*p)->canon_loc;
cselib_val *addr; cselib_val *addr;
struct elt_list **mem_chain; struct elt_list **mem_chain;
...@@ -1137,8 +1100,11 @@ cselib_invalidate_mem (rtx mem_rtx) ...@@ -1137,8 +1100,11 @@ cselib_invalidate_mem (rtx mem_rtx)
p = &(*p)->next; p = &(*p)->next;
continue; continue;
} }
if (!canon_x)
canon_x = (*p)->canon_loc = canon_rtx (x);
if (num_mems < PARAM_VALUE (PARAM_MAX_CSELIB_MEMORY_LOCATIONS) if (num_mems < PARAM_VALUE (PARAM_MAX_CSELIB_MEMORY_LOCATIONS)
&& ! cselib_mem_conflict_p (mem_rtx, x)) && ! canon_true_dependence (mem_rtx, GET_MODE (mem_rtx), mem_addr,
x, cselib_rtx_varies_p))
{ {
has_mem = true; has_mem = true;
num_mems++; num_mems++;
......
...@@ -49,6 +49,7 @@ struct elt_loc_list GTY(()) ...@@ -49,6 +49,7 @@ struct elt_loc_list GTY(())
struct elt_loc_list *next; struct elt_loc_list *next;
/* An rtl expression that holds the value. */ /* An rtl expression that holds the value. */
rtx loc; rtx loc;
rtx canon_loc;
/* The insn that made the equivalence. */ /* The insn that made the equivalence. */
rtx setting_insn; rtx setting_insn;
/* True when setting insn is inside libcall. */ /* True when setting insn is inside libcall. */
......
...@@ -47,7 +47,7 @@ static const struct { ...@@ -47,7 +47,7 @@ static const struct {
{ sizeof (unsigned long), 1 }, { sizeof (unsigned long), 1 },
{ sizeof (HOST_WIDE_INT), 1 }, { sizeof (HOST_WIDE_INT), 1 },
{ sizeof (unsigned HOST_WIDE_INT), 1 }, { sizeof (unsigned HOST_WIDE_INT), 1 },
{ sizeof (void *), 1 }, { sizeof (void *), 0 },
{ sizeof (char *), 1 }, { sizeof (char *), 1 },
{ sizeof (struct rtx_def *), 1 }, { sizeof (struct rtx_def *), 1 },
{ sizeof (struct rtvec_def *), 1 }, { sizeof (struct rtvec_def *), 1 },
......
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