summaryrefslogtreecommitdiff
path: root/gcc/config
diff options
context:
space:
mode:
authormeissner <meissner@138bc75d-0d04-0410-961f-82ee72b054a4>2015-11-24 18:46:07 +0000
committermeissner <meissner@138bc75d-0d04-0410-961f-82ee72b054a4>2015-11-24 18:46:07 +0000
commite5840d6591c657edc95afa08ccdea7822d772dbd (patch)
treefd2db6ffd9268ca7529ce5f177fcc6eb023cc9ca /gcc/config
parentd85c5b4fb9e8b2fdcd4bd505fbb9603438e31942 (diff)
downloadgcc-e5840d6591c657edc95afa08ccdea7822d772dbd.tar.gz
2015-11-24 David Edelsohn <dje.gcc@gmail.com>
Michael Meissner <meissner@linux.vnet.ibm.com> * config/rs6000/rs6000.md (UNSPEC_XSRDPI): New unspec. (Fv2): New mode attribute to be used when ISA 2.06 instructions are used on SF/DF values. (abs<mode>2_fpr): Use <Fv2> instead of <Fv>. (nabs<mode>2_fpr): Likewise. (neg<mode>2_fpr): Likewise. (copysign<mode>3_fcpsgn): Likewise. (smax<mode>3_vsx): Likewise. (smin<mode>3_vsx): Likewise. (floatsi<mode>2_lfiwax): Likewise. (floatunssi<mode>2_lfiwz): Likewise. (fctiwz_<mode>): Likewise. (fctiwuz_<mode>): Likewise. (btrunc<mode>2): Likewise. (ceil<mode>2): Likewise. (floor<mode>2): Likewise. (xsrdpi<mode>): Add support for the lround function. (lround<mode>2): Likewise. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@230829 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/config')
-rw-r--r--gcc/config/rs6000/rs6000.md106
1 files changed, 68 insertions, 38 deletions
diff --git a/gcc/config/rs6000/rs6000.md b/gcc/config/rs6000/rs6000.md
index 8c1ddb02a9c..9d3a5b29c3f 100644
--- a/gcc/config/rs6000/rs6000.md
+++ b/gcc/config/rs6000/rs6000.md
@@ -77,6 +77,7 @@
UNSPEC_FRIN
UNSPEC_FRIP
UNSPEC_FRIZ
+ UNSPEC_XSRDPI
UNSPEC_LD_MPIC ; load_macho_picbase
UNSPEC_RELD_MPIC ; re-load_macho_picbase
UNSPEC_MPIC_CORRECT ; macho_correct_pic
@@ -491,8 +492,16 @@
; SF/DF constraint for arithmetic on traditional floating point registers
(define_mode_attr Ff [(SF "f") (DF "d") (DI "d")])
-; SF/DF constraint for arithmetic on VSX registers
-(define_mode_attr Fv [(SF "wy") (DF "ws") (DI "wi")])
+; SF/DF constraint for arithmetic on VSX registers using instructions added in
+; ISA 2.06 (power7). This includes instructions that normally target DF mode,
+; but are used on SFmode, since internally SFmode values are kept in the DFmode
+; format.
+(define_mode_attr Fv [(SF "ww") (DF "ws") (DI "wi")])
+
+; SF/DF constraint for arithmetic on VSX registers. This is intended to be
+; used for DFmode instructions added in ISA 2.06 (power7) and SFmode
+; instructions added in ISA 2.07 (power8)
+(define_mode_attr Fv2 [(SF "wy") (DF "ws") (DI "wi")])
; SF/DF constraint for arithmetic on altivec registers
(define_mode_attr Fa [(SF "wu") (DF "wv")])
@@ -4344,9 +4353,9 @@
"")
(define_insn "*add<mode>3_fpr"
- [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
- (plus:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "%<Ff>,<Fv>")
- (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>")))]
+ [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv2>")
+ (plus:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "%<Ff>,<Fv2>")
+ (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv2>")))]
"TARGET_<MODE>_FPR"
"@
fadd<Ftrad> %0,%1,%2
@@ -4362,9 +4371,9 @@
"")
(define_insn "*sub<mode>3_fpr"
- [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
- (minus:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")
- (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>")))]
+ [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv2>")
+ (minus:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv2>")
+ (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv2>")))]
"TARGET_<MODE>_FPR"
"@
fsub<Ftrad> %0,%1,%2
@@ -4380,9 +4389,9 @@
"")
(define_insn "*mul<mode>3_fpr"
- [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
- (mult:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "%<Ff>,<Fv>")
- (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>")))]
+ [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv2>")
+ (mult:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "%<Ff>,<Fv2>")
+ (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv2>")))]
"TARGET_<MODE>_FPR"
"@
fmul<Ftrad> %0,%1,%2
@@ -4398,9 +4407,9 @@
"")
(define_insn "*div<mode>3_fpr"
- [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
- (div:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")
- (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>")))]
+ [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv2>")
+ (div:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv2>")
+ (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv2>")))]
"TARGET_<MODE>_FPR && !TARGET_SIMPLE_FPU"
"@
fdiv<Ftrad> %0,%1,%2
@@ -4409,8 +4418,8 @@
(set_attr "fp_type" "fp_div_<Fs>")])
(define_insn "sqrt<mode>2"
- [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
- (sqrt:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")))]
+ [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv2>")
+ (sqrt:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv2>")))]
"TARGET_<MODE>_FPR && !TARGET_SIMPLE_FPU
&& (TARGET_PPC_GPOPT || (<MODE>mode == SFmode && TARGET_XILINX_FPU))"
"@
@@ -4421,8 +4430,8 @@
;; Floating point reciprocal approximation
(define_insn "fre<Fs>"
- [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
- (unspec:SFDF [(match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")]
+ [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv2>")
+ (unspec:SFDF [(match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv2>")]
UNSPEC_FRES))]
"TARGET_<FFRE>"
"@
@@ -4431,8 +4440,8 @@
[(set_attr "type" "fp")])
(define_insn "*rsqrt<mode>2"
- [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
- (unspec:SFDF [(match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")]
+ [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv2>")
+ (unspec:SFDF [(match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv2>")]
UNSPEC_RSQRT))]
"RS6000_RECIP_HAVE_RSQRTE_P (<MODE>mode)"
"@
@@ -4443,8 +4452,8 @@
;; Floating point comparisons
(define_insn "*cmp<mode>_fpr"
[(set (match_operand:CCFP 0 "cc_reg_operand" "=y,y")
- (compare:CCFP (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")
- (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>")))]
+ (compare:CCFP (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv2>")
+ (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv2>")))]
"TARGET_<MODE>_FPR"
"@
fcmpu %0,%1,%2
@@ -5500,6 +5509,27 @@
[(set_attr "type" "fp")
(set_attr "fp_type" "fp_addsub_<Fs>")])
+(define_insn "*xsrdpi<mode>2"
+ [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Fv>")
+ (unspec:SFDF [(match_operand:SFDF 1 "gpc_reg_operand" "<Fv>")]
+ UNSPEC_XSRDPI))]
+ "TARGET_<MODE>_FPR && TARGET_VSX"
+ "xsrdpi %x0,%x1"
+ [(set_attr "type" "fp")
+ (set_attr "fp_type" "fp_addsub_<Fs>")])
+
+(define_expand "lround<mode>di2"
+ [(set (match_dup 2)
+ (unspec:SFDF [(match_operand:SFDF 1 "gpc_reg_operand" "wa")]
+ UNSPEC_XSRDPI))
+ (set (match_operand:DI 0 "gpc_reg_operand" "=d")
+ (unspec:DI [(match_dup 2)]
+ UNSPEC_FCTID))]
+ "TARGET_<MODE>_FPR && TARGET_VSX"
+{
+ operands[2] = gen_reg_rtx (<MODE>mode);
+})
+
; An UNSPEC is used so we don't have to support SImode in FP registers.
(define_insn "stfiwx"
[(set (match_operand:SI 0 "memory_operand" "=Z")
@@ -12468,11 +12498,11 @@
"")
(define_insn "*fma<mode>4_fpr"
- [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>,<Fv>")
+ [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv2>,<Fv2>")
(fma:SFDF
- (match_operand:SFDF 1 "gpc_reg_operand" "%<Ff>,<Fv>,<Fv>")
- (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>,0")
- (match_operand:SFDF 3 "gpc_reg_operand" "<Ff>,0,<Fv>")))]
+ (match_operand:SFDF 1 "gpc_reg_operand" "%<Ff>,<Fv2>,<Fv2>")
+ (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv2>,0")
+ (match_operand:SFDF 3 "gpc_reg_operand" "<Ff>,0,<Fv2>")))]
"TARGET_<MODE>_FPR"
"@
fmadd<Ftrad> %0,%1,%2,%3
@@ -12492,11 +12522,11 @@
"")
(define_insn "*fms<mode>4_fpr"
- [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>,<Fv>")
+ [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv2>,<Fv2>")
(fma:SFDF
- (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>,<Fv>")
- (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>,0")
- (neg:SFDF (match_operand:SFDF 3 "gpc_reg_operand" "<Ff>,0,<Fv>"))))]
+ (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv2>,<Fv2>")
+ (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv2>,0")
+ (neg:SFDF (match_operand:SFDF 3 "gpc_reg_operand" "<Ff>,0,<Fv2>"))))]
"TARGET_<MODE>_FPR"
"@
fmsub<Ftrad> %0,%1,%2,%3
@@ -12539,12 +12569,12 @@
"")
(define_insn "*nfma<mode>4_fpr"
- [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>,<Fv>")
+ [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv2>,<Fv2>")
(neg:SFDF
(fma:SFDF
- (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>,<Fv>")
- (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>,0")
- (match_operand:SFDF 3 "gpc_reg_operand" "<Ff>,0,<Fv>"))))]
+ (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv2>,<Fv2>")
+ (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv2>,0")
+ (match_operand:SFDF 3 "gpc_reg_operand" "<Ff>,0,<Fv2>"))))]
"TARGET_<MODE>_FPR"
"@
fnmadd<Ftrad> %0,%1,%2,%3
@@ -12565,13 +12595,13 @@
"")
(define_insn "*nfmssf4_fpr"
- [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>,<Fv>")
+ [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv2>,<Fv2>")
(neg:SFDF
(fma:SFDF
- (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>,<Fv>")
- (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>,0")
+ (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv2>,<Fv2>")
+ (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv2>,0")
(neg:SFDF
- (match_operand:SFDF 3 "gpc_reg_operand" "<Ff>,0,<Fv>")))))]
+ (match_operand:SFDF 3 "gpc_reg_operand" "<Ff>,0,<Fv2>")))))]
"TARGET_<MODE>_FPR"
"@
fnmsub<Ftrad> %0,%1,%2,%3