diff mbox series

[1/3] Add a DECL_RTL_REF rtx code

Message ID mptk1e5tibp.fsf@arm.com
State New
Headers show
Series Improve debug info for addressable vars | expand

Commit Message

Richard Sandiford June 1, 2019, 3:51 p.m. UTC
This patch adds a new rtx code for capturing a decl's DECL_RTL by
reference rather than by value.  When used in a VAR_LOCATION, the
VAR_LOCATION continues to track the decl as it changes over time,
rather than "remembering" the value that the decl had at the point
of the VAR_LOCATION.

2019-06-01  Richard Sandiford  <richard.sandiford@arm.com>

gcc/
	* rtl.def (DEF_RTL_EXPR): New rtx code.
	* doc/rtl.texi: Document it.
	* rtl.h (DECL_RTL_REF_TARGET): New macro.
	* rtl.c (rtx_equal_p_cb, rtx_equal_p): Handle DEF_RTL_EXPR.
	* alias.c (rtx_equal_for_memref_p): Likewise.
	* cselib.c (invariant_or_equiv_p, rtx_equal_for_cselib_1)
	(cselib_hash_rtx): Likewise.
	* dwarf2out.c (mem_loc_descriptor): Likewise.
	* print-rtl.c (rtx_writer::print_rtx_operand): Likewise.
diff mbox series

Patch

