/* Alias analysis for GNU C
- Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002 Free Software Foundation, Inc.
+ Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2003
+ Free Software Foundation, Inc.
Contributed by John Carr (jfc@mit.edu).
This file is part of GCC.
To see whether two alias sets can point to the same memory, we must
see if either alias set is a subset of the other. We need not trace
- past immediate descendents, however, since we propagate all
+ past immediate descendants, however, since we propagate all
grandchildren up one level.
Alias set zero is implicitly a superset of all other alias sets.
HOST_WIDE_INT alias_set;
/* The children of the alias set. These are not just the immediate
- children, but, in fact, all descendents. So, if we have:
+ children, but, in fact, all descendants. So, if we have:
struct T { struct S s; float f; }
static int nonlocal_referenced_p PARAMS ((rtx));
static int nonlocal_set_p_1 PARAMS ((rtx *, void *));
static int nonlocal_set_p PARAMS ((rtx));
+static void memory_modified_1 PARAMS ((rtx, rtx, void *));
/* Set up all info needed to perform alias analysis on memory references. */
{
/* If we're inside init_alias_analysis, use new_reg_base_value
to reduce the number of relaxation iterations. */
- if (new_reg_base_value && new_reg_base_value[regno])
+ if (new_reg_base_value && new_reg_base_value[regno]
+ && REG_N_SETS (regno) == 1)
return new_reg_base_value[regno];
if (reg_base_value[regno])
{
unsigned regno;
rtx src;
+ int n;
if (GET_CODE (dest) != REG)
return;
if (regno >= reg_base_value_size)
abort ();
+ /* If this spans multiple hard registers, then we must indicate that every
+ register has an unusable value. */
+ if (regno < FIRST_PSEUDO_REGISTER)
+ n = HARD_REGNO_NREGS (regno, GET_MODE (dest));
+ else
+ n = 1;
+ if (n != 1)
+ {
+ while (--n >= 0)
+ {
+ reg_seen[regno + n] = 1;
+ new_reg_base_value[regno + n] = 0;
+ }
+ return;
+ }
+
if (set)
{
/* A CLOBBER wipes out any old value but does not prevent a previously
return GEN_INT (ioffset);
}
-/* Return nonzero if we can deterimine the exprs corresponding to memrefs
+/* Return nonzero if we can determine the exprs corresponding to memrefs
X and Y and they do not overlap. */
static int
alias_sets = splay_tree_new (splay_tree_compare_ints, 0, 0);
}
+/* Set MEMORY_MODIFIED when X modifies DATA (that is assumed
+ to be memory reference. */
+static bool memory_modified;
+static void
+memory_modified_1 (x, pat, data)
+ rtx x, pat ATTRIBUTE_UNUSED;
+ void *data;
+{
+ if (GET_CODE (x) == MEM)
+ {
+ if (anti_dependence (x, (rtx)data) || output_dependence (x, (rtx)data))
+ memory_modified = true;
+ }
+}
+
+
+/* Return true when INSN possibly modify memory contents of MEM
+ (ie address can be modified). */
+bool
+memory_modified_in_insn_p (mem, insn)
+ rtx mem, insn;
+{
+ if (!INSN_P (insn))
+ return false;
+ memory_modified = false;
+ note_stores (PATTERN (insn), memory_modified_1, mem);
+ return memory_modified;
+}
+
/* Initialize the aliasing machinery. Initialize the REG_KNOWN_VALUE
array. */