var-tracking.c (vt_add_function_parameter): Remap incoming MEMs with crtl->args.inter...
authorJakub Jelinek <jakub@redhat.com>
Mon, 30 May 2011 15:16:40 +0000 (15:16 +0000)
committerEric Botcazou <ebotcazou@gcc.gnu.org>
Mon, 30 May 2011 15:16:40 +0000 (15:16 +0000)
* var-tracking.c (vt_add_function_parameter): Remap incoming MEMs with
crtl->args.internal_arg_pointer based address to arg_pointer_rtx if
there is a DRAP register and arg_pointer_rtx is the CFA pointer.
(vt_init_cfa_base): Don't equate cfa_base_rtx if stack was realigned.
(vt_initialize): Initialize cfa_base_rtx if there is a DRAP register.

From-SVN: r174438

gcc/ChangeLog
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.dg/guality/drap.c [new file with mode: 0644]
gcc/var-tracking.c

index 4a800f05b9b37454f334e246af02560ba08ea13e..12a6468dbe54db52ac67b1d8c17661385140c8d3 100644 (file)
@@ -1,3 +1,12 @@
+2011-05-30  Jakub Jelinek  <jakub@redhat.com>
+           Eric Botcazou  <ebotcazou@adacore.com>
+
+       * var-tracking.c (vt_add_function_parameter): Remap incoming MEMs with
+       crtl->args.internal_arg_pointer based address to arg_pointer_rtx if
+       there is a DRAP register and arg_pointer_rtx is the CFA pointer.
+       (vt_init_cfa_base): Don't equate cfa_base_rtx if stack was realigned.
+       (vt_initialize): Initialize cfa_base_rtx if there is a DRAP register.
+
 2011-05-30  Richard Guenther  <rguenther@suse.de>
 
        * gimple.c (gimple_types_compatible_p_1): Compare record
index d7df19bda9a11acef003a497480069eefaf3fe9e..e80c1b2c9b2450bf4bade4bc9ab09a31a92dd92d 100644 (file)
@@ -1,9 +1,13 @@
+2011-05-30  Jakub Jelinek  <jakub@redhat.com>
+           Eric Botcazou  <ebotcazou@adacore.com>
+
+       * gcc.dg/guality/drap.c: New test.
+
 2011-05-30  Richard Guenther  <rguenther@suse.de>
 
        PR tree-optimization/49210
-       * gnat.dg/boolean_subtype2.adb: New testcase.
-       * gnat.dg/boolean_subtype2.ads: Likewise.
-       * gnat.dg/boolean_subtype2_pkg.ads: Likewise.
+       * gnat.dg/boolean_subtype2.ad[sb]: New testcase.
+       * gnat.dg/boolean_subtype2_pkg.ads: New helper.
 
 2011-05-30  Jakub Jelinek  <jakub@redhat.com>
 
diff --git a/gcc/testsuite/gcc.dg/guality/drap.c b/gcc/testsuite/gcc.dg/guality/drap.c
new file mode 100644 (file)
index 0000000..573bb39
--- /dev/null
@@ -0,0 +1,30 @@
+/* { dg-do run { target { i?86-*-* x86_64-*-* } } } */
+/* { dg-options "-g -mforce-drap" } */
+
+volatile int v;
+
+__attribute__((noinline, noclone)) int
+bar (int a, int b)
+{
+#ifdef __x86_64__
+  asm volatile ("movq %%rsp, %%r10" : : : "r10");
+#else
+  asm volatile ("movl %%esp, %%ecx" : : : "ecx");
+#endif
+  return 0;
+}
+
+__attribute__((noinline, noclone)) int
+foo (int v0, int v1, int v2, int v3, int v4, int v5, int a, int b)
+{
+  __attribute__((aligned (32))) int c = bar (a, b);
+  v++;               /* { dg-final { gdb-test 21 "a" "5" } } */
+  return a + b + c;  /* { dg-final { gdb-test 22 "b" "6" } } */
+}
+
+int
+main (void)
+{
+  foo (0, 0, 0, 0, 0, 0, 5, 6);
+  return 0;
+}
index 5e7c2fc15dc3ba34e32301a2f4be9cc0eb40e0a6..2c16d08e02cb967408c5436d8cd4fb14e9e7b854 100644 (file)
@@ -8398,6 +8398,28 @@ vt_add_function_parameter (tree parm)
   if (GET_MODE (decl_rtl) == BLKmode || GET_MODE (incoming) == BLKmode)
     return;
 
