diff mbox

[committed] Add new bswap and abs patterns to PA

Message ID 1667CDA2-1D36-4B17-AB96-6000967E5D09@bell.net
State New
Headers show

Commit Message

John David Anglin Feb. 14, 2016, 6:35 p.m. UTC
The recent investigation of wrong code for the bswap tree optimization showed that we were
not generating optical bswap sequences on PA.  The PA 2.0 architecture manual shows optimized
sequences for half-word, word and double word variables.  The attached change implements
insn patterns for these operations.  The double word sequence isn't obvious.

In implementing these instructions, I noticed we could implement absqi2 and abshi2 using the
nullification feature of the PA architecture saving a test and branch.

Tested on hppa-unknown-linux-gnu, hppa2.0w-hp-hpux11.11 and hppa64-hp-hpux11.11 with
no observed regressions.

Committed to trunk.

Dave
--
John David Anglin	dave.anglin@bell.net
2016-02-14  John David Anglin  <danglin@gcc.gnu.org>

	* config/pa/pa.md (absqi2, absghi2, bswaphi2, bswapsi2, bswapdi2): New.
diff mbox

Patch

Index: config/pa/pa.md
===================================================================
--- config/pa/pa.md	(revision 233398)
+++ config/pa/pa.md	(working copy)
@@ -1179,6 +1179,22 @@ 
 [(set_attr "type" "multi,multi")
  (set_attr "length" "8,8")])
 
+(define_insn "absqi2"
+  [(set (match_operand:QI 0 "register_operand" "=r")
+	(abs:QI (match_operand:QI 1 "register_operand" "r")))]
+  ""
+  "{extrs|extrw,s},>= %1,31,8,%0\;subi 0,%0,%0"
+  [(set_attr "type" "multi")
+   (set_attr "length" "8")])
+
+(define_insn "abshi2"
+  [(set (match_operand:HI 0 "register_operand" "=r")
+	(abs:HI (match_operand:HI 1 "register_operand" "r")))]
+  ""
+  "{extrs|extrw,s},>= %1,31,16,%0\;subi 0,%0,%0"
+  [(set_attr "type" "multi")
+   (set_attr "length" "8")])
+
 (define_insn "abssi2"
   [(set (match_operand:SI 0 "register_operand" "=r")
 	(abs:SI (match_operand:SI 1 "register_operand" "r")))]
@@ -1195,6 +1211,30 @@ 
   [(set_attr "type" "multi")
    (set_attr "length" "8")])
 
+(define_insn "bswaphi2"
+  [(set (match_operand:HI 0 "register_operand" "=&r")
+	(bswap:HI (match_operand:HI 1 "register_operand" "r")))]
+  ""
+  "{extru|extrw,u} %1,23,8,%0\;{dep|depw} %1,23,8,%0"
+  [(set_attr "type" "multi")
+   (set_attr "length" "8")])
+
+(define_insn "bswapsi2"
+  [(set (match_operand:SI 0 "register_operand" "=&r")
+	(bswap:SI (match_operand:SI 1 "register_operand" "r")))]
+  ""
+  "{shd|shrpw} %1,%1,16,%0\;{dep|depw} %0,15,8,%0\;{shd|shrpw} %1,%0,8,%0"
+  [(set_attr "type" "multi")
+   (set_attr "length" "12")])
+
+(define_insn "bswapdi2"
+  [(set (match_operand:DI 0 "register_operand" "=&r")
+	(bswap:DI (match_operand:DI 1 "register_operand" "+r")))]
+  "TARGET_64BIT"
+  "permh,3210 %1,%1\;hshl %1,8,%0\;hshr,u %1,8,%1\;or %0,%1,%0"
+  [(set_attr "type" "multi")
+   (set_attr "length" "16")])
+
 ;;; Experimental conditional move patterns
 
 (define_expand "movsicc"