llvm.org GIT mirror llvm / 8699f53
[Hexagon] Resubmission of 220427 Modified library structure to deal with circular dependency between HexagonInstPrinter and HexagonMCInst. Adding encoding bits for add opcode. Adding llvm-mc tests. Removing unit tests. http://reviews.llvm.org/D5624 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@220584 91177308-0d34-0410-b5e6-96231b3b80d8 Colin LeMahieu 5 years ago
25 changed file(s) with 583 addition(s) and 627 deletion(s). Raw diff Collapse all Expand all
3939 )
4040
4141 add_subdirectory(TargetInfo)
42 add_subdirectory(InstPrinter)
4342 add_subdirectory(MCTargetDesc)
4443 add_subdirectory(Disassembler)
4747 };
4848 }
4949
50 static const uint16_t IntRegDecoderTable[] = {
51 Hexagon::R0, Hexagon::R1, Hexagon::R2, Hexagon::R3, Hexagon::R4,
52 Hexagon::R5, Hexagon::R6, Hexagon::R7, Hexagon::R8, Hexagon::R9,
53 Hexagon::R10, Hexagon::R11, Hexagon::R12, Hexagon::R13, Hexagon::R14,
54 Hexagon::R15, Hexagon::R16, Hexagon::R17, Hexagon::R18, Hexagon::R19,
55 Hexagon::R20, Hexagon::R21, Hexagon::R22, Hexagon::R23, Hexagon::R24,
56 Hexagon::R25, Hexagon::R26, Hexagon::R27, Hexagon::R28, Hexagon::R29,
57 Hexagon::R30, Hexagon::R31};
58
59 static const uint16_t PredRegDecoderTable[] = {Hexagon::P0, Hexagon::P1,
60 Hexagon::P2, Hexagon::P3};
61
62 static DecodeStatus DecodeIntRegsRegisterClass(MCInst &Inst, unsigned RegNo,
63 uint64_t /*Address*/,
64 void const *Decoder) {
65 if (RegNo > 31)
66 return MCDisassembler::Fail;
67
68 unsigned Register = IntRegDecoderTable[RegNo];
69 Inst.addOperand(MCOperand::CreateReg(Register));
70 return MCDisassembler::Success;
71 }
72
73 static DecodeStatus DecodePredRegsRegisterClass(MCInst &Inst, unsigned RegNo,
74 uint64_t /*Address*/,
75 void const *Decoder) {
76 if (RegNo > 3)
77 return MCDisassembler::Fail;
78
79 unsigned Register = PredRegDecoderTable[RegNo];
80 Inst.addOperand(MCOperand::CreateReg(Register));
81 return MCDisassembler::Success;
82 }
83
5084 #include "HexagonGenDisassemblerTables.inc"
5185
5286 static MCDisassembler *createHexagonDisassembler(Target const &T,
1717 #include "HexagonMachineFunctionInfo.h"
1818 #include "HexagonSubtarget.h"
1919 #include "HexagonTargetMachine.h"
20 #include "InstPrinter/HexagonInstPrinter.h"
20 #include "MCTargetDesc/HexagonInstPrinter.h"
2121 #include "MCTargetDesc/HexagonMCInst.h"
2222 #include "llvm/ADT/SmallString.h"
2323 #include "llvm/ADT/SmallVector.h"
194194 unsigned Size = BundleMIs.size();
195195 assert((Size+IgnoreCount) == MI->getBundleSize() && "Corrupt Bundle!");
196196 for (unsigned Index = 0; Index < Size; Index++) {
197 HexagonMCInst MCI;
198 MCI.setPacketStart(Index == 0);
197 HexagonMCInst MCI (BundleMIs[Index]->getOpcode());
198 MCI.setPacketBegin(Index == 0);
199199 MCI.setPacketEnd(Index == (Size-1));
200200
201201 HexagonLowerToMC(BundleMIs[Index], MCI, *this);
203203 }
204204 }
205205 else {
206 HexagonMCInst MCI;
206 HexagonMCInst MCI(MI->getOpcode());
207207 if (MI->getOpcode() == Hexagon::ENDLOOP0) {
208 MCI.setPacketStart(true);
208 MCI.setPacketBegin(true);
209209 MCI.setPacketEnd(true);
210210 }
211211 HexagonLowerToMC(MI, MCI, *this);
9090
9191 def HexagonWrapperCombineRR :
9292 SDNode<"HexagonISD::WrapperCombineRR", SDTHexagonI64I32I32>;
93
94 let hasSideEffects = 0, hasNewValue = 1, InputType = "reg" in
95 class T_ALU32_3op MajOp, bits<3> MinOp, bit OpsRev,
96 bit IsComm>
97 : ALU32_rr<(outs IntRegs:$Rd), (ins IntRegs:$Rs, IntRegs:$Rt),
98 "$Rd = "#mnemonic#"($Rs, $Rt)",
99 [], "", ALU32_3op_tc_1_SLOT0123>, ImmRegRel, PredRel {
100 let isCommutable = IsComm;
101 let BaseOpcode = mnemonic#_rr;
102 let CextOpcode = mnemonic;
103
104 bits<5> Rs;
105 bits<5> Rt;
106 bits<5> Rd;
107
108 let IClass = 0b1111;
109 let Inst{27} = 0b0;
110 let Inst{26-24} = MajOp;
111 let Inst{23-21} = MinOp;
112 let Inst{20-16} = !if(OpsRev,Rt,Rs);
113 let Inst{12-8} = !if(OpsRev,Rs,Rt);
114 let Inst{4-0} = Rd;
115 }
116
117 let hasSideEffects = 0, hasNewValue = 1 in
118 class T_ALU32_3op_pred MajOp, bits<3> MinOp,
119 bit OpsRev, bit PredNot, bit PredNew>
120 : ALU32_rr<(outs IntRegs:$Rd), (ins PredRegs:$Pu, IntRegs:$Rs, IntRegs:$Rt),
121 "if ("#!if(PredNot,"!","")#"$Pu"#!if(PredNew,".new","")#") "#
122 "$Rd = "#mnemonic#"($Rs, $Rt)",
123 [], "", ALU32_3op_tc_1_SLOT0123>, ImmRegRel, PredNewRel {
124 let isPredicated = 1;
125 let isPredicatedFalse = PredNot;
126 let isPredicatedNew = PredNew;
127 let BaseOpcode = mnemonic#_rr;
128 let CextOpcode = mnemonic;
129
130 bits<2> Pu;
131 bits<5> Rs;
132 bits<5> Rt;
133 bits<5> Rd;
134
135 let IClass = 0b1111;
136 let Inst{27} = 0b1;
137 let Inst{26-24} = MajOp;
138 let Inst{23-21} = MinOp;
139 let Inst{20-16} = !if(OpsRev,Rt,Rs);
140 let Inst{13} = PredNew;
141 let Inst{12-8} = !if(OpsRev,Rs,Rt);
142 let Inst{7} = PredNot;
143 let Inst{6-5} = Pu;
144 let Inst{4-0} = Rd;
145 }
146
147 multiclass T_ALU32_3op_p MajOp, bits<3> MinOp,
148 bit OpsRev> {
149 def t : T_ALU32_3op_pred;
150 def f : T_ALU32_3op_pred;
151 def tnew : T_ALU32_3op_pred;
152 def fnew : T_ALU32_3op_pred;
153 }
154
155 multiclass T_ALU32_3op_A2 MajOp, bits<3> MinOp,
156 bit OpsRev, bit IsComm> {
157 let isPredicable = 1 in
158 def A2_#NAME : T_ALU32_3op ;
159 defm A2_p#NAME : T_ALU32_3op_p;
160 }
161
162 let isCodeGenOnly = 0 in
163 defm add : T_ALU32_3op_A2<"add", 0b011, 0b000, 0, 1>;
93164
94165 multiclass ALU32_Pbase
95166 bit isPredNew> {
2323
2424 using namespace llvm;
2525
26 static MCOperand GetSymbolRef(const MachineOperand& MO, const MCSymbol* Symbol,
27 HexagonAsmPrinter& Printer) {
26 static MCOperand GetSymbolRef(const MachineOperand &MO, const MCSymbol *Symbol,
27 HexagonAsmPrinter &Printer) {
2828 MCContext &MC = Printer.OutContext;
2929 const MCExpr *ME;
3030
3838 }
3939
4040 // Create an MCInst from a MachineInstr
41 void llvm::HexagonLowerToMC(const MachineInstr* MI, HexagonMCInst& MCI,
42 HexagonAsmPrinter& AP) {
43 MCI.setOpcode(MI->getOpcode());
44 MCI.setDesc(MI->getDesc());
41 void llvm::HexagonLowerToMC(const MachineInstr *MI, HexagonMCInst &MCI,
42 HexagonAsmPrinter &AP) {
43 assert(MCI.getOpcode() == static_cast(MI->getOpcode()) &&
44 "MCI opcode should have been set on construction");
4545
4646 for (unsigned i = 0, e = MI->getNumOperands(); i < e; i++) {
4747 const MachineOperand &MO = MI->getOperand(i);
5353 llvm_unreachable("unknown operand type");
5454 case MachineOperand::MO_Register:
5555 // Ignore all implicit register operands.
56 if (MO.isImplicit()) continue;
56 if (MO.isImplicit())
57 continue;
5758 MCO = MCOperand::CreateReg(MO.getReg());
5859 break;
5960 case MachineOperand::MO_FPImmediate: {
6768 MCO = MCOperand::CreateImm(MO.getImm());
6869 break;
6970 case MachineOperand::MO_MachineBasicBlock:
70 MCO = MCOperand::CreateExpr
71 (MCSymbolRefExpr::Create(MO.getMBB()->getSymbol(),
72 AP.OutContext));
71 MCO = MCOperand::CreateExpr(
72 MCSymbolRefExpr::Create(MO.getMBB()->getSymbol(), AP.OutContext));
7373 break;
7474 case MachineOperand::MO_GlobalAddress:
7575 MCO = GetSymbolRef(MO, AP.getSymbol(MO.getGlobal()), AP);
7676 break;
7777 case MachineOperand::MO_ExternalSymbol:
78 MCO = GetSymbolRef(MO, AP.GetExternalSymbolSymbol(MO.getSymbolName()),
79 AP);
78 MCO =
79 GetSymbolRef(MO, AP.GetExternalSymbolSymbol(MO.getSymbolName()), AP);
8080 break;
8181 case MachineOperand::MO_JumpTableIndex:
8282 MCO = GetSymbolRef(MO, AP.GetJTISymbol(MO.getIndex()), AP);
8585 MCO = GetSymbolRef(MO, AP.GetCPISymbol(MO.getIndex()), AP);
8686 break;
8787 case MachineOperand::MO_BlockAddress:
88 MCO = GetSymbolRef(MO, AP.GetBlockAddressSymbol(MO.getBlockAddress()),AP);
88 MCO =
89 GetSymbolRef(MO, AP.GetBlockAddressSymbol(MO.getBlockAddress()), AP);
8990 break;
9091 }
9192
+0
-3
lib/Target/Hexagon/InstPrinter/CMakeLists.txt less more
None add_llvm_library(LLVMHexagonAsmPrinter
1 HexagonInstPrinter.cpp
2 )
+0
-254
lib/Target/Hexagon/InstPrinter/HexagonInstPrinter.cpp less more
None //===- HexagonInstPrinter.cpp - Convert Hexagon MCInst to assembly syntax -===//
1 //
2 // The LLVM Compiler Infrastructure
3 //
4 // This file is distributed under the University of Illinois Open Source
5 // License. See LICENSE.TXT for details.
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This class prints an Hexagon MCInst to a .s file.
10 //
11 //===----------------------------------------------------------------------===//
12
13 #include "HexagonAsmPrinter.h"
14 #include "Hexagon.h"
15 #include "HexagonInstPrinter.h"
16 #include "MCTargetDesc/HexagonMCInst.h"
17 #include "llvm/ADT/StringExtras.h"
18 #include "llvm/MC/MCAsmInfo.h"
19 #include "llvm/MC/MCExpr.h"
20 #include "llvm/MC/MCInst.h"
21 #include "llvm/Support/raw_ostream.h"
22
23 using namespace llvm;
24
25 #define DEBUG_TYPE "asm-printer"
26
27 #define GET_INSTRUCTION_NAME
28 #include "HexagonGenAsmWriter.inc"
29
30 const char HexagonInstPrinter::PacketPadding = '\t';
31 // Return the minimum value that a constant extendable operand can have
32 // without being extended.
33 static int getMinValue(uint64_t TSFlags) {
34 unsigned isSigned =
35 (TSFlags >> HexagonII::ExtentSignedPos) & HexagonII::ExtentSignedMask;
36 unsigned bits =
37 (TSFlags >> HexagonII::ExtentBitsPos) & HexagonII::ExtentBitsMask;
38
39 if (isSigned)
40 return -1U << (bits - 1);
41
42 return 0;
43 }
44
45 // Return the maximum value that a constant extendable operand can have
46 // without being extended.
47 static int getMaxValue(uint64_t TSFlags) {
48 unsigned isSigned =
49 (TSFlags >> HexagonII::ExtentSignedPos) & HexagonII::ExtentSignedMask;
50 unsigned bits =
51 (TSFlags >> HexagonII::ExtentBitsPos) & HexagonII::ExtentBitsMask;
52
53 if (isSigned)
54 return ~(-1U << (bits - 1));
55
56 return ~(-1U << bits);
57 }
58
59 // Return true if the instruction must be extended.
60 static bool isExtended(uint64_t TSFlags) {
61 return (TSFlags >> HexagonII::ExtendedPos) & HexagonII::ExtendedMask;
62 }
63
64 // Currently just used in an assert statement
65 static bool isExtendable(uint64_t TSFlags) LLVM_ATTRIBUTE_UNUSED;
66 // Return true if the instruction may be extended based on the operand value.
67 static bool isExtendable(uint64_t TSFlags) {
68 return (TSFlags >> HexagonII::ExtendablePos) & HexagonII::ExtendableMask;
69 }
70
71 StringRef HexagonInstPrinter::getOpcodeName(unsigned Opcode) const {
72 return MII.getName(Opcode);
73 }
74
75 StringRef HexagonInstPrinter::getRegName(unsigned RegNo) const {
76 return getRegisterName(RegNo);
77 }
78
79 void HexagonInstPrinter::printInst(const MCInst *MI, raw_ostream &O,
80 StringRef Annot) {
81 printInst((const HexagonMCInst*)(MI), O, Annot);
82 }
83
84 void HexagonInstPrinter::printInst(const HexagonMCInst *MI, raw_ostream &O,
85 StringRef Annot) {
86 const char startPacket = '{',
87 endPacket = '}';
88 // TODO: add outer HW loop when it's supported too.
89 if (MI->getOpcode() == Hexagon::ENDLOOP0) {
90 // Ending a harware loop is different from ending an regular packet.
91 assert(MI->isPacketEnd() && "Loop-end must also end the packet");
92
93 if (MI->isPacketStart()) {
94 // There must be a packet to end a loop.
95 // FIXME: when shuffling is always run, this shouldn't be needed.
96 HexagonMCInst Nop;
97 StringRef NoAnnot;
98
99 Nop.setOpcode (Hexagon::NOP);
100 Nop.setPacketStart (MI->isPacketStart());
101 printInst (&Nop, O, NoAnnot);
102 }
103
104 // Close the packet.
105 if (MI->isPacketEnd())
106 O << PacketPadding << endPacket;
107
108 printInstruction(MI, O);
109 }
110 else {
111 // Prefix the insn opening the packet.
112 if (MI->isPacketStart())
113 O << PacketPadding << startPacket << '\n';
114
115 printInstruction(MI, O);
116
117 // Suffix the insn closing the packet.
118 if (MI->isPacketEnd())
119 // Suffix the packet in a new line always, since the GNU assembler has
120 // issues with a closing brace on the same line as CONST{32,64}.
121 O << '\n' << PacketPadding << endPacket;
122 }
123
124 printAnnotation(O, Annot);
125 }
126
127 void HexagonInstPrinter::printOperand(const MCInst *MI, unsigned OpNo,
128 raw_ostream &O) const {
129 const MCOperand& MO = MI->getOperand(OpNo);
130
131 if (MO.isReg()) {
132 O << getRegisterName(MO.getReg());
133 } else if(MO.isExpr()) {
134 O << *MO.getExpr();
135 } else if(MO.isImm()) {
136 printImmOperand(MI, OpNo, O);
137 } else {
138 llvm_unreachable("Unknown operand");
139 }
140 }
141
142 void HexagonInstPrinter::printImmOperand(const MCInst *MI, unsigned OpNo,
143 raw_ostream &O) const {
144 const MCOperand& MO = MI->getOperand(OpNo);
145
146 if(MO.isExpr()) {
147 O << *MO.getExpr();
148 } else if(MO.isImm()) {
149 O << MI->getOperand(OpNo).getImm();
150 } else {
151 llvm_unreachable("Unknown operand");
152 }
153 }
154
155 void HexagonInstPrinter::printExtOperand(const MCInst *MI, unsigned OpNo,
156 raw_ostream &O) const {
157 const MCOperand &MO = MI->getOperand(OpNo);
158 const MCInstrDesc &MII = getMII().get(MI->getOpcode());
159
160 assert((isExtendable(MII.TSFlags) || isExtended(MII.TSFlags)) &&
161 "Expecting an extendable operand");
162
163 if (MO.isExpr() || isExtended(MII.TSFlags)) {
164 O << "#";
165 } else if (MO.isImm()) {
166 int ImmValue = MO.getImm();
167 if (ImmValue < getMinValue(MII.TSFlags) ||
168 ImmValue > getMaxValue(MII.TSFlags))
169 O << "#";
170 }
171 printOperand(MI, OpNo, O);
172 }
173
174 void HexagonInstPrinter::printUnsignedImmOperand(const MCInst *MI,
175 unsigned OpNo, raw_ostream &O) const {
176 O << MI->getOperand(OpNo).getImm();
177 }
178
179 void HexagonInstPrinter::printNegImmOperand(const MCInst *MI, unsigned OpNo,
180 raw_ostream &O) const {
181 O << -MI->getOperand(OpNo).getImm();
182 }
183
184 void HexagonInstPrinter::printNOneImmOperand(const MCInst *MI, unsigned OpNo,
185 raw_ostream &O) const {
186 O << -1;
187 }
188
189 void HexagonInstPrinter::printMEMriOperand(const MCInst *MI, unsigned OpNo,
190 raw_ostream &O) const {
191 const MCOperand& MO0 = MI->getOperand(OpNo);
192 const MCOperand& MO1 = MI->getOperand(OpNo + 1);
193
194 O << getRegisterName(MO0.getReg());
195 O << " + #" << MO1.getImm();
196 }
197
198 void HexagonInstPrinter::printFrameIndexOperand(const MCInst *MI, unsigned OpNo,
199 raw_ostream &O) const {
200 const MCOperand& MO0 = MI->getOperand(OpNo);
201 const MCOperand& MO1 = MI->getOperand(OpNo + 1);
202
203 O << getRegisterName(MO0.getReg()) << ", #" << MO1.getImm();
204 }
205
206 void HexagonInstPrinter::printGlobalOperand(const MCInst *MI, unsigned OpNo,
207 raw_ostream &O) const {
208 assert(MI->getOperand(OpNo).isExpr() && "Expecting expression");
209
210 printOperand(MI, OpNo, O);
211 }
212
213 void HexagonInstPrinter::printJumpTable(const MCInst *MI, unsigned OpNo,
214 raw_ostream &O) const {
215 assert(MI->getOperand(OpNo).isExpr() && "Expecting expression");
216
217 printOperand(MI, OpNo, O);
218 }
219
220 void HexagonInstPrinter::printConstantPool(const MCInst *MI, unsigned OpNo,
221 raw_ostream &O) const {
222 assert(MI->getOperand(OpNo).isExpr() && "Expecting expression");
223
224 printOperand(MI, OpNo, O);
225 }
226
227 void HexagonInstPrinter::printBranchOperand(const MCInst *MI, unsigned OpNo,
228 raw_ostream &O) const {
229 // Branches can take an immediate operand. This is used by the branch
230 // selection pass to print $+8, an eight byte displacement from the PC.
231 llvm_unreachable("Unknown branch operand.");
232 }
233
234 void HexagonInstPrinter::printCallOperand(const MCInst *MI, unsigned OpNo,
235 raw_ostream &O) const {
236 }
237
238 void HexagonInstPrinter::printAbsAddrOperand(const MCInst *MI, unsigned OpNo,
239 raw_ostream &O) const {
240 }
241
242 void HexagonInstPrinter::printPredicateOperand(const MCInst *MI, unsigned OpNo,
243 raw_ostream &O) const {
244 }
245
246 void HexagonInstPrinter::printSymbol(const MCInst *MI, unsigned OpNo,
247 raw_ostream &O, bool hi) const {
248 assert(MI->getOperand(OpNo).isImm() && "Unknown symbol operand");
249
250 O << '#' << (hi ? "HI" : "LO") << "(#";
251 printOperand(MI, OpNo, O);
252 O << ')';
253 }
+0
-87
lib/Target/Hexagon/InstPrinter/HexagonInstPrinter.h less more
None //===-- HexagonInstPrinter.h - Convert Hexagon MCInst to assembly syntax --===//
1 //
2 // The LLVM Compiler Infrastructure
3 //
4 // This file is distributed under the University of Illinois Open Source
5 // License. See LICENSE.TXT for details.
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This class prints an Hexagon MCInst to a .s file.
10 //
11 //===----------------------------------------------------------------------===//
12
13 #ifndef LLVM_LIB_TARGET_HEXAGON_INSTPRINTER_HEXAGONINSTPRINTER_H
14 #define LLVM_LIB_TARGET_HEXAGON_INSTPRINTER_HEXAGONINSTPRINTER_H
15
16 #include "llvm/MC/MCInstPrinter.h"
17 #include "llvm/MC/MCInstrInfo.h"
18
19 namespace llvm {
20 class HexagonMCInst;
21
22 class HexagonInstPrinter : public MCInstPrinter {
23 public:
24 explicit HexagonInstPrinter(const MCAsmInfo &MAI,
25 const MCInstrInfo &MII,
26 const MCRegisterInfo &MRI)
27 : MCInstPrinter(MAI, MII, MRI), MII(MII) {}
28
29 void printInst(const MCInst *MI, raw_ostream &O, StringRef Annot) override;
30 void printInst(const HexagonMCInst *MI, raw_ostream &O, StringRef Annot);
31 virtual StringRef getOpcodeName(unsigned Opcode) const;
32 void printInstruction(const MCInst *MI, raw_ostream &O);
33 StringRef getRegName(unsigned RegNo) const;
34 static const char *getRegisterName(unsigned RegNo);
35
36 void printOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O) const;
37 void printImmOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O) const;
38 void printExtOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O) const;
39 void printUnsignedImmOperand(const MCInst *MI, unsigned OpNo,
40 raw_ostream &O) const;
41 void printNegImmOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
42 const;
43 void printNOneImmOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
44 const;
45 void printMEMriOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
46 const;
47 void printFrameIndexOperand(const MCInst *MI, unsigned OpNo,
48 raw_ostream &O) const;
49 void printBranchOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
50 const;
51 void printCallOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
52 const;
53 void printAbsAddrOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
54 const;
55 void printPredicateOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
56 const;
57 void printGlobalOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
58 const;
59 void printJumpTable(const MCInst *MI, unsigned OpNo, raw_ostream &O) const;
60
61 void printConstantPool(const MCInst *MI, unsigned OpNo,
62 raw_ostream &O) const;
63
64 void printSymbolHi(const MCInst *MI, unsigned OpNo, raw_ostream &O) const
65 { printSymbol(MI, OpNo, O, true); }
66 void printSymbolLo(const MCInst *MI, unsigned OpNo, raw_ostream &O) const
67 { printSymbol(MI, OpNo, O, false); }
68
69 const MCInstrInfo &getMII() const {
70 return MII;
71 }
72
73 protected:
74 void printSymbol(const MCInst *MI, unsigned OpNo, raw_ostream &O, bool hi)
75 const;
76
77 static const char PacketPadding;
78
79 private:
80 const MCInstrInfo &MII;
81
82 };
83
84 } // end namespace llvm
85
86 #endif
+0
-23
lib/Target/Hexagon/InstPrinter/LLVMBuild.txt less more
None ;===- ./lib/Target/Hexagon/InstPrinter/LLVMBuild.txt -----------*- Conf -*--===;
1 ;
2 ; The LLVM Compiler Infrastructure
3 ;
4 ; This file is distributed under the University of Illinois Open Source
5 ; License. See LICENSE.TXT for details.
6 ;
7 ;===------------------------------------------------------------------------===;
8 ;
9 ; This is an LLVMBuild description file for the components in this subdirectory.
10 ;
11 ; For more information on the LLVMBuild system, please see:
12 ;
13 ; http://llvm.org/docs/LLVMBuild.html
14 ;
15 ;===------------------------------------------------------------------------===;
16
17 [component_0]
18 type = Library
19 name = HexagonAsmPrinter
20 parent = Hexagon
21 required_libraries = MC Support
22 add_to_library_groups = Hexagon
+0
-15
lib/Target/Hexagon/InstPrinter/Makefile less more
None ##===- lib/Target/Hexagon/InstPrinter/Makefile ----------------------------===##
1 #
2 # The LLVM Compiler Infrastructure
3 #
4 # This file is distributed under the University of Illinois Open Source
5 # License. See LICENSE.TXT for details.
6 #
7 ##===----------------------------------------------------------------------===##
8 LEVEL = ../../../..
9 LIBRARYNAME = LLVMHexagonAsmPrinter
10
11 # Hack: we need to include 'main' Hexagon target directory to grab private headers
12 CPPFLAGS = -I$(PROJ_OBJ_DIR)/.. -I$(PROJ_SRC_DIR)/..
13
14 include $(LEVEL)/Makefile.common
1515 ;===------------------------------------------------------------------------===;
1616
1717 [common]
18 subdirectories = Disassembler InstPrinter MCTargetDesc TargetInfo
18 subdirectories = Disassembler MCTargetDesc TargetInfo
1919
2020 [component_0]
2121 type = TargetGroup
2727 type = Library
2828 name = HexagonCodeGen
2929 parent = Hexagon
30 required_libraries = Analysis AsmPrinter CodeGen Core HexagonAsmPrinter HexagonDesc HexagonInfo MC SelectionDAG Support Target
30 required_libraries = Analysis AsmPrinter CodeGen Core HexagonDesc HexagonInfo MC SelectionDAG Support Target
3131 add_to_library_groups = Hexagon
0 add_llvm_library(LLVMHexagonDesc
1 HexagonInstPrinter.cpp
12 HexagonMCAsmInfo.cpp
23 HexagonMCCodeEmitter.cpp
34 HexagonMCInst.cpp
0 //===- HexagonInstPrinter.cpp - Convert Hexagon MCInst to assembly syntax -===//
1 //
2 // The LLVM Compiler Infrastructure
3 //
4 // This file is distributed under the University of Illinois Open Source
5 // License. See LICENSE.TXT for details.
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This class prints an Hexagon MCInst to a .s file.
10 //
11 //===----------------------------------------------------------------------===//
12
13 #include "HexagonAsmPrinter.h"
14 #include "Hexagon.h"
15 #include "HexagonInstPrinter.h"
16 #include "MCTargetDesc/HexagonMCInst.h"
17 #include "llvm/ADT/StringExtras.h"
18 #include "llvm/MC/MCAsmInfo.h"
19 #include "llvm/MC/MCExpr.h"
20 #include "llvm/MC/MCInst.h"
21 #include "llvm/Support/raw_ostream.h"
22
23 using namespace llvm;
24
25 #define DEBUG_TYPE "asm-printer"
26
27 #define GET_INSTRUCTION_NAME
28 #include "HexagonGenAsmWriter.inc"
29
30 const char HexagonInstPrinter::PacketPadding = '\t';
31 // Return the minimum value that a constant extendable operand can have
32 // without being extended.
33 static int getMinValue(uint64_t TSFlags) {
34 unsigned isSigned =
35 (TSFlags >> HexagonII::ExtentSignedPos) & HexagonII::ExtentSignedMask;
36 unsigned bits =
37 (TSFlags >> HexagonII::ExtentBitsPos) & HexagonII::ExtentBitsMask;
38
39 if (isSigned)
40 return -1U << (bits - 1);
41
42 return 0;
43 }
44
45 // Return the maximum value that a constant extendable operand can have
46 // without being extended.
47 static int getMaxValue(uint64_t TSFlags) {
48 unsigned isSigned =
49 (TSFlags >> HexagonII::ExtentSignedPos) & HexagonII::ExtentSignedMask;
50 unsigned bits =
51 (TSFlags >> HexagonII::ExtentBitsPos) & HexagonII::ExtentBitsMask;
52
53 if (isSigned)
54 return ~(-1U << (bits - 1));
55
56 return ~(-1U << bits);
57 }
58
59 // Return true if the instruction must be extended.
60 static bool isExtended(uint64_t TSFlags) {
61 return (TSFlags >> HexagonII::ExtendedPos) & HexagonII::ExtendedMask;
62 }
63
64 // Currently just used in an assert statement
65 static bool isExtendable(uint64_t TSFlags) LLVM_ATTRIBUTE_UNUSED;
66 // Return true if the instruction may be extended based on the operand value.
67 static bool isExtendable(uint64_t TSFlags) {
68 return (TSFlags >> HexagonII::ExtendablePos) & HexagonII::ExtendableMask;
69 }
70
71 StringRef HexagonInstPrinter::getOpcodeName(unsigned Opcode) const {
72 return MII.getName(Opcode);
73 }
74
75 StringRef HexagonInstPrinter::getRegName(unsigned RegNo) const {
76 return getRegisterName(RegNo);
77 }
78
79 void HexagonInstPrinter::printInst(const MCInst *MI, raw_ostream &O,
80 StringRef Annot) {
81 printInst((const HexagonMCInst*)(MI), O, Annot);
82 }
83
84 void HexagonInstPrinter::printInst(const HexagonMCInst *MI, raw_ostream &O,
85 StringRef Annot) {
86 const char startPacket = '{',
87 endPacket = '}';
88 // TODO: add outer HW loop when it's supported too.
89 if (MI->getOpcode() == Hexagon::ENDLOOP0) {
90 // Ending a harware loop is different from ending an regular packet.
91 assert(MI->isPacketEnd() && "Loop-end must also end the packet");
92
93 if (MI->isPacketBegin()) {
94 // There must be a packet to end a loop.
95 // FIXME: when shuffling is always run, this shouldn't be needed.
96 HexagonMCInst Nop (Hexagon::NOP);
97 StringRef NoAnnot;
98
99 Nop.setPacketBegin (MI->isPacketBegin());
100 printInst (&Nop, O, NoAnnot);
101 }
102
103 // Close the packet.
104 if (MI->isPacketEnd())
105 O << PacketPadding << endPacket;
106
107 printInstruction(MI, O);
108 }
109 else {
110 // Prefix the insn opening the packet.
111 if (MI->isPacketBegin())
112 O << PacketPadding << startPacket << '\n';
113
114 printInstruction(MI, O);
115
116 // Suffix the insn closing the packet.
117 if (MI->isPacketEnd())
118 // Suffix the packet in a new line always, since the GNU assembler has
119 // issues with a closing brace on the same line as CONST{32,64}.
120 O << '\n' << PacketPadding << endPacket;
121 }
122
123 printAnnotation(O, Annot);
124 }
125
126 void HexagonInstPrinter::printOperand(const MCInst *MI, unsigned OpNo,
127 raw_ostream &O) const {
128 const MCOperand& MO = MI->getOperand(OpNo);
129
130 if (MO.isReg()) {
131 O << getRegisterName(MO.getReg());
132 } else if(MO.isExpr()) {
133 O << *MO.getExpr();
134 } else if(MO.isImm()) {
135 printImmOperand(MI, OpNo, O);
136 } else {
137 llvm_unreachable("Unknown operand");
138 }
139 }
140
141 void HexagonInstPrinter::printImmOperand(const MCInst *MI, unsigned OpNo,
142 raw_ostream &O) const {
143 const MCOperand& MO = MI->getOperand(OpNo);
144
145 if(MO.isExpr()) {
146 O << *MO.getExpr();
147 } else if(MO.isImm()) {
148 O << MI->getOperand(OpNo).getImm();
149 } else {
150 llvm_unreachable("Unknown operand");
151 }
152 }
153
154 void HexagonInstPrinter::printExtOperand(const MCInst *MI, unsigned OpNo,
155 raw_ostream &O) const {
156 const MCOperand &MO = MI->getOperand(OpNo);
157 const MCInstrDesc &MII = getMII().get(MI->getOpcode());
158
159 assert((isExtendable(MII.TSFlags) || isExtended(MII.TSFlags)) &&
160 "Expecting an extendable operand");
161
162 if (MO.isExpr() || isExtended(MII.TSFlags)) {
163 O << "#";
164 } else if (MO.isImm()) {
165 int ImmValue = MO.getImm();
166 if (ImmValue < getMinValue(MII.TSFlags) ||
167 ImmValue > getMaxValue(MII.TSFlags))
168 O << "#";
169 }
170 printOperand(MI, OpNo, O);
171 }
172
173 void HexagonInstPrinter::printUnsignedImmOperand(const MCInst *MI,
174 unsigned OpNo, raw_ostream &O) const {
175 O << MI->getOperand(OpNo).getImm();
176 }
177
178 void HexagonInstPrinter::printNegImmOperand(const MCInst *MI, unsigned OpNo,
179 raw_ostream &O) const {
180 O << -MI->getOperand(OpNo).getImm();
181 }
182
183 void HexagonInstPrinter::printNOneImmOperand(const MCInst *MI, unsigned OpNo,
184 raw_ostream &O) const {
185 O << -1;
186 }
187
188 void HexagonInstPrinter::printMEMriOperand(const MCInst *MI, unsigned OpNo,
189 raw_ostream &O) const {
190 const MCOperand& MO0 = MI->getOperand(OpNo);
191 const MCOperand& MO1 = MI->getOperand(OpNo + 1);
192
193 O << getRegisterName(MO0.getReg());
194 O << " + #" << MO1.getImm();
195 }
196
197 void HexagonInstPrinter::printFrameIndexOperand(const MCInst *MI, unsigned OpNo,
198 raw_ostream &O) const {
199 const MCOperand& MO0 = MI->getOperand(OpNo);
200 const MCOperand& MO1 = MI->getOperand(OpNo + 1);
201
202 O << getRegisterName(MO0.getReg()) << ", #" << MO1.getImm();
203 }
204
205 void HexagonInstPrinter::printGlobalOperand(const MCInst *MI, unsigned OpNo,
206 raw_ostream &O) const {
207 assert(MI->getOperand(OpNo).isExpr() && "Expecting expression");
208
209 printOperand(MI, OpNo, O);
210 }
211
212 void HexagonInstPrinter::printJumpTable(const MCInst *MI, unsigned OpNo,
213 raw_ostream &O) const {
214 assert(MI->getOperand(OpNo).isExpr() && "Expecting expression");
215
216 printOperand(MI, OpNo, O);
217 }
218
219 void HexagonInstPrinter::printConstantPool(const MCInst *MI, unsigned OpNo,
220 raw_ostream &O) const {
221 assert(MI->getOperand(OpNo).isExpr() && "Expecting expression");
222
223 printOperand(MI, OpNo, O);
224 }
225
226 void HexagonInstPrinter::printBranchOperand(const MCInst *MI, unsigned OpNo,
227 raw_ostream &O) const {
228 // Branches can take an immediate operand. This is used by the branch
229 // selection pass to print $+8, an eight byte displacement from the PC.
230 llvm_unreachable("Unknown branch operand.");
231 }
232
233 void HexagonInstPrinter::printCallOperand(const MCInst *MI, unsigned OpNo,
234 raw_ostream &O) const {
235 }
236
237 void HexagonInstPrinter::printAbsAddrOperand(const MCInst *MI, unsigned OpNo,
238 raw_ostream &O) const {
239 }
240
241 void HexagonInstPrinter::printPredicateOperand(const MCInst *MI, unsigned OpNo,
242 raw_ostream &O) const {
243 }
244
245 void HexagonInstPrinter::printSymbol(const MCInst *MI, unsigned OpNo,
246 raw_ostream &O, bool hi) const {
247 assert(MI->getOperand(OpNo).isImm() && "Unknown symbol operand");
248
249 O << '#' << (hi ? "HI" : "LO") << "(#";
250 printOperand(MI, OpNo, O);
251 O << ')';
252 }
0 //===-- HexagonInstPrinter.h - Convert Hexagon MCInst to assembly syntax --===//
1 //
2 // The LLVM Compiler Infrastructure
3 //
4 // This file is distributed under the University of Illinois Open Source
5 // License. See LICENSE.TXT for details.
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This class prints an Hexagon MCInst to a .s file.
10 //
11 //===----------------------------------------------------------------------===//
12
13 #ifndef LLVM_LIB_TARGET_HEXAGON_INSTPRINTER_HEXAGONINSTPRINTER_H
14 #define LLVM_LIB_TARGET_HEXAGON_INSTPRINTER_HEXAGONINSTPRINTER_H
15
16 #include "llvm/MC/MCInstPrinter.h"
17 #include "llvm/MC/MCInstrInfo.h"
18
19 namespace llvm {
20 class HexagonMCInst;
21
22 class HexagonInstPrinter : public MCInstPrinter {
23 public:
24 explicit HexagonInstPrinter(const MCAsmInfo &MAI,
25 const MCInstrInfo &MII,
26 const MCRegisterInfo &MRI)
27 : MCInstPrinter(MAI, MII, MRI), MII(MII) {}
28
29 void printInst(const MCInst *MI, raw_ostream &O, StringRef Annot) override;
30 void printInst(const HexagonMCInst *MI, raw_ostream &O, StringRef Annot);
31 virtual StringRef getOpcodeName(unsigned Opcode) const;
32 void printInstruction(const MCInst *MI, raw_ostream &O);
33 StringRef getRegName(unsigned RegNo) const;
34 static const char *getRegisterName(unsigned RegNo);
35
36 void printOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O) const;
37 void printImmOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O) const;
38 void printExtOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O) const;
39 void printUnsignedImmOperand(const MCInst *MI, unsigned OpNo,
40 raw_ostream &O) const;
41 void printNegImmOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
42 const;
43 void printNOneImmOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
44 const;
45 void printMEMriOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
46 const;
47 void printFrameIndexOperand(const MCInst *MI, unsigned OpNo,
48 raw_ostream &O) const;
49 void printBranchOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
50 const;
51 void printCallOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
52 const;
53 void printAbsAddrOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
54 const;
55 void printPredicateOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
56 const;
57 void printGlobalOperand(const MCInst *MI, unsigned OpNo, raw_ostream &O)
58 const;
59 void printJumpTable(const MCInst *MI, unsigned OpNo, raw_ostream &O) const;
60
61 void printConstantPool(const MCInst *MI, unsigned OpNo,
62 raw_ostream &O) const;
63
64 void printSymbolHi(const MCInst *MI, unsigned OpNo, raw_ostream &O) const
65 { printSymbol(MI, OpNo, O, true); }
66 void printSymbolLo(const MCInst *MI, unsigned OpNo, raw_ostream &O) const
67 { printSymbol(MI, OpNo, O, false); }
68
69 const MCInstrInfo &getMII() const {
70 return MII;
71 }
72
73 protected:
74 void printSymbol(const MCInst *MI, unsigned OpNo, raw_ostream &O, bool hi)
75 const;
76
77 static const char PacketPadding;
78
79 private:
80 const MCInstrInfo &MII;
81
82 };
83
84 } // end namespace llvm
85
86 #endif
3737 uint32_t getPacketBits(HexagonMCInst const &HMI) {
3838 unsigned const ParseFieldOffset = 14;
3939 ParseField Field = HMI.isPacketEnd() ? ParseField::end : ParseField::last0;
40 return static_cast (Field) << ParseFieldOffset;
40 return static_cast(Field) << ParseFieldOffset;
4141 }
4242 void emitLittleEndian(uint64_t Binary, raw_ostream &OS) {
4343 OS << static_cast((Binary >> 0x00) & 0xff);
5656 SmallVectorImpl &Fixups,
5757 MCSubtargetInfo const &STI) const {
5858 HexagonMCInst const &HMB = static_cast(MI);
59 uint64_t Binary = getBinaryCodeForInstr(HMB, Fixups, STI) | getPacketBits(HMB);
60 assert(HMB.getDesc().getSize() == 4 && "All instructions should be 32bit");
59 uint64_t Binary =
60 getBinaryCodeForInstr(HMB, Fixups, STI) | getPacketBits(HMB);
61 Binary |= getPacketBits(HMB);
6162 emitLittleEndian(Binary, OS);
6263 ++MCNumEmitted;
6364 }
1111 //===----------------------------------------------------------------------===//
1212
1313 #include "HexagonInstrInfo.h"
14 #include "HexagonTargetMachine.h"
1415 #include "MCTargetDesc/HexagonBaseInfo.h"
1516 #include "MCTargetDesc/HexagonMCInst.h"
1617 #include "MCTargetDesc/HexagonMCTargetDesc.h"
18 #include "llvm/Support/TargetRegistry.h"
1719
1820 using namespace llvm;
1921
20 // Return the slots used by the insn.
21 unsigned HexagonMCInst::getUnits(const HexagonTargetMachine* TM) const {
22 const HexagonInstrInfo *QII = TM->getSubtargetImpl()->getInstrInfo();
23 const InstrItineraryData *II =
24 TM->getSubtargetImpl()->getInstrItineraryData();
25 const InstrStage*
26 IS = II->beginStage(QII->get(this->getOpcode()).getSchedClass());
22 HexagonMCInst::HexagonMCInst(unsigned op)
23 : packetBegin(false), packetEnd(false),
24 MCID(llvm::TheHexagonTarget.createMCInstrInfo()->get(op)) {
25 assert(MCID.getSize() == 4 && "All instructions should be 32bit");
26 setOpcode(op);
27 }
28
29 bool HexagonMCInst::isPacketBegin() const { return packetBegin; }
30 bool HexagonMCInst::isPacketEnd() const { return packetEnd; }
31 void HexagonMCInst::setPacketEnd(bool Y) { packetEnd = Y; }
32 void HexagonMCInst::setPacketBegin(bool Y) { packetBegin = Y; }
33
34 unsigned HexagonMCInst::getUnits(HexagonTargetMachine const &TM) const {
35 const HexagonInstrInfo *QII = TM.getSubtargetImpl()->getInstrInfo();
36 const InstrItineraryData *II = TM.getSubtargetImpl()->getInstrItineraryData();
37 const InstrStage *IS =
38 II->beginStage(QII->get(this->getOpcode()).getSchedClass());
2739
2840 return (IS->getUnits());
2941 }
3042
31 // Return the Hexagon ISA class for the insn.
32 unsigned HexagonMCInst::getType() const {
33 const uint64_t F = MCID->TSFlags;
34
35 return ((F >> HexagonII::TypePos) & HexagonII::TypeMask);
36 }
37
38 // Return whether the insn is an actual insn.
39 bool HexagonMCInst::isCanon() const {
40 return (!MCID->isPseudo() &&
41 !isPrefix() &&
42 getType() != HexagonII::TypeENDLOOP);
43 }
44
45 // Return whether the insn is a prefix.
46 bool HexagonMCInst::isPrefix() const {
47 return (getType() == HexagonII::TypePREFIX);
48 }
49
50 // Return whether the insn is solo, i.e., cannot be in a packet.
51 bool HexagonMCInst::isSolo() const {
52 const uint64_t F = MCID->TSFlags;
53 return ((F >> HexagonII::SoloPos) & HexagonII::SoloMask);
54 }
55
56 // Return whether the insn is a new-value consumer.
5743 bool HexagonMCInst::isNewValue() const {
58 const uint64_t F = MCID->TSFlags;
44 const uint64_t F = MCID.TSFlags;
5945 return ((F >> HexagonII::NewValuePos) & HexagonII::NewValueMask);
6046 }
6147
62 // Return whether the instruction is a legal new-value producer.
6348 bool HexagonMCInst::hasNewValue() const {
64 const uint64_t F = MCID->TSFlags;
49 const uint64_t F = MCID.TSFlags;
6550 return ((F >> HexagonII::hasNewValuePos) & HexagonII::hasNewValueMask);
6651 }
6752
68 // Return the operand that consumes or produces a new value.
69 const MCOperand& HexagonMCInst::getNewValue() const {
70 const uint64_t F = MCID->TSFlags;
71 const unsigned O = (F >> HexagonII::NewValueOpPos) &
72 HexagonII::NewValueOpMask;
73 const MCOperand& MCO = getOperand(O);
53 MCOperand const &HexagonMCInst::getNewValue() const {
54 const uint64_t F = MCID.TSFlags;
55 const unsigned O =
56 (F >> HexagonII::NewValueOpPos) & HexagonII::NewValueOpMask;
57 const MCOperand &MCO = getOperand(O);
7458
75 assert ((isNewValue() || hasNewValue()) && MCO.isReg());
59 assert((isNewValue() || hasNewValue()) && MCO.isReg());
7660 return (MCO);
7761 }
7862
8367 // 2) For immediate extended operands, return true only if the value is
8468 // out-of-range.
8569 // 3) For global address, always return true.
86
8770 bool HexagonMCInst::isConstExtended(void) const {
8871 if (isExtended())
8972 return true;
9275 return false;
9376
9477 short ExtOpNum = getCExtOpNum();
95 int MinValue = getMinValue();
96 int MaxValue = getMaxValue();
97 const MCOperand& MO = getOperand(ExtOpNum);
78 int MinValue = getMinValue();
79 int MaxValue = getMaxValue();
80 const MCOperand &MO = getOperand(ExtOpNum);
9881
9982 // We could be using an instruction with an extendable immediate and shoehorn
10083 // a global address into it. If it is a global address it will be constant
11396 return (ImmValue < MinValue || ImmValue > MaxValue);
11497 }
11598
116 // Return whether the instruction must be always extended.
11799 bool HexagonMCInst::isExtended(void) const {
118 const uint64_t F = MCID->TSFlags;
100 const uint64_t F = MCID.TSFlags;
119101 return (F >> HexagonII::ExtendedPos) & HexagonII::ExtendedMask;
120102 }
121103
122 // Return true if the instruction may be extended based on the operand value.
123104 bool HexagonMCInst::isExtendable(void) const {
124 const uint64_t F = MCID->TSFlags;
105 const uint64_t F = MCID.TSFlags;
125106 return (F >> HexagonII::ExtendablePos) & HexagonII::ExtendableMask;
126107 }
127108
128 // Return number of bits in the constant extended operand.
129109 unsigned HexagonMCInst::getBitCount(void) const {
130 const uint64_t F = MCID->TSFlags;
110 const uint64_t F = MCID.TSFlags;
131111 return ((F >> HexagonII::ExtentBitsPos) & HexagonII::ExtentBitsMask);
132112 }
133113
134 // Return constant extended operand number.
135114 unsigned short HexagonMCInst::getCExtOpNum(void) const {
136 const uint64_t F = MCID->TSFlags;
115 const uint64_t F = MCID.TSFlags;
137116 return ((F >> HexagonII::ExtendableOpPos) & HexagonII::ExtendableOpMask);
138117 }
139118
140 // Return whether the operand can be constant extended.
141119 bool HexagonMCInst::isOperandExtended(const unsigned short OperandNum) const {
142 const uint64_t F = MCID->TSFlags;
143 return ((F >> HexagonII::ExtendableOpPos) & HexagonII::ExtendableOpMask)
144 == OperandNum;
120 const uint64_t F = MCID.TSFlags;
121 return ((F >> HexagonII::ExtendableOpPos) & HexagonII::ExtendableOpMask) ==
122 OperandNum;
145123 }
146124
147 // Return the min value that a constant extendable operand can have
148 // without being extended.
149125 int HexagonMCInst::getMinValue(void) const {
150 const uint64_t F = MCID->TSFlags;
151 unsigned isSigned = (F >> HexagonII::ExtentSignedPos)
152 & HexagonII::ExtentSignedMask;
153 unsigned bits = (F >> HexagonII::ExtentBitsPos)
154 & HexagonII::ExtentBitsMask;
126 const uint64_t F = MCID.TSFlags;
127 unsigned isSigned =
128 (F >> HexagonII::ExtentSignedPos) & HexagonII::ExtentSignedMask;
129 unsigned bits = (F >> HexagonII::ExtentBitsPos) & HexagonII::ExtentBitsMask;
155130
156 if (isSigned) // if value is signed
131 if (isSigned)
157132 return -1U << (bits - 1);
158133 else
159134 return 0;
160135 }
161136
162 // Return the max value that a constant extendable operand can have
163 // without being extended.
164137 int HexagonMCInst::getMaxValue(void) const {
165 const uint64_t F = MCID->TSFlags;
166 unsigned isSigned = (F >> HexagonII::ExtentSignedPos)
167 & HexagonII::ExtentSignedMask;
168 unsigned bits = (F >> HexagonII::ExtentBitsPos)
169 & HexagonII::ExtentBitsMask;
138 const uint64_t F = MCID.TSFlags;
139 unsigned isSigned =
140 (F >> HexagonII::ExtentSignedPos) & HexagonII::ExtentSignedMask;
141 unsigned bits = (F >> HexagonII::ExtentBitsPos) & HexagonII::ExtentBitsMask;
170142
171 if (isSigned) // if value is signed
143 if (isSigned)
172144 return ~(-1U << (bits - 1));
173145 else
174146 return ~(-1U << bits);
1313 #ifndef LLVM_LIB_TARGET_HEXAGON_MCTARGETDESC_HEXAGONMCINST_H
1414 #define LLVM_LIB_TARGET_HEXAGON_MCTARGETDESC_HEXAGONMCINST_H
1515
16 #include "HexagonTargetMachine.h"
1716 #include "llvm/MC/MCInst.h"
1817
1918 namespace llvm {
20 class MCOperand;
19 class MCInstrDesc;
20 class MCOperand;
21 class HexagonTargetMachine;
2122
22 class HexagonMCInst: public MCInst {
23 // MCID is set during instruction lowering.
24 // It is needed in order to access TSFlags for
25 // use in checking MC instruction properties.
26 const MCInstrDesc *MCID;
23 class HexagonMCInst : public MCInst {
24 public:
25 explicit HexagonMCInst(unsigned op);
2726
28 // Packet start and end markers
29 unsigned packetStart: 1, packetEnd: 1;
27 /// 10.6 Instruction Packets
28 bool isPacketBegin() const;
29 /// \brief Is this marked as last in packet.
30 bool isPacketEnd() const;
31 void setPacketBegin(bool Y);
32 /// \brief Mark this as last in packet.
33 void setPacketEnd(bool Y);
34 /// \brief Return the slots used.
35 unsigned getUnits(HexagonTargetMachine const &TM) const;
36 bool isConstExtended() const;
37 /// \brief Return constant extended operand number.
38 unsigned short getCExtOpNum(void) const;
39 /// \brief Return whether this is a new-value consumer.
40 bool isNewValue() const;
41 /// \brief Return whether this is a legal new-value producer.
42 bool hasNewValue() const;
43 /// \brief Return the operand that consumes or produces a new value.
44 MCOperand const &getNewValue() const;
45 /// \brief Return number of bits in the constant extended operand.
46 unsigned getBitCount(void) const;
3047
31 public:
32 explicit HexagonMCInst():
33 MCInst(), MCID(nullptr), packetStart(0), packetEnd(0) {};
34 HexagonMCInst(const MCInstrDesc& mcid):
35 MCInst(), MCID(&mcid), packetStart(0), packetEnd(0) {};
36
37 bool isPacketStart() const { return (packetStart); };
38 bool isPacketEnd() const { return (packetEnd); };
39 void setPacketStart(bool Y) { packetStart = Y; };
40 void setPacketEnd(bool Y) { packetEnd = Y; };
41 void resetPacket() { setPacketStart(false); setPacketEnd(false); };
42
43 // Return the slots used by the insn.
44 unsigned getUnits(const HexagonTargetMachine* TM) const;
45
46 // Return the Hexagon ISA class for the insn.
47 unsigned getType() const;
48
49 void setDesc(const MCInstrDesc& mcid) { MCID = &mcid; };
50 const MCInstrDesc& getDesc(void) const { return *MCID; };
51
52 // Return whether the insn is an actual insn.
53 bool isCanon() const;
54
55 // Return whether the insn is a prefix.
56 bool isPrefix() const;
57
58 // Return whether the insn is solo, i.e., cannot be in a packet.
59 bool isSolo() const;
60
61 // Return whether the instruction needs to be constant extended.
62 bool isConstExtended() const;
63
64 // Return constant extended operand number.
65 unsigned short getCExtOpNum(void) const;
66
67 // Return whether the insn is a new-value consumer.
68 bool isNewValue() const;
69
70 // Return whether the instruction is a legal new-value producer.
71 bool hasNewValue() const;
72
73 // Return the operand that consumes or produces a new value.
74 const MCOperand& getNewValue() const;
75
76 // Return number of bits in the constant extended operand.
77 unsigned getBitCount(void) const;
78
79 private:
80 // Return whether the instruction must be always extended.
81 bool isExtended() const;
82
83 // Return true if the insn may be extended based on the operand value.
84 bool isExtendable() const;
85
86 // Return true if the operand can be constant extended.
87 bool isOperandExtended(const unsigned short OperandNum) const;
88
89 // Return the min value that a constant extendable operand can have
90 // without being extended.
91 int getMinValue() const;
92
93 // Return the max value that a constant extendable operand can have
94 // without being extended.
95 int getMaxValue() const;
96 };
48 private:
49 /// \brief Return whether this must be always extended.
50 bool isExtended() const;
51 /// \brief Return true if this may be extended based on the operand value.
52 bool isExtendable() const;
53 /// \brief Return if the operand can be constant extended.
54 bool isOperandExtended(unsigned short const OperandNum) const;
55 /// \brief Return the min value that a constant extendable operand can have
56 /// without being extended.
57 int getMinValue() const;
58 /// \brief Return the max value that a constant extendable operand can have
59 /// without being extended.
60 int getMaxValue() const;
61 bool packetBegin;
62 bool packetEnd;
63 MCInstrDesc const &MCID;
64 };
9765 }
9866
9967 #endif
1212
1313 #include "HexagonMCTargetDesc.h"
1414 #include "HexagonMCAsmInfo.h"
15 #include "InstPrinter/HexagonInstPrinter.h"
15 #include "MCTargetDesc/HexagonInstPrinter.h"
1616 #include "llvm/MC/MCCodeGenInfo.h"
1717 #include "llvm/MC/MCInstrInfo.h"
1818 #include "llvm/MC/MCRegisterInfo.h"
3333 #define GET_REGINFO_MC_DESC
3434 #include "HexagonGenRegisterInfo.inc"
3535
36 static MCInstrInfo *createHexagonMCInstrInfo() {
36 static llvm::MCInstrInfo *createHexagonMCInstrInfo() {
3737 MCInstrInfo *X = new MCInstrInfo();
3838 InitHexagonMCInstrInfo(X);
3939 return X;
1414 #define LLVM_LIB_TARGET_HEXAGON_MCTARGETDESC_HEXAGONMCTARGETDESC_H
1515
1616 namespace llvm {
17 struct InstrItinerary;
18 struct InstrStage;
1719 class MCCodeEmitter;
1820 class MCContext;
1921 class MCInstrInfo;
1818 type = Library
1919 name = HexagonDesc
2020 parent = Hexagon
21 required_libraries = HexagonAsmPrinter HexagonInfo MC Support
21 required_libraries = HexagonInfo MC Support
2222 add_to_library_groups = Hexagon
1313 BUILT_SOURCES = HexagonGenRegisterInfo.inc \
1414 HexagonGenInstrInfo.inc \
1515 HexagonGenAsmWriter.inc \
16 HexagonGenDAGISel.inc HexagonGenSubtargetInfo.inc \
17 HexagonGenCallingConv.inc \
18 HexagonGenDFAPacketizer.inc \
19 HexagonGenMCCodeEmitter.inc \
20 HexagonGenDisassemblerTables.inc
21
22 DIRS = InstPrinter TargetInfo MCTargetDesc Disassembler
23
24 include $(LEVEL)/Makefile.common
16 HexagonGenDAGISel.inc \
17 HexagonGenSubtargetInfo.inc \
18 HexagonGenCallingConv.inc \
19 HexagonGenDFAPacketizer.inc \
20 HexagonGenMCCodeEmitter.inc \
21 HexagonGenDisassemblerTables.inc
22
23 DIRS = TargetInfo MCTargetDesc Disassembler
24
25 include $(LEVEL)/Makefile.common
0 # RUN: llvm-mc --triple hexagon -disassemble < %s | FileCheck %s
1
2 0x11 0xdf 0x15 0xf3
3 # CHECK: r17 = add(r21, r31)
0 if 'Hexagon' not in config.root.targets:
1 config.unsupported = True
2
66 StringTableBuilderTest.cpp
77 YAMLTest.cpp
88 )
9
10 foreach(t ${LLVM_TARGETS_TO_BUILD})
11 if (IS_DIRECTORY "${CMAKE_CURRENT_LIST_DIR}/${t}")
12 add_subdirectory(${t})
13 endif (IS_DIRECTORY "${CMAKE_CURRENT_LIST_DIR}/${t}")
14 endforeach()
+0
-53
unittests/MC/Hexagon/HexagonMCCodeEmitterTest.cpp less more
None #include "gtest/gtest.h"
1
2 #include
3
4 #include "llvm/MC/MCCodeEmitter.h"
5 #include "llvm/MC/MCContext.h"
6 #include "llvm/Support/raw_ostream.h"
7 #include "llvm/Support/TargetRegistry.h"
8 #include "llvm/Support/TargetSelect.h"
9
10 #include "MCTargetDesc/HexagonMCInst.h"
11 #include "MCTargetDesc/HexagonMCTargetDesc.h"
12
13 namespace {
14 class TestEmitter {
15 public:
16 TestEmitter() : Triple("hexagon-unknown-elf") {
17 LLVMInitializeHexagonTargetInfo();
18 LLVMInitializeHexagonTarget();
19 LLVMInitializeHexagonTargetMC();
20 std::string error;
21 Target = llvm::TargetRegistry::lookupTarget("hexagon", error);
22 assert(Target != nullptr && "Expected to find target");
23 assert(error.empty() && "Error should be empty if we have a target");
24 RegisterInfo = Target->createMCRegInfo(Triple);
25 assert(RegisterInfo != nullptr && "Expecting to find register info");
26 AsmInfo = Target->createMCAsmInfo(*RegisterInfo, Triple);
27 assert(AsmInfo != nullptr && "Expecting to find asm info");
28 Context = new llvm::MCContext(AsmInfo, RegisterInfo, nullptr);
29 assert(Context != nullptr && "Expecting to create a context");
30 Subtarget = Target->createMCSubtargetInfo(Triple, "hexagonv4", "");
31 assert(Subtarget != nullptr && "Expecting to find a subtarget");
32 InstrInfo = Target->createMCInstrInfo();
33 assert(InstrInfo != nullptr && "Expecting to find instr info");
34 Emitter = Target->createMCCodeEmitter(*InstrInfo, *RegisterInfo, *Subtarget,
35 *Context);
36 assert(Emitter != nullptr);
37 }
38 std::string Triple;
39 llvm::Target const *Target;
40 llvm::MCRegisterInfo *RegisterInfo;
41 llvm::MCAsmInfo *AsmInfo;
42 llvm::MCContext *Context;
43 llvm::MCSubtargetInfo *Subtarget;
44 llvm::MCInstrInfo *InstrInfo;
45 llvm::MCCodeEmitter *Emitter;
46 };
47 TestEmitter Emitter;
48 }
49
50 TEST(HexagonMCCodeEmitter, emitter_creation) {
51 ASSERT_NE(nullptr, Emitter.Emitter);
52 }