]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
m68hc11.c (m68hc11_z_replacement): Use emit_insn_after when adding the save Z instruc...
authorStephane Carrez <stcarrez@nerim.fr>
Sun, 8 May 2005 18:54:51 +0000 (20:54 +0200)
committerStephane Carrez <ciceron@gcc.gnu.org>
Sun, 8 May 2005 18:54:51 +0000 (20:54 +0200)
* config/m68hc11/m68hc11.c (m68hc11_z_replacement): Use emit_insn_after
when adding the save Z instruction so that it is part of the good BB.
(reg_or_some_mem_operand): Do not allow the 68HC12 address indirect
addressing mode as it is not supported by bset and bclr.
(m68hc11_gen_movhi): Fix invalid generation of indexed indirect
addressing with movw.
(m68hc11_gen_movqi): Use pula and pulb instead of lda and ldb for
68HC12.
* config/m68hc11/m68hc11.md ("movhi_const0"): Use this pattern only
for 68HC11.
("*movhi_68hc12"): Handle movhi_const0.
("*subhi3", "subqi3"): Use general_operand for operand 1.
("*subhi3_zext"): Likewise.

From-SVN: r99402

gcc/ChangeLog
gcc/config/m68hc11/m68hc11.c

index a8fc36914d104b2b2171f256400604998dfef714..b75e41f7d22d31e7a537b1bdb8c45ce69b4836b9 100644 (file)
@@ -1,3 +1,19 @@
+2005-05-08  Stephane Carrez  <stcarrez@nerim.fr>
+
+       * config/m68hc11/m68hc11.c (m68hc11_z_replacement): Use emit_insn_after
+       when adding the save Z instruction so that it is part of the good BB.
+       (reg_or_some_mem_operand): Do not allow the 68HC12 address indirect
+       addressing mode as it is not supported by bset and bclr.
+       (m68hc11_gen_movhi): Fix invalid generation of indexed indirect
+       addressing with movw.
+       (m68hc11_gen_movqi): Use pula and pulb instead of lda and ldb for
+       68HC12.
+       * config/m68hc11/m68hc11.md ("movhi_const0"): Use this pattern only
+       for 68HC11.
+       ("*movhi_68hc12"): Handle movhi_const0.
+       ("*subhi3", "subqi3"): Use general_operand for operand 1.
+       ("*subhi3_zext"): Likewise.
+
 2005-05-08  Stephane Carrez  <stcarrez@nerim.fr>
 
        PR target/19051
index 8f054622c03e029045e054ab51bf87e5ac95a5f1..383025d4ae151e5dee4f1160584ffa641209895d 100644 (file)
@@ -1027,6 +1027,7 @@ reg_or_some_mem_operand (rtx operand, enum machine_mode mode)
   if (GET_CODE (operand) == MEM)
     {
       rtx op = XEXP (operand, 0);
+      int addr_mode;
 
       if (symbolic_memory_operand (op, mode))
        return 1;
@@ -1034,10 +1035,20 @@ reg_or_some_mem_operand (rtx operand, enum machine_mode mode)
       if (IS_STACK_PUSH (operand))
        return 1;
 
-      if (m68hc11_register_indirect_p (operand, mode))
-       return 1;
+      if (GET_CODE (operand) == REG && reload_in_progress
+          && REGNO (operand) >= FIRST_PSEUDO_REGISTER
+          && reg_equiv_memory_loc[REGNO (operand)])
+         {
+            operand = reg_equiv_memory_loc[REGNO (operand)];
+            operand = eliminate_regs (operand, 0, NULL_RTX);
+         }
+      if (GET_CODE (operand) != MEM)
+         return 0;
 
-      return 0;
+      operand = XEXP (operand, 0);
+      addr_mode = m68hc11_addr_mode | (reload_completed ? ADDR_STRICT : 0);
+      addr_mode &= ~ADDR_INDIRECT;
+      return register_indirect_p (operand, mode, addr_mode);
     }
 
   return register_operand (operand, mode);
