File: | llvm/utils/TableGen/X86RecognizableInstr.cpp |
Warning: | line 379, column 39 The left operand of '!=' is a garbage value |
Press '?' to see keyboard shortcuts
Keyboard shortcuts:
1 | //===- X86RecognizableInstr.cpp - Disassembler instruction spec --*- C++ -*-===// | |||
2 | // | |||
3 | // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. | |||
4 | // See https://llvm.org/LICENSE.txt for license information. | |||
5 | // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception | |||
6 | // | |||
7 | //===----------------------------------------------------------------------===// | |||
8 | // | |||
9 | // This file is part of the X86 Disassembler Emitter. | |||
10 | // It contains the implementation of a single recognizable instruction. | |||
11 | // Documentation for the disassembler emitter in general can be found in | |||
12 | // X86DisassemblerEmitter.h. | |||
13 | // | |||
14 | //===----------------------------------------------------------------------===// | |||
15 | ||||
16 | #include "X86RecognizableInstr.h" | |||
17 | #include "X86DisassemblerShared.h" | |||
18 | #include "X86ModRMFilters.h" | |||
19 | #include "llvm/Support/ErrorHandling.h" | |||
20 | #include <string> | |||
21 | ||||
22 | using namespace llvm; | |||
23 | using namespace X86Disassembler; | |||
24 | ||||
25 | /// byteFromBitsInit - Extracts a value at most 8 bits in width from a BitsInit. | |||
26 | /// Useful for switch statements and the like. | |||
27 | /// | |||
28 | /// @param init - A reference to the BitsInit to be decoded. | |||
29 | /// @return - The field, with the first bit in the BitsInit as the lowest | |||
30 | /// order bit. | |||
31 | static uint8_t byteFromBitsInit(BitsInit &init) { | |||
32 | int width = init.getNumBits(); | |||
33 | ||||
34 | assert(width <= 8 && "Field is too large for uint8_t!")(static_cast<void> (0)); | |||
35 | ||||
36 | int index; | |||
37 | uint8_t mask = 0x01; | |||
38 | ||||
39 | uint8_t ret = 0; | |||
40 | ||||
41 | for (index = 0; index < width; index++) { | |||
42 | if (cast<BitInit>(init.getBit(index))->getValue()) | |||
43 | ret |= mask; | |||
44 | ||||
45 | mask <<= 1; | |||
46 | } | |||
47 | ||||
48 | return ret; | |||
49 | } | |||
50 | ||||
51 | /// byteFromRec - Extract a value at most 8 bits in with from a Record given the | |||
52 | /// name of the field. | |||
53 | /// | |||
54 | /// @param rec - The record from which to extract the value. | |||
55 | /// @param name - The name of the field in the record. | |||
56 | /// @return - The field, as translated by byteFromBitsInit(). | |||
57 | static uint8_t byteFromRec(const Record* rec, StringRef name) { | |||
58 | BitsInit* bits = rec->getValueAsBitsInit(name); | |||
59 | return byteFromBitsInit(*bits); | |||
60 | } | |||
61 | ||||
62 | RecognizableInstr::RecognizableInstr(DisassemblerTables &tables, | |||
63 | const CodeGenInstruction &insn, | |||
64 | InstrUID uid) { | |||
65 | UID = uid; | |||
66 | ||||
67 | Rec = insn.TheDef; | |||
68 | Name = std::string(Rec->getName()); | |||
69 | Spec = &tables.specForUID(UID); | |||
70 | ||||
71 | if (!Rec->isSubClassOf("X86Inst")) { | |||
72 | ShouldBeEmitted = false; | |||
73 | return; | |||
74 | } | |||
75 | ||||
76 | OpPrefix = byteFromRec(Rec, "OpPrefixBits"); | |||
77 | OpMap = byteFromRec(Rec, "OpMapBits"); | |||
78 | Opcode = byteFromRec(Rec, "Opcode"); | |||
79 | Form = byteFromRec(Rec, "FormBits"); | |||
80 | Encoding = byteFromRec(Rec, "OpEncBits"); | |||
81 | ||||
82 | OpSize = byteFromRec(Rec, "OpSizeBits"); | |||
83 | AdSize = byteFromRec(Rec, "AdSizeBits"); | |||
84 | HasREX_WPrefix = Rec->getValueAsBit("hasREX_WPrefix"); | |||
85 | HasVEX_4V = Rec->getValueAsBit("hasVEX_4V"); | |||
86 | HasVEX_W = Rec->getValueAsBit("HasVEX_W"); | |||
87 | IgnoresVEX_W = Rec->getValueAsBit("IgnoresVEX_W"); | |||
88 | IgnoresVEX_L = Rec->getValueAsBit("ignoresVEX_L"); | |||
89 | HasEVEX_L2Prefix = Rec->getValueAsBit("hasEVEX_L2"); | |||
90 | HasEVEX_K = Rec->getValueAsBit("hasEVEX_K"); | |||
91 | HasEVEX_KZ = Rec->getValueAsBit("hasEVEX_Z"); | |||
92 | HasEVEX_B = Rec->getValueAsBit("hasEVEX_B"); | |||
93 | IsCodeGenOnly = Rec->getValueAsBit("isCodeGenOnly"); | |||
94 | ForceDisassemble = Rec->getValueAsBit("ForceDisassemble"); | |||
95 | CD8_Scale = byteFromRec(Rec, "CD8_Scale"); | |||
96 | ||||
97 | Name = std::string(Rec->getName()); | |||
98 | ||||
99 | Operands = &insn.Operands.OperandList; | |||
100 | ||||
101 | HasVEX_LPrefix = Rec->getValueAsBit("hasVEX_L"); | |||
102 | ||||
103 | EncodeRC = HasEVEX_B && | |||
104 | (Form == X86Local::MRMDestReg || Form == X86Local::MRMSrcReg); | |||
105 | ||||
106 | // Check for 64-bit inst which does not require REX | |||
107 | Is32Bit = false; | |||
108 | Is64Bit = false; | |||
109 | // FIXME: Is there some better way to check for In64BitMode? | |||
110 | std::vector<Record*> Predicates = Rec->getValueAsListOfDefs("Predicates"); | |||
111 | for (unsigned i = 0, e = Predicates.size(); i != e; ++i) { | |||
112 | if (Predicates[i]->getName().find("Not64Bit") != Name.npos || | |||
113 | Predicates[i]->getName().find("In32Bit") != Name.npos) { | |||
114 | Is32Bit = true; | |||
115 | break; | |||
116 | } | |||
117 | if (Predicates[i]->getName().find("In64Bit") != Name.npos) { | |||
118 | Is64Bit = true; | |||
119 | break; | |||
120 | } | |||
121 | } | |||
122 | ||||
123 | if (Form == X86Local::Pseudo || (IsCodeGenOnly && !ForceDisassemble)) { | |||
124 | ShouldBeEmitted = false; | |||
125 | return; | |||
126 | } | |||
127 | ||||
128 | ShouldBeEmitted = true; | |||
129 | } | |||
130 | ||||
131 | void RecognizableInstr::processInstr(DisassemblerTables &tables, | |||
132 | const CodeGenInstruction &insn, | |||
133 | InstrUID uid) | |||
134 | { | |||
135 | // Ignore "asm parser only" instructions. | |||
136 | if (insn.TheDef->getValueAsBit("isAsmParserOnly")) | |||
137 | return; | |||
138 | ||||
139 | RecognizableInstr recogInstr(tables, insn, uid); | |||
140 | ||||
141 | if (recogInstr.shouldBeEmitted()) { | |||
142 | recogInstr.emitInstructionSpecifier(); | |||
143 | recogInstr.emitDecodePath(tables); | |||
144 | } | |||
145 | } | |||
146 | ||||
147 | #define EVEX_KB(n)(HasEVEX_KZ && HasEVEX_B ? n_KZ_B : (HasEVEX_K && HasEVEX_B ? n_K_B : (HasEVEX_KZ ? n_KZ : (HasEVEX_K? n_K : ( HasEVEX_B ? n_B : n))))) (HasEVEX_KZ && HasEVEX_B ? n##_KZ_B : \ | |||
148 | (HasEVEX_K && HasEVEX_B ? n##_K_B : \ | |||
149 | (HasEVEX_KZ ? n##_KZ : \ | |||
150 | (HasEVEX_K? n##_K : (HasEVEX_B ? n##_B : n))))) | |||
151 | ||||
152 | InstructionContext RecognizableInstr::insnContext() const { | |||
153 | InstructionContext insnContext; | |||
154 | ||||
155 | if (Encoding == X86Local::EVEX) { | |||
156 | if (HasVEX_LPrefix && HasEVEX_L2Prefix) { | |||
157 | errs() << "Don't support VEX.L if EVEX_L2 is enabled: " << Name << "\n"; | |||
158 | llvm_unreachable("Don't support VEX.L if EVEX_L2 is enabled")__builtin_unreachable(); | |||
159 | } | |||
160 | // VEX_L & VEX_W | |||
161 | if (!EncodeRC && HasVEX_LPrefix && HasVEX_W) { | |||
162 | if (OpPrefix == X86Local::PD) | |||
163 | insnContext = EVEX_KB(IC_EVEX_L_W_OPSIZE)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_L_W_OPSIZE_KZ_B : ( HasEVEX_K && HasEVEX_B ? IC_EVEX_L_W_OPSIZE_K_B : (HasEVEX_KZ ? IC_EVEX_L_W_OPSIZE_KZ : (HasEVEX_K? IC_EVEX_L_W_OPSIZE_K : (HasEVEX_B ? IC_EVEX_L_W_OPSIZE_B : IC_EVEX_L_W_OPSIZE))))); | |||
164 | else if (OpPrefix == X86Local::XS) | |||
165 | insnContext = EVEX_KB(IC_EVEX_L_W_XS)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_L_W_XS_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_L_W_XS_K_B : (HasEVEX_KZ ? IC_EVEX_L_W_XS_KZ : (HasEVEX_K? IC_EVEX_L_W_XS_K : (HasEVEX_B ? IC_EVEX_L_W_XS_B : IC_EVEX_L_W_XS))))); | |||
166 | else if (OpPrefix == X86Local::XD) | |||
167 | insnContext = EVEX_KB(IC_EVEX_L_W_XD)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_L_W_XD_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_L_W_XD_K_B : (HasEVEX_KZ ? IC_EVEX_L_W_XD_KZ : (HasEVEX_K? IC_EVEX_L_W_XD_K : (HasEVEX_B ? IC_EVEX_L_W_XD_B : IC_EVEX_L_W_XD))))); | |||
168 | else if (OpPrefix == X86Local::PS) | |||
169 | insnContext = EVEX_KB(IC_EVEX_L_W)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_L_W_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_L_W_K_B : (HasEVEX_KZ ? IC_EVEX_L_W_KZ : (HasEVEX_K? IC_EVEX_L_W_K : (HasEVEX_B ? IC_EVEX_L_W_B : IC_EVEX_L_W ))))); | |||
170 | else { | |||
171 | errs() << "Instruction does not use a prefix: " << Name << "\n"; | |||
172 | llvm_unreachable("Invalid prefix")__builtin_unreachable(); | |||
173 | } | |||
174 | } else if (!EncodeRC && HasVEX_LPrefix) { | |||
175 | // VEX_L | |||
176 | if (OpPrefix == X86Local::PD) | |||
177 | insnContext = EVEX_KB(IC_EVEX_L_OPSIZE)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_L_OPSIZE_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_L_OPSIZE_K_B : (HasEVEX_KZ ? IC_EVEX_L_OPSIZE_KZ : (HasEVEX_K? IC_EVEX_L_OPSIZE_K : (HasEVEX_B ? IC_EVEX_L_OPSIZE_B : IC_EVEX_L_OPSIZE))))); | |||
178 | else if (OpPrefix == X86Local::XS) | |||
179 | insnContext = EVEX_KB(IC_EVEX_L_XS)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_L_XS_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_L_XS_K_B : (HasEVEX_KZ ? IC_EVEX_L_XS_KZ : (HasEVEX_K? IC_EVEX_L_XS_K : (HasEVEX_B ? IC_EVEX_L_XS_B : IC_EVEX_L_XS))))); | |||
180 | else if (OpPrefix == X86Local::XD) | |||
181 | insnContext = EVEX_KB(IC_EVEX_L_XD)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_L_XD_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_L_XD_K_B : (HasEVEX_KZ ? IC_EVEX_L_XD_KZ : (HasEVEX_K? IC_EVEX_L_XD_K : (HasEVEX_B ? IC_EVEX_L_XD_B : IC_EVEX_L_XD))))); | |||
182 | else if (OpPrefix == X86Local::PS) | |||
183 | insnContext = EVEX_KB(IC_EVEX_L)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_L_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_L_K_B : (HasEVEX_KZ ? IC_EVEX_L_KZ : (HasEVEX_K? IC_EVEX_L_K : (HasEVEX_B ? IC_EVEX_L_B : IC_EVEX_L ))))); | |||
184 | else { | |||
185 | errs() << "Instruction does not use a prefix: " << Name << "\n"; | |||
186 | llvm_unreachable("Invalid prefix")__builtin_unreachable(); | |||
187 | } | |||
188 | } else if (!EncodeRC && HasEVEX_L2Prefix && HasVEX_W) { | |||
189 | // EVEX_L2 & VEX_W | |||
190 | if (OpPrefix == X86Local::PD) | |||
191 | insnContext = EVEX_KB(IC_EVEX_L2_W_OPSIZE)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_L2_W_OPSIZE_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_L2_W_OPSIZE_K_B : ( HasEVEX_KZ ? IC_EVEX_L2_W_OPSIZE_KZ : (HasEVEX_K? IC_EVEX_L2_W_OPSIZE_K : (HasEVEX_B ? IC_EVEX_L2_W_OPSIZE_B : IC_EVEX_L2_W_OPSIZE)) ))); | |||
192 | else if (OpPrefix == X86Local::XS) | |||
193 | insnContext = EVEX_KB(IC_EVEX_L2_W_XS)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_L2_W_XS_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_L2_W_XS_K_B : (HasEVEX_KZ ? IC_EVEX_L2_W_XS_KZ : (HasEVEX_K? IC_EVEX_L2_W_XS_K : (HasEVEX_B ? IC_EVEX_L2_W_XS_B : IC_EVEX_L2_W_XS))))); | |||
194 | else if (OpPrefix == X86Local::XD) | |||
195 | insnContext = EVEX_KB(IC_EVEX_L2_W_XD)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_L2_W_XD_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_L2_W_XD_K_B : (HasEVEX_KZ ? IC_EVEX_L2_W_XD_KZ : (HasEVEX_K? IC_EVEX_L2_W_XD_K : (HasEVEX_B ? IC_EVEX_L2_W_XD_B : IC_EVEX_L2_W_XD))))); | |||
196 | else if (OpPrefix == X86Local::PS) | |||
197 | insnContext = EVEX_KB(IC_EVEX_L2_W)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_L2_W_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_L2_W_K_B : (HasEVEX_KZ ? IC_EVEX_L2_W_KZ : (HasEVEX_K? IC_EVEX_L2_W_K : (HasEVEX_B ? IC_EVEX_L2_W_B : IC_EVEX_L2_W))))); | |||
198 | else { | |||
199 | errs() << "Instruction does not use a prefix: " << Name << "\n"; | |||
200 | llvm_unreachable("Invalid prefix")__builtin_unreachable(); | |||
201 | } | |||
202 | } else if (!EncodeRC && HasEVEX_L2Prefix) { | |||
203 | // EVEX_L2 | |||
204 | if (OpPrefix == X86Local::PD) | |||
205 | insnContext = EVEX_KB(IC_EVEX_L2_OPSIZE)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_L2_OPSIZE_KZ_B : ( HasEVEX_K && HasEVEX_B ? IC_EVEX_L2_OPSIZE_K_B : (HasEVEX_KZ ? IC_EVEX_L2_OPSIZE_KZ : (HasEVEX_K? IC_EVEX_L2_OPSIZE_K : ( HasEVEX_B ? IC_EVEX_L2_OPSIZE_B : IC_EVEX_L2_OPSIZE))))); | |||
206 | else if (OpPrefix == X86Local::XD) | |||
207 | insnContext = EVEX_KB(IC_EVEX_L2_XD)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_L2_XD_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_L2_XD_K_B : (HasEVEX_KZ ? IC_EVEX_L2_XD_KZ : (HasEVEX_K? IC_EVEX_L2_XD_K : (HasEVEX_B ? IC_EVEX_L2_XD_B : IC_EVEX_L2_XD))))); | |||
208 | else if (OpPrefix == X86Local::XS) | |||
209 | insnContext = EVEX_KB(IC_EVEX_L2_XS)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_L2_XS_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_L2_XS_K_B : (HasEVEX_KZ ? IC_EVEX_L2_XS_KZ : (HasEVEX_K? IC_EVEX_L2_XS_K : (HasEVEX_B ? IC_EVEX_L2_XS_B : IC_EVEX_L2_XS))))); | |||
210 | else if (OpPrefix == X86Local::PS) | |||
211 | insnContext = EVEX_KB(IC_EVEX_L2)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_L2_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_L2_K_B : (HasEVEX_KZ ? IC_EVEX_L2_KZ : (HasEVEX_K? IC_EVEX_L2_K : (HasEVEX_B ? IC_EVEX_L2_B : IC_EVEX_L2 ))))); | |||
212 | else { | |||
213 | errs() << "Instruction does not use a prefix: " << Name << "\n"; | |||
214 | llvm_unreachable("Invalid prefix")__builtin_unreachable(); | |||
215 | } | |||
216 | } | |||
217 | else if (HasVEX_W) { | |||
218 | // VEX_W | |||
219 | if (OpPrefix == X86Local::PD) | |||
220 | insnContext = EVEX_KB(IC_EVEX_W_OPSIZE)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_W_OPSIZE_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_W_OPSIZE_K_B : (HasEVEX_KZ ? IC_EVEX_W_OPSIZE_KZ : (HasEVEX_K? IC_EVEX_W_OPSIZE_K : (HasEVEX_B ? IC_EVEX_W_OPSIZE_B : IC_EVEX_W_OPSIZE))))); | |||
221 | else if (OpPrefix == X86Local::XS) | |||
222 | insnContext = EVEX_KB(IC_EVEX_W_XS)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_W_XS_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_W_XS_K_B : (HasEVEX_KZ ? IC_EVEX_W_XS_KZ : (HasEVEX_K? IC_EVEX_W_XS_K : (HasEVEX_B ? IC_EVEX_W_XS_B : IC_EVEX_W_XS))))); | |||
223 | else if (OpPrefix == X86Local::XD) | |||
224 | insnContext = EVEX_KB(IC_EVEX_W_XD)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_W_XD_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_W_XD_K_B : (HasEVEX_KZ ? IC_EVEX_W_XD_KZ : (HasEVEX_K? IC_EVEX_W_XD_K : (HasEVEX_B ? IC_EVEX_W_XD_B : IC_EVEX_W_XD))))); | |||
225 | else if (OpPrefix == X86Local::PS) | |||
226 | insnContext = EVEX_KB(IC_EVEX_W)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_W_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_W_K_B : (HasEVEX_KZ ? IC_EVEX_W_KZ : (HasEVEX_K? IC_EVEX_W_K : (HasEVEX_B ? IC_EVEX_W_B : IC_EVEX_W ))))); | |||
227 | else { | |||
228 | errs() << "Instruction does not use a prefix: " << Name << "\n"; | |||
229 | llvm_unreachable("Invalid prefix")__builtin_unreachable(); | |||
230 | } | |||
231 | } | |||
232 | // No L, no W | |||
233 | else if (OpPrefix == X86Local::PD) | |||
234 | insnContext = EVEX_KB(IC_EVEX_OPSIZE)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_OPSIZE_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_OPSIZE_K_B : (HasEVEX_KZ ? IC_EVEX_OPSIZE_KZ : (HasEVEX_K? IC_EVEX_OPSIZE_K : (HasEVEX_B ? IC_EVEX_OPSIZE_B : IC_EVEX_OPSIZE))))); | |||
235 | else if (OpPrefix == X86Local::XD) | |||
236 | insnContext = EVEX_KB(IC_EVEX_XD)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_XD_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_XD_K_B : (HasEVEX_KZ ? IC_EVEX_XD_KZ : (HasEVEX_K? IC_EVEX_XD_K : (HasEVEX_B ? IC_EVEX_XD_B : IC_EVEX_XD ))))); | |||
237 | else if (OpPrefix == X86Local::XS) | |||
238 | insnContext = EVEX_KB(IC_EVEX_XS)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_XS_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_XS_K_B : (HasEVEX_KZ ? IC_EVEX_XS_KZ : (HasEVEX_K? IC_EVEX_XS_K : (HasEVEX_B ? IC_EVEX_XS_B : IC_EVEX_XS ))))); | |||
239 | else if (OpPrefix == X86Local::PS) | |||
240 | insnContext = EVEX_KB(IC_EVEX)(HasEVEX_KZ && HasEVEX_B ? IC_EVEX_KZ_B : (HasEVEX_K && HasEVEX_B ? IC_EVEX_K_B : (HasEVEX_KZ ? IC_EVEX_KZ : (HasEVEX_K ? IC_EVEX_K : (HasEVEX_B ? IC_EVEX_B : IC_EVEX))))); | |||
241 | else { | |||
242 | errs() << "Instruction does not use a prefix: " << Name << "\n"; | |||
243 | llvm_unreachable("Invalid prefix")__builtin_unreachable(); | |||
244 | } | |||
245 | /// eof EVEX | |||
246 | } else if (Encoding == X86Local::VEX || Encoding == X86Local::XOP) { | |||
247 | if (HasVEX_LPrefix && HasVEX_W) { | |||
248 | if (OpPrefix == X86Local::PD) | |||
249 | insnContext = IC_VEX_L_W_OPSIZE; | |||
250 | else if (OpPrefix == X86Local::XS) | |||
251 | insnContext = IC_VEX_L_W_XS; | |||
252 | else if (OpPrefix == X86Local::XD) | |||
253 | insnContext = IC_VEX_L_W_XD; | |||
254 | else if (OpPrefix == X86Local::PS) | |||
255 | insnContext = IC_VEX_L_W; | |||
256 | else { | |||
257 | errs() << "Instruction does not use a prefix: " << Name << "\n"; | |||
258 | llvm_unreachable("Invalid prefix")__builtin_unreachable(); | |||
259 | } | |||
260 | } else if (OpPrefix == X86Local::PD && HasVEX_LPrefix) | |||
261 | insnContext = IC_VEX_L_OPSIZE; | |||
262 | else if (OpPrefix == X86Local::PD && HasVEX_W) | |||
263 | insnContext = IC_VEX_W_OPSIZE; | |||
264 | else if (OpPrefix == X86Local::PD && Is64Bit && | |||
265 | AdSize == X86Local::AdSize32) | |||
266 | insnContext = IC_64BIT_VEX_OPSIZE_ADSIZE; | |||
267 | else if (OpPrefix == X86Local::PD && Is64Bit) | |||
268 | insnContext = IC_64BIT_VEX_OPSIZE; | |||
269 | else if (OpPrefix == X86Local::PD) | |||
270 | insnContext = IC_VEX_OPSIZE; | |||
271 | else if (HasVEX_LPrefix && OpPrefix == X86Local::XS) | |||
272 | insnContext = IC_VEX_L_XS; | |||
273 | else if (HasVEX_LPrefix && OpPrefix == X86Local::XD) | |||
274 | insnContext = IC_VEX_L_XD; | |||
275 | else if (HasVEX_W && OpPrefix == X86Local::XS) | |||
276 | insnContext = IC_VEX_W_XS; | |||
277 | else if (HasVEX_W && OpPrefix == X86Local::XD) | |||
278 | insnContext = IC_VEX_W_XD; | |||
279 | else if (HasVEX_W && OpPrefix == X86Local::PS) | |||
280 | insnContext = IC_VEX_W; | |||
281 | else if (HasVEX_LPrefix && OpPrefix == X86Local::PS) | |||
282 | insnContext = IC_VEX_L; | |||
283 | else if (OpPrefix == X86Local::XD) | |||
284 | insnContext = IC_VEX_XD; | |||
285 | else if (OpPrefix == X86Local::XS) | |||
286 | insnContext = IC_VEX_XS; | |||
287 | else if (OpPrefix == X86Local::PS) | |||
288 | insnContext = IC_VEX; | |||
289 | else { | |||
290 | errs() << "Instruction does not use a prefix: " << Name << "\n"; | |||
291 | llvm_unreachable("Invalid prefix")__builtin_unreachable(); | |||
292 | } | |||
293 | } else if (Is64Bit || HasREX_WPrefix || AdSize == X86Local::AdSize64) { | |||
294 | if (HasREX_WPrefix && (OpSize == X86Local::OpSize16 || OpPrefix == X86Local::PD)) | |||
295 | insnContext = IC_64BIT_REXW_OPSIZE; | |||
296 | else if (HasREX_WPrefix && AdSize == X86Local::AdSize32) | |||
297 | insnContext = IC_64BIT_REXW_ADSIZE; | |||
298 | else if (OpSize == X86Local::OpSize16 && OpPrefix == X86Local::XD) | |||
299 | insnContext = IC_64BIT_XD_OPSIZE; | |||
300 | else if (OpSize == X86Local::OpSize16 && OpPrefix == X86Local::XS) | |||
301 | insnContext = IC_64BIT_XS_OPSIZE; | |||
302 | else if (AdSize == X86Local::AdSize32 && OpPrefix == X86Local::PD) | |||
303 | insnContext = IC_64BIT_OPSIZE_ADSIZE; | |||
304 | else if (OpSize == X86Local::OpSize16 && AdSize == X86Local::AdSize32) | |||
305 | insnContext = IC_64BIT_OPSIZE_ADSIZE; | |||
306 | else if (OpSize == X86Local::OpSize16 || OpPrefix == X86Local::PD) | |||
307 | insnContext = IC_64BIT_OPSIZE; | |||
308 | else if (AdSize == X86Local::AdSize32) | |||
309 | insnContext = IC_64BIT_ADSIZE; | |||
310 | else if (HasREX_WPrefix && OpPrefix == X86Local::XS) | |||
311 | insnContext = IC_64BIT_REXW_XS; | |||
312 | else if (HasREX_WPrefix && OpPrefix == X86Local::XD) | |||
313 | insnContext = IC_64BIT_REXW_XD; | |||
314 | else if (OpPrefix == X86Local::XD) | |||
315 | insnContext = IC_64BIT_XD; | |||
316 | else if (OpPrefix == X86Local::XS) | |||
317 | insnContext = IC_64BIT_XS; | |||
318 | else if (HasREX_WPrefix) | |||
319 | insnContext = IC_64BIT_REXW; | |||
320 | else | |||
321 | insnContext = IC_64BIT; | |||
322 | } else { | |||
323 | if (OpSize == X86Local::OpSize16 && OpPrefix == X86Local::XD) | |||
324 | insnContext = IC_XD_OPSIZE; | |||
325 | else if (OpSize == X86Local::OpSize16 && OpPrefix == X86Local::XS) | |||
326 | insnContext = IC_XS_OPSIZE; | |||
327 | else if (AdSize == X86Local::AdSize16 && OpPrefix == X86Local::XD) | |||
328 | insnContext = IC_XD_ADSIZE; | |||
329 | else if (AdSize == X86Local::AdSize16 && OpPrefix == X86Local::XS) | |||
330 | insnContext = IC_XS_ADSIZE; | |||
331 | else if (AdSize == X86Local::AdSize16 && OpPrefix == X86Local::PD) | |||
332 | insnContext = IC_OPSIZE_ADSIZE; | |||
333 | else if (OpSize == X86Local::OpSize16 && AdSize == X86Local::AdSize16) | |||
334 | insnContext = IC_OPSIZE_ADSIZE; | |||
335 | else if (OpSize == X86Local::OpSize16 || OpPrefix == X86Local::PD) | |||
336 | insnContext = IC_OPSIZE; | |||
337 | else if (AdSize == X86Local::AdSize16) | |||
338 | insnContext = IC_ADSIZE; | |||
339 | else if (OpPrefix == X86Local::XD) | |||
340 | insnContext = IC_XD; | |||
341 | else if (OpPrefix == X86Local::XS) | |||
342 | insnContext = IC_XS; | |||
343 | else | |||
344 | insnContext = IC; | |||
345 | } | |||
346 | ||||
347 | return insnContext; | |||
348 | } | |||
349 | ||||
350 | void RecognizableInstr::adjustOperandEncoding(OperandEncoding &encoding) { | |||
351 | // The scaling factor for AVX512 compressed displacement encoding is an | |||
352 | // instruction attribute. Adjust the ModRM encoding type to include the | |||
353 | // scale for compressed displacement. | |||
354 | if ((encoding != ENCODING_RM && | |||
355 | encoding != ENCODING_VSIB && | |||
356 | encoding != ENCODING_SIB) ||CD8_Scale == 0) | |||
357 | return; | |||
358 | encoding = (OperandEncoding)(encoding + Log2_32(CD8_Scale)); | |||
359 | assert(((encoding >= ENCODING_RM && encoding <= ENCODING_RM_CD64) ||(static_cast<void> (0)) | |||
360 | (encoding == ENCODING_SIB) ||(static_cast<void> (0)) | |||
361 | (encoding >= ENCODING_VSIB && encoding <= ENCODING_VSIB_CD64)) &&(static_cast<void> (0)) | |||
362 | "Invalid CDisp scaling")(static_cast<void> (0)); | |||
363 | } | |||
364 | ||||
365 | void RecognizableInstr::handleOperand(bool optional, unsigned &operandIndex, | |||
366 | unsigned &physicalOperandIndex, | |||
367 | unsigned numPhysicalOperands, | |||
368 | const unsigned *operandMapping, | |||
369 | OperandEncoding (*encodingFromString) | |||
370 | (const std::string&, | |||
371 | uint8_t OpSize)) { | |||
372 | if (optional
| |||
373 | if (physicalOperandIndex >= numPhysicalOperands) | |||
374 | return; | |||
375 | } else { | |||
376 | assert(physicalOperandIndex < numPhysicalOperands)(static_cast<void> (0)); | |||
377 | } | |||
378 | ||||
379 | while (operandMapping[operandIndex] != operandIndex) { | |||
| ||||
380 | Spec->operands[operandIndex].encoding = ENCODING_DUP; | |||
381 | Spec->operands[operandIndex].type = | |||
382 | (OperandType)(TYPE_DUP0 + operandMapping[operandIndex]); | |||
383 | ++operandIndex; | |||
384 | } | |||
385 | ||||
386 | StringRef typeName = (*Operands)[operandIndex].Rec->getName(); | |||
387 | ||||
388 | OperandEncoding encoding = encodingFromString(std::string(typeName), OpSize); | |||
389 | // Adjust the encoding type for an operand based on the instruction. | |||
390 | adjustOperandEncoding(encoding); | |||
391 | Spec->operands[operandIndex].encoding = encoding; | |||
392 | Spec->operands[operandIndex].type = | |||
393 | typeFromString(std::string(typeName), HasREX_WPrefix, OpSize); | |||
394 | ||||
395 | ++operandIndex; | |||
396 | ++physicalOperandIndex; | |||
397 | } | |||
398 | ||||
399 | void RecognizableInstr::emitInstructionSpecifier() { | |||
400 | Spec->name = Name; | |||
401 | ||||
402 | Spec->insnContext = insnContext(); | |||
403 | ||||
404 | const std::vector<CGIOperandList::OperandInfo> &OperandList = *Operands; | |||
405 | ||||
406 | unsigned numOperands = OperandList.size(); | |||
407 | unsigned numPhysicalOperands = 0; | |||
408 | ||||
409 | // operandMapping maps from operands in OperandList to their originals. | |||
410 | // If operandMapping[i] != i, then the entry is a duplicate. | |||
411 | unsigned operandMapping[X86_MAX_OPERANDS]; | |||
412 | assert(numOperands <= X86_MAX_OPERANDS && "X86_MAX_OPERANDS is not large enough")(static_cast<void> (0)); | |||
413 | ||||
414 | for (unsigned operandIndex = 0; operandIndex < numOperands; ++operandIndex) { | |||
| ||||
415 | if (!OperandList[operandIndex].Constraints.empty()) { | |||
416 | const CGIOperandList::ConstraintInfo &Constraint = | |||
417 | OperandList[operandIndex].Constraints[0]; | |||
418 | if (Constraint.isTied()) { | |||
419 | operandMapping[operandIndex] = operandIndex; | |||
420 | operandMapping[Constraint.getTiedOperand()] = operandIndex; | |||
421 | } else { | |||
422 | ++numPhysicalOperands; | |||
423 | operandMapping[operandIndex] = operandIndex; | |||
424 | } | |||
425 | } else { | |||
426 | ++numPhysicalOperands; | |||
427 | operandMapping[operandIndex] = operandIndex; | |||
428 | } | |||
429 | } | |||
430 | ||||
431 | #define HANDLE_OPERAND(class) \ | |||
432 | handleOperand(false, \ | |||
433 | operandIndex, \ | |||
434 | physicalOperandIndex, \ | |||
435 | numPhysicalOperands, \ | |||
436 | operandMapping, \ | |||
437 | class##EncodingFromString); | |||
438 | ||||
439 | #define HANDLE_OPTIONAL(class) \ | |||
440 | handleOperand(true, \ | |||
441 | operandIndex, \ | |||
442 | physicalOperandIndex, \ | |||
443 | numPhysicalOperands, \ | |||
444 | operandMapping, \ | |||
445 | class##EncodingFromString); | |||
446 | ||||
447 | // operandIndex should always be < numOperands | |||
448 | unsigned operandIndex = 0; | |||
449 | // physicalOperandIndex should always be < numPhysicalOperands | |||
450 | unsigned physicalOperandIndex = 0; | |||
451 | ||||
452 | #ifndef NDEBUG1 | |||
453 | // Given the set of prefix bits, how many additional operands does the | |||
454 | // instruction have? | |||
455 | unsigned additionalOperands = 0; | |||
456 | if (HasVEX_4V) | |||
457 | ++additionalOperands; | |||
458 | if (HasEVEX_K) | |||
459 | ++additionalOperands; | |||
460 | #endif | |||
461 | ||||
462 | switch (Form) { | |||
463 | default: llvm_unreachable("Unhandled form")__builtin_unreachable(); | |||
464 | case X86Local::PrefixByte: | |||
465 | return; | |||
466 | case X86Local::RawFrmSrc: | |||
467 | HANDLE_OPERAND(relocation); | |||
468 | return; | |||
469 | case X86Local::RawFrmDst: | |||
470 | HANDLE_OPERAND(relocation); | |||
471 | return; | |||
472 | case X86Local::RawFrmDstSrc: | |||
473 | HANDLE_OPERAND(relocation); | |||
474 | HANDLE_OPERAND(relocation); | |||
475 | return; | |||
476 | case X86Local::RawFrm: | |||
477 | // Operand 1 (optional) is an address or immediate. | |||
478 | assert(numPhysicalOperands <= 1 &&(static_cast<void> (0)) | |||
479 | "Unexpected number of operands for RawFrm")(static_cast<void> (0)); | |||
480 | HANDLE_OPTIONAL(relocation) | |||
481 | break; | |||
482 | case X86Local::RawFrmMemOffs: | |||
483 | // Operand 1 is an address. | |||
484 | HANDLE_OPERAND(relocation); | |||
485 | break; | |||
486 | case X86Local::AddRegFrm: | |||
487 | // Operand 1 is added to the opcode. | |||
488 | // Operand 2 (optional) is an address. | |||
489 | assert(numPhysicalOperands >= 1 && numPhysicalOperands <= 2 &&(static_cast<void> (0)) | |||
490 | "Unexpected number of operands for AddRegFrm")(static_cast<void> (0)); | |||
491 | HANDLE_OPERAND(opcodeModifier) | |||
492 | HANDLE_OPTIONAL(relocation) | |||
493 | break; | |||
494 | case X86Local::AddCCFrm: | |||
495 | // Operand 1 (optional) is an address or immediate. | |||
496 | assert(numPhysicalOperands == 2 &&(static_cast<void> (0)) | |||
497 | "Unexpected number of operands for AddCCFrm")(static_cast<void> (0)); | |||
498 | HANDLE_OPERAND(relocation) | |||
499 | HANDLE_OPERAND(opcodeModifier) | |||
500 | break; | |||
501 | case X86Local::MRMDestReg: | |||
502 | // Operand 1 is a register operand in the R/M field. | |||
503 | // - In AVX512 there may be a mask operand here - | |||
504 | // Operand 2 is a register operand in the Reg/Opcode field. | |||
505 | // - In AVX, there is a register operand in the VEX.vvvv field here - | |||
506 | // Operand 3 (optional) is an immediate. | |||
507 | assert(numPhysicalOperands >= 2 + additionalOperands &&(static_cast<void> (0)) | |||
508 | numPhysicalOperands <= 3 + additionalOperands &&(static_cast<void> (0)) | |||
509 | "Unexpected number of operands for MRMDestRegFrm")(static_cast<void> (0)); | |||
510 | ||||
511 | HANDLE_OPERAND(rmRegister) | |||
512 | if (HasEVEX_K) | |||
513 | HANDLE_OPERAND(writemaskRegister) | |||
514 | ||||
515 | if (HasVEX_4V) | |||
516 | // FIXME: In AVX, the register below becomes the one encoded | |||
517 | // in ModRMVEX and the one above the one in the VEX.VVVV field | |||
518 | HANDLE_OPERAND(vvvvRegister) | |||
519 | ||||
520 | HANDLE_OPERAND(roRegister) | |||
521 | HANDLE_OPTIONAL(immediate) | |||
522 | break; | |||
523 | case X86Local::MRMDestMem: | |||
524 | case X86Local::MRMDestMemFSIB: | |||
525 | // Operand 1 is a memory operand (possibly SIB-extended) | |||
526 | // Operand 2 is a register operand in the Reg/Opcode field. | |||
527 | // - In AVX, there is a register operand in the VEX.vvvv field here - | |||
528 | // Operand 3 (optional) is an immediate. | |||
529 | assert(numPhysicalOperands >= 2 + additionalOperands &&(static_cast<void> (0)) | |||
530 | numPhysicalOperands <= 3 + additionalOperands &&(static_cast<void> (0)) | |||
531 | "Unexpected number of operands for MRMDestMemFrm with VEX_4V")(static_cast<void> (0)); | |||
532 | ||||
533 | HANDLE_OPERAND(memory) | |||
534 | ||||
535 | if (HasEVEX_K) | |||
536 | HANDLE_OPERAND(writemaskRegister) | |||
537 | ||||
538 | if (HasVEX_4V) | |||
539 | // FIXME: In AVX, the register below becomes the one encoded | |||
540 | // in ModRMVEX and the one above the one in the VEX.VVVV field | |||
541 | HANDLE_OPERAND(vvvvRegister) | |||
542 | ||||
543 | HANDLE_OPERAND(roRegister) | |||
544 | HANDLE_OPTIONAL(immediate) | |||
545 | break; | |||
546 | case X86Local::MRMSrcReg: | |||
547 | // Operand 1 is a register operand in the Reg/Opcode field. | |||
548 | // Operand 2 is a register operand in the R/M field. | |||
549 | // - In AVX, there is a register operand in the VEX.vvvv field here - | |||
550 | // Operand 3 (optional) is an immediate. | |||
551 | // Operand 4 (optional) is an immediate. | |||
552 | ||||
553 | assert(numPhysicalOperands >= 2 + additionalOperands &&(static_cast<void> (0)) | |||
554 | numPhysicalOperands <= 4 + additionalOperands &&(static_cast<void> (0)) | |||
555 | "Unexpected number of operands for MRMSrcRegFrm")(static_cast<void> (0)); | |||
556 | ||||
557 | HANDLE_OPERAND(roRegister) | |||
558 | ||||
559 | if (HasEVEX_K) | |||
560 | HANDLE_OPERAND(writemaskRegister) | |||
561 | ||||
562 | if (HasVEX_4V) | |||
563 | // FIXME: In AVX, the register below becomes the one encoded | |||
564 | // in ModRMVEX and the one above the one in the VEX.VVVV field | |||
565 | HANDLE_OPERAND(vvvvRegister) | |||
566 | ||||
567 | HANDLE_OPERAND(rmRegister) | |||
568 | HANDLE_OPTIONAL(immediate) | |||
569 | HANDLE_OPTIONAL(immediate) // above might be a register in 7:4 | |||
570 | break; | |||
571 | case X86Local::MRMSrcReg4VOp3: | |||
572 | assert(numPhysicalOperands == 3 &&(static_cast<void> (0)) | |||
573 | "Unexpected number of operands for MRMSrcReg4VOp3Frm")(static_cast<void> (0)); | |||
574 | HANDLE_OPERAND(roRegister) | |||
575 | HANDLE_OPERAND(rmRegister) | |||
576 | HANDLE_OPERAND(vvvvRegister) | |||
577 | break; | |||
578 | case X86Local::MRMSrcRegOp4: | |||
579 | assert(numPhysicalOperands >= 4 && numPhysicalOperands <= 5 &&(static_cast<void> (0)) | |||
580 | "Unexpected number of operands for MRMSrcRegOp4Frm")(static_cast<void> (0)); | |||
581 | HANDLE_OPERAND(roRegister) | |||
582 | HANDLE_OPERAND(vvvvRegister) | |||
583 | HANDLE_OPERAND(immediate) // Register in imm[7:4] | |||
584 | HANDLE_OPERAND(rmRegister) | |||
585 | HANDLE_OPTIONAL(immediate) | |||
586 | break; | |||
587 | case X86Local::MRMSrcRegCC: | |||
588 | assert(numPhysicalOperands == 3 &&(static_cast<void> (0)) | |||
589 | "Unexpected number of operands for MRMSrcRegCC")(static_cast<void> (0)); | |||
590 | HANDLE_OPERAND(roRegister) | |||
591 | HANDLE_OPERAND(rmRegister) | |||
592 | HANDLE_OPERAND(opcodeModifier) | |||
593 | break; | |||
594 | case X86Local::MRMSrcMem: | |||
595 | case X86Local::MRMSrcMemFSIB: | |||
596 | // Operand 1 is a register operand in the Reg/Opcode field. | |||
597 | // Operand 2 is a memory operand (possibly SIB-extended) | |||
598 | // - In AVX, there is a register operand in the VEX.vvvv field here - | |||
599 | // Operand 3 (optional) is an immediate. | |||
600 | ||||
601 | assert(numPhysicalOperands >= 2 + additionalOperands &&(static_cast<void> (0)) | |||
602 | numPhysicalOperands <= 4 + additionalOperands &&(static_cast<void> (0)) | |||
603 | "Unexpected number of operands for MRMSrcMemFrm")(static_cast<void> (0)); | |||
604 | ||||
605 | HANDLE_OPERAND(roRegister) | |||
606 | ||||
607 | if (HasEVEX_K) | |||
608 | HANDLE_OPERAND(writemaskRegister) | |||
609 | ||||
610 | if (HasVEX_4V) | |||
611 | // FIXME: In AVX, the register below becomes the one encoded | |||
612 | // in ModRMVEX and the one above the one in the VEX.VVVV field | |||
613 | HANDLE_OPERAND(vvvvRegister) | |||
614 | ||||
615 | HANDLE_OPERAND(memory) | |||
616 | HANDLE_OPTIONAL(immediate) | |||
617 | HANDLE_OPTIONAL(immediate) // above might be a register in 7:4 | |||
618 | break; | |||
619 | case X86Local::MRMSrcMem4VOp3: | |||
620 | assert(numPhysicalOperands == 3 &&(static_cast<void> (0)) | |||
621 | "Unexpected number of operands for MRMSrcMem4VOp3Frm")(static_cast<void> (0)); | |||
622 | HANDLE_OPERAND(roRegister) | |||
623 | HANDLE_OPERAND(memory) | |||
624 | HANDLE_OPERAND(vvvvRegister) | |||
625 | break; | |||
626 | case X86Local::MRMSrcMemOp4: | |||
627 | assert(numPhysicalOperands >= 4 && numPhysicalOperands <= 5 &&(static_cast<void> (0)) | |||
628 | "Unexpected number of operands for MRMSrcMemOp4Frm")(static_cast<void> (0)); | |||
629 | HANDLE_OPERAND(roRegister) | |||
630 | HANDLE_OPERAND(vvvvRegister) | |||
631 | HANDLE_OPERAND(immediate) // Register in imm[7:4] | |||
632 | HANDLE_OPERAND(memory) | |||
633 | HANDLE_OPTIONAL(immediate) | |||
634 | break; | |||
635 | case X86Local::MRMSrcMemCC: | |||
636 | assert(numPhysicalOperands == 3 &&(static_cast<void> (0)) | |||
637 | "Unexpected number of operands for MRMSrcMemCC")(static_cast<void> (0)); | |||
638 | HANDLE_OPERAND(roRegister) | |||
639 | HANDLE_OPERAND(memory) | |||
640 | HANDLE_OPERAND(opcodeModifier) | |||
641 | break; | |||
642 | case X86Local::MRMXrCC: | |||
643 | assert(numPhysicalOperands == 2 &&(static_cast<void> (0)) | |||
644 | "Unexpected number of operands for MRMXrCC")(static_cast<void> (0)); | |||
645 | HANDLE_OPERAND(rmRegister) | |||
646 | HANDLE_OPERAND(opcodeModifier) | |||
647 | break; | |||
648 | case X86Local::MRMr0: | |||
649 | // Operand 1 is a register operand in the R/M field. | |||
650 | HANDLE_OPERAND(roRegister) | |||
651 | break; | |||
652 | case X86Local::MRMXr: | |||
653 | case X86Local::MRM0r: | |||
654 | case X86Local::MRM1r: | |||
655 | case X86Local::MRM2r: | |||
656 | case X86Local::MRM3r: | |||
657 | case X86Local::MRM4r: | |||
658 | case X86Local::MRM5r: | |||
659 | case X86Local::MRM6r: | |||
660 | case X86Local::MRM7r: | |||
661 | // Operand 1 is a register operand in the R/M field. | |||
662 | // Operand 2 (optional) is an immediate or relocation. | |||
663 | // Operand 3 (optional) is an immediate. | |||
664 | assert(numPhysicalOperands >= 0 + additionalOperands &&(static_cast<void> (0)) | |||
665 | numPhysicalOperands <= 3 + additionalOperands &&(static_cast<void> (0)) | |||
666 | "Unexpected number of operands for MRMnr")(static_cast<void> (0)); | |||
667 | ||||
668 | if (HasVEX_4V) | |||
669 | HANDLE_OPERAND(vvvvRegister) | |||
670 | ||||
671 | if (HasEVEX_K) | |||
672 | HANDLE_OPERAND(writemaskRegister) | |||
673 | HANDLE_OPTIONAL(rmRegister) | |||
674 | HANDLE_OPTIONAL(relocation) | |||
675 | HANDLE_OPTIONAL(immediate) | |||
676 | break; | |||
677 | case X86Local::MRMXmCC: | |||
678 | assert(numPhysicalOperands == 2 &&(static_cast<void> (0)) | |||
679 | "Unexpected number of operands for MRMXm")(static_cast<void> (0)); | |||
680 | HANDLE_OPERAND(memory) | |||
681 | HANDLE_OPERAND(opcodeModifier) | |||
682 | break; | |||
683 | case X86Local::MRMXm: | |||
684 | case X86Local::MRM0m: | |||
685 | case X86Local::MRM1m: | |||
686 | case X86Local::MRM2m: | |||
687 | case X86Local::MRM3m: | |||
688 | case X86Local::MRM4m: | |||
689 | case X86Local::MRM5m: | |||
690 | case X86Local::MRM6m: | |||
691 | case X86Local::MRM7m: | |||
692 | // Operand 1 is a memory operand (possibly SIB-extended) | |||
693 | // Operand 2 (optional) is an immediate or relocation. | |||
694 | assert(numPhysicalOperands >= 1 + additionalOperands &&(static_cast<void> (0)) | |||
695 | numPhysicalOperands <= 2 + additionalOperands &&(static_cast<void> (0)) | |||
696 | "Unexpected number of operands for MRMnm")(static_cast<void> (0)); | |||
697 | ||||
698 | if (HasVEX_4V) | |||
699 | HANDLE_OPERAND(vvvvRegister) | |||
700 | if (HasEVEX_K) | |||
701 | HANDLE_OPERAND(writemaskRegister) | |||
702 | HANDLE_OPERAND(memory) | |||
703 | HANDLE_OPTIONAL(relocation) | |||
704 | break; | |||
705 | case X86Local::RawFrmImm8: | |||
706 | // operand 1 is a 16-bit immediate | |||
707 | // operand 2 is an 8-bit immediate | |||
708 | assert(numPhysicalOperands == 2 &&(static_cast<void> (0)) | |||
709 | "Unexpected number of operands for X86Local::RawFrmImm8")(static_cast<void> (0)); | |||
710 | HANDLE_OPERAND(immediate) | |||
711 | HANDLE_OPERAND(immediate) | |||
712 | break; | |||
713 | case X86Local::RawFrmImm16: | |||
714 | // operand 1 is a 16-bit immediate | |||
715 | // operand 2 is a 16-bit immediate | |||
716 | HANDLE_OPERAND(immediate) | |||
717 | HANDLE_OPERAND(immediate) | |||
718 | break; | |||
719 | case X86Local::MRM0X: | |||
720 | case X86Local::MRM1X: | |||
721 | case X86Local::MRM2X: | |||
722 | case X86Local::MRM3X: | |||
723 | case X86Local::MRM4X: | |||
724 | case X86Local::MRM5X: | |||
725 | case X86Local::MRM6X: | |||
726 | case X86Local::MRM7X: | |||
727 | #define MAP(from, to) case X86Local::MRM_##from: | |||
728 | X86_INSTR_MRM_MAPPINGMAP(C0, 64) MAP(C1, 65) MAP(C2, 66) MAP(C3, 67) MAP(C4, 68) MAP (C5, 69) MAP(C6, 70) MAP(C7, 71) MAP(C8, 72) MAP(C9, 73) MAP( CA, 74) MAP(CB, 75) MAP(CC, 76) MAP(CD, 77) MAP(CE, 78) MAP(CF , 79) MAP(D0, 80) MAP(D1, 81) MAP(D2, 82) MAP(D3, 83) MAP(D4, 84) MAP(D5, 85) MAP(D6, 86) MAP(D7, 87) MAP(D8, 88) MAP(D9, 89 ) MAP(DA, 90) MAP(DB, 91) MAP(DC, 92) MAP(DD, 93) MAP(DE, 94) MAP(DF, 95) MAP(E0, 96) MAP(E1, 97) MAP(E2, 98) MAP(E3, 99) MAP (E4, 100) MAP(E5, 101) MAP(E6, 102) MAP(E7, 103) MAP(E8, 104) MAP(E9, 105) MAP(EA, 106) MAP(EB, 107) MAP(EC, 108) MAP(ED, 109 ) MAP(EE, 110) MAP(EF, 111) MAP(F0, 112) MAP(F1, 113) MAP(F2, 114) MAP(F3, 115) MAP(F4, 116) MAP(F5, 117) MAP(F6, 118) MAP (F7, 119) MAP(F8, 120) MAP(F9, 121) MAP(FA, 122) MAP(FB, 123) MAP(FC, 124) MAP(FD, 125) MAP(FE, 126) MAP(FF, 127) | |||
729 | #undef MAP | |||
730 | HANDLE_OPTIONAL(relocation) | |||
731 | break; | |||
732 | } | |||
733 | ||||
734 | #undef HANDLE_OPERAND | |||
735 | #undef HANDLE_OPTIONAL | |||
736 | } | |||
737 | ||||
738 | void RecognizableInstr::emitDecodePath(DisassemblerTables &tables) const { | |||
739 | // Special cases where the LLVM tables are not complete | |||
740 | ||||
741 | #define MAP(from, to) \ | |||
742 | case X86Local::MRM_##from: | |||
743 | ||||
744 | llvm::Optional<OpcodeType> opcodeType; | |||
745 | switch (OpMap) { | |||
746 | default: llvm_unreachable("Invalid map!")__builtin_unreachable(); | |||
747 | case X86Local::OB: opcodeType = ONEBYTE; break; | |||
748 | case X86Local::TB: opcodeType = TWOBYTE; break; | |||
749 | case X86Local::T8: opcodeType = THREEBYTE_38; break; | |||
750 | case X86Local::TA: opcodeType = THREEBYTE_3A; break; | |||
751 | case X86Local::XOP8: opcodeType = XOP8_MAP; break; | |||
752 | case X86Local::XOP9: opcodeType = XOP9_MAP; break; | |||
753 | case X86Local::XOPA: opcodeType = XOPA_MAP; break; | |||
754 | case X86Local::ThreeDNow: opcodeType = THREEDNOW_MAP; break; | |||
755 | case X86Local::T_MAP5: opcodeType = MAP5; break; | |||
756 | case X86Local::T_MAP6: opcodeType = MAP6; break; | |||
757 | } | |||
758 | ||||
759 | std::unique_ptr<ModRMFilter> filter; | |||
760 | switch (Form) { | |||
761 | default: llvm_unreachable("Invalid form!")__builtin_unreachable(); | |||
762 | case X86Local::Pseudo: llvm_unreachable("Pseudo should not be emitted!")__builtin_unreachable(); | |||
763 | case X86Local::RawFrm: | |||
764 | case X86Local::AddRegFrm: | |||
765 | case X86Local::RawFrmMemOffs: | |||
766 | case X86Local::RawFrmSrc: | |||
767 | case X86Local::RawFrmDst: | |||
768 | case X86Local::RawFrmDstSrc: | |||
769 | case X86Local::RawFrmImm8: | |||
770 | case X86Local::RawFrmImm16: | |||
771 | case X86Local::AddCCFrm: | |||
772 | case X86Local::PrefixByte: | |||
773 | filter = std::make_unique<DumbFilter>(); | |||
774 | break; | |||
775 | case X86Local::MRMDestReg: | |||
776 | case X86Local::MRMSrcReg: | |||
777 | case X86Local::MRMSrcReg4VOp3: | |||
778 | case X86Local::MRMSrcRegOp4: | |||
779 | case X86Local::MRMSrcRegCC: | |||
780 | case X86Local::MRMXrCC: | |||
781 | case X86Local::MRMXr: | |||
782 | filter = std::make_unique<ModFilter>(true); | |||
783 | break; | |||
784 | case X86Local::MRMDestMem: | |||
785 | case X86Local::MRMDestMemFSIB: | |||
786 | case X86Local::MRMSrcMem: | |||
787 | case X86Local::MRMSrcMemFSIB: | |||
788 | case X86Local::MRMSrcMem4VOp3: | |||
789 | case X86Local::MRMSrcMemOp4: | |||
790 | case X86Local::MRMSrcMemCC: | |||
791 | case X86Local::MRMXmCC: | |||
792 | case X86Local::MRMXm: | |||
793 | filter = std::make_unique<ModFilter>(false); | |||
794 | break; | |||
795 | case X86Local::MRM0r: case X86Local::MRM1r: | |||
796 | case X86Local::MRM2r: case X86Local::MRM3r: | |||
797 | case X86Local::MRM4r: case X86Local::MRM5r: | |||
798 | case X86Local::MRM6r: case X86Local::MRM7r: | |||
799 | filter = std::make_unique<ExtendedFilter>(true, Form - X86Local::MRM0r); | |||
800 | break; | |||
801 | case X86Local::MRM0X: case X86Local::MRM1X: | |||
802 | case X86Local::MRM2X: case X86Local::MRM3X: | |||
803 | case X86Local::MRM4X: case X86Local::MRM5X: | |||
804 | case X86Local::MRM6X: case X86Local::MRM7X: | |||
805 | filter = std::make_unique<ExtendedFilter>(true, Form - X86Local::MRM0X); | |||
806 | break; | |||
807 | case X86Local::MRMr0: | |||
808 | filter = std::make_unique<ExtendedRMFilter>(true, Form - X86Local::MRMr0); | |||
809 | break; | |||
810 | case X86Local::MRM0m: case X86Local::MRM1m: | |||
811 | case X86Local::MRM2m: case X86Local::MRM3m: | |||
812 | case X86Local::MRM4m: case X86Local::MRM5m: | |||
813 | case X86Local::MRM6m: case X86Local::MRM7m: | |||
814 | filter = std::make_unique<ExtendedFilter>(false, Form - X86Local::MRM0m); | |||
815 | break; | |||
816 | X86_INSTR_MRM_MAPPINGMAP(C0, 64) MAP(C1, 65) MAP(C2, 66) MAP(C3, 67) MAP(C4, 68) MAP (C5, 69) MAP(C6, 70) MAP(C7, 71) MAP(C8, 72) MAP(C9, 73) MAP( CA, 74) MAP(CB, 75) MAP(CC, 76) MAP(CD, 77) MAP(CE, 78) MAP(CF , 79) MAP(D0, 80) MAP(D1, 81) MAP(D2, 82) MAP(D3, 83) MAP(D4, 84) MAP(D5, 85) MAP(D6, 86) MAP(D7, 87) MAP(D8, 88) MAP(D9, 89 ) MAP(DA, 90) MAP(DB, 91) MAP(DC, 92) MAP(DD, 93) MAP(DE, 94) MAP(DF, 95) MAP(E0, 96) MAP(E1, 97) MAP(E2, 98) MAP(E3, 99) MAP (E4, 100) MAP(E5, 101) MAP(E6, 102) MAP(E7, 103) MAP(E8, 104) MAP(E9, 105) MAP(EA, 106) MAP(EB, 107) MAP(EC, 108) MAP(ED, 109 ) MAP(EE, 110) MAP(EF, 111) MAP(F0, 112) MAP(F1, 113) MAP(F2, 114) MAP(F3, 115) MAP(F4, 116) MAP(F5, 117) MAP(F6, 118) MAP (F7, 119) MAP(F8, 120) MAP(F9, 121) MAP(FA, 122) MAP(FB, 123) MAP(FC, 124) MAP(FD, 125) MAP(FE, 126) MAP(FF, 127) | |||
817 | filter = std::make_unique<ExactFilter>(0xC0 + Form - X86Local::MRM_C0); | |||
818 | break; | |||
819 | } // switch (Form) | |||
820 | ||||
821 | uint8_t opcodeToSet = Opcode; | |||
822 | ||||
823 | unsigned AddressSize = 0; | |||
824 | switch (AdSize) { | |||
825 | case X86Local::AdSize16: AddressSize = 16; break; | |||
826 | case X86Local::AdSize32: AddressSize = 32; break; | |||
827 | case X86Local::AdSize64: AddressSize = 64; break; | |||
828 | } | |||
829 | ||||
830 | assert(opcodeType && "Opcode type not set")(static_cast<void> (0)); | |||
831 | assert(filter && "Filter not set")(static_cast<void> (0)); | |||
832 | ||||
833 | if (Form == X86Local::AddRegFrm || Form == X86Local::MRMSrcRegCC || | |||
834 | Form == X86Local::MRMSrcMemCC || Form == X86Local::MRMXrCC || | |||
835 | Form == X86Local::MRMXmCC || Form == X86Local::AddCCFrm) { | |||
836 | unsigned Count = Form == X86Local::AddRegFrm ? 8 : 16; | |||
837 | assert(((opcodeToSet % Count) == 0) && "ADDREG_FRM opcode not aligned")(static_cast<void> (0)); | |||
838 | ||||
839 | uint8_t currentOpcode; | |||
840 | ||||
841 | for (currentOpcode = opcodeToSet; currentOpcode < opcodeToSet + Count; | |||
842 | ++currentOpcode) | |||
843 | tables.setTableFields(*opcodeType, insnContext(), currentOpcode, *filter, | |||
844 | UID, Is32Bit, OpPrefix == 0, | |||
845 | IgnoresVEX_L || EncodeRC, | |||
846 | IgnoresVEX_W, AddressSize); | |||
847 | } else { | |||
848 | tables.setTableFields(*opcodeType, insnContext(), opcodeToSet, *filter, UID, | |||
849 | Is32Bit, OpPrefix == 0, IgnoresVEX_L || EncodeRC, | |||
850 | IgnoresVEX_W, AddressSize); | |||
851 | } | |||
852 | ||||
853 | #undef MAP | |||
854 | } | |||
855 | ||||
856 | #define TYPE(str, type) if (s == str) return type; | |||
857 | OperandType RecognizableInstr::typeFromString(const std::string &s, | |||
858 | bool hasREX_WPrefix, | |||
859 | uint8_t OpSize) { | |||
860 | if(hasREX_WPrefix) { | |||
861 | // For instructions with a REX_W prefix, a declared 32-bit register encoding | |||
862 | // is special. | |||
863 | TYPE("GR32", TYPE_R32) | |||
864 | } | |||
865 | if(OpSize == X86Local::OpSize16) { | |||
866 | // For OpSize16 instructions, a declared 16-bit register or | |||
867 | // immediate encoding is special. | |||
868 | TYPE("GR16", TYPE_Rv) | |||
869 | } else if(OpSize == X86Local::OpSize32) { | |||
870 | // For OpSize32 instructions, a declared 32-bit register or | |||
871 | // immediate encoding is special. | |||
872 | TYPE("GR32", TYPE_Rv) | |||
873 | } | |||
874 | TYPE("i16mem", TYPE_M) | |||
875 | TYPE("i16imm", TYPE_IMM) | |||
876 | TYPE("i16i8imm", TYPE_IMM) | |||
877 | TYPE("GR16", TYPE_R16) | |||
878 | TYPE("GR16orGR32orGR64", TYPE_R16) | |||
879 | TYPE("i32mem", TYPE_M) | |||
880 | TYPE("i32imm", TYPE_IMM) | |||
881 | TYPE("i32i8imm", TYPE_IMM) | |||
882 | TYPE("GR32", TYPE_R32) | |||
883 | TYPE("GR32orGR64", TYPE_R32) | |||
884 | TYPE("i64mem", TYPE_M) | |||
885 | TYPE("i64i32imm", TYPE_IMM) | |||
886 | TYPE("i64i8imm", TYPE_IMM) | |||
887 | TYPE("GR64", TYPE_R64) | |||
888 | TYPE("i8mem", TYPE_M) | |||
889 | TYPE("i8imm", TYPE_IMM) | |||
890 | TYPE("u4imm", TYPE_UIMM8) | |||
891 | TYPE("u8imm", TYPE_UIMM8) | |||
892 | TYPE("i16u8imm", TYPE_UIMM8) | |||
893 | TYPE("i32u8imm", TYPE_UIMM8) | |||
894 | TYPE("i64u8imm", TYPE_UIMM8) | |||
895 | TYPE("GR8", TYPE_R8) | |||
896 | TYPE("VR128", TYPE_XMM) | |||
897 | TYPE("VR128X", TYPE_XMM) | |||
898 | TYPE("f128mem", TYPE_M) | |||
899 | TYPE("f256mem", TYPE_M) | |||
900 | TYPE("f512mem", TYPE_M) | |||
901 | TYPE("FR128", TYPE_XMM) | |||
902 | TYPE("FR64", TYPE_XMM) | |||
903 | TYPE("FR64X", TYPE_XMM) | |||
904 | TYPE("f64mem", TYPE_M) | |||
905 | TYPE("sdmem", TYPE_M) | |||
906 | TYPE("FR16X", TYPE_XMM) | |||
907 | TYPE("FR32", TYPE_XMM) | |||
908 | TYPE("FR32X", TYPE_XMM) | |||
909 | TYPE("f32mem", TYPE_M) | |||
910 | TYPE("f16mem", TYPE_M) | |||
911 | TYPE("ssmem", TYPE_M) | |||
912 | TYPE("shmem", TYPE_M) | |||
913 | TYPE("RST", TYPE_ST) | |||
914 | TYPE("RSTi", TYPE_ST) | |||
915 | TYPE("i128mem", TYPE_M) | |||
916 | TYPE("i256mem", TYPE_M) | |||
917 | TYPE("i512mem", TYPE_M) | |||
918 | TYPE("i64i32imm_brtarget", TYPE_REL) | |||
919 | TYPE("i16imm_brtarget", TYPE_REL) | |||
920 | TYPE("i32imm_brtarget", TYPE_REL) | |||
921 | TYPE("ccode", TYPE_IMM) | |||
922 | TYPE("AVX512RC", TYPE_IMM) | |||
923 | TYPE("brtarget32", TYPE_REL) | |||
924 | TYPE("brtarget16", TYPE_REL) | |||
925 | TYPE("brtarget8", TYPE_REL) | |||
926 | TYPE("f80mem", TYPE_M) | |||
927 | TYPE("lea64_32mem", TYPE_M) | |||
928 | TYPE("lea64mem", TYPE_M) | |||
929 | TYPE("VR64", TYPE_MM64) | |||
930 | TYPE("i64imm", TYPE_IMM) | |||
931 | TYPE("anymem", TYPE_M) | |||
932 | TYPE("opaquemem", TYPE_M) | |||
933 | TYPE("sibmem", TYPE_MSIB) | |||
934 | TYPE("SEGMENT_REG", TYPE_SEGMENTREG) | |||
935 | TYPE("DEBUG_REG", TYPE_DEBUGREG) | |||
936 | TYPE("CONTROL_REG", TYPE_CONTROLREG) | |||
937 | TYPE("srcidx8", TYPE_SRCIDX) | |||
938 | TYPE("srcidx16", TYPE_SRCIDX) | |||
939 | TYPE("srcidx32", TYPE_SRCIDX) | |||
940 | TYPE("srcidx64", TYPE_SRCIDX) | |||
941 | TYPE("dstidx8", TYPE_DSTIDX) | |||
942 | TYPE("dstidx16", TYPE_DSTIDX) | |||
943 | TYPE("dstidx32", TYPE_DSTIDX) | |||
944 | TYPE("dstidx64", TYPE_DSTIDX) | |||
945 | TYPE("offset16_8", TYPE_MOFFS) | |||
946 | TYPE("offset16_16", TYPE_MOFFS) | |||
947 | TYPE("offset16_32", TYPE_MOFFS) | |||
948 | TYPE("offset32_8", TYPE_MOFFS) | |||
949 | TYPE("offset32_16", TYPE_MOFFS) | |||
950 | TYPE("offset32_32", TYPE_MOFFS) | |||
951 | TYPE("offset32_64", TYPE_MOFFS) | |||
952 | TYPE("offset64_8", TYPE_MOFFS) | |||
953 | TYPE("offset64_16", TYPE_MOFFS) | |||
954 | TYPE("offset64_32", TYPE_MOFFS) | |||
955 | TYPE("offset64_64", TYPE_MOFFS) | |||
956 | TYPE("VR256", TYPE_YMM) | |||
957 | TYPE("VR256X", TYPE_YMM) | |||
958 | TYPE("VR512", TYPE_ZMM) | |||
959 | TYPE("VK1", TYPE_VK) | |||
960 | TYPE("VK1WM", TYPE_VK) | |||
961 | TYPE("VK2", TYPE_VK) | |||
962 | TYPE("VK2WM", TYPE_VK) | |||
963 | TYPE("VK4", TYPE_VK) | |||
964 | TYPE("VK4WM", TYPE_VK) | |||
965 | TYPE("VK8", TYPE_VK) | |||
966 | TYPE("VK8WM", TYPE_VK) | |||
967 | TYPE("VK16", TYPE_VK) | |||
968 | TYPE("VK16WM", TYPE_VK) | |||
969 | TYPE("VK32", TYPE_VK) | |||
970 | TYPE("VK32WM", TYPE_VK) | |||
971 | TYPE("VK64", TYPE_VK) | |||
972 | TYPE("VK64WM", TYPE_VK) | |||
973 | TYPE("VK1Pair", TYPE_VK_PAIR) | |||
974 | TYPE("VK2Pair", TYPE_VK_PAIR) | |||
975 | TYPE("VK4Pair", TYPE_VK_PAIR) | |||
976 | TYPE("VK8Pair", TYPE_VK_PAIR) | |||
977 | TYPE("VK16Pair", TYPE_VK_PAIR) | |||
978 | TYPE("vx64mem", TYPE_MVSIBX) | |||
979 | TYPE("vx128mem", TYPE_MVSIBX) | |||
980 | TYPE("vx256mem", TYPE_MVSIBX) | |||
981 | TYPE("vy128mem", TYPE_MVSIBY) | |||
982 | TYPE("vy256mem", TYPE_MVSIBY) | |||
983 | TYPE("vx64xmem", TYPE_MVSIBX) | |||
984 | TYPE("vx128xmem", TYPE_MVSIBX) | |||
985 | TYPE("vx256xmem", TYPE_MVSIBX) | |||
986 | TYPE("vy128xmem", TYPE_MVSIBY) | |||
987 | TYPE("vy256xmem", TYPE_MVSIBY) | |||
988 | TYPE("vy512xmem", TYPE_MVSIBY) | |||
989 | TYPE("vz256mem", TYPE_MVSIBZ) | |||
990 | TYPE("vz512mem", TYPE_MVSIBZ) | |||
991 | TYPE("BNDR", TYPE_BNDR) | |||
992 | TYPE("TILE", TYPE_TMM) | |||
993 | errs() << "Unhandled type string " << s << "\n"; | |||
994 | llvm_unreachable("Unhandled type string")__builtin_unreachable(); | |||
995 | } | |||
996 | #undef TYPE | |||
997 | ||||
998 | #define ENCODING(str, encoding) if (s == str) return encoding; | |||
999 | OperandEncoding | |||
1000 | RecognizableInstr::immediateEncodingFromString(const std::string &s, | |||
1001 | uint8_t OpSize) { | |||
1002 | if(OpSize != X86Local::OpSize16) { | |||
1003 | // For instructions without an OpSize prefix, a declared 16-bit register or | |||
1004 | // immediate encoding is special. | |||
1005 | ENCODING("i16imm", ENCODING_IW) | |||
1006 | } | |||
1007 | ENCODING("i32i8imm", ENCODING_IB) | |||
1008 | ENCODING("AVX512RC", ENCODING_IRC) | |||
1009 | ENCODING("i16imm", ENCODING_Iv) | |||
1010 | ENCODING("i16i8imm", ENCODING_IB) | |||
1011 | ENCODING("i32imm", ENCODING_Iv) | |||
1012 | ENCODING("i64i32imm", ENCODING_ID) | |||
1013 | ENCODING("i64i8imm", ENCODING_IB) | |||
1014 | ENCODING("i8imm", ENCODING_IB) | |||
1015 | ENCODING("u4imm", ENCODING_IB) | |||
1016 | ENCODING("u8imm", ENCODING_IB) | |||
1017 | ENCODING("i16u8imm", ENCODING_IB) | |||
1018 | ENCODING("i32u8imm", ENCODING_IB) | |||
1019 | ENCODING("i64u8imm", ENCODING_IB) | |||
1020 | // This is not a typo. Instructions like BLENDVPD put | |||
1021 | // register IDs in 8-bit immediates nowadays. | |||
1022 | ENCODING("FR32", ENCODING_IB) | |||
1023 | ENCODING("FR64", ENCODING_IB) | |||
1024 | ENCODING("FR128", ENCODING_IB) | |||
1025 | ENCODING("VR128", ENCODING_IB) | |||
1026 | ENCODING("VR256", ENCODING_IB) | |||
1027 | ENCODING("FR16X", ENCODING_IB) | |||
1028 | ENCODING("FR32X", ENCODING_IB) | |||
1029 | ENCODING("FR64X", ENCODING_IB) | |||
1030 | ENCODING("VR128X", ENCODING_IB) | |||
1031 | ENCODING("VR256X", ENCODING_IB) | |||
1032 | ENCODING("VR512", ENCODING_IB) | |||
1033 | ENCODING("TILE", ENCODING_IB) | |||
1034 | errs() << "Unhandled immediate encoding " << s << "\n"; | |||
1035 | llvm_unreachable("Unhandled immediate encoding")__builtin_unreachable(); | |||
1036 | } | |||
1037 | ||||
1038 | OperandEncoding | |||
1039 | RecognizableInstr::rmRegisterEncodingFromString(const std::string &s, | |||
1040 | uint8_t OpSize) { | |||
1041 | ENCODING("RST", ENCODING_FP) | |||
1042 | ENCODING("RSTi", ENCODING_FP) | |||
1043 | ENCODING("GR16", ENCODING_RM) | |||
1044 | ENCODING("GR16orGR32orGR64",ENCODING_RM) | |||
1045 | ENCODING("GR32", ENCODING_RM) | |||
1046 | ENCODING("GR32orGR64", ENCODING_RM) | |||
1047 | ENCODING("GR64", ENCODING_RM) | |||
1048 | ENCODING("GR8", ENCODING_RM) | |||
1049 | ENCODING("VR128", ENCODING_RM) | |||
1050 | ENCODING("VR128X", ENCODING_RM) | |||
1051 | ENCODING("FR128", ENCODING_RM) | |||
1052 | ENCODING("FR64", ENCODING_RM) | |||
1053 | ENCODING("FR32", ENCODING_RM) | |||
1054 | ENCODING("FR64X", ENCODING_RM) | |||
1055 | ENCODING("FR32X", ENCODING_RM) | |||
1056 | ENCODING("FR16X", ENCODING_RM) | |||
1057 | ENCODING("VR64", ENCODING_RM) | |||
1058 | ENCODING("VR256", ENCODING_RM) | |||
1059 | ENCODING("VR256X", ENCODING_RM) | |||
1060 | ENCODING("VR512", ENCODING_RM) | |||
1061 | ENCODING("VK1", ENCODING_RM) | |||
1062 | ENCODING("VK2", ENCODING_RM) | |||
1063 | ENCODING("VK4", ENCODING_RM) | |||
1064 | ENCODING("VK8", ENCODING_RM) | |||
1065 | ENCODING("VK16", ENCODING_RM) | |||
1066 | ENCODING("VK32", ENCODING_RM) | |||
1067 | ENCODING("VK64", ENCODING_RM) | |||
1068 | ENCODING("VK1PAIR", ENCODING_RM) | |||
1069 | ENCODING("VK2PAIR", ENCODING_RM) | |||
1070 | ENCODING("VK4PAIR", ENCODING_RM) | |||
1071 | ENCODING("VK8PAIR", ENCODING_RM) | |||
1072 | ENCODING("VK16PAIR", ENCODING_RM) | |||
1073 | ENCODING("BNDR", ENCODING_RM) | |||
1074 | ENCODING("TILE", ENCODING_RM) | |||
1075 | errs() << "Unhandled R/M register encoding " << s << "\n"; | |||
1076 | llvm_unreachable("Unhandled R/M register encoding")__builtin_unreachable(); | |||
1077 | } | |||
1078 | ||||
1079 | OperandEncoding | |||
1080 | RecognizableInstr::roRegisterEncodingFromString(const std::string &s, | |||
1081 | uint8_t OpSize) { | |||
1082 | ENCODING("GR16", ENCODING_REG) | |||
1083 | ENCODING("GR16orGR32orGR64",ENCODING_REG) | |||
1084 | ENCODING("GR32", ENCODING_REG) | |||
1085 | ENCODING("GR32orGR64", ENCODING_REG) | |||
1086 | ENCODING("GR64", ENCODING_REG) | |||
1087 | ENCODING("GR8", ENCODING_REG) | |||
1088 | ENCODING("VR128", ENCODING_REG) | |||
1089 | ENCODING("FR128", ENCODING_REG) | |||
1090 | ENCODING("FR64", ENCODING_REG) | |||
1091 | ENCODING("FR32", ENCODING_REG) | |||
1092 | ENCODING("VR64", ENCODING_REG) | |||
1093 | ENCODING("SEGMENT_REG", ENCODING_REG) | |||
1094 | ENCODING("DEBUG_REG", ENCODING_REG) | |||
1095 | ENCODING("CONTROL_REG", ENCODING_REG) | |||
1096 | ENCODING("VR256", ENCODING_REG) | |||
1097 | ENCODING("VR256X", ENCODING_REG) | |||
1098 | ENCODING("VR128X", ENCODING_REG) | |||
1099 | ENCODING("FR64X", ENCODING_REG) | |||
1100 | ENCODING("FR32X", ENCODING_REG) | |||
1101 | ENCODING("FR16X", ENCODING_REG) | |||
1102 | ENCODING("VR512", ENCODING_REG) | |||
1103 | ENCODING("VK1", ENCODING_REG) | |||
1104 | ENCODING("VK2", ENCODING_REG) | |||
1105 | ENCODING("VK4", ENCODING_REG) | |||
1106 | ENCODING("VK8", ENCODING_REG) | |||
1107 | ENCODING("VK16", ENCODING_REG) | |||
1108 | ENCODING("VK32", ENCODING_REG) | |||
1109 | ENCODING("VK64", ENCODING_REG) | |||
1110 | ENCODING("VK1Pair", ENCODING_REG) | |||
1111 | ENCODING("VK2Pair", ENCODING_REG) | |||
1112 | ENCODING("VK4Pair", ENCODING_REG) | |||
1113 | ENCODING("VK8Pair", ENCODING_REG) | |||
1114 | ENCODING("VK16Pair", ENCODING_REG) | |||
1115 | ENCODING("VK1WM", ENCODING_REG) | |||
1116 | ENCODING("VK2WM", ENCODING_REG) | |||
1117 | ENCODING("VK4WM", ENCODING_REG) | |||
1118 | ENCODING("VK8WM", ENCODING_REG) | |||
1119 | ENCODING("VK16WM", ENCODING_REG) | |||
1120 | ENCODING("VK32WM", ENCODING_REG) | |||
1121 | ENCODING("VK64WM", ENCODING_REG) | |||
1122 | ENCODING("BNDR", ENCODING_REG) | |||
1123 | ENCODING("TILE", ENCODING_REG) | |||
1124 | errs() << "Unhandled reg/opcode register encoding " << s << "\n"; | |||
1125 | llvm_unreachable("Unhandled reg/opcode register encoding")__builtin_unreachable(); | |||
1126 | } | |||
1127 | ||||
1128 | OperandEncoding | |||
1129 | RecognizableInstr::vvvvRegisterEncodingFromString(const std::string &s, | |||
1130 | uint8_t OpSize) { | |||
1131 | ENCODING("GR32", ENCODING_VVVV) | |||
1132 | ENCODING("GR64", ENCODING_VVVV) | |||
1133 | ENCODING("FR32", ENCODING_VVVV) | |||
1134 | ENCODING("FR128", ENCODING_VVVV) | |||
1135 | ENCODING("FR64", ENCODING_VVVV) | |||
1136 | ENCODING("VR128", ENCODING_VVVV) | |||
1137 | ENCODING("VR256", ENCODING_VVVV) | |||
1138 | ENCODING("FR16X", ENCODING_VVVV) | |||
1139 | ENCODING("FR32X", ENCODING_VVVV) | |||
1140 | ENCODING("FR64X", ENCODING_VVVV) | |||
1141 | ENCODING("VR128X", ENCODING_VVVV) | |||
1142 | ENCODING("VR256X", ENCODING_VVVV) | |||
1143 | ENCODING("VR512", ENCODING_VVVV) | |||
1144 | ENCODING("VK1", ENCODING_VVVV) | |||
1145 | ENCODING("VK2", ENCODING_VVVV) | |||
1146 | ENCODING("VK4", ENCODING_VVVV) | |||
1147 | ENCODING("VK8", ENCODING_VVVV) | |||
1148 | ENCODING("VK16", ENCODING_VVVV) | |||
1149 | ENCODING("VK32", ENCODING_VVVV) | |||
1150 | ENCODING("VK64", ENCODING_VVVV) | |||
1151 | ENCODING("VK1PAIR", ENCODING_VVVV) | |||
1152 | ENCODING("VK2PAIR", ENCODING_VVVV) | |||
1153 | ENCODING("VK4PAIR", ENCODING_VVVV) | |||
1154 | ENCODING("VK8PAIR", ENCODING_VVVV) | |||
1155 | ENCODING("VK16PAIR", ENCODING_VVVV) | |||
1156 | ENCODING("TILE", ENCODING_VVVV) | |||
1157 | errs() << "Unhandled VEX.vvvv register encoding " << s << "\n"; | |||
1158 | llvm_unreachable("Unhandled VEX.vvvv register encoding")__builtin_unreachable(); | |||
1159 | } | |||
1160 | ||||
1161 | OperandEncoding | |||
1162 | RecognizableInstr::writemaskRegisterEncodingFromString(const std::string &s, | |||
1163 | uint8_t OpSize) { | |||
1164 | ENCODING("VK1WM", ENCODING_WRITEMASK) | |||
1165 | ENCODING("VK2WM", ENCODING_WRITEMASK) | |||
1166 | ENCODING("VK4WM", ENCODING_WRITEMASK) | |||
1167 | ENCODING("VK8WM", ENCODING_WRITEMASK) | |||
1168 | ENCODING("VK16WM", ENCODING_WRITEMASK) | |||
1169 | ENCODING("VK32WM", ENCODING_WRITEMASK) | |||
1170 | ENCODING("VK64WM", ENCODING_WRITEMASK) | |||
1171 | errs() << "Unhandled mask register encoding " << s << "\n"; | |||
1172 | llvm_unreachable("Unhandled mask register encoding")__builtin_unreachable(); | |||
1173 | } | |||
1174 | ||||
1175 | OperandEncoding | |||
1176 | RecognizableInstr::memoryEncodingFromString(const std::string &s, | |||
1177 | uint8_t OpSize) { | |||
1178 | ENCODING("i16mem", ENCODING_RM) | |||
1179 | ENCODING("i32mem", ENCODING_RM) | |||
1180 | ENCODING("i64mem", ENCODING_RM) | |||
1181 | ENCODING("i8mem", ENCODING_RM) | |||
1182 | ENCODING("shmem", ENCODING_RM) | |||
1183 | ENCODING("ssmem", ENCODING_RM) | |||
1184 | ENCODING("sdmem", ENCODING_RM) | |||
1185 | ENCODING("f128mem", ENCODING_RM) | |||
1186 | ENCODING("f256mem", ENCODING_RM) | |||
1187 | ENCODING("f512mem", ENCODING_RM) | |||
1188 | ENCODING("f64mem", ENCODING_RM) | |||
1189 | ENCODING("f32mem", ENCODING_RM) | |||
1190 | ENCODING("f16mem", ENCODING_RM) | |||
1191 | ENCODING("i128mem", ENCODING_RM) | |||
1192 | ENCODING("i256mem", ENCODING_RM) | |||
1193 | ENCODING("i512mem", ENCODING_RM) | |||
1194 | ENCODING("f80mem", ENCODING_RM) | |||
1195 | ENCODING("lea64_32mem", ENCODING_RM) | |||
1196 | ENCODING("lea64mem", ENCODING_RM) | |||
1197 | ENCODING("anymem", ENCODING_RM) | |||
1198 | ENCODING("opaquemem", ENCODING_RM) | |||
1199 | ENCODING("sibmem", ENCODING_SIB) | |||
1200 | ENCODING("vx64mem", ENCODING_VSIB) | |||
1201 | ENCODING("vx128mem", ENCODING_VSIB) | |||
1202 | ENCODING("vx256mem", ENCODING_VSIB) | |||
1203 | ENCODING("vy128mem", ENCODING_VSIB) | |||
1204 | ENCODING("vy256mem", ENCODING_VSIB) | |||
1205 | ENCODING("vx64xmem", ENCODING_VSIB) | |||
1206 | ENCODING("vx128xmem", ENCODING_VSIB) | |||
1207 | ENCODING("vx256xmem", ENCODING_VSIB) | |||
1208 | ENCODING("vy128xmem", ENCODING_VSIB) | |||
1209 | ENCODING("vy256xmem", ENCODING_VSIB) | |||
1210 | ENCODING("vy512xmem", ENCODING_VSIB) | |||
1211 | ENCODING("vz256mem", ENCODING_VSIB) | |||
1212 | ENCODING("vz512mem", ENCODING_VSIB) | |||
1213 | errs() << "Unhandled memory encoding " << s << "\n"; | |||
1214 | llvm_unreachable("Unhandled memory encoding")__builtin_unreachable(); | |||
1215 | } | |||
1216 | ||||
1217 | OperandEncoding | |||
1218 | RecognizableInstr::relocationEncodingFromString(const std::string &s, | |||
1219 | uint8_t OpSize) { | |||
1220 | if(OpSize != X86Local::OpSize16) { | |||
1221 | // For instructions without an OpSize prefix, a declared 16-bit register or | |||
1222 | // immediate encoding is special. | |||
1223 | ENCODING("i16imm", ENCODING_IW) | |||
1224 | } | |||
1225 | ENCODING("i16imm", ENCODING_Iv) | |||
1226 | ENCODING("i16i8imm", ENCODING_IB) | |||
1227 | ENCODING("i32imm", ENCODING_Iv) | |||
1228 | ENCODING("i32i8imm", ENCODING_IB) | |||
1229 | ENCODING("i64i32imm", ENCODING_ID) | |||
1230 | ENCODING("i64i8imm", ENCODING_IB) | |||
1231 | ENCODING("i8imm", ENCODING_IB) | |||
1232 | ENCODING("u8imm", ENCODING_IB) | |||
1233 | ENCODING("i16u8imm", ENCODING_IB) | |||
1234 | ENCODING("i32u8imm", ENCODING_IB) | |||
1235 | ENCODING("i64u8imm", ENCODING_IB) | |||
1236 | ENCODING("i64i32imm_brtarget", ENCODING_ID) | |||
1237 | ENCODING("i16imm_brtarget", ENCODING_IW) | |||
1238 | ENCODING("i32imm_brtarget", ENCODING_ID) | |||
1239 | ENCODING("brtarget32", ENCODING_ID) | |||
1240 | ENCODING("brtarget16", ENCODING_IW) | |||
1241 | ENCODING("brtarget8", ENCODING_IB) | |||
1242 | ENCODING("i64imm", ENCODING_IO) | |||
1243 | ENCODING("offset16_8", ENCODING_Ia) | |||
1244 | ENCODING("offset16_16", ENCODING_Ia) | |||
1245 | ENCODING("offset16_32", ENCODING_Ia) | |||
1246 | ENCODING("offset32_8", ENCODING_Ia) | |||
1247 | ENCODING("offset32_16", ENCODING_Ia) | |||
1248 | ENCODING("offset32_32", ENCODING_Ia) | |||
1249 | ENCODING("offset32_64", ENCODING_Ia) | |||
1250 | ENCODING("offset64_8", ENCODING_Ia) | |||
1251 | ENCODING("offset64_16", ENCODING_Ia) | |||
1252 | ENCODING("offset64_32", ENCODING_Ia) | |||
1253 | ENCODING("offset64_64", ENCODING_Ia) | |||
1254 | ENCODING("srcidx8", ENCODING_SI) | |||
1255 | ENCODING("srcidx16", ENCODING_SI) | |||
1256 | ENCODING("srcidx32", ENCODING_SI) | |||
1257 | ENCODING("srcidx64", ENCODING_SI) | |||
1258 | ENCODING("dstidx8", ENCODING_DI) | |||
1259 | ENCODING("dstidx16", ENCODING_DI) | |||
1260 | ENCODING("dstidx32", ENCODING_DI) | |||
1261 | ENCODING("dstidx64", ENCODING_DI) | |||
1262 | errs() << "Unhandled relocation encoding " << s << "\n"; | |||
1263 | llvm_unreachable("Unhandled relocation encoding")__builtin_unreachable(); | |||
1264 | } | |||
1265 | ||||
1266 | OperandEncoding | |||
1267 | RecognizableInstr::opcodeModifierEncodingFromString(const std::string &s, | |||
1268 | uint8_t OpSize) { | |||
1269 | ENCODING("GR32", ENCODING_Rv) | |||
1270 | ENCODING("GR64", ENCODING_RO) | |||
1271 | ENCODING("GR16", ENCODING_Rv) | |||
1272 | ENCODING("GR8", ENCODING_RB) | |||
1273 | ENCODING("ccode", ENCODING_CC) | |||
1274 | errs() << "Unhandled opcode modifier encoding " << s << "\n"; | |||
1275 | llvm_unreachable("Unhandled opcode modifier encoding")__builtin_unreachable(); | |||
1276 | } | |||
1277 | #undef ENCODING |