aboutsummaryrefslogtreecommitdiff
path: root/gcc/var-tracking.c
diff options
context:
space:
mode:
authorJakub Jelinek <jakub@redhat.com>2011-03-29 01:53:46 +0200
committerJakub Jelinek <jakub@gcc.gnu.org>2011-03-29 01:53:46 +0200
commit2b80199f41d444c88474b32792a7e828f2a96b68 (patch)
tree7d5601e9e49e4f8fa5cf78fc46ce899d76d94f4f /gcc/var-tracking.c
parentb9da60aea69647fd7957dc328a8431412157d3a7 (diff)
downloadgcc-2b80199f41d444c88474b32792a7e828f2a96b68.zip
gcc-2b80199f41d444c88474b32792a7e828f2a96b68.tar.gz
gcc-2b80199f41d444c88474b32792a7e828f2a96b68.tar.bz2
re PR debug/48203 (ICE in dwarf2out.c while building eglibc.)
PR debug/48203 * cfgexpand.c (expand_debug_expr) <case SSA_NAME>: Only create ENTRY_VALUE if incoming or address of incoming's MEM is a hard REG. * dwarf2out.c (mem_loc_descriptor): Don't emit DW_OP_GNU_entry_value of DW_OP_fbreg. * var-tracking.c (vt_add_function_parameter): Ensure cselib_lookup on ENTRY_VALUE is able to find the canonical parameter VALUE. * cselib.c (rtx_equal_for_cselib_1) <case ENTRY_VALUE>: Use rtx_equal_p instead of rtx_equal_for_cselib_1 to compare ENTRY_VALUE_EXPs. (cselib_hash_rtx) <case ENTRY_VALUE>: If ENTRY_VALUE_EXP is a REG_P or MEM_P with REG_P address, compute hash directly instead of calling cselib_hash_rtx on ENTRY_VALUE_EXP. (preserve_only_constants): Don't clear VALUES forwaring ENTRY_VALUE to some other VALUE. * gcc.dg/pr48203.c: New test. From-SVN: r171640
Diffstat (limited to 'gcc/var-tracking.c')
-rw-r--r--gcc/var-tracking.c37
1 files changed, 36 insertions, 1 deletions
diff --git a/gcc/var-tracking.c b/gcc/var-tracking.c
index ef02937..9729956 100644
--- a/gcc/var-tracking.c
+++ b/gcc/var-tracking.c
@@ -8472,7 +8472,7 @@ vt_add_function_parameter (tree parm)
VAR_INIT_STATUS_INITIALIZED, NULL, INSERT);
if (dv_is_value_p (dv))
{
- cselib_val *val = CSELIB_VAL_PTR (dv_as_value (dv));
+ cselib_val *val = CSELIB_VAL_PTR (dv_as_value (dv)), *val2;
struct elt_loc_list *el;
el = (struct elt_loc_list *)
ggc_alloc_cleared_atomic (sizeof (*el));
@@ -8481,6 +8481,23 @@ vt_add_function_parameter (tree parm)
ENTRY_VALUE_EXP (el->loc) = incoming;
el->setting_insn = get_insns ();
val->locs = el;
+ val2 = cselib_lookup_from_insn (el->loc, GET_MODE (incoming),
+ true, VOIDmode, get_insns ());
+ if (val2
+ && val2 != val
+ && val2->locs
+ && rtx_equal_p (val2->locs->loc, el->loc))
+ {
+ struct elt_loc_list *el2;
+
+ preserve_value (val2);
+ el2 = (struct elt_loc_list *)
+ ggc_alloc_cleared_atomic (sizeof (*el2));
+ el2->next = val2->locs;
+ el2->loc = dv_as_value (dv);
+ el2->setting_insn = get_insns ();
+ val2->locs = el2;
+ }
if (TREE_CODE (TREE_TYPE (parm)) == REFERENCE_TYPE
&& INTEGRAL_TYPE_P (TREE_TYPE (TREE_TYPE (parm))))
{
@@ -8499,6 +8516,24 @@ vt_add_function_parameter (tree parm)
ENTRY_VALUE_EXP (el->loc) = mem;
el->setting_insn = get_insns ();
val->locs = el;
+ val2 = cselib_lookup_from_insn (el->loc, GET_MODE (mem),
+ true, VOIDmode,
+ get_insns ());
+ if (val2
+ && val2 != val
+ && val2->locs
+ && rtx_equal_p (val2->locs->loc, el->loc))
+ {
+ struct elt_loc_list *el2;
+
+ preserve_value (val2);
+ el2 = (struct elt_loc_list *)
+ ggc_alloc_cleared_atomic (sizeof (*el2));
+ el2->next = val2->locs;
+ el2->loc = val->val_rtx;
+ el2->setting_insn = get_insns ();
+ val2->locs = el2;
+ }
}
}
}