]> gcc.gnu.org Git - gcc.git/commitdiff
i386.c (ix86_logical_operator): New function.
authorBernd Schmidt <crux@pool.informatik.rwth-aachen.de>
Thu, 12 Mar 1998 12:43:42 +0000 (05:43 -0700)
committerJeff Law <law@gcc.gnu.org>
Thu, 12 Mar 1998 12:43:42 +0000 (05:43 -0700)
        * i386.c (ix86_logical_operator): New function.
        (split_di): Ensure that when a MEM is split, the resulting MEMs have
        SImode.
        * i386.md (anddi3, xordi3, iordi3): New patterns. Add a define_split
        to implement them.

From-SVN: r18514

gcc/ChangeLog
gcc/config/i386/i386.c
gcc/config/i386/i386.md

index 9b08cfcc6262b5736c05622c6babfc8e2196e1c9..f339a1eb02f2f7b2a811aef271ec1237125408d5 100644 (file)
@@ -1,3 +1,11 @@
+Thu Mar 12 13:43:25 1998  Bernd Schmidt <crux@Pool.Informatik.RWTH-Aachen.DE>
+
+       * i386.c (ix86_logical_operator): New function.
+       (split_di): Ensure that when a MEM is split, the resulting MEMs have
+       SImode.
+       * i386.md (anddi3, xordi3, iordi3): New patterns. Add a define_split
+       to implement them.
+
 Thu Mar 12 15:13:16 1998  Kaveh R. Ghazi  <ghazi@caip.rutgers.edu>
                           Richard Earnshaw <rearnsha@arm.com>
                           Nick Clifton  <nickc@cygnus.com>
index 29ce98db81138066348891078fba1b5911b4f6fc..9f565ae18977b4d751631ba82dc5e7c7b7577d08 100644 (file)
@@ -1698,6 +1698,15 @@ arithmetic_comparison_operator (op, mode)
 
   return (code != GT && code != LE);
 }
+
+int
+ix86_logical_operator (op, mode)
+     register rtx op;
+     enum machine_mode mode;
+{
+  return GET_CODE (op) == AND || GET_CODE (op) == IOR || GET_CODE (op) == XOR;
+}
+
 \f
 /* Returns 1 if OP contains a symbol reference */
 
