aboutsummaryrefslogtreecommitdiffstats
path: root/test/CodeGen/Mips
diff options
context:
space:
mode:
authorStephen Hines <srhines@google.com>2014-07-21 00:45:20 -0700
committerStephen Hines <srhines@google.com>2014-07-21 00:45:20 -0700
commitc6a4f5e819217e1e12c458aed8e7b122e23a3a58 (patch)
tree81b7dd2bb4370a392f31d332a566c903b5744764 /test/CodeGen/Mips
parent19c6fbb3e8aaf74093afa08013134b61fa08f245 (diff)
downloadexternal_llvm-c6a4f5e819217e1e12c458aed8e7b122e23a3a58.zip
external_llvm-c6a4f5e819217e1e12c458aed8e7b122e23a3a58.tar.gz
external_llvm-c6a4f5e819217e1e12c458aed8e7b122e23a3a58.tar.bz2
Update LLVM for rebase to r212749.
Includes a cherry-pick of: r212948 - fixes a small issue with atomic calls Change-Id: Ib97bd980b59f18142a69506400911a6009d9df18
Diffstat (limited to 'test/CodeGen/Mips')
-rw-r--r--test/CodeGen/Mips/2008-08-01-AsmInline.ll2
-rw-r--r--test/CodeGen/Mips/2013-11-18-fp64-const0.ll2
-rw-r--r--test/CodeGen/Mips/Fast-ISel/loadstore2.ll83
-rw-r--r--test/CodeGen/Mips/Fast-ISel/simplestorefp1.ll38
-rw-r--r--test/CodeGen/Mips/abiflags-xx.ll6
-rw-r--r--test/CodeGen/Mips/abiflags32.ll12
-rw-r--r--test/CodeGen/Mips/analyzebranch.ll35
-rw-r--r--test/CodeGen/Mips/atomic.ll626
-rw-r--r--test/CodeGen/Mips/atomicops.ll3
-rw-r--r--test/CodeGen/Mips/buildpairextractelementf64.ll4
-rw-r--r--test/CodeGen/Mips/cconv/callee-saved-fpxx.ll58
-rw-r--r--test/CodeGen/Mips/cconv/callee-saved-fpxx1.ll24
-rw-r--r--test/CodeGen/Mips/cmov.ll614
-rw-r--r--test/CodeGen/Mips/countleading.ll90
-rw-r--r--test/CodeGen/Mips/divrem.ll363
-rw-r--r--test/CodeGen/Mips/dsp-r1.ll2
-rw-r--r--test/CodeGen/Mips/eh-return32.ll14
-rw-r--r--test/CodeGen/Mips/eh-return64.ll17
-rw-r--r--test/CodeGen/Mips/ehframe-indirect.ll34
-rw-r--r--test/CodeGen/Mips/fcmp.ll783
-rw-r--r--test/CodeGen/Mips/fcopysign.ll2
-rw-r--r--test/CodeGen/Mips/fmadd1.ll324
-rw-r--r--test/CodeGen/Mips/fp-indexed-ls.ll192
-rw-r--r--test/CodeGen/Mips/fpbr.ll93
-rw-r--r--test/CodeGen/Mips/inlineasm-cnstrnt-reg.ll3
-rw-r--r--test/CodeGen/Mips/lit.local.cfg3
-rw-r--r--test/CodeGen/Mips/llvm-ir/call.ll166
-rw-r--r--test/CodeGen/Mips/llvm-ir/indirectbr.ll34
-rw-r--r--test/CodeGen/Mips/llvm-ir/ret.ll205
-rw-r--r--test/CodeGen/Mips/longbranch.ll34
-rw-r--r--test/CodeGen/Mips/madd-msub.ll241
-rw-r--r--test/CodeGen/Mips/mips16ex.ll4
-rw-r--r--test/CodeGen/Mips/mips64-f128.ll358
-rw-r--r--test/CodeGen/Mips/mips64-fp-indexed-ls.ll110
-rw-r--r--test/CodeGen/Mips/mips64countleading.ll24
-rw-r--r--test/CodeGen/Mips/mips64instrs.ll126
-rw-r--r--test/CodeGen/Mips/mips64muldiv.ll57
-rw-r--r--test/CodeGen/Mips/mno-ldc1-sdc1.ll274
-rw-r--r--test/CodeGen/Mips/msa/special.ll4
-rw-r--r--test/CodeGen/Mips/no-odd-spreg.ll54
-rw-r--r--test/CodeGen/Mips/null-streamer.ll7
-rw-r--r--test/CodeGen/Mips/prevent-hoisting.ll144
-rw-r--r--test/CodeGen/Mips/select.ll800
-rw-r--r--test/CodeGen/Mips/selectcc.ll14
-rw-r--r--test/CodeGen/Mips/tls-alias.ll2
-rw-r--r--test/CodeGen/Mips/zeroreg.ll98
46 files changed, 5166 insertions, 1017 deletions
diff --git a/test/CodeGen/Mips/2008-08-01-AsmInline.ll b/test/CodeGen/Mips/2008-08-01-AsmInline.ll
index e274bc0..3c1bb39 100644
--- a/test/CodeGen/Mips/2008-08-01-AsmInline.ll
+++ b/test/CodeGen/Mips/2008-08-01-AsmInline.ll
@@ -1,4 +1,4 @@
-; RUN: llc -march=mips < %s | FileCheck %s
+; RUN: llc -march=mips -mcpu=mips32 < %s | FileCheck %s
; RUN: llc -march=mips64el -mcpu=mips64r2 -mattr=n64 < %s | FileCheck %s
%struct.DWstruct = type { i32, i32 }
diff --git a/test/CodeGen/Mips/2013-11-18-fp64-const0.ll b/test/CodeGen/Mips/2013-11-18-fp64-const0.ll
index f8390d9..6a210a0 100644
--- a/test/CodeGen/Mips/2013-11-18-fp64-const0.ll
+++ b/test/CodeGen/Mips/2013-11-18-fp64-const0.ll
@@ -1,5 +1,5 @@
; RUN: llc -march=mips -mattr=-fp64 < %s | FileCheck -check-prefix=CHECK-FP32 %s
-; RUN: llc -march=mips -mattr=+fp64 < %s | FileCheck -check-prefix=CHECK-FP64 %s
+; RUN: llc -march=mips -mcpu=mips32r2 -mattr=+fp64 < %s | FileCheck -check-prefix=CHECK-FP64 %s
; This test case is a simplified version of an llvm-stress generated test with
; seed=3718491962.
diff --git a/test/CodeGen/Mips/Fast-ISel/loadstore2.ll b/test/CodeGen/Mips/Fast-ISel/loadstore2.ll
new file mode 100644
index 0000000..f113a0e
--- /dev/null
+++ b/test/CodeGen/Mips/Fast-ISel/loadstore2.ll
@@ -0,0 +1,83 @@
+; ModuleID = 'loadstore2.c'
+target datalayout = "E-m:m-p:32:32-i8:8:32-i16:16:32-i64:64-n32-S64"
+target triple = "mips--linux-gnu"
+
+@c2 = common global i8 0, align 1
+@c1 = common global i8 0, align 1
+; RUN: llc -march=mipsel -relocation-model=pic -O0 -mips-fast-isel -fast-isel-abort -mcpu=mips32r2 \
+; RUN: < %s | FileCheck %s
+
+@s2 = common global i16 0, align 2
+@s1 = common global i16 0, align 2
+@i2 = common global i32 0, align 4
+@i1 = common global i32 0, align 4
+@f2 = common global float 0.000000e+00, align 4
+@f1 = common global float 0.000000e+00, align 4
+@d2 = common global double 0.000000e+00, align 8
+@d1 = common global double 0.000000e+00, align 8
+
+; Function Attrs: nounwind
+define void @cfoo() #0 {
+entry:
+ %0 = load i8* @c2, align 1
+ store i8 %0, i8* @c1, align 1
+; CHECK-LABEL: cfoo:
+; CHECK: lbu $[[REGc:[0-9]+]], 0(${{[0-9]+}})
+; CHECK: sb $[[REGc]], 0(${{[0-9]+}})
+
+
+ ret void
+}
+
+; Function Attrs: nounwind
+define void @sfoo() #0 {
+entry:
+ %0 = load i16* @s2, align 2
+ store i16 %0, i16* @s1, align 2
+; CHECK-LABEL: sfoo:
+; CHECK: lhu $[[REGs:[0-9]+]], 0(${{[0-9]+}})
+; CHECK: sh $[[REGs]], 0(${{[0-9]+}})
+
+ ret void
+}
+
+; Function Attrs: nounwind
+define void @ifoo() #0 {
+entry:
+ %0 = load i32* @i2, align 4
+ store i32 %0, i32* @i1, align 4
+; CHECK-LABEL: ifoo:
+; CHECK: lw $[[REGi:[0-9]+]], 0(${{[0-9]+}})
+; CHECK: sw $[[REGi]], 0(${{[0-9]+}})
+
+ ret void
+}
+
+; Function Attrs: nounwind
+define void @ffoo() #0 {
+entry:
+ %0 = load float* @f2, align 4
+ store float %0, float* @f1, align 4
+; CHECK-LABEL: ffoo:
+; CHECK: lwc1 $f[[REGf:[0-9]+]], 0(${{[0-9]+}})
+; CHECK: swc1 $f[[REGf]], 0(${{[0-9]+}})
+
+
+ ret void
+}
+
+; Function Attrs: nounwind
+define void @dfoo() #0 {
+entry:
+ %0 = load double* @d2, align 8
+ store double %0, double* @d1, align 8
+; CHECK-LABEL: dfoo:
+; CHECK: ldc1 $f[[REGd:[0-9]+]], 0(${{[0-9]+}})
+; CHECK: sdc1 $f[[REGd]], 0(${{[0-9]+}})
+; CHECK: .end dfoo
+ ret void
+}
+
+attributes #0 = { nounwind "less-precise-fpmad"="false" "no-frame-pointer-elim"="true" "no-frame-pointer-elim-non-leaf" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "stack-protector-buffer-size"="8" "unsafe-fp-math"="false" "use-soft-float"="false" }
+
+
diff --git a/test/CodeGen/Mips/Fast-ISel/simplestorefp1.ll b/test/CodeGen/Mips/Fast-ISel/simplestorefp1.ll
new file mode 100644
index 0000000..6759c01
--- /dev/null
+++ b/test/CodeGen/Mips/Fast-ISel/simplestorefp1.ll
@@ -0,0 +1,38 @@
+; RUN: llc -march=mipsel -relocation-model=pic -O0 -mips-fast-isel -fast-isel-abort -mcpu=mips32r2 \
+; RUN: < %s | FileCheck %s
+
+@f = common global float 0.000000e+00, align 4
+@de = common global double 0.000000e+00, align 8
+
+; Function Attrs: nounwind
+define void @f1() #0 {
+entry:
+ store float 0x3FFA76C8C0000000, float* @f, align 4
+ ret void
+; CHECK: .ent f1
+; CHECK: lui $[[REG1:[0-9]+]], 16339
+; CHECK: ori $[[REG2:[0-9]+]], $[[REG1]], 46662
+; CHECK: mtc1 $[[REG2]], $f[[REG3:[0-9]+]]
+; CHECK: lw $[[REG4:[0-9]+]], %got(f)(${{[0-9]+}})
+; CHECK: swc1 $f[[REG3]], 0($[[REG4]])
+; CHECK: .end f1
+
+}
+
+; Function Attrs: nounwind
+define void @d1() #0 {
+entry:
+ store double 1.234567e+00, double* @de, align 8
+; CHECK: .ent d1
+; CHECK: lui $[[REG1a:[0-9]+]], 16371
+; CHECK: ori $[[REG2a:[0-9]+]], $[[REG1a]], 49353
+; CHECK: lui $[[REG1b:[0-9]+]], 21403
+; CHECK: ori $[[REG2b:[0-9]+]], $[[REG1b]], 34951
+; CHECK: mtc1 $[[REG2b]], $f[[REG3:[0-9]+]]
+; CHECK: mthc1 $[[REG2a]], $f[[REG3]]
+; CHECK: sdc1 $f[[REG3]], 0(${{[0-9]+}})
+; CHECK: .end d1
+ ret void
+}
+
+attributes #0 = { nounwind "less-precise-fpmad"="false" "no-frame-pointer-elim"="true" "no-frame-pointer-elim-non-leaf" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "stack-protector-buffer-size"="8" "unsafe-fp-math"="false" "use-soft-float"="false" }
diff --git a/test/CodeGen/Mips/abiflags-xx.ll b/test/CodeGen/Mips/abiflags-xx.ll
new file mode 100644
index 0000000..b8aa071
--- /dev/null
+++ b/test/CodeGen/Mips/abiflags-xx.ll
@@ -0,0 +1,6 @@
+; RUN: llc -filetype=asm -mtriple mipsel-unknown-linux -mcpu=mips32 -mattr=fpxx %s -o - | FileCheck %s
+; XFAIL: *
+
+; CHECK: .nan legacy
+; CHECK: .module fp=xx
+
diff --git a/test/CodeGen/Mips/abiflags32.ll b/test/CodeGen/Mips/abiflags32.ll
new file mode 100644
index 0000000..093964f
--- /dev/null
+++ b/test/CodeGen/Mips/abiflags32.ll
@@ -0,0 +1,12 @@
+; RUN: llc -filetype=asm -mtriple mipsel-unknown-linux -mcpu=mips32 %s -o - | FileCheck %s
+; RUN: llc -filetype=asm -mtriple mipsel-unknown-linux -mcpu=mips32 -mattr=fp64 %s -o - | FileCheck -check-prefix=CHECK-64 %s
+; RUN: llc -filetype=asm -mtriple mipsel-unknown-linux -mcpu=mips64 -mattr=-n64,n32 %s -o - | FileCheck -check-prefix=CHECK-64n %s
+
+; CHECK: .nan legacy
+; CHECK: .module fp=32
+
+; CHECK-64: .nan legacy
+; CHECK-64: .module fp=64
+
+; CHECK-64n: .nan legacy
+; CHECK-64n: .module fp=64
diff --git a/test/CodeGen/Mips/analyzebranch.ll b/test/CodeGen/Mips/analyzebranch.ll
index 8ec5d93..4b5d097 100644
--- a/test/CodeGen/Mips/analyzebranch.ll
+++ b/test/CodeGen/Mips/analyzebranch.ll
@@ -1,9 +1,25 @@
-; RUN: llc -march=mips < %s | FileCheck %s
+; RUN: llc -march=mips -mcpu=mips32 < %s | FileCheck %s -check-prefix=ALL -check-prefix=FCC
+; RUN: llc -march=mips -mcpu=mips32r2 < %s | FileCheck %s -check-prefix=ALL -check-prefix=FCC
+; RUN: llc -march=mips -mcpu=mips32r6 < %s | FileCheck %s -check-prefix=ALL -check-prefix=GPR -check-prefix=32-GPR
+; RUN: llc -march=mips64 -mcpu=mips4 < %s | FileCheck %s -check-prefix=ALL -check-prefix=FCC
+; RUN: llc -march=mips64 -mcpu=mips64 < %s | FileCheck %s -check-prefix=ALL -check-prefix=FCC
+; RUN: llc -march=mips64 -mcpu=mips64r2 < %s | FileCheck %s -check-prefix=ALL -check-prefix=FCC
+; RUN: llc -march=mips64 -mcpu=mips64r6 < %s | FileCheck %s -check-prefix=ALL -check-prefix=GPR -check-prefix=64-GPR
define double @foo(double %a, double %b) nounwind readnone {
entry:
-; CHECK: bc1f $BB
-; CHECK: nop
+; ALL-LABEL: foo:
+
+; FCC: bc1f $BB
+; FCC: nop
+
+; 32-GPR: mtc1 $zero, $[[Z:f[0-9]]]
+; 32-GPR: mthc1 $zero, $[[Z:f[0-9]]]
+; 64-GPR: dmtc1 $zero, $[[Z:f[0-9]]]
+; GPR: cmp.lt.d $[[FGRCC:f[0-9]+]], $[[Z]], $f12
+; GPR: mfc1 $[[GPRCC:[0-9]+]], $[[FGRCC]]
+; GPR-NOT: not $[[GPRCC]], $[[GPRCC]]
+; GPR: bnez $[[GPRCC]], $BB
%cmp = fcmp ogt double %a, 0.000000e+00
br i1 %cmp, label %if.end6, label %if.else
@@ -25,8 +41,17 @@ return: ; preds = %if.else, %if.end6
define void @f1(float %f) nounwind {
entry:
-; CHECK: bc1f $BB
-; CHECK: nop
+; ALL-LABEL: f1:
+
+; FCC: bc1f $BB
+; FCC: nop
+
+; GPR: mtc1 $zero, $[[Z:f[0-9]]]
+; GPR: cmp.eq.s $[[FGRCC:f[0-9]+]], $f12, $[[Z]]
+; GPR: mfc1 $[[GPRCC:[0-9]+]], $[[FGRCC]]
+; GPR-NOT: not $[[GPRCC]], $[[GPRCC]]
+; GPR: beqz $[[GPRCC]], $BB
+
%cmp = fcmp une float %f, 0.000000e+00
br i1 %cmp, label %if.then, label %if.end
diff --git a/test/CodeGen/Mips/atomic.ll b/test/CodeGen/Mips/atomic.ll
index 77d7bf3..066d42c 100644
--- a/test/CodeGen/Mips/atomic.ll
+++ b/test/CodeGen/Mips/atomic.ll
@@ -1,5 +1,14 @@
-; RUN: llc -march=mipsel --disable-machine-licm < %s | FileCheck %s -check-prefix=CHECK-EL
-; RUN: llc -march=mips --disable-machine-licm < %s | FileCheck %s -check-prefix=CHECK-EB
+; RUN: llc -march=mipsel --disable-machine-licm -mcpu=mips32 < %s | FileCheck %s -check-prefix=ALL -check-prefix=MIPS32-ANY -check-prefix=NO-SEB-SEH -check-prefix=CHECK-EL
+; RUN: llc -march=mipsel --disable-machine-licm -mcpu=mips32r2 < %s | FileCheck %s -check-prefix=ALL -check-prefix=MIPS32-ANY -check-prefix=HAS-SEB-SEH -check-prefix=CHECK-EL
+; RUN: llc -march=mipsel --disable-machine-licm -mcpu=mips32r6 < %s | FileCheck %s -check-prefix=ALL -check-prefix=MIPS32-ANY -check-prefix=HAS-SEB-SEH -check-prefix=CHECK-EL
+; RUN: llc -march=mips64el --disable-machine-licm -mcpu=mips4 < %s | FileCheck %s -check-prefix=ALL -check-prefix=MIPS64-ANY -check-prefix=NO-SEB-SEH -check-prefix=CHECK-EL
+; RUN: llc -march=mips64el --disable-machine-licm -mcpu=mips64 < %s | FileCheck %s -check-prefix=ALL -check-prefix=MIPS64-ANY -check-prefix=NO-SEB-SEH -check-prefix=CHECK-EL
+; RUN: llc -march=mips64el --disable-machine-licm -mcpu=mips64r2 < %s | FileCheck %s -check-prefix=ALL -check-prefix=MIPS64-ANY -check-prefix=HAS-SEB-SEH -check-prefix=CHECK-EL
+; RUN: llc -march=mips64el --disable-machine-licm -mcpu=mips64r6 < %s | FileCheck %s -check-prefix=ALL -check-prefix=MIPS64-ANY -check-prefix=HAS-SEB-SEH -check-prefix=CHECK-EL
+
+; Keep one big-endian check so that we don't reduce testing, but don't add more
+; since endianness doesn't affect the body of the atomic operations.
+; RUN: llc -march=mips --disable-machine-licm -mcpu=mips32 < %s | FileCheck %s -check-prefix=ALL -check-prefix=MIPS32-ANY -check-prefix=CHECK-EB
@x = common global i32 0, align 4
@@ -8,21 +17,16 @@ entry:
%0 = atomicrmw add i32* @x, i32 %incr monotonic
ret i32 %0
-; CHECK-EL-LABEL: AtomicLoadAdd32:
-; CHECK-EL: lw $[[R0:[0-9]+]], %got(x)
-; CHECK-EL: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EL: ll $[[R1:[0-9]+]], 0($[[R0]])
-; CHECK-EL: addu $[[R2:[0-9]+]], $[[R1]], $4
-; CHECK-EL: sc $[[R2]], 0($[[R0]])
-; CHECK-EL: beqz $[[R2]], $[[BB0]]
-
-; CHECK-EB-LABEL: AtomicLoadAdd32:
-; CHECK-EB: lw $[[R0:[0-9]+]], %got(x)
-; CHECK-EB: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EB: ll $[[R1:[0-9]+]], 0($[[R0]])
-; CHECK-EB: addu $[[R2:[0-9]+]], $[[R1]], $4
-; CHECK-EB: sc $[[R2]], 0($[[R0]])
-; CHECK-EB: beqz $[[R2]], $[[BB0]]
+; ALL-LABEL: AtomicLoadAdd32:
+
+; MIPS32-ANY: lw $[[R0:[0-9]+]], %got(x)
+; MIPS64-ANY: ld $[[R0:[0-9]+]], %got_disp(x)(
+
+; ALL: $[[BB0:[A-Z_0-9]+]]:
+; ALL: ll $[[R1:[0-9]+]], 0($[[R0]])
+; ALL: addu $[[R2:[0-9]+]], $[[R1]], $4
+; ALL: sc $[[R2]], 0($[[R0]])
+; ALL: beqz $[[R2]], $[[BB0]]
}
define i32 @AtomicLoadNand32(i32 %incr) nounwind {
@@ -30,23 +34,17 @@ entry:
%0 = atomicrmw nand i32* @x, i32 %incr monotonic
ret i32 %0
-; CHECK-EL-LABEL: AtomicLoadNand32:
-; CHECK-EL: lw $[[R0:[0-9]+]], %got(x)
-; CHECK-EL: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EL: ll $[[R1:[0-9]+]], 0($[[R0]])
-; CHECK-EL: and $[[R3:[0-9]+]], $[[R1]], $4
-; CHECK-EL: nor $[[R2:[0-9]+]], $zero, $[[R3]]
-; CHECK-EL: sc $[[R2]], 0($[[R0]])
-; CHECK-EL: beqz $[[R2]], $[[BB0]]
-
-; CHECK-EB-LABEL: AtomicLoadNand32:
-; CHECK-EB: lw $[[R0:[0-9]+]], %got(x)
-; CHECK-EB: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EB: ll $[[R1:[0-9]+]], 0($[[R0]])
-; CHECK-EB: and $[[R3:[0-9]+]], $[[R1]], $4
-; CHECK-EB: nor $[[R2:[0-9]+]], $zero, $[[R3]]
-; CHECK-EB: sc $[[R2]], 0($[[R0]])
-; CHECK-EB: beqz $[[R2]], $[[BB0]]
+; ALL-LABEL: AtomicLoadNand32:
+
+; MIPS32-ANY: lw $[[R0:[0-9]+]], %got(x)
+; MIPS64-ANY: ld $[[R0:[0-9]+]], %got_disp(x)(
+
+; ALL: $[[BB0:[A-Z_0-9]+]]:
+; ALL: ll $[[R1:[0-9]+]], 0($[[R0]])
+; ALL: and $[[R3:[0-9]+]], $[[R1]], $4
+; ALL: nor $[[R2:[0-9]+]], $zero, $[[R3]]
+; ALL: sc $[[R2]], 0($[[R0]])
+; ALL: beqz $[[R2]], $[[BB0]]
}
define i32 @AtomicSwap32(i32 %newval) nounwind {
@@ -57,19 +55,15 @@ entry:
%0 = atomicrmw xchg i32* @x, i32 %tmp monotonic
ret i32 %0
-; CHECK-EL-LABEL: AtomicSwap32:
-; CHECK-EL: lw $[[R0:[0-9]+]], %got(x)
-; CHECK-EL: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EL: ll ${{[0-9]+}}, 0($[[R0]])
-; CHECK-EL: sc $[[R2:[0-9]+]], 0($[[R0]])
-; CHECK-EL: beqz $[[R2]], $[[BB0]]
-
-; CHECK-EB-LABEL: AtomicSwap32:
-; CHECK-EB: lw $[[R0:[0-9]+]], %got(x)
-; CHECK-EB: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EB: ll ${{[0-9]+}}, 0($[[R0]])
-; CHECK-EB: sc $[[R2:[0-9]+]], 0($[[R0]])
-; CHECK-EB: beqz $[[R2]], $[[BB0]]
+; ALL-LABEL: AtomicSwap32:
+
+; MIPS32-ANY: lw $[[R0:[0-9]+]], %got(x)
+; MIPS64-ANY: ld $[[R0:[0-9]+]], %got_disp(x)
+
+; ALL: $[[BB0:[A-Z_0-9]+]]:
+; ALL: ll ${{[0-9]+}}, 0($[[R0]])
+; ALL: sc $[[R2:[0-9]+]], 0($[[R0]])
+; ALL: beqz $[[R2]], $[[BB0]]
}
define i32 @AtomicCmpSwap32(i32 %oldval, i32 %newval) nounwind {
@@ -78,25 +72,20 @@ entry:
store i32 %newval, i32* %newval.addr, align 4
%tmp = load i32* %newval.addr, align 4
%0 = cmpxchg i32* @x, i32 %oldval, i32 %tmp monotonic monotonic
- ret i32 %0
+ %1 = extractvalue { i32, i1 } %0, 0
+ ret i32 %1
+
+; ALL-LABEL: AtomicCmpSwap32:
-; CHECK-EL-LABEL: AtomicCmpSwap32:
-; CHECK-EL: lw $[[R0:[0-9]+]], %got(x)
-; CHECK-EL: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EL: ll $2, 0($[[R0]])
-; CHECK-EL: bne $2, $4, $[[BB1:[A-Z_0-9]+]]
-; CHECK-EL: sc $[[R2:[0-9]+]], 0($[[R0]])
-; CHECK-EL: beqz $[[R2]], $[[BB0]]
-; CHECK-EL: $[[BB1]]:
-
-; CHECK-EB-LABEL: AtomicCmpSwap32:
-; CHECK-EB: lw $[[R0:[0-9]+]], %got(x)
-; CHECK-EB: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EB: ll $2, 0($[[R0]])
-; CHECK-EB: bne $2, $4, $[[BB1:[A-Z_0-9]+]]
-; CHECK-EB: sc $[[R2:[0-9]+]], 0($[[R0]])
-; CHECK-EB: beqz $[[R2]], $[[BB0]]
-; CHECK-EB: $[[BB1]]:
+; MIPS32-ANY: lw $[[R0:[0-9]+]], %got(x)
+; MIPS64-ANY: ld $[[R0:[0-9]+]], %got_disp(x)(
+
+; ALL: $[[BB0:[A-Z_0-9]+]]:
+; ALL: ll $2, 0($[[R0]])
+; ALL: bne $2, $4, $[[BB1:[A-Z_0-9]+]]
+; ALL: sc $[[R2:[0-9]+]], 0($[[R0]])
+; ALL: beqz $[[R2]], $[[BB0]]
+; ALL: $[[BB1]]:
}
@@ -108,56 +97,38 @@ entry:
%0 = atomicrmw add i8* @y, i8 %incr monotonic
ret i8 %0
-; CHECK-EL-LABEL: AtomicLoadAdd8:
-; CHECK-EL: lw $[[R0:[0-9]+]], %got(y)
-; CHECK-EL: addiu $[[R1:[0-9]+]], $zero, -4
-; CHECK-EL: and $[[R2:[0-9]+]], $[[R0]], $[[R1]]
-; CHECK-EL: andi $[[R3:[0-9]+]], $[[R0]], 3
-; CHECK-EL: sll $[[R4:[0-9]+]], $[[R3]], 3
-; CHECK-EL: ori $[[R5:[0-9]+]], $zero, 255
-; CHECK-EL: sllv $[[R6:[0-9]+]], $[[R5]], $[[R4]]
-; CHECK-EL: nor $[[R7:[0-9]+]], $zero, $[[R6]]
-; CHECK-EL: sllv $[[R9:[0-9]+]], $4, $[[R4]]
-
-; CHECK-EL: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EL: ll $[[R10:[0-9]+]], 0($[[R2]])
-; CHECK-EL: addu $[[R11:[0-9]+]], $[[R10]], $[[R9]]
-; CHECK-EL: and $[[R12:[0-9]+]], $[[R11]], $[[R6]]
-; CHECK-EL: and $[[R13:[0-9]+]], $[[R10]], $[[R7]]
-; CHECK-EL: or $[[R14:[0-9]+]], $[[R13]], $[[R12]]
-; CHECK-EL: sc $[[R14]], 0($[[R2]])
-; CHECK-EL: beqz $[[R14]], $[[BB0]]
-
-; CHECK-EL: and $[[R15:[0-9]+]], $[[R10]], $[[R6]]
-; CHECK-EL: srlv $[[R16:[0-9]+]], $[[R15]], $[[R4]]
-; CHECK-EL: sll $[[R17:[0-9]+]], $[[R16]], 24
-; CHECK-EL: sra $2, $[[R17]], 24
-
-; CHECK-EB-LABEL: AtomicLoadAdd8:
-; CHECK-EB: lw $[[R0:[0-9]+]], %got(y)
-; CHECK-EB: addiu $[[R1:[0-9]+]], $zero, -4
-; CHECK-EB: and $[[R2:[0-9]+]], $[[R0]], $[[R1]]
-; CHECK-EB: andi $[[R3:[0-9]+]], $[[R0]], 3
-; CHECK-EB: xori $[[R4:[0-9]+]], $[[R3]], 3
-; CHECK-EB: sll $[[R5:[0-9]+]], $[[R4]], 3
-; CHECK-EB: ori $[[R6:[0-9]+]], $zero, 255
-; CHECK-EB: sllv $[[R7:[0-9]+]], $[[R6]], $[[R5]]
-; CHECK-EB: nor $[[R8:[0-9]+]], $zero, $[[R7]]
-; CHECK-EB: sllv $[[R9:[0-9]+]], $4, $[[R5]]
-
-; CHECK-EB: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EB: ll $[[R10:[0-9]+]], 0($[[R2]])
-; CHECK-EB: addu $[[R11:[0-9]+]], $[[R10]], $[[R9]]
-; CHECK-EB: and $[[R12:[0-9]+]], $[[R11]], $[[R7]]
-; CHECK-EB: and $[[R13:[0-9]+]], $[[R10]], $[[R8]]
-; CHECK-EB: or $[[R14:[0-9]+]], $[[R13]], $[[R12]]
-; CHECK-EB: sc $[[R14]], 0($[[R2]])
-; CHECK-EB: beqz $[[R14]], $[[BB0]]
-
-; CHECK-EB: and $[[R15:[0-9]+]], $[[R10]], $[[R7]]
-; CHECK-EB: srlv $[[R16:[0-9]+]], $[[R15]], $[[R5]]
-; CHECK-EB: sll $[[R17:[0-9]+]], $[[R16]], 24
-; CHECK-EB: sra $2, $[[R17]], 24
+; ALL-LABEL: AtomicLoadAdd8:
+
+; MIPS32-ANY: lw $[[R0:[0-9]+]], %got(y)
+; MIPS64-ANY: ld $[[R0:[0-9]+]], %got_disp(y)(
+
+; ALL: addiu $[[R1:[0-9]+]], $zero, -4
+; ALL: and $[[R2:[0-9]+]], $[[R0]], $[[R1]]
+; ALL: andi $[[R3:[0-9]+]], $[[R0]], 3
+; CHECK-EB: xori $[[R4:[0-9]+]], $[[R3]], 3
+; CHECK-EB: sll $[[R5:[0-9]+]], $[[R4]], 3
+; CHECK-EL: sll $[[R5:[0-9]+]], $[[R3]], 3
+; ALL: ori $[[R6:[0-9]+]], $zero, 255
+; ALL: sllv $[[R7:[0-9]+]], $[[R6]], $[[R5]]
+; ALL: nor $[[R8:[0-9]+]], $zero, $[[R7]]
+; ALL: sllv $[[R9:[0-9]+]], $4, $[[R5]]
+
+; ALL: $[[BB0:[A-Z_0-9]+]]:
+; ALL: ll $[[R10:[0-9]+]], 0($[[R2]])
+; ALL: addu $[[R11:[0-9]+]], $[[R10]], $[[R9]]
+; ALL: and $[[R12:[0-9]+]], $[[R11]], $[[R7]]
+; ALL: and $[[R13:[0-9]+]], $[[R10]], $[[R8]]
+; ALL: or $[[R14:[0-9]+]], $[[R13]], $[[R12]]
+; ALL: sc $[[R14]], 0($[[R2]])
+; ALL: beqz $[[R14]], $[[BB0]]
+
+; ALL: and $[[R15:[0-9]+]], $[[R10]], $[[R7]]
+; ALL: srlv $[[R16:[0-9]+]], $[[R15]], $[[R5]]
+
+; NO-SEB-SEH: sll $[[R17:[0-9]+]], $[[R16]], 24
+; NO-SEB-SEH: sra $2, $[[R17]], 24
+
+; HAS-SEB-SEH: seb $2, $[[R16]]
}
define signext i8 @AtomicLoadSub8(i8 signext %incr) nounwind {
@@ -165,56 +136,38 @@ entry:
%0 = atomicrmw sub i8* @y, i8 %incr monotonic
ret i8 %0
-; CHECK-EL-LABEL: AtomicLoadSub8:
-; CHECK-EL: lw $[[R0:[0-9]+]], %got(y)
-; CHECK-EL: addiu $[[R1:[0-9]+]], $zero, -4
-; CHECK-EL: and $[[R2:[0-9]+]], $[[R0]], $[[R1]]
-; CHECK-EL: andi $[[R3:[0-9]+]], $[[R0]], 3
-; CHECK-EL: sll $[[R4:[0-9]+]], $[[R3]], 3
-; CHECK-EL: ori $[[R5:[0-9]+]], $zero, 255
-; CHECK-EL: sllv $[[R6:[0-9]+]], $[[R5]], $[[R4]]
-; CHECK-EL: nor $[[R7:[0-9]+]], $zero, $[[R6]]
-; CHECK-EL: sllv $[[R9:[0-9]+]], $4, $[[R4]]
-
-; CHECK-EL: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EL: ll $[[R10:[0-9]+]], 0($[[R2]])
-; CHECK-EL: subu $[[R11:[0-9]+]], $[[R10]], $[[R9]]
-; CHECK-EL: and $[[R12:[0-9]+]], $[[R11]], $[[R6]]
-; CHECK-EL: and $[[R13:[0-9]+]], $[[R10]], $[[R7]]
-; CHECK-EL: or $[[R14:[0-9]+]], $[[R13]], $[[R12]]
-; CHECK-EL: sc $[[R14]], 0($[[R2]])
-; CHECK-EL: beqz $[[R14]], $[[BB0]]
-
-; CHECK-EL: and $[[R15:[0-9]+]], $[[R10]], $[[R6]]
-; CHECK-EL: srlv $[[R16:[0-9]+]], $[[R15]], $[[R4]]
-; CHECK-EL: sll $[[R17:[0-9]+]], $[[R16]], 24
-; CHECK-EL: sra $2, $[[R17]], 24
-
-; CHECK-EB-LABEL: AtomicLoadSub8:
-; CHECK-EB: lw $[[R0:[0-9]+]], %got(y)
-; CHECK-EB: addiu $[[R1:[0-9]+]], $zero, -4
-; CHECK-EB: and $[[R2:[0-9]+]], $[[R0]], $[[R1]]
-; CHECK-EB: andi $[[R3:[0-9]+]], $[[R0]], 3
+; ALL-LABEL: AtomicLoadSub8:
+
+; MIPS32-ANY: lw $[[R0:[0-9]+]], %got(y)
+; MIPS64-ANY: ld $[[R0:[0-9]+]], %got_disp(y)(
+
+; ALL: addiu $[[R1:[0-9]+]], $zero, -4
+; ALL: and $[[R2:[0-9]+]], $[[R0]], $[[R1]]
+; ALL: andi $[[R3:[0-9]+]], $[[R0]], 3
+; CHECK-EL: sll $[[R5:[0-9]+]], $[[R3]], 3
; CHECK-EB: xori $[[R4:[0-9]+]], $[[R3]], 3
; CHECK-EB: sll $[[R5:[0-9]+]], $[[R4]], 3
-; CHECK-EB: ori $[[R6:[0-9]+]], $zero, 255
-; CHECK-EB: sllv $[[R7:[0-9]+]], $[[R6]], $[[R5]]
-; CHECK-EB: nor $[[R8:[0-9]+]], $zero, $[[R7]]
-; CHECK-EB: sllv $[[R9:[0-9]+]], $4, $[[R5]]
-
-; CHECK-EB: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EB: ll $[[R10:[0-9]+]], 0($[[R2]])
-; CHECK-EB: subu $[[R11:[0-9]+]], $[[R10]], $[[R9]]
-; CHECK-EB: and $[[R12:[0-9]+]], $[[R11]], $[[R7]]
-; CHECK-EB: and $[[R13:[0-9]+]], $[[R10]], $[[R8]]
-; CHECK-EB: or $[[R14:[0-9]+]], $[[R13]], $[[R12]]
-; CHECK-EB: sc $[[R14]], 0($[[R2]])
-; CHECK-EB: beqz $[[R14]], $[[BB0]]
-
-; CHECK-EB: and $[[R15:[0-9]+]], $[[R10]], $[[R7]]
-; CHECK-EB: srlv $[[R16:[0-9]+]], $[[R15]], $[[R5]]
-; CHECK-EB: sll $[[R17:[0-9]+]], $[[R16]], 24
-; CHECK-EB: sra $2, $[[R17]], 24
+; ALL: ori $[[R6:[0-9]+]], $zero, 255
+; ALL: sllv $[[R7:[0-9]+]], $[[R6]], $[[R5]]
+; ALL: nor $[[R8:[0-9]+]], $zero, $[[R7]]
+; ALL: sllv $[[R9:[0-9]+]], $4, $[[R5]]
+
+; ALL: $[[BB0:[A-Z_0-9]+]]:
+; ALL: ll $[[R10:[0-9]+]], 0($[[R2]])
+; ALL: subu $[[R11:[0-9]+]], $[[R10]], $[[R9]]
+; ALL: and $[[R12:[0-9]+]], $[[R11]], $[[R7]]
+; ALL: and $[[R13:[0-9]+]], $[[R10]], $[[R8]]
+; ALL: or $[[R14:[0-9]+]], $[[R13]], $[[R12]]
+; ALL: sc $[[R14]], 0($[[R2]])
+; ALL: beqz $[[R14]], $[[BB0]]
+
+; ALL: and $[[R15:[0-9]+]], $[[R10]], $[[R7]]
+; ALL: srlv $[[R16:[0-9]+]], $[[R15]], $[[R5]]
+
+; NO-SEB-SEH: sll $[[R17:[0-9]+]], $[[R16]], 24
+; NO-SEB-SEH: sra $2, $[[R17]], 24
+
+; HAS-SEB-SEH:seb $2, $[[R16]]
}
define signext i8 @AtomicLoadNand8(i8 signext %incr) nounwind {
@@ -222,58 +175,39 @@ entry:
%0 = atomicrmw nand i8* @y, i8 %incr monotonic
ret i8 %0
-; CHECK-EL-LABEL: AtomicLoadNand8:
-; CHECK-EL: lw $[[R0:[0-9]+]], %got(y)
-; CHECK-EL: addiu $[[R1:[0-9]+]], $zero, -4
-; CHECK-EL: and $[[R2:[0-9]+]], $[[R0]], $[[R1]]
-; CHECK-EL: andi $[[R3:[0-9]+]], $[[R0]], 3
-; CHECK-EL: sll $[[R4:[0-9]+]], $[[R3]], 3
-; CHECK-EL: ori $[[R5:[0-9]+]], $zero, 255
-; CHECK-EL: sllv $[[R6:[0-9]+]], $[[R5]], $[[R4]]
-; CHECK-EL: nor $[[R7:[0-9]+]], $zero, $[[R6]]
-; CHECK-EL: sllv $[[R9:[0-9]+]], $4, $[[R4]]
-
-; CHECK-EL: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EL: ll $[[R10:[0-9]+]], 0($[[R2]])
-; CHECK-EL: and $[[R18:[0-9]+]], $[[R10]], $[[R9]]
-; CHECK-EL: nor $[[R11:[0-9]+]], $zero, $[[R18]]
-; CHECK-EL: and $[[R12:[0-9]+]], $[[R11]], $[[R6]]
-; CHECK-EL: and $[[R13:[0-9]+]], $[[R10]], $[[R7]]
-; CHECK-EL: or $[[R14:[0-9]+]], $[[R13]], $[[R12]]
-; CHECK-EL: sc $[[R14]], 0($[[R2]])
-; CHECK-EL: beqz $[[R14]], $[[BB0]]
-
-; CHECK-EL: and $[[R15:[0-9]+]], $[[R10]], $[[R6]]
-; CHECK-EL: srlv $[[R16:[0-9]+]], $[[R15]], $[[R4]]
-; CHECK-EL: sll $[[R17:[0-9]+]], $[[R16]], 24
-; CHECK-EL: sra $2, $[[R17]], 24
-
-; CHECK-EB-LABEL: AtomicLoadNand8:
-; CHECK-EB: lw $[[R0:[0-9]+]], %got(y)
-; CHECK-EB: addiu $[[R1:[0-9]+]], $zero, -4
-; CHECK-EB: and $[[R2:[0-9]+]], $[[R0]], $[[R1]]
-; CHECK-EB: andi $[[R3:[0-9]+]], $[[R0]], 3
-; CHECK-EB: xori $[[R4:[0-9]+]], $[[R3]], 3
-; CHECK-EB: sll $[[R5:[0-9]+]], $[[R4]], 3
-; CHECK-EB: ori $[[R6:[0-9]+]], $zero, 255
-; CHECK-EB: sllv $[[R7:[0-9]+]], $[[R6]], $[[R5]]
-; CHECK-EB: nor $[[R8:[0-9]+]], $zero, $[[R7]]
-; CHECK-EB: sllv $[[R9:[0-9]+]], $4, $[[R5]]
-
-; CHECK-EB: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EB: ll $[[R10:[0-9]+]], 0($[[R2]])
-; CHECK-EB: and $[[R18:[0-9]+]], $[[R10]], $[[R9]]
-; CHECK-EB: nor $[[R11:[0-9]+]], $zero, $[[R18]]
-; CHECK-EB: and $[[R12:[0-9]+]], $[[R11]], $[[R7]]
-; CHECK-EB: and $[[R13:[0-9]+]], $[[R10]], $[[R8]]
-; CHECK-EB: or $[[R14:[0-9]+]], $[[R13]], $[[R12]]
-; CHECK-EB: sc $[[R14]], 0($[[R2]])
-; CHECK-EB: beqz $[[R14]], $[[BB0]]
-
-; CHECK-EB: and $[[R15:[0-9]+]], $[[R10]], $[[R7]]
-; CHECK-EB: srlv $[[R16:[0-9]+]], $[[R15]], $[[R5]]
-; CHECK-EB: sll $[[R17:[0-9]+]], $[[R16]], 24
-; CHECK-EB: sra $2, $[[R17]], 24
+; ALL-LABEL: AtomicLoadNand8:
+
+; MIPS32-ANY: lw $[[R0:[0-9]+]], %got(y)
+; MIPS64-ANY: ld $[[R0:[0-9]+]], %got_disp(y)(
+
+; ALL: addiu $[[R1:[0-9]+]], $zero, -4
+; ALL: and $[[R2:[0-9]+]], $[[R0]], $[[R1]]
+; ALL: andi $[[R3:[0-9]+]], $[[R0]], 3
+; CHECK-EL: sll $[[R5:[0-9]+]], $[[R3]], 3
+; CHECK-EB: xori $[[R4:[0-9]+]], $[[R3]], 3
+; CHECK-EB: sll $[[R5:[0-9]+]], $[[R4]], 3
+; ALL: ori $[[R6:[0-9]+]], $zero, 255
+; ALL: sllv $[[R7:[0-9]+]], $[[R6]], $[[R5]]
+; ALL: nor $[[R8:[0-9]+]], $zero, $[[R7]]
+; ALL: sllv $[[R9:[0-9]+]], $4, $[[R5]]
+
+; ALL: $[[BB0:[A-Z_0-9]+]]:
+; ALL: ll $[[R10:[0-9]+]], 0($[[R2]])
+; ALL: and $[[R18:[0-9]+]], $[[R10]], $[[R9]]
+; ALL: nor $[[R11:[0-9]+]], $zero, $[[R18]]
+; ALL: and $[[R12:[0-9]+]], $[[R11]], $[[R7]]
+; ALL: and $[[R13:[0-9]+]], $[[R10]], $[[R8]]
+; ALL: or $[[R14:[0-9]+]], $[[R13]], $[[R12]]
+; ALL: sc $[[R14]], 0($[[R2]])
+; ALL: beqz $[[R14]], $[[BB0]]
+
+; ALL: and $[[R15:[0-9]+]], $[[R10]], $[[R7]]
+; ALL: srlv $[[R16:[0-9]+]], $[[R15]], $[[R5]]
+
+; NO-SEB-SEH: sll $[[R17:[0-9]+]], $[[R16]], 24
+; NO-SEB-SEH: sra $2, $[[R17]], 24
+
+; HAS-SEB-SEH: seb $2, $[[R16]]
}
define signext i8 @AtomicSwap8(i8 signext %newval) nounwind {
@@ -281,121 +215,126 @@ entry:
%0 = atomicrmw xchg i8* @y, i8 %newval monotonic
ret i8 %0
-; CHECK-EL-LABEL: AtomicSwap8:
-; CHECK-EL: lw $[[R0:[0-9]+]], %got(y)
-; CHECK-EL: addiu $[[R1:[0-9]+]], $zero, -4
-; CHECK-EL: and $[[R2:[0-9]+]], $[[R0]], $[[R1]]
-; CHECK-EL: andi $[[R3:[0-9]+]], $[[R0]], 3
-; CHECK-EL: sll $[[R4:[0-9]+]], $[[R3]], 3
-; CHECK-EL: ori $[[R5:[0-9]+]], $zero, 255
-; CHECK-EL: sllv $[[R6:[0-9]+]], $[[R5]], $[[R4]]
-; CHECK-EL: nor $[[R7:[0-9]+]], $zero, $[[R6]]
-; CHECK-EL: sllv $[[R9:[0-9]+]], $4, $[[R4]]
-
-; CHECK-EL: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EL: ll $[[R10:[0-9]+]], 0($[[R2]])
-; CHECK-EL: and $[[R18:[0-9]+]], $[[R9]], $[[R6]]
-; CHECK-EL: and $[[R13:[0-9]+]], $[[R10]], $[[R7]]
-; CHECK-EL: or $[[R14:[0-9]+]], $[[R13]], $[[R18]]
-; CHECK-EL: sc $[[R14]], 0($[[R2]])
-; CHECK-EL: beqz $[[R14]], $[[BB0]]
-
-; CHECK-EL: and $[[R15:[0-9]+]], $[[R10]], $[[R6]]
-; CHECK-EL: srlv $[[R16:[0-9]+]], $[[R15]], $[[R4]]
-; CHECK-EL: sll $[[R17:[0-9]+]], $[[R16]], 24
-; CHECK-EL: sra $2, $[[R17]], 24
-
-; CHECK-EB-LABEL: AtomicSwap8:
-; CHECK-EB: lw $[[R0:[0-9]+]], %got(y)
-; CHECK-EB: addiu $[[R1:[0-9]+]], $zero, -4
-; CHECK-EB: and $[[R2:[0-9]+]], $[[R0]], $[[R1]]
-; CHECK-EB: andi $[[R3:[0-9]+]], $[[R0]], 3
-; CHECK-EB: xori $[[R4:[0-9]+]], $[[R3]], 3
-; CHECK-EB: sll $[[R5:[0-9]+]], $[[R4]], 3
-; CHECK-EB: ori $[[R6:[0-9]+]], $zero, 255
-; CHECK-EB: sllv $[[R7:[0-9]+]], $[[R6]], $[[R5]]
-; CHECK-EB: nor $[[R8:[0-9]+]], $zero, $[[R7]]
-; CHECK-EB: sllv $[[R9:[0-9]+]], $4, $[[R5]]
-
-; CHECK-EB: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EB: ll $[[R10:[0-9]+]], 0($[[R2]])
-; CHECK-EB: and $[[R18:[0-9]+]], $[[R9]], $[[R7]]
-; CHECK-EB: and $[[R13:[0-9]+]], $[[R10]], $[[R8]]
-; CHECK-EB: or $[[R14:[0-9]+]], $[[R13]], $[[R18]]
-; CHECK-EB: sc $[[R14]], 0($[[R2]])
-; CHECK-EB: beqz $[[R14]], $[[BB0]]
-
-; CHECK-EB: and $[[R15:[0-9]+]], $[[R10]], $[[R7]]
-; CHECK-EB: srlv $[[R16:[0-9]+]], $[[R15]], $[[R5]]
-; CHECK-EB: sll $[[R17:[0-9]+]], $[[R16]], 24
-; CHECK-EB: sra $2, $[[R17]], 24
+; ALL-LABEL: AtomicSwap8:
+
+; MIPS32-ANY: lw $[[R0:[0-9]+]], %got(y)
+; MIPS64-ANY: ld $[[R0:[0-9]+]], %got_disp(y)(
+
+; ALL: addiu $[[R1:[0-9]+]], $zero, -4
+; ALL: and $[[R2:[0-9]+]], $[[R0]], $[[R1]]
+; ALL: andi $[[R3:[0-9]+]], $[[R0]], 3
+; CHECK-EL: sll $[[R5:[0-9]+]], $[[R3]], 3
+; CHECK-EB: xori $[[R4:[0-9]+]], $[[R3]], 3
+; CHECK-EB: sll $[[R5:[0-9]+]], $[[R4]], 3
+; ALL: ori $[[R6:[0-9]+]], $zero, 255
+; ALL: sllv $[[R7:[0-9]+]], $[[R6]], $[[R5]]
+; ALL: nor $[[R8:[0-9]+]], $zero, $[[R7]]
+; ALL: sllv $[[R9:[0-9]+]], $4, $[[R5]]
+
+; ALL: $[[BB0:[A-Z_0-9]+]]:
+; ALL: ll $[[R10:[0-9]+]], 0($[[R2]])
+; ALL: and $[[R18:[0-9]+]], $[[R9]], $[[R7]]
+; ALL: and $[[R13:[0-9]+]], $[[R10]], $[[R8]]
+; ALL: or $[[R14:[0-9]+]], $[[R13]], $[[R18]]
+; ALL: sc $[[R14]], 0($[[R2]])
+; ALL: beqz $[[R14]], $[[BB0]]
+
+; ALL: and $[[R15:[0-9]+]], $[[R10]], $[[R7]]
+; ALL: srlv $[[R16:[0-9]+]], $[[R15]], $[[R5]]
+
+; NO-SEB-SEH: sll $[[R17:[0-9]+]], $[[R16]], 24
+; NO-SEB-SEH: sra $2, $[[R17]], 24
+
+; HAS-SEB-SEH: seb $2, $[[R16]]
}
define signext i8 @AtomicCmpSwap8(i8 signext %oldval, i8 signext %newval) nounwind {
entry:
- %0 = cmpxchg i8* @y, i8 %oldval, i8 %newval monotonic monotonic
+ %pair0 = cmpxchg i8* @y, i8 %oldval, i8 %newval monotonic monotonic
+ %0 = extractvalue { i8, i1 } %pair0, 0
ret i8 %0
-; CHECK-EL-LABEL: AtomicCmpSwap8:
-; CHECK-EL: lw $[[R0:[0-9]+]], %got(y)
-; CHECK-EL: addiu $[[R1:[0-9]+]], $zero, -4
-; CHECK-EL: and $[[R2:[0-9]+]], $[[R0]], $[[R1]]
-; CHECK-EL: andi $[[R3:[0-9]+]], $[[R0]], 3
-; CHECK-EL: sll $[[R4:[0-9]+]], $[[R3]], 3
-; CHECK-EL: ori $[[R5:[0-9]+]], $zero, 255
-; CHECK-EL: sllv $[[R6:[0-9]+]], $[[R5]], $[[R4]]
-; CHECK-EL: nor $[[R7:[0-9]+]], $zero, $[[R6]]
-; CHECK-EL: andi $[[R8:[0-9]+]], $4, 255
-; CHECK-EL: sllv $[[R9:[0-9]+]], $[[R8]], $[[R4]]
-; CHECK-EL: andi $[[R10:[0-9]+]], $5, 255
-; CHECK-EL: sllv $[[R11:[0-9]+]], $[[R10]], $[[R4]]
-
-; CHECK-EL: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EL: ll $[[R12:[0-9]+]], 0($[[R2]])
-; CHECK-EL: and $[[R13:[0-9]+]], $[[R12]], $[[R6]]
-; CHECK-EL: bne $[[R13]], $[[R9]], $[[BB1:[A-Z_0-9]+]]
-
-; CHECK-EL: and $[[R14:[0-9]+]], $[[R12]], $[[R7]]
-; CHECK-EL: or $[[R15:[0-9]+]], $[[R14]], $[[R11]]
-; CHECK-EL: sc $[[R15]], 0($[[R2]])
-; CHECK-EL: beqz $[[R15]], $[[BB0]]
-
-; CHECK-EL: $[[BB1]]:
-; CHECK-EL: srlv $[[R16:[0-9]+]], $[[R13]], $[[R4]]
-; CHECK-EL: sll $[[R17:[0-9]+]], $[[R16]], 24
-; CHECK-EL: sra $2, $[[R17]], 24
-
-; CHECK-EB-LABEL: AtomicCmpSwap8:
-; CHECK-EB: lw $[[R0:[0-9]+]], %got(y)
-; CHECK-EB: addiu $[[R1:[0-9]+]], $zero, -4
-; CHECK-EB: and $[[R2:[0-9]+]], $[[R0]], $[[R1]]
-; CHECK-EB: andi $[[R3:[0-9]+]], $[[R0]], 3
-; CHECK-EB: xori $[[R4:[0-9]+]], $[[R3]], 3
-; CHECK-EB: sll $[[R5:[0-9]+]], $[[R4]], 3
-; CHECK-EB: ori $[[R6:[0-9]+]], $zero, 255
-; CHECK-EB: sllv $[[R7:[0-9]+]], $[[R6]], $[[R5]]
-; CHECK-EB: nor $[[R8:[0-9]+]], $zero, $[[R7]]
-; CHECK-EB: andi $[[R9:[0-9]+]], $4, 255
-; CHECK-EB: sllv $[[R10:[0-9]+]], $[[R9]], $[[R5]]
-; CHECK-EB: andi $[[R11:[0-9]+]], $5, 255
-; CHECK-EB: sllv $[[R12:[0-9]+]], $[[R11]], $[[R5]]
-
-; CHECK-EB: $[[BB0:[A-Z_0-9]+]]:
-; CHECK-EB: ll $[[R13:[0-9]+]], 0($[[R2]])
-; CHECK-EB: and $[[R14:[0-9]+]], $[[R13]], $[[R7]]
-; CHECK-EB: bne $[[R14]], $[[R10]], $[[BB1:[A-Z_0-9]+]]
-
-; CHECK-EB: and $[[R15:[0-9]+]], $[[R13]], $[[R8]]
-; CHECK-EB: or $[[R16:[0-9]+]], $[[R15]], $[[R12]]
-; CHECK-EB: sc $[[R16]], 0($[[R2]])
-; CHECK-EB: beqz $[[R16]], $[[BB0]]
-
-; CHECK-EB: $[[BB1]]:
-; CHECK-EB: srlv $[[R17:[0-9]+]], $[[R14]], $[[R5]]
-; CHECK-EB: sll $[[R18:[0-9]+]], $[[R17]], 24
-; CHECK-EB: sra $2, $[[R18]], 24
+; ALL-LABEL: AtomicCmpSwap8:
+
+; MIPS32-ANY: lw $[[R0:[0-9]+]], %got(y)
+; MIPS64-ANY: ld $[[R0:[0-9]+]], %got_disp(y)(
+
+; ALL: addiu $[[R1:[0-9]+]], $zero, -4
+; ALL: and $[[R2:[0-9]+]], $[[R0]], $[[R1]]
+; ALL: andi $[[R3:[0-9]+]], $[[R0]], 3
+; CHECK-EL: sll $[[R5:[0-9]+]], $[[R3]], 3
+; CHECK-EB: xori $[[R4:[0-9]+]], $[[R3]], 3
+; CHECK-EB: sll $[[R5:[0-9]+]], $[[R4]], 3
+; ALL: ori $[[R6:[0-9]+]], $zero, 255
+; ALL: sllv $[[R7:[0-9]+]], $[[R6]], $[[R5]]
+; ALL: nor $[[R8:[0-9]+]], $zero, $[[R7]]
+; ALL: andi $[[R9:[0-9]+]], $4, 255
+; ALL: sllv $[[R10:[0-9]+]], $[[R9]], $[[R5]]
+; ALL: andi $[[R11:[0-9]+]], $5, 255
+; ALL: sllv $[[R12:[0-9]+]], $[[R11]], $[[R5]]
+
+; ALL: $[[BB0:[A-Z_0-9]+]]:
+; ALL: ll $[[R13:[0-9]+]], 0($[[R2]])
+; ALL: and $[[R14:[0-9]+]], $[[R13]], $[[R7]]
+; ALL: bne $[[R14]], $[[R10]], $[[BB1:[A-Z_0-9]+]]
+
+; ALL: and $[[R15:[0-9]+]], $[[R13]], $[[R8]]
+; ALL: or $[[R16:[0-9]+]], $[[R15]], $[[R12]]
+; ALL: sc $[[R16]], 0($[[R2]])
+; ALL: beqz $[[R16]], $[[BB0]]
+
+; ALL: $[[BB1]]:
+; ALL: srlv $[[R17:[0-9]+]], $[[R14]], $[[R5]]
+
+; NO-SEB-SEH: sll $[[R18:[0-9]+]], $[[R17]], 24
+; NO-SEB-SEH: sra $2, $[[R18]], 24
+
+; HAS-SEB-SEH: seb $2, $[[R17]]
+}
+
+; Check one i16 so that we cover the seh sign extend
+@z = common global i16 0, align 1
+
+define signext i16 @AtomicLoadAdd16(i16 signext %incr) nounwind {
+entry:
+ %0 = atomicrmw add i16* @z, i16 %incr monotonic
+ ret i16 %0
+
+; ALL-LABEL: AtomicLoadAdd16:
+
+; MIPS32-ANY: lw $[[R0:[0-9]+]], %got(z)
+; MIPS64-ANY: ld $[[R0:[0-9]+]], %got_disp(z)(
+
+; ALL: addiu $[[R1:[0-9]+]], $zero, -4
+; ALL: and $[[R2:[0-9]+]], $[[R0]], $[[R1]]
+; ALL: andi $[[R3:[0-9]+]], $[[R0]], 3
+; CHECK-EB: xori $[[R4:[0-9]+]], $[[R3]], 2
+; CHECK-EB: sll $[[R5:[0-9]+]], $[[R4]], 3
+; CHECK-EL: sll $[[R5:[0-9]+]], $[[R3]], 3
+; ALL: ori $[[R6:[0-9]+]], $zero, 65535
+; ALL: sllv $[[R7:[0-9]+]], $[[R6]], $[[R5]]
+; ALL: nor $[[R8:[0-9]+]], $zero, $[[R7]]
+; ALL: sllv $[[R9:[0-9]+]], $4, $[[R5]]
+
+; ALL: $[[BB0:[A-Z_0-9]+]]:
+; ALL: ll $[[R10:[0-9]+]], 0($[[R2]])
+; ALL: addu $[[R11:[0-9]+]], $[[R10]], $[[R9]]
+; ALL: and $[[R12:[0-9]+]], $[[R11]], $[[R7]]
+; ALL: and $[[R13:[0-9]+]], $[[R10]], $[[R8]]
+; ALL: or $[[R14:[0-9]+]], $[[R13]], $[[R12]]
+; ALL: sc $[[R14]], 0($[[R2]])
+; ALL: beqz $[[R14]], $[[BB0]]
+
+; ALL: and $[[R15:[0-9]+]], $[[R10]], $[[R7]]
+; ALL: srlv $[[R16:[0-9]+]], $[[R15]], $[[R5]]
+
+; NO-SEB-SEH: sll $[[R17:[0-9]+]], $[[R16]], 16
+; NO-SEB-SEH: sra $2, $[[R17]], 16
+
+; MIPS32R2: seh $2, $[[R16]]
}
+
@countsint = common global i32 0, align 4
define i32 @CheckSync(i32 %v) nounwind noinline {
@@ -403,19 +342,13 @@ entry:
%0 = atomicrmw add i32* @countsint, i32 %v seq_cst
ret i32 %0
-; CHECK-EL-LABEL: CheckSync:
-; CHECK-EL: sync 0
-; CHECK-EL: ll
-; CHECK-EL: sc
-; CHECK-EL: beq
-; CHECK-EL: sync 0
-
-; CHECK-EB-LABEL: CheckSync:
-; CHECK-EB: sync 0
-; CHECK-EB: ll
-; CHECK-EB: sc
-; CHECK-EB: beq
-; CHECK-EB: sync 0
+; ALL-LABEL: CheckSync:
+
+; ALL: sync
+; ALL: ll
+; ALL: sc
+; ALL: beq
+; ALL: sync
}
; make sure that this assertion in
@@ -429,8 +362,29 @@ entry:
define i32 @zeroreg() nounwind {
entry:
- %0 = cmpxchg i32* @a, i32 1, i32 0 seq_cst seq_cst
+ %pair0 = cmpxchg i32* @a, i32 1, i32 0 seq_cst seq_cst
+ %0 = extractvalue { i32, i1 } %pair0, 0
%1 = icmp eq i32 %0, 1
%conv = zext i1 %1 to i32
ret i32 %conv
}
+
+; Check that MIPS32R6 has the correct offset range.
+; FIXME: At the moment, we don't seem to do addr+offset for any atomic load/store.
+define i32 @AtomicLoadAdd32_OffGt9Bit(i32 %incr) nounwind {
+entry:
+ %0 = atomicrmw add i32* getelementptr(i32* @x, i32 256), i32 %incr monotonic
+ ret i32 %0
+
+; ALL-LABEL: AtomicLoadAdd32_OffGt9Bit:
+
+; MIPS32-ANY: lw $[[R0:[0-9]+]], %got(x)
+; MIPS64-ANY: ld $[[R0:[0-9]+]], %got_disp(x)(
+
+; ALL: addiu $[[PTR:[0-9]+]], $[[R0]], 1024
+; ALL: $[[BB0:[A-Z_0-9]+]]:
+; ALL: ll $[[R1:[0-9]+]], 0($[[PTR]])
+; ALL: addu $[[R2:[0-9]+]], $[[R1]], $4
+; ALL: sc $[[R2]], 0($[[PTR]])
+; ALL: beqz $[[R2]], $[[BB0]]
+}
diff --git a/test/CodeGen/Mips/atomicops.ll b/test/CodeGen/Mips/atomicops.ll
index dc07c63..c264152 100644
--- a/test/CodeGen/Mips/atomicops.ll
+++ b/test/CodeGen/Mips/atomicops.ll
@@ -20,7 +20,8 @@ entry:
%add.i = add nsw i32 %0, 2
%1 = load volatile i32* %x, align 4
%call1 = call i32 (i8*, ...)* @printf(i8* getelementptr inbounds ([8 x i8]* @.str, i32 0, i32 0), i32 %add.i, i32 %1) nounwind
- %2 = cmpxchg i32* %x, i32 1, i32 2 seq_cst seq_cst
+ %pair = cmpxchg i32* %x, i32 1, i32 2 seq_cst seq_cst
+ %2 = extractvalue { i32, i1 } %pair, 0
%3 = load volatile i32* %x, align 4
%call2 = call i32 (i8*, ...)* @printf(i8* getelementptr inbounds ([8 x i8]* @.str, i32 0, i32 0), i32 %2, i32 %3) nounwind
%4 = atomicrmw xchg i32* %x, i32 1 seq_cst
diff --git a/test/CodeGen/Mips/buildpairextractelementf64.ll b/test/CodeGen/Mips/buildpairextractelementf64.ll
index b9bf2b6..88d1d07 100644
--- a/test/CodeGen/Mips/buildpairextractelementf64.ll
+++ b/test/CodeGen/Mips/buildpairextractelementf64.ll
@@ -1,7 +1,7 @@
; RUN: llc -march=mipsel < %s | FileCheck %s -check-prefix=FP32 -check-prefix=CHECK
; RUN: llc -march=mips < %s | FileCheck %s -check-prefix=FP32 -check-prefix=CHECK
-; RUN: llc -march=mipsel -mattr=+fp64 < %s | FileCheck %s -check-prefix=FP64 -check-prefix=CHECK
-; RUN: llc -march=mips -mattr=+fp64 < %s | FileCheck %s -check-prefix=FP64 -check-prefix=CHECK
+; RUN: llc -march=mipsel -mcpu=mips32r2 -mattr=+fp64 < %s | FileCheck %s -check-prefix=FP64 -check-prefix=CHECK
+; RUN: llc -march=mips -mcpu=mips32r2 -mattr=+fp64 < %s | FileCheck %s -check-prefix=FP64 -check-prefix=CHECK
@a = external global i32
diff --git a/test/CodeGen/Mips/cconv/callee-saved-fpxx.ll b/test/CodeGen/Mips/cconv/callee-saved-fpxx.ll
new file mode 100644
index 0000000..4b28b99
--- /dev/null
+++ b/test/CodeGen/Mips/cconv/callee-saved-fpxx.ll
@@ -0,0 +1,58 @@
+; RUN: llc -march=mips -mattr=+o32,+fpxx < %s | FileCheck --check-prefix=ALL --check-prefix=O32-FPXX %s
+; RUN: llc -march=mipsel -mattr=+o32,+fpxx < %s | FileCheck --check-prefix=ALL --check-prefix=O32-FPXX %s
+; RUN: llc -march=mips -mattr=+o32,+fpxx < %s | FileCheck --check-prefix=ALL --check-prefix=O32-FPXX-INV %s
+; RUN: llc -march=mipsel -mattr=+o32,+fpxx < %s | FileCheck --check-prefix=ALL --check-prefix=O32-FPXX-INV %s
+
+; RUN-TODO: llc -march=mips64 -mattr=+o32,+fpxx < %s | FileCheck --check-prefix=ALL --check-prefix=O32-FPXX %s
+; RUN-TODO: llc -march=mips64el -mattr=+o32,+fpxx < %s | FileCheck --check-prefix=ALL --check-prefix=O32-FPXX %s
+; RUN-TODO: llc -march=mips64 -mattr=+o32,+fpxx < %s | FileCheck --check-prefix=ALL --check-prefix=O32-FPXX-INV --check-prefix=O32-FPXX-INV %s
+; RUN-TODO: llc -march=mips64el -mattr=+o32,+fpxx < %s | FileCheck --check-prefix=ALL --check-prefix=O32-FPXX-INV --check-prefix=O32-FPXX-INV %s
+
+define void @fpu_clobber() nounwind {
+entry:
+ call void asm "# Clobber", "~{$f0},~{$f1},~{$f2},~{$f3},~{$f4},~{$f5},~{$f6},~{$f7},~{$f8},~{$f9},~{$f10},~{$f11},~{$f12},~{$f13},~{$f14},~{$f15},~{$f16},~{$f17},~{$f18},~{$f19},~{$f20},~{$f21},~{$f22},~{$f23},~{$f24},~{$f25},~{$f26},~{$f27},~{$f28},~{$f29},~{$f30},~{$f31}"()
+ ret void
+}
+
+; O32-FPXX-LABEL: fpu_clobber:
+; O32-FPXX-INV-NOT: sdc1 $f0,
+; O32-FPXX-INV-NOT: sdc1 $f1,
+; O32-FPXX-INV-NOT: sdc1 $f2,
+; O32-FPXX-INV-NOT: sdc1 $f3,
+; O32-FPXX-INV-NOT: sdc1 $f4,
+; O32-FPXX-INV-NOT: sdc1 $f5,
+; O32-FPXX-INV-NOT: sdc1 $f6,
+; O32-FPXX-INV-NOT: sdc1 $f7,
+; O32-FPXX-INV-NOT: sdc1 $f8,
+; O32-FPXX-INV-NOT: sdc1 $f9,
+; O32-FPXX-INV-NOT: sdc1 $f10,
+; O32-FPXX-INV-NOT: sdc1 $f11,
+; O32-FPXX-INV-NOT: sdc1 $f12,
+; O32-FPXX-INV-NOT: sdc1 $f13,
+; O32-FPXX-INV-NOT: sdc1 $f14,
+; O32-FPXX-INV-NOT: sdc1 $f15,
+; O32-FPXX-INV-NOT: sdc1 $f16,
+; O32-FPXX-INV-NOT: sdc1 $f17,
+; O32-FPXX-INV-NOT: sdc1 $f18,
+; O32-FPXX-INV-NOT: sdc1 $f19,
+; O32-FPXX-INV-NOT: sdc1 $f21,
+; O32-FPXX-INV-NOT: sdc1 $f23,
+; O32-FPXX-INV-NOT: sdc1 $f25,
+; O32-FPXX-INV-NOT: sdc1 $f27,
+; O32-FPXX-INV-NOT: sdc1 $f29,
+; O32-FPXX-INV-NOT: sdc1 $f31,
+
+; O32-FPXX: addiu $sp, $sp, -48
+; O32-FPXX-DAG: sdc1 [[F20:\$f20]], [[OFF20:[0-9]+]]($sp)
+; O32-FPXX-DAG: sdc1 [[F22:\$f22]], [[OFF22:[0-9]+]]($sp)
+; O32-FPXX-DAG: sdc1 [[F24:\$f24]], [[OFF24:[0-9]+]]($sp)
+; O32-FPXX-DAG: sdc1 [[F26:\$f26]], [[OFF26:[0-9]+]]($sp)
+; O32-FPXX-DAG: sdc1 [[F28:\$f28]], [[OFF28:[0-9]+]]($sp)
+; O32-FPXX-DAG: sdc1 [[F30:\$f30]], [[OFF30:[0-9]+]]($sp)
+; O32-FPXX-DAG: ldc1 [[F20]], [[OFF20]]($sp)
+; O32-FPXX-DAG: ldc1 [[F22]], [[OFF22]]($sp)
+; O32-FPXX-DAG: ldc1 [[F24]], [[OFF24]]($sp)
+; O32-FPXX-DAG: ldc1 [[F26]], [[OFF26]]($sp)
+; O32-FPXX-DAG: ldc1 [[F28]], [[OFF28]]($sp)
+; O32-FPXX-DAG: ldc1 [[F30]], [[OFF30]]($sp)
+; O32-FPXX: addiu $sp, $sp, 48
diff --git a/test/CodeGen/Mips/cconv/callee-saved-fpxx1.ll b/test/CodeGen/Mips/cconv/callee-saved-fpxx1.ll
new file mode 100644
index 0000000..489879e
--- /dev/null
+++ b/test/CodeGen/Mips/cconv/callee-saved-fpxx1.ll
@@ -0,0 +1,24 @@
+; RUN: llc -march=mips -mattr=+o32,+fp64 < %s | FileCheck --check-prefix=O32-FP64-INV %s
+; RUN: llc -march=mipsel -mattr=+o32,+fp64 < %s | FileCheck --check-prefix=O32-FP64-INV %s
+
+; RUN: llc -march=mips -mattr=+o32,+fpxx < %s | FileCheck --check-prefix=O32-FPXX %s
+; RUN: llc -march=mipsel -mattr=+o32,+fpxx < %s | FileCheck --check-prefix=O32-FPXX %s
+
+; RUN-TODO: llc -march=mips64 -mattr=+o32,+fpxx < %s | FileCheck --check-prefix=O32-FPXX %s
+; RUN-TODO: llc -march=mips64el -mattr=+o32,+fpxx < %s | FileCheck --check-prefix=O32-FPXX %s
+
+define void @fpu_clobber() nounwind {
+entry:
+ call void asm "# Clobber", "~{$f21}"()
+ ret void
+}
+
+; O32-FPXX-LABEL: fpu_clobber:
+
+; O32-FPXX: addiu $sp, $sp, -8
+
+; O32-FP64-INV-NOT: sdc1 $f20,
+; O32-FPXX-DAG: sdc1 [[F20:\$f20]], [[OFF20:[0-9]+]]($sp)
+; O32-FPXX-DAG: ldc1 [[F20]], [[OFF20]]($sp)
+
+; O32-FPXX: addiu $sp, $sp, 8
diff --git a/test/CodeGen/Mips/cmov.ll b/test/CodeGen/Mips/cmov.ll
index b9732eb..999bdb4 100644
--- a/test/CodeGen/Mips/cmov.ll
+++ b/test/CodeGen/Mips/cmov.ll
@@ -1,17 +1,43 @@
-; RUN: llc -march=mips < %s | FileCheck %s -check-prefix=O32
-; RUN: llc -march=mips -regalloc=basic < %s | FileCheck %s -check-prefix=O32
-; RUN: llc -march=mips64el -mcpu=mips4 -mattr=n64 < %s | FileCheck %s -check-prefix=N64
-; RUN: llc -march=mips64el -mcpu=mips64 -mattr=n64 < %s | FileCheck %s -check-prefix=N64
+; RUN: llc -march=mips -mcpu=mips32 < %s | FileCheck %s -check-prefix=ALL -check-prefix=32-CMOV
+; RUN: llc -march=mips -mcpu=mips32 -regalloc=basic < %s | FileCheck %s -check-prefix=ALL -check-prefix=32-CMOV
+; RUN: llc -march=mips -mcpu=mips32r2 < %s | FileCheck %s -check-prefix=ALL -check-prefix=32-CMOV
+; RUN: llc -march=mips -mcpu=mips32r6 < %s | FileCheck %s -check-prefix=ALL -check-prefix=32-CMP
+; RUN: llc -march=mips64el -mcpu=mips4 < %s | FileCheck %s -check-prefix=ALL -check-prefix=64-CMOV
+; RUN: llc -march=mips64el -mcpu=mips64 < %s | FileCheck %s -check-prefix=ALL -check-prefix=64-CMOV
+; RUN: llc -march=mips64el -mcpu=mips64r6 < %s | FileCheck %s -check-prefix=ALL -check-prefix=64-CMP
@i1 = global [3 x i32] [i32 1, i32 2, i32 3], align 4
@i3 = common global i32* null, align 4
-; O32-DAG: lw $[[R0:[0-9]+]], %got(i3)
-; O32-DAG: addiu $[[R1:[0-9]+]], ${{[0-9]+}}, %got(i1)
-; O32: movn $[[R0]], $[[R1]], ${{[0-9]+}}
-; N64-DAG: ldr $[[R0:[0-9]+]]
-; N64-DAG: ld $[[R1:[0-9]+]], %got_disp(i1)
-; N64: movn $[[R0]], $[[R1]], ${{[0-9]+}}
+; ALL-LABEL: cmov1:
+
+; 32-CMOV-DAG: lw $[[R0:[0-9]+]], %got(i3)
+; 32-CMOV-DAG: addiu $[[R1:[0-9]+]], ${{[0-9]+}}, %got(i1)
+; 32-CMOV-DAG: movn $[[R0]], $[[R1]], $4
+; 32-CMOV-DAG: lw $2, 0($[[R0]])
+
+; 32-CMP-DAG: lw $[[R0:[0-9]+]], %got(i3)
+; 32-CMP-DAG: addiu $[[R1:[0-9]+]], ${{[0-9]+}}, %got(i1)
+; 32-CMP-DAG: selnez $[[T0:[0-9]+]], $[[R1]], $4
+; 32-CMP-DAG: seleqz $[[T1:[0-9]+]], $[[R0]], $4
+; 32-CMP-DAG: or $[[T2:[0-9]+]], $[[T0]], $[[T1]]
+; 32-CMP-DAG: lw $2, 0($[[T2]])
+
+; 64-CMOV-DAG: ldr $[[R0:[0-9]+]]
+; 64-CMOV-DAG: ld $[[R1:[0-9]+]], %got_disp(i1)
+; 64-CMOV-DAG: movn $[[R0]], $[[R1]], $4
+
+; 64-CMP-DAG: ld $[[R0:[0-9]+]], %got_disp(i3)(
+; 64-CMP-DAG: daddiu $[[R1:[0-9]+]], ${{[0-9]+}}, %got_disp(i1)
+; FIXME: This sll works around an implementation detail in the code generator
+; (setcc's result is i32 so bits 32-63 are undefined). It's not really
+; needed.
+; 64-CMP-DAG: sll $[[CC:[0-9]+]], $4, 0
+; 64-CMP-DAG: selnez $[[T0:[0-9]+]], $[[R1]], $[[CC]]
+; 64-CMP-DAG: seleqz $[[T1:[0-9]+]], $[[R0]], $[[CC]]
+; 64-CMP-DAG: or $[[T2:[0-9]+]], $[[T0]], $[[T1]]
+; 64-CMP-DAG: ld $2, 0($[[T2]])
+
define i32* @cmov1(i32 %s) nounwind readonly {
entry:
%tobool = icmp ne i32 %s, 0
@@ -23,14 +49,35 @@ entry:
@c = global i32 1, align 4
@d = global i32 0, align 4
-; O32-LABEL: cmov2:
-; O32: addiu $[[R1:[0-9]+]], ${{[a-z0-9]+}}, %got(d)
-; O32: addiu $[[R0:[0-9]+]], ${{[a-z0-9]+}}, %got(c)
-; O32: movn $[[R1]], $[[R0]], ${{[0-9]+}}
-; N64-LABEL: cmov2:
-; N64: daddiu $[[R1:[0-9]+]], ${{[0-9]+}}, %got_disp(d)
-; N64: daddiu $[[R0:[0-9]+]], ${{[0-9]+}}, %got_disp(c)
-; N64: movn $[[R1]], $[[R0]], ${{[0-9]+}}
+; ALL-LABEL: cmov2:
+
+; 32-CMOV-DAG: addiu $[[R1:[0-9]+]], ${{[0-9]+}}, %got(d)
+; 32-CMOV-DAG: addiu $[[R0:[0-9]+]], ${{[0-9]+}}, %got(c)
+; 32-CMOV-DAG: movn $[[R1]], $[[R0]], $4
+; 32-CMOV-DAG: lw $2, 0($[[R0]])
+
+; 32-CMP-DAG: addiu $[[R1:[0-9]+]], ${{[0-9]+}}, %got(d)
+; 32-CMP-DAG: addiu $[[R0:[0-9]+]], ${{[0-9]+}}, %got(c)
+; 32-CMP-DAG: selnez $[[T0:[0-9]+]], $[[R0]], $4
+; 32-CMP-DAG: seleqz $[[T1:[0-9]+]], $[[R1]], $4
+; 32-CMP-DAG: or $[[T2:[0-9]+]], $[[T0]], $[[T1]]
+; 32-CMP-DAG: lw $2, 0($[[T2]])
+
+; 64-CMOV: daddiu $[[R1:[0-9]+]], ${{[0-9]+}}, %got_disp(d)
+; 64-CMOV: daddiu $[[R0:[0-9]+]], ${{[0-9]+}}, %got_disp(c)
+; 64-CMOV: movn $[[R1]], $[[R0]], $4
+
+; 64-CMP-DAG: daddiu $[[R1:[0-9]+]], ${{[0-9]+}}, %got_disp(d)
+; 64-CMP-DAG: daddiu $[[R0:[0-9]+]], ${{[0-9]+}}, %got_disp(c)
+; FIXME: This sll works around an implementation detail in the code generator
+; (setcc's result is i32 so bits 32-63 are undefined). It's not really
+; needed.
+; 64-CMP-DAG: sll $[[CC:[0-9]+]], $4, 0
+; 64-CMP-DAG: selnez $[[T0:[0-9]+]], $[[R0]], $[[CC]]
+; 64-CMP-DAG: seleqz $[[T1:[0-9]+]], $[[R1]], $[[CC]]
+; 64-CMP-DAG: or $[[T2:[0-9]+]], $[[T0]], $[[T1]]
+; 64-CMP-DAG: lw $2, 0($[[T2]])
+
define i32 @cmov2(i32 %s) nounwind readonly {
entry:
%tobool = icmp ne i32 %s, 0
@@ -40,9 +87,28 @@ entry:
ret i32 %cond
}
-; O32-LABEL: cmov3:
-; O32: xori $[[R0:[0-9]+]], ${{[0-9]+}}, 234
-; O32: movz ${{[0-9]+}}, ${{[0-9]+}}, $[[R0]]
+; ALL-LABEL: cmov3:
+
+; We won't check the result register since we can't know if the move is first
+; or last. We do know it will be either one of two registers so we can at least
+; check that.
+
+; 32-CMOV: xori $[[R0:[0-9]+]], $4, 234
+; 32-CMOV: movz ${{[26]}}, $5, $[[R0]]
+
+; 32-CMP-DAG: xori $[[CC:[0-9]+]], $4, 234
+; 32-CMP-DAG: seleqz $[[T0:[0-9]+]], $5, $[[CC]]
+; 32-CMP-DAG: selnez $[[T1:[0-9]+]], $6, $[[CC]]
+; 32-CMP-DAG: or $2, $[[T0]], $[[T1]]
+
+; 64-CMOV: xori $[[R0:[0-9]+]], $4, 234
+; 64-CMOV: movz ${{[26]}}, $5, $[[R0]]
+
+; 64-CMP-DAG: xori $[[CC:[0-9]+]], $4, 234
+; 64-CMP-DAG: seleqz $[[T0:[0-9]+]], $5, $[[CC]]
+; 64-CMP-DAG: selnez $[[T1:[0-9]+]], $6, $[[CC]]
+; 64-CMP-DAG: or $2, $[[T0]], $[[T1]]
+
define i32 @cmov3(i32 %a, i32 %b, i32 %c) nounwind readnone {
entry:
%cmp = icmp eq i32 %a, 234
@@ -50,9 +116,36 @@ entry:
ret i32 %cond
}
-; N64-LABEL: cmov4:
-; N64: xori $[[R0:[0-9]+]], ${{[0-9]+}}, 234
-; N64: movz ${{[0-9]+}}, ${{[0-9]+}}, $[[R0]]
+; ALL-LABEL: cmov4:
+
+; We won't check the result register since we can't know if the move is first
+; or last. We do know it will be one of two registers so we can at least check
+; that.
+
+; 32-CMOV-DAG: xori $[[R0:[0-9]+]], $4, 234
+; 32-CMOV-DAG: lw $[[R1:2]], 16($sp)
+; 32-CMOV-DAG: lw $[[R2:3]], 20($sp)
+; 32-CMOV-DAG: movz $[[R1]], $6, $[[R0]]
+; 32-CMOV-DAG: movz $[[R2]], $7, $[[R0]]
+
+; 32-CMP-DAG: xori $[[R0:[0-9]+]], $4, 234
+; 32-CMP-DAG: lw $[[R1:[0-9]+]], 16($sp)
+; 32-CMP-DAG: lw $[[R2:[0-9]+]], 20($sp)
+; 32-CMP-DAG: seleqz $[[T0:[0-9]+]], $6, $[[R0]]
+; 32-CMP-DAG: seleqz $[[T1:[0-9]+]], $7, $[[R0]]
+; 32-CMP-DAG: selnez $[[T2:[0-9]+]], $[[R1]], $[[R0]]
+; 32-CMP-DAG: selnez $[[T3:[0-9]+]], $[[R2]], $[[R0]]
+; 32-CMP-DAG: or $2, $[[T0]], $[[T2]]
+; 32-CMP-DAG: or $3, $[[T1]], $[[T3]]
+
+; 64-CMOV: xori $[[R0:[0-9]+]], $4, 234
+; 64-CMOV: movz ${{[26]}}, $5, $[[R0]]
+
+; 64-CMP-DAG: xori $[[R0:[0-9]+]], $4, 234
+; 64-CMP-DAG: seleqz $[[T0:[0-9]+]], $5, $[[R0]]
+; 64-CMP-DAG: selnez $[[T1:[0-9]+]], $6, $[[R0]]
+; 64-CMP-DAG: or $2, $[[T0]], $[[T1]]
+
define i64 @cmov4(i32 %a, i64 %b, i64 %c) nounwind readnone {
entry:
%cmp = icmp eq i32 %a, 234
@@ -68,9 +161,33 @@ entry:
; (movz t, (setlt a, N + 1), f)
; if N + 1 fits in 16-bit.
-; O32-LABEL: slti0:
-; O32: slti $[[R0:[0-9]+]], ${{[0-9]+}}, 32767
-; O32: movz ${{[0-9]+}}, ${{[0-9]+}}, $[[R0]]
+; ALL-LABEL: slti0:
+
+; 32-CMOV-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 32-CMOV-DAG: addiu $[[I5:2]], $zero, 5
+; 32-CMOV-DAG: slti $[[R0:[0-9]+]], $4, 32767
+; 32-CMOV-DAG: movz $[[I5]], $[[I3]], $[[R0]]
+
+; 32-CMP-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 32-CMP-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 32-CMP-DAG: slti $[[R0:[0-9]+]], $4, 32767
+; FIXME: We can do better than this by using selccz to choose between +0 and +2
+; 32-CMP-DAG: seleqz $[[T0:[0-9]+]], $[[I3]], $[[R0]]
+; 32-CMP-DAG: selnez $[[T1:[0-9]+]], $[[I5]], $[[R0]]
+; 32-CMP-DAG: or $2, $[[T0]], $[[T1]]
+
+; 64-CMOV-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 64-CMOV-DAG: addiu $[[I5:2]], $zero, 5
+; 64-CMOV-DAG: slti $[[R0:[0-9]+]], $4, 32767
+; 64-CMOV-DAG: movz $[[I5]], $[[I3]], $[[R0]]
+
+; 64-CMP-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 64-CMP-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 64-CMP-DAG: slti $[[R0:[0-9]+]], $4, 32767
+; FIXME: We can do better than this by using selccz to choose between +0 and +2
+; 64-CMP-DAG: seleqz $[[T0:[0-9]+]], $[[I3]], $[[R0]]
+; 64-CMP-DAG: selnez $[[T1:[0-9]+]], $[[I5]], $[[R0]]
+; 64-CMP-DAG: or $2, $[[T0]], $[[T1]]
define i32 @slti0(i32 %a) {
entry:
@@ -79,19 +196,72 @@ entry:
ret i32 %cond
}
-; O32-LABEL: slti1:
-; O32: slt ${{[0-9]+}}
+; ALL-LABEL: slti1:
+
+; 32-CMOV-DAG: addiu $[[I7:[0-9]+]], $zero, 7
+; 32-CMOV-DAG: addiu $[[I5:2]], $zero, 5
+; 32-CMOV-DAG: addiu $[[R1:[0-9]+]], $zero, 32767
+; 32-CMOV-DAG: slt $[[R0:[0-9]+]], $[[R1]], $4
+; 32-CMOV-DAG: movn $[[I5]], $[[I7]], $[[R0]]
+
+; 32-CMP-DAG: addiu $[[I7:[0-9]+]], $zero, 7
+; 32-CMP-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 32-CMP-DAG: addiu $[[I32767:[0-9]+]], $zero, 32767
+; 32-CMP-DAG: slt $[[R0:[0-9]+]], $[[I32767]], $4
+; FIXME: We can do better than this by using selccz to choose between -0 and -2
+; 32-CMP-DAG: selnez $[[T0:[0-9]+]], $[[I7]], $[[R0]]
+; 32-CMP-DAG: seleqz $[[T1:[0-9]+]], $[[I5]], $[[R0]]
+; 32-CMP-DAG: or $2, $[[T0]], $[[T1]]
+
+; 64-CMOV-DAG: addiu $[[I7:[0-9]+]], $zero, 7
+; 64-CMOV-DAG: addiu $[[I5:2]], $zero, 5
+; 64-CMOV-DAG: addiu $[[R1:[0-9]+]], $zero, 32767
+; 64-CMOV-DAG: slt $[[R0:[0-9]+]], $[[R1]], $4
+; 64-CMOV-DAG: movn $[[I5]], $[[I7]], $[[R0]]
+
+; 64-CMP-DAG: addiu $[[I7:[0-9]+]], $zero, 7
+; 64-CMP-DAG: addiu $[[I5:2]], $zero, 5
+; 64-CMP-DAG: addiu $[[R1:[0-9]+]], $zero, 32767
+; 64-CMP-DAG: slt $[[R0:[0-9]+]], $[[R1]], $4
+; FIXME: We can do better than this by using selccz to choose between -0 and -2
+; 64-CMP-DAG: selnez $[[T0:[0-9]+]], $[[I7]], $[[R0]]
+; 64-CMP-DAG: seleqz $[[T1:[0-9]+]], $[[I5]], $[[R0]]
+; 64-CMP-DAG: or $2, $[[T0]], $[[T1]]
define i32 @slti1(i32 %a) {
entry:
%cmp = icmp sgt i32 %a, 32767
- %cond = select i1 %cmp, i32 3, i32 5
+ %cond = select i1 %cmp, i32 7, i32 5
ret i32 %cond
}
-; O32-LABEL: slti2:
-; O32: slti $[[R0:[0-9]+]], ${{[0-9]+}}, -32768
-; O32: movz ${{[0-9]+}}, ${{[0-9]+}}, $[[R0]]
+; ALL-LABEL: slti2:
+
+; 32-CMOV-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 32-CMOV-DAG: addiu $[[I5:2]], $zero, 5
+; 32-CMOV-DAG: slti $[[R0:[0-9]+]], $4, -32768
+; 32-CMOV-DAG: movz $[[I5]], $[[I3]], $[[R0]]
+
+; 32-CMP-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 32-CMP-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 32-CMP-DAG: slti $[[R0:[0-9]+]], $4, -32768
+; FIXME: We can do better than this by using selccz to choose between +0 and +2
+; 32-CMP-DAG: seleqz $[[T0:[0-9]+]], $[[I3]], $[[R0]]
+; 32-CMP-DAG: selnez $[[T1:[0-9]+]], $[[I5]], $[[R0]]
+; 32-CMP-DAG: or $2, $[[T0]], $[[T1]]
+
+; 64-CMOV-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 64-CMOV-DAG: addiu $[[I5:2]], $zero, 5
+; 64-CMOV-DAG: slti $[[R0:[0-9]+]], $4, -32768
+; 64-CMOV-DAG: movz $[[I5]], $[[I3]], $[[R0]]
+
+; 64-CMP-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 64-CMP-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 64-CMP-DAG: slti $[[R0:[0-9]+]], $4, -32768
+; FIXME: We can do better than this by using selccz to choose between +0 and +2
+; 64-CMP-DAG: seleqz $[[T0:[0-9]+]], $[[I3]], $[[R0]]
+; 64-CMP-DAG: selnez $[[T1:[0-9]+]], $[[I5]], $[[R0]]
+; 64-CMP-DAG: or $2, $[[T0]], $[[T1]]
define i32 @slti2(i32 %a) {
entry:
@@ -100,8 +270,41 @@ entry:
ret i32 %cond
}
-; O32-LABEL: slti3:
-; O32: slt ${{[0-9]+}}
+; ALL-LABEL: slti3:
+
+; 32-CMOV-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 32-CMOV-DAG: addiu $[[I5:2]], $zero, 5
+; 32-CMOV-DAG: lui $[[R1:[0-9]+]], 65535
+; 32-CMOV-DAG: ori $[[R1]], $[[R1]], 32766
+; 32-CMOV-DAG: slt $[[R0:[0-9]+]], $[[R1]], $4
+; 32-CMOV-DAG: movn $[[I5]], $[[I3]], $[[R0]]
+
+; 32-CMP-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 32-CMP-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 32-CMP-DAG: lui $[[IMM:[0-9]+]], 65535
+; 32-CMP-DAG: ori $[[IMM]], $[[IMM]], 32766
+; 32-CMP-DAG: slt $[[R0:[0-9]+]], $[[I32767]], $4
+; FIXME: We can do better than this by using selccz to choose between -0 and -2
+; 32-CMP-DAG: selnez $[[T0:[0-9]+]], $[[I3]], $[[R0]]
+; 32-CMP-DAG: seleqz $[[T1:[0-9]+]], $[[I5]], $[[R0]]
+; 32-CMP-DAG: or $2, $[[T0]], $[[T1]]
+
+; 64-CMOV-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 64-CMOV-DAG: addiu $[[I5:2]], $zero, 5
+; 64-CMOV-DAG: lui $[[R1:[0-9]+]], 65535
+; 64-CMOV-DAG: ori $[[R1]], $[[R1]], 32766
+; 64-CMOV-DAG: slt $[[R0:[0-9]+]], $[[R1]], $4
+; 64-CMOV-DAG: movn $[[I5]], $[[I3]], $[[R0]]
+
+; 64-CMP-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 64-CMP-DAG: addiu $[[I5:2]], $zero, 5
+; 64-CMP-DAG: lui $[[IMM:[0-9]+]], 65535
+; 64-CMP-DAG: ori $[[IMM]], $[[IMM]], 32766
+; 64-CMP-DAG: slt $[[R0:[0-9]+]], $[[IMM]], $4
+; FIXME: We can do better than this by using selccz to choose between -0 and -2
+; 64-CMP-DAG: selnez $[[T0:[0-9]+]], $[[I3]], $[[R0]]
+; 64-CMP-DAG: seleqz $[[T1:[0-9]+]], $[[I5]], $[[R0]]
+; 64-CMP-DAG: or $2, $[[T0]], $[[T1]]
define i32 @slti3(i32 %a) {
entry:
@@ -112,30 +315,117 @@ entry:
; 64-bit patterns.
-; N64-LABEL: slti64_0:
-; N64: slti $[[R0:[0-9]+]], ${{[0-9]+}}, 32767
-; N64: movz ${{[0-9]+}}, ${{[0-9]+}}, $[[R0]]
+; ALL-LABEL: slti64_0:
+
+; 32-CMOV-DAG: slt $[[CC:[0-9]+]], $zero, $4
+; 32-CMOV-DAG: addiu $[[I32766:[0-9]+]], $zero, 32766
+; 32-CMOV-DAG: sltu $[[R1:[0-9]+]], $[[I32766]], $5
+; 32-CMOV-DAG: movz $[[CC:[0-9]+]], $[[R1]], $4
+; 32-CMOV-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 32-CMOV-DAG: addiu $[[I4:3]], $zero, 4
+; 32-CMOV-DAG: movn $[[I4]], $[[I5]], $[[CC]]
+; 32-CMOV-DAG: addiu $2, $zero, 0
+
+; 32-CMP-DAG: slt $[[CC0:[0-9]+]], $zero, $4
+; 32-CMP-DAG: addiu $[[I32766:[0-9]+]], $zero, 32766
+; 32-CMP-DAG: sltu $[[CC1:[0-9]+]], $[[I32766]], $5
+; 32-CMP-DAG: selnez $[[CC2:[0-9]+]], $[[CC0]], $4
+; 32-CMP-DAG: seleqz $[[CC3:[0-9]+]], $[[CC1]], $4
+; 32-CMP: or $[[CC:[0-9]+]], $[[CC3]], $[[CC2]]
+; 32-CMP-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 32-CMP-DAG: addiu $[[I4:[0-9]+]], $zero, 4
+; 32-CMP-DAG: seleqz $[[T0:[0-9]+]], $[[I4]], $[[CC]]
+; 32-CMP-DAG: selnez $[[T1:[0-9]+]], $[[I5]], $[[CC]]
+; 32-CMP-DAG: or $3, $[[T1]], $[[T0]]
+; 32-CMP-DAG: addiu $2, $zero, 0
+
+; 64-CMOV-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 64-CMOV-DAG: addiu $[[I4:2]], $zero, 4
+; 64-CMOV-DAG: slti $[[R0:[0-9]+]], $4, 32767
+; 64-CMOV-DAG: movz $[[I4]], $[[I5]], $[[R0]]
+
+; 64-CMP-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 64-CMP-DAG: addiu $[[I4:[0-9]+]], $zero, 4
+; 64-CMP-DAG: slti $[[R0:[0-9]+]], $4, 32767
+; FIXME: We can do better than this by adding/subtracting the result of slti
+; to/from one of the constants.
+; 64-CMP-DAG: seleqz $[[T0:[0-9]+]], $[[I5]], $[[R0]]
+; 64-CMP-DAG: selnez $[[T1:[0-9]+]], $[[I4]], $[[R0]]
+; 64-CMP-DAG: or $2, $[[T0]], $[[T1]]
define i64 @slti64_0(i64 %a) {
entry:
%cmp = icmp sgt i64 %a, 32766
- %conv = select i1 %cmp, i64 3, i64 4
+ %conv = select i1 %cmp, i64 5, i64 4
ret i64 %conv
}
-; N64-LABEL: slti64_1:
-; N64: slt ${{[0-9]+}}
+; ALL-LABEL: slti64_1:
+
+; 32-CMOV-DAG: slt $[[CC:[0-9]+]], $zero, $4
+; 32-CMOV-DAG: addiu $[[I32766:[0-9]+]], $zero, 32767
+; 32-CMOV-DAG: sltu $[[R1:[0-9]+]], $[[I32766]], $5
+; 32-CMOV-DAG: movz $[[CC:[0-9]+]], $[[R1]], $4
+; 32-CMOV-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 32-CMOV-DAG: addiu $[[I4:3]], $zero, 4
+; 32-CMOV-DAG: movn $[[I4]], $[[I5]], $[[CC]]
+; 32-CMOV-DAG: addiu $2, $zero, 0
+
+; 32-CMP-DAG: slt $[[CC0:[0-9]+]], $zero, $4
+; 32-CMP-DAG: addiu $[[I32766:[0-9]+]], $zero, 32767
+; 32-CMP-DAG: sltu $[[CC1:[0-9]+]], $[[I32766]], $5
+; 32-CMP-DAG: selnez $[[CC2:[0-9]+]], $[[CC0]], $4
+; 32-CMP-DAG: seleqz $[[CC3:[0-9]+]], $[[CC1]], $4
+; 32-CMP: or $[[CC:[0-9]+]], $[[CC3]], $[[CC2]]
+; 32-CMP-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 32-CMP-DAG: addiu $[[I4:[0-9]+]], $zero, 4
+; 32-CMP-DAG: seleqz $[[T0:[0-9]+]], $[[I4]], $[[CC]]
+; 32-CMP-DAG: selnez $[[T1:[0-9]+]], $[[I5]], $[[CC]]
+; 32-CMP-DAG: or $3, $[[T1]], $[[T0]]
+; 32-CMP-DAG: addiu $2, $zero, 0
+
+; 64-CMOV-DAG: daddiu $[[I5:[0-9]+]], $zero, 5
+; 64-CMOV-DAG: daddiu $[[I4:2]], $zero, 4
+; 64-CMOV-DAG: daddiu $[[R1:[0-9]+]], $zero, 32767
+; 64-CMOV-DAG: slt $[[R0:[0-9]+]], $[[R1]], $4
+; 64-CMOV-DAG: movn $[[I4]], $[[I5]], $[[R0]]
+
+; 64-CMP-DAG: daddiu $[[I5:[0-9]+]], $zero, 5
+; 64-CMP-DAG: daddiu $[[I4:2]], $zero, 4
+; 64-CMP-DAG: daddiu $[[R1:[0-9]+]], $zero, 32767
+; 64-CMP-DAG: slt $[[R0:[0-9]+]], $[[R1]], $4
+; FIXME: We can do better than this by using selccz to choose between -0 and -2
+; 64-CMP-DAG: selnez $[[T0:[0-9]+]], $[[I5]], $[[R0]]
+; 64-CMP-DAG: seleqz $[[T1:[0-9]+]], $[[I4]], $[[R0]]
+; 64-CMP-DAG: or $2, $[[T0]], $[[T1]]
define i64 @slti64_1(i64 %a) {
entry:
%cmp = icmp sgt i64 %a, 32767
- %conv = select i1 %cmp, i64 3, i64 4
+ %conv = select i1 %cmp, i64 5, i64 4
ret i64 %conv
}
-; N64-LABEL: slti64_2:
-; N64: slti $[[R0:[0-9]+]], ${{[0-9]+}}, -32768
-; N64: movz ${{[0-9]+}}, ${{[0-9]+}}, $[[R0]]
+; ALL-LABEL: slti64_2:
+
+; FIXME: The 32-bit versions of this test are too complicated to reasonably
+; match at the moment. They do show some missing optimizations though
+; such as:
+; (movz $a, $b, (neg $c)) -> (movn $a, $b, $c)
+
+; 64-CMOV-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 64-CMOV-DAG: addiu $[[I4:2]], $zero, 4
+; 64-CMOV-DAG: slti $[[R0:[0-9]+]], $4, -32768
+; 64-CMOV-DAG: movz $[[I4]], $[[I3]], $[[R0]]
+
+; 64-CMP-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 64-CMP-DAG: addiu $[[I4:[0-9]+]], $zero, 4
+; 64-CMP-DAG: slti $[[R0:[0-9]+]], $4, -32768
+; FIXME: We can do better than this by adding/subtracting the result of slti
+; to/from one of the constants.
+; 64-CMP-DAG: seleqz $[[T0:[0-9]+]], $[[I3]], $[[R0]]
+; 64-CMP-DAG: selnez $[[T1:[0-9]+]], $[[I4]], $[[R0]]
+; 64-CMP-DAG: or $2, $[[T0]], $[[T1]]
define i64 @slti64_2(i64 %a) {
entry:
@@ -144,21 +434,64 @@ entry:
ret i64 %conv
}
-; N64-LABEL: slti64_3:
-; N64: slt ${{[0-9]+}}
+; ALL-LABEL: slti64_3:
+
+; FIXME: The 32-bit versions of this test are too complicated to reasonably
+; match at the moment. They do show some missing optimizations though
+; such as:
+; (movz $a, $b, (neg $c)) -> (movn $a, $b, $c)
+
+; 64-CMOV-DAG: daddiu $[[I5:[0-9]+]], $zero, 5
+; 64-CMOV-DAG: daddiu $[[I4:2]], $zero, 4
+; 64-CMOV-DAG: daddiu $[[R1:[0-9]+]], ${{[0-9]+}}, 32766
+; 64-CMOV-DAG: slt $[[R0:[0-9]+]], $[[R1]], $4
+; 64-CMOV-DAG: movn $[[I4]], $[[I5]], $[[R0]]
+
+; 64-CMP-DAG: daddiu $[[I5:[0-9]+]], $zero, 5
+; 64-CMP-DAG: daddiu $[[I4:2]], $zero, 4
+; 64-CMP-DAG: daddiu $[[R1:[0-9]+]], ${{[0-9]+}}, 32766
+; 64-CMP-DAG: slt $[[R0:[0-9]+]], $[[R1]], $4
+; FIXME: We can do better than this by using selccz to choose between -0 and -2
+; 64-CMP-DAG: selnez $[[T0:[0-9]+]], $[[I5]], $[[R0]]
+; 64-CMP-DAG: seleqz $[[T1:[0-9]+]], $[[I4]], $[[R0]]
+; 64-CMP-DAG: or $2, $[[T0]], $[[T1]]
define i64 @slti64_3(i64 %a) {
entry:
%cmp = icmp sgt i64 %a, -32770
- %conv = select i1 %cmp, i64 3, i64 4
+ %conv = select i1 %cmp, i64 5, i64 4
ret i64 %conv
}
; sltiu instructions.
-; O32-LABEL: sltiu0:
-; O32: sltiu $[[R0:[0-9]+]], ${{[0-9]+}}, 32767
-; O32: movz ${{[0-9]+}}, ${{[0-9]+}}, $[[R0]]
+; ALL-LABEL: sltiu0:
+
+; 32-CMOV-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 32-CMOV-DAG: addiu $[[I5:2]], $zero, 5
+; 32-CMOV-DAG: sltiu $[[R0:[0-9]+]], $4, 32767
+; 32-CMOV-DAG: movz $[[I5]], $[[I3]], $[[R0]]
+
+; 32-CMP-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 32-CMP-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 32-CMP-DAG: sltiu $[[R0:[0-9]+]], $4, 32767
+; FIXME: We can do better than this by using selccz to choose between +0 and +2
+; 32-CMP-DAG: seleqz $[[T0:[0-9]+]], $[[I3]], $[[R0]]
+; 32-CMP-DAG: selnez $[[T1:[0-9]+]], $[[I5]], $[[R0]]
+; 32-CMP-DAG: or $2, $[[T0]], $[[T1]]
+
+; 64-CMOV-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 64-CMOV-DAG: addiu $[[I5:2]], $zero, 5
+; 64-CMOV-DAG: sltiu $[[R0:[0-9]+]], $4, 32767
+; 64-CMOV-DAG: movz $[[I5]], $[[I3]], $[[R0]]
+
+; 64-CMP-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 64-CMP-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 64-CMP-DAG: sltiu $[[R0:[0-9]+]], $4, 32767
+; FIXME: We can do better than this by using selccz to choose between +0 and +2
+; 64-CMP-DAG: seleqz $[[T0:[0-9]+]], $[[I3]], $[[R0]]
+; 64-CMP-DAG: selnez $[[T1:[0-9]+]], $[[I5]], $[[R0]]
+; 64-CMP-DAG: or $2, $[[T0]], $[[T1]]
define i32 @sltiu0(i32 %a) {
entry:
@@ -167,19 +500,72 @@ entry:
ret i32 %cond
}
-; O32-LABEL: sltiu1:
-; O32: sltu ${{[0-9]+}}
+; ALL-LABEL: sltiu1:
+
+; 32-CMOV-DAG: addiu $[[I7:[0-9]+]], $zero, 7
+; 32-CMOV-DAG: addiu $[[I5:2]], $zero, 5
+; 32-CMOV-DAG: addiu $[[R1:[0-9]+]], $zero, 32767
+; 32-CMOV-DAG: sltu $[[R0:[0-9]+]], $[[R1]], $4
+; 32-CMOV-DAG: movn $[[I5]], $[[I7]], $[[R0]]
+
+; 32-CMP-DAG: addiu $[[I7:[0-9]+]], $zero, 7
+; 32-CMP-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 32-CMP-DAG: addiu $[[I32767:[0-9]+]], $zero, 32767
+; 32-CMP-DAG: sltu $[[R0:[0-9]+]], $[[I32767]], $4
+; FIXME: We can do better than this by using selccz to choose between -0 and -2
+; 32-CMP-DAG: selnez $[[T0:[0-9]+]], $[[I7]], $[[R0]]
+; 32-CMP-DAG: seleqz $[[T1:[0-9]+]], $[[I5]], $[[R0]]
+; 32-CMP-DAG: or $2, $[[T0]], $[[T1]]
+
+; 64-CMOV-DAG: addiu $[[I7:[0-9]+]], $zero, 7
+; 64-CMOV-DAG: addiu $[[I5:2]], $zero, 5
+; 64-CMOV-DAG: addiu $[[R1:[0-9]+]], $zero, 32767
+; 64-CMOV-DAG: sltu $[[R0:[0-9]+]], $[[R1]], $4
+; 64-CMOV-DAG: movn $[[I5]], $[[I7]], $[[R0]]
+
+; 64-CMP-DAG: addiu $[[I7:[0-9]+]], $zero, 7
+; 64-CMP-DAG: addiu $[[I5:2]], $zero, 5
+; 64-CMP-DAG: addiu $[[R1:[0-9]+]], $zero, 32767
+; 64-CMP-DAG: sltu $[[R0:[0-9]+]], $[[R1]], $4
+; FIXME: We can do better than this by using selccz to choose between -0 and -2
+; 64-CMP-DAG: selnez $[[T0:[0-9]+]], $[[I7]], $[[R0]]
+; 64-CMP-DAG: seleqz $[[T1:[0-9]+]], $[[I5]], $[[R0]]
+; 64-CMP-DAG: or $2, $[[T0]], $[[T1]]
define i32 @sltiu1(i32 %a) {
entry:
%cmp = icmp ugt i32 %a, 32767
- %cond = select i1 %cmp, i32 3, i32 5
+ %cond = select i1 %cmp, i32 7, i32 5
ret i32 %cond
}
-; O32-LABEL: sltiu2:
-; O32: sltiu $[[R0:[0-9]+]], ${{[0-9]+}}, -32768
-; O32: movz ${{[0-9]+}}, ${{[0-9]+}}, $[[R0]]
+; ALL-LABEL: sltiu2:
+
+; 32-CMOV-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 32-CMOV-DAG: addiu $[[I5:2]], $zero, 5
+; 32-CMOV-DAG: sltiu $[[R0:[0-9]+]], $4, -32768
+; 32-CMOV-DAG: movz $[[I5]], $[[I3]], $[[R0]]
+
+; 32-CMP-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 32-CMP-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 32-CMP-DAG: sltiu $[[R0:[0-9]+]], $4, -32768
+; FIXME: We can do better than this by using selccz to choose between +0 and +2
+; 32-CMP-DAG: seleqz $[[T0:[0-9]+]], $[[I3]], $[[R0]]
+; 32-CMP-DAG: selnez $[[T1:[0-9]+]], $[[I5]], $[[R0]]
+; 32-CMP-DAG: or $2, $[[T0]], $[[T1]]
+
+; 64-CMOV-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 64-CMOV-DAG: addiu $[[I5:2]], $zero, 5
+; 64-CMOV-DAG: sltiu $[[R0:[0-9]+]], $4, -32768
+; 64-CMOV-DAG: movz $[[I5]], $[[I3]], $[[R0]]
+
+; 64-CMP-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 64-CMP-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 64-CMP-DAG: sltiu $[[R0:[0-9]+]], $4, -32768
+; FIXME: We can do better than this by using selccz to choose between +0 and +2
+; 64-CMP-DAG: seleqz $[[T0:[0-9]+]], $[[I3]], $[[R0]]
+; 64-CMP-DAG: selnez $[[T1:[0-9]+]], $[[I5]], $[[R0]]
+; 64-CMP-DAG: or $2, $[[T0]], $[[T1]]
define i32 @sltiu2(i32 %a) {
entry:
@@ -188,8 +574,41 @@ entry:
ret i32 %cond
}
-; O32-LABEL: sltiu3:
-; O32: sltu ${{[0-9]+}}
+; ALL-LABEL: sltiu3:
+
+; 32-CMOV-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 32-CMOV-DAG: addiu $[[I5:2]], $zero, 5
+; 32-CMOV-DAG: lui $[[R1:[0-9]+]], 65535
+; 32-CMOV-DAG: ori $[[R1]], $[[R1]], 32766
+; 32-CMOV-DAG: sltu $[[R0:[0-9]+]], $[[R1]], $4
+; 32-CMOV-DAG: movn $[[I5]], $[[I3]], $[[R0]]
+
+; 32-CMP-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 32-CMP-DAG: addiu $[[I5:[0-9]+]], $zero, 5
+; 32-CMP-DAG: lui $[[IMM:[0-9]+]], 65535
+; 32-CMP-DAG: ori $[[IMM]], $[[IMM]], 32766
+; 32-CMP-DAG: sltu $[[R0:[0-9]+]], $[[I32767]], $4
+; FIXME: We can do better than this by using selccz to choose between -0 and -2
+; 32-CMP-DAG: selnez $[[T0:[0-9]+]], $[[I3]], $[[R0]]
+; 32-CMP-DAG: seleqz $[[T1:[0-9]+]], $[[I5]], $[[R0]]
+; 32-CMP-DAG: or $2, $[[T0]], $[[T1]]
+
+; 64-CMOV-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 64-CMOV-DAG: addiu $[[I5:2]], $zero, 5
+; 64-CMOV-DAG: lui $[[R1:[0-9]+]], 65535
+; 64-CMOV-DAG: ori $[[R1]], $[[R1]], 32766
+; 64-CMOV-DAG: sltu $[[R0:[0-9]+]], $[[R1]], $4
+; 64-CMOV-DAG: movn $[[I5]], $[[I3]], $[[R0]]
+
+; 64-CMP-DAG: addiu $[[I3:[0-9]+]], $zero, 3
+; 64-CMP-DAG: addiu $[[I5:2]], $zero, 5
+; 64-CMP-DAG: lui $[[IMM:[0-9]+]], 65535
+; 64-CMP-DAG: ori $[[IMM]], $[[IMM]], 32766
+; 64-CMP-DAG: sltu $[[R0:[0-9]+]], $[[IMM]], $4
+; FIXME: We can do better than this by using selccz to choose between -0 and -2
+; 64-CMP-DAG: selnez $[[T0:[0-9]+]], $[[I3]], $[[R0]]
+; 64-CMP-DAG: seleqz $[[T1:[0-9]+]], $[[I5]], $[[R0]]
+; 64-CMP-DAG: or $2, $[[T0]], $[[T1]]
define i32 @sltiu3(i32 %a) {
entry:
@@ -210,11 +629,25 @@ define i32 @slti4(i32 %a) nounwind readnone {
ret i32 %2
}
-; O32-LABEL: slti4:
-; O32-DAG: slti [[R1:\$[0-9]+]], $4, 7
-; O32-DAG: addiu [[R2:\$[0-9]+]], [[R1]], 3
-; O32-NOT: movn
-; O32:.size slti4
+; ALL-LABEL: slti4:
+
+; 32-CMOV-DAG: slti [[R1:\$[0-9]+]], $4, 7
+; 32-CMOV-DAG: addiu $2, [[R1]], 3
+; 32-CMOV-NOT: movn
+
+; 32-CMP-DAG: slti [[R1:\$[0-9]+]], $4, 7
+; 32-CMP-DAG: addiu $2, [[R1]], 3
+; 32-CMP-NOT: seleqz
+; 32-CMP-NOT: selnez
+
+; 64-CMOV-DAG: slti [[R1:\$[0-9]+]], $4, 7
+; 64-CMOV-DAG: addiu $2, [[R1]], 3
+; 64-CMOV-NOT: movn
+
+; 64-CMP-DAG: slti [[R1:\$[0-9]+]], $4, 7
+; 64-CMP-DAG: addiu $2, [[R1]], 3
+; 64-CMP-NOT: seleqz
+; 64-CMP-NOT: selnez
define i32 @slti5(i32 %a) nounwind readnone {
%1 = icmp slt i32 %a, 7
@@ -222,11 +655,25 @@ define i32 @slti5(i32 %a) nounwind readnone {
ret i32 %2
}
-; O32-LABEL: slti5:
-; O32-DAG: slti [[R1:\$[0-9]+]], $4, 7
-; O32-DAG: addiu [[R3:\$[0-9]+]], [[R2:\$[a-z0-9]+]], -4
-; O32-NOT: movn
-; O32:.size slti5
+; ALL-LABEL: slti5:
+
+; 32-CMOV-DAG: slti [[R1:\$[0-9]+]], $4, 7
+; 32-CMOV-DAG: addiu [[R3:\$[0-9]+]], [[R2:\$[a-z0-9]+]], -4
+; 32-CMOV-NOT: movn
+
+; 32-CMP-DAG: slti [[R1:\$[0-9]+]], $4, 7
+; 32-CMP-DAG: addiu [[R3:\$[0-9]+]], [[R2:\$[a-z0-9]+]], -4
+; 32-CMP-NOT: seleqz
+; 32-CMP-NOT: selnez
+
+; 64-CMOV-DAG: slti [[R1:\$[0-9]+]], $4, 7
+; 64-CMOV-DAG: addiu [[R3:\$[0-9]+]], [[R2:\$[a-z0-9]+]], -4
+; 64-CMOV-NOT: movn
+
+; 64-CMP-DAG: slti [[R1:\$[0-9]+]], $4, 7
+; 64-CMP-DAG: addiu [[R3:\$[0-9]+]], [[R2:\$[a-z0-9]+]], -4
+; 64-CMP-NOT: seleqz
+; 64-CMP-NOT: selnez
define i32 @slti6(i32 %a) nounwind readnone {
%1 = icmp slt i32 %a, 7
@@ -234,9 +681,26 @@ define i32 @slti6(i32 %a) nounwind readnone {
ret i32 %2
}
-; O32-LABEL: slti6:
-; O32-DAG: slti [[R1:\$[0-9]+]], $4, 7
-; O32-DAG: xori [[R1]], [[R1]], 1
-; O32-DAG: addiu [[R2:\$[0-9]+]], [[R1]], 3
-; O32-NOT: movn
-; O32:.size slti6
+; ALL-LABEL: slti6:
+
+; 32-CMOV-DAG: slti [[R1:\$[0-9]+]], $4, 7
+; 32-CMOV-DAG: xori [[R1]], [[R1]], 1
+; 32-CMOV-DAG: addiu [[R2:\$[0-9]+]], [[R1]], 3
+; 32-CMOV-NOT: movn
+
+; 32-CMP-DAG: slti [[R1:\$[0-9]+]], $4, 7
+; 32-CMP-DAG: xori [[R1]], [[R1]], 1
+; 32-CMP-DAG: addiu [[R2:\$[0-9]+]], [[R1]], 3
+; 32-CMP-NOT: seleqz
+; 32-CMP-NOT: selnez
+
+; 64-CMOV-DAG: slti [[R1:\$[0-9]+]], $4, 7
+; 64-CMOV-DAG: xori [[R1]], [[R1]], 1
+; 64-CMOV-DAG: addiu [[R2:\$[0-9]+]], [[R1]], 3
+; 64-CMOV-NOT: movn
+
+; 64-CMP-DAG: slti [[R1:\$[0-9]+]], $4, 7
+; 64-CMP-DAG: xori [[R1]], [[R1]], 1
+; 64-CMP-DAG: addiu [[R2:\$[0-9]+]], [[R1]], 3
+; 64-CMP-NOT: seleqz
+; 64-CMP-NOT: selnez
diff --git a/test/CodeGen/Mips/countleading.ll b/test/CodeGen/Mips/countleading.ll
new file mode 100644
index 0000000..6e63cff
--- /dev/null
+++ b/test/CodeGen/Mips/countleading.ll
@@ -0,0 +1,90 @@
+; RUN: llc -march=mipsel -mcpu=mips32 < %s | FileCheck -check-prefix=ALL -check-prefix=MIPS32-R1-R2 -check-prefix=MIPS32-GT-R1 %s
+; RUN: llc -march=mipsel -mcpu=mips32r2 < %s | FileCheck -check-prefix=ALL -check-prefix=MIPS32-R1-R2 -check-prefix=MIPS32-GT-R1 %s
+; RUN: llc -march=mipsel -mcpu=mips32r6 < %s | FileCheck -check-prefix=ALL -check-prefix=MIPS32-R6 -check-prefix=MIPS32-GT-R1 %s
+; RUN: llc -march=mips64el -mcpu=mips4 < %s | FileCheck -check-prefix=ALL -check-prefix=MIPS4 %s
+; RUN: llc -march=mips64el -mcpu=mips64 < %s | FileCheck -check-prefix=ALL -check-prefix=MIPS64-GT-R1 %s
+; RUN: llc -march=mips64el -mcpu=mips64r2 < %s | FileCheck -check-prefix=ALL -check-prefix=MIPS64-GT-R1 %s
+; R!N: llc -march=mips64el -mcpu=mips64r6 < %s | FileCheck -check-prefix=ALL -check-prefix=MIPS64-GT-R1 %s
+
+; Prefixes:
+; ALL - All
+; MIPS32-GT-R1 - MIPS64r1 and above (does not include MIPS64's)
+; MIPS64-GT-R1 - MIPS64r1 and above
+
+define i32 @ctlz_i32(i32 %X) nounwind readnone {
+entry:
+; ALL-LABEL: ctlz_i32:
+
+; MIPS4-NOT: clz
+
+; MIPS32-GT-R1: clz $2, $4
+
+; MIPS64-GT-R1: clz $2, $4
+
+ %tmp1 = tail call i32 @llvm.ctlz.i32(i32 %X, i1 true)
+ ret i32 %tmp1
+}
+
+declare i32 @llvm.ctlz.i32(i32, i1) nounwind readnone
+
+define i32 @ctlo_i32(i32 %X) nounwind readnone {
+entry:
+; ALL-LABEL: ctlo_i32:
+
+; MIPS4-NOT: clo
+
+; MIPS32-GT-R1: clo $2, $4
+
+; MIPS64-GT-R1: clo $2, $4
+
+ %neg = xor i32 %X, -1
+ %tmp1 = tail call i32 @llvm.ctlz.i32(i32 %neg, i1 true)
+ ret i32 %tmp1
+}
+
+define i64 @ctlz_i64(i64 %X) nounwind readnone {
+entry:
+; ALL-LABEL: ctlz_i64:
+
+; MIPS4-NOT: dclz
+
+; MIPS32-GT-R1-DAG: clz $[[R0:[0-9]+]], $4
+; MIPS32-GT-R1-DAG: clz $[[R1:[0-9]+]], $5
+; MIPS32-GT-R1-DAG: addiu $[[R2:2+]], $[[R0]], 32
+; MIPS32-R1-R2-DAG: movn $[[R2]], $[[R1]], $5
+; MIPS32-R6-DAG: seleqz $[[R5:[0-9]+]], $[[R2]], $5
+; MIPS32-R6-DAG: selnez $[[R6:[0-9]+]], $[[R1]], $5
+; MIPS32-R6-DAG: or $2, $[[R6]], $[[R5]]
+; MIPS32-GT-R1-DAG: addiu $3, $zero, 0
+
+; MIPS64-GT-R1: dclz $2, $4
+
+ %tmp1 = tail call i64 @llvm.ctlz.i64(i64 %X, i1 true)
+ ret i64 %tmp1
+}
+
+declare i64 @llvm.ctlz.i64(i64, i1) nounwind readnone
+
+define i64 @ctlo_i64(i64 %X) nounwind readnone {
+entry:
+; ALL-LABEL: ctlo_i64:
+
+; MIPS4-NOT: dclo
+
+; MIPS32-GT-R1-DAG: clo $[[R0:[0-9]+]], $4
+; MIPS32-GT-R1-DAG: clo $[[R1:[0-9]+]], $5
+; MIPS32-GT-R1-DAG: addiu $[[R2:2+]], $[[R0]], 32
+; MIPS32-GT-R1-DAG: addiu $[[R3:[0-9]+]], $zero, -1
+; MIPS32-GT-R1-DAG: xor $[[R4:[0-9]+]], $5, $[[R3]]
+; MIPS32-R1-R2-DAG: movn $[[R2]], $[[R1]], $[[R4]]
+; MIPS32-R6-DAG: selnez $[[R5:[0-9]+]], $[[R1]], $[[R4]]
+; MIPS32-R6-DAG: seleqz $[[R6:[0-9]+]], $[[R2]], $[[R4]]
+; MIPS32-R6-DAG: or $2, $[[R5]], $[[R6]]
+; MIPS32-GT-R1-DAG: addiu $3, $zero, 0
+
+; MIPS64-GT-R1: dclo $2, $4
+
+ %neg = xor i64 %X, -1
+ %tmp1 = tail call i64 @llvm.ctlz.i64(i64 %neg, i1 true)
+ ret i64 %tmp1
+}
diff --git a/test/CodeGen/Mips/divrem.ll b/test/CodeGen/Mips/divrem.ll
index b631c3b..97f8360 100644
--- a/test/CodeGen/Mips/divrem.ll
+++ b/test/CodeGen/Mips/divrem.ll
@@ -1,77 +1,223 @@
-; RUN: llc -march=mips -verify-machineinstrs < %s |\
-; RUN: FileCheck %s -check-prefix=TRAP
-; RUN: llc -march=mips -mno-check-zero-division < %s |\
-; RUN: FileCheck %s -check-prefix=NOCHECK
+; RUN: llc -march=mips -mcpu=mips32 -verify-machineinstrs < %s | FileCheck %s -check-prefix=ALL -check-prefix=ACC32 -check-prefix=ACC32-TRAP
+; RUN: llc -march=mips -mcpu=mips32r2 -verify-machineinstrs < %s | FileCheck %s -check-prefix=ALL -check-prefix=ACC32 -check-prefix=ACC32-TRAP
+; RUN: llc -march=mips -mcpu=mips32r6 -verify-machineinstrs < %s | FileCheck %s -check-prefix=ALL -check-prefix=GPR32 -check-prefix=GPR32-TRAP
+; RUN: llc -march=mips64 -mcpu=mips64 -verify-machineinstrs < %s | FileCheck %s -check-prefix=ALL -check-prefix=ACC64 -check-prefix=ACC64-TRAP
+; RUN: llc -march=mips64 -mcpu=mips64r2 -verify-machineinstrs < %s | FileCheck %s -check-prefix=ALL -check-prefix=ACC64 -check-prefix=ACC64-TRAP
+; RUN: llc -march=mips64 -mcpu=mips64r6 -verify-machineinstrs < %s | FileCheck %s -check-prefix=ALL -check-prefix=GPR64 -check-prefix=GPR64-TRAP
-; TRAP-LABEL: sdiv1:
-; TRAP: div $zero, ${{[0-9]+}}, $[[R0:[0-9]+]]
-; TRAP: teq $[[R0]], $zero, 7
-; TRAP: mflo
+; RUN: llc -march=mips -mcpu=mips32 -mno-check-zero-division < %s | FileCheck %s -check-prefix=ALL -check-prefix=ACC32 -check-prefix=NOCHECK
+; RUN: llc -march=mips -mcpu=mips32r2 -mno-check-zero-division < %s | FileCheck %s -check-prefix=ALL -check-prefix=ACC32 -check-prefix=NOCHECK
+; RUN: llc -march=mips -mcpu=mips32r6 -mno-check-zero-division < %s | FileCheck %s -check-prefix=ALL -check-prefix=GPR32 -check-prefix=NOCHECK
+; RUN: llc -march=mips64 -mcpu=mips64 -mno-check-zero-division < %s | FileCheck %s -check-prefix=ALL -check-prefix=ACC64 -check-prefix=NOCHECK
+; RUN: llc -march=mips64 -mcpu=mips64r2 -mno-check-zero-division < %s | FileCheck %s -check-prefix=ALL -check-prefix=ACC64 -check-prefix=NOCHECK
+; RUN: llc -march=mips64 -mcpu=mips64r6 -mno-check-zero-division < %s | FileCheck %s -check-prefix=ALL -check-prefix=GPR64 -check-prefix=NOCHECK
-; NOCHECK-LABEL: sdiv1:
-; NOCHECK-NOT: teq
-; NOCHECK: .end sdiv1
+; FileCheck Prefixes:
+; ALL - All targets
+; ACC32 - Accumulator based multiply/divide on 32-bit targets
+; ACC64 - Same as ACC32 but only for 64-bit targets
+; GPR32 - GPR based multiply/divide on 32-bit targets
+; GPR64 - Same as GPR32 but only for 64-bit targets
+; ACC32-TRAP - Same as TRAP and ACC32 combined
+; ACC64-TRAP - Same as TRAP and ACC64 combined
+; GPR32-TRAP - Same as TRAP and GPR32 combined
+; GPR64-TRAP - Same as TRAP and GPR64 combined
+; NOCHECK - Division by zero will not be detected
@g0 = common global i32 0, align 4
@g1 = common global i32 0, align 4
define i32 @sdiv1(i32 %a0, i32 %a1) nounwind readnone {
entry:
+; ALL-LABEL: sdiv1:
+
+; ACC32: div $zero, $4, $5
+; ACC32-TRAP: teq $5, $zero, 7
+
+; ACC64: div $zero, $4, $5
+; ACC64-TRAP: teq $5, $zero, 7
+
+; GPR32: div $2, $4, $5
+; GPR32-TRAP: teq $5, $zero, 7
+
+; GPR64: div $2, $4, $5
+; GPR64-TRAP: teq $5, $zero, 7
+
+; NOCHECK-NOT: teq
+
+; ACC32: mflo $2
+; ACC64: mflo $2
+
+; ALL: .end sdiv1
+
%div = sdiv i32 %a0, %a1
ret i32 %div
}
-; TRAP-LABEL: srem1:
-; TRAP: div $zero, ${{[0-9]+}}, $[[R0:[0-9]+]]
-; TRAP: teq $[[R0]], $zero, 7
-; TRAP: mfhi
-
define i32 @srem1(i32 %a0, i32 %a1) nounwind readnone {
entry:
+; ALL-LABEL: srem1:
+
+; ACC32: div $zero, $4, $5
+; ACC32-TRAP: teq $5, $zero, 7
+
+; ACC64: div $zero, $4, $5
+; ACC64-TRAP: teq $5, $zero, 7
+
+; GPR32: mod $2, $4, $5
+; GPR32-TRAP: teq $5, $zero, 7
+
+; GPR64: mod $2, $4, $5
+; GPR64-TRAP: teq $5, $zero, 7
+
+; NOCHECK-NOT: teq
+
+; ACC32: mfhi $2
+; ACC64: mfhi $2
+
+; ALL: .end srem1
+
%rem = srem i32 %a0, %a1
ret i32 %rem
}
-; TRAP-LABEL: udiv1:
-; TRAP: divu $zero, ${{[0-9]+}}, $[[R0:[0-9]+]]
-; TRAP: teq $[[R0]], $zero, 7
-; TRAP: mflo
-
define i32 @udiv1(i32 %a0, i32 %a1) nounwind readnone {
entry:
+; ALL-LABEL: udiv1:
+
+; ACC32: divu $zero, $4, $5
+; ACC32-TRAP: teq $5, $zero, 7
+
+; ACC64: divu $zero, $4, $5
+; ACC64-TRAP: teq $5, $zero, 7
+
+; GPR32: divu $2, $4, $5
+; GPR32-TRAP: teq $5, $zero, 7
+
+; GPR64: divu $2, $4, $5
+; GPR64-TRAP: teq $5, $zero, 7
+
+; NOCHECK-NOT: teq
+
+; ACC32: mflo $2
+; ACC64: mflo $2
+
+; ALL: .end udiv1
%div = udiv i32 %a0, %a1
ret i32 %div
}
-; TRAP-LABEL: urem1:
-; TRAP: divu $zero, ${{[0-9]+}}, $[[R0:[0-9]+]]
-; TRAP: teq $[[R0]], $zero, 7
-; TRAP: mfhi
-
define i32 @urem1(i32 %a0, i32 %a1) nounwind readnone {
entry:
+; ALL-LABEL: urem1:
+
+; ACC32: divu $zero, $4, $5
+; ACC32-TRAP: teq $5, $zero, 7
+
+; ACC64: divu $zero, $4, $5
+; ACC64-TRAP: teq $5, $zero, 7
+
+; GPR32: modu $2, $4, $5
+; GPR32-TRAP: teq $5, $zero, 7
+
+; GPR64: modu $2, $4, $5
+; GPR64-TRAP: teq $5, $zero, 7
+
+; NOCHECK-NOT: teq
+
+; ACC32: mfhi $2
+; ACC64: mfhi $2
+
+; ALL: .end urem1
+
%rem = urem i32 %a0, %a1
ret i32 %rem
}
-; TRAP: div $zero,
define i32 @sdivrem1(i32 %a0, i32 %a1, i32* nocapture %r) nounwind {
entry:
+; ALL-LABEL: sdivrem1:
+
+; ACC32: div $zero, $4, $5
+; ACC32-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+; ACC32: mflo $2
+; ACC32: mfhi $[[R0:[0-9]+]]
+; ACC32: sw $[[R0]], 0(${{[0-9]+}})
+
+; ACC64: div $zero, $4, $5
+; ACC64-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+; ACC64: mflo $2
+; ACC64: mfhi $[[R0:[0-9]+]]
+; ACC64: sw $[[R0]], 0(${{[0-9]+}})
+
+; GPR32: mod $[[R0:[0-9]+]], $4, $5
+; GPR32-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+; GPR32: sw $[[R0]], 0(${{[0-9]+}})
+; GPR32-DAG: div $2, $4, $5
+; GPR32-TRAP: teq $5, $zero, 7
+
+; GPR64: mod $[[R0:[0-9]+]], $4, $5
+; GPR64-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+; GPR64: sw $[[R0]], 0(${{[0-9]+}})
+; GPR64-DAG: div $2, $4, $5
+; GPR64-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+
+; ALL: .end sdivrem1
+
%rem = srem i32 %a0, %a1
store i32 %rem, i32* %r, align 4
%div = sdiv i32 %a0, %a1
ret i32 %div
}
-; TRAP: divu $zero,
define i32 @udivrem1(i32 %a0, i32 %a1, i32* nocapture %r) nounwind {
entry:
+; ALL-LABEL: udivrem1:
+
+; ACC32: divu $zero, $4, $5
+; ACC32-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+; ACC32: mflo $2
+; ACC32: mfhi $[[R0:[0-9]+]]
+; ACC32: sw $[[R0]], 0(${{[0-9]+}})
+
+; ACC64: divu $zero, $4, $5
+; ACC64-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+; ACC64: mflo $2
+; ACC64: mfhi $[[R0:[0-9]+]]
+; ACC64: sw $[[R0]], 0(${{[0-9]+}})
+
+; GPR32: modu $[[R0:[0-9]+]], $4, $5
+; GPR32-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+; GPR32: sw $[[R0]], 0(${{[0-9]+}})
+; GPR32-DAG: divu $2, $4, $5
+; GPR32-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+
+; GPR64: modu $[[R0:[0-9]+]], $4, $5
+; GPR64-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+; GPR64: sw $[[R0]], 0(${{[0-9]+}})
+; GPR64-DAG: divu $2, $4, $5
+; GPR64-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+
+; ALL: .end udivrem1
+
%rem = urem i32 %a0, %a1
store i32 %rem, i32* %r, align 4
%div = udiv i32 %a0, %a1
ret i32 %div
}
+; FIXME: It's not clear what this is supposed to test.
define i32 @killFlags() {
entry:
%0 = load i32* @g0, align 4
@@ -79,3 +225,164 @@ entry:
%div = sdiv i32 %0, %1
ret i32 %div
}
+
+define i64 @sdiv2(i64 %a0, i64 %a1) nounwind readnone {
+entry:
+; ALL-LABEL: sdiv2:
+
+; ACC32: lw $25, %call16(__divdi3)(
+; ACC32: jalr $25
+
+; ACC64: ddiv $zero, $4, $5
+; ACC64-TRAP: teq $5, $zero, 7
+
+; GPR64: ddiv $2, $4, $5
+; GPR64-TRAP: teq $5, $zero, 7
+
+; NOCHECK-NOT: teq
+
+; ACC64: mflo $2
+
+; ALL: .end sdiv2
+
+ %div = sdiv i64 %a0, %a1
+ ret i64 %div
+}
+
+define i64 @srem2(i64 %a0, i64 %a1) nounwind readnone {
+entry:
+; ALL-LABEL: srem2:
+
+; ACC32: lw $25, %call16(__moddi3)(
+; ACC32: jalr $25
+
+; ACC64: div $zero, $4, $5
+; ACC64-TRAP: teq $5, $zero, 7
+
+; GPR64: dmod $2, $4, $5
+; GPR64-TRAP: teq $5, $zero, 7
+
+; NOCHECK-NOT: teq
+
+; ACC64: mfhi $2
+
+; ALL: .end srem2
+
+ %rem = srem i64 %a0, %a1
+ ret i64 %rem
+}
+
+define i64 @udiv2(i64 %a0, i64 %a1) nounwind readnone {
+entry:
+; ALL-LABEL: udiv2:
+
+; ACC32: lw $25, %call16(__udivdi3)(
+; ACC32: jalr $25
+
+; ACC64: divu $zero, $4, $5
+; ACC64-TRAP: teq $5, $zero, 7
+
+; GPR64: ddivu $2, $4, $5
+; GPR64-TRAP: teq $5, $zero, 7
+
+; NOCHECK-NOT: teq
+
+; ACC64: mflo $2
+
+; ALL: .end udiv2
+ %div = udiv i64 %a0, %a1
+ ret i64 %div
+}
+
+define i64 @urem2(i64 %a0, i64 %a1) nounwind readnone {
+entry:
+; ALL-LABEL: urem2:
+
+; ACC32: lw $25, %call16(__umoddi3)(
+; ACC32: jalr $25
+
+; ACC64: divu $zero, $4, $5
+; ACC64-TRAP: teq $5, $zero, 7
+
+; GPR64: dmodu $2, $4, $5
+; GPR64-TRAP: teq $5, $zero, 7
+
+; NOCHECK-NOT: teq
+
+; ACC64: mfhi $2
+
+; ALL: .end urem2
+
+ %rem = urem i64 %a0, %a1
+ ret i64 %rem
+}
+
+define i64 @sdivrem2(i64 %a0, i64 %a1, i64* nocapture %r) nounwind {
+entry:
+; ALL-LABEL: sdivrem2:
+
+; sdivrem2 is too complex to effectively check. We can at least check for the
+; calls though.
+; ACC32: lw $25, %call16(__moddi3)(
+; ACC32: jalr $25
+; ACC32: lw $25, %call16(__divdi3)(
+; ACC32: jalr $25
+
+; ACC64: ddiv $zero, $4, $5
+; ACC64-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+; ACC64: mflo $2
+; ACC64: mfhi $[[R0:[0-9]+]]
+; ACC64: sd $[[R0]], 0(${{[0-9]+}})
+
+; GPR64: dmod $[[R0:[0-9]+]], $4, $5
+; GPR64-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+; GPR64: sd $[[R0]], 0(${{[0-9]+}})
+
+; GPR64-DAG: ddiv $2, $4, $5
+; GPR64-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+
+; ALL: .end sdivrem2
+
+ %rem = srem i64 %a0, %a1
+ store i64 %rem, i64* %r, align 8
+ %div = sdiv i64 %a0, %a1
+ ret i64 %div
+}
+
+define i64 @udivrem2(i64 %a0, i64 %a1, i64* nocapture %r) nounwind {
+entry:
+; ALL-LABEL: udivrem2:
+
+; udivrem2 is too complex to effectively check. We can at least check for the
+; calls though.
+; ACC32: lw $25, %call16(__umoddi3)(
+; ACC32: jalr $25
+; ACC32: lw $25, %call16(__udivdi3)(
+; ACC32: jalr $25
+
+; ACC64: ddivu $zero, $4, $5
+; ACC64-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+; ACC64: mflo $2
+; ACC64: mfhi $[[R0:[0-9]+]]
+; ACC64: sd $[[R0]], 0(${{[0-9]+}})
+
+; GPR64: dmodu $[[R0:[0-9]+]], $4, $5
+; GPR64-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+; GPR64: sd $[[R0]], 0(${{[0-9]+}})
+
+; GPR64-DAG: ddivu $2, $4, $5
+; GPR64-TRAP: teq $5, $zero, 7
+; NOCHECK-NOT: teq
+
+; ALL: .end udivrem2
+
+ %rem = urem i64 %a0, %a1
+ store i64 %rem, i64* %r, align 8
+ %div = udiv i64 %a0, %a1
+ ret i64 %div
+}
diff --git a/test/CodeGen/Mips/dsp-r1.ll b/test/CodeGen/Mips/dsp-r1.ll
index acdd17d..fbd9703 100644
--- a/test/CodeGen/Mips/dsp-r1.ll
+++ b/test/CodeGen/Mips/dsp-r1.ll
@@ -1,4 +1,4 @@
-; RUN: llc -march=mipsel -mattr=+dsp < %s | FileCheck %s
+; RUN: llc -march=mipsel -mcpu=mips32 -mattr=+dsp < %s | FileCheck %s
define i32 @test__builtin_mips_extr_w1(i32 %i0, i32, i64 %a0) nounwind {
entry:
diff --git a/test/CodeGen/Mips/eh-return32.ll b/test/CodeGen/Mips/eh-return32.ll
index c3003b3..748050c 100644
--- a/test/CodeGen/Mips/eh-return32.ll
+++ b/test/CodeGen/Mips/eh-return32.ll
@@ -1,4 +1,6 @@
-; RUN: llc -march=mipsel -mcpu=mips32 < %s | FileCheck %s
+; RUN: llc -march=mipsel -mcpu=mips32 -asm-show-inst < %s | FileCheck %s -check-prefix=CHECK -check-prefix=NOT-R6
+; RUN: llc -march=mipsel -mcpu=mips32r2 -asm-show-inst < %s | FileCheck %s -check-prefix=CHECK -check-prefix=NOT-R6
+; RUN: llc -march=mipsel -mcpu=mips32r6 -asm-show-inst < %s | FileCheck %s -check-prefix=CHECK -check-prefix=R6
declare void @llvm.eh.return.i32(i32, i8*)
declare void @foo(...)
@@ -9,7 +11,7 @@ entry:
call void @llvm.eh.return.i32(i32 %offset, i8* %handler)
unreachable
-; CHECK: f1
+; CHECK: f1:
; CHECK: addiu $sp, $sp, -[[spoffset:[0-9]+]]
; check that $a0-$a3 are saved on stack.
@@ -41,7 +43,8 @@ entry:
; CHECK: addiu $sp, $sp, [[spoffset]]
; CHECK: move $25, $2
; CHECK: move $ra, $2
-; CHECK: jr $ra
+; NOT-R6: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6: jr $ra # <MCInst #{{[0-9]+}} JALR
; CHECK: addu $sp, $sp, $3
}
@@ -50,7 +53,7 @@ entry:
call void @llvm.eh.return.i32(i32 %offset, i8* %handler)
unreachable
-; CHECK: f2
+; CHECK: f2:
; CHECK: addiu $sp, $sp, -[[spoffset:[0-9]+]]
; check that $a0-$a3 are saved on stack.
@@ -80,6 +83,7 @@ entry:
; CHECK: addiu $sp, $sp, [[spoffset]]
; CHECK: move $25, $2
; CHECK: move $ra, $2
-; CHECK: jr $ra
+; NOT-R6: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6: jr $ra # <MCInst #{{[0-9]+}} JALR
; CHECK: addu $sp, $sp, $3
}
diff --git a/test/CodeGen/Mips/eh-return64.ll b/test/CodeGen/Mips/eh-return64.ll
index 8c5af50..74a4323 100644
--- a/test/CodeGen/Mips/eh-return64.ll
+++ b/test/CodeGen/Mips/eh-return64.ll
@@ -1,5 +1,7 @@
-; RUN: llc -march=mips64el -mcpu=mips4 < %s | FileCheck %s
-; RUN: llc -march=mips64el -mcpu=mips64 < %s | FileCheck %s
+; RUN: llc -march=mips64el -mcpu=mips4 -asm-show-inst < %s | FileCheck %s -check-prefix=CHECK -check-prefix=NOT-R6
+; RUN: llc -march=mips64el -mcpu=mips64 -asm-show-inst < %s | FileCheck %s -check-prefix=CHECK -check-prefix=NOT-R6
+; RUN: llc -march=mips64el -mcpu=mips64r2 -asm-show-inst < %s | FileCheck %s -check-prefix=CHECK -check-prefix=NOT-R6
+; RUN: llc -march=mips64el -mcpu=mips64r6 -asm-show-inst < %s | FileCheck %s -check-prefix=CHECK -check-prefix=R6
declare void @llvm.eh.return.i64(i64, i8*)
declare void @foo(...)
@@ -10,7 +12,7 @@ entry:
call void @llvm.eh.return.i64(i64 %offset, i8* %handler)
unreachable
-; CHECK: f1
+; CHECK: f1:
; CHECK: daddiu $sp, $sp, -[[spoffset:[0-9]+]]
; check that $a0-$a3 are saved on stack.
@@ -42,9 +44,9 @@ entry:
; CHECK: daddiu $sp, $sp, [[spoffset]]
; CHECK: move $25, $2
; CHECK: move $ra, $2
-; CHECK: jr $ra
+; NOT-R6: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6: jr $ra # <MCInst #{{[0-9]+}} JALR
; CHECK: daddu $sp, $sp, $3
-
}
define void @f2(i64 %offset, i8* %handler) {
@@ -52,7 +54,7 @@ entry:
call void @llvm.eh.return.i64(i64 %offset, i8* %handler)
unreachable
-; CHECK: f2
+; CHECK: f2:
; CHECK: .cfi_startproc
; CHECK: daddiu $sp, $sp, -[[spoffset:[0-9]+]]
; CHECK: .cfi_def_cfa_offset [[spoffset]]
@@ -84,7 +86,8 @@ entry:
; CHECK: daddiu $sp, $sp, [[spoffset]]
; CHECK: move $25, $2
; CHECK: move $ra, $2
-; CHECK: jr $ra
+; NOT-R6: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6: jr $ra # <MCInst #{{[0-9]+}} JALR
; CHECK: daddu $sp, $sp, $3
; CHECK: .cfi_endproc
}
diff --git a/test/CodeGen/Mips/ehframe-indirect.ll b/test/CodeGen/Mips/ehframe-indirect.ll
new file mode 100644
index 0000000..e78497a
--- /dev/null
+++ b/test/CodeGen/Mips/ehframe-indirect.ll
@@ -0,0 +1,34 @@
+; RUN: llc -mtriple=mipsel-linux-gnu < %s | FileCheck %s
+; RUN: llc -mtriple=mipsel-linux-android < %s | FileCheck %s
+
+define i32 @main() {
+; CHECK: .cfi_startproc
+; CHECK: .cfi_personality 128, DW.ref.__gxx_personality_v0
+
+entry:
+ invoke void @foo() to label %cont unwind label %lpad
+; CHECK: foo
+; CHECK: jalr
+
+lpad:
+ %0 = landingpad { i8*, i32 } personality i8*
+ bitcast (i32 (...)* @__gxx_personality_v0 to i8*) catch i8* null
+ ret i32 0
+
+cont:
+ ret i32 0
+}
+; CHECK: .cfi_endproc
+
+declare i32 @__gxx_personality_v0(...)
+
+declare void @foo()
+
+; CHECK: .hidden DW.ref.__gxx_personality_v0
+; CHECK: .weak DW.ref.__gxx_personality_v0
+; CHECK: .section .data.DW.ref.__gxx_personality_v0,"aGw",@progbits,DW.ref.__gxx_personality_v0,comdat
+; CHECK: .align 2
+; CHECK: .type DW.ref.__gxx_personality_v0,@object
+; CHECK: .size DW.ref.__gxx_personality_v0, 4
+; CHECK: DW.ref.__gxx_personality_v0:
+; CHECK: .4byte __gxx_personality_v0
diff --git a/test/CodeGen/Mips/fcmp.ll b/test/CodeGen/Mips/fcmp.ll
new file mode 100644
index 0000000..b775983
--- /dev/null
+++ b/test/CodeGen/Mips/fcmp.ll
@@ -0,0 +1,783 @@
+; RUN: llc < %s -march=mipsel -mcpu=mips32 | FileCheck %s -check-prefix=ALL -check-prefix=32-C
+; RUN: llc < %s -march=mipsel -mcpu=mips32r2 | FileCheck %s -check-prefix=ALL -check-prefix=32-C
+; RUN: llc < %s -march=mipsel -mcpu=mips32r6 | FileCheck %s -check-prefix=ALL -check-prefix=32-CMP
+; RUN: llc < %s -march=mips64el -mcpu=mips4 | FileCheck %s -check-prefix=ALL -check-prefix=64-C
+; RUN: llc < %s -march=mips64el -mcpu=mips64 | FileCheck %s -check-prefix=ALL -check-prefix=64-C
+; RUN: llc < %s -march=mips64el -mcpu=mips64r2 | FileCheck %s -check-prefix=ALL -check-prefix=64-C
+; RUN: llc < %s -march=mips64el -mcpu=mips64r6 | FileCheck %s -check-prefix=ALL -check-prefix=64-CMP
+
+define i32 @false_f32(float %a, float %b) nounwind {
+; ALL-LABEL: false_f32:
+; ALL: addiu $2, $zero, 0
+
+ %1 = fcmp false float %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @oeq_f32(float %a, float %b) nounwind {
+; ALL-LABEL: oeq_f32:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.eq.s $f12, $f14
+; 32-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.eq.s $f12, $f13
+; 64-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.eq.s $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.eq.s $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp oeq float %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @ogt_f32(float %a, float %b) nounwind {
+; ALL-LABEL: ogt_f32:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.ule.s $f12, $f14
+; 32-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.ule.s $f12, $f13
+; 64-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.lt.s $[[T0:f[0-9]+]], $f14, $f12
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.lt.s $[[T0:f[0-9]+]], $f13, $f12
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp ogt float %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @oge_f32(float %a, float %b) nounwind {
+; ALL-LABEL: oge_f32:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.ult.s $f12, $f14
+; 32-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.ult.s $f12, $f13
+; 64-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.le.s $[[T0:f[0-9]+]], $f14, $f12
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.le.s $[[T0:f[0-9]+]], $f13, $f12
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp oge float %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @olt_f32(float %a, float %b) nounwind {
+; ALL-LABEL: olt_f32:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.olt.s $f12, $f14
+; 32-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.olt.s $f12, $f13
+; 64-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.lt.s $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.lt.s $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp olt float %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @ole_f32(float %a, float %b) nounwind {
+; ALL-LABEL: ole_f32:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.ole.s $f12, $f14
+; 32-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.ole.s $f12, $f13
+; 64-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.le.s $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.le.s $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp ole float %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @one_f32(float %a, float %b) nounwind {
+; ALL-LABEL: one_f32:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.ueq.s $f12, $f14
+; 32-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.ueq.s $f12, $f13
+; 64-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.ueq.s $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: not $[[T2:[0-9]+]], $[[T1]]
+; 32-CMP-DAG: andi $2, $[[T2]], 1
+
+; 64-CMP-DAG: cmp.ueq.s $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: not $[[T2:[0-9]+]], $[[T1]]
+; 64-CMP-DAG: andi $2, $[[T2]], 1
+
+ %1 = fcmp one float %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @ord_f32(float %a, float %b) nounwind {
+; ALL-LABEL: ord_f32:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.un.s $f12, $f14
+; 32-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.un.s $f12, $f13
+; 64-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.un.s $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: not $[[T2:[0-9]+]], $[[T1]]
+; 32-CMP-DAG: andi $2, $[[T2]], 1
+
+; 64-CMP-DAG: cmp.un.s $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: not $[[T2:[0-9]+]], $[[T1]]
+; 64-CMP-DAG: andi $2, $[[T2]], 1
+
+ %1 = fcmp ord float %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @ueq_f32(float %a, float %b) nounwind {
+; ALL-LABEL: ueq_f32:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.ueq.s $f12, $f14
+; 32-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.ueq.s $f12, $f13
+; 64-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.ueq.s $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.ueq.s $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp ueq float %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @ugt_f32(float %a, float %b) nounwind {
+; ALL-LABEL: ugt_f32:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.ole.s $f12, $f14
+; 32-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.ole.s $f12, $f13
+; 64-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.ult.s $[[T0:f[0-9]+]], $f14, $f12
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.ult.s $[[T0:f[0-9]+]], $f13, $f12
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp ugt float %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @uge_f32(float %a, float %b) nounwind {
+; ALL-LABEL: uge_f32:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.olt.s $f12, $f14
+; 32-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.olt.s $f12, $f13
+; 64-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.ule.s $[[T0:f[0-9]+]], $f14, $f12
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.ule.s $[[T0:f[0-9]+]], $f13, $f12
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp uge float %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @ult_f32(float %a, float %b) nounwind {
+; ALL-LABEL: ult_f32:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.ult.s $f12, $f14
+; 32-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.ult.s $f12, $f13
+; 64-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.ult.s $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.ult.s $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp ult float %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @ule_f32(float %a, float %b) nounwind {
+; ALL-LABEL: ule_f32:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.ule.s $f12, $f14
+; 32-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.ule.s $f12, $f13
+; 64-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.ule.s $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.ule.s $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp ule float %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @une_f32(float %a, float %b) nounwind {
+; ALL-LABEL: une_f32:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.eq.s $f12, $f14
+; 32-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.eq.s $f12, $f13
+; 64-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.eq.s $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: not $[[T2:[0-9]+]], $[[T1]]
+; 32-CMP-DAG: andi $2, $[[T2]], 1
+
+; 64-CMP-DAG: cmp.eq.s $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: not $[[T2:[0-9]+]], $[[T1]]
+; 64-CMP-DAG: andi $2, $[[T2]], 1
+
+ %1 = fcmp une float %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @uno_f32(float %a, float %b) nounwind {
+; ALL-LABEL: uno_f32:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.un.s $f12, $f14
+; 32-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.un.s $f12, $f13
+; 64-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.un.s $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.un.s $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp uno float %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @true_f32(float %a, float %b) nounwind {
+; ALL-LABEL: true_f32:
+; ALL: addiu $2, $zero, 1
+
+ %1 = fcmp true float %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @false_f64(double %a, double %b) nounwind {
+; ALL-LABEL: false_f64:
+; ALL: addiu $2, $zero, 0
+
+ %1 = fcmp false double %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @oeq_f64(double %a, double %b) nounwind {
+; ALL-LABEL: oeq_f64:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.eq.d $f12, $f14
+; 32-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.eq.d $f12, $f13
+; 64-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.eq.d $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.eq.d $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp oeq double %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @ogt_f64(double %a, double %b) nounwind {
+; ALL-LABEL: ogt_f64:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.ule.d $f12, $f14
+; 32-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.ule.d $f12, $f13
+; 64-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.lt.d $[[T0:f[0-9]+]], $f14, $f12
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.lt.d $[[T0:f[0-9]+]], $f13, $f12
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp ogt double %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @oge_f64(double %a, double %b) nounwind {
+; ALL-LABEL: oge_f64:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.ult.d $f12, $f14
+; 32-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.ult.d $f12, $f13
+; 64-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.le.d $[[T0:f[0-9]+]], $f14, $f12
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.le.d $[[T0:f[0-9]+]], $f13, $f12
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp oge double %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @olt_f64(double %a, double %b) nounwind {
+; ALL-LABEL: olt_f64:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.olt.d $f12, $f14
+; 32-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.olt.d $f12, $f13
+; 64-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.lt.d $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.lt.d $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp olt double %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @ole_f64(double %a, double %b) nounwind {
+; ALL-LABEL: ole_f64:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.ole.d $f12, $f14
+; 32-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.ole.d $f12, $f13
+; 64-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.le.d $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.le.d $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp ole double %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @one_f64(double %a, double %b) nounwind {
+; ALL-LABEL: one_f64:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.ueq.d $f12, $f14
+; 32-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.ueq.d $f12, $f13
+; 64-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.ueq.d $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: not $[[T2:[0-9]+]], $[[T1]]
+; 32-CMP-DAG: andi $2, $[[T2]], 1
+
+; 64-CMP-DAG: cmp.ueq.d $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: not $[[T2:[0-9]+]], $[[T1]]
+; 64-CMP-DAG: andi $2, $[[T2]], 1
+
+ %1 = fcmp one double %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @ord_f64(double %a, double %b) nounwind {
+; ALL-LABEL: ord_f64:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.un.d $f12, $f14
+; 32-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.un.d $f12, $f13
+; 64-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.un.d $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: not $[[T2:[0-9]+]], $[[T1]]
+; 32-CMP-DAG: andi $2, $[[T2]], 1
+
+; 64-CMP-DAG: cmp.un.d $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: not $[[T2:[0-9]+]], $[[T1]]
+; 64-CMP-DAG: andi $2, $[[T2]], 1
+
+ %1 = fcmp ord double %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @ueq_f64(double %a, double %b) nounwind {
+; ALL-LABEL: ueq_f64:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.ueq.d $f12, $f14
+; 32-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.ueq.d $f12, $f13
+; 64-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.ueq.d $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.ueq.d $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp ueq double %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @ugt_f64(double %a, double %b) nounwind {
+; ALL-LABEL: ugt_f64:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.ole.d $f12, $f14
+; 32-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.ole.d $f12, $f13
+; 64-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.ult.d $[[T0:f[0-9]+]], $f14, $f12
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.ult.d $[[T0:f[0-9]+]], $f13, $f12
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp ugt double %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @uge_f64(double %a, double %b) nounwind {
+; ALL-LABEL: uge_f64:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.olt.d $f12, $f14
+; 32-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.olt.d $f12, $f13
+; 64-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.ule.d $[[T0:f[0-9]+]], $f14, $f12
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.ule.d $[[T0:f[0-9]+]], $f13, $f12
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp uge double %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @ult_f64(double %a, double %b) nounwind {
+; ALL-LABEL: ult_f64:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.ult.d $f12, $f14
+; 32-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.ult.d $f12, $f13
+; 64-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.ult.d $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.ult.d $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp ult double %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @ule_f64(double %a, double %b) nounwind {
+; ALL-LABEL: ule_f64:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.ule.d $f12, $f14
+; 32-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.ule.d $f12, $f13
+; 64-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.ule.d $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.ule.d $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp ule double %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @une_f64(double %a, double %b) nounwind {
+; ALL-LABEL: une_f64:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.eq.d $f12, $f14
+; 32-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.eq.d $f12, $f13
+; 64-C-DAG: movf $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.eq.d $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: not $[[T2:[0-9]+]], $[[T1]]
+; 32-CMP-DAG: andi $2, $[[T2]], 1
+
+; 64-CMP-DAG: cmp.eq.d $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: not $[[T2:[0-9]+]], $[[T1]]
+; 64-CMP-DAG: andi $2, $[[T2]], 1
+
+ %1 = fcmp une double %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @uno_f64(double %a, double %b) nounwind {
+; ALL-LABEL: uno_f64:
+
+; 32-C-DAG: addiu $[[T0:2]], $zero, 0
+; 32-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 32-C-DAG: c.un.d $f12, $f14
+; 32-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 64-C-DAG: addiu $[[T0:2]], $zero, 0
+; 64-C-DAG: addiu $[[T1:[0-9]+]], $zero, 1
+; 64-C-DAG: c.un.d $f12, $f13
+; 64-C-DAG: movt $[[T0]], $1, $fcc0
+
+; 32-CMP-DAG: cmp.un.d $[[T0:f[0-9]+]], $f12, $f14
+; 32-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 32-CMP-DAG: andi $2, $[[T1]], 1
+
+; 64-CMP-DAG: cmp.un.d $[[T0:f[0-9]+]], $f12, $f13
+; 64-CMP-DAG: mfc1 $[[T1:[0-9]+]], $[[T0]]
+; 64-CMP-DAG: andi $2, $[[T1]], 1
+
+ %1 = fcmp uno double %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
+
+define i32 @true_f64(double %a, double %b) nounwind {
+; ALL-LABEL: true_f64:
+; ALL: addiu $2, $zero, 1
+
+ %1 = fcmp true double %a, %b
+ %2 = zext i1 %1 to i32
+ ret i32 %2
+}
diff --git a/test/CodeGen/Mips/fcopysign.ll b/test/CodeGen/Mips/fcopysign.ll
index 44c4117..3a9d9c7 100644
--- a/test/CodeGen/Mips/fcopysign.ll
+++ b/test/CodeGen/Mips/fcopysign.ll
@@ -17,7 +17,7 @@ entry:
; 32R2: ext $[[EXT:[0-9]+]], ${{[0-9]+}}, 31, 1
; 32R2: ins $[[INS:[0-9]+]], $[[EXT]], 31, 1
-; 32R2: mtc1 $[[INS]], $f1
+; 32R2: mthc1 $[[INS]], $f0
; 64: daddiu $[[T0:[0-9]+]], $zero, 1
; 64: dsll $[[MSK1:[0-9]+]], $[[T0]], 63
diff --git a/test/CodeGen/Mips/fmadd1.ll b/test/CodeGen/Mips/fmadd1.ll
index a9a8e21..271631e 100644
--- a/test/CodeGen/Mips/fmadd1.ll
+++ b/test/CodeGen/Mips/fmadd1.ll
@@ -5,15 +5,54 @@
; IEEE 754 (1985) and IEEE 754 (2008). These instructions are therefore only
; available when -enable-no-nans-fp-math is given.
-; RUN: llc < %s -march=mipsel -mcpu=mips32r2 -enable-no-nans-fp-math | FileCheck %s -check-prefix=32R2 -check-prefix=CHECK
-; RUN: llc < %s -march=mips64el -mcpu=mips64r2 -mattr=n64 -enable-no-nans-fp-math | FileCheck %s -check-prefix=64R2 -check-prefix=CHECK
-; RUN: llc < %s -march=mipsel -mcpu=mips32r2 | FileCheck %s -check-prefix=32R2NAN -check-prefix=CHECK
-; RUN: llc < %s -march=mips64el -mcpu=mips64r2 -mattr=n64 | FileCheck %s -check-prefix=64R2NAN -check-prefix=CHECK
+; RUN: llc < %s -march=mipsel -mcpu=mips32 -enable-no-nans-fp-math | FileCheck %s -check-prefix=ALL -check-prefix=32 -check-prefix=32-NONAN
+; RUN: llc < %s -march=mipsel -mcpu=mips32r2 -enable-no-nans-fp-math | FileCheck %s -check-prefix=ALL -check-prefix=32R2 -check-prefix=32R2-NONAN
+; RUN: llc < %s -march=mipsel -mcpu=mips32r6 -enable-no-nans-fp-math | FileCheck %s -check-prefix=ALL -check-prefix=32R6 -check-prefix=32R6-NONAN
+; RUN: llc < %s -march=mips64el -mcpu=mips64 -mattr=n64 -enable-no-nans-fp-math | FileCheck %s -check-prefix=ALL -check-prefix=64 -check-prefix=64-NONAN
+; RUN: llc < %s -march=mips64el -mcpu=mips64r2 -mattr=n64 -enable-no-nans-fp-math | FileCheck %s -check-prefix=ALL -check-prefix=64R2 -check-prefix=64R2-NONAN
+; RUN: llc < %s -march=mips64el -mcpu=mips64r6 -mattr=n64 -enable-no-nans-fp-math | FileCheck %s -check-prefix=ALL -check-prefix=64R6 -check-prefix=64R6-NONAN
+; RUN: llc < %s -march=mipsel -mcpu=mips32 | FileCheck %s -check-prefix=ALL -check-prefix=32 -check-prefix=32-NAN
+; RUN: llc < %s -march=mipsel -mcpu=mips32r2 | FileCheck %s -check-prefix=ALL -check-prefix=32R2 -check-prefix=32R2-NAN
+; RUN: llc < %s -march=mipsel -mcpu=mips32r6 | FileCheck %s -check-prefix=ALL -check-prefix=32R6 -check-prefix=32R6-NAN
+; RUN: llc < %s -march=mips64el -mcpu=mips64 -mattr=n64 | FileCheck %s -check-prefix=ALL -check-prefix=64 -check-prefix=64-NAN
+; RUN: llc < %s -march=mips64el -mcpu=mips64r2 -mattr=n64 | FileCheck %s -check-prefix=ALL -check-prefix=64R2 -check-prefix=64R2-NAN
+; RUN: llc < %s -march=mips64el -mcpu=mips64r6 -mattr=n64 | FileCheck %s -check-prefix=ALL -check-prefix=64R6 -check-prefix=64R6-NAN
define float @FOO0float(float %a, float %b, float %c) nounwind readnone {
entry:
-; CHECK-LABEL: FOO0float:
-; CHECK: madd.s
+; ALL-LABEL: FOO0float:
+
+; 32-DAG: mtc1 $6, $[[T0:f[0-9]+]]
+; 32-DAG: mul.s $[[T1:f[0-9]+]], $f12, $f14
+; 32-DAG: add.s $[[T2:f[0-9]+]], $[[T1]], $[[T0]]
+; 32-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32-DAG: add.s $f0, $[[T1]], $[[T2]]
+
+; 32R2: mtc1 $6, $[[T0:f[0-9]+]]
+; 32R2: madd.s $[[T1:f[0-9]+]], $[[T0]], $f12, $f14
+; 32R2: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32R2: add.s $f0, $[[T1]], $[[T2]]
+
+; 32R6-DAG: mtc1 $6, $[[T0:f[0-9]+]]
+; 32R6-DAG: mul.s $[[T1:f[0-9]+]], $f12, $f14
+; 32R6-DAG: add.s $[[T2:f[0-9]+]], $[[T1]], $[[T0]]
+; 32R6-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32R6-DAG: add.s $f0, $[[T1]], $[[T2]]
+
+; 64-DAG: mul.s $[[T1:f[0-9]+]], $f12, $f13
+; 64-DAG: add.s $[[T2:f[0-9]+]], $[[T1]], $f14
+; 64-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 64-DAG: add.s $f0, $[[T1]], $[[T2]]
+
+; 64R2: madd.s $[[T0:f[0-9]+]], $f14, $f12, $f13
+; 64R2: mtc1 $zero, $[[T1:f[0-9]+]]
+; 64R2: add.s $f0, $[[T0]], $[[T1]]
+
+; 64R6-DAG: mul.s $[[T0:f[0-9]+]], $f12, $f13
+; 64R6-DAG: add.s $[[T1:f[0-9]+]], $[[T0]], $f14
+; 64R6-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 64R6-DAG: add.s $f0, $[[T1]], $[[T2]]
+
%mul = fmul float %a, %b
%add = fadd float %mul, %c
%add1 = fadd float %add, 0.000000e+00
@@ -22,8 +61,39 @@ entry:
define float @FOO1float(float %a, float %b, float %c) nounwind readnone {
entry:
-; CHECK-LABEL: FOO1float:
-; CHECK: msub.s
+; ALL-LABEL: FOO1float:
+
+; 32-DAG: mtc1 $6, $[[T0:f[0-9]+]]
+; 32-DAG: mul.s $[[T1:f[0-9]+]], $f12, $f14
+; 32-DAG: sub.s $[[T2:f[0-9]+]], $[[T1]], $[[T0]]
+; 32-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32-DAG: add.s $f0, $[[T1]], $[[T2]]
+
+; 32R2: mtc1 $6, $[[T0:f[0-9]+]]
+; 32R2: msub.s $[[T1:f[0-9]+]], $[[T0]], $f12, $f14
+; 32R2: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32R2: add.s $f0, $[[T1]], $[[T2]]
+
+; 32R6-DAG: mtc1 $6, $[[T0:f[0-9]+]]
+; 32R6-DAG: mul.s $[[T1:f[0-9]+]], $f12, $f14
+; 32R6-DAG: sub.s $[[T2:f[0-9]+]], $[[T1]], $[[T0]]
+; 32R6-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32R6-DAG: add.s $f0, $[[T1]], $[[T2]]
+
+; 64-DAG: mul.s $[[T1:f[0-9]+]], $f12, $f13
+; 64-DAG: sub.s $[[T2:f[0-9]+]], $[[T1]], $f14
+; 64-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 64-DAG: add.s $f0, $[[T1]], $[[T2]]
+
+; 64R2: msub.s $[[T0:f[0-9]+]], $f14, $f12, $f13
+; 64R2: mtc1 $zero, $[[T1:f[0-9]+]]
+; 64R2: add.s $f0, $[[T0]], $[[T1]]
+
+; 64R6-DAG: mul.s $[[T0:f[0-9]+]], $f12, $f13
+; 64R6-DAG: sub.s $[[T1:f[0-9]+]], $[[T0]], $f14
+; 64R6-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 64R6-DAG: add.s $f0, $[[T1]], $[[T2]]
+
%mul = fmul float %a, %b
%sub = fsub float %mul, %c
%add = fadd float %sub, 0.000000e+00
@@ -32,11 +102,44 @@ entry:
define float @FOO2float(float %a, float %b, float %c) nounwind readnone {
entry:
-; CHECK-LABEL: FOO2float:
-; 32R2: nmadd.s
-; 64R2: nmadd.s
-; 32R2NAN: madd.s
-; 64R2NAN: madd.s
+; ALL-LABEL: FOO2float:
+
+; 32-DAG: mtc1 $6, $[[T0:f[0-9]+]]
+; 32-DAG: mul.s $[[T1:f[0-9]+]], $f12, $f14
+; 32-DAG: add.s $[[T2:f[0-9]+]], $[[T1]], $[[T0]]
+; 32-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32-DAG: sub.s $f0, $[[T2]], $[[T1]]
+
+; 32R2-NONAN: mtc1 $6, $[[T0:f[0-9]+]]
+; 32R2-NONAN: nmadd.s $f0, $[[T0]], $f12, $f14
+
+; 32R2-NAN: mtc1 $6, $[[T0:f[0-9]+]]
+; 32R2-NAN: madd.s $[[T1:f[0-9]+]], $[[T0]], $f12, $f14
+; 32R2-NAN: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32R2-NAN: sub.s $f0, $[[T2]], $[[T1]]
+
+; 32R6-DAG: mtc1 $6, $[[T0:f[0-9]+]]
+; 32R6-DAG: mul.s $[[T1:f[0-9]+]], $f12, $f14
+; 32R6-DAG: add.s $[[T2:f[0-9]+]], $[[T1]], $[[T0]]
+; 32R6-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32R6-DAG: sub.s $f0, $[[T2]], $[[T1]]
+
+; 64-DAG: mul.s $[[T1:f[0-9]+]], $f12, $f13
+; 64-DAG: add.s $[[T2:f[0-9]+]], $[[T1]], $f14
+; 64-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 64-DAG: sub.s $f0, $[[T2]], $[[T1]]
+
+; 64R2-NONAN: nmadd.s $f0, $f14, $f12, $f13
+
+; 64R2-NAN: madd.s $[[T0:f[0-9]+]], $f14, $f12, $f13
+; 64R2-NAN: mtc1 $zero, $[[T1:f[0-9]+]]
+; 64R2-NAN: sub.s $f0, $[[T1]], $[[T0]]
+
+; 64R6-DAG: mul.s $[[T1:f[0-9]+]], $f12, $f13
+; 64R6-DAG: add.s $[[T2:f[0-9]+]], $[[T1]], $f14
+; 64R6-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 64R6-DAG: sub.s $f0, $[[T2]], $[[T1]]
+
%mul = fmul float %a, %b
%add = fadd float %mul, %c
%sub = fsub float 0.000000e+00, %add
@@ -45,11 +148,36 @@ entry:
define float @FOO3float(float %a, float %b, float %c) nounwind readnone {
entry:
-; CHECK-LABEL: FOO3float:
-; 32R2: nmsub.s
-; 64R2: nmsub.s
-; 32R2NAN: msub.s
-; 64R2NAN: msub.s
+; ALL-LABEL: FOO3float:
+
+; 32-DAG: mtc1 $6, $[[T0:f[0-9]+]]
+; 32-DAG: mul.s $[[T1:f[0-9]+]], $f12, $f14
+; 32-DAG: sub.s $[[T2:f[0-9]+]], $[[T1]], $[[T0]]
+; 32-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32-DAG: sub.s $f0, $[[T2]], $[[T1]]
+
+; 32R2-NONAN: mtc1 $6, $[[T0:f[0-9]+]]
+; 32R2-NONAN: nmsub.s $f0, $[[T0]], $f12, $f14
+
+; 32R2-NAN: mtc1 $6, $[[T0:f[0-9]+]]
+; 32R2-NAN: msub.s $[[T1:f[0-9]+]], $[[T0]], $f12, $f14
+; 32R2-NAN: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32R2-NAN: sub.s $f0, $[[T2]], $[[T1]]
+
+; 64-DAG: mul.s $[[T1:f[0-9]+]], $f12, $f13
+; 64-DAG: sub.s $[[T2:f[0-9]+]], $[[T1]], $f14
+; 64-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 64-DAG: sub.s $f0, $[[T2]], $[[T1]]
+
+; 64R2-NAN: msub.s $[[T0:f[0-9]+]], $f14, $f12, $f13
+; 64R2-NAN: mtc1 $zero, $[[T1:f[0-9]+]]
+; 64R2-NAN: sub.s $f0, $[[T1]], $[[T0]]
+
+; 64R6-DAG: mul.s $[[T1:f[0-9]+]], $f12, $f13
+; 64R6-DAG: sub.s $[[T2:f[0-9]+]], $[[T1]], $f14
+; 64R6-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 64R6-DAG: sub.s $f0, $[[T2]], $[[T1]]
+
%mul = fmul float %a, %b
%sub = fsub float %mul, %c
%sub1 = fsub float 0.000000e+00, %sub
@@ -58,8 +186,40 @@ entry:
define double @FOO10double(double %a, double %b, double %c) nounwind readnone {
entry:
-; CHECK-LABEL: FOO10double:
-; CHECK: madd.d
+; ALL-LABEL: FOO10double:
+
+; 32-DAG: ldc1 $[[T0:f[0-9]+]], 16($sp)
+; 32-DAG: mul.d $[[T1:f[0-9]+]], $f12, $f14
+; 32-DAG: add.d $[[T2:f[0-9]+]], $[[T1]], $[[T0]]
+; 32-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32-DAG: add.d $f0, $[[T1]], $[[T2]]
+
+; 32R2: ldc1 $[[T0:f[0-9]+]], 16($sp)
+; 32R2: madd.d $[[T1:f[0-9]+]], $[[T0]], $f12, $f14
+; 32R2: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32R2: mthc1 $zero, $[[T2]]
+; 32R2: add.d $f0, $[[T1]], $[[T2]]
+
+; 32R6-DAG: ldc1 $[[T0:f[0-9]+]], 16($sp)
+; 32R6-DAG: mul.d $[[T1:f[0-9]+]], $f12, $f14
+; 32R6-DAG: add.d $[[T2:f[0-9]+]], $[[T1]], $[[T0]]
+; 32R6-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32R6-DAG: add.d $f0, $[[T1]], $[[T2]]
+
+; 64-DAG: mul.d $[[T1:f[0-9]+]], $f12, $f13
+; 64-DAG: add.d $[[T2:f[0-9]+]], $[[T1]], $f14
+; 64-DAG: dmtc1 $zero, $[[T2:f[0-9]+]]
+; 64-DAG: add.d $f0, $[[T1]], $[[T2]]
+
+; 64R2: madd.d $[[T0:f[0-9]+]], $f14, $f12, $f13
+; 64R2: mtc1 $zero, $[[T1:f[0-9]+]]
+; 64R2: add.d $f0, $[[T0]], $[[T1]]
+
+; 64R6-DAG: mul.d $[[T1:f[0-9]+]], $f12, $f13
+; 64R6-DAG: add.d $[[T2:f[0-9]+]], $[[T1]], $f14
+; 64R6-DAG: dmtc1 $zero, $[[T2:f[0-9]+]]
+; 64R6-DAG: add.d $f0, $[[T1]], $[[T2]]
+
%mul = fmul double %a, %b
%add = fadd double %mul, %c
%add1 = fadd double %add, 0.000000e+00
@@ -68,8 +228,40 @@ entry:
define double @FOO11double(double %a, double %b, double %c) nounwind readnone {
entry:
-; CHECK-LABEL: FOO11double:
-; CHECK: msub.d
+; ALL-LABEL: FOO11double:
+
+; 32-DAG: ldc1 $[[T0:f[0-9]+]], 16($sp)
+; 32-DAG: mul.d $[[T1:f[0-9]+]], $f12, $f14
+; 32-DAG: sub.d $[[T2:f[0-9]+]], $[[T1]], $[[T0]]
+; 32-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32-DAG: add.d $f0, $[[T1]], $[[T2]]
+
+; 32R2: ldc1 $[[T0:f[0-9]+]], 16($sp)
+; 32R2: msub.d $[[T1:f[0-9]+]], $[[T0]], $f12, $f14
+; 32R2: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32R2: mthc1 $zero, $[[T2]]
+; 32R2: add.d $f0, $[[T1]], $[[T2]]
+
+; 32R6-DAG: ldc1 $[[T0:f[0-9]+]], 16($sp)
+; 32R6-DAG: mul.d $[[T1:f[0-9]+]], $f12, $f14
+; 32R6-DAG: sub.d $[[T2:f[0-9]+]], $[[T1]], $[[T0]]
+; 32R6-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32R6-DAG: add.d $f0, $[[T1]], $[[T2]]
+
+; 64-DAG: mul.d $[[T1:f[0-9]+]], $f12, $f13
+; 64-DAG: sub.d $[[T2:f[0-9]+]], $[[T1]], $f14
+; 64-DAG: dmtc1 $zero, $[[T2:f[0-9]+]]
+; 64-DAG: add.d $f0, $[[T1]], $[[T2]]
+
+; 64R2: msub.d $[[T0:f[0-9]+]], $f14, $f12, $f13
+; 64R2: mtc1 $zero, $[[T1:f[0-9]+]]
+; 64R2: add.d $f0, $[[T0]], $[[T1]]
+
+; 64R6-DAG: mul.d $[[T1:f[0-9]+]], $f12, $f13
+; 64R6-DAG: sub.d $[[T2:f[0-9]+]], $[[T1]], $f14
+; 64R6-DAG: dmtc1 $zero, $[[T2:f[0-9]+]]
+; 64R6-DAG: add.d $f0, $[[T1]], $[[T2]]
+
%mul = fmul double %a, %b
%sub = fsub double %mul, %c
%add = fadd double %sub, 0.000000e+00
@@ -78,11 +270,45 @@ entry:
define double @FOO12double(double %a, double %b, double %c) nounwind readnone {
entry:
-; CHECK-LABEL: FOO12double:
-; 32R2: nmadd.d
-; 64R2: nmadd.d
-; 32R2NAN: madd.d
-; 64R2NAN: madd.d
+; ALL-LABEL: FOO12double:
+
+; 32-DAG: ldc1 $[[T0:f[0-9]+]], 16($sp)
+; 32-DAG: mul.d $[[T1:f[0-9]+]], $f12, $f14
+; 32-DAG: add.d $[[T2:f[0-9]+]], $[[T1]], $[[T0]]
+; 32-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32-DAG: sub.d $f0, $[[T2]], $[[T1]]
+
+; 32R2-NONAN: ldc1 $[[T0:f[0-9]+]], 16($sp)
+; 32R2-NONAN: nmadd.d $f0, $[[T0]], $f12, $f14
+
+; 32R2-NAN: ldc1 $[[T0:f[0-9]+]], 16($sp)
+; 32R2-NAN: madd.d $[[T1:f[0-9]+]], $[[T0]], $f12, $f14
+; 32R2-NAN: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32R2-NAN: mthc1 $zero, $[[T2]]
+; 32R2-NAN: sub.d $f0, $[[T2]], $[[T1]]
+
+; 32R6-DAG: ldc1 $[[T0:f[0-9]+]], 16($sp)
+; 32R6-DAG: mul.d $[[T1:f[0-9]+]], $f12, $f14
+; 32R6-DAG: add.d $[[T2:f[0-9]+]], $[[T1]], $[[T0]]
+; 32R6-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32R6-DAG: sub.d $f0, $[[T2]], $[[T1]]
+
+; 64-DAG: mul.d $[[T1:f[0-9]+]], $f12, $f13
+; 64-DAG: add.d $[[T2:f[0-9]+]], $[[T1]], $f14
+; 64-DAG: dmtc1 $zero, $[[T2:f[0-9]+]]
+; 64-DAG: sub.d $f0, $[[T2]], $[[T1]]
+
+; 64R2-NONAN: nmadd.d $f0, $f14, $f12, $f13
+
+; 64R2-NAN: madd.d $[[T0:f[0-9]+]], $f14, $f12, $f13
+; 64R2-NAN: mtc1 $zero, $[[T1:f[0-9]+]]
+; 64R2-NAN: sub.d $f0, $[[T1]], $[[T0]]
+
+; 64R6-DAG: mul.d $[[T1:f[0-9]+]], $f12, $f13
+; 64R6-DAG: add.d $[[T2:f[0-9]+]], $[[T1]], $f14
+; 64R6-DAG: dmtc1 $zero, $[[T2:f[0-9]+]]
+; 64R6-DAG: sub.d $f0, $[[T2]], $[[T1]]
+
%mul = fmul double %a, %b
%add = fadd double %mul, %c
%sub = fsub double 0.000000e+00, %add
@@ -91,11 +317,45 @@ entry:
define double @FOO13double(double %a, double %b, double %c) nounwind readnone {
entry:
-; CHECK-LABEL: FOO13double:
-; 32R2: nmsub.d
-; 64R2: nmsub.d
-; 32R2NAN: msub.d
-; 64R2NAN: msub.d
+; ALL-LABEL: FOO13double:
+
+; 32-DAG: ldc1 $[[T0:f[0-9]+]], 16($sp)
+; 32-DAG: mul.d $[[T1:f[0-9]+]], $f12, $f14
+; 32-DAG: sub.d $[[T2:f[0-9]+]], $[[T1]], $[[T0]]
+; 32-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32-DAG: sub.d $f0, $[[T2]], $[[T1]]
+
+; 32R2-NONAN: ldc1 $[[T0:f[0-9]+]], 16($sp)
+; 32R2-NONAN: nmsub.d $f0, $[[T0]], $f12, $f14
+
+; 32R2-NAN: ldc1 $[[T0:f[0-9]+]], 16($sp)
+; 32R2-NAN: msub.d $[[T1:f[0-9]+]], $[[T0]], $f12, $f14
+; 32R2-NAN: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32R2-NAN: mthc1 $zero, $[[T2]]
+; 32R2-NAN: sub.d $f0, $[[T2]], $[[T1]]
+
+; 32R6-DAG: ldc1 $[[T0:f[0-9]+]], 16($sp)
+; 32R6-DAG: mul.d $[[T1:f[0-9]+]], $f12, $f14
+; 32R6-DAG: sub.d $[[T2:f[0-9]+]], $[[T1]], $[[T0]]
+; 32R6-DAG: mtc1 $zero, $[[T2:f[0-9]+]]
+; 32R6-DAG: sub.d $f0, $[[T2]], $[[T1]]
+
+; 64-DAG: mul.d $[[T1:f[0-9]+]], $f12, $f13
+; 64-DAG: sub.d $[[T2:f[0-9]+]], $[[T1]], $f14
+; 64-DAG: dmtc1 $zero, $[[T2:f[0-9]+]]
+; 64-DAG: sub.d $f0, $[[T2]], $[[T1]]
+
+; 64R2-NONAN: nmsub.d $f0, $f14, $f12, $f13
+
+; 64R2-NAN: msub.d $[[T0:f[0-9]+]], $f14, $f12, $f13
+; 64R2-NAN: mtc1 $zero, $[[T1:f[0-9]+]]
+; 64R2-NAN: sub.d $f0, $[[T1]], $[[T0]]
+
+; 64R6-DAG: mul.d $[[T1:f[0-9]+]], $f12, $f13
+; 64R6-DAG: sub.d $[[T2:f[0-9]+]], $[[T1]], $f14
+; 64R6-DAG: dmtc1 $zero, $[[T2:f[0-9]+]]
+; 64R6-DAG: sub.d $f0, $[[T2]], $[[T1]]
+
%mul = fmul double %a, %b
%sub = fsub double %mul, %c
%sub1 = fsub double 0.000000e+00, %sub
diff --git a/test/CodeGen/Mips/fp-indexed-ls.ll b/test/CodeGen/Mips/fp-indexed-ls.ll
index d8c37e7..787e131 100644
--- a/test/CodeGen/Mips/fp-indexed-ls.ll
+++ b/test/CodeGen/Mips/fp-indexed-ls.ll
@@ -1,6 +1,13 @@
-; RUN: llc -march=mipsel -mcpu=mips32r2 < %s | FileCheck %s
-; RUN: llc -mtriple=mipsel-none-nacl-gnu -mcpu=mips32r2 < %s \
-; RUN: | FileCheck %s -check-prefix=CHECK-NACL
+; RUN: llc -march=mipsel -mcpu=mips32 < %s | FileCheck %s -check-prefix=ALL -check-prefix=MIPS32R1
+; RUN: llc -march=mipsel -mcpu=mips32r2 < %s | FileCheck %s -check-prefix=ALL -check-prefix=MIPS32R2
+; RUN: llc -march=mipsel -mcpu=mips32r6 < %s | FileCheck %s -check-prefix=ALL -check-prefix=MIPS32R6
+; RUN: llc -march=mips64el -mcpu=mips4 -mattr=n64 < %s | FileCheck %s -check-prefix=ALL -check-prefix=MIPS4
+; RUN: llc -march=mips64el -mcpu=mips64 -mattr=n64 < %s | FileCheck %s -check-prefix=ALL -check-prefix=MIPS4
+; RUN: llc -march=mips64el -mcpu=mips64r2 -mattr=n64 < %s | FileCheck %s -check-prefix=ALL -check-prefix=MIPS4
+; RUN: llc -march=mips64el -mcpu=mips64r6 -mattr=n64 < %s | FileCheck %s -check-prefix=ALL -check-prefix=MIPS64R6
+
+; Check that [ls][dwu]xc1 are not emitted for nacl.
+; RUN: llc -mtriple=mipsel-none-nacl-gnu -mcpu=mips32r2 < %s | FileCheck %s -check-prefix=CHECK-NACL
%struct.S = type <{ [4 x float] }>
%struct.S2 = type <{ [4 x double] }>
@@ -14,8 +21,30 @@
define float @foo0(float* nocapture %b, i32 %o) nounwind readonly {
entry:
-; CHECK: lwxc1
+; ALL-LABEL: foo0:
+
+; MIPS32R1: sll $[[T1:[0-9]+]], $5, 2
+; MIPS32R1: addu $[[T3:[0-9]+]], $4, $[[T1]]
+; MIPS32R1: lwc1 $f0, 0($[[T3]])
+
+; MIPS32R2: sll $[[T1:[0-9]+]], $5, 2
+; MIPS32R2: lwxc1 $f0, $[[T1]]($4)
+
+; MIPS32R6: sll $[[T1:[0-9]+]], $5, 2
+; MIPS32R6: addu $[[T3:[0-9]+]], $4, $[[T1]]
+; MIPS32R6: lwc1 $f0, 0($[[T3]])
+
+; MIPS4: sll $[[T0:[0-9]+]], $5, 0
+; MIPS4: dsll $[[T1:[0-9]+]], $[[T0]], 2
+; MIPS4: lwxc1 $f0, $[[T1]]($4)
+
+; MIPS64R6: sll $[[T0:[0-9]+]], $5, 0
+; MIPS64R6: dsll $[[T1:[0-9]+]], $[[T0]], 2
+; MIPS64R6: daddu $[[T3:[0-9]+]], $4, $[[T1]]
+; MIPS64R6: lwc1 $f0, 0($[[T3]])
+
; CHECK-NACL-NOT: lwxc1
+
%arrayidx = getelementptr inbounds float* %b, i32 %o
%0 = load float* %arrayidx, align 4
ret float %0
@@ -23,8 +52,30 @@ entry:
define double @foo1(double* nocapture %b, i32 %o) nounwind readonly {
entry:
-; CHECK: ldxc1
+; ALL-LABEL: foo1:
+
+; MIPS32R1: sll $[[T1:[0-9]+]], $5, 3
+; MIPS32R1: addu $[[T3:[0-9]+]], $4, $[[T1]]
+; MIPS32R1: ldc1 $f0, 0($[[T3]])
+
+; MIPS32R2: sll $[[T1:[0-9]+]], $5, 3
+; MIPS32R2: ldxc1 $f0, $[[T1]]($4)
+
+; MIPS32R6: sll $[[T1:[0-9]+]], $5, 3
+; MIPS32R6: addu $[[T3:[0-9]+]], $4, $[[T1]]
+; MIPS32R6: ldc1 $f0, 0($[[T3]])
+
+; MIPS4: sll $[[T0:[0-9]+]], $5, 0
+; MIPS4: dsll $[[T1:[0-9]+]], $[[T0]], 3
+; MIPS4: ldxc1 $f0, $[[T1]]($4)
+
+; MIPS64R6: sll $[[T0:[0-9]+]], $5, 0
+; MIPS64R6: dsll $[[T1:[0-9]+]], $[[T0]], 3
+; MIPS64R6: daddu $[[T3:[0-9]+]], $4, $[[T1]]
+; MIPS64R6: ldc1 $f0, 0($[[T3]])
+
; CHECK-NACL-NOT: ldxc1
+
%arrayidx = getelementptr inbounds double* %b, i32 %o
%0 = load double* %arrayidx, align 8
ret double %0
@@ -32,7 +83,23 @@ entry:
define float @foo2(i32 %b, i32 %c) nounwind readonly {
entry:
-; CHECK-NOT: luxc1
+; ALL-LABEL: foo2:
+
+; luxc1 did not exist in MIPS32r1
+; MIPS32R1-NOT: luxc1
+
+; luxc1 is a misnomer since it aligns the given pointer downwards and performs
+; an aligned load. We mustn't use it to handle unaligned loads.
+; MIPS32R2-NOT: luxc1
+
+; luxc1 was removed in MIPS32r6
+; MIPS32R6-NOT: luxc1
+
+; MIPS4-NOT: luxc1
+
+; luxc1 was removed in MIPS64r6
+; MIPS64R6-NOT: luxc1
+
%arrayidx1 = getelementptr inbounds [4 x %struct.S]* @s, i32 0, i32 %b, i32 0, i32 %c
%0 = load float* %arrayidx1, align 1
ret float %0
@@ -40,8 +107,28 @@ entry:
define void @foo3(float* nocapture %b, i32 %o) nounwind {
entry:
-; CHECK: swxc1
+; ALL-LABEL: foo3:
+
+; MIPS32R1-DAG: lwc1 $[[T0:f0]], 0(${{[0-9]+}})
+; MIPS32R1-DAG: addu $[[T1:[0-9]+]], $4, ${{[0-9]+}}
+; MIPS32R1-DAG: swc1 $[[T0]], 0($[[T1]])
+
+; MIPS32R2: lwc1 $[[T0:f0]], 0(${{[0-9]+}})
+; MIPS32R2: swxc1 $[[T0]], ${{[0-9]+}}($4)
+
+; MIPS32R6-DAG: lwc1 $[[T0:f0]], 0(${{[0-9]+}})
+; MIPS32R6-DAG: addu $[[T1:[0-9]+]], $4, ${{[0-9]+}}
+; MIPS32R6-DAG: swc1 $[[T0]], 0($[[T1]])
+
+; MIPS4: lwc1 $[[T0:f0]], 0(${{[0-9]+}})
+; MIPS4: swxc1 $[[T0]], ${{[0-9]+}}($4)
+
+; MIPS64R6-DAG: lwc1 $[[T0:f0]], 0(${{[0-9]+}})
+; MIPS64R6-DAG: daddu $[[T1:[0-9]+]], $4, ${{[0-9]+}}
+; MIPS64R6-DAG: swc1 $[[T0]], 0($[[T1]])
+
; CHECK-NACL-NOT: swxc1
+
%0 = load float* @gf, align 4
%arrayidx = getelementptr inbounds float* %b, i32 %o
store float %0, float* %arrayidx, align 4
@@ -50,8 +137,28 @@ entry:
define void @foo4(double* nocapture %b, i32 %o) nounwind {
entry:
-; CHECK: sdxc1
+; ALL-LABEL: foo4:
+
+; MIPS32R1-DAG: ldc1 $[[T0:f0]], 0(${{[0-9]+}})
+; MIPS32R1-DAG: addu $[[T1:[0-9]+]], $4, ${{[0-9]+}}
+; MIPS32R1-DAG: sdc1 $[[T0]], 0($[[T1]])
+
+; MIPS32R2: ldc1 $[[T0:f0]], 0(${{[0-9]+}})
+; MIPS32R2: sdxc1 $[[T0]], ${{[0-9]+}}($4)
+
+; MIPS32R6-DAG: ldc1 $[[T0:f0]], 0(${{[0-9]+}})
+; MIPS32R6-DAG: addu $[[T1:[0-9]+]], $4, ${{[0-9]+}}
+; MIPS32R6-DAG: sdc1 $[[T0]], 0($[[T1]])
+
+; MIPS4: ldc1 $[[T0:f0]], 0(${{[0-9]+}})
+; MIPS4: sdxc1 $[[T0]], ${{[0-9]+}}($4)
+
+; MIPS64R6-DAG: ldc1 $[[T0:f0]], 0(${{[0-9]+}})
+; MIPS64R6-DAG: daddu $[[T1:[0-9]+]], $4, ${{[0-9]+}}
+; MIPS64R6-DAG: sdc1 $[[T0]], 0($[[T1]])
+
; CHECK-NACL-NOT: sdxc1
+
%0 = load double* @gd, align 8
%arrayidx = getelementptr inbounds double* %b, i32 %o
store double %0, double* %arrayidx, align 8
@@ -60,7 +167,18 @@ entry:
define void @foo5(i32 %b, i32 %c) nounwind {
entry:
-; CHECK-NOT: suxc1
+; ALL-LABEL: foo5:
+
+; MIPS32R1-NOT: suxc1
+
+; MIPS32R2-NOT: suxc1
+
+; MIPS32R6-NOT: suxc1
+
+; MIPS4-NOT: suxc1
+
+; MIPS64R6-NOT: suxc1
+
%0 = load float* @gf, align 4
%arrayidx1 = getelementptr inbounds [4 x %struct.S]* @s, i32 0, i32 %b, i32 0, i32 %c
store float %0, float* %arrayidx1, align 1
@@ -69,8 +187,18 @@ entry:
define double @foo6(i32 %b, i32 %c) nounwind readonly {
entry:
-; CHECK: foo6
-; CHECK-NOT: luxc1
+; ALL-LABEL: foo6:
+
+; MIPS32R1-NOT: luxc1
+
+; MIPS32R2-NOT: luxc1
+
+; MIPS32R6-NOT: luxc1
+
+; MIPS4-NOT: luxc1
+
+; MIPS64R6-NOT: luxc1
+
%arrayidx1 = getelementptr inbounds [4 x %struct.S2]* @s2, i32 0, i32 %b, i32 0, i32 %c
%0 = load double* %arrayidx1, align 1
ret double %0
@@ -78,8 +206,18 @@ entry:
define void @foo7(i32 %b, i32 %c) nounwind {
entry:
-; CHECK: foo7
-; CHECK-NOT: suxc1
+; ALL-LABEL: foo7:
+
+; MIPS32R1-NOT: suxc1
+
+; MIPS32R2-NOT: suxc1
+
+; MIPS32R6-NOT: suxc1
+
+; MIPS4-NOT: suxc1
+
+; MIPS64R6-NOT: suxc1
+
%0 = load double* @gd, align 8
%arrayidx1 = getelementptr inbounds [4 x %struct.S2]* @s2, i32 0, i32 %b, i32 0, i32 %c
store double %0, double* %arrayidx1, align 1
@@ -88,16 +226,36 @@ entry:
define float @foo8() nounwind readonly {
entry:
-; CHECK: foo8
-; CHECK-NOT: luxc1
+; ALL-LABEL: foo8:
+
+; MIPS32R1-NOT: luxc1
+
+; MIPS32R2-NOT: luxc1
+
+; MIPS32R6-NOT: luxc1
+
+; MIPS4-NOT: luxc1
+
+; MIPS64R6-NOT: luxc1
+
%0 = load float* getelementptr inbounds (%struct.S3* @s3, i32 0, i32 1), align 1
ret float %0
}
define void @foo9(float %f) nounwind {
entry:
-; CHECK: foo9
-; CHECK-NOT: suxc1
+; ALL-LABEL: foo9:
+
+; MIPS32R1-NOT: suxc1
+
+; MIPS32R2-NOT: suxc1
+
+; MIPS32R6-NOT: suxc1
+
+; MIPS4-NOT: suxc1
+
+; MIPS64R6-NOT: suxc1
+
store float %f, float* getelementptr inbounds (%struct.S3* @s3, i32 0, i32 1), align 1
ret void
}
diff --git a/test/CodeGen/Mips/fpbr.ll b/test/CodeGen/Mips/fpbr.ll
index a136557..311b830 100644
--- a/test/CodeGen/Mips/fpbr.ll
+++ b/test/CodeGen/Mips/fpbr.ll
@@ -1,9 +1,25 @@
-; RUN: llc < %s -march=mipsel | FileCheck %s
+; RUN: llc < %s -march=mipsel -mcpu=mips32 | FileCheck %s -check-prefix=ALL -check-prefix=FCC -check-prefix=32-FCC
+; RUN: llc < %s -march=mipsel -mcpu=mips32r2 | FileCheck %s -check-prefix=ALL -check-prefix=FCC -check-prefix=32-FCC
+; RUN: llc < %s -march=mipsel -mcpu=mips32r6 | FileCheck %s -check-prefix=ALL -check-prefix=GPR -check-prefix=32-GPR
+; RUN: llc < %s -march=mips64el -mcpu=mips64 | FileCheck %s -check-prefix=ALL -check-prefix=FCC -check-prefix=64-FCC
+; RUN: llc < %s -march=mips64el -mcpu=mips64r2 | FileCheck %s -check-prefix=ALL -check-prefix=FCC -check-prefix=64-FCC
+; RUN: llc < %s -march=mips64el -mcpu=mips64r6 | FileCheck %s -check-prefix=ALL -check-prefix=GPR -check-prefix=64-GPR
define void @func0(float %f2, float %f3) nounwind {
entry:
-; CHECK: c.eq.s
-; CHECK: bc1f
+; ALL-LABEL: func0:
+
+; 32-FCC: c.eq.s $f12, $f14
+; 64-FCC: c.eq.s $f12, $f13
+; FCC: bc1f $BB0_2
+
+; 32-GPR: cmp.eq.s $[[FGRCC:f[0-9]+]], $f12, $f14
+; 64-GPR: cmp.eq.s $[[FGRCC:f[0-9]+]], $f12, $f13
+; GPR: mfc1 $[[GPRCC:[0-9]+]], $[[FGRCC:f[0-9]+]]
+; FIXME: We ought to be able to transform not+bnez -> beqz
+; GPR: not $[[GPRCC]], $[[GPRCC]]
+; GPR: bnez $[[GPRCC]], $BB0_2
+
%cmp = fcmp oeq float %f2, %f3
br i1 %cmp, label %if.then, label %if.else
@@ -25,8 +41,18 @@ declare void @g1(...)
define void @func1(float %f2, float %f3) nounwind {
entry:
-; CHECK: c.olt.s
-; CHECK: bc1f
+; ALL-LABEL: func1:
+
+; 32-FCC: c.olt.s $f12, $f14
+; 64-FCC: c.olt.s $f12, $f13
+; FCC: bc1f $BB1_2
+
+; 32-GPR: cmp.ule.s $[[FGRCC:f[0-9]+]], $f14, $f12
+; 64-GPR: cmp.ule.s $[[FGRCC:f[0-9]+]], $f13, $f12
+; GPR: mfc1 $[[GPRCC:[0-9]+]], $[[FGRCC:f[0-9]+]]
+; GPR-NOT: not $[[GPRCC]], $[[GPRCC]]
+; GPR: bnez $[[GPRCC]], $BB1_2
+
%cmp = fcmp olt float %f2, %f3
br i1 %cmp, label %if.then, label %if.else
@@ -44,8 +70,18 @@ if.end: ; preds = %if.else, %if.then
define void @func2(float %f2, float %f3) nounwind {
entry:
-; CHECK: c.ole.s
-; CHECK: bc1t
+; ALL-LABEL: func2:
+
+; 32-FCC: c.ole.s $f12, $f14
+; 64-FCC: c.ole.s $f12, $f13
+; FCC: bc1t $BB2_2
+
+; 32-GPR: cmp.ult.s $[[FGRCC:f[0-9]+]], $f14, $f12
+; 64-GPR: cmp.ult.s $[[FGRCC:f[0-9]+]], $f13, $f12
+; GPR: mfc1 $[[GPRCC:[0-9]+]], $[[FGRCC:f[0-9]+]]
+; GPR-NOT: not $[[GPRCC]], $[[GPRCC]]
+; GPR: beqz $[[GPRCC]], $BB2_2
+
%cmp = fcmp ugt float %f2, %f3
br i1 %cmp, label %if.else, label %if.then
@@ -63,8 +99,19 @@ if.end: ; preds = %if.else, %if.then
define void @func3(double %f2, double %f3) nounwind {
entry:
-; CHECK: c.eq.d
-; CHECK: bc1f
+; ALL-LABEL: func3:
+
+; 32-FCC: c.eq.d $f12, $f14
+; 64-FCC: c.eq.d $f12, $f13
+; FCC: bc1f $BB3_2
+
+; 32-GPR: cmp.eq.d $[[FGRCC:f[0-9]+]], $f12, $f14
+; 64-GPR: cmp.eq.d $[[FGRCC:f[0-9]+]], $f12, $f13
+; GPR: mfc1 $[[GPRCC:[0-9]+]], $[[FGRCC:f[0-9]+]]
+; FIXME: We ought to be able to transform not+bnez -> beqz
+; GPR: not $[[GPRCC]], $[[GPRCC]]
+; GPR: bnez $[[GPRCC]], $BB3_2
+
%cmp = fcmp oeq double %f2, %f3
br i1 %cmp, label %if.then, label %if.else
@@ -82,8 +129,18 @@ if.end: ; preds = %if.else, %if.then
define void @func4(double %f2, double %f3) nounwind {
entry:
-; CHECK: c.olt.d
-; CHECK: bc1f
+; ALL-LABEL: func4:
+
+; 32-FCC: c.olt.d $f12, $f14
+; 64-FCC: c.olt.d $f12, $f13
+; FCC: bc1f $BB4_2
+
+; 32-GPR: cmp.ule.d $[[FGRCC:f[0-9]+]], $f14, $f12
+; 64-GPR: cmp.ule.d $[[FGRCC:f[0-9]+]], $f13, $f12
+; GPR: mfc1 $[[GPRCC:[0-9]+]], $[[FGRCC:f[0-9]+]]
+; GPR-NOT: not $[[GPRCC]], $[[GPRCC]]
+; GPR: bnez $[[GPRCC]], $BB4_2
+
%cmp = fcmp olt double %f2, %f3
br i1 %cmp, label %if.then, label %if.else
@@ -101,8 +158,18 @@ if.end: ; preds = %if.else, %if.then
define void @func5(double %f2, double %f3) nounwind {
entry:
-; CHECK: c.ole.d
-; CHECK: bc1t
+; ALL-LABEL: func5:
+
+; 32-FCC: c.ole.d $f12, $f14
+; 64-FCC: c.ole.d $f12, $f13
+; FCC: bc1t $BB5_2
+
+; 32-GPR: cmp.ult.d $[[FGRCC:f[0-9]+]], $f14, $f12
+; 64-GPR: cmp.ult.d $[[FGRCC:f[0-9]+]], $f13, $f12
+; GPR: mfc1 $[[GPRCC:[0-9]+]], $[[FGRCC:f[0-9]+]]
+; GPR-NOT: not $[[GPRCC]], $[[GPRCC]]
+; GPR: beqz $[[GPRCC]], $BB5_2
+
%cmp = fcmp ugt double %f2, %f3
br i1 %cmp, label %if.else, label %if.then
diff --git a/test/CodeGen/Mips/inlineasm-cnstrnt-reg.ll b/test/CodeGen/Mips/inlineasm-cnstrnt-reg.ll
index 9464918..a67ddce 100644
--- a/test/CodeGen/Mips/inlineasm-cnstrnt-reg.ll
+++ b/test/CodeGen/Mips/inlineasm-cnstrnt-reg.ll
@@ -1,6 +1,7 @@
; Positive test for inline register constraints
;
-; RUN: llc -march=mipsel < %s | FileCheck %s
+; RUN: llc -march=mipsel -mcpu=mips32 < %s | FileCheck %s
+; RUN: llc -march=mipsel -mcpu=mips32r2 < %s | FileCheck %s
define i32 @main() nounwind {
entry:
diff --git a/test/CodeGen/Mips/lit.local.cfg b/test/CodeGen/Mips/lit.local.cfg
index 1fa54b4..a3183a2 100644
--- a/test/CodeGen/Mips/lit.local.cfg
+++ b/test/CodeGen/Mips/lit.local.cfg
@@ -1,4 +1,3 @@
-targets = set(config.root.targets_to_build.split())
-if not 'Mips' in targets:
+if not 'Mips' in config.root.targets:
config.unsupported = True
diff --git a/test/CodeGen/Mips/llvm-ir/call.ll b/test/CodeGen/Mips/llvm-ir/call.ll
new file mode 100644
index 0000000..4cbf43c
--- /dev/null
+++ b/test/CodeGen/Mips/llvm-ir/call.ll
@@ -0,0 +1,166 @@
+; Test the 'call' instruction and the tailcall variant.
+
+; FIXME: We should remove the need for -enable-mips-tail-calls
+; RUN: llc -march=mips -mcpu=mips32 -enable-mips-tail-calls < %s | FileCheck %s -check-prefix=ALL -check-prefix=O32
+; RUN: llc -march=mips -mcpu=mips32r2 -enable-mips-tail-calls < %s | FileCheck %s -check-prefix=ALL -check-prefix=O32
+; RUN: llc -march=mips -mcpu=mips32r6 -enable-mips-tail-calls < %s | FileCheck %s -check-prefix=ALL -check-prefix=O32
+; RUN: llc -march=mips64 -mcpu=mips4 -enable-mips-tail-calls < %s | FileCheck %s -check-prefix=ALL -check-prefix=N64
+; RUN: llc -march=mips64 -mcpu=mips64 -enable-mips-tail-calls < %s | FileCheck %s -check-prefix=ALL -check-prefix=N64
+; RUN: llc -march=mips64 -mcpu=mips64r2 -enable-mips-tail-calls < %s | FileCheck %s -check-prefix=ALL -check-prefix=N64
+; RUN: llc -march=mips64 -mcpu=mips64r6 -enable-mips-tail-calls < %s | FileCheck %s -check-prefix=ALL -check-prefix=N64
+
+declare void @extern_void_void()
+declare i32 @extern_i32_void()
+declare float @extern_float_void()
+
+define i32 @call_void_void() {
+; ALL-LABEL: call_void_void:
+
+; O32: lw $[[TGT:[0-9]+]], %call16(extern_void_void)($gp)
+
+; N64: ld $[[TGT:[0-9]+]], %call16(extern_void_void)($gp)
+
+; ALL: jalr $[[TGT]]
+
+ call void @extern_void_void()
+ ret i32 0
+}
+
+define i32 @call_i32_void() {
+; ALL-LABEL: call_i32_void:
+
+; O32: lw $[[TGT:[0-9]+]], %call16(extern_i32_void)($gp)
+
+; N64: ld $[[TGT:[0-9]+]], %call16(extern_i32_void)($gp)
+
+; ALL: jalr $[[TGT]]
+
+ %1 = call i32 @extern_i32_void()
+ %2 = add i32 %1, 1
+ ret i32 %2
+}
+
+define float @call_float_void() {
+; ALL-LABEL: call_float_void:
+
+; FIXME: Not sure why we don't use $gp directly on such a simple test. We should
+; look into it at some point.
+; O32: addu $[[GP:[0-9]+]], ${{[0-9]+}}, $25
+; O32: lw $[[TGT:[0-9]+]], %call16(extern_float_void)($[[GP]])
+
+; N64: ld $[[TGT:[0-9]+]], %call16(extern_float_void)($gp)
+
+; ALL: jalr $[[TGT]]
+
+; O32: move $gp, $[[GP]]
+
+ %1 = call float @extern_float_void()
+ %2 = fadd float %1, 1.0
+ ret float %2
+}
+
+define void @musttail_call_void_void() {
+; ALL-LABEL: musttail_call_void_void:
+
+; O32: lw $[[TGT:[0-9]+]], %call16(extern_void_void)($gp)
+
+; N64: ld $[[TGT:[0-9]+]], %call16(extern_void_void)($gp)
+
+; NOT-R6: jr $[[TGT]]
+; R6: r6.jr $[[TGT]]
+
+ musttail call void @extern_void_void()
+ ret void
+}
+
+define i32 @musttail_call_i32_void() {
+; ALL-LABEL: musttail_call_i32_void:
+
+; O32: lw $[[TGT:[0-9]+]], %call16(extern_i32_void)($gp)
+
+; N64: ld $[[TGT:[0-9]+]], %call16(extern_i32_void)($gp)
+
+; NOT-R6: jr $[[TGT]]
+; R6: r6.jr $[[TGT]]
+
+ %1 = musttail call i32 @extern_i32_void()
+ ret i32 %1
+}
+
+define float @musttail_call_float_void() {
+; ALL-LABEL: musttail_call_float_void:
+
+; O32: lw $[[TGT:[0-9]+]], %call16(extern_float_void)($gp)
+
+; N64: ld $[[TGT:[0-9]+]], %call16(extern_float_void)($gp)
+
+; NOT-R6: jr $[[TGT]]
+; R6: r6.jr $[[TGT]]
+
+ %1 = musttail call float @extern_float_void()
+ ret float %1
+}
+
+define i32 @indirect_call_void_void(void ()* %addr) {
+; ALL-LABEL: indirect_call_void_void:
+
+; ALL: move $25, $4
+; ALL: jalr $25
+
+ call void %addr()
+ ret i32 0
+}
+
+define i32 @indirect_call_i32_void(i32 ()* %addr) {
+; ALL-LABEL: indirect_call_i32_void:
+
+; ALL: move $25, $4
+; ALL: jalr $25
+
+ %1 = call i32 %addr()
+ %2 = add i32 %1, 1
+ ret i32 %2
+}
+
+define float @indirect_call_float_void(float ()* %addr) {
+; ALL-LABEL: indirect_call_float_void:
+
+; ALL: move $25, $4
+; ALL: jalr $25
+
+ %1 = call float %addr()
+ %2 = fadd float %1, 1.0
+ ret float %2
+}
+
+; We can't use 'musttail' here because the verifier is too conservative and
+; prohibits any prototype difference.
+define void @tail_indirect_call_void_void(void ()* %addr) {
+; ALL-LABEL: tail_indirect_call_void_void:
+
+; ALL: move $25, $4
+; ALL: jr $25
+
+ tail call void %addr()
+ ret void
+}
+
+define i32 @tail_indirect_call_i32_void(i32 ()* %addr) {
+; ALL-LABEL: tail_indirect_call_i32_void:
+
+; ALL: move $25, $4
+; ALL: jr $25
+
+ %1 = tail call i32 %addr()
+ ret i32 %1
+}
+
+define float @tail_indirect_call_float_void(float ()* %addr) {
+; ALL-LABEL: tail_indirect_call_float_void:
+
+; ALL: move $25, $4
+; ALL: jr $25
+
+ %1 = tail call float %addr()
+ ret float %1
+}
diff --git a/test/CodeGen/Mips/llvm-ir/indirectbr.ll b/test/CodeGen/Mips/llvm-ir/indirectbr.ll
new file mode 100644
index 0000000..d8fd787
--- /dev/null
+++ b/test/CodeGen/Mips/llvm-ir/indirectbr.ll
@@ -0,0 +1,34 @@
+; Test all important variants of the unconditional 'br' instruction.
+
+; RUN: llc -march=mips -mcpu=mips32 -asm-show-inst < %s | FileCheck %s -check-prefix=ALL -check-prefix=NOT-R6
+; RUN: llc -march=mips -mcpu=mips32r2 -asm-show-inst < %s | FileCheck %s -check-prefix=ALL -check-prefix=NOT-R6
+; RUN: llc -march=mips -mcpu=mips32r6 -asm-show-inst < %s | FileCheck %s -check-prefix=ALL -check-prefix=R6
+; RUN: llc -march=mips64 -mcpu=mips4 -asm-show-inst < %s | FileCheck %s -check-prefix=ALL -check-prefix=NOT-R6
+; RUN: llc -march=mips64 -mcpu=mips64 -asm-show-inst < %s | FileCheck %s -check-prefix=ALL -check-prefix=NOT-R6
+; RUN: llc -march=mips64 -mcpu=mips64r2 -asm-show-inst < %s | FileCheck %s -check-prefix=ALL -check-prefix=NOT-R6
+; RUN: llc -march=mips64 -mcpu=mips64r6 -asm-show-inst < %s | FileCheck %s -check-prefix=ALL -check-prefix=R6
+
+define i32 @br(i8 *%addr) {
+; ALL-LABEL: br:
+; NOT-R6: jr $4 # <MCInst #{{[0-9]+}} JR
+; R6: jr $4 # <MCInst #{{[0-9]+}} JALR
+
+; ALL: $BB0_1: # %L1
+; NOT-R6: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6: jr $ra # <MCInst #{{[0-9]+}} JALR
+; ALL: addiu $2, $zero, 0
+
+; ALL: $BB0_2: # %L2
+; NOT-R6: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6: jr $ra # <MCInst #{{[0-9]+}} JALR
+; ALL: addiu $2, $zero, 1
+
+entry:
+ indirectbr i8* %addr, [label %L1, label %L2]
+
+L1:
+ ret i32 0
+
+L2:
+ ret i32 1
+}
diff --git a/test/CodeGen/Mips/llvm-ir/ret.ll b/test/CodeGen/Mips/llvm-ir/ret.ll
new file mode 100644
index 0000000..8f5b115
--- /dev/null
+++ b/test/CodeGen/Mips/llvm-ir/ret.ll
@@ -0,0 +1,205 @@
+; Test all important variants of the 'ret' instruction.
+;
+; For non-void returns it is necessary to have something to return so we also
+; test constant generation here.
+;
+; We'll test pointer returns in a separate file since the relocation model
+; affects it and it's undesirable to repeat the non-pointer returns for each
+; relocation model.
+
+; RUN: llc -march=mips -mcpu=mips32 -asm-show-inst < %s | FileCheck %s -check-prefix=ALL -check-prefix=GPR32 -check-prefix=NO-MTHC1 -check-prefix=NOT-R6
+; RUN: llc -march=mips -mcpu=mips32r2 -asm-show-inst < %s | FileCheck %s -check-prefix=ALL -check-prefix=GPR32 -check-prefix=MTHC1 -check-prefix=NOT-R6
+; RUN: llc -march=mips -mcpu=mips32r6 -asm-show-inst < %s | FileCheck %s -check-prefix=ALL -check-prefix=GPR32 -check-prefix=MTHC1 -check-prefix=R6
+; RUN: llc -march=mips64 -mcpu=mips4 -asm-show-inst < %s | FileCheck %s -check-prefix=ALL -check-prefix=GPR64 -check-prefix=DMTC1 -check-prefix=NOT-R6
+; RUN: llc -march=mips64 -mcpu=mips64 -asm-show-inst < %s | FileCheck %s -check-prefix=ALL -check-prefix=GPR64 -check-prefix=DMTC1 -check-prefix=NOT-R6
+; RUN: llc -march=mips64 -mcpu=mips64r2 -asm-show-inst < %s | FileCheck %s -check-prefix=ALL -check-prefix=GPR64 -check-prefix=DMTC1 -check-prefix=NOT-R6
+; RUN: llc -march=mips64 -mcpu=mips64r6 -asm-show-inst < %s | FileCheck %s -check-prefix=ALL -check-prefix=GPR64 -check-prefix=DMTC1 -check-prefix=R6
+
+define void @ret_void() {
+; ALL-LABEL: ret_void:
+
+; NOT-R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JALR
+
+ ret void
+}
+
+define i8 @ret_i8() {
+; ALL-LABEL: ret_i8:
+; ALL-DAG: addiu $2, $zero, 3
+
+; NOT-R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JALR
+
+ ret i8 3
+}
+
+define i16 @ret_i16_3() {
+; ALL-LABEL: ret_i16_3:
+; ALL-DAG: addiu $2, $zero, 3
+
+; NOT-R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JALR
+
+ ret i16 3
+}
+
+define i16 @ret_i16_256() {
+; ALL-LABEL: ret_i16_256:
+; ALL-DAG: addiu $2, $zero, 256
+
+; NOT-R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JALR
+
+ ret i16 256
+}
+
+define i16 @ret_i16_257() {
+; ALL-LABEL: ret_i16_257:
+; ALL-DAG: addiu $2, $zero, 257
+
+; NOT-R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JALR
+
+ ret i16 257
+}
+
+define i32 @ret_i32_257() {
+; ALL-LABEL: ret_i32_257:
+; ALL-DAG: addiu $2, $zero, 257
+
+; NOT-R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JALR
+
+ ret i32 257
+}
+
+define i32 @ret_i32_65536() {
+; ALL-LABEL: ret_i32_65536:
+; ALL-DAG: lui $2, 1
+
+; NOT-R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JALR
+
+ ret i32 65536
+}
+
+define i32 @ret_i32_65537() {
+; ALL-LABEL: ret_i32_65537:
+; ALL: lui $[[T0:[0-9]+]], 1
+; ALL-DAG: ori $2, $[[T0]], 1
+
+; NOT-R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JALR
+
+ ret i32 65537
+}
+
+define i64 @ret_i64_65537() {
+; ALL-LABEL: ret_i64_65537:
+; ALL: lui $[[T0:[0-9]+]], 1
+
+; GPR32-DAG: ori $3, $[[T0]], 1
+; GPR32-DAG: addiu $2, $zero, 0
+
+; GPR64-DAG: daddiu $2, $[[T0]], 1
+
+; NOT-R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JALR
+
+ ret i64 65537
+}
+
+define i64 @ret_i64_281479271677952() {
+; ALL-LABEL: ret_i64_281479271677952:
+; ALL-DAG: lui $[[T0:[0-9]+]], 1
+
+; GPR32-DAG: ori $2, $[[T0]], 1
+; GPR32-DAG: addiu $3, $zero, 0
+
+; GPR64-DAG: daddiu $[[T1:[0-9]+]], $[[T0]], 1
+; GPR64-DAG: dsll $2, $[[T1]], 32
+
+; NOT-R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JALR
+
+ ret i64 281479271677952
+}
+
+define i64 @ret_i64_281479271809026() {
+; ALL-LABEL: ret_i64_281479271809026:
+; GPR32-DAG: lui $[[T0:[0-9]+]], 1
+; GPR32-DAG: lui $[[T1:[0-9]+]], 2
+; GPR32-DAG: ori $2, $[[T0]], 1
+; GPR32-DAG: ori $3, $[[T1]], 2
+
+; GPR64-DAG: ori $[[T0:[0-9]+]], $zero, 32769
+; GPR64-DAG: dsll $[[T1:[0-9]+]], $[[T0]], 16
+; GPR64-DAG: daddiu $[[T0:[0-9]+]], $[[T0]], -32767
+; GPR64-DAG: dsll $[[T1:[0-9]+]], $[[T0]], 17
+; GPR64-DAG: daddiu $2, $[[T1]], 2
+
+; NOT-R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JALR
+
+ ret i64 281479271809026
+}
+
+define float @ret_float_0x0() {
+; ALL-LABEL: ret_float_0x0:
+
+; NO-MTHC1-DAG: mtc1 $zero, $f0
+
+; MTHC1-DAG: mtc1 $zero, $f0
+
+; DMTC-DAG: dmtc1 $zero, $f0
+
+; NOT-R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JALR
+
+ ret float 0x0000000000000000
+}
+
+define float @ret_float_0x3() {
+; ALL-LABEL: ret_float_0x3:
+
+; Use a constant pool
+; O32-DAG: lwc1 $f0, %lo($CPI
+; N64-DAG: lwc1 $f0, %got_ofst($CPI
+
+; NOT-R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JALR
+
+; float constants are written as double constants
+ ret float 0x36b8000000000000
+}
+
+define double @ret_double_0x0() {
+; ALL-LABEL: ret_double_0x0:
+
+; NO-MTHC1-DAG: mtc1 $zero, $f0
+; NO-MTHC1-DAG: mtc1 $zero, $f1
+
+; MTHC1-DAG: mtc1 $zero, $f0
+; MTHC1-DAG: mthc1 $zero, $f0
+
+; DMTC-DAG: dmtc1 $zero, $f0
+
+; NOT-R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JALR
+
+ ret double 0x0000000000000000
+}
+
+define double @ret_double_0x3() {
+; ALL-LABEL: ret_double_0x3:
+
+; Use a constant pool
+; O32-DAG: ldc1 $f0, %lo($CPI
+; N64-DAG: ldc1 $f0, %got_ofst($CPI
+
+; NOT-R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JR
+; R6-DAG: jr $ra # <MCInst #{{[0-9]+}} JALR
+
+ ret double 0x0000000000000003
+}
diff --git a/test/CodeGen/Mips/longbranch.ll b/test/CodeGen/Mips/longbranch.ll
index c7fe6fd..a403744 100644
--- a/test/CodeGen/Mips/longbranch.ll
+++ b/test/CodeGen/Mips/longbranch.ll
@@ -7,6 +7,8 @@
; RUN: < %s | FileCheck %s -check-prefix=N64
; RUN: llc -march=mipsel -mcpu=mips32r2 -mattr=micromips \
; RUN: -force-mips-long-branch -O3 < %s | FileCheck %s -check-prefix=MICROMIPS
+; RUN: llc -mtriple=mipsel-none-nacl -force-mips-long-branch -O3 < %s \
+; RUN: | FileCheck %s -check-prefix=NACL
@x = external global i32
@@ -126,4 +128,36 @@ end:
; MICROMIPS: $[[BB2]]:
; MICROMIPS: jr $ra
; MICROMIPS: nop
+
+
+; Check the NaCl version. Check that sp change is not in the branch delay slot
+; of "jr $1" instruction. Check that target of indirect branch "jr $1" is
+; bundle aligned.
+
+; NACL: lui $[[R0:[0-9]+]], %hi(_gp_disp)
+; NACL: addiu $[[R0]], $[[R0]], %lo(_gp_disp)
+; NACL: bnez $4, $[[BB0:BB[0-9_]+]]
+; NACL: addu $[[GP:[0-9]+]], $[[R0]], $25
+
+; Check for long branch expansion:
+; NACL: addiu $sp, $sp, -8
+; NACL-NEXT: sw $ra, 0($sp)
+; NACL-NEXT: lui $1, %hi(($[[BB2:BB[0-9_]+]])-($[[BB1:BB[0-9_]+]]))
+; NACL-NEXT: bal $[[BB1]]
+; NACL-NEXT: addiu $1, $1, %lo(($[[BB2]])-($[[BB1]]))
+; NACL-NEXT: $[[BB1]]:
+; NACL-NEXT: addu $1, $ra, $1
+; NACL-NEXT: lw $ra, 0($sp)
+; NACL-NEXT: addiu $sp, $sp, 8
+; NACL-NEXT: jr $1
+; NACL-NEXT: nop
+
+; NACL: $[[BB0]]:
+; NACL: lw $[[R1:[0-9]+]], %got(x)($[[GP]])
+; NACL: addiu $[[R2:[0-9]+]], $zero, 1
+; NACL: sw $[[R2]], 0($[[R1]])
+; NACL: .align 4
+; NACL-NEXT: $[[BB2]]:
+; NACL: jr $ra
+; NACL: nop
}
diff --git a/test/CodeGen/Mips/madd-msub.ll b/test/CodeGen/Mips/madd-msub.ll
index 0dbb2c2..8222967 100644
--- a/test/CodeGen/Mips/madd-msub.ll
+++ b/test/CodeGen/Mips/madd-msub.ll
@@ -1,9 +1,49 @@
-; RUN: llc -march=mips < %s | FileCheck %s -check-prefix=32
-; RUN: llc -march=mips -mattr=dsp < %s | FileCheck %s -check-prefix=DSP
+; RUN: llc -march=mips -mcpu=mips32 < %s | FileCheck %s -check-prefix=ALL -check-prefix=32
+; RUN: llc -march=mips -mcpu=mips32r2 < %s | FileCheck %s -check-prefix=ALL -check-prefix=32
+; RUN: llc -march=mips -mcpu=mips32r6 < %s | FileCheck %s -check-prefix=ALL -check-prefix=32R6
+; RUN: llc -march=mips -mcpu=mips32 -mattr=dsp < %s | FileCheck %s -check-prefix=DSP
+; RUN: llc -march=mips -mcpu=mips64 < %s | FileCheck %s -check-prefix=ALL -check-prefix=64
+; RUN: llc -march=mips -mcpu=mips64r2 < %s | FileCheck %s -check-prefix=ALL -check-prefix=64
+; RUN: llc -march=mips -mcpu=mips64r6 < %s | FileCheck %s -check-prefix=ALL -check-prefix=64R6
+
+; FIXME: The MIPS16 test should check its output
; RUN: llc -march=mips -mcpu=mips16 < %s
-; 32: madd ${{[0-9]+}}
-; DSP: madd $ac
+; ALL-LABEL: madd1:
+
+; 32-DAG: sra $[[T0:[0-9]+]], $6, 31
+; 32-DAG: mtlo $6
+; 32-DAG: [[m:m]]add ${{[45]}}, ${{[45]}}
+; 32-DAG: [[m]]fhi $2
+; 32-DAG: [[m]]flo $3
+
+; DSP-DAG: sra $[[T0:[0-9]+]], $6, 31
+; DSP-DAG: mtlo $[[AC:ac[0-3]+]], $6
+; DSP-DAG: madd $[[AC]], ${{[45]}}, ${{[45]}}
+; DSP-DAG: mfhi $2, $[[AC]]
+; DSP-DAG: mflo $3, $[[AC]]
+
+; 32R6-DAG: mul $[[T0:[0-9]+]], ${{[45]}}, ${{[45]}}
+; 32R6-DAG: addu $[[T1:[0-9]+]], $[[T0]], $6
+; 32R6-DAG: sltu $[[T2:[0-9]+]], $[[T1]], $6
+; 32R6-DAG: sra $[[T3:[0-9]+]], $6, 31
+; 32R6-DAG: addu $[[T4:[0-9]+]], $[[T2]], $[[T3]]
+; 32R6-DAG: muh $[[T5:[0-9]+]], ${{[45]}}, ${{[45]}}
+; 32R6-DAG: addu $2, $[[T5]], $[[T4]]
+
+; 64-DAG: sll $[[T0:[0-9]+]], $4, 0
+; 64-DAG: sll $[[T1:[0-9]+]], $5, 0
+; 64-DAG: d[[m:m]]ult $[[T1]], $[[T0]]
+; 64-DAG: [[m]]flo $[[T2:[0-9]+]]
+; 64-DAG: sll $[[T3:[0-9]+]], $6, 0
+; 64-DAG: daddu $2, $[[T2]], $[[T3]]
+
+; 64R6-DAG: sll $[[T0:[0-9]+]], $4, 0
+; 64R6-DAG: sll $[[T1:[0-9]+]], $5, 0
+; 64R6-DAG: dmul $[[T2:[0-9]+]], $[[T1]], $[[T0]]
+; 64R6-DAG: sll $[[T3:[0-9]+]], $6, 0
+; 64R6-DAG: daddu $2, $[[T2]], $[[T3]]
+
define i64 @madd1(i32 %a, i32 %b, i32 %c) nounwind readnone {
entry:
%conv = sext i32 %a to i64
@@ -14,8 +54,47 @@ entry:
ret i64 %add
}
-; 32: maddu ${{[0-9]+}}
-; DSP: maddu $ac
+; ALL-LABEL: madd2:
+
+; FIXME: We don't really need this instruction
+; 32-DAG: addiu $[[T0:[0-9]+]], $zero, 0
+; 32-DAG: mtlo $6
+; 32-DAG: [[m:m]]addu ${{[45]}}, ${{[45]}}
+; 32-DAG: [[m]]fhi $2
+; 32-DAG: [[m]]flo $3
+
+; DSP-DAG: addiu $[[T0:[0-9]+]], $zero, 0
+; DSP-DAG: mtlo $[[AC:ac[0-3]+]], $6
+; DSP-DAG: maddu $[[AC]], ${{[45]}}, ${{[45]}}
+; DSP-DAG: mfhi $2, $[[AC]]
+; DSP-DAG: mflo $3, $[[AC]]
+
+; 32R6-DAG: mul $[[T0:[0-9]+]], ${{[45]}}, ${{[45]}}
+; 32R6-DAG: addu $[[T1:[0-9]+]], $[[T0]], $6
+; 32R6-DAG: sltu $[[T2:[0-9]+]], $[[T1]], $6
+; FIXME: There's a redundant move here. We should remove it
+; 32R6-DAG: muhu $[[T3:[0-9]+]], ${{[45]}}, ${{[45]}}
+; 32R6-DAG: addu $2, $[[T3]], $[[T2]]
+
+; 64-DAG: dsll $[[T0:[0-9]+]], $4, 32
+; 64-DAG: dsrl $[[T1:[0-9]+]], $[[T0]], 32
+; 64-DAG: dsll $[[T2:[0-9]+]], $5, 32
+; 64-DAG: dsrl $[[T3:[0-9]+]], $[[T2]], 32
+; 64-DAG: d[[m:m]]ult $[[T3]], $[[T1]]
+; 64-DAG: [[m]]flo $[[T4:[0-9]+]]
+; 64-DAG: dsll $[[T5:[0-9]+]], $6, 32
+; 64-DAG: dsrl $[[T6:[0-9]+]], $[[T5]], 32
+; 64-DAG: daddu $2, $[[T4]], $[[T6]]
+
+; 64R6-DAG: dsll $[[T0:[0-9]+]], $4, 32
+; 64R6-DAG: dsrl $[[T1:[0-9]+]], $[[T0]], 32
+; 64R6-DAG: dsll $[[T2:[0-9]+]], $5, 32
+; 64R6-DAG: dsrl $[[T3:[0-9]+]], $[[T2]], 32
+; 64R6-DAG: dmul $[[T4:[0-9]+]], $[[T3]], $[[T1]]
+; 64R6-DAG: dsll $[[T5:[0-9]+]], $6, 32
+; 64R6-DAG: dsrl $[[T6:[0-9]+]], $[[T5]], 32
+; 64R6-DAG: daddu $2, $[[T4]], $[[T6]]
+
define i64 @madd2(i32 %a, i32 %b, i32 %c) nounwind readnone {
entry:
%conv = zext i32 %a to i64
@@ -26,8 +105,38 @@ entry:
ret i64 %add
}
-; 32: madd ${{[0-9]+}}
-; DSP: madd $ac
+; ALL-LABEL: madd3:
+
+; 32-DAG: mthi $6
+; 32-DAG: mtlo $7
+; 32-DAG: [[m:m]]add ${{[45]}}, ${{[45]}}
+; 32-DAG: [[m]]fhi $2
+; 32-DAG: [[m]]flo $3
+
+; DSP-DAG: mthi $[[AC:ac[0-3]+]], $6
+; DSP-DAG: mtlo $[[AC]], $7
+; DSP-DAG: madd $[[AC]], ${{[45]}}, ${{[45]}}
+; DSP-DAG: mfhi $2, $[[AC]]
+; DSP-DAG: mflo $3, $[[AC]]
+
+; 32R6-DAG: mul $[[T0:[0-9]+]], ${{[45]}}, ${{[45]}}
+; 32R6-DAG: addu $[[T1:[0-9]+]], $[[T0]], $7
+; 32R6-DAG: sltu $[[T2:[0-9]+]], $[[T1]], $7
+; 32R6-DAG: addu $[[T4:[0-9]+]], $[[T2]], $6
+; 32R6-DAG: muh $[[T5:[0-9]+]], ${{[45]}}, ${{[45]}}
+; 32R6-DAG: addu $2, $[[T5]], $[[T4]]
+
+; 64-DAG: sll $[[T0:[0-9]+]], $4, 0
+; 64-DAG: sll $[[T1:[0-9]+]], $5, 0
+; 64-DAG: d[[m:m]]ult $[[T1]], $[[T0]]
+; 64-DAG: [[m]]flo $[[T2:[0-9]+]]
+; 64-DAG: daddu $2, $[[T2]], $6
+
+; 64R6-DAG: sll $[[T0:[0-9]+]], $4, 0
+; 64R6-DAG: sll $[[T1:[0-9]+]], $5, 0
+; 64R6-DAG: dmul $[[T2:[0-9]+]], $[[T1]], $[[T0]]
+; 64R6-DAG: daddu $2, $[[T2]], $6
+
define i64 @madd3(i32 %a, i32 %b, i64 %c) nounwind readnone {
entry:
%conv = sext i32 %a to i64
@@ -37,8 +146,41 @@ entry:
ret i64 %add
}
-; 32: msub ${{[0-9]+}}
-; DSP: msub $ac
+; ALL-LABEL: msub1:
+
+; 32-DAG: sra $[[T0:[0-9]+]], $6, 31
+; 32-DAG: mtlo $6
+; 32-DAG: [[m:m]]sub ${{[45]}}, ${{[45]}}
+; 32-DAG: [[m]]fhi $2
+; 32-DAG: [[m]]flo $3
+
+; DSP-DAG: sra $[[T0:[0-9]+]], $6, 31
+; DSP-DAG: mtlo $[[AC:ac[0-3]+]], $6
+; DSP-DAG: msub $[[AC]], ${{[45]}}, ${{[45]}}
+; DSP-DAG: mfhi $2, $[[AC]]
+; DSP-DAG: mflo $3, $[[AC]]
+
+; 32R6-DAG: muh $[[T0:[0-9]+]], ${{[45]}}, ${{[45]}}
+; 32R6-DAG: mul $[[T1:[0-9]+]], ${{[45]}}, ${{[45]}}
+; 32R6-DAG: sltu $[[T3:[0-9]+]], $6, $[[T1]]
+; 32R6-DAG: addu $[[T4:[0-9]+]], $[[T3]], $[[T0]]
+; 32R6-DAG: sra $[[T5:[0-9]+]], $6, 31
+; 32R6-DAG: subu $2, $[[T5]], $[[T4]]
+; 32R6-DAG: subu $3, $6, $[[T1]]
+
+; 64-DAG: sll $[[T0:[0-9]+]], $4, 0
+; 64-DAG: sll $[[T1:[0-9]+]], $5, 0
+; 64-DAG: d[[m:m]]ult $[[T1]], $[[T0]]
+; 64-DAG: [[m]]flo $[[T2:[0-9]+]]
+; 64-DAG: sll $[[T3:[0-9]+]], $6, 0
+; 64-DAG: dsubu $2, $[[T3]], $[[T2]]
+
+; 64R6-DAG: sll $[[T0:[0-9]+]], $4, 0
+; 64R6-DAG: sll $[[T1:[0-9]+]], $5, 0
+; 64R6-DAG: dmul $[[T2:[0-9]+]], $[[T1]], $[[T0]]
+; 64R6-DAG: sll $[[T3:[0-9]+]], $6, 0
+; 64R6-DAG: dsubu $2, $[[T3]], $[[T2]]
+
define i64 @msub1(i32 %a, i32 %b, i32 %c) nounwind readnone {
entry:
%conv = sext i32 %c to i64
@@ -49,8 +191,48 @@ entry:
ret i64 %sub
}
-; 32: msubu ${{[0-9]+}}
-; DSP: msubu $ac
+; ALL-LABEL: msub2:
+
+; FIXME: We don't really need this instruction
+; 32-DAG: addiu $[[T0:[0-9]+]], $zero, 0
+; 32-DAG: mtlo $6
+; 32-DAG: [[m:m]]subu ${{[45]}}, ${{[45]}}
+; 32-DAG: [[m]]fhi $2
+; 32-DAG: [[m]]flo $3
+
+; DSP-DAG: addiu $[[T0:[0-9]+]], $zero, 0
+; DSP-DAG: mtlo $[[AC:ac[0-3]+]], $6
+; DSP-DAG: msubu $[[AC]], ${{[45]}}, ${{[45]}}
+; DSP-DAG: mfhi $2, $[[AC]]
+; DSP-DAG: mflo $3, $[[AC]]
+
+; 32R6-DAG: muhu $[[T0:[0-9]+]], ${{[45]}}, ${{[45]}}
+; 32R6-DAG: mul $[[T1:[0-9]+]], ${{[45]}}, ${{[45]}}
+
+; 32R6-DAG: sltu $[[T2:[0-9]+]], $6, $[[T1]]
+; 32R6-DAG: addu $[[T3:[0-9]+]], $[[T2]], $[[T0]]
+; 32R6-DAG: negu $2, $[[T3]]
+; 32R6-DAG: subu $3, $6, $[[T1]]
+
+; 64-DAG: dsll $[[T0:[0-9]+]], $4, 32
+; 64-DAG: dsrl $[[T1:[0-9]+]], $[[T0]], 32
+; 64-DAG: dsll $[[T2:[0-9]+]], $5, 32
+; 64-DAG: dsrl $[[T3:[0-9]+]], $[[T2]], 32
+; 64-DAG: d[[m:m]]ult $[[T3]], $[[T1]]
+; 64-DAG: [[m]]flo $[[T4:[0-9]+]]
+; 64-DAG: dsll $[[T5:[0-9]+]], $6, 32
+; 64-DAG: dsrl $[[T6:[0-9]+]], $[[T5]], 32
+; 64-DAG: dsubu $2, $[[T6]], $[[T4]]
+
+; 64R6-DAG: dsll $[[T0:[0-9]+]], $4, 32
+; 64R6-DAG: dsrl $[[T1:[0-9]+]], $[[T0]], 32
+; 64R6-DAG: dsll $[[T2:[0-9]+]], $5, 32
+; 64R6-DAG: dsrl $[[T3:[0-9]+]], $[[T2]], 32
+; 64R6-DAG: dmul $[[T4:[0-9]+]], $[[T3]], $[[T1]]
+; 64R6-DAG: dsll $[[T5:[0-9]+]], $6, 32
+; 64R6-DAG: dsrl $[[T6:[0-9]+]], $[[T5]], 32
+; 64R6-DAG: dsubu $2, $[[T6]], $[[T4]]
+
define i64 @msub2(i32 %a, i32 %b, i32 %c) nounwind readnone {
entry:
%conv = zext i32 %c to i64
@@ -61,8 +243,39 @@ entry:
ret i64 %sub
}
-; 32: msub ${{[0-9]+}}
-; DSP: msub $ac
+; ALL-LABEL: msub3:
+
+; FIXME: We don't really need this instruction
+; 32-DAG: mthi $6
+; 32-DAG: mtlo $7
+; 32-DAG: [[m:m]]sub ${{[45]}}, ${{[45]}}
+; 32-DAG: [[m]]fhi $2
+; 32-DAG: [[m]]flo $3
+
+; DSP-DAG: addiu $[[T0:[0-9]+]], $zero, 0
+; DSP-DAG: mtlo $[[AC:ac[0-3]+]], $6
+; DSP-DAG: msub $[[AC]], ${{[45]}}, ${{[45]}}
+; DSP-DAG: mfhi $2, $[[AC]]
+; DSP-DAG: mflo $3, $[[AC]]
+
+; 32R6-DAG: muh $[[T0:[0-9]+]], ${{[45]}}, ${{[45]}}
+; 32R6-DAG: mul $[[T1:[0-9]+]], ${{[45]}}, ${{[45]}}
+; 32R6-DAG: sltu $[[T2:[0-9]+]], $7, $[[T1]]
+; 32R6-DAG: addu $[[T3:[0-9]+]], $[[T2]], $[[T0]]
+; 32R6-DAG: subu $2, $6, $[[T3]]
+; 32R6-DAG: subu $3, $7, $[[T1]]
+
+; 64-DAG: sll $[[T0:[0-9]+]], $4, 0
+; 64-DAG: sll $[[T1:[0-9]+]], $5, 0
+; 64-DAG: d[[m:m]]ult $[[T1]], $[[T0]]
+; 64-DAG: [[m]]flo $[[T2:[0-9]+]]
+; 64-DAG: dsubu $2, $6, $[[T2]]
+
+; 64R6-DAG: sll $[[T0:[0-9]+]], $4, 0
+; 64R6-DAG: sll $[[T1:[0-9]+]], $5, 0
+; 64R6-DAG: dmul $[[T2:[0-9]+]], $[[T1]], $[[T0]]
+; 64R6-DAG: dsubu $2, $6, $[[T2]]
+
define i64 @msub3(i32 %a, i32 %b, i64 %c) nounwind readnone {
entry:
%conv = sext i32 %a to i64
diff --git a/test/CodeGen/Mips/mips16ex.ll b/test/CodeGen/Mips/mips16ex.ll
index ecb30b5..a1a9919 100644
--- a/test/CodeGen/Mips/mips16ex.ll
+++ b/test/CodeGen/Mips/mips16ex.ll
@@ -1,6 +1,8 @@
; RUN: llc -march=mipsel -mcpu=mips16 -relocation-model=pic -O3 < %s | FileCheck %s -check-prefix=16
-;16: $eh_func_begin0=.
+;16: .cfi_personality
+;16-NEXT: [[TMP:.*]]:
+;16-NEXT: $eh_func_begin0 = ([[TMP]])
@.str = private unnamed_addr constant [7 x i8] c"hello\0A\00", align 1
@_ZTIi = external constant i8*
@.str1 = private unnamed_addr constant [15 x i8] c"exception %i \0A\00", align 1
diff --git a/test/CodeGen/Mips/mips64-f128.ll b/test/CodeGen/Mips/mips64-f128.ll
index 4d590b6..7f7d515 100644
--- a/test/CodeGen/Mips/mips64-f128.ll
+++ b/test/CodeGen/Mips/mips64-f128.ll
@@ -1,7 +1,11 @@
; RUN: llc -mtriple=mips64el-unknown-unknown -mcpu=mips4 -soft-float -O1 \
-; RUN: -disable-mips-delay-filler < %s | FileCheck %s
+; RUN: -disable-mips-delay-filler < %s | FileCheck %s -check-prefix=ALL -check-prefix=C_CC_FMT
; RUN: llc -mtriple=mips64el-unknown-unknown -mcpu=mips64 -soft-float -O1 \
-; RUN: -disable-mips-delay-filler < %s | FileCheck %s
+; RUN: -disable-mips-delay-filler < %s | FileCheck %s -check-prefix=ALL -check-prefix=C_CC_FMT
+; RUN: llc -mtriple=mips64el-unknown-unknown -mcpu=mips64r2 -soft-float -O1 \
+; RUN: -disable-mips-delay-filler < %s | FileCheck %s -check-prefix=ALL -check-prefix=C_CC_FMT
+; RUN: llc -mtriple=mips64el-unknown-unknown -mcpu=mips64r6 -soft-float -O1 \
+; RUN: -disable-mips-delay-filler < %s | FileCheck %s -check-prefix=ALL -check-prefix=CMP_CC_FMT
@gld0 = external global fp128
@gld1 = external global fp128
@@ -9,8 +13,8 @@
@gf1 = external global float
@gd1 = external global double
-; CHECK-LABEL: addLD:
-; CHECK: ld $25, %call16(__addtf3)
+; ALL-LABEL: addLD:
+; ALL: ld $25, %call16(__addtf3)
define fp128 @addLD() {
entry:
@@ -20,8 +24,8 @@ entry:
ret fp128 %add
}
-; CHECK-LABEL: subLD:
-; CHECK: ld $25, %call16(__subtf3)
+; ALL-LABEL: subLD:
+; ALL: ld $25, %call16(__subtf3)
define fp128 @subLD() {
entry:
@@ -31,8 +35,8 @@ entry:
ret fp128 %sub
}
-; CHECK-LABEL: mulLD:
-; CHECK: ld $25, %call16(__multf3)
+; ALL-LABEL: mulLD:
+; ALL: ld $25, %call16(__multf3)
define fp128 @mulLD() {
entry:
@@ -42,8 +46,8 @@ entry:
ret fp128 %mul
}
-; CHECK-LABEL: divLD:
-; CHECK: ld $25, %call16(__divtf3)
+; ALL-LABEL: divLD:
+; ALL: ld $25, %call16(__divtf3)
define fp128 @divLD() {
entry:
@@ -53,8 +57,8 @@ entry:
ret fp128 %div
}
-; CHECK-LABEL: conv_LD_char:
-; CHECK: ld $25, %call16(__floatsitf)
+; ALL-LABEL: conv_LD_char:
+; ALL: ld $25, %call16(__floatsitf)
define fp128 @conv_LD_char(i8 signext %a) {
entry:
@@ -62,8 +66,8 @@ entry:
ret fp128 %conv
}
-; CHECK-LABEL: conv_LD_short:
-; CHECK: ld $25, %call16(__floatsitf)
+; ALL-LABEL: conv_LD_short:
+; ALL: ld $25, %call16(__floatsitf)
define fp128 @conv_LD_short(i16 signext %a) {
entry:
@@ -71,8 +75,8 @@ entry:
ret fp128 %conv
}
-; CHECK-LABEL: conv_LD_int:
-; CHECK: ld $25, %call16(__floatsitf)
+; ALL-LABEL: conv_LD_int:
+; ALL: ld $25, %call16(__floatsitf)
define fp128 @conv_LD_int(i32 %a) {
entry:
@@ -80,8 +84,8 @@ entry:
ret fp128 %conv
}
-; CHECK-LABEL: conv_LD_LL:
-; CHECK: ld $25, %call16(__floatditf)
+; ALL-LABEL: conv_LD_LL:
+; ALL: ld $25, %call16(__floatditf)
define fp128 @conv_LD_LL(i64 %a) {
entry:
@@ -89,8 +93,8 @@ entry:
ret fp128 %conv
}
-; CHECK-LABEL: conv_LD_UChar:
-; CHECK: ld $25, %call16(__floatunsitf)
+; ALL-LABEL: conv_LD_UChar:
+; ALL: ld $25, %call16(__floatunsitf)
define fp128 @conv_LD_UChar(i8 zeroext %a) {
entry:
@@ -98,8 +102,8 @@ entry:
ret fp128 %conv
}
-; CHECK-LABEL: conv_LD_UShort:
-; CHECK: ld $25, %call16(__floatunsitf)
+; ALL-LABEL: conv_LD_UShort:
+; ALL: ld $25, %call16(__floatunsitf)
define fp128 @conv_LD_UShort(i16 zeroext %a) {
entry:
@@ -107,8 +111,8 @@ entry:
ret fp128 %conv
}
-; CHECK-LABEL: conv_LD_UInt:
-; CHECK: ld $25, %call16(__floatunsitf)
+; ALL-LABEL: conv_LD_UInt:
+; ALL: ld $25, %call16(__floatunsitf)
define fp128 @conv_LD_UInt(i32 %a) {
entry:
@@ -116,8 +120,8 @@ entry:
ret fp128 %conv
}
-; CHECK-LABEL: conv_LD_ULL:
-; CHECK: ld $25, %call16(__floatunditf)
+; ALL-LABEL: conv_LD_ULL:
+; ALL: ld $25, %call16(__floatunditf)
define fp128 @conv_LD_ULL(i64 %a) {
entry:
@@ -125,8 +129,8 @@ entry:
ret fp128 %conv
}
-; CHECK-LABEL: conv_char_LD:
-; CHECK: ld $25, %call16(__fixtfsi)
+; ALL-LABEL: conv_char_LD:
+; ALL: ld $25, %call16(__fixtfsi)
define signext i8 @conv_char_LD(fp128 %a) {
entry:
@@ -134,8 +138,8 @@ entry:
ret i8 %conv
}
-; CHECK-LABEL: conv_short_LD:
-; CHECK: ld $25, %call16(__fixtfsi)
+; ALL-LABEL: conv_short_LD:
+; ALL: ld $25, %call16(__fixtfsi)
define signext i16 @conv_short_LD(fp128 %a) {
entry:
@@ -143,8 +147,8 @@ entry:
ret i16 %conv
}
-; CHECK-LABEL: conv_int_LD:
-; CHECK: ld $25, %call16(__fixtfsi)
+; ALL-LABEL: conv_int_LD:
+; ALL: ld $25, %call16(__fixtfsi)
define i32 @conv_int_LD(fp128 %a) {
entry:
@@ -152,8 +156,8 @@ entry:
ret i32 %conv
}
-; CHECK-LABEL: conv_LL_LD:
-; CHECK: ld $25, %call16(__fixtfdi)
+; ALL-LABEL: conv_LL_LD:
+; ALL: ld $25, %call16(__fixtfdi)
define i64 @conv_LL_LD(fp128 %a) {
entry:
@@ -161,8 +165,8 @@ entry:
ret i64 %conv
}
-; CHECK-LABEL: conv_UChar_LD:
-; CHECK: ld $25, %call16(__fixtfsi)
+; ALL-LABEL: conv_UChar_LD:
+; ALL: ld $25, %call16(__fixtfsi)
define zeroext i8 @conv_UChar_LD(fp128 %a) {
entry:
@@ -170,8 +174,8 @@ entry:
ret i8 %conv
}
-; CHECK-LABEL: conv_UShort_LD:
-; CHECK: ld $25, %call16(__fixtfsi)
+; ALL-LABEL: conv_UShort_LD:
+; ALL: ld $25, %call16(__fixtfsi)
define zeroext i16 @conv_UShort_LD(fp128 %a) {
entry:
@@ -179,8 +183,8 @@ entry:
ret i16 %conv
}
-; CHECK-LABEL: conv_UInt_LD:
-; CHECK: ld $25, %call16(__fixunstfsi)
+; ALL-LABEL: conv_UInt_LD:
+; ALL: ld $25, %call16(__fixunstfsi)
define i32 @conv_UInt_LD(fp128 %a) {
entry:
@@ -188,8 +192,8 @@ entry:
ret i32 %conv
}
-; CHECK-LABEL: conv_ULL_LD:
-; CHECK: ld $25, %call16(__fixunstfdi)
+; ALL-LABEL: conv_ULL_LD:
+; ALL: ld $25, %call16(__fixunstfdi)
define i64 @conv_ULL_LD(fp128 %a) {
entry:
@@ -197,8 +201,8 @@ entry:
ret i64 %conv
}
-; CHECK-LABEL: conv_LD_float:
-; CHECK: ld $25, %call16(__extendsftf2)
+; ALL-LABEL: conv_LD_float:
+; ALL: ld $25, %call16(__extendsftf2)
define fp128 @conv_LD_float(float %a) {
entry:
@@ -206,8 +210,8 @@ entry:
ret fp128 %conv
}
-; CHECK-LABEL: conv_LD_double:
-; CHECK: ld $25, %call16(__extenddftf2)
+; ALL-LABEL: conv_LD_double:
+; ALL: ld $25, %call16(__extenddftf2)
define fp128 @conv_LD_double(double %a) {
entry:
@@ -215,8 +219,8 @@ entry:
ret fp128 %conv
}
-; CHECK-LABEL: conv_float_LD:
-; CHECK: ld $25, %call16(__trunctfsf2)
+; ALL-LABEL: conv_float_LD:
+; ALL: ld $25, %call16(__trunctfsf2)
define float @conv_float_LD(fp128 %a) {
entry:
@@ -224,8 +228,8 @@ entry:
ret float %conv
}
-; CHECK-LABEL: conv_double_LD:
-; CHECK: ld $25, %call16(__trunctfdf2)
+; ALL-LABEL: conv_double_LD:
+; ALL: ld $25, %call16(__trunctfdf2)
define double @conv_double_LD(fp128 %a) {
entry:
@@ -233,13 +237,13 @@ entry:
ret double %conv
}
-; CHECK-LABEL: libcall1_fabsl:
-; CHECK-DAG: ld $[[R0:[0-9]+]], 8($[[R4:[0-9]+]])
-; CHECK-DAG: daddiu $[[R1:[0-9]+]], $zero, 1
-; CHECK-DAG: dsll $[[R2:[0-9]+]], $[[R1]], 63
-; CHECK-DAG: daddiu $[[R3:[0-9]+]], $[[R2]], -1
-; CHECK-DAG: and $4, $[[R0]], $[[R3]]
-; CHECK-DAG: ld $2, 0($[[R4]])
+; ALL-LABEL: libcall1_fabsl:
+; ALL-DAG: ld $[[R0:[0-9]+]], 8($[[R4:[0-9]+]])
+; ALL-DAG: daddiu $[[R1:[0-9]+]], $zero, 1
+; ALL-DAG: dsll $[[R2:[0-9]+]], $[[R1]], 63
+; ALL-DAG: daddiu $[[R3:[0-9]+]], $[[R2]], -1
+; ALL-DAG: and $4, $[[R0]], $[[R3]]
+; ALL-DAG: ld $2, 0($[[R4]])
define fp128 @libcall1_fabsl() {
entry:
@@ -250,8 +254,8 @@ entry:
declare fp128 @fabsl(fp128) #1
-; CHECK-LABEL: libcall1_ceill:
-; CHECK: ld $25, %call16(ceill)
+; ALL-LABEL: libcall1_ceill:
+; ALL: ld $25, %call16(ceill)
define fp128 @libcall1_ceill() {
entry:
@@ -262,8 +266,8 @@ entry:
declare fp128 @ceill(fp128) #1
-; CHECK-LABEL: libcall1_sinl:
-; CHECK: ld $25, %call16(sinl)
+; ALL-LABEL: libcall1_sinl:
+; ALL: ld $25, %call16(sinl)
define fp128 @libcall1_sinl() {
entry:
@@ -274,8 +278,8 @@ entry:
declare fp128 @sinl(fp128) #2
-; CHECK-LABEL: libcall1_cosl:
-; CHECK: ld $25, %call16(cosl)
+; ALL-LABEL: libcall1_cosl:
+; ALL: ld $25, %call16(cosl)
define fp128 @libcall1_cosl() {
entry:
@@ -286,8 +290,8 @@ entry:
declare fp128 @cosl(fp128) #2
-; CHECK-LABEL: libcall1_expl:
-; CHECK: ld $25, %call16(expl)
+; ALL-LABEL: libcall1_expl:
+; ALL: ld $25, %call16(expl)
define fp128 @libcall1_expl() {
entry:
@@ -298,8 +302,8 @@ entry:
declare fp128 @expl(fp128) #2
-; CHECK-LABEL: libcall1_exp2l:
-; CHECK: ld $25, %call16(exp2l)
+; ALL-LABEL: libcall1_exp2l:
+; ALL: ld $25, %call16(exp2l)
define fp128 @libcall1_exp2l() {
entry:
@@ -310,8 +314,8 @@ entry:
declare fp128 @exp2l(fp128) #2
-; CHECK-LABEL: libcall1_logl:
-; CHECK: ld $25, %call16(logl)
+; ALL-LABEL: libcall1_logl:
+; ALL: ld $25, %call16(logl)
define fp128 @libcall1_logl() {
entry:
@@ -322,8 +326,8 @@ entry:
declare fp128 @logl(fp128) #2
-; CHECK-LABEL: libcall1_log2l:
-; CHECK: ld $25, %call16(log2l)
+; ALL-LABEL: libcall1_log2l:
+; ALL: ld $25, %call16(log2l)
define fp128 @libcall1_log2l() {
entry:
@@ -334,8 +338,8 @@ entry:
declare fp128 @log2l(fp128) #2
-; CHECK-LABEL: libcall1_log10l:
-; CHECK: ld $25, %call16(log10l)
+; ALL-LABEL: libcall1_log10l:
+; ALL: ld $25, %call16(log10l)
define fp128 @libcall1_log10l() {
entry:
@@ -346,8 +350,8 @@ entry:
declare fp128 @log10l(fp128) #2
-; CHECK-LABEL: libcall1_nearbyintl:
-; CHECK: ld $25, %call16(nearbyintl)
+; ALL-LABEL: libcall1_nearbyintl:
+; ALL: ld $25, %call16(nearbyintl)
define fp128 @libcall1_nearbyintl() {
entry:
@@ -358,8 +362,8 @@ entry:
declare fp128 @nearbyintl(fp128) #1
-; CHECK-LABEL: libcall1_floorl:
-; CHECK: ld $25, %call16(floorl)
+; ALL-LABEL: libcall1_floorl:
+; ALL: ld $25, %call16(floorl)
define fp128 @libcall1_floorl() {
entry:
@@ -370,8 +374,8 @@ entry:
declare fp128 @floorl(fp128) #1
-; CHECK-LABEL: libcall1_sqrtl:
-; CHECK: ld $25, %call16(sqrtl)
+; ALL-LABEL: libcall1_sqrtl:
+; ALL: ld $25, %call16(sqrtl)
define fp128 @libcall1_sqrtl() {
entry:
@@ -382,8 +386,8 @@ entry:
declare fp128 @sqrtl(fp128) #2
-; CHECK-LABEL: libcall1_rintl:
-; CHECK: ld $25, %call16(rintl)
+; ALL-LABEL: libcall1_rintl:
+; ALL: ld $25, %call16(rintl)
define fp128 @libcall1_rintl() {
entry:
@@ -394,8 +398,8 @@ entry:
declare fp128 @rintl(fp128) #1
-; CHECK-LABEL: libcall_powil:
-; CHECK: ld $25, %call16(__powitf2)
+; ALL-LABEL: libcall_powil:
+; ALL: ld $25, %call16(__powitf2)
define fp128 @libcall_powil(fp128 %a, i32 %b) {
entry:
@@ -405,18 +409,18 @@ entry:
declare fp128 @llvm.powi.f128(fp128, i32) #3
-; CHECK-LABEL: libcall2_copysignl:
-; CHECK-DAG: daddiu $[[R2:[0-9]+]], $zero, 1
-; CHECK-DAG: dsll $[[R3:[0-9]+]], $[[R2]], 63
-; CHECK-DAG: ld $[[R0:[0-9]+]], %got_disp(gld1)
-; CHECK-DAG: ld $[[R1:[0-9]+]], 8($[[R0]])
-; CHECK-DAG: and $[[R4:[0-9]+]], $[[R1]], $[[R3]]
-; CHECK-DAG: ld $[[R5:[0-9]+]], %got_disp(gld0)
-; CHECK-DAG: ld $[[R6:[0-9]+]], 8($[[R5]])
-; CHECK-DAG: daddiu $[[R7:[0-9]+]], $[[R3]], -1
-; CHECK-DAG: and $[[R8:[0-9]+]], $[[R6]], $[[R7]]
-; CHECK-DAG: or $4, $[[R8]], $[[R4]]
-; CHECK-DAG: ld $2, 0($[[R5]])
+; ALL-LABEL: libcall2_copysignl:
+; ALL-DAG: daddiu $[[R2:[0-9]+]], $zero, 1
+; ALL-DAG: dsll $[[R3:[0-9]+]], $[[R2]], 63
+; ALL-DAG: ld $[[R0:[0-9]+]], %got_disp(gld1)
+; ALL-DAG: ld $[[R1:[0-9]+]], 8($[[R0]])
+; ALL-DAG: and $[[R4:[0-9]+]], $[[R1]], $[[R3]]
+; ALL-DAG: ld $[[R5:[0-9]+]], %got_disp(gld0)
+; ALL-DAG: ld $[[R6:[0-9]+]], 8($[[R5]])
+; ALL-DAG: daddiu $[[R7:[0-9]+]], $[[R3]], -1
+; ALL-DAG: and $[[R8:[0-9]+]], $[[R6]], $[[R7]]
+; ALL-DAG: or $4, $[[R8]], $[[R4]]
+; ALL-DAG: ld $2, 0($[[R5]])
define fp128 @libcall2_copysignl() {
entry:
@@ -428,8 +432,8 @@ entry:
declare fp128 @copysignl(fp128, fp128) #1
-; CHECK-LABEL: libcall2_powl:
-; CHECK: ld $25, %call16(powl)
+; ALL-LABEL: libcall2_powl:
+; ALL: ld $25, %call16(powl)
define fp128 @libcall2_powl() {
entry:
@@ -441,8 +445,8 @@ entry:
declare fp128 @powl(fp128, fp128) #2
-; CHECK-LABEL: libcall2_fmodl:
-; CHECK: ld $25, %call16(fmodl)
+; ALL-LABEL: libcall2_fmodl:
+; ALL: ld $25, %call16(fmodl)
define fp128 @libcall2_fmodl() {
entry:
@@ -454,8 +458,8 @@ entry:
declare fp128 @fmodl(fp128, fp128) #2
-; CHECK-LABEL: libcall3_fmal:
-; CHECK: ld $25, %call16(fmal)
+; ALL-LABEL: libcall3_fmal:
+; ALL: ld $25, %call16(fmal)
define fp128 @libcall3_fmal() {
entry:
@@ -468,8 +472,8 @@ entry:
declare fp128 @llvm.fma.f128(fp128, fp128, fp128) #4
-; CHECK-LABEL: cmp_lt:
-; CHECK: ld $25, %call16(__lttf2)
+; ALL-LABEL: cmp_lt:
+; ALL: ld $25, %call16(__lttf2)
define i32 @cmp_lt(fp128 %a, fp128 %b) {
entry:
@@ -478,8 +482,8 @@ entry:
ret i32 %conv
}
-; CHECK-LABEL: cmp_le:
-; CHECK: ld $25, %call16(__letf2)
+; ALL-LABEL: cmp_le:
+; ALL: ld $25, %call16(__letf2)
define i32 @cmp_le(fp128 %a, fp128 %b) {
entry:
@@ -488,8 +492,8 @@ entry:
ret i32 %conv
}
-; CHECK-LABEL: cmp_gt:
-; CHECK: ld $25, %call16(__gttf2)
+; ALL-LABEL: cmp_gt:
+; ALL: ld $25, %call16(__gttf2)
define i32 @cmp_gt(fp128 %a, fp128 %b) {
entry:
@@ -498,8 +502,8 @@ entry:
ret i32 %conv
}
-; CHECK-LABEL: cmp_ge:
-; CHECK: ld $25, %call16(__getf2)
+; ALL-LABEL: cmp_ge:
+; ALL: ld $25, %call16(__getf2)
define i32 @cmp_ge(fp128 %a, fp128 %b) {
entry:
@@ -508,8 +512,8 @@ entry:
ret i32 %conv
}
-; CHECK-LABEL: cmp_eq:
-; CHECK: ld $25, %call16(__eqtf2)
+; ALL-LABEL: cmp_eq:
+; ALL: ld $25, %call16(__eqtf2)
define i32 @cmp_eq(fp128 %a, fp128 %b) {
entry:
@@ -518,8 +522,8 @@ entry:
ret i32 %conv
}
-; CHECK-LABEL: cmp_ne:
-; CHECK: ld $25, %call16(__netf2)
+; ALL-LABEL: cmp_ne:
+; ALL: ld $25, %call16(__netf2)
define i32 @cmp_ne(fp128 %a, fp128 %b) {
entry:
@@ -528,10 +532,10 @@ entry:
ret i32 %conv
}
-; CHECK-LABEL: load_LD_LD:
-; CHECK: ld $[[R0:[0-9]+]], %got_disp(gld1)
-; CHECK: ld $2, 0($[[R0]])
-; CHECK: ld $4, 8($[[R0]])
+; ALL-LABEL: load_LD_LD:
+; ALL: ld $[[R0:[0-9]+]], %got_disp(gld1)
+; ALL: ld $2, 0($[[R0]])
+; ALL: ld $4, 8($[[R0]])
define fp128 @load_LD_LD() {
entry:
@@ -539,11 +543,11 @@ entry:
ret fp128 %0
}
-; CHECK-LABEL: load_LD_float:
-; CHECK: ld $[[R0:[0-9]+]], %got_disp(gf1)
-; CHECK: lw $4, 0($[[R0]])
-; CHECK: ld $25, %call16(__extendsftf2)
-; CHECK: jalr $25
+; ALL-LABEL: load_LD_float:
+; ALL: ld $[[R0:[0-9]+]], %got_disp(gf1)
+; ALL: lw $4, 0($[[R0]])
+; ALL: ld $25, %call16(__extendsftf2)
+; ALL: jalr $25
define fp128 @load_LD_float() {
entry:
@@ -552,11 +556,11 @@ entry:
ret fp128 %conv
}
-; CHECK-LABEL: load_LD_double:
-; CHECK: ld $[[R0:[0-9]+]], %got_disp(gd1)
-; CHECK: ld $4, 0($[[R0]])
-; CHECK: ld $25, %call16(__extenddftf2)
-; CHECK: jalr $25
+; ALL-LABEL: load_LD_double:
+; ALL: ld $[[R0:[0-9]+]], %got_disp(gd1)
+; ALL: ld $4, 0($[[R0]])
+; ALL: ld $25, %call16(__extenddftf2)
+; ALL: jalr $25
define fp128 @load_LD_double() {
entry:
@@ -565,13 +569,13 @@ entry:
ret fp128 %conv
}
-; CHECK-LABEL: store_LD_LD:
-; CHECK: ld $[[R0:[0-9]+]], %got_disp(gld1)
-; CHECK: ld $[[R1:[0-9]+]], 0($[[R0]])
-; CHECK: ld $[[R2:[0-9]+]], 8($[[R0]])
-; CHECK: ld $[[R3:[0-9]+]], %got_disp(gld0)
-; CHECK: sd $[[R2]], 8($[[R3]])
-; CHECK: sd $[[R1]], 0($[[R3]])
+; ALL-LABEL: store_LD_LD:
+; ALL: ld $[[R0:[0-9]+]], %got_disp(gld1)
+; ALL: ld $[[R1:[0-9]+]], 0($[[R0]])
+; ALL: ld $[[R2:[0-9]+]], 8($[[R0]])
+; ALL: ld $[[R3:[0-9]+]], %got_disp(gld0)
+; ALL: sd $[[R2]], 8($[[R3]])
+; ALL: sd $[[R1]], 0($[[R3]])
define void @store_LD_LD() {
entry:
@@ -580,14 +584,14 @@ entry:
ret void
}
-; CHECK-LABEL: store_LD_float:
-; CHECK: ld $[[R0:[0-9]+]], %got_disp(gld1)
-; CHECK: ld $4, 0($[[R0]])
-; CHECK: ld $5, 8($[[R0]])
-; CHECK: ld $25, %call16(__trunctfsf2)
-; CHECK: jalr $25
-; CHECK: ld $[[R1:[0-9]+]], %got_disp(gf1)
-; CHECK: sw $2, 0($[[R1]])
+; ALL-LABEL: store_LD_float:
+; ALL: ld $[[R0:[0-9]+]], %got_disp(gld1)
+; ALL: ld $4, 0($[[R0]])
+; ALL: ld $5, 8($[[R0]])
+; ALL: ld $25, %call16(__trunctfsf2)
+; ALL: jalr $25
+; ALL: ld $[[R1:[0-9]+]], %got_disp(gf1)
+; ALL: sw $2, 0($[[R1]])
define void @store_LD_float() {
entry:
@@ -597,14 +601,14 @@ entry:
ret void
}
-; CHECK-LABEL: store_LD_double:
-; CHECK: ld $[[R0:[0-9]+]], %got_disp(gld1)
-; CHECK: ld $4, 0($[[R0]])
-; CHECK: ld $5, 8($[[R0]])
-; CHECK: ld $25, %call16(__trunctfdf2)
-; CHECK: jalr $25
-; CHECK: ld $[[R1:[0-9]+]], %got_disp(gd1)
-; CHECK: sd $2, 0($[[R1]])
+; ALL-LABEL: store_LD_double:
+; ALL: ld $[[R0:[0-9]+]], %got_disp(gld1)
+; ALL: ld $4, 0($[[R0]])
+; ALL: ld $5, 8($[[R0]])
+; ALL: ld $25, %call16(__trunctfdf2)
+; ALL: jalr $25
+; ALL: ld $[[R1:[0-9]+]], %got_disp(gd1)
+; ALL: sd $2, 0($[[R1]])
define void @store_LD_double() {
entry:
@@ -614,11 +618,22 @@ entry:
ret void
}
-; CHECK-LABEL: select_LD:
-; CHECK: movn $8, $6, $4
-; CHECK: movn $9, $7, $4
-; CHECK: move $2, $8
-; CHECK: move $4, $9
+; ALL-LABEL: select_LD:
+; C_CC_FMT: movn $8, $6, $4
+; C_CC_FMT: movn $9, $7, $4
+; C_CC_FMT: move $2, $8
+; C_CC_FMT: move $4, $9
+
+; FIXME: This sll works around an implementation detail in the code generator
+; (setcc's result is i32 so bits 32-63 are undefined). It's not really
+; needed.
+; CMP_CC_FMT-DAG: sll $[[CC:[0-9]+]], $4, 0
+; CMP_CC_FMT-DAG: seleqz $[[EQ1:[0-9]+]], $8, $[[CC]]
+; CMP_CC_FMT-DAG: selnez $[[NE1:[0-9]+]], $6, $[[CC]]
+; CMP_CC_FMT-DAG: or $2, $[[NE1]], $[[EQ1]]
+; CMP_CC_FMT-DAG: seleqz $[[EQ2:[0-9]+]], $9, $[[CC]]
+; CMP_CC_FMT-DAG: selnez $[[NE2:[0-9]+]], $7, $[[CC]]
+; CMP_CC_FMT-DAG: or $4, $[[NE2]], $[[EQ2]]
define fp128 @select_LD(i32 %a, i64, fp128 %b, fp128 %c) {
entry:
@@ -627,18 +642,27 @@ entry:
ret fp128 %cond
}
-; CHECK-LABEL: selectCC_LD:
-; CHECK: move $[[R0:[0-9]+]], $11
-; CHECK: move $[[R1:[0-9]+]], $10
-; CHECK: move $[[R2:[0-9]+]], $9
-; CHECK: move $[[R3:[0-9]+]], $8
-; CHECK: ld $25, %call16(__gttf2)($gp)
-; CHECK: jalr $25
-; CHECK: slti $1, $2, 1
-; CHECK: movz $[[R1]], $[[R3]], $1
-; CHECK: movz $[[R0]], $[[R2]], $1
-; CHECK: move $2, $[[R1]]
-; CHECK: move $4, $[[R0]]
+; ALL-LABEL: selectCC_LD:
+; ALL: move $[[R0:[0-9]+]], $11
+; ALL: move $[[R1:[0-9]+]], $10
+; ALL: move $[[R2:[0-9]+]], $9
+; ALL: move $[[R3:[0-9]+]], $8
+; ALL: ld $25, %call16(__gttf2)($gp)
+; ALL: jalr $25
+
+; C_CC_FMT: slti $[[CC:[0-9]+]], $2, 1
+; C_CC_FMT: movz $[[R1]], $[[R3]], $[[CC]]
+; C_CC_FMT: movz $[[R0]], $[[R2]], $[[CC]]
+; C_CC_FMT: move $2, $[[R1]]
+; C_CC_FMT: move $4, $[[R0]]
+
+; CMP_CC_FMT: slt $[[CC:[0-9]+]], $zero, $2
+; CMP_CC_FMT: seleqz $[[EQ1:[0-9]+]], $[[R1]], $[[CC]]
+; CMP_CC_FMT: selnez $[[NE1:[0-9]+]], $[[R3]], $[[CC]]
+; CMP_CC_FMT: or $2, $[[NE1]], $[[EQ1]]
+; CMP_CC_FMT: seleqz $[[EQ2:[0-9]+]], $[[R0]], $[[CC]]
+; CMP_CC_FMT: selnez $[[NE2:[0-9]+]], $[[R2]], $[[CC]]
+; CMP_CC_FMT: or $4, $[[NE2]], $[[EQ2]]
define fp128 @selectCC_LD(fp128 %a, fp128 %b, fp128 %c, fp128 %d) {
entry:
diff --git a/test/CodeGen/Mips/mips64-fp-indexed-ls.ll b/test/CodeGen/Mips/mips64-fp-indexed-ls.ll
deleted file mode 100644
index bbdc05c..0000000
--- a/test/CodeGen/Mips/mips64-fp-indexed-ls.ll
+++ /dev/null
@@ -1,110 +0,0 @@
-; RUN: llc -march=mips64el -mcpu=mips64r2 -mattr=n64 < %s | FileCheck %s
-
-%struct.S = type <{ [4 x float] }>
-%struct.S2 = type <{ [4 x double] }>
-%struct.S3 = type <{ i8, float }>
-
-@s = external global [4 x %struct.S]
-@gf = external global float
-@gd = external global double
-@s2 = external global [4 x %struct.S2]
-@s3 = external global %struct.S3
-
-define float @foo0(float* nocapture %b, i32 %o) nounwind readonly {
-entry:
-; CHECK: lwxc1
- %idxprom = zext i32 %o to i64
- %arrayidx = getelementptr inbounds float* %b, i64 %idxprom
- %0 = load float* %arrayidx, align 4
- ret float %0
-}
-
-define double @foo1(double* nocapture %b, i32 %o) nounwind readonly {
-entry:
-; CHECK: ldxc1
- %idxprom = zext i32 %o to i64
- %arrayidx = getelementptr inbounds double* %b, i64 %idxprom
- %0 = load double* %arrayidx, align 8
- ret double %0
-}
-
-define float @foo2(i32 %b, i32 %c) nounwind readonly {
-entry:
-; CHECK-NOT: luxc1
- %idxprom = zext i32 %c to i64
- %idxprom1 = zext i32 %b to i64
- %arrayidx2 = getelementptr inbounds [4 x %struct.S]* @s, i64 0, i64 %idxprom1, i32 0, i64 %idxprom
- %0 = load float* %arrayidx2, align 1
- ret float %0
-}
-
-define void @foo3(float* nocapture %b, i32 %o) nounwind {
-entry:
-; CHECK: swxc1
- %0 = load float* @gf, align 4
- %idxprom = zext i32 %o to i64
- %arrayidx = getelementptr inbounds float* %b, i64 %idxprom
- store float %0, float* %arrayidx, align 4
- ret void
-}
-
-define void @foo4(double* nocapture %b, i32 %o) nounwind {
-entry:
-; CHECK: sdxc1
- %0 = load double* @gd, align 8
- %idxprom = zext i32 %o to i64
- %arrayidx = getelementptr inbounds double* %b, i64 %idxprom
- store double %0, double* %arrayidx, align 8
- ret void
-}
-
-define void @foo5(i32 %b, i32 %c) nounwind {
-entry:
-; CHECK-NOT: suxc1
- %0 = load float* @gf, align 4
- %idxprom = zext i32 %c to i64
- %idxprom1 = zext i32 %b to i64
- %arrayidx2 = getelementptr inbounds [4 x %struct.S]* @s, i64 0, i64 %idxprom1, i32 0, i64 %idxprom
- store float %0, float* %arrayidx2, align 1
- ret void
-}
-
-define double @foo6(i32 %b, i32 %c) nounwind readonly {
-entry:
-; CHECK: foo6
-; CHECK-NOT: luxc1
- %idxprom = zext i32 %c to i64
- %idxprom1 = zext i32 %b to i64
- %arrayidx2 = getelementptr inbounds [4 x %struct.S2]* @s2, i64 0, i64 %idxprom1, i32 0, i64 %idxprom
- %0 = load double* %arrayidx2, align 1
- ret double %0
-}
-
-define void @foo7(i32 %b, i32 %c) nounwind {
-entry:
-; CHECK: foo7
-; CHECK-NOT: suxc1
- %0 = load double* @gd, align 8
- %idxprom = zext i32 %c to i64
- %idxprom1 = zext i32 %b to i64
- %arrayidx2 = getelementptr inbounds [4 x %struct.S2]* @s2, i64 0, i64 %idxprom1, i32 0, i64 %idxprom
- store double %0, double* %arrayidx2, align 1
- ret void
-}
-
-define float @foo8() nounwind readonly {
-entry:
-; CHECK: foo8
-; CHECK-NOT: luxc1
- %0 = load float* getelementptr inbounds (%struct.S3* @s3, i64 0, i32 1), align 1
- ret float %0
-}
-
-define void @foo9(float %f) nounwind {
-entry:
-; CHECK: foo9
-; CHECK-NOT: suxc1
- store float %f, float* getelementptr inbounds (%struct.S3* @s3, i64 0, i32 1), align 1
- ret void
-}
-
diff --git a/test/CodeGen/Mips/mips64countleading.ll b/test/CodeGen/Mips/mips64countleading.ll
deleted file mode 100644
index 252f323..0000000
--- a/test/CodeGen/Mips/mips64countleading.ll
+++ /dev/null
@@ -1,24 +0,0 @@
-; RUN: llc -march=mips64el -mcpu=mips4 < %s | FileCheck -check-prefix=CHECK -check-prefix=MIPS4 %s
-; RUN: llc -march=mips64el -mcpu=mips64 < %s | FileCheck -check-prefix=CHECK -check-prefix=MIPS64 %s
-
-define i64 @t1(i64 %X) nounwind readnone {
-entry:
-; CHECK-LABEL: t1:
-; MIPS4-NOT: dclz
-; MIPS64: dclz
- %tmp1 = tail call i64 @llvm.ctlz.i64(i64 %X, i1 true)
- ret i64 %tmp1
-}
-
-declare i64 @llvm.ctlz.i64(i64, i1) nounwind readnone
-
-define i64 @t3(i64 %X) nounwind readnone {
-entry:
-; CHECK-LABEL: t3:
-; MIPS4-NOT: dclo
-; MIPS64: dclo
- %neg = xor i64 %X, -1
- %tmp1 = tail call i64 @llvm.ctlz.i64(i64 %neg, i1 true)
- ret i64 %tmp1
-}
-
diff --git a/test/CodeGen/Mips/mips64instrs.ll b/test/CodeGen/Mips/mips64instrs.ll
index 58f11f1..ed617be 100644
--- a/test/CodeGen/Mips/mips64instrs.ll
+++ b/test/CodeGen/Mips/mips64instrs.ll
@@ -1,99 +1,128 @@
-; RUN: llc -march=mips64el -mcpu=mips4 -verify-machineinstrs < %s | FileCheck -check-prefix=CHECK -check-prefix=MIPS4 %s
-; RUN: llc -march=mips64el -mcpu=mips64 -verify-machineinstrs < %s | FileCheck -check-prefix=CHECK -check-prefix=MIPS64 %s
+; RUN: llc -march=mips64el -mcpu=mips4 -verify-machineinstrs < %s | FileCheck -check-prefix=ALL -check-prefix=MIPS4 -check-prefix=ACCMULDIV %s
+; RUN: llc -march=mips64el -mcpu=mips64 -verify-machineinstrs < %s | FileCheck -check-prefix=ALL -check-prefix=HAS-DCLO -check-prefix=ACCMULDIV %s
+; RUN: llc -march=mips64el -mcpu=mips64r2 -verify-machineinstrs < %s | FileCheck -check-prefix=ALL -check-prefix=HAS-DCLO -check-prefix=ACCMULDIV %s
+; RUN: llc -march=mips64el -mcpu=mips64r6 -verify-machineinstrs < %s | FileCheck -check-prefix=ALL -check-prefix=HAS-DCLO -check-prefix=GPRMULDIV %s
@gll0 = common global i64 0, align 8
@gll1 = common global i64 0, align 8
define i64 @f0(i64 %a0, i64 %a1) nounwind readnone {
entry:
-; CHECK: daddu
+; ALL-LABEL: f0:
+; ALL: daddu $2, ${{[45]}}, ${{[45]}}
%add = add nsw i64 %a1, %a0
ret i64 %add
}
define i64 @f1(i64 %a0, i64 %a1) nounwind readnone {
entry:
-; CHECK: dsubu
+; ALL-LABEL: f1:
+; ALL: dsubu $2, $4, $5
%sub = sub nsw i64 %a0, %a1
ret i64 %sub
}
define i64 @f4(i64 %a0, i64 %a1) nounwind readnone {
entry:
-; CHECK: and
+; ALL-LABEL: f4:
+; ALL: and $2, ${{[45]}}, ${{[45]}}
%and = and i64 %a1, %a0
ret i64 %and
}
define i64 @f5(i64 %a0, i64 %a1) nounwind readnone {
entry:
-; CHECK: or
+; ALL-LABEL: f5:
+; ALL: or $2, ${{[45]}}, ${{[45]}}
%or = or i64 %a1, %a0
ret i64 %or
}
define i64 @f6(i64 %a0, i64 %a1) nounwind readnone {
entry:
-; CHECK: xor
+; ALL-LABEL: f6:
+; ALL: xor $2, ${{[45]}}, ${{[45]}}
%xor = xor i64 %a1, %a0
ret i64 %xor
}
define i64 @f7(i64 %a0) nounwind readnone {
entry:
-; CHECK: daddiu ${{[0-9]+}}, ${{[0-9]+}}, 20
+; ALL-LABEL: f7:
+; ALL: daddiu $2, $4, 20
%add = add nsw i64 %a0, 20
ret i64 %add
}
define i64 @f8(i64 %a0) nounwind readnone {
entry:
-; CHECK: daddiu ${{[0-9]+}}, ${{[0-9]+}}, -20
+; ALL-LABEL: f8:
+; ALL: daddiu $2, $4, -20
%sub = add nsw i64 %a0, -20
ret i64 %sub
}
define i64 @f9(i64 %a0) nounwind readnone {
entry:
-; CHECK: andi ${{[0-9]+}}, ${{[0-9]+}}, 20
+; ALL-LABEL: f9:
+; ALL: andi $2, $4, 20
%and = and i64 %a0, 20
ret i64 %and
}
define i64 @f10(i64 %a0) nounwind readnone {
entry:
-; CHECK: ori ${{[0-9]+}}, ${{[0-9]+}}, 20
+; ALL-LABEL: f10:
+; ALL: ori $2, $4, 20
%or = or i64 %a0, 20
ret i64 %or
}
define i64 @f11(i64 %a0) nounwind readnone {
entry:
-; CHECK: xori ${{[0-9]+}}, ${{[0-9]+}}, 20
+; ALL-LABEL: f11:
+; ALL: xori $2, $4, 20
%xor = xor i64 %a0, 20
ret i64 %xor
}
define i64 @f12(i64 %a, i64 %b) nounwind readnone {
entry:
-; CHECK: mult
+; ALL-LABEL: f12:
+
+; ACCMULDIV: mult ${{[45]}}, ${{[45]}}
+; GPRMULDIV: dmul $2, ${{[45]}}, ${{[45]}}
+
%mul = mul nsw i64 %b, %a
ret i64 %mul
}
define i64 @f13(i64 %a, i64 %b) nounwind readnone {
entry:
-; CHECK: mult
+; ALL-LABEL: f13:
+
+; ACCMULDIV: mult ${{[45]}}, ${{[45]}}
+; GPRMULDIV: dmul $2, ${{[45]}}, ${{[45]}}
+
%mul = mul i64 %b, %a
ret i64 %mul
}
define i64 @f14(i64 %a, i64 %b) nounwind readnone {
entry:
-; CHECK-LABEL: f14:
-; CHECK: ddiv $zero, ${{[0-9]+}}, $[[R0:[0-9]+]]
-; CHECK: teq $[[R0]], $zero, 7
-; CHECK: mflo
+; ALL-LABEL: f14:
+; ALL-DAG: ld $[[P0:[0-9]+]], %got_disp(gll0)(
+; ALL-DAG: ld $[[P1:[0-9]+]], %got_disp(gll1)(
+; ALL-DAG: ld $[[T0:[0-9]+]], 0($[[P0]])
+; ALL-DAG: ld $[[T1:[0-9]+]], 0($[[P1]])
+
+; ACCMULDIV: ddiv $zero, $[[T0]], $[[T1]]
+; ACCMULDIV: teq $[[T1]], $zero, 7
+; ACCMULDIV: mflo $2
+
+; GPRMULDIV: ddiv $2, $[[T0]], $[[T1]]
+; GPRMULDIV: teq $[[T1]], $zero, 7
+
%0 = load i64* @gll0, align 8
%1 = load i64* @gll1, align 8
%div = sdiv i64 %0, %1
@@ -102,10 +131,19 @@ entry:
define i64 @f15() nounwind readnone {
entry:
-; CHECK-LABEL: f15:
-; CHECK: ddivu $zero, ${{[0-9]+}}, $[[R0:[0-9]+]]
-; CHECK: teq $[[R0]], $zero, 7
-; CHECK: mflo
+; ALL-LABEL: f15:
+; ALL-DAG: ld $[[P0:[0-9]+]], %got_disp(gll0)(
+; ALL-DAG: ld $[[P1:[0-9]+]], %got_disp(gll1)(
+; ALL-DAG: ld $[[T0:[0-9]+]], 0($[[P0]])
+; ALL-DAG: ld $[[T1:[0-9]+]], 0($[[P1]])
+
+; ACCMULDIV: ddivu $zero, $[[T0]], $[[T1]]
+; ACCMULDIV: teq $[[T1]], $zero, 7
+; ACCMULDIV: mflo $2
+
+; GPRMULDIV: ddivu $2, $[[T0]], $[[T1]]
+; GPRMULDIV: teq $[[T1]], $zero, 7
+
%0 = load i64* @gll0, align 8
%1 = load i64* @gll1, align 8
%div = udiv i64 %0, %1
@@ -114,20 +152,30 @@ entry:
define i64 @f16(i64 %a, i64 %b) nounwind readnone {
entry:
-; CHECK-LABEL: f16:
-; CHECK: ddiv $zero, ${{[0-9]+}}, $[[R0:[0-9]+]]
-; CHECK: teq $[[R0]], $zero, 7
-; CHECK: mfhi
+; ALL-LABEL: f16:
+
+; ACCMULDIV: ddiv $zero, $4, $5
+; ACCMULDIV: teq $5, $zero, 7
+; ACCMULDIV: mfhi $2
+
+; GPRMULDIV: dmod $2, $4, $5
+; GPRMULDIV: teq $5, $zero, 7
+
%rem = srem i64 %a, %b
ret i64 %rem
}
define i64 @f17(i64 %a, i64 %b) nounwind readnone {
entry:
-; CHECK-LABEL: f17:
-; CHECK: ddivu $zero, ${{[0-9]+}}, $[[R0:[0-9]+]]
-; CHECK: teq $[[R0]], $zero, 7
-; CHECK: mfhi
+; ALL-LABEL: f17:
+
+; ACCMULDIV: ddivu $zero, $4, $5
+; ACCMULDIV: teq $5, $zero, 7
+; ACCMULDIV: mfhi $2
+
+; GPRMULDIV: dmodu $2, $4, $5
+; GPRMULDIV: teq $5, $zero, 7
+
%rem = urem i64 %a, %b
ret i64 %rem
}
@@ -136,24 +184,26 @@ declare i64 @llvm.ctlz.i64(i64, i1) nounwind readnone
define i64 @f18(i64 %X) nounwind readnone {
entry:
-; CHECK-LABEL: f18:
+; ALL-LABEL: f18:
; The MIPS4 version is too long to reasonably test. At least check we don't get dclz
-; MIPS4-NOT: dclz
+; MIPS4-NOT: dclz
+
+; HAS-DCLO: dclz $2, $4
-; MIPS64: dclz $2, $4
%tmp1 = tail call i64 @llvm.ctlz.i64(i64 %X, i1 true)
ret i64 %tmp1
}
define i64 @f19(i64 %X) nounwind readnone {
entry:
-; CHECK-LABEL: f19:
+; ALL-LABEL: f19:
; The MIPS4 version is too long to reasonably test. At least check we don't get dclo
-; MIPS4-NOT: dclo
+; MIPS4-NOT: dclo
+
+; HAS-DCLO: dclo $2, $4
-; MIPS64: dclo $2, $4
%neg = xor i64 %X, -1
%tmp1 = tail call i64 @llvm.ctlz.i64(i64 %neg, i1 true)
ret i64 %tmp1
@@ -161,8 +211,8 @@ entry:
define i64 @f20(i64 %a, i64 %b) nounwind readnone {
entry:
-; CHECK-LABEL: f20:
-; CHECK: nor
+; ALL-LABEL: f20:
+; ALL: nor $2, ${{[45]}}, ${{[45]}}
%or = or i64 %b, %a
%neg = xor i64 %or, -1
ret i64 %neg
diff --git a/test/CodeGen/Mips/mips64muldiv.ll b/test/CodeGen/Mips/mips64muldiv.ll
index 39c73e9..32d05a9 100644
--- a/test/CodeGen/Mips/mips64muldiv.ll
+++ b/test/CodeGen/Mips/mips64muldiv.ll
@@ -1,50 +1,79 @@
-; RUN: llc -march=mips64el -mcpu=mips4 < %s | FileCheck %s
-; RUN: llc -march=mips64el -mcpu=mips64 < %s | FileCheck %s
+; RUN: llc -march=mips64el -mcpu=mips4 < %s | FileCheck %s -check-prefix=ALL -check-prefix=ACC
+; RUN: llc -march=mips64el -mcpu=mips64 < %s | FileCheck %s -check-prefix=ALL -check-prefix=ACC
+; RUN: llc -march=mips64el -mcpu=mips64r2 < %s | FileCheck %s -check-prefix=ALL -check-prefix=ACC
+; RUN: llc -march=mips64el -mcpu=mips64r6 < %s | FileCheck %s -check-prefix=ALL -check-prefix=GPR
+
+; FileCheck prefixes:
+; ALL - All targets
+; ACC - Targets with accumulator based mul/div (i.e. pre-MIPS32r6)
+; GPR - Targets with register based mul/div (i.e. MIPS32r6)
define i64 @m0(i64 %a0, i64 %a1) nounwind readnone {
entry:
-; CHECK: dmult
-; CHECK: mflo
+; ALL-LABEL: m0:
+; ACC: dmult ${{[45]}}, ${{[45]}}
+; ACC: mflo $2
+; GPR: dmul $2, ${{[45]}}, ${{[45]}}
%mul = mul i64 %a1, %a0
ret i64 %mul
}
define i64 @m1(i64 %a) nounwind readnone {
entry:
-; CHECK: dmult
-; CHECK: mfhi
+; ALL-LABEL: m1:
+; ALL: lui $[[T0:[0-9]+]], 21845
+; ALL: addiu $[[T0]], $[[T0]], 21845
+; ALL: dsll $[[T0]], $[[T0]], 16
+; ALL: addiu $[[T0]], $[[T0]], 21845
+; ALL: dsll $[[T0]], $[[T0]], 16
+; ALL: addiu $[[T0]], $[[T0]], 21846
+
+; ACC: dmult $4, $[[T0]]
+; ACC: mfhi $[[T1:[0-9]+]]
+; GPR: dmuh $[[T1:[0-9]+]], $4, $[[T0]]
+
+; ALL: dsrl $2, $[[T1]], 63
+; ALL: daddu $2, $[[T1]], $2
%div = sdiv i64 %a, 3
ret i64 %div
}
define i64 @d0(i64 %a0, i64 %a1) nounwind readnone {
entry:
-; CHECK: ddivu
-; CHECK: mflo
+; ALL-LABEL: d0:
+; ACC: ddivu $zero, $4, $5
+; ACC: mflo $2
+; GPR: ddivu $2, $4, $5
%div = udiv i64 %a0, %a1
ret i64 %div
}
define i64 @d1(i64 %a0, i64 %a1) nounwind readnone {
entry:
-; CHECK: ddiv
-; CHECK: mflo
+; ALL-LABEL: d1:
+; ACC: ddiv $zero, $4, $5
+; ACC: mflo $2
+; GPR: ddiv $2, $4, $5
%div = sdiv i64 %a0, %a1
ret i64 %div
}
define i64 @d2(i64 %a0, i64 %a1) nounwind readnone {
entry:
-; CHECK: ddivu
-; CHECK: mfhi
+; ALL-LABEL: d2:
+; ACC: ddivu $zero, $4, $5
+; ACC: mfhi $2
+; GPR: dmodu $2, $4, $5
%rem = urem i64 %a0, %a1
ret i64 %rem
}
define i64 @d3(i64 %a0, i64 %a1) nounwind readnone {
entry:
-; CHECK: ddiv
-; CHECK: mfhi
+; ALL-LABEL: d3:
+; ACC: ddiv $zero, $4, $5
+; ACC: mfhi $2
+; GPR: dmod $2, $4, $5
%rem = srem i64 %a0, %a1
ret i64 %rem
}
diff --git a/test/CodeGen/Mips/mno-ldc1-sdc1.ll b/test/CodeGen/Mips/mno-ldc1-sdc1.ll
index f4854f8..244b03d 100644
--- a/test/CodeGen/Mips/mno-ldc1-sdc1.ll
+++ b/test/CodeGen/Mips/mno-ldc1-sdc1.ll
@@ -1,33 +1,113 @@
-; RUN: llc -march=mipsel -relocation-model=pic -mno-ldc1-sdc1 -mcpu=mips32r2 \
-; RUN: < %s | FileCheck %s -check-prefix=LE-PIC
-; RUN: llc -march=mipsel -relocation-model=static -mno-ldc1-sdc1 < %s | \
-; RUN: FileCheck %s -check-prefix=LE-STATIC
-; RUN: llc -march=mips -relocation-model=pic -mno-ldc1-sdc1 < %s | \
-; RUN: FileCheck %s -check-prefix=BE-PIC
+; Check that [sl]dc1 are normally emitted. MIPS32r2 should have [sl]dxc1 too.
+; RUN: llc -march=mipsel -mcpu=mips32 < %s | \
+; RUN: FileCheck %s -check-prefix=ALL -check-prefix=32R1-LDC1
; RUN: llc -march=mipsel -mcpu=mips32r2 < %s | \
-; RUN: FileCheck %s -check-prefix=CHECK-LDC1-SDC1
+; RUN: FileCheck %s -check-prefix=ALL -check-prefix=32R2-LDXC1
+; RUN: llc -march=mipsel -mcpu=mips32r6 < %s | \
+; RUN: FileCheck %s -check-prefix=ALL -check-prefix=32R6-LDC1
+
+; Check that -mno-ldc1-sdc1 disables [sl]dc1
+; RUN: llc -march=mipsel -relocation-model=pic -mno-ldc1-sdc1 \
+; RUN: -mcpu=mips32 < %s | \
+; RUN: FileCheck %s -check-prefix=ALL -check-prefix=32R1 \
+; RUN: -check-prefix=32R1-LE -check-prefix=32R1-LE-PIC
+; RUN: llc -march=mipsel -relocation-model=pic -mno-ldc1-sdc1 \
+; RUN: -mcpu=mips32r2 < %s | \
+; RUN: FileCheck %s -check-prefix=ALL -check-prefix=32R2 \
+; RUN: -check-prefix=32R2-LE -check-prefix=32R2-LE-PIC
+; RUN: llc -march=mipsel -relocation-model=pic -mno-ldc1-sdc1 \
+; RUN: -mcpu=mips32r6 < %s | \
+; RUN: FileCheck %s -check-prefix=ALL -check-prefix=32R6 \
+; RUN: -check-prefix=32R6-LE -check-prefix=32R6-LE-PIC
+
+; Check again for big-endian
+; RUN: llc -march=mips -relocation-model=pic -mno-ldc1-sdc1 \
+; RUN: -mcpu=mips32 < %s | \
+; RUN: FileCheck %s -check-prefix=ALL -check-prefix=32R1 \
+; RUN: -check-prefix=32R1-BE -check-prefix=32R1-BE-PIC
+; RUN: llc -march=mips -relocation-model=pic -mno-ldc1-sdc1 \
+; RUN: -mcpu=mips32r2 < %s | \
+; RUN: FileCheck %s -check-prefix=ALL -check-prefix=32R2 \
+; RUN: -check-prefix=32R2-BE -check-prefix=32R2-BE-PIC
+; RUN: llc -march=mips -relocation-model=pic -mno-ldc1-sdc1 \
+; RUN: -mcpu=mips32r6 < %s | \
+; RUN: FileCheck %s -check-prefix=ALL -check-prefix=32R6 \
+; RUN: -check-prefix=32R6-BE -check-prefix=32R6-BE-PIC
+
+; Check again for the static relocation model
+; RUN: llc -march=mipsel -relocation-model=static -mno-ldc1-sdc1 \
+; RUN: -mcpu=mips32 < %s | \
+; RUN: FileCheck %s -check-prefix=ALL -check-prefix=32R1 \
+; RUN: -check-prefix=32R1-LE -check-prefix=32R1-LE-STATIC
+; RUN: llc -march=mipsel -relocation-model=static -mno-ldc1-sdc1 \
+; RUN: -mcpu=mips32r2 < %s | \
+; RUN: FileCheck %s -check-prefix=ALL -check-prefix=32R2 \
+; RUN: -check-prefix=32R2-LE -check-prefix=32R2-LE-STATIC
+; RUN: llc -march=mipsel -relocation-model=static -mno-ldc1-sdc1 \
+; RUN: -mcpu=mips32r6 < %s | \
+; RUN: FileCheck %s -check-prefix=ALL -check-prefix=32R6 \
+; RUN: -check-prefix=32R6-LE -check-prefix=32R6-LE-STATIC
@g0 = common global double 0.000000e+00, align 8
-; LE-PIC-LABEL: test_ldc1:
-; LE-PIC-DAG: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
-; LE-PIC-DAG: lw $[[R1:[0-9]+]], 4(${{[0-9]+}})
-; LE-PIC-DAG: mtc1 $[[R0]], $f0
-; LE-PIC-DAG: mtc1 $[[R1]], $f1
-; LE-STATIC-LABEL: test_ldc1:
-; LE-STATIC-DAG: lui $[[R0:[0-9]+]], %hi(g0)
-; LE-STATIC-DAG: lw $[[R1:[0-9]+]], %lo(g0)($[[R0]])
-; LE-STATIC-DAG: addiu $[[R2:[0-9]+]], $[[R0]], %lo(g0)
-; LE-STATIC-DAG: lw $[[R3:[0-9]+]], 4($[[R2]])
-; LE-STATIC-DAG: mtc1 $[[R1]], $f0
-; LE-STATIC-DAG: mtc1 $[[R3]], $f1
-; BE-PIC-LABEL: test_ldc1:
-; BE-PIC-DAG: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
-; BE-PIC-DAG: lw $[[R1:[0-9]+]], 4(${{[0-9]+}})
-; BE-PIC-DAG: mtc1 $[[R1]], $f0
-; BE-PIC-DAG: mtc1 $[[R0]], $f1
-; CHECK-LDC1-SDC1-LABEL: test_ldc1:
-; CHECK-LDC1-SDC1: ldc1 $f{{[0-9]+}}
+; ALL-LABEL: test_ldc1:
+
+; 32R1-LE-PIC-DAG: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 32R1-LE-PIC-DAG: lw $[[R1:[0-9]+]], 4(${{[0-9]+}})
+; 32R1-LE-PIC-DAG: mtc1 $[[R0]], $f0
+; 32R1-LE-PIC-DAG: mtc1 $[[R1]], $f1
+
+; 32R2-LE-PIC-DAG: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 32R2-LE-PIC-DAG: lw $[[R1:[0-9]+]], 4(${{[0-9]+}})
+; 32R2-LE-PIC-DAG: mtc1 $[[R0]], $f0
+; 32R2-LE-PIC-DAG: mthc1 $[[R1]], $f0
+
+; 32R6-LE-PIC-DAG: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 32R6-LE-PIC-DAG: lw $[[R1:[0-9]+]], 4(${{[0-9]+}})
+; 32R6-LE-PIC-DAG: mtc1 $[[R0]], $f0
+; 32R6-LE-PIC-DAG: mthc1 $[[R1]], $f0
+
+; 32R1-LE-STATIC-DAG: lui $[[R0:[0-9]+]], %hi(g0)
+; 32R1-LE-STATIC-DAG: lw $[[R1:[0-9]+]], %lo(g0)($[[R0]])
+; 32R1-LE-STATIC-DAG: addiu $[[R2:[0-9]+]], $[[R0]], %lo(g0)
+; 32R1-LE-STATIC-DAG: lw $[[R3:[0-9]+]], 4($[[R2]])
+; 32R1-LE-STATIC-DAG: mtc1 $[[R1]], $f0
+; 32R1-LE-STATIC-DAG: mtc1 $[[R3]], $f1
+
+; 32R2-LE-STATIC-DAG: lui $[[R0:[0-9]+]], %hi(g0)
+; 32R2-LE-STATIC-DAG: lw $[[R1:[0-9]+]], %lo(g0)($[[R0]])
+; 32R2-LE-STATIC-DAG: addiu $[[R2:[0-9]+]], $[[R0]], %lo(g0)
+; 32R2-LE-STATIC-DAG: lw $[[R3:[0-9]+]], 4($[[R2]])
+; 32R2-LE-STATIC-DAG: mtc1 $[[R1]], $f0
+; 32R2-LE-STATIC-DAG: mthc1 $[[R3]], $f0
+
+; 32R6-LE-STATIC-DAG: lui $[[R0:[0-9]+]], %hi(g0)
+; 32R6-LE-STATIC-DAG: lw $[[R1:[0-9]+]], %lo(g0)($[[R0]])
+; 32R6-LE-STATIC-DAG: addiu $[[R2:[0-9]+]], $[[R0]], %lo(g0)
+; 32R6-LE-STATIC-DAG: lw $[[R3:[0-9]+]], 4($[[R2]])
+; 32R6-LE-STATIC-DAG: mtc1 $[[R1]], $f0
+; 32R6-LE-STATIC-DAG: mthc1 $[[R3]], $f0
+
+; 32R1-BE-PIC-DAG: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 32R1-BE-PIC-DAG: lw $[[R1:[0-9]+]], 4(${{[0-9]+}})
+; 32R1-BE-PIC-DAG: mtc1 $[[R1]], $f0
+; 32R1-BE-PIC-DAG: mtc1 $[[R0]], $f1
+
+; 32R2-BE-PIC-DAG: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 32R2-BE-PIC-DAG: lw $[[R1:[0-9]+]], 4(${{[0-9]+}})
+; 32R2-BE-PIC-DAG: mtc1 $[[R1]], $f0
+; 32R2-BE-PIC-DAG: mthc1 $[[R0]], $f0
+
+; 32R6-BE-PIC-DAG: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 32R6-BE-PIC-DAG: lw $[[R1:[0-9]+]], 4(${{[0-9]+}})
+; 32R6-BE-PIC-DAG: mtc1 $[[R1]], $f0
+; 32R6-BE-PIC-DAG: mthc1 $[[R0]], $f0
+
+; 32R1-LDC1: ldc1 $f0, 0(${{[0-9]+}})
+
+; 32R2-LDXC1: ldc1 $f0, 0(${{[0-9]+}})
+
+; 32R6-LDC1: ldc1 $f0, 0(${{[0-9]+}})
define double @test_ldc1() {
entry:
@@ -35,25 +115,64 @@ entry:
ret double %0
}
-; LE-PIC-LABEL: test_sdc1:
-; LE-PIC-DAG: mfc1 $[[R0:[0-9]+]], $f12
-; LE-PIC-DAG: mfc1 $[[R1:[0-9]+]], $f13
-; LE-PIC-DAG: sw $[[R0]], 0(${{[0-9]+}})
-; LE-PIC-DAG: sw $[[R1]], 4(${{[0-9]+}})
-; LE-STATIC-LABEL: test_sdc1:
-; LE-STATIC-DAG: mfc1 $[[R0:[0-9]+]], $f12
-; LE-STATIC-DAG: mfc1 $[[R1:[0-9]+]], $f13
-; LE-STATIC-DAG: lui $[[R2:[0-9]+]], %hi(g0)
-; LE-STATIC-DAG: sw $[[R0]], %lo(g0)($[[R2]])
-; LE-STATIC-DAG: addiu $[[R3:[0-9]+]], $[[R2]], %lo(g0)
-; LE-STATIC-DAG: sw $[[R1]], 4($[[R3]])
-; BE-PIC-LABEL: test_sdc1:
-; BE-PIC-DAG: mfc1 $[[R0:[0-9]+]], $f12
-; BE-PIC-DAG: mfc1 $[[R1:[0-9]+]], $f13
-; BE-PIC-DAG: sw $[[R1]], 0(${{[0-9]+}})
-; BE-PIC-DAG: sw $[[R0]], 4(${{[0-9]+}})
-; CHECK-LDC1-SDC1-LABEL: test_sdc1:
-; CHECK-LDC1-SDC1: sdc1 $f{{[0-9]+}}
+; ALL-LABEL: test_sdc1:
+
+; 32R1-LE-PIC-DAG: mfc1 $[[R0:[0-9]+]], $f12
+; 32R1-LE-PIC-DAG: mfc1 $[[R1:[0-9]+]], $f13
+; 32R1-LE-PIC-DAG: sw $[[R0]], 0(${{[0-9]+}})
+; 32R1-LE-PIC-DAG: sw $[[R1]], 4(${{[0-9]+}})
+
+; 32R2-LE-PIC-DAG: mfc1 $[[R0:[0-9]+]], $f12
+; 32R2-LE-PIC-DAG: mfc1 $[[R1:[0-9]+]], $f13
+; 32R2-LE-PIC-DAG: sw $[[R0]], 0(${{[0-9]+}})
+; 32R2-LE-PIC-DAG: sw $[[R1]], 4(${{[0-9]+}})
+
+; 32R6-LE-PIC-DAG: mfc1 $[[R0:[0-9]+]], $f12
+; 32R6-LE-PIC-DAG: mfhc1 $[[R1:[0-9]+]], $f12
+; 32R6-LE-PIC-DAG: sw $[[R0]], 0(${{[0-9]+}})
+; 32R6-LE-PIC-DAG: sw $[[R1]], 4(${{[0-9]+}})
+
+; 32R1-LE-STATIC-DAG: mfc1 $[[R0:[0-9]+]], $f12
+; 32R1-LE-STATIC-DAG: mfc1 $[[R1:[0-9]+]], $f13
+; 32R1-LE-STATIC-DAG: lui $[[R2:[0-9]+]], %hi(g0)
+; 32R1-LE-STATIC-DAG: sw $[[R0]], %lo(g0)($[[R2]])
+; 32R1-LE-STATIC-DAG: addiu $[[R3:[0-9]+]], $[[R2]], %lo(g0)
+; 32R1-LE-STATIC-DAG: sw $[[R1]], 4($[[R3]])
+
+; 32R2-LE-STATIC-DAG: mfc1 $[[R0:[0-9]+]], $f12
+; 32R2-LE-STATIC-DAG: mfc1 $[[R1:[0-9]+]], $f13
+; 32R2-LE-STATIC-DAG: lui $[[R2:[0-9]+]], %hi(g0)
+; 32R2-LE-STATIC-DAG: sw $[[R0]], %lo(g0)($[[R2]])
+; 32R2-LE-STATIC-DAG: addiu $[[R3:[0-9]+]], $[[R2]], %lo(g0)
+; 32R2-LE-STATIC-DAG: sw $[[R1]], 4($[[R3]])
+
+; 32R6-LE-STATIC-DAG: mfc1 $[[R0:[0-9]+]], $f12
+; 32R6-LE-STATIC-DAG: mfhc1 $[[R1:[0-9]+]], $f12
+; 32R6-LE-STATIC-DAG: lui $[[R2:[0-9]+]], %hi(g0)
+; 32R6-LE-STATIC-DAG: sw $[[R0]], %lo(g0)($[[R2]])
+; 32R6-LE-STATIC-DAG: addiu $[[R3:[0-9]+]], $[[R2]], %lo(g0)
+; 32R6-LE-STATIC-DAG: sw $[[R1]], 4($[[R3]])
+
+; 32R1-BE-PIC-DAG: mfc1 $[[R0:[0-9]+]], $f12
+; 32R1-BE-PIC-DAG: mfc1 $[[R1:[0-9]+]], $f13
+; 32R1-BE-PIC-DAG: sw $[[R1]], 0(${{[0-9]+}})
+; 32R1-BE-PIC-DAG: sw $[[R0]], 4(${{[0-9]+}})
+
+; 32R2-BE-PIC-DAG: mfc1 $[[R0:[0-9]+]], $f12
+; 32R2-BE-PIC-DAG: mfc1 $[[R1:[0-9]+]], $f13
+; 32R2-BE-PIC-DAG: sw $[[R1]], 0(${{[0-9]+}})
+; 32R2-BE-PIC-DAG: sw $[[R0]], 4(${{[0-9]+}})
+
+; 32R6-BE-PIC-DAG: mfc1 $[[R0:[0-9]+]], $f12
+; 32R6-BE-PIC-DAG: mfhc1 $[[R1:[0-9]+]], $f12
+; 32R6-BE-PIC-DAG: sw $[[R1]], 0(${{[0-9]+}})
+; 32R6-BE-PIC-DAG: sw $[[R0]], 4(${{[0-9]+}})
+
+; 32R1-LDC1: sdc1 $f{{[0-9]+}}, 0(${{[0-9]+}})
+
+; 32R2-LDXC1: sdc1 $f{{[0-9]+}}, 0(${{[0-9]+}})
+
+; 32R6-LDC1: sdc1 $f{{[0-9]+}}, 0(${{[0-9]+}})
define void @test_sdc1(double %a) {
entry:
@@ -61,14 +180,35 @@ entry:
ret void
}
+; ALL-LABEL: test_ldxc1:
+
+; 32R1-LE-DAG: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 32R1-LE-DAG: lw $[[R1:[0-9]+]], 4(${{[0-9]+}})
+; 32R1-BE-DAG: lw $[[R0:[0-9]+]], 4(${{[0-9]+}})
+; 32R1-BE-DAG: lw $[[R1:[0-9]+]], 0(${{[0-9]+}})
+; 32R1-DAG: mtc1 $[[R0]], $f0
+; 32R1-DAG: mtc1 $[[R1]], $f1
+
+; 32R2-LE-DAG: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 32R2-LE-DAG: lw $[[R1:[0-9]+]], 4(${{[0-9]+}})
+; 32R2-BE-DAG: lw $[[R0:[0-9]+]], 4(${{[0-9]+}})
+; 32R2-BE-DAG: lw $[[R1:[0-9]+]], 0(${{[0-9]+}})
+; 32R2-DAG: mtc1 $[[R0]], $f0
+; 32R2-DAG: mthc1 $[[R1]], $f0
-; LE-PIC-LABEL: test_ldxc1:
-; LE-PIC-DAG: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
-; LE-PIC-DAG: lw $[[R1:[0-9]+]], 4(${{[0-9]+}})
-; LE-PIC-DAG: mtc1 $[[R0]], $f0
-; LE-PIC-DAG: mtc1 $[[R1]], $f1
-; CHECK-LDC1-SDC1-LABEL: test_ldxc1:
-; CHECK-LDC1-SDC1: ldxc1 $f{{[0-9]+}}
+; 32R6-LE-DAG: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 32R6-LE-DAG: lw $[[R1:[0-9]+]], 4(${{[0-9]+}})
+; 32R6-BE-DAG: lw $[[R0:[0-9]+]], 4(${{[0-9]+}})
+; 32R6-BE-DAG: lw $[[R1:[0-9]+]], 0(${{[0-9]+}})
+; 32R6-DAG: mtc1 $[[R0]], $f0
+; 32R6-DAG: mthc1 $[[R1]], $f0
+
+; 32R1-LDC1: ldc1 $f0, 0(${{[0-9]+}})
+
+; 32R2-LDXC1: sll $[[OFFSET:[0-9]+]], $5, 3
+; 32R2-LDXC1: ldxc1 $f0, $[[OFFSET]]($4)
+
+; 32R6-LDC1: ldc1 $f0, 0(${{[0-9]+}})
define double @test_ldxc1(double* nocapture readonly %a, i32 %i) {
entry:
@@ -77,13 +217,29 @@ entry:
ret double %0
}
-; LE-PIC-LABEL: test_sdxc1:
-; LE-PIC-DAG: mfc1 $[[R0:[0-9]+]], $f12
-; LE-PIC-DAG: mfc1 $[[R1:[0-9]+]], $f13
-; LE-PIC-DAG: sw $[[R0]], 0(${{[0-9]+}})
-; LE-PIC-DAG: sw $[[R1]], 4(${{[0-9]+}})
-; CHECK-LDC1-SDC1-LABEL: test_sdxc1:
-; CHECK-LDC1-SDC1: sdxc1 $f{{[0-9]+}}
+; ALL-LABEL: test_sdxc1:
+
+; 32R1-DAG: mfc1 $[[R0:[0-9]+]], $f12
+; 32R1-DAG: mfc1 $[[R1:[0-9]+]], $f13
+; 32R1-DAG: sw $[[R0]], 0(${{[0-9]+}})
+; 32R1-DAG: sw $[[R1]], 4(${{[0-9]+}})
+
+; 32R2-DAG: mfc1 $[[R0:[0-9]+]], $f12
+; 32R2-DAG: mfc1 $[[R1:[0-9]+]], $f13
+; 32R2-DAG: sw $[[R0]], 0(${{[0-9]+}})
+; 32R2-DAG: sw $[[R1]], 4(${{[0-9]+}})
+
+; 32R6-DAG: mfc1 $[[R0:[0-9]+]], $f12
+; 32R6-DAG: mfhc1 $[[R1:[0-9]+]], $f12
+; 32R6-DAG: sw $[[R0]], 0(${{[0-9]+}})
+; 32R6-DAG: sw $[[R1]], 4(${{[0-9]+}})
+
+; 32R1-LDC1: sdc1 $f{{[0-9]+}}, 0(${{[0-9]+}})
+
+; 32R2-LDXC1: sll $[[OFFSET:[0-9]+]], $7, 3
+; 32R2-LDXC1: sdxc1 $f{{[0-9]+}}, $[[OFFSET]]($6)
+
+; 32R6-LDC1: sdc1 $f{{[0-9]+}}, 0(${{[0-9]+}})
define void @test_sdxc1(double %b, double* nocapture %a, i32 %i) {
entry:
diff --git a/test/CodeGen/Mips/msa/special.ll b/test/CodeGen/Mips/msa/special.ll
index f65a14f..b9badf5 100644
--- a/test/CodeGen/Mips/msa/special.ll
+++ b/test/CodeGen/Mips/msa/special.ll
@@ -4,6 +4,10 @@
; RUN: FileCheck %s --check-prefix=MIPS32
; RUN: llc -march=mips64 -mcpu=mips64r2 -mattr=+msa,+fp64 < %s | \
; RUN: FileCheck %s --check-prefix=MIPS64
+; RUN: llc -march=mips -mcpu=mips32r6 -mattr=+msa < %s | \
+; RUN: FileCheck %s --check-prefix=MIPS32
+; RUN: llc -march=mips64 -mcpu=mips64r6 -mattr=+msa < %s | \
+; RUN: FileCheck %s --check-prefix=MIPS64
define i32 @llvm_mips_lsa_test(i32 %a, i32 %b) nounwind {
entry:
diff --git a/test/CodeGen/Mips/no-odd-spreg.ll b/test/CodeGen/Mips/no-odd-spreg.ll
new file mode 100644
index 0000000..b42ed6a
--- /dev/null
+++ b/test/CodeGen/Mips/no-odd-spreg.ll
@@ -0,0 +1,54 @@
+; RUN: llc -march=mipsel -mcpu=mips32 < %s | FileCheck %s -check-prefix=ALL -check-prefix=ODDSPREG
+; RUN: llc -march=mipsel -mcpu=mips32 -mattr=+nooddspreg < %s | FileCheck %s -check-prefix=ALL -check-prefix=NOODDSPREG
+; RUN: llc -march=mipsel -mcpu=mips32r6 -mattr=fp64 < %s | FileCheck %s -check-prefix=ALL -check-prefix=ODDSPREG
+; RUN: llc -march=mipsel -mcpu=mips32r6 -mattr=fp64,+nooddspreg < %s | FileCheck %s -check-prefix=ALL -check-prefix=NOODDSPREG
+
+; ODDSPREG: .module oddspreg
+; NOODDSPREG: .module nooddspreg
+
+define float @two_floats(float %a) {
+entry:
+ ; Clobber all except $f12 and $f13
+ ;
+ ; The intention is that if odd single precision registers are permitted, the
+ ; allocator will choose $f12 and $f13 to avoid the spill/reload.
+ ;
+ ; On the other hand, if odd single precision registers are not permitted, it
+ ; will be forced to spill/reload either %a or %0.
+
+ %0 = fadd float %a, 1.0
+ call void asm "# Clobber", "~{$f0},~{$f1},~{$f2},~{$f3},~{$f4},~{$f5},~{$f6},~{$f7},~{$f8},~{$f9},~{$f10},~{$f11},~{$f14},~{$f15},~{$f16},~{$f17},~{$f18},~{$f19},~{$f20},~{$f21},~{$f22},~{$f23},~{$f24},~{$f25},~{$f26},~{$f27},~{$f28},~{$f29},~{$f30},~{$f31}"()
+ %1 = fadd float %a, %0
+ ret float %1
+}
+
+; ALL-LABEL: two_floats:
+; ODDSPREG: add.s $f13, $f12, ${{f[0-9]+}}
+; ODDSPREG-NOT: swc1
+; ODDSPREG-NOT: lwc1
+; ODDSPREG: add.s $f0, $f12, $f13
+
+; NOODDSPREG: add.s $[[T0:f[0-9]*[02468]]], $f12, ${{f[0-9]+}}
+; NOODDSPREG: swc1 $[[T0]],
+; NOODDSPREG: lwc1 $[[T1:f[0-9]*[02468]]],
+; NOODDSPREG: add.s $f0, $f12, $[[T1]]
+
+define double @two_doubles(double %a) {
+entry:
+ ; Clobber all except $f12 and $f13
+ ;
+ ; -mno-odd-sp-reg doesn't need to affect double precision values so both cases
+ ; use $f12 and $f13.
+
+ %0 = fadd double %a, 1.0
+ call void asm "# Clobber", "~{$f0},~{$f1},~{$f2},~{$f3},~{$f4},~{$f5},~{$f6},~{$f7},~{$f8},~{$f9},~{$f10},~{$f11},~{$f14},~{$f15},~{$f16},~{$f17},~{$f18},~{$f19},~{$f20},~{$f21},~{$f22},~{$f23},~{$f24},~{$f25},~{$f26},~{$f27},~{$f28},~{$f29},~{$f30},~{$f31}"()
+ %1 = fadd double %a, %0
+ ret double %1
+}
+
+; ALL-LABEL: two_doubles:
+; ALL: add.d $[[T0:f[0-9]+]], $f12, ${{f[0-9]+}}
+; ALL: add.d $f0, $f12, $[[T0]]
+
+
+; INVALID: -mattr=+nooddspreg is not currently permitted for a 32-bit FPU register file (FR=0 mode).
diff --git a/test/CodeGen/Mips/null-streamer.ll b/test/CodeGen/Mips/null-streamer.ll
new file mode 100644
index 0000000..56cebbf
--- /dev/null
+++ b/test/CodeGen/Mips/null-streamer.ll
@@ -0,0 +1,7 @@
+; Test the null streamer with a terget streamer.
+; RUN: llc -O0 -filetype=null -mtriple=mips-linux < %s
+
+define i32 @main() {
+entry:
+ ret i32 0
+}
diff --git a/test/CodeGen/Mips/prevent-hoisting.ll b/test/CodeGen/Mips/prevent-hoisting.ll
new file mode 100644
index 0000000..da665c2
--- /dev/null
+++ b/test/CodeGen/Mips/prevent-hoisting.ll
@@ -0,0 +1,144 @@
+; RUN: llc -march=mipsel -O3 < %s | FileCheck %s
+
+
+; MIPS direct branches implicitly define register $at. This test makes sure that
+; code hoisting optimization (which moves identical instructions at the start of
+; two basic blocks to the common predecessor block) takes this into account and
+; doesn't move definition of $at to the predecessor block (which would make $at
+; live-in at the start of successor block).
+
+
+; CHECK-LABEL: readLumaCoeff8x8_CABAC
+
+; The check for "addiu" instruction is added so that we can match the correct "b" instruction.
+; CHECK: addiu ${{[0-9]+}}, $zero, -1
+; CHECK: b $[[BB0:BB[0-9_]+]]
+
+; Check that sll instruction that writes to $1 starts basic block.
+; CHECK: {{BB[0-9_#]+}}:
+; CHECK-NEXT: sll $1, $[[R0:[0-9]+]], 4
+
+; Check that identical sll instruction starts another basic block.
+; CHECK: [[BB0]]:
+; CHECK-NEXT: sll $1, $[[R0]], 4
+
+
+%struct.img_par = type { i32, i32, i32, i32, i32*, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, [16 x [16 x i16]], [6 x [32 x i32]], [16 x [16 x i32]], [4 x [12 x [4 x [4 x i32]]]], [16 x i32], i8**, i32*, i32***, i32**, i32, i32, i32, i32, %struct.Slice*, %struct.macroblock*, i32, i32, i32, i32, i32, i32, %struct.DecRefPicMarking_s*, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, [3 x i32], i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32***, i32***, i32****, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, [3 x [2 x i32]], [3 x [2 x i32]], i32, i32, i32, i32, %struct.timeb, %struct.timeb, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32 }
+%struct.Slice = type { i32, i32, i32, i32, i32, i32, i32, i32, i32, %struct.datapartition*, %struct.MotionInfoContexts*, %struct.TextureInfoContexts*, i32, i32*, i32*, i32*, i32, i32*, i32*, i32*, i32 (%struct.img_par*, %struct.inp_par*)*, i32, i32, i32, i32 }
+%struct.datapartition = type { %struct.Bitstream*, %struct.DecodingEnvironment, i32 (%struct.syntaxelement*, %struct.img_par*, %struct.datapartition*)* }
+%struct.Bitstream = type { i32, i32, i32, i32, i8*, i32 }
+%struct.DecodingEnvironment = type { i32, i32, i32, i32, i32, i8*, i32* }
+%struct.syntaxelement = type { i32, i32, i32, i32, i32, i32, i32, i32, void (i32, i32, i32*, i32*)*, void (%struct.syntaxelement*, %struct.img_par*, %struct.DecodingEnvironment*)* }
+%struct.MotionInfoContexts = type { [4 x [11 x %struct.BiContextType]], [2 x [9 x %struct.BiContextType]], [2 x [10 x %struct.BiContextType]], [2 x [6 x %struct.BiContextType]], [4 x %struct.BiContextType], [4 x %struct.BiContextType], [3 x %struct.BiContextType] }
+%struct.BiContextType = type { i16, i8 }
+%struct.TextureInfoContexts = type { [2 x %struct.BiContextType], [4 x %struct.BiContextType], [3 x [4 x %struct.BiContextType]], [10 x [4 x %struct.BiContextType]], [10 x [15 x %struct.BiContextType]], [10 x [15 x %struct.BiContextType]], [10 x [5 x %struct.BiContextType]], [10 x [5 x %struct.BiContextType]], [10 x [15 x %struct.BiContextType]], [10 x [15 x %struct.BiContextType]] }
+%struct.inp_par = type { [1000 x i8], [1000 x i8], [1000 x i8], i32, i32, i32, i32, i32, i32, i32, i32 }
+%struct.macroblock = type { i32, [2 x i32], i32, i32, %struct.macroblock*, %struct.macroblock*, i32, [2 x [4 x [4 x [2 x i32]]]], i32, i64, i64, i32, i32, [4 x i8], [4 x i8], i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32 }
+%struct.DecRefPicMarking_s = type { i32, i32, i32, i32, i32, %struct.DecRefPicMarking_s* }
+%struct.timeb = type { i32, i16, i16, i16 }
+
+@assignSE2partition = external global [0 x [20 x i32]]
+@FIELD_SCAN8x8 = external constant [64 x [2 x i8]]
+
+
+define void @readLumaCoeff8x8_CABAC(%struct.img_par* %img, i32 %b8) {
+
+ %1 = load i32* undef, align 4
+ br i1 false, label %2, label %3
+
+; <label>:2 ; preds = %0
+ br label %3
+
+; <label>:3 ; preds = %2, %0
+ br i1 undef, label %switch.lookup, label %4
+
+switch.lookup: ; preds = %3
+ br label %4
+
+; <label>:4 ; preds = %switch.lookup, %3
+ br i1 undef, label %5, label %6
+
+; <label>:5 ; preds = %4
+ br label %6
+
+; <label>:6 ; preds = %5, %4
+ %7 = phi [2 x i8]* [ getelementptr inbounds ([64 x [2 x i8]]* @FIELD_SCAN8x8, i32 0, i32 0), %4 ], [ null, %5 ]
+ br i1 undef, label %switch.lookup6, label %8
+
+switch.lookup6: ; preds = %6
+ br label %8
+
+; <label>:8 ; preds = %switch.lookup6, %6
+ br i1 undef, label %.loopexit, label %9
+
+; <label>:9 ; preds = %8
+ %10 = and i32 %b8, 1
+ %11 = shl nuw nsw i32 %10, 3
+ %12 = getelementptr inbounds %struct.Slice* null, i32 0, i32 9
+ br i1 undef, label %.preheader, label %.preheader11
+
+.preheader11: ; preds = %21, %9
+ %k.014 = phi i32 [ %27, %21 ], [ 0, %9 ]
+ %coef_ctr.013 = phi i32 [ %23, %21 ], [ -1, %9 ]
+ br i1 false, label %13, label %14
+
+; <label>:13 ; preds = %.preheader11
+ br label %15
+
+; <label>:14 ; preds = %.preheader11
+ br label %15
+
+; <label>:15 ; preds = %14, %13
+ %16 = getelementptr inbounds [0 x [20 x i32]]* @assignSE2partition, i32 0, i32 %1, i32 undef
+ %17 = load i32* %16, align 4
+ %18 = getelementptr inbounds %struct.datapartition* null, i32 %17, i32 2
+ %19 = load i32 (%struct.syntaxelement*, %struct.img_par*, %struct.datapartition*)** %18, align 4
+ %20 = call i32 %19(%struct.syntaxelement* undef, %struct.img_par* %img, %struct.datapartition* undef)
+ br i1 false, label %.loopexit, label %21
+
+; <label>:21 ; preds = %15
+ %22 = add i32 %coef_ctr.013, 1
+ %23 = add i32 %22, 0
+ %24 = getelementptr inbounds [2 x i8]* %7, i32 %23, i32 0
+ %25 = add nsw i32 0, %11
+ %26 = getelementptr inbounds %struct.img_par* %img, i32 0, i32 27, i32 undef, i32 %25
+ store i32 0, i32* %26, align 4
+ %27 = add nsw i32 %k.014, 1
+ %28 = icmp slt i32 %27, 65
+ br i1 %28, label %.preheader11, label %.loopexit
+
+.preheader: ; preds = %36, %9
+ %k.110 = phi i32 [ %45, %36 ], [ 0, %9 ]
+ %coef_ctr.29 = phi i32 [ %39, %36 ], [ -1, %9 ]
+ br i1 false, label %29, label %30
+
+; <label>:29 ; preds = %.preheader
+ br label %31
+
+; <label>:30 ; preds = %.preheader
+ br label %31
+
+; <label>:31 ; preds = %30, %29
+ %32 = getelementptr inbounds [0 x [20 x i32]]* @assignSE2partition, i32 0, i32 %1, i32 undef
+ %33 = load i32* %32, align 4
+ %34 = getelementptr inbounds %struct.datapartition* null, i32 %33
+ %35 = call i32 undef(%struct.syntaxelement* undef, %struct.img_par* %img, %struct.datapartition* %34)
+ br i1 false, label %.loopexit, label %36
+
+; <label>:36 ; preds = %31
+ %37 = load i32* undef, align 4
+ %38 = add i32 %coef_ctr.29, 1
+ %39 = add i32 %38, %37
+ %40 = getelementptr inbounds [2 x i8]* %7, i32 %39, i32 0
+ %41 = load i8* %40, align 1
+ %42 = zext i8 %41 to i32
+ %43 = add nsw i32 %42, %11
+ %44 = getelementptr inbounds %struct.img_par* %img, i32 0, i32 27, i32 undef, i32 %43
+ store i32 0, i32* %44, align 4
+ %45 = add nsw i32 %k.110, 1
+ %46 = icmp slt i32 %45, 65
+ br i1 %46, label %.preheader, label %.loopexit
+
+.loopexit: ; preds = %36, %31, %21, %15, %8
+ ret void
+}
diff --git a/test/CodeGen/Mips/select.ll b/test/CodeGen/Mips/select.ll
index 06e2a86..eb2198b 100644
--- a/test/CodeGen/Mips/select.ll
+++ b/test/CodeGen/Mips/select.ll
@@ -1,135 +1,705 @@
-; RUN: llc < %s -march=mipsel | FileCheck %s -check-prefix=CHECK
+; RUN: llc < %s -march=mipsel -mcpu=mips32 | FileCheck %s -check-prefix=ALL -check-prefix=32
+; RUN: llc < %s -march=mipsel -mcpu=mips32r2 | FileCheck %s -check-prefix=ALL -check-prefix=32R2
+; RUN: llc < %s -march=mipsel -mcpu=mips32r6 | FileCheck %s -check-prefix=ALL -check-prefix=32R6
+; RUN: llc < %s -march=mips64el -mcpu=mips64 | FileCheck %s -check-prefix=ALL -check-prefix=64
+; RUN: llc < %s -march=mips64el -mcpu=mips64r2 | FileCheck %s -check-prefix=ALL -check-prefix=64R2
+; RUN: llc < %s -march=mips64el -mcpu=mips64r6 | FileCheck %s -check-prefix=ALL -check-prefix=64R6
@d2 = external global double
@d3 = external global double
-define i32 @sel1(i32 %s, i32 %f0, i32 %f1) nounwind readnone {
+define i32 @i32_icmp_ne_i32_val(i32 %s, i32 %f0, i32 %f1) nounwind readnone {
entry:
-; CHECK: movn
+; ALL-LABEL: i32_icmp_ne_i32_val:
+
+; 32: movn $5, $6, $4
+; 32: move $2, $5
+
+; 32R2: movn $5, $6, $4
+; 32R2: move $2, $5
+
+; 32R6-DAG: seleqz $[[T0:[0-9]+]], $5, $4
+; 32R6-DAG: selnez $[[T1:[0-9]+]], $6, $4
+; 32R6: or $2, $[[T1]], $[[T0]]
+
+; 64: movn $5, $6, $4
+; 64: move $2, $5
+
+; 64R2: movn $5, $6, $4
+; 64R2: move $2, $5
+
+; 64R6-DAG: seleqz $[[T0:[0-9]+]], $5, $4
+; 64R6-DAG: selnez $[[T1:[0-9]+]], $6, $4
+; 64R6: or $2, $[[T1]], $[[T0]]
+
%tobool = icmp ne i32 %s, 0
%cond = select i1 %tobool, i32 %f1, i32 %f0
ret i32 %cond
}
-define float @sel2(i32 %s, float %f0, float %f1) nounwind readnone {
+define i64 @i32_icmp_ne_i64_val(i32 %s, i64 %f0, i64 %f1) nounwind readnone {
+entry:
+; ALL-LABEL: i32_icmp_ne_i64_val:
+
+; 32-DAG: lw $[[F1:[0-9]+]], 16($sp)
+; 32-DAG: movn $6, $[[F1]], $4
+; 32-DAG: lw $[[F1H:[0-9]+]], 20($sp)
+; 32: movn $7, $[[F1H]], $4
+; 32: move $2, $6
+; 32: move $3, $7
+
+; 32R2-DAG: lw $[[F1:[0-9]+]], 16($sp)
+; 32R2-DAG: movn $6, $[[F1]], $4
+; 32R2-DAG: lw $[[F1H:[0-9]+]], 20($sp)
+; 32R2: movn $7, $[[F1H]], $4
+; 32R2: move $2, $6
+; 32R2: move $3, $7
+
+; 32R6-DAG: lw $[[F1:[0-9]+]], 16($sp)
+; 32R6-DAG: seleqz $[[T0:[0-9]+]], $6, $4
+; 32R6-DAG: selnez $[[T1:[0-9]+]], $[[F1]], $4
+; 32R6: or $2, $[[T1]], $[[T0]]
+; 32R6-DAG: lw $[[F1H:[0-9]+]], 20($sp)
+; 32R6-DAG: seleqz $[[T0:[0-9]+]], $7, $4
+; 32R6-DAG: selnez $[[T1:[0-9]+]], $[[F1H]], $4
+; 32R6: or $3, $[[T1]], $[[T0]]
+
+; 64: movn $5, $6, $4
+; 64: move $2, $5
+
+; 64R2: movn $5, $6, $4
+; 64R2: move $2, $5
+
+; FIXME: This sll works around an implementation detail in the code generator
+; (setcc's result is i32 so bits 32-63 are undefined). It's not really
+; needed.
+; 64R6-DAG: sll $[[CC:[0-9]+]], $4, 0
+; 64R6-DAG: seleqz $[[T0:[0-9]+]], $5, $[[CC]]
+; 64R6-DAG: selnez $[[T1:[0-9]+]], $6, $[[CC]]
+; 64R6: or $2, $[[T1]], $[[T0]]
+
+ %tobool = icmp ne i32 %s, 0
+ %cond = select i1 %tobool, i64 %f1, i64 %f0
+ ret i64 %cond
+}
+
+define i64 @i64_icmp_ne_i64_val(i64 %s, i64 %f0, i64 %f1) nounwind readnone {
entry:
-; CHECK: movn.s
+; ALL-LABEL: i64_icmp_ne_i64_val:
+
+; 32-DAG: or $[[CC:[0-9]+]], $4
+; 32-DAG: lw $[[F1:[0-9]+]], 16($sp)
+; 32-DAG: movn $6, $[[F1]], $[[CC]]
+; 32-DAG: lw $[[F1H:[0-9]+]], 20($sp)
+; 32: movn $7, $[[F1H]], $[[CC]]
+; 32: move $2, $6
+; 32: move $3, $7
+
+; 32R2-DAG: or $[[CC:[0-9]+]], $4
+; 32R2-DAG: lw $[[F1:[0-9]+]], 16($sp)
+; 32R2-DAG: movn $6, $[[F1]], $[[CC]]
+; 32R2-DAG: lw $[[F1H:[0-9]+]], 20($sp)
+; 32R2: movn $7, $[[F1H]], $[[CC]]
+; 32R2: move $2, $6
+; 32R2: move $3, $7
+
+; 32R6-DAG: lw $[[F1:[0-9]+]], 16($sp)
+; 32R6-DAG: or $[[T2:[0-9]+]], $4, $5
+; 32R6-DAG: seleqz $[[T0:[0-9]+]], $6, $[[T2]]
+; 32R6-DAG: selnez $[[T1:[0-9]+]], $[[F1]], $[[T2]]
+; 32R6: or $2, $[[T1]], $[[T0]]
+; 32R6-DAG: lw $[[F1H:[0-9]+]], 20($sp)
+; 32R6-DAG: seleqz $[[T0:[0-9]+]], $7, $[[T2]]
+; 32R6-DAG: selnez $[[T1:[0-9]+]], $[[F1H]], $[[T2]]
+; 32R6: or $3, $[[T1]], $[[T0]]
+
+; 64: movn $5, $6, $4
+; 64: move $2, $5
+
+; 64R2: movn $5, $6, $4
+; 64R2: move $2, $5
+
+; 64R6-DAG: seleqz $[[T0:[0-9]+]], $5, $4
+; 64R6-DAG: selnez $[[T1:[0-9]+]], $6, $4
+; 64R6: or $2, $[[T1]], $[[T0]]
+
+ %tobool = icmp ne i64 %s, 0
+ %cond = select i1 %tobool, i64 %f1, i64 %f0
+ ret i64 %cond
+}
+
+define float @i32_icmp_ne_f32_val(i32 %s, float %f0, float %f1) nounwind readnone {
+entry:
+; ALL-LABEL: i32_icmp_ne_f32_val:
+
+; 32-DAG: mtc1 $5, $[[F0:f[0-9]+]]
+; 32-DAG: mtc1 $6, $[[F1:f0]]
+; 32: movn.s $[[F1]], $[[F0]], $4
+
+; 32R2-DAG: mtc1 $5, $[[F0:f[0-9]+]]
+; 32R2-DAG: mtc1 $6, $[[F1:f0]]
+; 32R2: movn.s $[[F1]], $[[F0]], $4
+
+; 32R6-DAG: mtc1 $5, $[[F0:f[0-9]+]]
+; 32R6-DAG: mtc1 $6, $[[F1:f[0-9]+]]
+; 32R6: sltu $[[T0:[0-9]+]], $zero, $4
+; 32R6: mtc1 $[[T0]], $[[CC:f0]]
+; 32R6: sel.s $[[CC]], $[[F1]], $[[F0]]
+
+; 64: movn.s $f14, $f13, $4
+; 64: mov.s $f0, $f14
+
+; 64R2: movn.s $f14, $f13, $4
+; 64R2: mov.s $f0, $f14
+
+; 64R6: sltu $[[T0:[0-9]+]], $zero, $4
+; 64R6: mtc1 $[[T0]], $[[CC:f0]]
+; 64R6: sel.s $[[CC]], $f14, $f13
+
%tobool = icmp ne i32 %s, 0
%cond = select i1 %tobool, float %f0, float %f1
ret float %cond
}
-define double @sel2_1(i32 %s, double %f0, double %f1) nounwind readnone {
+define double @i32_icmp_ne_f64_val(i32 %s, double %f0, double %f1) nounwind readnone {
entry:
-; CHECK: movn.d
+; ALL-LABEL: i32_icmp_ne_f64_val:
+
+; 32-DAG: mtc1 $6, $[[F0:f[1-3]*[02468]+]]
+; 32-DAG: mtc1 $7, $[[F0H:f[1-3]*[13579]+]]
+; 32-DAG: ldc1 $[[F1:f0]], 16($sp)
+; 32: movn.d $[[F1]], $[[F0]], $4
+
+; 32R2-DAG: mtc1 $6, $[[F0:f[0-9]+]]
+; 32R2-DAG: mthc1 $7, $[[F0]]
+; 32R2-DAG: ldc1 $[[F1:f0]], 16($sp)
+; 32R2: movn.d $[[F1]], $[[F0]], $4
+
+; 32R6-DAG: mtc1 $6, $[[F0:f[0-9]+]]
+; 32R6-DAG: mthc1 $7, $[[F0]]
+; 32R6-DAG: sltu $[[T0:[0-9]+]], $zero, $4
+; 32R6-DAG: mtc1 $[[T0]], $[[CC:f0]]
+; 32R6-DAG: ldc1 $[[F1:f[0-9]+]], 16($sp)
+; 32R6: sel.d $[[CC]], $[[F1]], $[[F0]]
+
+; 64: movn.d $f14, $f13, $4
+; 64: mov.d $f0, $f14
+
+; 64R2: movn.d $f14, $f13, $4
+; 64R2: mov.d $f0, $f14
+
+; 64R6-DAG: sltu $[[T0:[0-9]+]], $zero, $4
+; 64R6-DAG: mtc1 $[[T0]], $[[CC:f0]]
+; 64R6: sel.d $[[CC]], $f14, $f13
+
%tobool = icmp ne i32 %s, 0
%cond = select i1 %tobool, double %f0, double %f1
ret double %cond
}
-define float @sel3(float %f0, float %f1, float %f2, float %f3) nounwind readnone {
+define float @f32_fcmp_oeq_f32_val(float %f0, float %f1, float %f2, float %f3) nounwind readnone {
entry:
-; CHECK: c.eq.s
-; CHECK: movt.s
+; ALL-LABEL: f32_fcmp_oeq_f32_val:
+
+; 32-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32: c.eq.s $[[F2]], $[[F3]]
+; 32: movt.s $f14, $f12, $fcc0
+; 32: mov.s $f0, $f14
+
+; 32R2-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32R2-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32R2: c.eq.s $[[F2]], $[[F3]]
+; 32R2: movt.s $f14, $f12, $fcc0
+; 32R2: mov.s $f0, $f14
+
+; 32R6-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32R6-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32R6: cmp.eq.s $[[CC:f0]], $[[F2]], $[[F3]]
+; 32R6: sel.s $[[CC]], $f14, $f12
+
+; 64: c.eq.s $f14, $f15
+; 64: movt.s $f13, $f12, $fcc0
+; 64: mov.s $f0, $f13
+
+; 64R2: c.eq.s $f14, $f15
+; 64R2: movt.s $f13, $f12, $fcc0
+; 64R2: mov.s $f0, $f13
+
+; 64R6: cmp.eq.s $[[CC:f0]], $f14, $f15
+; 64R6: sel.s $[[CC]], $f13, $f12
+
%cmp = fcmp oeq float %f2, %f3
%cond = select i1 %cmp, float %f0, float %f1
ret float %cond
}
-define float @sel4(float %f0, float %f1, float %f2, float %f3) nounwind readnone {
+define float @f32_fcmp_olt_f32_val(float %f0, float %f1, float %f2, float %f3) nounwind readnone {
entry:
-; CHECK: c.olt.s
-; CHECK: movt.s
+; ALL-LABEL: f32_fcmp_olt_f32_val:
+
+; 32-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32: c.olt.s $[[F2]], $[[F3]]
+; 32: movt.s $f14, $f12, $fcc0
+; 32: mov.s $f0, $f14
+
+; 32R2-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32R2-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32R2: c.olt.s $[[F2]], $[[F3]]
+; 32R2: movt.s $f14, $f12, $fcc0
+; 32R2: mov.s $f0, $f14
+
+; 32R6-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32R6-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32R6: cmp.lt.s $[[CC:f0]], $[[F2]], $[[F3]]
+; 32R6: sel.s $[[CC]], $f14, $f12
+
+; 64: c.olt.s $f14, $f15
+; 64: movt.s $f13, $f12, $fcc0
+; 64: mov.s $f0, $f13
+
+; 64R2: c.olt.s $f14, $f15
+; 64R2: movt.s $f13, $f12, $fcc0
+; 64R2: mov.s $f0, $f13
+
+; 64R6: cmp.lt.s $[[CC:f0]], $f14, $f15
+; 64R6: sel.s $[[CC]], $f13, $f12
+
%cmp = fcmp olt float %f2, %f3
%cond = select i1 %cmp, float %f0, float %f1
ret float %cond
}
-define float @sel5(float %f0, float %f1, float %f2, float %f3) nounwind readnone {
+define float @f32_fcmp_ogt_f32_val(float %f0, float %f1, float %f2, float %f3) nounwind readnone {
entry:
-; CHECK: c.ule.s
-; CHECK: movf.s
+; ALL-LABEL: f32_fcmp_ogt_f32_val:
+
+; 32-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32: c.ule.s $[[F2]], $[[F3]]
+; 32: movf.s $f14, $f12, $fcc0
+; 32: mov.s $f0, $f14
+
+; 32R2-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32R2-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32R2: c.ule.s $[[F2]], $[[F3]]
+; 32R2: movf.s $f14, $f12, $fcc0
+; 32R2: mov.s $f0, $f14
+
+; 32R6-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32R6-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32R6: cmp.lt.s $[[CC:f0]], $[[F3]], $[[F2]]
+; 32R6: sel.s $[[CC]], $f14, $f12
+
+; 64: c.ule.s $f14, $f15
+; 64: movf.s $f13, $f12, $fcc0
+; 64: mov.s $f0, $f13
+
+; 64R2: c.ule.s $f14, $f15
+; 64R2: movf.s $f13, $f12, $fcc0
+; 64R2: mov.s $f0, $f13
+
+; 64R6: cmp.lt.s $[[CC:f0]], $f15, $f14
+; 64R6: sel.s $[[CC]], $f13, $f12
+
%cmp = fcmp ogt float %f2, %f3
%cond = select i1 %cmp, float %f0, float %f1
ret float %cond
}
-define double @sel5_1(double %f0, double %f1, float %f2, float %f3) nounwind readnone {
+define double @f32_fcmp_ogt_f64_val(double %f0, double %f1, float %f2, float %f3) nounwind readnone {
entry:
-; CHECK: c.ule.s
-; CHECK: movf.d
+; ALL-LABEL: f32_fcmp_ogt_f64_val:
+
+; 32-DAG: lwc1 $[[F2:f[0-9]+]], 16($sp)
+; 32-DAG: lwc1 $[[F3:f[0-9]+]], 20($sp)
+; 32: c.ule.s $[[F2]], $[[F3]]
+; 32: movf.d $f14, $f12, $fcc0
+; 32: mov.d $f0, $f14
+
+; 32R2-DAG: lwc1 $[[F2:f[0-9]+]], 16($sp)
+; 32R2-DAG: lwc1 $[[F3:f[0-9]+]], 20($sp)
+; 32R2: c.ule.s $[[F2]], $[[F3]]
+; 32R2: movf.d $f14, $f12, $fcc0
+; 32R2: mov.d $f0, $f14
+
+; 32R6-DAG: lwc1 $[[F2:f[0-9]+]], 16($sp)
+; 32R6-DAG: lwc1 $[[F3:f[0-9]+]], 20($sp)
+; 32R6: cmp.lt.s $[[CC:f0]], $[[F3]], $[[F2]]
+; 32R6: sel.d $[[CC]], $f14, $f12
+
+; 64: c.ule.s $f14, $f15
+; 64: movf.d $f13, $f12, $fcc0
+; 64: mov.d $f0, $f13
+
+; 64R2: c.ule.s $f14, $f15
+; 64R2: movf.d $f13, $f12, $fcc0
+; 64R2: mov.d $f0, $f13
+
+; 64R6: cmp.lt.s $[[CC:f0]], $f15, $f14
+; 64R6: sel.d $[[CC]], $f13, $f12
+
%cmp = fcmp ogt float %f2, %f3
%cond = select i1 %cmp, double %f0, double %f1
ret double %cond
}
-define double @sel6(double %f0, double %f1, double %f2, double %f3) nounwind readnone {
+define double @f64_fcmp_oeq_f64_val(double %f0, double %f1, double %f2, double %f3) nounwind readnone {
entry:
-; CHECK: c.eq.d
-; CHECK: movt.d
+; ALL-LABEL: f64_fcmp_oeq_f64_val:
+
+; 32-DAG: ldc1 $[[F2:f[0-9]+]], 16($sp)
+; 32-DAG: ldc1 $[[F3:f[0-9]+]], 24($sp)
+; 32: c.eq.d $[[F2]], $[[F3]]
+; 32: movt.d $f14, $f12, $fcc0
+; 32: mov.d $f0, $f14
+
+; 32R2-DAG: ldc1 $[[F2:f[0-9]+]], 16($sp)
+; 32R2-DAG: ldc1 $[[F3:f[0-9]+]], 24($sp)
+; 32R2: c.eq.d $[[F2]], $[[F3]]
+; 32R2: movt.d $f14, $f12, $fcc0
+; 32R2: mov.d $f0, $f14
+
+; 32R6-DAG: ldc1 $[[F2:f[0-9]+]], 16($sp)
+; 32R6-DAG: ldc1 $[[F3:f[0-9]+]], 24($sp)
+; 32R6: cmp.eq.d $[[CC:f0]], $[[F2]], $[[F3]]
+; 32R6: sel.d $[[CC]], $f14, $f12
+
+; 64: c.eq.d $f14, $f15
+; 64: movt.d $f13, $f12, $fcc0
+; 64: mov.d $f0, $f13
+
+; 64R2: c.eq.d $f14, $f15
+; 64R2: movt.d $f13, $f12, $fcc0
+; 64R2: mov.d $f0, $f13
+
+; 64R6: cmp.eq.d $[[CC:f0]], $f14, $f15
+; 64R6: sel.d $[[CC]], $f13, $f12
+
%cmp = fcmp oeq double %f2, %f3
%cond = select i1 %cmp, double %f0, double %f1
ret double %cond
}
-define double @sel7(double %f0, double %f1, double %f2, double %f3) nounwind readnone {
+define double @f64_fcmp_olt_f64_val(double %f0, double %f1, double %f2, double %f3) nounwind readnone {
entry:
-; CHECK: c.olt.d
-; CHECK: movt.d
+; ALL-LABEL: f64_fcmp_olt_f64_val:
+
+; 32-DAG: ldc1 $[[F2:f[0-9]+]], 16($sp)
+; 32-DAG: ldc1 $[[F3:f[0-9]+]], 24($sp)
+; 32: c.olt.d $[[F2]], $[[F3]]
+; 32: movt.d $f14, $f12, $fcc0
+; 32: mov.d $f0, $f14
+
+; 32R2-DAG: ldc1 $[[F2:f[0-9]+]], 16($sp)
+; 32R2-DAG: ldc1 $[[F3:f[0-9]+]], 24($sp)
+; 32R2: c.olt.d $[[F2]], $[[F3]]
+; 32R2: movt.d $f14, $f12, $fcc0
+; 32R2: mov.d $f0, $f14
+
+; 32R6-DAG: ldc1 $[[F2:f[0-9]+]], 16($sp)
+; 32R6-DAG: ldc1 $[[F3:f[0-9]+]], 24($sp)
+; 32R6: cmp.lt.d $[[CC:f0]], $[[F2]], $[[F3]]
+; 32R6: sel.d $[[CC]], $f14, $f12
+
+; 64: c.olt.d $f14, $f15
+; 64: movt.d $f13, $f12, $fcc0
+; 64: mov.d $f0, $f13
+
+; 64R2: c.olt.d $f14, $f15
+; 64R2: movt.d $f13, $f12, $fcc0
+; 64R2: mov.d $f0, $f13
+
+; 64R6: cmp.lt.d $[[CC:f0]], $f14, $f15
+; 64R6: sel.d $[[CC]], $f13, $f12
+
%cmp = fcmp olt double %f2, %f3
%cond = select i1 %cmp, double %f0, double %f1
ret double %cond
}
-define double @sel8(double %f0, double %f1, double %f2, double %f3) nounwind readnone {
+define double @f64_fcmp_ogt_f64_val(double %f0, double %f1, double %f2, double %f3) nounwind readnone {
entry:
-; CHECK: c.ule.d
-; CHECK: movf.d
+; ALL-LABEL: f64_fcmp_ogt_f64_val:
+
+; 32-DAG: ldc1 $[[F2:f[0-9]+]], 16($sp)
+; 32-DAG: ldc1 $[[F3:f[0-9]+]], 24($sp)
+; 32: c.ule.d $[[F2]], $[[F3]]
+; 32: movf.d $f14, $f12, $fcc0
+; 32: mov.d $f0, $f14
+
+; 32R2-DAG: ldc1 $[[F2:f[0-9]+]], 16($sp)
+; 32R2-DAG: ldc1 $[[F3:f[0-9]+]], 24($sp)
+; 32R2: c.ule.d $[[F2]], $[[F3]]
+; 32R2: movf.d $f14, $f12, $fcc0
+; 32R2: mov.d $f0, $f14
+
+; 32R6-DAG: ldc1 $[[F2:f[0-9]+]], 16($sp)
+; 32R6-DAG: ldc1 $[[F3:f[0-9]+]], 24($sp)
+; 32R6: cmp.lt.d $[[CC:f0]], $[[F3]], $[[F2]]
+; 32R6: sel.d $[[CC]], $f14, $f12
+
+; 64: c.ule.d $f14, $f15
+; 64: movf.d $f13, $f12, $fcc0
+; 64: mov.d $f0, $f13
+
+; 64R2: c.ule.d $f14, $f15
+; 64R2: movf.d $f13, $f12, $fcc0
+; 64R2: mov.d $f0, $f13
+
+; 64R6: cmp.lt.d $[[CC:f0]], $f15, $f14
+; 64R6: sel.d $[[CC]], $f13, $f12
+
%cmp = fcmp ogt double %f2, %f3
%cond = select i1 %cmp, double %f0, double %f1
ret double %cond
}
-define float @sel8_1(float %f0, float %f1, double %f2, double %f3) nounwind readnone {
+define float @f64_fcmp_ogt_f32_val(float %f0, float %f1, double %f2, double %f3) nounwind readnone {
entry:
-; CHECK: c.ule.d
-; CHECK: movf.s
+; ALL-LABEL: f64_fcmp_ogt_f32_val:
+
+; 32-DAG: mtc1 $6, $[[F2:f[1-3]*[02468]+]]
+; 32-DAG: mtc1 $7, $[[F2H:f[1-3]*[13579]+]]
+; 32-DAG: ldc1 $[[F3:f[0-9]+]], 16($sp)
+; 32: c.ule.d $[[F2]], $[[F3]]
+; 32: movf.s $f14, $f12, $fcc0
+; 32: mov.s $f0, $f14
+
+; 32R2-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32R2-DAG: mthc1 $7, $[[F2]]
+; 32R2-DAG: ldc1 $[[F3:f[0-9]+]], 16($sp)
+; 32R2: c.ule.d $[[F2]], $[[F3]]
+; 32R2: movf.s $f14, $f12, $fcc0
+; 32R2: mov.s $f0, $f14
+
+; 32R6-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32R6-DAG: mthc1 $7, $[[F2]]
+; 32R6-DAG: ldc1 $[[F3:f[0-9]+]], 16($sp)
+; 32R6: cmp.lt.d $[[CC:f0]], $[[F3]], $[[F2]]
+; 32R6: sel.s $[[CC]], $f14, $f12
+
+; 64: c.ule.d $f14, $f15
+; 64: movf.s $f13, $f12, $fcc0
+; 64: mov.s $f0, $f13
+
+; 64R2: c.ule.d $f14, $f15
+; 64R2: movf.s $f13, $f12, $fcc0
+; 64R2: mov.s $f0, $f13
+
+; 64R6: cmp.lt.d $[[CC:f0]], $f15, $f14
+; 64R6: sel.s $[[CC]], $f13, $f12
+
%cmp = fcmp ogt double %f2, %f3
%cond = select i1 %cmp, float %f0, float %f1
ret float %cond
}
-define i32 @sel9(i32 %f0, i32 %f1, float %f2, float %f3) nounwind readnone {
+define i32 @f32_fcmp_oeq_i32_val(i32 %f0, i32 %f1, float %f2, float %f3) nounwind readnone {
entry:
-; CHECK: c.eq.s
-; CHECK: movt
+; ALL-LABEL: f32_fcmp_oeq_i32_val:
+
+; 32-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32: c.eq.s $[[F2]], $[[F3]]
+; 32: movt $5, $4, $fcc0
+; 32: move $2, $5
+
+; 32R2-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32R2-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32R2: c.eq.s $[[F2]], $[[F3]]
+; 32R2: movt $5, $4, $fcc0
+; 32R2: move $2, $5
+
+; 32R6-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32R6-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32R6: cmp.eq.s $[[CC:f[0-9]+]], $[[F2]], $[[F3]]
+; 32R6: mfc1 $[[CCGPR:[0-9]+]], $[[CC]]
+; 32R6: andi $[[CCGPR]], $[[CCGPR]], 1
+; 32R6: seleqz $[[EQ:[0-9]+]], $5, $[[CCGPR]]
+; 32R6: selnez $[[NE:[0-9]+]], $4, $[[CCGPR]]
+; 32R6: or $2, $[[NE]], $[[EQ]]
+
+; 64: c.eq.s $f14, $f15
+; 64: movt $5, $4, $fcc0
+; 64: move $2, $5
+
+; 64R2: c.eq.s $f14, $f15
+; 64R2: movt $5, $4, $fcc0
+; 64R2: move $2, $5
+
+; 64R6: cmp.eq.s $[[CC:f[0-9]+]], $f14, $f15
+; 64R6: mfc1 $[[CCGPR:[0-9]+]], $[[CC]]
+; 64R6: andi $[[CCGPR]], $[[CCGPR]], 1
+; 64R6: seleqz $[[EQ:[0-9]+]], $5, $[[CCGPR]]
+; 64R6: selnez $[[NE:[0-9]+]], $4, $[[CCGPR]]
+; 64R6: or $2, $[[NE]], $[[EQ]]
+
%cmp = fcmp oeq float %f2, %f3
%cond = select i1 %cmp, i32 %f0, i32 %f1
ret i32 %cond
}
-define i32 @sel10(i32 %f0, i32 %f1, float %f2, float %f3) nounwind readnone {
+define i32 @f32_fcmp_olt_i32_val(i32 %f0, i32 %f1, float %f2, float %f3) nounwind readnone {
entry:
-; CHECK: c.olt.s
-; CHECK: movt
+; ALL-LABEL: f32_fcmp_olt_i32_val:
+
+; 32-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32: c.olt.s $[[F2]], $[[F3]]
+; 32: movt $5, $4, $fcc0
+; 32: move $2, $5
+
+; 32R2-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32R2-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32R2: c.olt.s $[[F2]], $[[F3]]
+; 32R2: movt $5, $4, $fcc0
+; 32R2: move $2, $5
+
+; 32R6-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32R6-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32R6: cmp.lt.s $[[CC:f[0-9]+]], $[[F2]], $[[F3]]
+; 32R6: mfc1 $[[CCGPR:[0-9]+]], $[[CC]]
+; 32R6: andi $[[CCGPR]], $[[CCGPR]], 1
+; 32R6: seleqz $[[EQ:[0-9]+]], $5, $[[CCGPR]]
+; 32R6: selnez $[[NE:[0-9]+]], $4, $[[CCGPR]]
+; 32R6: or $2, $[[NE]], $[[EQ]]
+
+; 64: c.olt.s $f14, $f15
+; 64: movt $5, $4, $fcc0
+; 64: move $2, $5
+
+; 64R2: c.olt.s $f14, $f15
+; 64R2: movt $5, $4, $fcc0
+; 64R2: move $2, $5
+
+; 64R6: cmp.lt.s $[[CC:f[0-9]+]], $f14, $f15
+; 64R6: mfc1 $[[CCGPR:[0-9]+]], $[[CC]]
+; 64R6: andi $[[CCGPR]], $[[CCGPR]], 1
+; 64R6: seleqz $[[EQ:[0-9]+]], $5, $[[CCGPR]]
+; 64R6: selnez $[[NE:[0-9]+]], $4, $[[CCGPR]]
+; 64R6: or $2, $[[NE]], $[[EQ]]
%cmp = fcmp olt float %f2, %f3
%cond = select i1 %cmp, i32 %f0, i32 %f1
ret i32 %cond
}
-define i32 @sel11(i32 %f0, i32 %f1, float %f2, float %f3) nounwind readnone {
+define i32 @f32_fcmp_ogt_i32_val(i32 %f0, i32 %f1, float %f2, float %f3) nounwind readnone {
entry:
-; CHECK: c.ule.s
-; CHECK: movf
+; ALL-LABEL: f32_fcmp_ogt_i32_val:
+
+; 32-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32: c.ule.s $[[F2]], $[[F3]]
+; 32: movf $5, $4, $fcc0
+; 32: move $2, $5
+
+; 32R2-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32R2-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32R2: c.ule.s $[[F2]], $[[F3]]
+; 32R2: movf $5, $4, $fcc0
+; 32R2: move $2, $5
+
+; 32R6-DAG: mtc1 $6, $[[F2:f[0-9]+]]
+; 32R6-DAG: mtc1 $7, $[[F3:f[0-9]+]]
+; 32R6: cmp.lt.s $[[CC:f[0-9]+]], $[[F3]], $[[F2]]
+; 32R6: mfc1 $[[CCGPR:[0-9]+]], $[[CC]]
+; 32R6: andi $[[CCGPR]], $[[CCGPR]], 1
+; 32R6: seleqz $[[EQ:[0-9]+]], $5, $[[CCGPR]]
+; 32R6: selnez $[[NE:[0-9]+]], $4, $[[CCGPR]]
+; 32R6: or $2, $[[NE]], $[[EQ]]
+
+; 64: c.ule.s $f14, $f15
+; 64: movf $5, $4, $fcc0
+; 64: move $2, $5
+
+; 64R2: c.ule.s $f14, $f15
+; 64R2: movf $5, $4, $fcc0
+; 64R2: move $2, $5
+
+; 64R6: cmp.lt.s $[[CC:f[0-9]+]], $f15, $f14
+; 64R6: mfc1 $[[CCGPR:[0-9]+]], $[[CC]]
+; 64R6: andi $[[CCGPR]], $[[CCGPR]], 1
+; 64R6: seleqz $[[EQ:[0-9]+]], $5, $[[CCGPR]]
+; 64R6: selnez $[[NE:[0-9]+]], $4, $[[CCGPR]]
+; 64R6: or $2, $[[NE]], $[[EQ]]
+
%cmp = fcmp ogt float %f2, %f3
%cond = select i1 %cmp, i32 %f0, i32 %f1
ret i32 %cond
}
-define i32 @sel12(i32 %f0, i32 %f1) nounwind readonly {
+define i32 @f64_fcmp_oeq_i32_val(i32 %f0, i32 %f1) nounwind readonly {
entry:
-; CHECK: c.eq.d
-; CHECK: movt
+; ALL-LABEL: f64_fcmp_oeq_i32_val:
+
+; 32-DAG: addiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(_gp_disp)
+; 32-DAG: addu $[[GOT:[0-9]+]], $[[T0]], $25
+; 32-DAG: lw $[[D2:[0-9]+]], %got(d2)($1)
+; 32-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 32-DAG: lw $[[D3:[0-9]+]], %got(d3)($1)
+; 32-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 32: c.eq.d $[[TMP]], $[[TMP1]]
+; 32: movt $5, $4, $fcc0
+; 32: move $2, $5
+
+; 32R2-DAG: addiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(_gp_disp)
+; 32R2-DAG: addu $[[GOT:[0-9]+]], $[[T0]], $25
+; 32R2-DAG: lw $[[D2:[0-9]+]], %got(d2)($1)
+; 32R2-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 32R2-DAG: lw $[[D3:[0-9]+]], %got(d3)($1)
+; 32R2-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 32R2: c.eq.d $[[TMP]], $[[TMP1]]
+; 32R2: movt $5, $4, $fcc0
+; 32R2: move $2, $5
+
+; 32R6-DAG: addiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(_gp_disp)
+; 32R6-DAG: addu $[[GOT:[0-9]+]], $[[T0]], $25
+; 32R6-DAG: lw $[[D2:[0-9]+]], %got(d2)($1)
+; 32R6-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 32R6-DAG: lw $[[D3:[0-9]+]], %got(d3)($1)
+; 32R6-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 32R6: cmp.eq.d $[[CC:f[0-9]+]], $[[TMP]], $[[TMP1]]
+; 32R6: mfc1 $[[CCGPR:[0-9]+]], $[[CC]]
+; 32R6: andi $[[CCGPR]], $[[CCGPR]], 1
+; 32R6: seleqz $[[EQ:[0-9]+]], $5, $[[CCGPR]]
+; 32R6: selnez $[[NE:[0-9]+]], $4, $[[CCGPR]]
+; 32R6: or $2, $[[NE]], $[[EQ]]
+
+; 64-DAG: daddiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(%neg(%gp_rel(f64_fcmp_oeq_i32_val)))
+; 64-DAG: daddu $[[GOT:[0-9]+]], $[[T0]], $25
+; 64-DAG: ld $[[D2:[0-9]+]], %got_disp(d2)($1)
+; 64-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 64-DAG: ld $[[D3:[0-9]+]], %got_disp(d3)($1)
+; 64-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 64: c.eq.d $[[TMP]], $[[TMP1]]
+; 64: movt $5, $4, $fcc0
+; 64: move $2, $5
+
+; 64R2-DAG: daddiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(%neg(%gp_rel(f64_fcmp_oeq_i32_val)))
+; 64R2-DAG: daddu $[[GOT:[0-9]+]], $[[T0]], $25
+; 64R2-DAG: ld $[[D2:[0-9]+]], %got_disp(d2)($1)
+; 64R2-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 64R2-DAG: ld $[[D3:[0-9]+]], %got_disp(d3)($1)
+; 64R2-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 64R2: c.eq.d $[[TMP]], $[[TMP1]]
+; 64R2: movt $5, $4, $fcc0
+; 64R2: move $2, $5
+
+; 64R6-DAG: daddiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(%neg(%gp_rel(f64_fcmp_oeq_i32_val)))
+; 64R6-DAG: daddu $[[GOT:[0-9]+]], $[[T0]], $25
+; 64R6-DAG: ld $[[D2:[0-9]+]], %got_disp(d2)($1)
+; 64R6-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 64R6-DAG: ld $[[D3:[0-9]+]], %got_disp(d3)($1)
+; 64R6-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 64R6: cmp.eq.d $[[CC:f[0-9]+]], $[[TMP]], $[[TMP1]]
+; 64R6: mfc1 $[[CCGPR:[0-9]+]], $[[CC]]
+; 64R6: andi $[[CCGPR]], $[[CCGPR]], 1
+; 64R6: seleqz $[[EQ:[0-9]+]], $5, $[[CCGPR]]
+; 64R6: selnez $[[NE:[0-9]+]], $4, $[[CCGPR]]
+; 64R6: or $2, $[[NE]], $[[EQ]]
+
%tmp = load double* @d2, align 8
%tmp1 = load double* @d3, align 8
%cmp = fcmp oeq double %tmp, %tmp1
@@ -137,10 +707,76 @@ entry:
ret i32 %cond
}
-define i32 @sel13(i32 %f0, i32 %f1) nounwind readonly {
+define i32 @f64_fcmp_olt_i32_val(i32 %f0, i32 %f1) nounwind readonly {
entry:
-; CHECK: c.olt.d
-; CHECK: movt
+; ALL-LABEL: f64_fcmp_olt_i32_val:
+
+; 32-DAG: addiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(_gp_disp)
+; 32-DAG: addu $[[GOT:[0-9]+]], $[[T0]], $25
+; 32-DAG: lw $[[D2:[0-9]+]], %got(d2)($1)
+; 32-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 32-DAG: lw $[[D3:[0-9]+]], %got(d3)($1)
+; 32-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 32: c.olt.d $[[TMP]], $[[TMP1]]
+; 32: movt $5, $4, $fcc0
+; 32: move $2, $5
+
+; 32R2-DAG: addiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(_gp_disp)
+; 32R2-DAG: addu $[[GOT:[0-9]+]], $[[T0]], $25
+; 32R2-DAG: lw $[[D2:[0-9]+]], %got(d2)($1)
+; 32R2-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 32R2-DAG: lw $[[D3:[0-9]+]], %got(d3)($1)
+; 32R2-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 32R2: c.olt.d $[[TMP]], $[[TMP1]]
+; 32R2: movt $5, $4, $fcc0
+; 32R2: move $2, $5
+
+; 32R6-DAG: addiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(_gp_disp)
+; 32R6-DAG: addu $[[GOT:[0-9]+]], $[[T0]], $25
+; 32R6-DAG: lw $[[D2:[0-9]+]], %got(d2)($1)
+; 32R6-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 32R6-DAG: lw $[[D3:[0-9]+]], %got(d3)($1)
+; 32R6-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 32R6: cmp.lt.d $[[CC:f[0-9]+]], $[[TMP]], $[[TMP1]]
+; 32R6: mfc1 $[[CCGPR:[0-9]+]], $[[CC]]
+; 32R6: andi $[[CCGPR]], $[[CCGPR]], 1
+; 32R6: seleqz $[[EQ:[0-9]+]], $5, $[[CCGPR]]
+; 32R6: selnez $[[NE:[0-9]+]], $4, $[[CCGPR]]
+; 32R6: or $2, $[[NE]], $[[EQ]]
+
+; 64-DAG: daddiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(%neg(%gp_rel(f64_fcmp_olt_i32_val)))
+; 64-DAG: daddu $[[GOT:[0-9]+]], $[[T0]], $25
+; 64-DAG: ld $[[D2:[0-9]+]], %got_disp(d2)($1)
+; 64-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 64-DAG: ld $[[D3:[0-9]+]], %got_disp(d3)($1)
+; 64-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 64: c.olt.d $[[TMP]], $[[TMP1]]
+; 64: movt $5, $4, $fcc0
+; 64: move $2, $5
+
+; 64R2-DAG: daddiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(%neg(%gp_rel(f64_fcmp_olt_i32_val)))
+; 64R2-DAG: daddu $[[GOT:[0-9]+]], $[[T0]], $25
+; 64R2-DAG: ld $[[D2:[0-9]+]], %got_disp(d2)($1)
+; 64R2-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 64R2-DAG: ld $[[D3:[0-9]+]], %got_disp(d3)($1)
+; 64R2-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 64R2: c.olt.d $[[TMP]], $[[TMP1]]
+; 64R2: movt $5, $4, $fcc0
+; 64R2: move $2, $5
+
+; 64R6-DAG: daddiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(%neg(%gp_rel(f64_fcmp_olt_i32_val)))
+; 64R6-DAG: daddu $[[GOT:[0-9]+]], $[[T0]], $25
+; 64R6-DAG: ld $[[D2:[0-9]+]], %got_disp(d2)($1)
+; 64R6-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 64R6-DAG: ld $[[D3:[0-9]+]], %got_disp(d3)($1)
+; 64R6-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 64R6: cmp.lt.d $[[CC:f[0-9]+]], $[[TMP]], $[[TMP1]]
+; 64R6: mfc1 $[[CCGPR:[0-9]+]], $[[CC]]
+; 64R6: andi $[[CCGPR]], $[[CCGPR]], 1
+; 64R6: seleqz $[[EQ:[0-9]+]], $5, $[[CCGPR]]
+; 64R6: selnez $[[NE:[0-9]+]], $4, $[[CCGPR]]
+; 64R6: or $2, $[[NE]], $[[EQ]]
+
%tmp = load double* @d2, align 8
%tmp1 = load double* @d3, align 8
%cmp = fcmp olt double %tmp, %tmp1
@@ -148,10 +784,76 @@ entry:
ret i32 %cond
}
-define i32 @sel14(i32 %f0, i32 %f1) nounwind readonly {
+define i32 @f64_fcmp_ogt_i32_val(i32 %f0, i32 %f1) nounwind readonly {
entry:
-; CHECK: c.ule.d
-; CHECK: movf
+; ALL-LABEL: f64_fcmp_ogt_i32_val:
+
+; 32-DAG: addiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(_gp_disp)
+; 32-DAG: addu $[[GOT:[0-9]+]], $[[T0]], $25
+; 32-DAG: lw $[[D2:[0-9]+]], %got(d2)($1)
+; 32-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 32-DAG: lw $[[D3:[0-9]+]], %got(d3)($1)
+; 32-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 32: c.ule.d $[[TMP]], $[[TMP1]]
+; 32: movf $5, $4, $fcc0
+; 32: move $2, $5
+
+; 32R2-DAG: addiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(_gp_disp)
+; 32R2-DAG: addu $[[GOT:[0-9]+]], $[[T0]], $25
+; 32R2-DAG: lw $[[D2:[0-9]+]], %got(d2)($1)
+; 32R2-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 32R2-DAG: lw $[[D3:[0-9]+]], %got(d3)($1)
+; 32R2-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 32R2: c.ule.d $[[TMP]], $[[TMP1]]
+; 32R2: movf $5, $4, $fcc0
+; 32R2: move $2, $5
+
+; 32R6-DAG: addiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(_gp_disp)
+; 32R6-DAG: addu $[[GOT:[0-9]+]], $[[T0]], $25
+; 32R6-DAG: lw $[[D2:[0-9]+]], %got(d2)($1)
+; 32R6-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 32R6-DAG: lw $[[D3:[0-9]+]], %got(d3)($1)
+; 32R6-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 32R6: cmp.lt.d $[[CC:f[0-9]+]], $[[TMP1]], $[[TMP]]
+; 32R6: mfc1 $[[CCGPR:[0-9]+]], $[[CC]]
+; 32R6: andi $[[CCGPR]], $[[CCGPR]], 1
+; 32R6: seleqz $[[EQ:[0-9]+]], $5, $[[CCGPR]]
+; 32R6: selnez $[[NE:[0-9]+]], $4, $[[CCGPR]]
+; 32R6: or $2, $[[NE]], $[[EQ]]
+
+; 64-DAG: daddiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(%neg(%gp_rel(f64_fcmp_ogt_i32_val)))
+; 64-DAG: daddu $[[GOT:[0-9]+]], $[[T0]], $25
+; 64-DAG: ld $[[D2:[0-9]+]], %got_disp(d2)($1)
+; 64-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 64-DAG: ld $[[D3:[0-9]+]], %got_disp(d3)($1)
+; 64-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 64: c.ule.d $[[TMP]], $[[TMP1]]
+; 64: movf $5, $4, $fcc0
+; 64: move $2, $5
+
+; 64R2-DAG: daddiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(%neg(%gp_rel(f64_fcmp_ogt_i32_val)))
+; 64R2-DAG: daddu $[[GOT:[0-9]+]], $[[T0]], $25
+; 64R2-DAG: ld $[[D2:[0-9]+]], %got_disp(d2)($1)
+; 64R2-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 64R2-DAG: ld $[[D3:[0-9]+]], %got_disp(d3)($1)
+; 64R2-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 64R2: c.ule.d $[[TMP]], $[[TMP1]]
+; 64R2: movf $5, $4, $fcc0
+; 64R2: move $2, $5
+
+; 64R6-DAG: daddiu $[[T0:[0-9]+]], ${{[0-9]+}}, %lo(%neg(%gp_rel(f64_fcmp_ogt_i32_val)))
+; 64R6-DAG: daddu $[[GOT:[0-9]+]], $[[T0]], $25
+; 64R6-DAG: ld $[[D2:[0-9]+]], %got_disp(d2)($1)
+; 64R6-DAG: ldc1 $[[TMP:f[0-9]+]], 0($[[D2]])
+; 64R6-DAG: ld $[[D3:[0-9]+]], %got_disp(d3)($1)
+; 64R6-DAG: ldc1 $[[TMP1:f[0-9]+]], 0($[[D3]])
+; 64R6: cmp.lt.d $[[CC:f[0-9]+]], $[[TMP1]], $[[TMP]]
+; 64R6: mfc1 $[[CCGPR:[0-9]+]], $[[CC]]
+; 64R6: andi $[[CCGPR]], $[[CCGPR]], 1
+; 64R6: seleqz $[[EQ:[0-9]+]], $5, $[[CCGPR]]
+; 64R6: selnez $[[NE:[0-9]+]], $4, $[[CCGPR]]
+; 64R6: or $2, $[[NE]], $[[EQ]]
+
%tmp = load double* @d2, align 8
%tmp1 = load double* @d3, align 8
%cmp = fcmp ogt double %tmp, %tmp1
diff --git a/test/CodeGen/Mips/selectcc.ll b/test/CodeGen/Mips/selectcc.ll
index aeef60e..9790a0a 100644
--- a/test/CodeGen/Mips/selectcc.ll
+++ b/test/CodeGen/Mips/selectcc.ll
@@ -1,5 +1,7 @@
-; RUN: llc -march=mipsel < %s
-; RUN: llc -march=mipsel -pre-RA-sched=source < %s | FileCheck %s --check-prefix=SOURCE-SCHED
+; RUN: llc -march=mipsel -mcpu=mips32 < %s
+; RUN: llc -march=mipsel -mcpu=mips32 -pre-RA-sched=source < %s | FileCheck %s --check-prefix=SOURCE-SCHED
+; RUN: llc -march=mipsel -mcpu=mips32r2 < %s
+; RUN: llc -march=mipsel -mcpu=mips32r2 -pre-RA-sched=source < %s | FileCheck %s --check-prefix=SOURCE-SCHED
@gf0 = external global float
@gf1 = external global float
@@ -16,13 +18,11 @@ entry:
; SOURCE-SCHED: lw
; SOURCE-SCHED: lui
; SOURCE-SCHED: sw
-; SOURCE-SCHED: addiu
-; SOURCE-SCHED: addiu
-; SOURCE-SCHED: c.olt.s
-; SOURCE-SCHED: movt
+; SOURCE-SCHED: lw
+; SOURCE-SCHED: lwc1
; SOURCE-SCHED: mtc1
+; SOURCE-SCHED: c.olt.s
; SOURCE-SCHED: jr
-
store float 0.000000e+00, float* @gf0, align 4
store float 1.000000e+00, float* @gf1, align 4
%cmp = fcmp olt float %a, %b
diff --git a/test/CodeGen/Mips/tls-alias.ll b/test/CodeGen/Mips/tls-alias.ll
index 80fbe87..b61f84e 100644
--- a/test/CodeGen/Mips/tls-alias.ll
+++ b/test/CodeGen/Mips/tls-alias.ll
@@ -1,7 +1,7 @@
; RUN: llc -march=mipsel -relocation-model=pic -disable-mips-delay-filler < %s | FileCheck %s
@foo = thread_local global i32 42
-@bar = hidden alias i32* @foo
+@bar = hidden thread_local alias i32* @foo
define i32* @zed() {
; CHECK-DAG: __tls_get_addr
diff --git a/test/CodeGen/Mips/zeroreg.ll b/test/CodeGen/Mips/zeroreg.ll
index e0e93e2..a1b6cb0 100644
--- a/test/CodeGen/Mips/zeroreg.ll
+++ b/test/CodeGen/Mips/zeroreg.ll
@@ -1,21 +1,109 @@
-; RUN: llc < %s -march=mipsel | FileCheck %s
+; RUN: llc < %s -march=mipsel -mcpu=mips32 | FileCheck %s -check-prefix=ALL -check-prefix=32-CMOV
+; RUN: llc < %s -march=mipsel -mcpu=mips32r2 | FileCheck %s -check-prefix=ALL -check-prefix=32-CMOV
+; RUN: llc < %s -march=mipsel -mcpu=mips32r6 | FileCheck %s -check-prefix=ALL -check-prefix=32R6
+; RUN: llc < %s -march=mipsel -mcpu=mips4 | FileCheck %s -check-prefix=ALL -check-prefix=64-CMOV
+; RUN: llc < %s -march=mipsel -mcpu=mips64 | FileCheck %s -check-prefix=ALL -check-prefix=64-CMOV
+; RUN: llc < %s -march=mipsel -mcpu=mips64r2 | FileCheck %s -check-prefix=ALL -check-prefix=64-CMOV
+; RUN: llc < %s -march=mipsel -mcpu=mips64r6 | FileCheck %s -check-prefix=ALL -check-prefix=64R6
@g1 = external global i32
-define i32 @foo0(i32 %s) nounwind readonly {
+define i32 @sel_icmp_nez_i32_z0(i32 %s) nounwind readonly {
entry:
-; CHECK: movn ${{[0-9]+}}, $zero
+; ALL-LABEL: sel_icmp_nez_i32_z0:
+
+; 32-CMOV: lw $2, 0(${{[0-9]+}})
+; 32-CMOV: movn $2, $zero, $4
+
+; 32R6: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 32R6: seleqz $2, $[[R0]], $4
+
+; 64-CMOV: lw $2, 0(${{[0-9]+}})
+; 64-CMOV: movn $2, $zero, $4
+
+; 64R6: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 64R6: seleqz $2, $[[R0]], $4
+
%tobool = icmp ne i32 %s, 0
%0 = load i32* @g1, align 4
%cond = select i1 %tobool, i32 0, i32 %0
ret i32 %cond
}
-define i32 @foo1(i32 %s) nounwind readonly {
+define i32 @sel_icmp_nez_i32_z1(i32 %s) nounwind readonly {
entry:
-; CHECK: movz ${{[0-9]+}}, $zero
+; ALL-LABEL: sel_icmp_nez_i32_z1:
+
+; 32-CMOV: lw $2, 0(${{[0-9]+}})
+; 32-CMOV: movz $2, $zero, $4
+
+; 32R6: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 32R6: selnez $2, $[[R0]], $4
+
+; 64-CMOV: lw $2, 0(${{[0-9]+}})
+; 64-CMOV: movz $2, $zero, $4
+
+; 64R6: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 64R6: selnez $2, $[[R0]], $4
+
%tobool = icmp ne i32 %s, 0
%0 = load i32* @g1, align 4
%cond = select i1 %tobool, i32 %0, i32 0
ret i32 %cond
}
+
+@g2 = external global i64
+
+define i64 @sel_icmp_nez_i64_z0(i64 %s) nounwind readonly {
+entry:
+; ALL-LABEL: sel_icmp_nez_i64_z0:
+
+; 32-CMOV-DAG: lw $[[R0:2]], 0(${{[0-9]+}})
+; 32-CMOV-DAG: lw $[[R1:3]], 4(${{[0-9]+}})
+; 32-CMOV-DAG: movn $[[R0]], $zero, $4
+; 32-CMOV-DAG: movn $[[R1]], $zero, $4
+
+; 32R6-DAG: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 32R6-DAG: lw $[[R1:[0-9]+]], 4(${{[0-9]+}})
+; 32R6-DAG: or $[[CC:[0-9]+]], $4, $5
+; 32R6-DAG: seleqz $2, $[[R0]], $[[CC]]
+; 32R6-DAG: seleqz $3, $[[R1]], $[[CC]]
+
+; 64-CMOV: ld $2, 0(${{[0-9]+}})
+; 64-CMOV: movn $2, $zero, $4
+
+; 64R6: ld $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 64R6: seleqz $2, $[[R0]], $4
+
+ %tobool = icmp ne i64 %s, 0
+ %0 = load i64* @g2, align 4
+ %cond = select i1 %tobool, i64 0, i64 %0
+ ret i64 %cond
+}
+
+define i64 @sel_icmp_nez_i64_z1(i64 %s) nounwind readonly {
+entry:
+; ALL-LABEL: sel_icmp_nez_i64_z1:
+
+; 32-CMOV-DAG: lw $[[R0:2]], 0(${{[0-9]+}})
+; 32-CMOV-DAG: lw $[[R1:3]], 4(${{[0-9]+}})
+; 32-CMOV-DAG: movz $[[R0]], $zero, $4
+; 32-CMOV-DAG: movz $[[R1]], $zero, $4
+
+; 32R6-DAG: lw $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 32R6-DAG: lw $[[R1:[0-9]+]], 4(${{[0-9]+}})
+; 32R6-DAG: or $[[CC:[0-9]+]], $4, $5
+; 32R6-DAG: selnez $2, $[[R0]], $[[CC]]
+; 32R6-DAG: selnez $3, $[[R1]], $[[CC]]
+
+; 64-CMOV: ld $2, 0(${{[0-9]+}})
+; 64-CMOV: movz $2, $zero, $4
+
+; 64R6: ld $[[R0:[0-9]+]], 0(${{[0-9]+}})
+; 64R6: selnez $2, $[[R0]], $4
+
+ %tobool = icmp ne i64 %s, 0
+ %0 = load i64* @g2, align 4
+ %cond = select i1 %tobool, i64 %0, i64 0
+ ret i64 %cond
+}