summaryrefslogtreecommitdiffstats
path: root/llvm/lib/Target
diff options
context:
space:
mode:
authorSimon Dardis <simon.dardis@imgtec.com>2016-09-16 13:50:43 +0000
committerSimon Dardis <simon.dardis@imgtec.com>2016-09-16 13:50:43 +0000
commitcf060794cd4da110c96530f437f2f2586347b1f3 (patch)
treef6143302de154a4a2a1d110c84d214ec7ef7e0b7 /llvm/lib/Target
parentceae630c9b6f2f3ef9534efc733109ea1007de06 (diff)
downloadbcm5719-llvm-cf060794cd4da110c96530f437f2f2586347b1f3.tar.gz
bcm5719-llvm-cf060794cd4da110c96530f437f2f2586347b1f3.zip
[mips] Fix aui/daui/dahi/dati for MIPSR6
For compatiblity with binutils, define these instructions to take two registers with a 16bit unsigned immediate. Both of the registers have to be same for dahi and dati. Reviewers: vkalintiris, dsanders, zoran.jovanovic Differential Review: https://reviews.llvm.org/D21473 llvm-svn: 281724
Diffstat (limited to 'llvm/lib/Target')
-rw-r--r--llvm/lib/Target/Mips/AsmParser/MipsAsmParser.cpp10
-rw-r--r--llvm/lib/Target/Mips/Disassembler/MipsDisassembler.cpp36
-rw-r--r--llvm/lib/Target/Mips/MicroMips32r6InstrInfo.td2
-rw-r--r--llvm/lib/Target/Mips/MicroMips64r6InstrInfo.td12
-rw-r--r--llvm/lib/Target/Mips/Mips32r6InstrInfo.td2
-rw-r--r--llvm/lib/Target/Mips/Mips64r6InstrInfo.td10
-rw-r--r--llvm/lib/Target/Mips/MipsInstrInfo.td14
7 files changed, 75 insertions, 11 deletions
diff --git a/llvm/lib/Target/Mips/AsmParser/MipsAsmParser.cpp b/llvm/lib/Target/Mips/AsmParser/MipsAsmParser.cpp
index cdbf4a62c8c..600316acaeb 100644
--- a/llvm/lib/Target/Mips/AsmParser/MipsAsmParser.cpp
+++ b/llvm/lib/Target/Mips/AsmParser/MipsAsmParser.cpp
@@ -3824,6 +3824,8 @@ MipsAsmParser::checkEarlyTargetMatchPredicate(MCInst &Inst,
return Match_Success;
case Mips::DATI:
case Mips::DAHI:
+ case Mips::DATI_MM64R6:
+ case Mips::DAHI_MM64R6:
if (static_cast<MipsOperand &>(*Operands[1])
.isValidForTie(static_cast<MipsOperand &>(*Operands[2])))
return Match_Success;
@@ -3832,6 +3834,14 @@ MipsAsmParser::checkEarlyTargetMatchPredicate(MCInst &Inst,
}
unsigned MipsAsmParser::checkTargetMatchPredicate(MCInst &Inst) {
switch (Inst.getOpcode()) {
+ // As described by the MIPSR6 spec, daui must not use the zero operand for
+ // its source operand.
+ case Mips::DAUI:
+ case Mips::DAUI_MM64R6:
+ if (Inst.getOperand(1).getReg() == Mips::ZERO ||
+ Inst.getOperand(1).getReg() == Mips::ZERO_64)
+ return Match_RequiresNoZeroRegister;
+ return Match_Success;
// As described by the Mips32r2 spec, the registers Rd and Rs for
// jalr.hb must be different.
// It also applies for registers Rt and Rs of microMIPSr6 jalrc.hb instruction
diff --git a/llvm/lib/Target/Mips/Disassembler/MipsDisassembler.cpp b/llvm/lib/Target/Mips/Disassembler/MipsDisassembler.cpp
index f53998ea8e7..74a8f4f2152 100644
--- a/llvm/lib/Target/Mips/Disassembler/MipsDisassembler.cpp
+++ b/llvm/lib/Target/Mips/Disassembler/MipsDisassembler.cpp
@@ -439,6 +439,14 @@ static DecodeStatus DecodeINSVE_DF(MCInst &MI, InsnType insn, uint64_t Address,
const void *Decoder);
template <typename InsnType>
+static DecodeStatus DecodeDAHIDATIMMR6(MCInst &MI, InsnType insn, uint64_t Address,
+ const void *Decoder);
+
+template <typename InsnType>
+static DecodeStatus DecodeDAHIDATI(MCInst &MI, InsnType insn, uint64_t Address,
+ const void *Decoder);
+
+template <typename InsnType>
static DecodeStatus
DecodeAddiGroupBranch(MCInst &MI, InsnType insn, uint64_t Address,
const void *Decoder);
@@ -596,6 +604,34 @@ static DecodeStatus DecodeINSVE_DF(MCInst &MI, InsnType insn, uint64_t Address,
}
template <typename InsnType>
+static DecodeStatus DecodeDAHIDATIMMR6(MCInst &MI, InsnType insn, uint64_t Address,
+ const void *Decoder) {
+ InsnType Rt = fieldFromInstruction(insn, 16, 5);
+ InsnType Imm = fieldFromInstruction(insn, 0, 16);
+ MI.addOperand(MCOperand::createReg(getReg(Decoder, Mips::GPR64RegClassID,
+ Rt)));
+ MI.addOperand(MCOperand::createReg(getReg(Decoder, Mips::GPR64RegClassID,
+ Rt)));
+ MI.addOperand(MCOperand::createImm(Imm));
+
+ return MCDisassembler::Success;
+}
+
+template <typename InsnType>
+static DecodeStatus DecodeDAHIDATI(MCInst &MI, InsnType insn, uint64_t Address,
+ const void *Decoder) {
+ InsnType Rt = fieldFromInstruction(insn, 21, 5);
+ InsnType Imm = fieldFromInstruction(insn, 0, 16);
+ MI.addOperand(MCOperand::createReg(getReg(Decoder, Mips::GPR64RegClassID,
+ Rt)));
+ MI.addOperand(MCOperand::createReg(getReg(Decoder, Mips::GPR64RegClassID,
+ Rt)));
+ MI.addOperand(MCOperand::createImm(Imm));
+
+ return MCDisassembler::Success;
+}
+
+template <typename InsnType>
static DecodeStatus DecodeAddiGroupBranch(MCInst &MI, InsnType insn,
uint64_t Address,
const void *Decoder) {
diff --git a/llvm/lib/Target/Mips/MicroMips32r6InstrInfo.td b/llvm/lib/Target/Mips/MicroMips32r6InstrInfo.td
index b8d8aa0ce20..913074ba15a 100644
--- a/llvm/lib/Target/Mips/MicroMips32r6InstrInfo.td
+++ b/llvm/lib/Target/Mips/MicroMips32r6InstrInfo.td
@@ -567,7 +567,7 @@ class ALIGN_MMR6_DESC : ALIGN_MMR6_DESC_BASE<"align", GPR32Opnd, uimm2,
class AUI_MMR6_DESC_BASE<string instr_asm, RegisterOperand GPROpnd,
InstrItinClass Itin> : MMR6Arch<instr_asm> {
dag OutOperandList = (outs GPROpnd:$rt);
- dag InOperandList = (ins GPROpnd:$rs, simm16:$imm);
+ dag InOperandList = (ins GPROpnd:$rs, uimm16:$imm);
string AsmString = !strconcat(instr_asm, "\t$rt, $rs, $imm");
list<dag> Pattern = [];
InstrItinClass Itinerary = Itin;
diff --git a/llvm/lib/Target/Mips/MicroMips64r6InstrInfo.td b/llvm/lib/Target/Mips/MicroMips64r6InstrInfo.td
index 508b34299bb..1f152d0e190 100644
--- a/llvm/lib/Target/Mips/MicroMips64r6InstrInfo.td
+++ b/llvm/lib/Target/Mips/MicroMips64r6InstrInfo.td
@@ -81,7 +81,7 @@ class DAUI_MMR6_DESC_BASE<string instr_asm, RegisterOperand GPROpnd,
InstrItinClass Itin>
: MMR6Arch<instr_asm>, MipsR6Inst {
dag OutOperandList = (outs GPROpnd:$rt);
- dag InOperandList = (ins GPROpnd:$rs, simm16:$imm);
+ dag InOperandList = (ins GPROpnd:$rs, uimm16:$imm);
string AsmString = !strconcat(instr_asm, "\t$rt, $rs, $imm");
list<dag> Pattern = [];
InstrItinClass Itinerary = Itin;
@@ -92,8 +92,8 @@ class DAHI_DATI_DESC_BASE<string instr_asm, RegisterOperand GPROpnd,
InstrItinClass Itin>
: MMR6Arch<instr_asm>, MipsR6Inst {
dag OutOperandList = (outs GPROpnd:$rs);
- dag InOperandList = (ins GPROpnd:$rt, simm16:$imm);
- string AsmString = !strconcat(instr_asm, "\t$rt, $imm");
+ dag InOperandList = (ins GPROpnd:$rt, uimm16:$imm);
+ string AsmString = !strconcat(instr_asm, "\t$rs, $rt, $imm");
string Constraints = "$rs = $rt";
InstrItinClass Itinerary = Itin;
}
@@ -360,8 +360,10 @@ class LWUPC_MM64R6_DESC {
let DecoderNamespace = "MicroMipsR6" in {
def DAUI_MM64R6 : StdMMR6Rel, DAUI_MMR6_DESC, DAUI_MMR6_ENC, ISA_MICROMIPS64R6;
- def DAHI_MM64R6 : StdMMR6Rel, DAHI_MMR6_DESC, DAHI_MMR6_ENC, ISA_MICROMIPS64R6;
- def DATI_MM64R6 : StdMMR6Rel, DATI_MMR6_DESC, DATI_MMR6_ENC, ISA_MICROMIPS64R6;
+ let DecoderMethod = "DecodeDAHIDATIMMR6" in {
+ def DAHI_MM64R6 : StdMMR6Rel, DAHI_MMR6_DESC, DAHI_MMR6_ENC, ISA_MICROMIPS64R6;
+ def DATI_MM64R6 : StdMMR6Rel, DATI_MMR6_DESC, DATI_MMR6_ENC, ISA_MICROMIPS64R6;
+ }
def DEXT_MM64R6 : StdMMR6Rel, DEXT_MMR6_DESC, DEXT_MMR6_ENC,
ISA_MICROMIPS64R6;
def DEXTM_MM64R6 : StdMMR6Rel, DEXTM_MMR6_DESC, DEXTM_MMR6_ENC,
diff --git a/llvm/lib/Target/Mips/Mips32r6InstrInfo.td b/llvm/lib/Target/Mips/Mips32r6InstrInfo.td
index e81869513b6..34e3936b3cd 100644
--- a/llvm/lib/Target/Mips/Mips32r6InstrInfo.td
+++ b/llvm/lib/Target/Mips/Mips32r6InstrInfo.td
@@ -324,7 +324,7 @@ class AUI_DESC_BASE<string instr_asm, RegisterOperand GPROpnd,
InstrItinClass itin = NoItinerary>
: MipsR6Arch<instr_asm> {
dag OutOperandList = (outs GPROpnd:$rs);
- dag InOperandList = (ins GPROpnd:$rt, simm16:$imm);
+ dag InOperandList = (ins GPROpnd:$rt, uimm16:$imm);
string AsmString = !strconcat(instr_asm, "\t$rs, $rt, $imm");
list<dag> Pattern = [];
InstrItinClass Itinerary = itin;
diff --git a/llvm/lib/Target/Mips/Mips64r6InstrInfo.td b/llvm/lib/Target/Mips/Mips64r6InstrInfo.td
index c380dfdc480..dabf4e0a52e 100644
--- a/llvm/lib/Target/Mips/Mips64r6InstrInfo.td
+++ b/llvm/lib/Target/Mips/Mips64r6InstrInfo.td
@@ -48,8 +48,8 @@ class SCD_R6_ENC : SPECIAL3_LL_SC_FM<OPCODE6_SCD>;
class AHI_ATI_DESC_BASE<string instr_asm, RegisterOperand GPROpnd, InstrItinClass itin> {
dag OutOperandList = (outs GPROpnd:$rs);
- dag InOperandList = (ins GPROpnd:$rt, simm16_relaxed:$imm);
- string AsmString = !strconcat(instr_asm, "\t$rt, $rs, $imm");
+ dag InOperandList = (ins GPROpnd:$rt, uimm16_altrelaxed:$imm);
+ string AsmString = !strconcat(instr_asm, "\t$rs, $rt, $imm");
string Constraints = "$rs = $rt";
InstrItinClass Itinerary = itin;
}
@@ -111,8 +111,10 @@ class SC64_R6_DESC : SC_R6_DESC_BASE<"sc", GPR32Opnd, II_SC>;
//===----------------------------------------------------------------------===//
let AdditionalPredicates = [NotInMicroMips] in {
- def DATI : DATI_ENC, DATI_DESC, ISA_MIPS64R6;
- def DAHI : DAHI_ENC, DAHI_DESC, ISA_MIPS64R6;
+ let DecoderMethod = "DecodeDAHIDATI" in {
+ def DATI : DATI_ENC, DATI_DESC, ISA_MIPS64R6;
+ def DAHI : DAHI_ENC, DAHI_DESC, ISA_MIPS64R6;
+ }
def DAUI : DAUI_ENC, DAUI_DESC, ISA_MIPS64R6;
def DALIGN : DALIGN_ENC, DALIGN_DESC, ISA_MIPS64R6;
def DBITSWAP : R6MMR6Rel, DBITSWAP_ENC, DBITSWAP_DESC, ISA_MIPS64R6;
diff --git a/llvm/lib/Target/Mips/MipsInstrInfo.td b/llvm/lib/Target/Mips/MipsInstrInfo.td
index 39b31074608..131a7519d3c 100644
--- a/llvm/lib/Target/Mips/MipsInstrInfo.td
+++ b/llvm/lib/Target/Mips/MipsInstrInfo.td
@@ -507,6 +507,14 @@ def UImm16RelaxedAsmOperandClass
let PredicateMethod = "isAnyImm<16>";
let DiagnosticType = "UImm16_Relaxed";
}
+// Similar to the relaxed classes which take an SImm and render it as
+// an UImm, this takes a UImm and renders it as an SImm.
+def UImm16AltRelaxedAsmOperandClass
+ : SImmAsmOperandClass<16, [UImm16RelaxedAsmOperandClass]> {
+ let Name = "UImm16_AltRelaxed";
+ let PredicateMethod = "isUImm<16>";
+ let DiagnosticType = "UImm16_AltRelaxed";
+}
def UImm16AsmOperandClass
: UImmAsmOperandClass<16, [UImm16RelaxedAsmOperandClass]>;
def SImm16RelaxedAsmOperandClass
@@ -515,6 +523,7 @@ def SImm16RelaxedAsmOperandClass
let PredicateMethod = "isAnyImm<16>";
let DiagnosticType = "SImm16_Relaxed";
}
+
def SImm16AsmOperandClass
: SImmAsmOperandClass<16, [SImm16RelaxedAsmOperandClass]>;
def ConstantSImm10Lsl3AsmOperandClass : AsmOperandClass {
@@ -785,6 +794,11 @@ def uimm16_64_relaxed : Operand<i64> {
!cast<AsmOperandClass>("UImm16RelaxedAsmOperandClass");
}
+def uimm16_altrelaxed : Operand<i32> {
+ let PrintMethod = "printUImm<16>";
+ let ParserMatchClass =
+ !cast<AsmOperandClass>("UImm16AltRelaxedAsmOperandClass");
+}
// Like uimm5 but reports a less confusing error for 32-63 when
// an instruction alias permits that.
def uimm5_report_uimm6 : Operand<i32> {
OpenPOWER on IntegriCloud