diff --git a/llvm/lib/Target/X86/X86ISelLowering.cpp b/llvm/lib/Target/X86/X86ISelLowering.cpp index 97a406d176a55..b4352527b3cc1 100644 --- a/llvm/lib/Target/X86/X86ISelLowering.cpp +++ b/llvm/lib/Target/X86/X86ISelLowering.cpp @@ -21439,32 +21439,32 @@ SDValue X86TargetLowering::LowerUINT_TO_FP(SDValue Op, bool IsStrict = Op->isStrictFPOpcode(); unsigned OpNo = IsStrict ? 1 : 0; SDValue Src = Op.getOperand(OpNo); - SDLoc dl(Op); + SDValue Chain = IsStrict ? Op.getOperand(0) : DAG.getEntryNode(); auto PtrVT = getPointerTy(DAG.getDataLayout()); MVT SrcVT = Src.getSimpleValueType(); MVT DstVT = Op->getSimpleValueType(0); - SDValue Chain = IsStrict ? Op.getOperand(0) : DAG.getEntryNode(); - - // Bail out when we don't have native conversion instructions. - if (DstVT == MVT::f128) - return SDValue(); + SDLoc dl(Op); if (isBF16orSoftF16(DstVT, Subtarget)) return promoteXINT_TO_FP(Op, dl, DAG); else if (isLegalConversion(SrcVT, DstVT, false, Subtarget)) return Op; + if (Subtarget.isTargetWin64() && SrcVT == MVT::i128) + return LowerWin64_INT128_TO_FP(Op, DAG); + + if (SDValue Extract = vectorizeExtractedCast(Op, dl, DAG, Subtarget)) + return Extract; + if (SDValue V = lowerFPToIntToFP(Op, dl, DAG, Subtarget)) return V; if (DstVT.isVector()) return lowerUINT_TO_FP_vec(Op, dl, DAG, Subtarget); - if (Subtarget.isTargetWin64() && SrcVT == MVT::i128) - return LowerWin64_INT128_TO_FP(Op, DAG); - - if (SDValue Extract = vectorizeExtractedCast(Op, dl, DAG, Subtarget)) - return Extract; + // Bail out when we don't have native conversion instructions. + if (DstVT == MVT::f128) + return SDValue(); if (Subtarget.hasAVX512() && isScalarFPTypeInSSEReg(DstVT) && (SrcVT == MVT::i32 || (SrcVT == MVT::i64 && Subtarget.is64Bit()))) { diff --git a/llvm/test/CodeGen/X86/fp128-cast.ll b/llvm/test/CodeGen/X86/fp128-cast.ll index 6d4ec063ccd46..2fef3746729c1 100644 --- a/llvm/test/CodeGen/X86/fp128-cast.ll +++ b/llvm/test/CodeGen/X86/fp128-cast.ll @@ -1,6 +1,7 @@ ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py ; RUN: llc < %s -O2 -mtriple=x86_64-linux-android -mattr=+sse | FileCheck %s --check-prefix=X64-SSE ; RUN: llc < %s -O2 -mtriple=x86_64-linux-gnu -mattr=+sse | FileCheck %s --check-prefix=X64-SSE +; RUN: llc < %s -O2 -mtriple=x86_64-pc-windows-gnu -mattr=+sse | FileCheck %s --check-prefix=WIN64-SSE ; RUN: llc < %s -O2 -mtriple=i686-linux-gnu -mattr=+mmx | FileCheck %s --check-prefix=X86 ; RUN: llc < %s -O2 -mtriple=x86_64-linux-android -mattr=+avx | FileCheck %s --check-prefix=X64-AVX ; RUN: llc < %s -O2 -mtriple=x86_64-linux-gnu -mattr=+avx | FileCheck %s --check-prefix=X64-AVX @@ -31,6 +32,17 @@ define dso_local void @TestFPExtF32_F128() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestFPExtF32_F128: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movss {{.*#+}} xmm1 = mem[0],zero,zero,zero +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __extendsftf2 +; WIN64-SSE-NEXT: movaps {{[0-9]+}}(%rsp), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, vf128(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestFPExtF32_F128: ; X86: # %bb.0: # %entry ; X86-NEXT: pushl %esi @@ -78,6 +90,17 @@ define dso_local void @TestFPExtF64_F128() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestFPExtF64_F128: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movsd {{.*#+}} xmm1 = mem[0],zero +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __extenddftf2 +; WIN64-SSE-NEXT: movaps {{[0-9]+}}(%rsp), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, vf128(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestFPExtF64_F128: ; X86: # %bb.0: # %entry ; X86-NEXT: pushl %esi @@ -126,6 +149,19 @@ define dso_local void @TestFPExtF80_F128() nounwind { ; X64-SSE-NEXT: addq $24, %rsp ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestFPExtF80_F128: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $72, %rsp +; WIN64-SSE-NEXT: fldt vf80(%rip) +; WIN64-SSE-NEXT: fstpt {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rdx +; WIN64-SSE-NEXT: callq __extendxftf2 +; WIN64-SSE-NEXT: movaps {{[0-9]+}}(%rsp), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, vf128(%rip) +; WIN64-SSE-NEXT: addq $72, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestFPExtF80_F128: ; X86: # %bb.0: # %entry ; X86-NEXT: pushl %esi @@ -174,6 +210,17 @@ define dso_local void @TestFPToSIF128_I16() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestFPToSIF128_I16: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movaps vf128(%rip), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __fixtfsi +; WIN64-SSE-NEXT: movw %ax, vi16(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestFPToSIF128_I16: ; X86: # %bb.0: # %entry ; X86-NEXT: subl $12, %esp @@ -212,6 +259,17 @@ define dso_local void @TestFPToUIF128_I16() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestFPToUIF128_I16: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movaps vf128(%rip), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __fixtfsi +; WIN64-SSE-NEXT: movw %ax, vi16(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestFPToUIF128_I16: ; X86: # %bb.0: # %entry ; X86-NEXT: subl $12, %esp @@ -250,6 +308,17 @@ define dso_local void @TestFPToSIF128_I32() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestFPToSIF128_I32: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movaps vf128(%rip), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __fixtfsi +; WIN64-SSE-NEXT: movl %eax, vi32(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestFPToSIF128_I32: ; X86: # %bb.0: # %entry ; X86-NEXT: subl $12, %esp @@ -288,6 +357,17 @@ define dso_local void @TestFPToUIF128_U32() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestFPToUIF128_U32: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movaps vf128(%rip), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __fixunstfsi +; WIN64-SSE-NEXT: movl %eax, vu32(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestFPToUIF128_U32: ; X86: # %bb.0: # %entry ; X86-NEXT: subl $12, %esp @@ -327,6 +407,18 @@ define dso_local void @TestFPToSIF128_I64() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestFPToSIF128_I64: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movaps vf128(%rip), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __fixtfsi +; WIN64-SSE-NEXT: cltq +; WIN64-SSE-NEXT: movq %rax, vi64(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestFPToSIF128_I64: ; X86: # %bb.0: # %entry ; X86-NEXT: subl $12, %esp @@ -370,6 +462,18 @@ define dso_local void @TestFPToUIF128_U64() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestFPToUIF128_U64: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movaps vf128(%rip), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __fixunstfsi +; WIN64-SSE-NEXT: movl %eax, %eax +; WIN64-SSE-NEXT: movq %rax, vu64(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestFPToUIF128_U64: ; X86: # %bb.0: # %entry ; X86-NEXT: subl $12, %esp @@ -412,6 +516,17 @@ define dso_local void @TestFPToSIF128_I128() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestFPToSIF128_I128: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movaps vf128(%rip), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __fixtfti +; WIN64-SSE-NEXT: movaps %xmm0, vi128(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestFPToSIF128_I128: ; X86: # %bb.0: # %entry ; X86-NEXT: pushl %esi @@ -467,6 +582,17 @@ define dso_local void @TestFPToUIF128_U128() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestFPToUIF128_U128: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movaps vf128(%rip), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __fixunstfti +; WIN64-SSE-NEXT: movaps %xmm0, vu128(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestFPToUIF128_U128: ; X86: # %bb.0: # %entry ; X86-NEXT: pushl %esi @@ -521,6 +647,17 @@ define dso_local void @TestFPTruncF128_F32() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestFPTruncF128_F32: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movaps vf128(%rip), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __trunctfsf2 +; WIN64-SSE-NEXT: movss %xmm0, vf32(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestFPTruncF128_F32: ; X86: # %bb.0: # %entry ; X86-NEXT: subl $12, %esp @@ -559,6 +696,17 @@ define dso_local void @TestFPTruncF128_F64() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestFPTruncF128_F64: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movaps vf128(%rip), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __trunctfdf2 +; WIN64-SSE-NEXT: movsd %xmm0, vf64(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestFPTruncF128_F64: ; X86: # %bb.0: # %entry ; X86-NEXT: subl $12, %esp @@ -597,6 +745,19 @@ define dso_local void @TestFPTruncF128_F80() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestFPTruncF128_F80: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $72, %rsp +; WIN64-SSE-NEXT: movaps vf128(%rip), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rdx +; WIN64-SSE-NEXT: callq __trunctfxf2 +; WIN64-SSE-NEXT: fldt {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: fstpt vf80(%rip) +; WIN64-SSE-NEXT: addq $72, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestFPTruncF128_F80: ; X86: # %bb.0: # %entry ; X86-NEXT: subl $12, %esp @@ -635,6 +796,17 @@ define dso_local void @TestSIToFPI16_F128() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestSIToFPI16_F128: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movswl vi16(%rip), %edx +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __floatsitf +; WIN64-SSE-NEXT: movaps {{[0-9]+}}(%rsp), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, vf128(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestSIToFPI16_F128: ; X86: # %bb.0: # %entry ; X86-NEXT: pushl %esi @@ -683,6 +855,17 @@ define dso_local void @TestSIToFPU16_F128() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestSIToFPU16_F128: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movzwl vi16(%rip), %edx +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __floatsitf +; WIN64-SSE-NEXT: movaps {{[0-9]+}}(%rsp), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, vf128(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestSIToFPU16_F128: ; X86: # %bb.0: # %entry ; X86-NEXT: pushl %esi @@ -731,6 +914,17 @@ define dso_local void @TestSIToFPI32_F128() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestSIToFPI32_F128: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movl vi32(%rip), %edx +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __floatsitf +; WIN64-SSE-NEXT: movaps {{[0-9]+}}(%rsp), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, vf128(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestSIToFPI32_F128: ; X86: # %bb.0: # %entry ; X86-NEXT: pushl %esi @@ -777,6 +971,17 @@ define dso_local void @TestUIToFPU32_F128() #2 { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestUIToFPU32_F128: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movl vu32(%rip), %edx +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __floatunsitf +; WIN64-SSE-NEXT: movaps {{[0-9]+}}(%rsp), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, vf128(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestUIToFPU32_F128: ; X86: # %bb.0: # %entry ; X86-NEXT: pushl %esi @@ -823,6 +1028,17 @@ define dso_local void @TestSIToFPI64_F128() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestSIToFPI64_F128: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movq vi64(%rip), %rdx +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __floatditf +; WIN64-SSE-NEXT: movaps {{[0-9]+}}(%rsp), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, vf128(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestSIToFPI64_F128: ; X86: # %bb.0: # %entry ; X86-NEXT: pushl %esi @@ -870,6 +1086,17 @@ define dso_local void @TestUIToFPU64_F128() #2 { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestUIToFPU64_F128: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $56, %rsp +; WIN64-SSE-NEXT: movq vu64(%rip), %rdx +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __floatunditf +; WIN64-SSE-NEXT: movaps {{[0-9]+}}(%rsp), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, vf128(%rip) +; WIN64-SSE-NEXT: addq $56, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestUIToFPU64_F128: ; X86: # %bb.0: # %entry ; X86-NEXT: pushl %esi @@ -918,6 +1145,19 @@ define dso_local void @TestSIToFPI128_F128() nounwind { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestSIToFPI128_F128: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $72, %rsp +; WIN64-SSE-NEXT: movaps vi128(%rip), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rdx +; WIN64-SSE-NEXT: callq __floattitf +; WIN64-SSE-NEXT: movaps {{[0-9]+}}(%rsp), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, vf128(%rip) +; WIN64-SSE-NEXT: addq $72, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestSIToFPI128_F128: ; X86: # %bb.0: # %entry ; X86-NEXT: pushl %esi @@ -973,6 +1213,19 @@ define dso_local void @TestUIToFPU128_F128() #2 { ; X64-SSE-NEXT: popq %rax ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestUIToFPU128_F128: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $72, %rsp +; WIN64-SSE-NEXT: movaps vu128(%rip), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rdx +; WIN64-SSE-NEXT: callq __floatuntitf +; WIN64-SSE-NEXT: movaps {{[0-9]+}}(%rsp), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, vf128(%rip) +; WIN64-SSE-NEXT: addq $72, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestUIToFPU128_F128: ; X86: # %bb.0: # %entry ; X86-NEXT: pushl %esi @@ -1030,6 +1283,23 @@ define dso_local i32 @TestConst128(fp128 %v) nounwind { ; X64-SSE-NEXT: popq %rcx ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestConst128: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $72, %rsp +; WIN64-SSE-NEXT: movaps (%rcx), %xmm0 +; WIN64-SSE-NEXT: movaps {{.*#+}} xmm1 = [1.0E+0] +; WIN64-SSE-NEXT: movaps %xmm1, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rdx +; WIN64-SSE-NEXT: callq __gttf2 +; WIN64-SSE-NEXT: xorl %ecx, %ecx +; WIN64-SSE-NEXT: testl %eax, %eax +; WIN64-SSE-NEXT: setg %cl +; WIN64-SSE-NEXT: movl %ecx, %eax +; WIN64-SSE-NEXT: addq $72, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestConst128: ; X86: # %bb.0: # %entry ; X86-NEXT: subl $12, %esp @@ -1081,6 +1351,23 @@ define dso_local i32 @TestConst128Zero(fp128 %v) nounwind { ; X64-SSE-NEXT: popq %rcx ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestConst128Zero: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $72, %rsp +; WIN64-SSE-NEXT: movaps (%rcx), %xmm0 +; WIN64-SSE-NEXT: xorps %xmm1, %xmm1 +; WIN64-SSE-NEXT: movaps %xmm1, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rdx +; WIN64-SSE-NEXT: callq __gttf2 +; WIN64-SSE-NEXT: xorl %ecx, %ecx +; WIN64-SSE-NEXT: testl %eax, %eax +; WIN64-SSE-NEXT: setg %cl +; WIN64-SSE-NEXT: movl %ecx, %eax +; WIN64-SSE-NEXT: addq $72, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestConst128Zero: ; X86: # %bb.0: # %entry ; X86-NEXT: subl $12, %esp @@ -1148,6 +1435,27 @@ define dso_local i32 @TestBits128(fp128 %ld) nounwind { ; X64-SSE-NEXT: addq $24, %rsp ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestBits128: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: subq $104, %rsp +; WIN64-SSE-NEXT: movaps (%rcx), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rdx +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %r8 +; WIN64-SSE-NEXT: callq __multf3 +; WIN64-SSE-NEXT: movaps {{[0-9]+}}(%rsp), %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: movq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: movq %rcx, %rdx +; WIN64-SSE-NEXT: shrq $32, %rdx +; WIN64-SSE-NEXT: xorl %eax, %eax +; WIN64-SSE-NEXT: orl %ecx, %edx +; WIN64-SSE-NEXT: sete %al +; WIN64-SSE-NEXT: addq $104, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestBits128: ; X86: # %bb.0: # %entry ; X86-NEXT: pushl %esi @@ -1225,6 +1533,15 @@ define fp128 @TestPair128(i64 %a, i64 %b) nounwind { ; X64-SSE-NEXT: movaps -{{[0-9]+}}(%rsp), %xmm0 ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestPair128: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: movq %rcx, %rax +; WIN64-SSE-NEXT: addq $3, %r8 +; WIN64-SSE-NEXT: adcq $0, %rdx +; WIN64-SSE-NEXT: movq %rdx, 8(%rcx) +; WIN64-SSE-NEXT: movq %r8, (%rcx) +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestPair128: ; X86: # %bb.0: # %entry ; X86-NEXT: pushl %edi @@ -1279,6 +1596,31 @@ define fp128 @TestTruncCopysign(fp128 %x, i32 %n) nounwind { ; X64-SSE-NEXT: .LBB26_2: # %cleanup ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: TestTruncCopysign: +; WIN64-SSE: # %bb.0: # %entry +; WIN64-SSE-NEXT: pushq %rsi +; WIN64-SSE-NEXT: subq $64, %rsp +; WIN64-SSE-NEXT: movq %rcx, %rsi +; WIN64-SSE-NEXT: movaps (%rdx), %xmm0 +; WIN64-SSE-NEXT: cmpl $50001, %r8d # imm = 0xC351 +; WIN64-SSE-NEXT: jl .LBB26_2 +; WIN64-SSE-NEXT: # %bb.1: # %if.then +; WIN64-SSE-NEXT: movaps %xmm0, {{[0-9]+}}(%rsp) +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: callq __trunctfdf2 +; WIN64-SSE-NEXT: andps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 +; WIN64-SSE-NEXT: orps {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 +; WIN64-SSE-NEXT: leaq {{[0-9]+}}(%rsp), %rcx +; WIN64-SSE-NEXT: movaps %xmm0, %xmm1 +; WIN64-SSE-NEXT: callq __extenddftf2 +; WIN64-SSE-NEXT: movaps {{[0-9]+}}(%rsp), %xmm0 +; WIN64-SSE-NEXT: .LBB26_2: # %cleanup +; WIN64-SSE-NEXT: movaps %xmm0, (%rsi) +; WIN64-SSE-NEXT: movq %rsi, %rax +; WIN64-SSE-NEXT: addq $64, %rsp +; WIN64-SSE-NEXT: popq %rsi +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: TestTruncCopysign: ; X86: # %bb.0: # %entry ; X86-NEXT: pushl %edi @@ -1370,6 +1712,18 @@ define i1 @PR34866(i128 %x) nounwind { ; X64-SSE-NEXT: sete %al ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: PR34866: +; WIN64-SSE: # %bb.0: +; WIN64-SSE-NEXT: subq $24, %rsp +; WIN64-SSE-NEXT: xorps %xmm0, %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, (%rsp) +; WIN64-SSE-NEXT: xorq {{[0-9]+}}(%rsp), %rdx +; WIN64-SSE-NEXT: xorq (%rsp), %rcx +; WIN64-SSE-NEXT: orq %rdx, %rcx +; WIN64-SSE-NEXT: sete %al +; WIN64-SSE-NEXT: addq $24, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: PR34866: ; X86: # %bb.0: ; X86-NEXT: subl $12, %esp @@ -1407,6 +1761,18 @@ define i1 @PR34866_commute(i128 %x) nounwind { ; X64-SSE-NEXT: sete %al ; X64-SSE-NEXT: retq ; +; WIN64-SSE-LABEL: PR34866_commute: +; WIN64-SSE: # %bb.0: +; WIN64-SSE-NEXT: subq $24, %rsp +; WIN64-SSE-NEXT: xorps %xmm0, %xmm0 +; WIN64-SSE-NEXT: movaps %xmm0, (%rsp) +; WIN64-SSE-NEXT: xorq {{[0-9]+}}(%rsp), %rdx +; WIN64-SSE-NEXT: xorq (%rsp), %rcx +; WIN64-SSE-NEXT: orq %rdx, %rcx +; WIN64-SSE-NEXT: sete %al +; WIN64-SSE-NEXT: addq $24, %rsp +; WIN64-SSE-NEXT: retq +; ; X86-LABEL: PR34866_commute: ; X86: # %bb.0: ; X86-NEXT: subl $12, %esp