@@ -3688,17 +3697,20 @@ split_di (operands, num, lo_half, hi_half)
 {
   while (num--)
     {
-      if (GET_CODE (operands[num]) == REG)
+      rtx op = operands[num];
+      if (GET_CODE (op) == REG)
        {
-         lo_half[num] = gen_rtx_REG (SImode, REGNO (operands[num]));
-         hi_half[num] = gen_rtx_REG (SImode, REGNO (operands[num]) + 1);
+         lo_half[num] = gen_rtx_REG (SImode, REGNO (op));
+         hi_half[num] = gen_rtx_REG (SImode, REGNO (op) + 1);
        }
-      else if (CONSTANT_P (operands[num]))
-       split_double (operands[num], &lo_half[num], &hi_half[num]);
-      else if (offsettable_memref_p (operands[num]))
+      else if (CONSTANT_P (op))
+       split_double (op, &lo_half[num], &hi_half[num]);
+      else if (offsettable_memref_p (op))
        {
-         lo_half[num] = operands[num];
-         hi_half[num] = adj_offsettable_operand (operands[num], 4);
+         rtx lo_addr = XEXP (op, 0);
+         rtx hi_addr = XEXP (adj_offsettable_operand (op, 4), 0);
+         lo_half[num] = change_address (op, SImode, lo_addr);
+         hi_half[num] = change_address (op, SImode, hi_addr);
        }
       else
        abort();
index a9c84203cec7e1ec948e48557b74fee838438a2a..ae084aee83f90c614e3dd4e4fe16acc564788db0 100644 (file)
@@ -4253,6 +4253,107 @@ byte_xor_operation:
   ""
   "* return AS2 (xor%B0,%2,%0);")
 \f
+;; logical operations for DImode
+
+
+(define_insn "anddi3"
+  [(set (match_operand:DI 0 "general_operand" "=&r,&ro,!r,o,!&r,!o,!o")
+       (and:DI (match_operand:DI 1 "general_operand" "%0,0,0,0iF,or,riF,o")
+               (match_operand:DI 2 "general_operand" "o,riF,0,or,or,oriF,o")))
+   (clobber (match_scratch:SI 3 "=X,X,X,&r,X,&r,&r"))]
+  ""
+  "#")
+
+(define_insn "iordi3"
+  [(set (match_operand:DI 0 "general_operand" "=&r,&ro,!r,o,!&r,!o,!o")
+       (ior:DI (match_operand:DI 1 "general_operand" "%0,0,0,0iF,or,riF,o")
+               (match_operand:DI 2 "general_operand" "o,riF,0,or,or,oriF,o")))
+   (clobber (match_scratch:SI 3 "=X,X,X,&r,X,&r,&r"))]
+  ""
+  "#")
+  
+(define_insn "xordi3"
+  [(set (match_operand:DI 0 "general_operand" "=&r,&ro,!r,o,!&r,!o,!o")
+       (xor:DI (match_operand:DI 1 "general_operand" "%0,0,0,0iF,or,riF,o")
+               (match_operand:DI 2 "general_operand" "o,riF,0,or,or,oriF,o")))
+   (clobber (match_scratch:SI 3 "=X,X,X,&r,X,&r,&r"))]
+  ""
+  "#")
+
+(define_split
+  [(set (match_operand:DI 0 "general_operand" "=&r,&ro,!r,o,!&r,!o,!o")
+       (match_operator:DI 4 "ix86_logical_operator"
+         [(match_operand:DI 1 "general_operand" "%0,0,0,0iF,or,riF,o")
+          (match_operand:DI 2 "general_operand" "o,riF,0,or,or,oriF,o")]))
+   (clobber (match_scratch:SI 3 "=X,X,X,&r,X,&r,&r"))]
+  "reload_completed"
+  [(const_int 0)]
+  "
+{
+  rtx low[3], high[3], xops[7], temp;
+  rtx (*genfunc)() = (GET_CODE (operands[4]) == AND ? gen_andsi3
+                     : GET_CODE (operands[4]) == IOR ? gen_iorsi3
+                     : GET_CODE (operands[4]) == XOR ? gen_xorsi3
+                     : 0);
+
+  if (rtx_equal_p (operands[0], operands[2]))
+    {
+      temp = operands[1];
+      operands[1] = operands[2];
+      operands[2] = temp;
+    }
+
+  split_di (operands, 3, low, high);
+  if (!rtx_equal_p (operands[0], operands[1]))
+    {
+      xops[0] = high[0];
+      xops[1] = low[0];
+      xops[2] = high[1];
+      xops[3] = low[1];
+
+      if (GET_CODE (operands[0]) != MEM)
+       {
+         emit_insn (gen_movsi (xops[1], xops[3]));
+         emit_insn (gen_movsi (xops[0], xops[2]));
+       }
+      else
+       {
+         xops[4] = high[2];
+         xops[5] = low[2];
+         xops[6] = operands[3];
+         emit_insn (gen_movsi (xops[6], xops[3]));
+         emit_insn ((*genfunc) (xops[6], xops[6], xops[5]));
+         emit_insn (gen_movsi (xops[1], xops[6]));
+         emit_insn (gen_movsi (xops[6], xops[2]));
+         emit_insn ((*genfunc) (xops[6], xops[6], xops[4]));
+         emit_insn (gen_movsi (xops[0], xops[6]));
+         DONE;
+       }
+    }
+
+  if (GET_CODE (operands[3]) == REG && GET_CODE (operands[2]) != REG)
+    {
+      xops[0] = high[0];
+      xops[1] = low[0];
+      xops[2] = high[2];
+      xops[3] = low[2];
+      xops[4] = operands[3];
+
+      emit_insn (gen_movsi (xops[4], xops[3]));
+      emit_insn ((*genfunc) (xops[1], xops[1], xops[4]));
+      emit_insn (gen_movsi (xops[4], xops[2]));
+      emit_insn ((*genfunc) (xops[0], xops[0], xops[4]));
+    }
+
+  else
+    {
+      emit_insn ((*genfunc) (low[0], low[0], low[2]));
+      emit_insn ((*genfunc) (high[0], high[0], high[2]));
+    }
+
+  DONE;
+}")
+
 ;;- negation instructions
 
 (define_insn "negdi2"
This page took 0.094156 seconds and 5 git commands to generate.