OSDN Git Service

(output_move_double): Handle reg[n,n+1] = mem[reg[n] + reg[n+1]].
authorrms <rms@138bc75d-0d04-0410-961f-82ee72b054a4>
Mon, 28 Jun 1993 18:21:17 +0000 (18:21 +0000)
committerrms <rms@138bc75d-0d04-0410-961f-82ee72b054a4>
Mon, 28 Jun 1993 18:21:17 +0000 (18:21 +0000)
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@4789 138bc75d-0d04-0410-961f-82ee72b054a4

gcc/config/ns32k/ns32k.c

index eb47d9c..6dd4a96 100644 (file)
@@ -316,7 +316,42 @@ output_move_double (operands)
       return singlemove_string (operands);
     }
 
-  /* Not autodecrementing.  Do the two words, low-numbered first.  */
+  /* If the first move would clobber the source of the second one,
+     do them in the other order.  */
+
+  /* Overlapping registers.  */
+  if (optype0 == REGOP && optype1 == REGOP
+      && REGNO (op0) == REGNO (latehalf[1]))
+    {
+      /* Do that word.  */
+      output_asm_insn (singlemove_string (latehalf), latehalf);
+      /* Do low-numbered word.  */
+      return singlemove_string (operands);
+    }
+  /* Loading into a register which overlaps a register used in the address.  */
+  else if (optype0 == REGOP && optype1 != REGOP
+          && reg_overlap_mentioned_p (op0, op1))
+    {
+      if (reg_mentioned_p (op0, XEXP (op1, 0))
+         && reg_mentioned_p (latehalf[0], XEXP (op1, 0)))
+       {
+         /* If both halves of dest are used in the src memory address,
+            add the two regs and put them in the low reg (op0).
+            Then it works to load latehalf first.  */
+         rtx xops[2];
+         xops[0] = latehalf[0];
+         xops[1] = op0;
+         output_asm_insn ("addd %0,%1", xops);
+         operands[1] = gen_rtx (MEM, DImode, op0);
+         latehalf[1] = adj_offsettable_operand (operands[1], 4);
+       }
+      /* Do the late half first.  */
+      output_asm_insn (singlemove_string (latehalf), latehalf);
+      /* Then clobber.  */
+      return singlemove_string (operands);
+    }
+
+  /* Normal case.  Do the two words, low-numbered first.  */
 
   output_asm_insn (singlemove_string (operands), operands);