summaryrefslogtreecommitdiffstats
path: root/llvm/lib/Target/MBlaze/Disassembler/MBlazeDisassembler.cpp
diff options
context:
space:
mode:
authorWesley Peck <peckw@wesleypeck.com>2010-11-13 02:37:59 +0000
committerWesley Peck <peckw@wesleypeck.com>2010-11-13 02:37:59 +0000
commitb3099e68634a9232dbfb0c6428039ab1342c4fc2 (patch)
treea660a464c7c81d2b7e9b8c9b98e60035d7d37fc2 /llvm/lib/Target/MBlaze/Disassembler/MBlazeDisassembler.cpp
parent2bcb8daa44d09221981a3e24e68239ab83e12e9d (diff)
downloadbcm5719-llvm-b3099e68634a9232dbfb0c6428039ab1342c4fc2.tar.gz
bcm5719-llvm-b3099e68634a9232dbfb0c6428039ab1342c4fc2.zip
1. Adding test cases for MBlaze MC disassembler.
2. Fixing several errors in disassembler uncovered by test cases. 3. Fixing invalid encoding of PCMPEQ and PCMPNE uncovered by test cases. llvm-svn: 118969
Diffstat (limited to 'llvm/lib/Target/MBlaze/Disassembler/MBlazeDisassembler.cpp')
-rw-r--r--llvm/lib/Target/MBlaze/Disassembler/MBlazeDisassembler.cpp94
1 files changed, 82 insertions, 12 deletions
diff --git a/llvm/lib/Target/MBlaze/Disassembler/MBlazeDisassembler.cpp b/llvm/lib/Target/MBlaze/Disassembler/MBlazeDisassembler.cpp
index e09829c70e8..c2b5a9f1a8f 100644
--- a/llvm/lib/Target/MBlaze/Disassembler/MBlazeDisassembler.cpp
+++ b/llvm/lib/Target/MBlaze/Disassembler/MBlazeDisassembler.cpp
@@ -103,7 +103,7 @@ static unsigned decodeMUL(uint32_t insn) {
}
static unsigned decodeSEXT(uint32_t insn) {
- switch (getIMM(insn)) {
+ switch (insn&0x7FF) {
default: return UNSUPPORTED;
case 0x60: return MBlaze::SEXT8;
case 0x68: return MBlaze::WIC;
@@ -118,7 +118,7 @@ static unsigned decodeSEXT(uint32_t insn) {
}
static unsigned decodeBEQ(uint32_t insn) {
- switch (getRD(insn)) {
+ switch ((insn>>21)&0x1F) {
default: return UNSUPPORTED;
case 0x00: return MBlaze::BEQ;
case 0x10: return MBlaze::BEQD;
@@ -136,7 +136,7 @@ static unsigned decodeBEQ(uint32_t insn) {
}
static unsigned decodeBEQI(uint32_t insn) {
- switch (getRD(insn)) {
+ switch ((insn>>21)&0x1F) {
default: return UNSUPPORTED;
case 0x00: return MBlaze::BEQI;
case 0x10: return MBlaze::BEQID;
@@ -342,6 +342,22 @@ static unsigned decodeIDIV(uint32_t insn) {
}
}
+static unsigned decodeLBU(uint32_t insn) {
+ switch ((insn>>9)&0x1) {
+ default: return UNSUPPORTED;
+ case 0x0: return MBlaze::LBU;
+ case 0x1: return MBlaze::LBUR;
+ }
+}
+
+static unsigned decodeLHU(uint32_t insn) {
+ switch ((insn>>9)&0x1) {
+ default: return UNSUPPORTED;
+ case 0x0: return MBlaze::LHU;
+ case 0x1: return MBlaze::LHUR;
+ }
+}
+
static unsigned decodeLW(uint32_t insn) {
switch ((insn>>9)&0x3) {
default: return UNSUPPORTED;
@@ -351,6 +367,22 @@ static unsigned decodeLW(uint32_t insn) {
}
}
+static unsigned decodeSB(uint32_t insn) {
+ switch ((insn>>9)&0x1) {
+ default: return UNSUPPORTED;
+ case 0x0: return MBlaze::SB;
+ case 0x1: return MBlaze::SBR;
+ }
+}
+
+static unsigned decodeSH(uint32_t insn) {
+ switch ((insn>>9)&0x1) {
+ default: return UNSUPPORTED;
+ case 0x0: return MBlaze::SH;
+ case 0x1: return MBlaze::SHR;
+ }
+}
+
static unsigned decodeSW(uint32_t insn) {
switch ((insn>>9)&0x3) {
default: return UNSUPPORTED;
@@ -364,10 +396,10 @@ static unsigned decodeMFS(uint32_t insn) {
switch ((insn>>15)&0x1) {
default: return UNSUPPORTED;
case 0x0:
- switch ((insn>>16)&0x1F) {
+ switch ((insn>>16)&0x1) {
default: return UNSUPPORTED;
- case 0x22: return MBlaze::MSRCLR;
- case 0x20: return MBlaze::MSRSET;
+ case 0x0: return MBlaze::MSRSET;
+ case 0x1: return MBlaze::MSRCLR;
}
case 0x1:
switch ((insn>>14)&0x1) {
@@ -389,7 +421,7 @@ static unsigned decodeOR(uint32_t insn) {
static unsigned decodeXOR(uint32_t insn) {
switch (getFLAGS(insn)) {
default: return UNSUPPORTED;
- case 0x000: return MBlaze::OR;
+ case 0x000: return MBlaze::XOR;
case 0x400: return MBlaze::PCMPEQ;
}
}
@@ -397,7 +429,7 @@ static unsigned decodeXOR(uint32_t insn) {
static unsigned decodeANDN(uint32_t insn) {
switch (getFLAGS(insn)) {
default: return UNSUPPORTED;
- case 0x000: return MBlaze::OR;
+ case 0x000: return MBlaze::ANDN;
case 0x400: return MBlaze::PCMPNE;
}
}
@@ -428,7 +460,11 @@ static unsigned getOPCODE(uint32_t insn) {
case MBlaze::GET: return decodeGET(insn);
case MBlaze::GETD: return decodeGETD(insn);
case MBlaze::IDIV: return decodeIDIV(insn);
+ case MBlaze::LBU: return decodeLBU(insn);
+ case MBlaze::LHU: return decodeLHU(insn);
case MBlaze::LW: return decodeLW(insn);
+ case MBlaze::SB: return decodeSB(insn);
+ case MBlaze::SH: return decodeSH(insn);
case MBlaze::SW: return decodeSW(insn);
case MBlaze::MFS: return decodeMFS(insn);
case MBlaze::OR: return decodeOR(insn);
@@ -455,7 +491,7 @@ bool MBlazeDisassembler::getInstruction(MCInst &instr,
// The machine instruction.
uint32_t insn;
uint8_t bytes[4];
-
+
// We want to read exactly 4 bytes of data.
if (region.readBytes(address, 4, (uint8_t*)bytes, NULL) == -1)
return false;
@@ -475,16 +511,50 @@ bool MBlazeDisassembler::getInstruction(MCInst &instr,
switch ((tsFlags & MBlazeII::FormMask)) {
default: llvm_unreachable("unknown instruction encoding");
+ case MBlazeII::FRRRR:
+ instr.addOperand(MCOperand::CreateReg(getRD(insn)));
+ instr.addOperand(MCOperand::CreateReg(getRB(insn)));
+ instr.addOperand(MCOperand::CreateReg(getRA(insn)));
+ break;
+
case MBlazeII::FRRR:
instr.addOperand(MCOperand::CreateReg(getRD(insn)));
instr.addOperand(MCOperand::CreateReg(getRA(insn)));
instr.addOperand(MCOperand::CreateReg(getRB(insn)));
break;
+ case MBlazeII::FRI:
+ switch (opcode) {
+ default: llvm_unreachable("unknown instruction encoding");
+ case MBlaze::MFS:
+ instr.addOperand(MCOperand::CreateReg(getRD(insn)));
+ instr.addOperand(MCOperand::CreateImm(insn&0x3FFF));
+ break;
+ case MBlaze::MTS:
+ instr.addOperand(MCOperand::CreateImm(insn&0x3FFF));
+ instr.addOperand(MCOperand::CreateReg(getRA(insn)));
+ break;
+ case MBlaze::MSRSET:
+ case MBlaze::MSRCLR:
+ instr.addOperand(MCOperand::CreateReg(getRD(insn)));
+ instr.addOperand(MCOperand::CreateImm(insn&0x7FFF));
+ break;
+ }
+ break;
+
case MBlazeII::FRRI:
instr.addOperand(MCOperand::CreateReg(getRD(insn)));
instr.addOperand(MCOperand::CreateReg(getRA(insn)));
- instr.addOperand(MCOperand::CreateImm(getIMM(insn)));
+ switch (opcode) {
+ default:
+ instr.addOperand(MCOperand::CreateImm(getIMM(insn)));
+ break;
+ case MBlaze::BSRLI:
+ case MBlaze::BSRAI:
+ case MBlaze::BSLLI:
+ instr.addOperand(MCOperand::CreateImm(insn&0x1F));
+ break;
+ }
break;
case MBlazeII::FCRR:
@@ -568,8 +638,8 @@ static MCDisassembler *createMBlazeDisassembler(const Target &T) {
return new MBlazeDisassembler;
}
-extern "C" void LLVMInitializeMBlazeDisassembler() {
+extern "C" void LLVMInitializeMBlazeDisassembler() {
// Register the disassembler.
- TargetRegistry::RegisterMCDisassembler(TheMBlazeTarget,
+ TargetRegistry::RegisterMCDisassembler(TheMBlazeTarget,
createMBlazeDisassembler);
}
OpenPOWER on IntegriCloud