+  /* If there is a DRAP register, rewrite the incoming location of parameters
+     passed on the stack into MEMs based on the argument pointer, as the DRAP
+     register can be reused for other purposes and we do not track locations
+     based on generic registers.  But the prerequisite is that this argument
+     pointer be also the virtual CFA pointer, see vt_initialize.  */
+  if (MEM_P (incoming)
+      && stack_realign_drap
+      && arg_pointer_rtx == cfa_base_rtx
+      && (XEXP (incoming, 0) == crtl->args.internal_arg_pointer
+         || (GET_CODE (XEXP (incoming, 0)) == PLUS
+             && XEXP (XEXP (incoming, 0), 0)
+                == crtl->args.internal_arg_pointer
+             && CONST_INT_P (XEXP (XEXP (incoming, 0), 1)))))
+    {
+      HOST_WIDE_INT off = -FIRST_PARM_OFFSET (current_function_decl);
+      if (GET_CODE (XEXP (incoming, 0)) == PLUS)
+       off += INTVAL (XEXP (XEXP (incoming, 0), 1));
+      incoming
+       = replace_equiv_address_nv (incoming,
+                                   plus_constant (arg_pointer_rtx, off));
+    }
+
   if (!vt_get_decl_and_offset (incoming, &decl, &offset))
     {
       if (REG_P (incoming) || MEM_P (incoming))
@@ -8647,9 +8669,11 @@ vt_init_cfa_base (void)
 
   /* Tell alias analysis that cfa_base_rtx should share
      find_base_term value with stack pointer or hard frame pointer.  */
-  vt_equate_reg_base_value (cfa_base_rtx,
-                           frame_pointer_needed
-                           ? hard_frame_pointer_rtx : stack_pointer_rtx);
+  if (!frame_pointer_needed)
+    vt_equate_reg_base_value (cfa_base_rtx, stack_pointer_rtx);
+  else if (!crtl->stack_realign_tried)
+    vt_equate_reg_base_value (cfa_base_rtx, hard_frame_pointer_rtx);
+
   val = cselib_lookup_from_insn (cfa_base_rtx, GET_MODE (cfa_base_rtx), 1,
                                 VOIDmode, get_insns ());
   preserve_value (val);
@@ -8780,6 +8804,33 @@ vt_initialize (void)
        fp_cfa_offset = -1;
     }
 
+  /* If the stack is realigned and a DRAP register is used, we're going to
+     rewrite MEMs based on it representing incoming locations of parameters
+     passed on the stack into MEMs based on the argument pointer.  Although
+     we aren't going to rewrite other MEMs, we still need to initialize the
+     virtual CFA pointer in order to ensure that the argument pointer will
+     be seen as a constant throughout the function.
+
+     ??? This doesn't work if FRAME_POINTER_CFA_OFFSET is defined.  */
+  else if (stack_realign_drap)
+    {
+      rtx reg, elim;
+
+#ifdef FRAME_POINTER_CFA_OFFSET
+      reg = frame_pointer_rtx;
+#else
+      reg = arg_pointer_rtx;
+#endif
+      elim = eliminate_regs (reg, VOIDmode, NULL_RTX);
+      if (elim != reg)
+       {
+         if (GET_CODE (elim) == PLUS)
+           elim = XEXP (elim, 0);
+         if (elim == hard_frame_pointer_rtx)
+           vt_init_cfa_base ();
+       }
+    }
+
   if (frame_pointer_needed)
     {
       rtx insn;