Index: gcc/rtl.def
===================================================================
--- gcc/rtl.def	2019-05-31 17:27:35.155089238 +0100
+++ gcc/rtl.def	2019-06-01 16:38:31.985677188 +0100
@@ -775,6 +775,11 @@  DEF_RTL_EXPR(DEBUG_IMPLICIT_PTR, "debug_
    parameter.  */
 DEF_RTL_EXPR(ENTRY_VALUE, "entry_value", "0", RTX_OBJ)
 
+/* Captures the DECL_RTL of a DECL by reference rather than by value,
+   so that it tracks the DECL_RTL as it evolves over time.  The single
+   argument is the DECL, accessed via DECL_RTL_REF_TARGET.  */
+DEF_RTL_EXPR(DECL_RTL_REF, "decl_rtl_ref", "t", RTX_OBJ)
+
 /* Used in VAR_LOCATION for a reference to a parameter that has
    been optimized away completely.  */
 DEF_RTL_EXPR(DEBUG_PARAMETER_REF, "debug_parameter_ref", "t", RTX_OBJ)
Index: gcc/doc/rtl.texi
===================================================================
--- gcc/doc/rtl.texi	2019-03-08 18:14:25.581010702 +0000
+++ gcc/doc/rtl.texi	2019-06-01 16:38:31.969677234 +0100
@@ -3675,6 +3675,14 @@  Stands for the location of a @var{decl}
 Stands for the value a @var{decl} had at the entry point of the
 containing function.
 
+@findex decl_rtl_ref
+@item (decl_rtl_ref:@var{mode} @var{decl})
+Captures @samp{DECL_RTL (@var{decl})} by reference rather than by value,
+so that it tracks the @code{DECL_RTL} as it evolves over time.  This is
+useful for describing the debug location of a variable that spends part
+of its lifetime in memory and that can be indirectly modified while
+stored in memory.
+
 @findex debug_parameter_ref
 @item (debug_parameter_ref:@var{mode} @var{decl})
 Refers to a parameter that was completely optimized out.
@@ -4018,11 +4026,20 @@  temporaries and determining expressions
 value of each user variable at as many points (ranges, actually) in the
 program as possible.
 
-Unlike @code{NOTE_INSN_VAR_LOCATION}, the value expression in an
-@code{INSN_VAR_LOCATION} denotes a value at that specific point in the
-program, rather than an expression that can be evaluated at any later
-point before an overriding @code{VAR_LOCATION} is encountered.  E.g.,
-if a user variable is bound to a @code{REG} and then a subsequent insn
+@findex decl_rtl_ref
+@code{INSN_VAR_LOCATION} and @code{NOTE_INSN_VAR_LOCATION} differ in the
+way that they ``capture'' potentially-variable parts of an expression.
+An @code{INSN_VAR_LOCATION} captures any potentially-variable subexpression
+@emph{by value} unless it contains an explicit by-reference capture
+such as @code{decl_rtl_ref}.  A @code{NOTE_INSN_VAR_LOCATION}
+instead captures @emph{every} subexpression by reference.
+
+Capturing a subexpression @var{x} by value means that the subexpression
+represents the value @var{x} had at that particular point in time.
+Capturing by reference means that the subexpression tracks the value
+of @var{x} as it evolves over time.
+
+E.g., if a user variable is bound to a @code{REG} and then a subsequent insn
 modifies the @code{REG}, the note location would keep mapping the user
 variable to the register across the insn, whereas the insn location
 would keep the variable bound to the value, so that the variable
Index: gcc/rtl.h
===================================================================
--- gcc/rtl.h	2019-05-29 10:49:39.892700893 +0100
+++ gcc/rtl.h	2019-06-01 16:38:31.985677188 +0100
@@ -1608,6 +1608,9 @@  #define REG_NOTES(INSN)	XEXP(INSN, 6)
    question.  */
 #define ENTRY_VALUE_EXP(RTX) (RTL_CHECKC1 (RTX, 0, ENTRY_VALUE).rt_rtx)
 
+/* The decl referenced by a DECL_RTL_REF.  */
+#define DECL_RTL_REF_TARGET(RTX) (RTL_CHECKC1 (RTX, 0, DECL_RTL_REF).rt_tree)
+
 enum reg_note
 {
 #define DEF_REG_NOTE(NAME) NAME,
Index: gcc/rtl.c
===================================================================
--- gcc/rtl.c	2019-04-26 10:59:07.730195479 +0100
+++ gcc/rtl.c	2019-06-01 16:38:31.985677188 +0100
@@ -486,6 +486,9 @@  rtx_equal_p_cb (const_rtx x, const_rtx y
     case ENTRY_VALUE:
       return rtx_equal_p_cb (ENTRY_VALUE_EXP (x), ENTRY_VALUE_EXP (y), cb);
 
+    case DECL_RTL_REF:
+      return DECL_RTL_REF_TARGET (x) == DECL_RTL_REF_TARGET (y);
+
     default:
       break;
     }
@@ -628,6 +631,9 @@  rtx_equal_p (const_rtx x, const_rtx y)
     case ENTRY_VALUE:
       return rtx_equal_p (ENTRY_VALUE_EXP (x), ENTRY_VALUE_EXP (y));
 
+    case DECL_RTL_REF:
+      return DECL_RTL_REF_TARGET (x) == DECL_RTL_REF_TARGET (y);
+
     default:
       break;
     }
Index: gcc/alias.c
===================================================================
--- gcc/alias.c	2019-05-29 10:49:39.520701975 +0100
+++ gcc/alias.c	2019-06-01 16:38:31.969677234 +0100
@@ -1769,6 +1769,9 @@  rtx_equal_for_memref_p (const_rtx x, con
       /* This is magic, don't go through canonicalization et al.  */
       return rtx_equal_p (ENTRY_VALUE_EXP (x), ENTRY_VALUE_EXP (y));
 
+    case DECL_RTL_REF:
+      return DECL_RTL_REF_TARGET (x) == DECL_RTL_REF_TARGET (y);
+
     case VALUE:
     CASE_CONST_UNIQUE:
       /* Pointer equality guarantees equality for these nodes.  */
Index: gcc/cselib.c
===================================================================
--- gcc/cselib.c	2019-03-08 18:15:33.700751752 +0000
+++ gcc/cselib.c	2019-06-01 16:38:31.969677234 +0100
@@ -466,6 +466,7 @@  invariant_or_equiv_p (cselib_val *v)
       if (GET_CODE (v->locs->loc) == DEBUG_EXPR
 	  || GET_CODE (v->locs->loc) == DEBUG_IMPLICIT_PTR
 	  || GET_CODE (v->locs->loc) == ENTRY_VALUE
+	  || GET_CODE (v->locs->loc) == DECL_RTL_REF
 	  || GET_CODE (v->locs->loc) == DEBUG_PARAMETER_REF)
 	return true;
 
@@ -952,6 +953,9 @@  rtx_equal_for_cselib_1 (rtx x, rtx y, ma
 	 use rtx_equal_for_cselib_1 to compare the operands.  */
       return rtx_equal_p (ENTRY_VALUE_EXP (x), ENTRY_VALUE_EXP (y));
 
+    case DECL_RTL_REF:
+      return DECL_RTL_REF_TARGET (x) == DECL_RTL_REF_TARGET (y);
+
     case LABEL_REF:
       return label_ref_label (x) == label_ref_label (y);
 
@@ -1126,6 +1130,11 @@  cselib_hash_rtx (rtx x, int create, mach
 	hash += cselib_hash_rtx (ENTRY_VALUE_EXP (x), create, memmode);
       return hash ? hash : (unsigned int) ENTRY_VALUE;
 
+    case DECL_RTL_REF:
+      hash += ((unsigned) DECL_RTL_REF << 7)
+	      + DECL_UID (DECL_RTL_REF_TARGET (x));
+      return hash ? hash : (unsigned int) DECL_RTL_REF;
+
     case CONST_INT:
       hash += ((unsigned) CONST_INT << 7) + UINTVAL (x);
       return hash ? hash : (unsigned int) CONST_INT;
Index: gcc/dwarf2out.c
===================================================================
--- gcc/dwarf2out.c	2019-05-29 10:49:38.836703961 +0100
+++ gcc/dwarf2out.c	2019-06-01 16:38:31.977677211 +0100
@@ -15855,6 +15855,10 @@  mem_loc_descriptor (rtx rtl, machine_mod
       mem_loc_result->dw_loc_oprnd1.v.val_loc = op0;
       break;
 
+    case DECL_RTL_REF:
+      return mem_loc_descriptor (DECL_RTL (DECL_RTL_REF_TARGET (rtl)),
+				 mode, mem_mode, initialized);
+
     case DEBUG_PARAMETER_REF:
       mem_loc_result = parameter_ref_descriptor (rtl);
       break;
Index: gcc/print-rtl.c
===================================================================
--- gcc/print-rtl.c	2019-03-08 18:15:33.660751905 +0000
+++ gcc/print-rtl.c	2019-06-01 16:38:31.981677200 +0100
@@ -678,6 +678,8 @@  rtx_writer::print_rtx_operand (const_rtx
 	print_mem_expr (m_outfile, DEBUG_IMPLICIT_PTR_DECL (in_rtx));
       else if (idx == 0 && GET_CODE (in_rtx) == DEBUG_PARAMETER_REF)
 	print_mem_expr (m_outfile, DEBUG_PARAMETER_REF_DECL (in_rtx));
+      else if (idx == 0 && GET_CODE (in_rtx) == DECL_RTL_REF)
+	print_mem_expr (m_outfile, DECL_RTL_REF_TARGET (in_rtx));
       else
 	dump_addr (m_outfile, " ", XTREE (in_rtx, idx));
 #endif