@@ -3221,10 +3232,13 @@ m68hc11_gen_movhi (rtx insn, rtx *operands)
 
   if (TARGET_M6812)
     {
-      if (IS_STACK_PUSH (operands[0]) && H_REG_P (operands[1]))
+      rtx from = operands[1];
+      rtx to = operands[0];
+
+      if (IS_STACK_PUSH (to) && H_REG_P (from))
        {
           cc_status = cc_prev_status;
-         switch (REGNO (operands[1]))
+         switch (REGNO (from))
            {
            case HARD_X_REGNUM:
            case HARD_Y_REGNUM:
@@ -3239,10 +3253,10 @@ m68hc11_gen_movhi (rtx insn, rtx *operands)
            }
          return;
        }
-      if (IS_STACK_POP (operands[1]) && H_REG_P (operands[0]))
+      if (IS_STACK_POP (from) && H_REG_P (to))
        {
           cc_status = cc_prev_status;
-         switch (REGNO (operands[0]))
+         switch (REGNO (to))
            {
            case HARD_X_REGNUM:
            case HARD_Y_REGNUM:
@@ -3273,11 +3287,52 @@ m68hc11_gen_movhi (rtx insn, rtx *operands)
          else
            output_asm_insn ("st%1\t%0", operands);
        }
+
+      /* The 68hc12 does not support (MEM:HI (MEM:HI)) with the movw
+         instruction.  We have to use a scratch register as temporary location.
+         Trying to use a specific pattern or constrain failed.  */
+      else if (GET_CODE (to) == MEM && GET_CODE (XEXP (to, 0)) == MEM)
+        {
+          rtx ops[4];
+
+          ops[0] = to;
+          ops[2] = from;
+          ops[3] = 0;
+          if (dead_register_here (insn, d_reg))
+            ops[1] = d_reg;
+          else if (dead_register_here (insn, ix_reg))
+            ops[1] = ix_reg;
+          else if (dead_register_here (insn, iy_reg))
+            ops[1] = iy_reg;
+          else
+            {
+              ops[1] = d_reg;
+              ops[3] = d_reg;
+              output_asm_insn ("psh%3", ops);
+            }
+
+          ops[0] = to;
+          ops[2] = from;
+          output_asm_insn ("ld%1\t%2", ops);
+          output_asm_insn ("st%1\t%0", ops);
+          if (ops[3])
+            output_asm_insn ("pul%3", ops);
+        }
+
+      /* Use movw for non-null constants or when we are clearing
+         a volatile memory reference.  However, this is possible
+         only if the memory reference has a small offset or is an
+         absolute address.  */
+      else if (GET_CODE (from) == CONST_INT
+               && INTVAL (from) == 0
+               && (MEM_VOLATILE_P (to) == 0
+                   || m68hc11_small_indexed_indirect_p (to, HImode) == 0))
+        {
+          output_asm_insn ("clr\t%h0", operands);
+          output_asm_insn ("clr\t%b0", operands);
+        }
       else
        {
-         rtx from = operands[1];
-         rtx to = operands[0];
-
          if ((m68hc11_register_indirect_p (from, GET_MODE (from))
               && !m68hc11_small_indexed_indirect_p (from, GET_MODE (from)))
              || (m68hc11_register_indirect_p (to, GET_MODE (to))
@@ -3294,6 +3349,7 @@ m68hc11_gen_movhi (rtx insn, rtx *operands)
                  ops[0] = to;
                  ops[1] = operands[2];
                  m68hc11_gen_movhi (insn, ops);
+                  return;
                }
              else
                {
@@ -3301,19 +3357,11 @@ m68hc11_gen_movhi (rtx insn, rtx *operands)
                   fatal_insn ("move insn not handled", insn);
                }
            }
-         else
-           {
-             if (GET_CODE (from) == CONST_INT && INTVAL (from) == 0)
-               {
-                 output_asm_insn ("clr\t%h0", operands);
-                 output_asm_insn ("clr\t%b0", operands);
-               }
-             else
-               {
-                  m68hc11_notice_keep_cc (operands[0]);
-                 output_asm_insn ("movw\t%1,%0", operands);
-               }
-           }
+          else
+            {
+              m68hc11_notice_keep_cc (operands[0]);
+              output_asm_insn ("movw\t%1,%0", operands);
+            }
        }
       return;
     }
@@ -3641,8 +3689,10 @@ m68hc11_gen_movqi (rtx insn, rtx *operands)
        }
       else if (H_REG_P (operands[0]))
        {
-         if (Q_REG_P (operands[0]))
-           output_asm_insn ("lda%0\t%b1", operands);
+          if (IS_STACK_POP (operands[1]))
+            output_asm_insn ("pul%b0", operands);
+         else if (Q_REG_P (operands[0]))
+            output_asm_insn ("lda%0\t%b1", operands);
          else if (D_REG_P (operands[0]))
            output_asm_insn ("ldab\t%b1", operands);
          else
@@ -5006,9 +5056,11 @@ m68hc11_z_replacement (rtx insn)
       if (info.save_before_last)
        save_pos_insn = PREV_INSN (save_pos_insn);
 
-      emit_insn_before (gen_movhi (gen_rtx (REG, HImode, SOFT_Z_REGNUM),
-                                  gen_rtx (REG, HImode, info.regno)),
-                       save_pos_insn);
+      /* Use emit_insn_after () to ensure the new insn is part of
+         the good basic block.  */
+      emit_insn_after (gen_movhi (gen_rtx (REG, HImode, SOFT_Z_REGNUM),
+                                  gen_rtx (REG, HImode, info.regno)),
+                       PREV_INSN (save_pos_insn));
     }
 
   if (info.must_push_reg && info.last)
@@ -5047,8 +5099,8 @@ m68hc11_z_replacement (rtx insn)
       else
        dst = gen_rtx (REG, HImode, SOFT_SAVED_XY_REGNUM);
 
-      emit_insn_before (gen_movhi (gen_rtx (REG, HImode, info.regno),
-                                  dst), insn);
+      emit_insn_after (gen_movhi (gen_rtx (REG, HImode, info.regno),
+                                  dst), PREV_INSN (insn));
     }
 
 }