Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
torvalds
GitHub Repository: torvalds/linux
Path: blob/master/tools/arch/x86/include/asm/inat.h
29274 views
1
/* SPDX-License-Identifier: GPL-2.0-or-later */
2
#ifndef _ASM_X86_INAT_H
3
#define _ASM_X86_INAT_H
4
/*
5
* x86 instruction attributes
6
*
7
* Written by Masami Hiramatsu <[email protected]>
8
*/
9
#include "inat_types.h" /* __ignore_sync_check__ */
10
11
/*
12
* Internal bits. Don't use bitmasks directly, because these bits are
13
* unstable. You should use checking functions.
14
*/
15
16
#define INAT_OPCODE_TABLE_SIZE 256
17
#define INAT_GROUP_TABLE_SIZE 8
18
19
/* Legacy last prefixes */
20
#define INAT_PFX_OPNDSZ 1 /* 0x66 */ /* LPFX1 */
21
#define INAT_PFX_REPE 2 /* 0xF3 */ /* LPFX2 */
22
#define INAT_PFX_REPNE 3 /* 0xF2 */ /* LPFX3 */
23
/* Other Legacy prefixes */
24
#define INAT_PFX_LOCK 4 /* 0xF0 */
25
#define INAT_PFX_CS 5 /* 0x2E */
26
#define INAT_PFX_DS 6 /* 0x3E */
27
#define INAT_PFX_ES 7 /* 0x26 */
28
#define INAT_PFX_FS 8 /* 0x64 */
29
#define INAT_PFX_GS 9 /* 0x65 */
30
#define INAT_PFX_SS 10 /* 0x36 */
31
#define INAT_PFX_ADDRSZ 11 /* 0x67 */
32
/* x86-64 REX prefix */
33
#define INAT_PFX_REX 12 /* 0x4X */
34
/* AVX VEX prefixes */
35
#define INAT_PFX_VEX2 13 /* 2-bytes VEX prefix */
36
#define INAT_PFX_VEX3 14 /* 3-bytes VEX prefix */
37
#define INAT_PFX_EVEX 15 /* EVEX prefix */
38
/* x86-64 REX2 prefix */
39
#define INAT_PFX_REX2 16 /* 0xD5 */
40
/* AMD XOP prefix */
41
#define INAT_PFX_XOP 17 /* 0x8F */
42
43
#define INAT_LSTPFX_MAX 3
44
#define INAT_LGCPFX_MAX 11
45
46
/* Immediate size */
47
#define INAT_IMM_BYTE 1
48
#define INAT_IMM_WORD 2
49
#define INAT_IMM_DWORD 3
50
#define INAT_IMM_QWORD 4
51
#define INAT_IMM_PTR 5
52
#define INAT_IMM_VWORD32 6
53
#define INAT_IMM_VWORD 7
54
55
/* Legacy prefix */
56
#define INAT_PFX_OFFS 0
57
#define INAT_PFX_BITS 5
58
#define INAT_PFX_MAX ((1 << INAT_PFX_BITS) - 1)
59
#define INAT_PFX_MASK (INAT_PFX_MAX << INAT_PFX_OFFS)
60
/* Escape opcodes */
61
#define INAT_ESC_OFFS (INAT_PFX_OFFS + INAT_PFX_BITS)
62
#define INAT_ESC_BITS 2
63
#define INAT_ESC_MAX ((1 << INAT_ESC_BITS) - 1)
64
#define INAT_ESC_MASK (INAT_ESC_MAX << INAT_ESC_OFFS)
65
/* Group opcodes (1-16) */
66
#define INAT_GRP_OFFS (INAT_ESC_OFFS + INAT_ESC_BITS)
67
#define INAT_GRP_BITS 5
68
#define INAT_GRP_MAX ((1 << INAT_GRP_BITS) - 1)
69
#define INAT_GRP_MASK (INAT_GRP_MAX << INAT_GRP_OFFS)
70
/* Immediates */
71
#define INAT_IMM_OFFS (INAT_GRP_OFFS + INAT_GRP_BITS)
72
#define INAT_IMM_BITS 3
73
#define INAT_IMM_MASK (((1 << INAT_IMM_BITS) - 1) << INAT_IMM_OFFS)
74
/* Flags */
75
#define INAT_FLAG_OFFS (INAT_IMM_OFFS + INAT_IMM_BITS)
76
#define INAT_MODRM (1 << (INAT_FLAG_OFFS))
77
#define INAT_FORCE64 (1 << (INAT_FLAG_OFFS + 1))
78
#define INAT_SCNDIMM (1 << (INAT_FLAG_OFFS + 2))
79
#define INAT_MOFFSET (1 << (INAT_FLAG_OFFS + 3))
80
#define INAT_VARIANT (1 << (INAT_FLAG_OFFS + 4))
81
#define INAT_VEXOK (1 << (INAT_FLAG_OFFS + 5))
82
#define INAT_XOPOK INAT_VEXOK
83
#define INAT_VEXONLY (1 << (INAT_FLAG_OFFS + 6))
84
#define INAT_EVEXONLY (1 << (INAT_FLAG_OFFS + 7))
85
#define INAT_NO_REX2 (1 << (INAT_FLAG_OFFS + 8))
86
#define INAT_REX2_VARIANT (1 << (INAT_FLAG_OFFS + 9))
87
#define INAT_EVEX_SCALABLE (1 << (INAT_FLAG_OFFS + 10))
88
#define INAT_INV64 (1 << (INAT_FLAG_OFFS + 11))
89
/* Attribute making macros for attribute tables */
90
#define INAT_MAKE_PREFIX(pfx) (pfx << INAT_PFX_OFFS)
91
#define INAT_MAKE_ESCAPE(esc) (esc << INAT_ESC_OFFS)
92
#define INAT_MAKE_GROUP(grp) ((grp << INAT_GRP_OFFS) | INAT_MODRM)
93
#define INAT_MAKE_IMM(imm) (imm << INAT_IMM_OFFS)
94
95
/* Identifiers for segment registers */
96
#define INAT_SEG_REG_IGNORE 0
97
#define INAT_SEG_REG_DEFAULT 1
98
#define INAT_SEG_REG_CS 2
99
#define INAT_SEG_REG_SS 3
100
#define INAT_SEG_REG_DS 4
101
#define INAT_SEG_REG_ES 5
102
#define INAT_SEG_REG_FS 6
103
#define INAT_SEG_REG_GS 7
104
105
/* Attribute search APIs */
106
extern insn_attr_t inat_get_opcode_attribute(insn_byte_t opcode);
107
extern int inat_get_last_prefix_id(insn_byte_t last_pfx);
108
extern insn_attr_t inat_get_escape_attribute(insn_byte_t opcode,
109
int lpfx_id,
110
insn_attr_t esc_attr);
111
extern insn_attr_t inat_get_group_attribute(insn_byte_t modrm,
112
int lpfx_id,
113
insn_attr_t esc_attr);
114
extern insn_attr_t inat_get_avx_attribute(insn_byte_t opcode,
115
insn_byte_t vex_m,
116
insn_byte_t vex_pp);
117
extern insn_attr_t inat_get_xop_attribute(insn_byte_t opcode,
118
insn_byte_t map_select);
119
120
/* Attribute checking functions */
121
static inline int inat_is_legacy_prefix(insn_attr_t attr)
122
{
123
attr &= INAT_PFX_MASK;
124
return attr && attr <= INAT_LGCPFX_MAX;
125
}
126
127
static inline int inat_is_address_size_prefix(insn_attr_t attr)
128
{
129
return (attr & INAT_PFX_MASK) == INAT_PFX_ADDRSZ;
130
}
131
132
static inline int inat_is_operand_size_prefix(insn_attr_t attr)
133
{
134
return (attr & INAT_PFX_MASK) == INAT_PFX_OPNDSZ;
135
}
136
137
static inline int inat_is_rex_prefix(insn_attr_t attr)
138
{
139
return (attr & INAT_PFX_MASK) == INAT_PFX_REX;
140
}
141
142
static inline int inat_is_rex2_prefix(insn_attr_t attr)
143
{
144
return (attr & INAT_PFX_MASK) == INAT_PFX_REX2;
145
}
146
147
static inline int inat_last_prefix_id(insn_attr_t attr)
148
{
149
if ((attr & INAT_PFX_MASK) > INAT_LSTPFX_MAX)
150
return 0;
151
else
152
return attr & INAT_PFX_MASK;
153
}
154
155
static inline int inat_is_vex_prefix(insn_attr_t attr)
156
{
157
attr &= INAT_PFX_MASK;
158
return attr == INAT_PFX_VEX2 || attr == INAT_PFX_VEX3 ||
159
attr == INAT_PFX_EVEX;
160
}
161
162
static inline int inat_is_evex_prefix(insn_attr_t attr)
163
{
164
return (attr & INAT_PFX_MASK) == INAT_PFX_EVEX;
165
}
166
167
static inline int inat_is_vex3_prefix(insn_attr_t attr)
168
{
169
return (attr & INAT_PFX_MASK) == INAT_PFX_VEX3;
170
}
171
172
static inline int inat_is_xop_prefix(insn_attr_t attr)
173
{
174
return (attr & INAT_PFX_MASK) == INAT_PFX_XOP;
175
}
176
177
static inline int inat_is_escape(insn_attr_t attr)
178
{
179
return attr & INAT_ESC_MASK;
180
}
181
182
static inline int inat_escape_id(insn_attr_t attr)
183
{
184
return (attr & INAT_ESC_MASK) >> INAT_ESC_OFFS;
185
}
186
187
static inline int inat_is_group(insn_attr_t attr)
188
{
189
return attr & INAT_GRP_MASK;
190
}
191
192
static inline int inat_group_id(insn_attr_t attr)
193
{
194
return (attr & INAT_GRP_MASK) >> INAT_GRP_OFFS;
195
}
196
197
static inline int inat_group_common_attribute(insn_attr_t attr)
198
{
199
return attr & ~INAT_GRP_MASK;
200
}
201
202
static inline int inat_has_immediate(insn_attr_t attr)
203
{
204
return attr & INAT_IMM_MASK;
205
}
206
207
static inline int inat_immediate_size(insn_attr_t attr)
208
{
209
return (attr & INAT_IMM_MASK) >> INAT_IMM_OFFS;
210
}
211
212
static inline int inat_has_modrm(insn_attr_t attr)
213
{
214
return attr & INAT_MODRM;
215
}
216
217
static inline int inat_is_force64(insn_attr_t attr)
218
{
219
return attr & INAT_FORCE64;
220
}
221
222
static inline int inat_has_second_immediate(insn_attr_t attr)
223
{
224
return attr & INAT_SCNDIMM;
225
}
226
227
static inline int inat_has_moffset(insn_attr_t attr)
228
{
229
return attr & INAT_MOFFSET;
230
}
231
232
static inline int inat_has_variant(insn_attr_t attr)
233
{
234
return attr & INAT_VARIANT;
235
}
236
237
static inline int inat_accept_vex(insn_attr_t attr)
238
{
239
return attr & INAT_VEXOK;
240
}
241
242
static inline int inat_accept_xop(insn_attr_t attr)
243
{
244
return attr & INAT_XOPOK;
245
}
246
247
static inline int inat_must_vex(insn_attr_t attr)
248
{
249
return attr & (INAT_VEXONLY | INAT_EVEXONLY);
250
}
251
252
static inline int inat_must_evex(insn_attr_t attr)
253
{
254
return attr & INAT_EVEXONLY;
255
}
256
257
static inline int inat_evex_scalable(insn_attr_t attr)
258
{
259
return attr & INAT_EVEX_SCALABLE;
260
}
261
262
static inline int inat_is_invalid64(insn_attr_t attr)
263
{
264
return attr & INAT_INV64;
265
}
266
#endif
267
268