function.c (schedule_fixup_var_refs): New function, broken out of put_reg_into_stack.
authorJ"orn Rennecke <amylaar@cygnus.co.uk>
Fri, 4 Aug 2000 22:06:49 +0000 (22:06 +0000)
committerJoern Rennecke <amylaar@gcc.gnu.org>
Fri, 4 Aug 2000 22:06:49 +0000 (23:06 +0100)
* function.c (schedule_fixup_var_refs): New function, broken out
of put_reg_into_stack.
(put_reg_into_stack): Use it.
(put_var_into_stack): In CONCAT case, fixup up references for
components only after fixing up references to the whole concat.
testsuite:
* gcc.c-torture/execute/20000804-1.c: New test.

From-SVN: r35495

gcc/ChangeLog
gcc/function.c
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.c-torture/compile/20000804-1.c [new file with mode: 0644]

index d9824063f262e9b75b866bc702cda9822229bf0d..4552578089ff8b94dbda0a697533dca0740bb4bc 100644 (file)
@@ -1,3 +1,11 @@
+Fri Aug  4 23:01:58 2000  J"orn Rennecke <amylaar@cygnus.co.uk>
+
+       * function.c (schedule_fixup_var_refs): New function, broken out
+       of put_reg_into_stack.
+       (put_reg_into_stack): Use it.
+       (put_var_into_stack): In CONCAT case, fixup up references for
+       components only after fixing up references to the whole concat.
+
 2000-08-04  Rodney Brown  <RodneyBrown@pmsc.com>
 
        * alias.c (mark_constant_function): Use INSN_P.
index 1b5740917e00486108079ba5de01f153f9ecc9b9..9fa8861c71ebda1d9ec7b0cfb1974d0b3f6179c2 100644 (file)
@@ -253,6 +253,9 @@ static void put_reg_into_stack      PARAMS ((struct function *, rtx, tree,
                                         enum machine_mode, enum machine_mode,
                                         int, unsigned int, int,
                                         struct hash_table *));
+static void schedule_fixup_var_refs PARAMS ((struct function *, rtx, tree,
+                                            enum machine_mode,
+                                            struct hash_table *));
 static void fixup_var_refs     PARAMS ((rtx, enum machine_mode, int, 
                                         struct hash_table *));
 static struct fixup_replacement
@@ -1405,20 +1408,25 @@ put_var_into_stack (decl)
   else if (GET_CODE (reg) == CONCAT)
     {
       /* A CONCAT contains two pseudos; put them both in the stack.
-        We do it so they end up consecutive.  */
+        We do it so they end up consecutive.
+        We fixup references to the parts only after we fixup references
+        to the whole CONCAT, lest we do double fixups for the latter
+        references.  */
       enum machine_mode part_mode = GET_MODE (XEXP (reg, 0));
       tree part_type = type_for_mode (part_mode, 0);
+      rtx lopart = XEXP (reg, 0);
+      rtx hipart = XEXP (reg, 1);
 #ifdef FRAME_GROWS_DOWNWARD
       /* Since part 0 should have a lower address, do it second.  */
-      put_reg_into_stack (function, XEXP (reg, 1), part_type, part_mode,
-                         part_mode, volatilep, 0, usedp, 0);
-      put_reg_into_stack (function, XEXP (reg, 0), part_type, part_mode,
-                         part_mode, volatilep, 0, usedp, 0);
+      put_reg_into_stack (function, hipart, part_type, part_mode,
+                         part_mode, volatilep, 0, 0, 0);
+      put_reg_into_stack (function, lopart, part_type, part_mode,
+                         part_mode, volatilep, 0, 0, 0);
 #else
-      put_reg_into_stack (function, XEXP (reg, 0), part_type, part_mode,
-                         part_mode, volatilep, 0, usedp, 0);
-      put_reg_into_stack (function, XEXP (reg, 1), part_type, part_mode,
-                         part_mode, volatilep, 0, usedp, 0);
+      put_reg_into_stack (function, lopart, part_type, part_mode,
+                         part_mode, volatilep, 0, 0, 0);
+      put_reg_into_stack (function, hipart, part_type, part_mode,
+                         part_mode, volatilep, 0, 0, 0);
 #endif
 
       /* Change the CONCAT into a combined MEM for both parts.  */
@@ -1431,6 +1439,13 @@ put_var_into_stack (decl)
       /* Prevent sharing of rtl that might lose.  */
       if (GET_CODE (XEXP (reg, 0)) == PLUS)
        XEXP (reg, 0) = copy_rtx (XEXP (reg, 0));
+      if (usedp)
+       {
+         schedule_fixup_var_refs (function, reg, TREE_TYPE (decl),
+                                  promoted_mode, 0);
+         schedule_fixup_var_refs (function, lopart, part_type, part_mode, 0);
+         schedule_fixup_var_refs (function, hipart, part_type, part_mode, 0);
+       }
     }
   else
     return;
@@ -1490,11 +1505,22 @@ put_reg_into_stack (function, reg, type, promoted_mode, decl_mode, volatile_p,
   MEM_SET_IN_STRUCT_P (reg,
                       AGGREGATE_TYPE_P (type) || MEM_IN_STRUCT_P (new));
   MEM_ALIAS_SET (reg) = get_alias_set (type);
+  if (used_p)
+    schedule_fixup_var_refs (function, reg, type, promoted_mode, ht);
+}
 
-  /* Now make sure that all refs to the variable, previously made
-     when it was a register, are fixed up to be valid again.  */
-
-  if (used_p && function != 0)
+/* Make sure that all refs to the variable, previously made
+   when it was a register, are fixed up to be valid again.
+   See function above for meaning of arguments.  */
+static void
+schedule_fixup_var_refs (function, reg, type, promoted_mode, ht)
+     struct function *function;
+     rtx reg;
+     tree type;
+     enum machine_mode promoted_mode;
+     struct hash_table *ht;
+{
+  if (function != 0)
     {
       struct var_refs_queue *temp;
 
@@ -1506,7 +1532,7 @@ put_reg_into_stack (function, reg, type, promoted_mode, decl_mode, volatile_p,
       temp->next = function->fixup_var_refs_queue;
       function->fixup_var_refs_queue = temp;
     }
-  else if (used_p)
+  else
     /* Variable is local; fix it up now.  */
     fixup_var_refs (reg, promoted_mode, TREE_UNSIGNED (type), ht);
 }
index f2ba4f1eda8108dcb07da5ed9e552fd28dee4ca5..8faddfe81b99ed681d82db4964dcd90890c03b1e 100644 (file)
@@ -1,3 +1,7 @@
+Fri Aug  4 23:00:50 2000  J"orn Rennecke <amylaar@cygnus.co.uk>
+
+       * gcc.c-torture/execute/20000804-1.c: New test.
+
 2000-08-04  Joseph S. Myers  <jsm28@cam.ac.uk>
 
        * gcc.dg/c90-printf-1.c, gcc.dg/c94-printf-1.c: New tests.
diff --git a/gcc/testsuite/gcc.c-torture/compile/20000804-1.c b/gcc/testsuite/gcc.c-torture/compile/20000804-1.c
new file mode 100644 (file)
index 0000000..d99cb7b
--- /dev/null
@@ -0,0 +1,12 @@
+/* Copyright (C) 2000 Free Software Foundation */
+__complex__ long long f ()
+{
+  int i[99];
+  __complex__ long long v;
+
+  v += f ();
+  asm("": "+r" (v) : "r" (0), "r" (1));
+  v = 2;
+  return v;
+  g (&v);
+}