diff options
author | Derek Schuff <dschuff@chromium.org> | 2012-11-27 11:21:28 -0800 |
---|---|---|
committer | Derek Schuff <dschuff@chromium.org> | 2012-11-27 11:22:07 -0800 |
commit | 3c4392af7177f4bd64bdc8659de729b9e65716e8 (patch) | |
tree | e38ea5f509f28448725fc257c7f0276eac4f647a /lib/Target/ARM/InstPrinter | |
parent | 3b46d602e10074ce1d54b49a3c5ec9ed708425a6 (diff) | |
parent | 8d20b5f9ff609e70fae5c865931ab0f29e639d9c (diff) |
Merge commit '8d20b5f9ff609e70fae5c865931ab0f29e639d9c'
Conflicts:
lib/CodeGen/AsmPrinter/DwarfDebug.cpp
lib/CodeGen/AsmPrinter/DwarfDebug.h
lib/Target/ARM/MCTargetDesc/ARMAsmBackend.cpp
lib/Target/Mips/MipsISelDAGToDAG.cpp
lib/Target/Mips/MipsInstrFPU.td
lib/Target/Mips/MipsSubtarget.cpp
lib/Target/Mips/MipsSubtarget.h
lib/Target/X86/X86MCInstLower.cpp
tools/Makefile
tools/llc/llc.cpp
Diffstat (limited to 'lib/Target/ARM/InstPrinter')
-rw-r--r-- | lib/Target/ARM/InstPrinter/ARMInstPrinter.cpp | 38 | ||||
-rw-r--r-- | lib/Target/ARM/InstPrinter/ARMInstPrinter.h | 1 |
2 files changed, 39 insertions, 0 deletions
diff --git a/lib/Target/ARM/InstPrinter/ARMInstPrinter.cpp b/lib/Target/ARM/InstPrinter/ARMInstPrinter.cpp index beeabb6d42..75de07e7a9 100644 --- a/lib/Target/ARM/InstPrinter/ARMInstPrinter.cpp +++ b/lib/Target/ARM/InstPrinter/ARMInstPrinter.cpp @@ -317,6 +317,35 @@ void ARMInstPrinter::printInst(const MCInst *MI, raw_ostream &O, return; } + // Combine 2 GPRs from disassember into a GPRPair to match with instr def. + // ldrexd/strexd require even/odd GPR pair. To enforce this constraint, + // a single GPRPair reg operand is used in the .td file to replace the two + // GPRs. However, when decoding them, the two GRPs cannot be automatically + // expressed as a GPRPair, so we have to manually merge them. + // FIXME: We would really like to be able to tablegen'erate this. + if (Opcode == ARM::LDREXD || Opcode == ARM::STREXD) { + const MCRegisterClass& MRC = MRI.getRegClass(ARM::GPRRegClassID); + bool isStore = Opcode == ARM::STREXD; + unsigned Reg = MI->getOperand(isStore ? 1 : 0).getReg(); + if (MRC.contains(Reg)) { + MCInst NewMI; + MCOperand NewReg; + NewMI.setOpcode(Opcode); + + if (isStore) + NewMI.addOperand(MI->getOperand(0)); + NewReg = MCOperand::CreateReg(MRI.getMatchingSuperReg(Reg, ARM::gsub_0, + &MRI.getRegClass(ARM::GPRPairRegClassID))); + NewMI.addOperand(NewReg); + + // Copy the rest operands into NewMI. + for(unsigned i= isStore ? 3 : 2; i < MI->getNumOperands(); ++i) + NewMI.addOperand(MI->getOperand(i)); + printInstruction(&NewMI, O); + return; + } + } + printInstruction(MI, O); printAnnotation(O, Annot); } @@ -756,6 +785,15 @@ void ARMInstPrinter::printRegisterList(const MCInst *MI, unsigned OpNum, O << "}"; } +void ARMInstPrinter::printGPRPairOperand(const MCInst *MI, unsigned OpNum, + raw_ostream &O) { + unsigned Reg = MI->getOperand(OpNum).getReg(); + printRegName(O, MRI.getSubReg(Reg, ARM::gsub_0)); + O << ", "; + printRegName(O, MRI.getSubReg(Reg, ARM::gsub_1)); +} + + void ARMInstPrinter::printSetendOperand(const MCInst *MI, unsigned OpNum, raw_ostream &O) { const MCOperand &Op = MI->getOperand(OpNum); diff --git a/lib/Target/ARM/InstPrinter/ARMInstPrinter.h b/lib/Target/ARM/InstPrinter/ARMInstPrinter.h index b7bab5fdcd..edff75d886 100644 --- a/lib/Target/ARM/InstPrinter/ARMInstPrinter.h +++ b/lib/Target/ARM/InstPrinter/ARMInstPrinter.h @@ -124,6 +124,7 @@ public: void printNEONModImmOperand(const MCInst *MI, unsigned OpNum, raw_ostream &O); void printImmPlusOneOperand(const MCInst *MI, unsigned OpNum, raw_ostream &O); void printRotImmOperand(const MCInst *MI, unsigned OpNum, raw_ostream &O); + void printGPRPairOperand(const MCInst *MI, unsigned OpNum, raw_ostream &O); void printPCLabel(const MCInst *MI, unsigned OpNum, raw_ostream &O); void printThumbLdrLabelOperand(const MCInst *MI, unsigned OpNum, |