summaryrefslogtreecommitdiff
path: root/erts/emulator/asmjit/x86/x86instdb_p.h
blob: 4bfa0b9183dda0fbaa9c876279736d5978c2de3d (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
// This file is part of AsmJit project <https://asmjit.com>
//
// See asmjit.h or LICENSE.md for license and copyright information
// SPDX-License-Identifier: Zlib

#ifndef ASMJIT_X86_X86INSTDB_P_H_INCLUDED
#define ASMJIT_X86_X86INSTDB_P_H_INCLUDED

#include "../x86/x86instdb.h"

ASMJIT_BEGIN_SUB_NAMESPACE(x86)

//! \cond INTERNAL
//! \addtogroup asmjit_x86
//! \{

namespace InstDB {

//! Instruction encoding (X86).
//!
//! This is a specific identifier that is used by AsmJit to describe the way each instruction is encoded. Some
//! encodings are special only for a single instruction as X86 instruction set contains a lot of legacy encodings,
//! and some encodings describe a group of instructions that share some commons, like MMX, SSE, AVX, AVX512
//! instructions, etc...
enum EncodingId : uint32_t {
  kEncodingNone = 0,                     //!< Never used.
  kEncodingX86Op,                        //!< X86 [OP].
  kEncodingX86Op_Mod11RM,                //!< X86 [OP] (opcode with ModRM byte where MOD must be 11b).
  kEncodingX86Op_Mod11RM_I8,             //!< X86 [OP] (opcode with ModRM byte + 8-bit immediate).
  kEncodingX86Op_xAddr,                  //!< X86 [OP] (implicit address in the first register operand).
  kEncodingX86Op_xAX,                    //!< X86 [OP] (implicit or explicit '?AX' form).
  kEncodingX86Op_xDX_xAX,                //!< X86 [OP] (implicit or explicit '?DX, ?AX' form).
  kEncodingX86Op_MemZAX,                 //!< X86 [OP] (implicit or explicit '[EAX|RAX]' form).
  kEncodingX86I_xAX,                     //!< X86 [I] (implicit or explicit '?AX' form).
  kEncodingX86M,                         //!< X86 [M] (handles 2|4|8-bytes size).
  kEncodingX86M_NoMemSize,               //!< X86 [M] (handles 2|4|8-bytes size, but doesn't consider memory size).
  kEncodingX86M_NoSize,                  //!< X86 [M] (doesn't handle any size).
  kEncodingX86M_GPB,                     //!< X86 [M] (handles single-byte size).
  kEncodingX86M_GPB_MulDiv,              //!< X86 [M] (like GPB, handles implicit|explicit MUL|DIV|IDIV).
  kEncodingX86M_Only,                    //!< X86 [M] (restricted to memory operand of any size).
  kEncodingX86M_Only_EDX_EAX,            //!< X86 [M] (memory operand only, followed by implicit <edx> and <eax>).
  kEncodingX86M_Nop,                     //!< X86 [M] (special case of NOP instruction).
  kEncodingX86R_Native,                  //!< X86 [R] (register must be either 32-bit or 64-bit depending on arch).
  kEncodingX86R_FromM,                   //!< X86 [R] - which specifies memory address.
  kEncodingX86R32_EDX_EAX,               //!< X86 [R32] followed by implicit EDX and EAX.
  kEncodingX86Rm,                        //!< X86 [RM] (doesn't handle single-byte size).
  kEncodingX86Rm_Raw66H,                 //!< X86 [RM] (used by LZCNT, POPCNT, and TZCNT).
  kEncodingX86Rm_NoSize,                 //!< X86 [RM] (doesn't add REX.W prefix if 64-bit reg is used).
  kEncodingX86Mr,                        //!< X86 [MR] (doesn't handle single-byte size).
  kEncodingX86Mr_NoSize,                 //!< X86 [MR] (doesn't handle any size).
  kEncodingX86Arith,                     //!< X86 adc, add, and, cmp, or, sbb, sub, xor.
  kEncodingX86Bswap,                     //!< X86 bswap.
  kEncodingX86Bt,                        //!< X86 bt, btc, btr, bts.
  kEncodingX86Call,                      //!< X86 call.
  kEncodingX86Cmpxchg,                   //!< X86 [MR] cmpxchg.
  kEncodingX86Cmpxchg8b_16b,             //!< X86 [MR] cmpxchg8b, cmpxchg16b.
  kEncodingX86Crc,                       //!< X86 crc32.
  kEncodingX86Enter,                     //!< X86 enter.
  kEncodingX86Imul,                      //!< X86 imul.
  kEncodingX86In,                        //!< X86 in.
  kEncodingX86Ins,                       //!< X86 ins[b|q|d].
  kEncodingX86IncDec,                    //!< X86 inc, dec.
  kEncodingX86Int,                       //!< X86 int (interrupt).
  kEncodingX86Jcc,                       //!< X86 jcc.
  kEncodingX86JecxzLoop,                 //!< X86 jcxz, jecxz, jrcxz, loop, loope, loopne.
  kEncodingX86Jmp,                       //!< X86 jmp.
  kEncodingX86JmpRel,                    //!< X86 xbegin.
  kEncodingX86LcallLjmp,                 //!< X86 lcall/ljmp.
  kEncodingX86Lea,                       //!< X86 lea.
  kEncodingX86Mov,                       //!< X86 mov (all possible cases).
  kEncodingX86Movabs,                    //!< X86 movabs.
  kEncodingX86MovsxMovzx,                //!< X86 movsx, movzx.
  kEncodingX86MovntiMovdiri,             //!< X86 movnti/movdiri.
  kEncodingX86EnqcmdMovdir64b,           //!< X86 enqcmd/enqcmds/movdir64b.
  kEncodingX86Out,                       //!< X86 out.
  kEncodingX86Outs,                      //!< X86 out[b|w|d].
  kEncodingX86Push,                      //!< X86 push.
  kEncodingX86Pop,                       //!< X86 pop.
  kEncodingX86Ret,                       //!< X86 ret.
  kEncodingX86Rot,                       //!< X86 rcl, rcr, rol, ror, sal, sar, shl, shr.
  kEncodingX86Set,                       //!< X86 setcc.
  kEncodingX86ShldShrd,                  //!< X86 shld, shrd.
  kEncodingX86StrRm,                     //!< X86 lods.
  kEncodingX86StrMr,                     //!< X86 scas, stos.
  kEncodingX86StrMm,                     //!< X86 cmps, movs.
  kEncodingX86Test,                      //!< X86 test.
  kEncodingX86Xadd,                      //!< X86 xadd.
  kEncodingX86Xchg,                      //!< X86 xchg.
  kEncodingX86Fence,                     //!< X86 lfence, mfence, sfence.
  kEncodingX86Bndmov,                    //!< X86 [RM|MR] (used by BNDMOV).
  kEncodingFpuOp,                        //!< FPU [OP].
  kEncodingFpuArith,                     //!< FPU fadd, fdiv, fdivr, fmul, fsub, fsubr.
  kEncodingFpuCom,                       //!< FPU fcom, fcomp.
  kEncodingFpuFldFst,                    //!< FPU fld, fst, fstp.
  kEncodingFpuM,                         //!< FPU fiadd, ficom, ficomp, fidiv, fidivr, fild, fimul, fist, fistp, fisttp, fisub, fisubr.
  kEncodingFpuR,                         //!< FPU fcmov, fcomi, fcomip, ffree, fucom, fucomi, fucomip, fucomp, fxch.
  kEncodingFpuRDef,                      //!< FPU faddp, fdivp, fdivrp, fmulp, fsubp, fsubrp.
  kEncodingFpuStsw,                      //!< FPU fnstsw, Fstsw.
  kEncodingExtRm,                        //!< EXT [RM].
  kEncodingExtRm_XMM0,                   //!< EXT [RM<XMM0>].
  kEncodingExtRm_ZDI,                    //!< EXT [RM<ZDI>].
  kEncodingExtRm_P,                      //!< EXT [RM] (propagates 66H if the instruction uses XMM register).
  kEncodingExtRm_Wx,                     //!< EXT [RM] (propagates REX.W if GPQ is used or the second operand is GPQ/QWORD_PTR).
  kEncodingExtRm_Wx_GpqOnly,             //!< EXT [RM] (propagates REX.W if the first operand is GPQ register).
  kEncodingExtRmRi,                      //!< EXT [RM|RI].
  kEncodingExtRmRi_P,                    //!< EXT [RM|RI] (propagates 66H if the instruction uses XMM register).
  kEncodingExtRmi,                       //!< EXT [RMI].
  kEncodingExtRmi_P,                     //!< EXT [RMI] (propagates 66H if the instruction uses XMM register).
  kEncodingExtPextrw,                    //!< EXT pextrw.
  kEncodingExtExtract,                   //!< EXT pextrb, pextrd, pextrq, extractps.
  kEncodingExtMov,                       //!< EXT mov?? - #1:[MM|XMM, MM|XMM|Mem] #2:[MM|XMM|Mem, MM|XMM].
  kEncodingExtMovbe,                     //!< EXT movbe.
  kEncodingExtMovd,                      //!< EXT movd.
  kEncodingExtMovq,                      //!< EXT movq.
  kEncodingExtExtrq,                     //!< EXT extrq (SSE4A).
  kEncodingExtInsertq,                   //!< EXT insrq (SSE4A).
  kEncodingExt3dNow,                     //!< EXT [RMI] (3DNOW specific).
  kEncodingVexOp,                        //!< VEX [OP].
  kEncodingVexOpMod,                     //!< VEX [OP] with MODR/M.
  kEncodingVexKmov,                      //!< VEX [RM|MR] (used by kmov[b|w|d|q]).
  kEncodingVexR_Wx,                      //!< VEX|EVEX [R] (propagatex VEX.W if GPQ used).
  kEncodingVexM,                         //!< VEX|EVEX [M].
  kEncodingVexM_VM,                      //!< VEX|EVEX [M] (propagates VEX|EVEX.L, VSIB support).
  kEncodingVexMr_Lx,                     //!< VEX|EVEX [MR] (propagates VEX|EVEX.L if YMM used).
  kEncodingVexMr_VM,                     //!< VEX|EVEX [MR] (VSIB support).
  kEncodingVexMri,                       //!< VEX|EVEX [MRI].
  kEncodingVexMri_Lx,                    //!< VEX|EVEX [MRI] (propagates VEX|EVEX.L if YMM used).
  kEncodingVexMri_Vpextrw,               //!< VEX|EVEX [MRI] (special case required by VPEXTRW instruction).
  kEncodingVexRm,                        //!< VEX|EVEX [RM].
  kEncodingVexRm_ZDI,                    //!< VEX|EVEX [RM<ZDI>].
  kEncodingVexRm_Wx,                     //!< VEX|EVEX [RM] (propagates VEX|EVEX.W if GPQ used).
  kEncodingVexRm_Lx,                     //!< VEX|EVEX [RM] (propagates VEX|EVEX.L if YMM used).
  kEncodingVexRm_Lx_Narrow,              //!< VEX|EVEX [RM] (the destination vector size is narrowed).
  kEncodingVexRm_Lx_Bcst,                //!< VEX|EVEX [RM] (can handle broadcast r32/r64).
  kEncodingVexRm_VM,                     //!< VEX|EVEX [RM] (propagates VEX|EVEX.L, VSIB support).
  kEncodingVexRm_T1_4X,                  //!<     EVEX [RM] (used by NN instructions that use RM-T1_4X encoding).
  kEncodingVexRmi,                       //!< VEX|EVEX [RMI].
  kEncodingVexRmi_Wx,                    //!< VEX|EVEX [RMI] (propagates VEX|EVEX.W if GPQ used).
  kEncodingVexRmi_Lx,                    //!< VEX|EVEX [RMI] (propagates VEX|EVEX.L if YMM used).
  kEncodingVexRvm,                       //!< VEX|EVEX [RVM].
  kEncodingVexRvm_Wx,                    //!< VEX|EVEX [RVM] (propagates VEX|EVEX.W if GPQ used).
  kEncodingVexRvm_ZDX_Wx,                //!< VEX|EVEX [RVM<ZDX>] (propagates VEX|EVEX.W if GPQ used).
  kEncodingVexRvm_Lx,                    //!< VEX|EVEX [RVM] (propagates VEX|EVEX.L if YMM used).
  kEncodingVexRvm_Lx_KEvex,              //!< VEX|EVEX [RVM] (forces EVEX prefix if K register is used on destination).
  kEncodingVexRvm_Lx_2xK,                //!< VEX|EVEX [RVM] (vp2intersectd/vp2intersectq).
  kEncodingVexRvmr,                      //!< VEX|EVEX [RVMR].
  kEncodingVexRvmr_Lx,                   //!< VEX|EVEX [RVMR] (propagates VEX|EVEX.L if YMM used).
  kEncodingVexRvmi,                      //!< VEX|EVEX [RVMI].
  kEncodingVexRvmi_KEvex,                //!< VEX|EVEX [RVMI] (forces EVEX prefix if K register is used on destination).
  kEncodingVexRvmi_Lx,                   //!< VEX|EVEX [RVMI] (propagates VEX|EVEX.L if YMM used).
  kEncodingVexRvmi_Lx_KEvex,             //!< VEX|EVEX [RVMI] (forces EVEX prefix if K register is used on destination).
  kEncodingVexRmv,                       //!< VEX|EVEX [RMV].
  kEncodingVexRmv_Wx,                    //!< VEX|EVEX [RMV] (propagates VEX|EVEX.W if GPQ used).
  kEncodingVexRmv_VM,                    //!< VEX|EVEX [RMV] (propagates VEX|EVEX.L, VSIB support).
  kEncodingVexRmvRm_VM,                  //!< VEX|EVEX [RMV|RM] (propagates VEX|EVEX.L, VSIB support).
  kEncodingVexRmvi,                      //!< VEX|EVEX [RMVI].
  kEncodingVexRmMr,                      //!< VEX|EVEX [RM|MR].
  kEncodingVexRmMr_Lx,                   //!< VEX|EVEX [RM|MR] (propagates VEX|EVEX.L if YMM used).
  kEncodingVexRvmRmv,                    //!< VEX|EVEX [RVM|RMV].
  kEncodingVexRvmRmi,                    //!< VEX|EVEX [RVM|RMI].
  kEncodingVexRvmRmi_Lx,                 //!< VEX|EVEX [RVM|RMI] (propagates VEX|EVEX.L if YMM used).
  kEncodingVexRvmRmvRmi,                 //!< VEX|EVEX [RVM|RMV|RMI].
  kEncodingVexRvmMr,                     //!< VEX|EVEX [RVM|MR].
  kEncodingVexRvmMvr,                    //!< VEX|EVEX [RVM|MVR].
  kEncodingVexRvmMvr_Lx,                 //!< VEX|EVEX [RVM|MVR] (propagates VEX|EVEX.L if YMM used).
  kEncodingVexRvmVmi,                    //!< VEX|EVEX [RVM|VMI].
  kEncodingVexRvmVmi_Lx,                 //!< VEX|EVEX [RVM|VMI] (propagates VEX|EVEX.L if YMM used).
  kEncodingVexRvmVmi_Lx_MEvex,           //!< VEX|EVEX [RVM|VMI] (propagates EVEX if the second operand is memory).
  kEncodingVexVm,                        //!< VEX|EVEX [VM].
  kEncodingVexVm_Wx,                     //!< VEX|EVEX [VM] (propagates VEX|EVEX.W if GPQ used).
  kEncodingVexVmi,                       //!< VEX|EVEX [VMI].
  kEncodingVexVmi_Lx,                    //!< VEX|EVEX [VMI] (propagates VEX|EVEX.L if YMM used).
  kEncodingVexVmi4_Wx,                   //!< VEX|EVEX [VMI] (propagates VEX|EVEX.W if GPQ used, DWORD Immediate).
  kEncodingVexVmi_Lx_MEvex,              //!< VEX|EVEX [VMI] (force EVEX prefix when the second operand is memory)
  kEncodingVexRvrmRvmr,                  //!< VEX|EVEX [RVRM|RVMR].
  kEncodingVexRvrmRvmr_Lx,               //!< VEX|EVEX [RVRM|RVMR] (propagates VEX|EVEX.L if YMM used).
  kEncodingVexRvrmiRvmri_Lx,             //!< VEX|EVEX [RVRMI|RVMRI] (propagates VEX|EVEX.L if YMM used).
  kEncodingVexMovdMovq,                  //!< VEX|EVEX vmovd, vmovq.
  kEncodingVexMovssMovsd,                //!< VEX|EVEX vmovss, vmovsd.
  kEncodingFma4,                         //!< FMA4 [R, R, R/M, R/M].
  kEncodingFma4_Lx,                      //!< FMA4 [R, R, R/M, R/M] (propagates AVX.L if YMM used).
  kEncodingAmxCfg,                       //!< AMX ldtilecfg/sttilecfg.
  kEncodingAmxR,                         //!< AMX [R] - tilezero.
  kEncodingAmxRm,                        //!< AMX tileloadd/tileloaddt1.
  kEncodingAmxMr,                        //!< AMX tilestored.
  kEncodingAmxRmv,                       //!< AMX instructions that use TMM registers.
  kEncodingCount                         //!< Count of instruction encodings.
};

//! Additional information table, provides CPU extensions required to execute an instruction and RW flags.
struct AdditionalInfo {
  //! Index to `_instFlagsTable`.
  uint8_t _instFlagsIndex;
  //! Index to `_rwFlagsTable`.
  uint8_t _rwFlagsIndex;
  //! Features vector.
  uint8_t _features[6];

  inline const uint8_t* featuresBegin() const noexcept { return _features; }
  inline const uint8_t* featuresEnd() const noexcept { return _features + ASMJIT_ARRAY_SIZE(_features); }
};

// ${NameLimits:Begin}
// ------------------- Automatically generated, do not edit -------------------
enum : uint32_t { kMaxNameSize = 17 };
// ----------------------------------------------------------------------------
// ${NameLimits:End}

struct InstNameIndex {
  uint16_t start;
  uint16_t end;
};

struct RWInfo {
  enum Category : uint8_t {
    kCategoryGeneric,
    kCategoryMov,
    kCategoryMovabs,
    kCategoryImul,
    kCategoryMovh64,
    kCategoryPunpcklxx,
    kCategoryVmaskmov,
    kCategoryVmovddup,
    kCategoryVmovmskpd,
    kCategoryVmovmskps,
    kCategoryVmov1_2,
    kCategoryVmov1_4,
    kCategoryVmov1_8,
    kCategoryVmov2_1,
    kCategoryVmov4_1,
    kCategoryVmov8_1
  };

  uint8_t category;
  uint8_t rmInfo;
  uint8_t opInfoIndex[6];
};

struct RWInfoOp {
  uint64_t rByteMask;
  uint64_t wByteMask;
  uint8_t physId;
  uint8_t consecutiveLeadCount;
  uint8_t reserved[2];
  OpRWFlags flags;
};

//! R/M information.
//!
//! This data is used to replace register operand by a memory operand reliably.
struct RWInfoRm {
  enum Category : uint8_t {
    kCategoryNone = 0,
    kCategoryFixed,
    kCategoryConsistent,
    kCategoryHalf,
    kCategoryQuarter,
    kCategoryEighth
  };

  enum Flags : uint8_t {
    kFlagAmbiguous = 0x01,
    //! Special semantics for PEXTRW - memory operand can only be used with SSE4.1 instruction and it's forbidden in MMX.
    kFlagPextrw = 0x02,
    //! Special semantics for MOVSS and MOVSD - doesn't zero extend the destination if the operation is a reg to reg move.
    kFlagMovssMovsd = 0x04,
    //! Special semantics for AVX shift instructions that do not provide reg/mem in AVX/AVX2 mode (AVX-512 is required).
    kFlagFeatureIfRMI = 0x08
  };

  uint8_t category;
  uint8_t rmOpsMask;
  uint8_t fixedSize;
  uint8_t flags;
  uint8_t rmFeature;
};

struct RWFlagsInfoTable {
  //! CPU/FPU flags read.
  uint32_t readFlags;
  //! CPU/FPU flags written or undefined.
  uint32_t writeFlags;
};

extern const uint8_t rwInfoIndexA[Inst::_kIdCount];
extern const uint8_t rwInfoIndexB[Inst::_kIdCount];
extern const RWInfo rwInfoA[];
extern const RWInfo rwInfoB[];
extern const RWInfoOp rwInfoOp[];
extern const RWInfoRm rwInfoRm[];
extern const RWFlagsInfoTable _rwFlagsInfoTable[];
extern const InstRWFlags _instFlagsTable[];

extern const uint32_t _mainOpcodeTable[];
extern const uint32_t _altOpcodeTable[];

#ifndef ASMJIT_NO_TEXT
extern const uint32_t _instNameIndexTable[];
extern const char _instNameStringTable[];
extern const InstNameIndex instNameIndex[26];
#endif // !ASMJIT_NO_TEXT

extern const AdditionalInfo _additionalInfoTable[];

} // {InstDB}

//! \}
//! \endcond

ASMJIT_END_SUB_NAMESPACE

#endif // ASMJIT_X86_X86INSTDB_P_H_INCLUDED