forked from OSchip/llvm-project
Add MC support for the v8fp instructions: vmaxnm and vminnm.
llvm-svn: 185767
This commit is contained in:
parent
48b6a881be
commit
2efaa733a2
|
@ -1549,7 +1549,7 @@ class ADbI<bits<5> opcod1, bits<2> opcod2, bit op6, bit op4, dag oops,
|
||||||
}
|
}
|
||||||
|
|
||||||
// FP, binary, not predicated
|
// FP, binary, not predicated
|
||||||
class ADbInp<bits<5> opcod1, bits<2> opcod2, dag oops, dag iops,
|
class ADbInp<bits<5> opcod1, bits<2> opcod2, bit opcod3, dag oops, dag iops,
|
||||||
InstrItinClass itin, string asm, list<dag> pattern>
|
InstrItinClass itin, string asm, list<dag> pattern>
|
||||||
: VFPXI<oops, iops, AddrModeNone, 4, IndexModeNone,
|
: VFPXI<oops, iops, AddrModeNone, 4, IndexModeNone,
|
||||||
VFPBinaryFrm, itin, asm, "", pattern>
|
VFPBinaryFrm, itin, asm, "", pattern>
|
||||||
|
@ -1573,7 +1573,7 @@ class ADbInp<bits<5> opcod1, bits<2> opcod2, dag oops, dag iops,
|
||||||
let Inst{21-20} = opcod2;
|
let Inst{21-20} = opcod2;
|
||||||
let Inst{11-9} = 0b101;
|
let Inst{11-9} = 0b101;
|
||||||
let Inst{8} = 1; // double precision
|
let Inst{8} = 1; // double precision
|
||||||
let Inst{6} = 0;
|
let Inst{6} = opcod3;
|
||||||
let Inst{4} = 0;
|
let Inst{4} = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1637,7 +1637,7 @@ class ASbI<bits<5> opcod1, bits<2> opcod2, bit op6, bit op4, dag oops, dag iops,
|
||||||
}
|
}
|
||||||
|
|
||||||
// Single precision, binary, not predicated
|
// Single precision, binary, not predicated
|
||||||
class ASbInp<bits<5> opcod1, bits<2> opcod2, dag oops, dag iops,
|
class ASbInp<bits<5> opcod1, bits<2> opcod2, bit opcod3, dag oops, dag iops,
|
||||||
InstrItinClass itin, string asm, list<dag> pattern>
|
InstrItinClass itin, string asm, list<dag> pattern>
|
||||||
: VFPXI<oops, iops, AddrModeNone, 4, IndexModeNone,
|
: VFPXI<oops, iops, AddrModeNone, 4, IndexModeNone,
|
||||||
VFPBinaryFrm, itin, asm, "", pattern>
|
VFPBinaryFrm, itin, asm, "", pattern>
|
||||||
|
@ -1661,7 +1661,7 @@ class ASbInp<bits<5> opcod1, bits<2> opcod2, dag oops, dag iops,
|
||||||
let Inst{21-20} = opcod2;
|
let Inst{21-20} = opcod2;
|
||||||
let Inst{11-9} = 0b101;
|
let Inst{11-9} = 0b101;
|
||||||
let Inst{8} = 0; // Single precision
|
let Inst{8} = 0; // Single precision
|
||||||
let Inst{6} = 0;
|
let Inst{6} = opcod3;
|
||||||
let Inst{4} = 0;
|
let Inst{4} = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -335,12 +335,12 @@ def VNMULS : ASbI<0b11100, 0b10, 1, 0,
|
||||||
|
|
||||||
multiclass vsel_inst<string op, bits<2> opc> {
|
multiclass vsel_inst<string op, bits<2> opc> {
|
||||||
let DecoderNamespace = "VFPV8", PostEncoderMethod = "" in {
|
let DecoderNamespace = "VFPV8", PostEncoderMethod = "" in {
|
||||||
def S : ASbInp<0b11100, opc,
|
def S : ASbInp<0b11100, opc, 0,
|
||||||
(outs SPR:$Sd), (ins SPR:$Sn, SPR:$Sm),
|
(outs SPR:$Sd), (ins SPR:$Sn, SPR:$Sm),
|
||||||
NoItinerary, !strconcat("vsel", op, ".f32\t$Sd, $Sn, $Sm"),
|
NoItinerary, !strconcat("vsel", op, ".f32\t$Sd, $Sn, $Sm"),
|
||||||
[]>, Requires<[HasV8FP]>;
|
[]>, Requires<[HasV8FP]>;
|
||||||
|
|
||||||
def D : ADbInp<0b11100, opc,
|
def D : ADbInp<0b11100, opc, 0,
|
||||||
(outs DPR:$Dd), (ins DPR:$Dn, DPR:$Dm),
|
(outs DPR:$Dd), (ins DPR:$Dn, DPR:$Dm),
|
||||||
NoItinerary, !strconcat("vsel", op, ".f64\t$Dd, $Dn, $Dm"),
|
NoItinerary, !strconcat("vsel", op, ".f64\t$Dd, $Dn, $Dm"),
|
||||||
[]>, Requires<[HasV8FP]>;
|
[]>, Requires<[HasV8FP]>;
|
||||||
|
@ -352,6 +352,23 @@ defm VSELGE : vsel_inst<"ge", 0b10>;
|
||||||
defm VSELEQ : vsel_inst<"eq", 0b00>;
|
defm VSELEQ : vsel_inst<"eq", 0b00>;
|
||||||
defm VSELVS : vsel_inst<"vs", 0b01>;
|
defm VSELVS : vsel_inst<"vs", 0b01>;
|
||||||
|
|
||||||
|
multiclass vmaxmin_inst<string op, bit opc> {
|
||||||
|
let DecoderNamespace = "VFPV8", PostEncoderMethod = "" in {
|
||||||
|
def S : ASbInp<0b11101, 0b00, opc,
|
||||||
|
(outs SPR:$Sd), (ins SPR:$Sn, SPR:$Sm),
|
||||||
|
NoItinerary, !strconcat(op, ".f32\t$Sd, $Sn, $Sm"),
|
||||||
|
[]>, Requires<[HasV8FP]>;
|
||||||
|
|
||||||
|
def D : ADbInp<0b11101, 0b00, opc,
|
||||||
|
(outs DPR:$Dd), (ins DPR:$Dn, DPR:$Dm),
|
||||||
|
NoItinerary, !strconcat(op, ".f64\t$Dd, $Dn, $Dm"),
|
||||||
|
[]>, Requires<[HasV8FP]>;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
defm VMAXNM : vmaxmin_inst<"vmaxnm", 0>;
|
||||||
|
defm VMINNM : vmaxmin_inst<"vminnm", 1>;
|
||||||
|
|
||||||
// Match reassociated forms only if not sign dependent rounding.
|
// Match reassociated forms only if not sign dependent rounding.
|
||||||
def : Pat<(fmul (fneg DPR:$a), (f64 DPR:$b)),
|
def : Pat<(fmul (fneg DPR:$a), (f64 DPR:$b)),
|
||||||
(VNMULD DPR:$a, DPR:$b)>, Requires<[NoHonorSignDependentRounding]>;
|
(VNMULD DPR:$a, DPR:$b)>, Requires<[NoHonorSignDependentRounding]>;
|
||||||
|
|
|
@ -4905,7 +4905,8 @@ StringRef ARMAsmParser::splitMnemonic(StringRef Mnemonic,
|
||||||
Mnemonic == "vcgt" || Mnemonic == "vcle" || Mnemonic == "smlal" ||
|
Mnemonic == "vcgt" || Mnemonic == "vcle" || Mnemonic == "smlal" ||
|
||||||
Mnemonic == "umaal" || Mnemonic == "umlal" || Mnemonic == "vabal" ||
|
Mnemonic == "umaal" || Mnemonic == "umlal" || Mnemonic == "vabal" ||
|
||||||
Mnemonic == "vmlal" || Mnemonic == "vpadal" || Mnemonic == "vqdmlal" ||
|
Mnemonic == "vmlal" || Mnemonic == "vpadal" || Mnemonic == "vqdmlal" ||
|
||||||
Mnemonic == "fmuls" || Mnemonic.startswith("vsel"))
|
Mnemonic == "fmuls" || Mnemonic == "vmaxnm" || Mnemonic == "vminnm" ||
|
||||||
|
Mnemonic.startswith("vsel"))
|
||||||
return Mnemonic;
|
return Mnemonic;
|
||||||
|
|
||||||
// First, split out any predication code. Ignore mnemonics we know aren't
|
// First, split out any predication code. Ignore mnemonics we know aren't
|
||||||
|
@ -5005,7 +5006,8 @@ getMnemonicAcceptInfo(StringRef Mnemonic, bool &CanAcceptCarrySet,
|
||||||
if (Mnemonic == "bkpt" || Mnemonic == "cbnz" || Mnemonic == "setend" ||
|
if (Mnemonic == "bkpt" || Mnemonic == "cbnz" || Mnemonic == "setend" ||
|
||||||
Mnemonic == "cps" || Mnemonic == "it" || Mnemonic == "cbz" ||
|
Mnemonic == "cps" || Mnemonic == "it" || Mnemonic == "cbz" ||
|
||||||
Mnemonic == "trap" || Mnemonic == "setend" ||
|
Mnemonic == "trap" || Mnemonic == "setend" ||
|
||||||
Mnemonic.startswith("cps") || Mnemonic.startswith("vsel")) {
|
Mnemonic.startswith("cps") || Mnemonic == "vmaxnm" ||
|
||||||
|
Mnemonic == "vminnm" || Mnemonic.startswith("vsel")) {
|
||||||
// These mnemonics are never predicable
|
// These mnemonics are never predicable
|
||||||
CanAcceptPredicationCode = false;
|
CanAcceptPredicationCode = false;
|
||||||
} else if (!isThumb()) {
|
} else if (!isThumb()) {
|
||||||
|
|
|
@ -39,3 +39,14 @@
|
||||||
@ CHECK: vselvs.f32 s21, s16, s14 @ encoding: [0x07,0xaa,0x58,0xfe]
|
@ CHECK: vselvs.f32 s21, s16, s14 @ encoding: [0x07,0xaa,0x58,0xfe]
|
||||||
vselvs.f64 d0, d1, d31
|
vselvs.f64 d0, d1, d31
|
||||||
@ CHECK: vselvs.f64 d0, d1, d31 @ encoding: [0x2f,0x0b,0x11,0xfe]
|
@ CHECK: vselvs.f64 d0, d1, d31 @ encoding: [0x2f,0x0b,0x11,0xfe]
|
||||||
|
|
||||||
|
|
||||||
|
@ VMAXNM / VMINNM
|
||||||
|
vmaxnm.f32 s5, s12, s0
|
||||||
|
@ CHECK: vmaxnm.f32 s5, s12, s0 @ encoding: [0x00,0x2a,0xc6,0xfe]
|
||||||
|
vmaxnm.f64 d5, d22, d30
|
||||||
|
@ CHECK: vmaxnm.f64 d5, d22, d30 @ encoding: [0xae,0x5b,0x86,0xfe]
|
||||||
|
vminnm.f32 s0, s0, s12
|
||||||
|
@ CHECK: vminnm.f32 s0, s0, s12 @ encoding: [0x46,0x0a,0x80,0xfe]
|
||||||
|
vminnm.f64 d4, d6, d9
|
||||||
|
@ CHECK: vminnm.f64 d4, d6, d9 @ encoding: [0x49,0x4b,0x86,0xfe]
|
||||||
|
|
|
@ -48,3 +48,16 @@
|
||||||
|
|
||||||
0x2f 0x0b 0x11 0xfe
|
0x2f 0x0b 0x11 0xfe
|
||||||
# CHECK: vselvs.f64 d0, d1, d31
|
# CHECK: vselvs.f64 d0, d1, d31
|
||||||
|
|
||||||
|
|
||||||
|
0x00 0x2a 0xc6 0xfe
|
||||||
|
# CHECK: vmaxnm.f32 s5, s12, s0
|
||||||
|
|
||||||
|
0xae 0x5b 0x86 0xfe
|
||||||
|
# CHECK: vmaxnm.f64 d5, d22, d30
|
||||||
|
|
||||||
|
0x46 0x0a 0x80 0xfe
|
||||||
|
# CHECK: vminnm.f32 s0, s0, s12
|
||||||
|
|
||||||
|
0x49 0x4b 0x86 0xfe
|
||||||
|
# CHECK: vminnm.f64 d4, d6, d9
|
||||||
|
|
Loading…
Reference in New Issue