Index: lib/Target/Mips/MicroMipsInstrFPU.td =================================================================== --- lib/Target/Mips/MicroMipsInstrFPU.td +++ lib/Target/Mips/MicroMipsInstrFPU.td @@ -70,8 +70,13 @@ def CVT_L_D64_MM : MMRel, ABSS_FT<"cvt.l.d", FGR64Opnd, FGR64Opnd, II_CVT>, ROUND_W_FM_MM<1, 0x4>, INSN_MIPS3_32R2; -def FABS_S_MM : MMRel, ABSS_FT<"abs.s", FGR32Opnd, FGR32Opnd, II_ABS, fabs>, - ABS_FM_MM<0, 0xd>; +let AdditionalPredicates = [UseAbs] in { + def FABS_S_MM : MMRel, ABSS_FT<"abs.s", FGR32Opnd, FGR32Opnd, II_ABS, fabs>, + ABS_FM_MM<0, 0xd>; + def FABS_MM : MMRel, ABSS_FT<"abs.d", AFGR64Opnd, AFGR64Opnd, II_ABS, fabs>, + ABS_FM_MM<1, 0xd>; +} + def FMOV_S_MM : MMRel, ABSS_FT<"mov.s", FGR32Opnd, FGR32Opnd, II_MOV_S>, ABS_FM_MM<0, 0x1>; def FNEG_S_MM : MMRel, ABSS_FT<"neg.s", FGR32Opnd, FGR32Opnd, II_NEG, fneg>, @@ -85,8 +90,6 @@ def CVT_S_W_MM : MMRel, ABSS_FT<"cvt.s.w", FGR32Opnd, FGR32Opnd, II_CVT>, ABS_FM_MM<1, 0x6d>; -def FABS_MM : MMRel, ABSS_FT<"abs.d", AFGR64Opnd, AFGR64Opnd, II_ABS, fabs>, - ABS_FM_MM<1, 0xd>; def FNEG_MM : MMRel, ABSS_FT<"neg.d", AFGR64Opnd, AFGR64Opnd, II_NEG, fneg>, ABS_FM_MM<1, 0x2d>; Index: lib/Target/Mips/Mips.td =================================================================== --- lib/Target/Mips/Mips.td +++ lib/Target/Mips/Mips.td @@ -79,6 +79,8 @@ "Support for FPXX">; def FeatureNaN2008 : SubtargetFeature<"nan2008", "IsNaN2008bit", "true", "IEEE 754-2008 NaN encoding">; +def FeatureAbs2008 : SubtargetFeature<"abs2008", "Abs2008", "true", + "IEEE 754-2008 abs mode">; def FeatureSingleFloat : SubtargetFeature<"single-float", "IsSingleFloat", "true", "Only supports single precision float">; def FeatureSoftFloat : SubtargetFeature<"soft-float", "IsSoftFloat", "true", @@ -138,7 +140,7 @@ "Mips32r6", "Mips32r6 ISA Support [experimental]", [FeatureMips32r5, FeatureFP64Bit, - FeatureNaN2008]>; + FeatureNaN2008, FeatureAbs2008]>; def FeatureMips64 : SubtargetFeature<"mips64", "MipsArchVersion", "Mips64", "Mips64 ISA Support", [FeatureMips5, FeatureMips32]>; @@ -155,7 +157,7 @@ "Mips64r6", "Mips64r6 ISA Support [experimental]", [FeatureMips32r6, FeatureMips64r5, - FeatureNaN2008]>; + FeatureNaN2008, FeatureAbs2008]>; def FeatureSym32 : SubtargetFeature<"sym32", "HasSym32", "true", "Symbols are 32 bit on Mips64">; Index: lib/Target/Mips/MipsISelLowering.cpp =================================================================== --- lib/Target/Mips/MipsISelLowering.cpp +++ lib/Target/Mips/MipsISelLowering.cpp @@ -368,6 +368,11 @@ setOperationAction(ISD::FCOPYSIGN, MVT::f64, Custom); setOperationAction(ISD::FP_TO_SINT, MVT::i32, Custom); + if (!(TM.Options.NoNaNsFPMath || Subtarget.inAbs2008Mode())) { + setOperationAction(ISD::FABS, MVT::f32, Custom); + setOperationAction(ISD::FABS, MVT::f64, Custom); + } + if (Subtarget.isGP64bit()) { setOperationAction(ISD::GlobalAddress, MVT::i64, Custom); setOperationAction(ISD::BlockAddress, MVT::i64, Custom); @@ -1267,6 +1272,7 @@ case ISD::VASTART: return lowerVASTART(Op, DAG); case ISD::VAARG: return lowerVAARG(Op, DAG); case ISD::FCOPYSIGN: return lowerFCOPYSIGN(Op, DAG); + case ISD::FABS: return lowerFABS(Op, DAG); case ISD::FRAMEADDR: return lowerFRAMEADDR(Op, DAG); case ISD::RETURNADDR: return lowerRETURNADDR(Op, DAG); case ISD::EH_RETURN: return lowerEH_RETURN(Op, DAG); @@ -2399,6 +2405,71 @@ return lowerFCOPYSIGN32(Op, DAG, Subtarget.hasExtractInsert()); } +static SDValue lowerFABS32(SDValue Op, SelectionDAG &DAG, + bool HasExtractInsert) { + SDLoc DL(Op); + SDValue Res, Const1 = DAG.getConstant(1, DL, MVT::i32); + + // If operand is of type f64, extract the upper 32-bit. Otherwise, bitcast it + // to i32. + SDValue X = (Op.getValueType() == MVT::f32) + ? DAG.getNode(ISD::BITCAST, DL, MVT::i32, Op.getOperand(0)) + : DAG.getNode(MipsISD::ExtractElementF64, DL, MVT::i32, + Op.getOperand(0), Const1); + + // Clear MSB. + if (HasExtractInsert) + Res = DAG.getNode(MipsISD::Ins, DL, MVT::i32, + DAG.getRegister(Mips::ZERO, MVT::i32), + DAG.getConstant(31, DL, MVT::i32), Const1, X); + else { + // TODO: Provide DAG patterns which transform (and x, cst) + // back to a (shl (srl x (clz cst)) (clz cst)) sequence. + SDValue SllX = DAG.getNode(ISD::SHL, DL, MVT::i32, X, Const1); + Res = DAG.getNode(ISD::SRL, DL, MVT::i32, SllX, Const1); + } + + if (Op.getValueType() == MVT::f32) + return DAG.getNode(ISD::BITCAST, DL, MVT::f32, Res); + + // FIXME: For mips32r2, the sequence of (BuildPairF64 (ins (ExtractElementF64 + // Op 1), $zero, 31 1) (ExtractElementF64 Op 0)) and the Op has one use, we + // should be able to drop the usage of mfc1/mtc1 and rewrite the register in + // place. + SDValue LowX = + DAG.getNode(MipsISD::ExtractElementF64, DL, MVT::i32, Op.getOperand(0), + DAG.getConstant(0, DL, MVT::i32)); + return DAG.getNode(MipsISD::BuildPairF64, DL, MVT::f64, LowX, Res); +} + +static SDValue lowerFABS64(SDValue Op, SelectionDAG &DAG, + bool HasExtractInsert) { + SDLoc DL(Op); + SDValue Res, Const1 = DAG.getConstant(1, DL, MVT::i32); + + // Bitcast to integer node. + SDValue X = DAG.getNode(ISD::BITCAST, DL, MVT::i64, Op.getOperand(0)); + + // Clear MSB. + if (HasExtractInsert) + Res = DAG.getNode(MipsISD::Ins, DL, MVT::i64, + DAG.getRegister(Mips::ZERO_64, MVT::i64), + DAG.getConstant(63, DL, MVT::i32), Const1, X); + else { + SDValue SllX = DAG.getNode(ISD::SHL, DL, MVT::i64, X, Const1); + Res = DAG.getNode(ISD::SRL, DL, MVT::i64, SllX, Const1); + } + + return DAG.getNode(ISD::BITCAST, DL, MVT::f64, Res); +} + +SDValue MipsTargetLowering::lowerFABS(SDValue Op, SelectionDAG &DAG) const { + if ((ABI.IsN32() || ABI.IsN64()) && (Op.getValueType() == MVT::f64)) + return lowerFABS64(Op, DAG, Subtarget.hasExtractInsert()); + + return lowerFABS32(Op, DAG, Subtarget.hasExtractInsert()); +} + SDValue MipsTargetLowering:: lowerFRAMEADDR(SDValue Op, SelectionDAG &DAG) const { // check the depth Index: lib/Target/Mips/MipsInstrFPU.td =================================================================== --- lib/Target/Mips/MipsInstrFPU.td +++ lib/Target/Mips/MipsInstrFPU.td @@ -425,11 +425,14 @@ def PseudoCVT_D64_L : ABSS_FT<"", FGR64Opnd, GPR64Opnd, II_CVT>; } -def FABS_S : MMRel, ABSS_FT<"abs.s", FGR32Opnd, FGR32Opnd, II_ABS, fabs>, - ABSS_FM<0x5, 16>; +let AdditionalPredicates = [NotInMicroMips, UseAbs] in { + def FABS_S : MMRel, ABSS_FT<"abs.s", FGR32Opnd, FGR32Opnd, II_ABS, fabs>, + ABSS_FM<0x5, 16>; + defm FABS : ABSS_M<"abs.d", II_ABS, fabs>, ABSS_FM<0x5, 17>; +} + def FNEG_S : MMRel, ABSS_FT<"neg.s", FGR32Opnd, FGR32Opnd, II_NEG, fneg>, ABSS_FM<0x7, 16>; -defm FABS : ABSS_M<"abs.d", II_ABS, fabs>, ABSS_FM<0x5, 17>; defm FNEG : ABSS_M<"neg.d", II_NEG, fneg>, ABSS_FM<0x7, 17>; def FSQRT_S : MMRel, StdMMR6Rel, ABSS_FT<"sqrt.s", FGR32Opnd, FGR32Opnd, Index: lib/Target/Mips/MipsInstrInfo.td =================================================================== --- lib/Target/Mips/MipsInstrInfo.td +++ lib/Target/Mips/MipsInstrInfo.td @@ -225,6 +225,8 @@ def RelocNotPIC : Predicate<"!TM.isPositionIndependent()">; def RelocPIC : Predicate<"TM.isPositionIndependent()">; def NoNaNsFPMath : Predicate<"TM.Options.NoNaNsFPMath">; +def UseAbs : Predicate<"Subtarget->inAbs2008Mode() ||" + "TM.Options.NoNaNsFPMath">; def HasStdEnc : Predicate<"Subtarget->hasStandardEncoding()">, AssemblerPredicate<"!FeatureMips16">; def NotDSP : Predicate<"!Subtarget->hasDSP()">; Index: lib/Target/Mips/MipsSubtarget.h =================================================================== --- lib/Target/Mips/MipsSubtarget.h +++ lib/Target/Mips/MipsSubtarget.h @@ -78,6 +78,9 @@ // IsNan2008 - IEEE 754-2008 NaN encoding. bool IsNaN2008bit; + // Abs2008 - Use IEEE 754-2008 Abs instruction. + bool Abs2008; + // IsGP64bit - General-purpose registers are 64 bits wide bool IsGP64bit; @@ -241,6 +244,7 @@ bool useOddSPReg() const { return UseOddSPReg; } bool noOddSPReg() const { return !UseOddSPReg; } bool isNaN2008() const { return IsNaN2008bit; } + bool inAbs2008Mode() const { return Abs2008; } bool isGP64bit() const { return IsGP64bit; } bool isGP32bit() const { return !IsGP64bit; } unsigned getGPRSizeInBytes() const { return isGP64bit() ? 8 : 4; } Index: lib/Target/Mips/MipsSubtarget.cpp =================================================================== --- lib/Target/Mips/MipsSubtarget.cpp +++ lib/Target/Mips/MipsSubtarget.cpp @@ -65,16 +65,17 @@ : MipsGenSubtargetInfo(TT, CPU, FS), MipsArchVersion(MipsDefault), IsLittle(little), IsSoftFloat(false), IsSingleFloat(false), IsFPXX(false), NoABICalls(false), IsFP64bit(false), UseOddSPReg(true), - IsNaN2008bit(false), IsGP64bit(false), HasVFPU(false), HasCnMips(false), - HasMips3_32(false), HasMips3_32r2(false), HasMips4_32(false), - HasMips4_32r2(false), HasMips5_32r2(false), InMips16Mode(false), - InMips16HardFloat(Mips16HardFloat), InMicroMipsMode(false), HasDSP(false), - HasDSPR2(false), HasDSPR3(false), AllowMixed16_32(Mixed16_32 | Mips_Os16), - Os16(Mips_Os16), HasMSA(false), UseTCCInDIV(false), HasSym32(false), - HasEVA(false), DisableMadd4(false), HasMT(false), - StackAlignOverride(StackAlignOverride), TM(TM), TargetTriple(TT), - TSInfo(), InstrInfo(MipsInstrInfo::create( - initializeSubtargetDependencies(CPU, FS, TM))), + IsNaN2008bit(false), Abs2008(false), IsGP64bit(false), HasVFPU(false), + HasCnMips(false), HasMips3_32(false), HasMips3_32r2(false), + HasMips4_32(false), HasMips4_32r2(false), HasMips5_32r2(false), + InMips16Mode(false), InMips16HardFloat(Mips16HardFloat), + InMicroMipsMode(false), HasDSP(false), HasDSPR2(false), HasDSPR3(false), + AllowMixed16_32(Mixed16_32 | Mips_Os16), Os16(Mips_Os16), HasMSA(false), + UseTCCInDIV(false), HasSym32(false), HasEVA(false), DisableMadd4(false), + HasMT(false), StackAlignOverride(StackAlignOverride), TM(TM), + TargetTriple(TT), TSInfo(), + InstrInfo( + MipsInstrInfo::create(initializeSubtargetDependencies(CPU, FS, TM))), FrameLowering(MipsFrameLowering::create(*this)), TLInfo(MipsTargetLowering::create(TM, *this)) { @@ -104,11 +105,18 @@ if (IsFPXX && (isABI_N32() || isABI_N64())) report_fatal_error("FPXX is not permitted for the N32/N64 ABI's.", false); + if (inAbs2008Mode() && hasMips32() && !hasMips32r2()) { + report_fatal_error("IEEE 754-2008 Abs is not supported for the given " + "architecture.", + false); + } + if (hasMips32r6()) { StringRef ISA = hasMips64r6() ? "MIPS64r6" : "MIPS32r6"; assert(isFP64bit()); assert(isNaN2008()); + assert(inAbs2008Mode()); if (hasDSP()) report_fatal_error(ISA + " is not compatible with the DSP ASE", false); } Index: test/CodeGen/Mips/fabs.ll =================================================================== --- test/CodeGen/Mips/fabs.ll +++ test/CodeGen/Mips/fabs.ll @@ -1,23 +1,84 @@ -; Check that abs.[ds] is selected and does not depend on -enable-no-nans-fp-math -; They obey the Has2008 and ABS2008 configuration bits which govern the -; conformance to IEEE 754 (1985) and IEEE 754 (2008). When these bits are not -; present, they confirm to 1985. +; Check that abs.[ds] is only selected for mips32r6 or mips64r6 when no +; additional options are passed. For revisions prior mips32r6 and mips64r6, +; abs.[ds] does not generate the correct result when working with NaNs, and +; should be explicitly enabled with -enable-no-nans-fp-math or +abs2008 options. + ; In 1985 mode, abs.[ds] are arithmetic (i.e. they raise invalid operation ; exceptions when given NaN's). In 2008 mode, they are non-arithmetic (i.e. ; they are copies and don't raise any exceptions). -; RUN: llc < %s -mtriple=mipsel-linux-gnu -mcpu=mips32 | FileCheck %s -; RUN: llc < %s -mtriple=mipsel-linux-gnu -mcpu=mips32r2 | FileCheck %s -; RUN: llc < %s -mtriple=mipsel-linux-gnu -mcpu=mips32 -enable-no-nans-fp-math | FileCheck %s +; Testing default values +; RUN: llc < %s -mtriple=mipsel-linux-gnu -mcpu=mips32 | FileCheck %s \ +; RUN: -check-prefix=CHECK-ABSLEGACY +; RUN: llc < %s -mtriple=mips64el-linux-gnu -mcpu=mips64 | FileCheck %s \ +; RUN: -check-prefix=CHECK-ABSLEGACY +; RUN: llc < %s -mtriple=mipsel-linux-gnu -mcpu=mips32r2 | FileCheck %s \ +; RUN: -check-prefix=CHECK-ABSLEGACY +; RUN: llc < %s -mtriple=mips64el-linux-gnu -mcpu=mips64r2 | FileCheck %s \ +; RUN: -check-prefix=CHECK-ABSLEGACY +; RUN: llc < %s -mtriple=mipsel-linux-gnu -mcpu=mips32r6 | FileCheck %s \ +; RUN: -check-prefix=CHECK-ABS2008 +; RUN: llc < %s -mtriple=mips64el-linux-gnu -mcpu=mips64r6 | FileCheck %s \ +; RUN: -check-prefix=CHECK-ABS2008 +; RUN: llc < %s -mtriple=mips-linux-gnu -mcpu=mips32 | FileCheck %s \ +; RUN: -check-prefix=CHECK-ABSLEGACY +; RUN: llc < %s -mtriple=mips64-linux-gnu -mcpu=mips64 | FileCheck %s \ +; RUN: -check-prefix=CHECK-ABSLEGACY +; RUN: llc < %s -mtriple=mips-linux-gnu -mcpu=mips32r2 | FileCheck %s \ +; RUN: -check-prefix=CHECK-ABSLEGACY +; RUN: llc < %s -mtriple=mips64-linux-gnu -mcpu=mips64r2 | FileCheck %s \ +; RUN: -check-prefix=CHECK-ABSLEGACY +; RUN: llc < %s -mtriple=mips-linux-gnu -mcpu=mips32r6 | FileCheck %s \ +; RUN: -check-prefix=CHECK-ABS2008 +; RUN: llc < %s -mtriple=mips64-linux-gnu -mcpu=mips64r6 | FileCheck %s \ +; RUN: -check-prefix=CHECK-ABS2008 +; Testing non-default values +; RUN: llc < %s -mtriple=mipsel-linux-gnu -mcpu=mips32r2 -mattr=+abs2008 \ +; RUN: | FileCheck %s -check-prefix=CHECK-ABS2008 +; RUN: llc < %s -mtriple=mips64el-linux-gnu -mcpu=mips64r2 -mattr=+abs2008 \ +; RUN: | FileCheck %s -check-prefix=CHECK-ABS2008 +; RUN: llc < %s -mtriple=mips-linux-gnu -mcpu=mips32r2 -mattr=+abs2008 \ +; RUN: | FileCheck %s -check-prefix=CHECK-ABS2008 +; RUN: llc < %s -mtriple=mips64-linux-gnu -mcpu=mips64r2 -mattr=+abs2008 \ +; RUN: | FileCheck %s -check-prefix=CHECK-ABS2008 +; Testing -enable-no-nans-fp-math +; RUN: llc < %s -mtriple=mipsel-linux-gnu -mcpu=mips32 \ +; RUN: -enable-no-nans-fp-math | FileCheck %s -check-prefix=CHECK-ABS2008 +; RUN: llc < %s -mtriple=mips64el-linux-gnu -mcpu=mips64 \ +; RUN: -enable-no-nans-fp-math | FileCheck %s -check-prefix=CHECK-ABS2008 +; RUN: llc < %s -mtriple=mips-linux-gnu -mcpu=mips32 \ +; RUN: -enable-no-nans-fp-math | FileCheck %s -check-prefix=CHECK-ABS2008 +; RUN: llc < %s -mtriple=mips64-linux-gnu -mcpu=mips64 \ +; RUN: -enable-no-nans-fp-math | FileCheck %s -check-prefix=CHECK-ABS2008 -; RUN: llc < %s -mtriple=mips64el-linux-gnu -mcpu=mips64 | FileCheck %s -; RUN: llc < %s -mtriple=mips64el-linux-gnu -mcpu=mips64 -enable-no-nans-fp-math | FileCheck %s +; microMIPS +; Testing default values +; RUN: llc < %s -mtriple=mipsel-linux-gnu -mcpu=mips32 -mattr=+micromips \ +; RUN: | FileCheck %s -check-prefix=CHECK-ABSLEGACY +; RUN: llc < %s -mtriple=mipsel-linux-gnu -mcpu=mips32r2 -mattr=+micromips \ +; RUN: | FileCheck %s -check-prefix=CHECK-ABSLEGACY +; RUN: llc < %s -mtriple=mips-linux-gnu -mcpu=mips32 -mattr=+micromips \ +; RUN: | FileCheck %s -check-prefix=CHECK-ABSLEGACY +; RUN: llc < %s -mtriple=mips-linux-gnu -mcpu=mips32r2 -mattr=+micromips \ +; RUN: | FileCheck %s -check-prefix=CHECK-ABSLEGACY +; Testing non-default values +; RUN: llc < %s -mtriple=mipsel-linux-gnu -mcpu=mips32r2 \ +; RUN: -mattr=+abs2008,+micromips | FileCheck %s -check-prefix=CHECK-ABS2008 +; RUN: llc < %s -mtriple=mips-linux-gnu -mcpu=mips32r2 \ +; RUN: -mattr=+abs2008,+micromips | FileCheck %s -check-prefix=CHECK-ABS2008 +; Testing -enable-no-nans-fp-math +; RUN: llc < %s -mtriple=mipsel-linux-gnu -mcpu=mips32 -mattr=+micromips \ +; RUN: -enable-no-nans-fp-math | FileCheck %s -check-prefix=CHECK-ABS2008 +; RUN: llc < %s -mtriple=mips-linux-gnu -mcpu=mips32 -mattr=+micromips \ +; RUN: -enable-no-nans-fp-math | FileCheck %s -check-prefix=CHECK-ABS2008 define float @foo0(float %a) nounwind readnone { entry: ; CHECK-LABEL: foo0 -; CHECK: abs.s +; CHECK-ABS2008: abs.s +; CHECK-ABSLEGACY: {{(ori|ins)}} +; CHECK-ABSLEGACY-NOT: abs.s %call = tail call float @fabsf(float %a) nounwind readnone ret float %call @@ -29,7 +90,9 @@ entry: ; CHECK-LABEL: foo1: -; CHECK: abs.d +; CHECK-ABS2008: abs.d +; CHECK-ABSLEGACY: {{(ori|ins|dsll)}} +; CHECK-ABSLEGACY-NOT: abs.d %call = tail call double @fabs(double %a) nounwind readnone ret double %call Index: test/CodeGen/Mips/msa/f16-llvm-ir.ll =================================================================== --- test/CodeGen/Mips/msa/f16-llvm-ir.ll +++ test/CodeGen/Mips/msa/f16-llvm-ir.ll @@ -1,21 +1,26 @@ ; RUN: llc -relocation-model=pic -march=mipsel -mcpu=mips32r5 \ -; RUN: -mattr=+fp64,+msa -verify-machineinstrs < %s | FileCheck %s \ +; RUN: -mattr=+fp64,+msa,+abs2008 -verify-machineinstrs < %s \ +; RUN: | FileCheck %s \ ; RUN: --check-prefixes=ALL,MIPS32,MIPSR5,MIPS32-O32,MIPS32R5-O32 ; RUN: llc -relocation-model=pic -march=mips64el -mcpu=mips64r5 \ -; RUN: -mattr=+fp64,+msa -verify-machineinstrs -target-abi n32 < %s | FileCheck %s \ +; RUN: -mattr=+fp64,+msa,+abs2008 -verify-machineinstrs \ +; RUN: -target-abi n32 < %s | FileCheck %s \ ; RUN: --check-prefixes=ALL,MIPS64,MIPSR5,MIPS64-N32,MIPS64R5-N32 ; RUN: llc -relocation-model=pic -march=mips64el -mcpu=mips64r5 \ -; RUN: -mattr=+fp64,+msa -verify-machineinstrs -target-abi n64 < %s | FileCheck %s \ +; RUN: -mattr=+fp64,+msa,+abs2008 -verify-machineinstrs \ +; RUN: -target-abi n64 < %s | FileCheck %s \ ; RUN: --check-prefixes=ALL,MIPS64,MIPSR5,MIPS64-N64,MIPS64R5-N64 ; RUN: llc -relocation-model=pic -march=mipsel -mcpu=mips32r6 \ ; RUN: -mattr=+fp64,+msa -verify-machineinstrs < %s | FileCheck %s \ ; RUN: --check-prefixes=ALL,MIPS32,MIPSR6,MIPSR6-O32 ; RUN: llc -relocation-model=pic -march=mips64el -mcpu=mips64r6 \ -; RUN: -mattr=+fp64,+msa -verify-machineinstrs -target-abi n32 < %s | FileCheck %s \ +; RUN: -mattr=+fp64,+msa -verify-machineinstrs -target-abi n32 < %s \ +; RUN: | FileCheck %s \ ; RUN: --check-prefixes=ALL,MIPS64,MIPSR6,MIPS64-N32,MIPSR6-N32 ; RUN: llc -relocation-model=pic -march=mips64el -mcpu=mips64r6 \ -; RUN: -mattr=+fp64,+msa -verify-machineinstrs -target-abi n64 < %s | FileCheck %s \ +; RUN: -mattr=+fp64,+msa -verify-machineinstrs -target-abi n64 < %s \ +; RUN: | FileCheck %s \ ; RUN: --check-prefixes=ALL,MIPS64,MIPSR6,MIPS64-N64,MIPSR6-N64