Enable Intel AVX512_VBMI2 instructions.
[deliverable/binutils-gdb.git] / opcodes / i386-gen.c
CommitLineData
2571583a 1/* Copyright (C) 2007-2017 Free Software Foundation, Inc.
40b8e679 2
9b201bb5 3 This file is part of the GNU opcodes library.
40b8e679 4
9b201bb5 5 This library is free software; you can redistribute it and/or modify
40b8e679 6 it under the terms of the GNU General Public License as published by
9b201bb5
NC
7 the Free Software Foundation; either version 3, or (at your option)
8 any later version.
40b8e679 9
9b201bb5
NC
10 It is distributed in the hope that it will be useful, but WITHOUT
11 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
12 or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
13 License for more details.
40b8e679
L
14
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
9b201bb5
NC
17 Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
18 MA 02110-1301, USA. */
40b8e679 19
40fb9820 20#include "sysdep.h"
40b8e679 21#include <stdio.h>
40b8e679
L
22#include <errno.h>
23#include "getopt.h"
24#include "libiberty.h"
c587b3f9 25#include "hashtab.h"
40b8e679
L
26#include "safe-ctype.h"
27
28#include "i386-opc.h"
29
30#include <libintl.h>
31#define _(String) gettext (String)
32
33static const char *program_name = NULL;
34static int debug = 0;
35
40fb9820
L
36typedef struct initializer
37{
38 const char *name;
39 const char *init;
40} initializer;
41
8acd5377 42static initializer cpu_flag_init[] =
40fb9820
L
43{
44 { "CPU_UNKNOWN_FLAGS",
7a9068fe 45 "~(CpuL1OM|CpuK1OM)" },
40fb9820
L
46 { "CPU_GENERIC32_FLAGS",
47 "Cpu186|Cpu286|Cpu386" },
29c048b6 48 { "CPU_GENERIC64_FLAGS",
1848e567 49 "CPU_PENTIUMPRO_FLAGS|CpuClflush|CpuSYSCALL|CPU_MMX_FLAGS|CPU_SSE2_FLAGS|CpuLM" },
40fb9820
L
50 { "CPU_NONE_FLAGS",
51 "0" },
52 { "CPU_I186_FLAGS",
53 "Cpu186" },
54 { "CPU_I286_FLAGS",
1848e567 55 "CPU_I186_FLAGS|Cpu286" },
40fb9820 56 { "CPU_I386_FLAGS",
1848e567 57 "CPU_I286_FLAGS|Cpu386" },
40fb9820 58 { "CPU_I486_FLAGS",
1848e567 59 "CPU_I386_FLAGS|Cpu486" },
40fb9820 60 { "CPU_I586_FLAGS",
1848e567 61 "CPU_I486_FLAGS|CPU_387_FLAGS|Cpu586" },
40fb9820 62 { "CPU_I686_FLAGS",
1848e567 63 "CPU_I586_FLAGS|Cpu686|Cpu687" },
22109423 64 { "CPU_PENTIUMPRO_FLAGS",
1848e567 65 "CPU_I686_FLAGS|CpuNop" },
40fb9820 66 { "CPU_P2_FLAGS",
1848e567 67 "CPU_PENTIUMPRO_FLAGS|CPU_MMX_FLAGS" },
40fb9820 68 { "CPU_P3_FLAGS",
1848e567 69 "CPU_P2_FLAGS|CPU_SSE_FLAGS" },
40fb9820 70 { "CPU_P4_FLAGS",
1848e567 71 "CPU_P3_FLAGS|CpuClflush|CPU_SSE2_FLAGS" },
40fb9820 72 { "CPU_NOCONA_FLAGS",
1848e567 73 "CPU_GENERIC64_FLAGS|CpuFISTTP|CPU_SSE3_FLAGS|CpuCX16" },
40fb9820 74 { "CPU_CORE_FLAGS",
1848e567 75 "CPU_P4_FLAGS|CpuFISTTP|CPU_SSE3_FLAGS|CpuCX16" },
40fb9820 76 { "CPU_CORE2_FLAGS",
1848e567 77 "CPU_NOCONA_FLAGS|CPU_SSSE3_FLAGS" },
bd5295b2 78 { "CPU_COREI7_FLAGS",
1848e567 79 "CPU_CORE2_FLAGS|CPU_SSE4_2_FLAGS|CpuRdtscp" },
40fb9820 80 { "CPU_K6_FLAGS",
1848e567 81 "Cpu186|Cpu286|Cpu386|Cpu486|Cpu586|CpuSYSCALL|Cpu387|CPU_MMX_FLAGS" },
40fb9820 82 { "CPU_K6_2_FLAGS",
1848e567 83 "CPU_K6_FLAGS|Cpu3dnow" },
40fb9820 84 { "CPU_ATHLON_FLAGS",
1848e567 85 "CPU_K6_2_FLAGS|Cpu686|Cpu687|CpuNop|Cpu3dnowA" },
40fb9820 86 { "CPU_K8_FLAGS",
1848e567 87 "CPU_ATHLON_FLAGS|CpuRdtscp|CPU_SSE2_FLAGS|CpuLM" },
40fb9820 88 { "CPU_AMDFAM10_FLAGS",
1848e567 89 "CPU_K8_FLAGS|CpuFISTTP|CPU_SSE4A_FLAGS|CpuABM" },
68339fdf 90 { "CPU_BDVER1_FLAGS",
1848e567 91 "CPU_GENERIC64_FLAGS|CpuFISTTP|CpuRdtscp|CpuCX16|CPU_SSE4_2_FLAGS|CpuSSE4A|CpuABM|CpuFMA4|CpuXOP|CpuLWP|CpuSVME|CpuXsave|CpuAES|CpuAVX|CpuPCLMUL|CpuLZCNT|CpuPRFCHW" },
4cab4add 92 { "CPU_BDVER2_FLAGS",
1848e567 93 "CPU_BDVER1_FLAGS|CpuFMA|CpuBMI|CpuTBM|CpuF16C" },
5e5c50d3 94 { "CPU_BDVER3_FLAGS",
1848e567 95 "CPU_BDVER2_FLAGS|CpuXsaveopt|CpuFSGSBase" },
c7b0bd56 96 { "CPU_BDVER4_FLAGS",
1848e567 97 "CPU_BDVER3_FLAGS|CpuAVX2|CpuMovbe|CpuBMI2|CpuRdRnd|CpuMWAITX" },
029f3522 98 { "CPU_ZNVER1_FLAGS",
1848e567 99 "CPU_GENERIC64_FLAGS|CpuFISTTP|CpuRdtscp|CpuCX16|CPU_SSE4_2_FLAGS|CpuSSE4A|CpuABM|CpuSVME|CpuXsave|CpuAES|CpuAVX|CpuPCLMUL|CpuLZCNT|CpuPRFCHW|CpuFMA|CpuBMI|CpuF16C|CpuXsaveopt|CpuFSGSBase|CpuAVX2|CpuMovbe|CpuBMI2|CpuRdRnd|CpuADX|CpuRdSeed|CpuSMAP|CpuSHA|CpuXSAVEC|CpuXSAVES|CpuClflushOpt|CpuCLZERO|CpuMWAITX" },
7b458c12 100 { "CPU_BTVER1_FLAGS",
1848e567 101 "CPU_GENERIC64_FLAGS|CpuFISTTP|CpuCX16|CpuRdtscp|CPU_SSSE3_FLAGS|CpuSSE4A|CpuABM|CpuPRFCHW|CpuCX16|CpuClflush|CpuFISTTP|CpuSVME|CpuLZCNT" },
7b458c12 102 { "CPU_BTVER2_FLAGS",
1848e567 103 "CPU_BTVER1_FLAGS|CPU_SSE4_2_FLAGS|CpuBMI|CpuF16C|CpuAES|CpuPCLMUL|CpuAVX|CpuMovbe|CpuXsave|CpuXsaveopt|CpuPRFCHW" },
309d3373
JB
104 { "CPU_8087_FLAGS",
105 "Cpu8087" },
106 { "CPU_287_FLAGS",
1848e567 107 "CPU_8087_FLAGS|Cpu287" },
309d3373 108 { "CPU_387_FLAGS",
1848e567
L
109 "CPU_287_FLAGS|Cpu387" },
110 { "CPU_687_FLAGS",
111 "CPU_387_FLAGS|Cpu687" },
bd5295b2
L
112 { "CPU_CLFLUSH_FLAGS",
113 "CpuClflush" },
22109423
L
114 { "CPU_NOP_FLAGS",
115 "CpuNop" },
bd5295b2
L
116 { "CPU_SYSCALL_FLAGS",
117 "CpuSYSCALL" },
40fb9820 118 { "CPU_MMX_FLAGS",
1848e567 119 "CpuRegMMX|CpuMMX" },
40fb9820 120 { "CPU_SSE_FLAGS",
1848e567 121 "CpuRegXMM|CpuSSE" },
40fb9820 122 { "CPU_SSE2_FLAGS",
1848e567 123 "CPU_SSE_FLAGS|CpuSSE2" },
40fb9820 124 { "CPU_SSE3_FLAGS",
1848e567 125 "CPU_SSE2_FLAGS|CpuSSE3" },
40fb9820 126 { "CPU_SSSE3_FLAGS",
1848e567 127 "CPU_SSE3_FLAGS|CpuSSSE3" },
40fb9820 128 { "CPU_SSE4_1_FLAGS",
1848e567 129 "CPU_SSSE3_FLAGS|CpuSSE4_1" },
40fb9820 130 { "CPU_SSE4_2_FLAGS",
1848e567 131 "CPU_SSE4_1_FLAGS|CpuSSE4_2" },
6305a203
L
132 { "CPU_VMX_FLAGS",
133 "CpuVMX" },
134 { "CPU_SMX_FLAGS",
135 "CpuSMX" },
f03fe4c1
L
136 { "CPU_XSAVE_FLAGS",
137 "CpuXsave" },
c7b8aa3a 138 { "CPU_XSAVEOPT_FLAGS",
1848e567 139 "CPU_XSAVE_FLAGS|CpuXsaveopt" },
c0f3af97 140 { "CPU_AES_FLAGS",
1848e567 141 "CPU_SSE2_FLAGS|CpuAES" },
594ab6a3 142 { "CPU_PCLMUL_FLAGS",
1848e567 143 "CPU_SSE2_FLAGS|CpuPCLMUL" },
c0f3af97 144 { "CPU_FMA_FLAGS",
1848e567 145 "CPU_AVX_FLAGS|CpuFMA" },
922d8de8 146 { "CPU_FMA4_FLAGS",
1848e567 147 "CPU_AVX_FLAGS|CpuFMA4" },
5dd85c99 148 { "CPU_XOP_FLAGS",
1848e567 149 "CPU_SSE4A_FLAGS|CPU_FMA4_FLAGS|CpuXOP" },
f88c9eb0
SP
150 { "CPU_LWP_FLAGS",
151 "CpuLWP" },
f12dc422
L
152 { "CPU_BMI_FLAGS",
153 "CpuBMI" },
2a2a0f38
QN
154 { "CPU_TBM_FLAGS",
155 "CpuTBM" },
f1f8f695
L
156 { "CPU_MOVBE_FLAGS",
157 "CpuMovbe" },
60aa667e
L
158 { "CPU_CX16_FLAGS",
159 "CpuCX16" },
1b7f3fb0
L
160 { "CPU_RDTSCP_FLAGS",
161 "CpuRdtscp" },
f1f8f695
L
162 { "CPU_EPT_FLAGS",
163 "CpuEPT" },
c7b8aa3a
L
164 { "CPU_FSGSBASE_FLAGS",
165 "CpuFSGSBase" },
166 { "CPU_RDRND_FLAGS",
167 "CpuRdRnd" },
168 { "CPU_F16C_FLAGS",
1848e567 169 "CPU_AVX_FLAGS|CpuF16C" },
6c30d220
L
170 { "CPU_BMI2_FLAGS",
171 "CpuBMI2" },
172 { "CPU_LZCNT_FLAGS",
173 "CpuLZCNT" },
42164a71
L
174 { "CPU_HLE_FLAGS",
175 "CpuHLE" },
176 { "CPU_RTM_FLAGS",
177 "CpuRTM" },
6c30d220
L
178 { "CPU_INVPCID_FLAGS",
179 "CpuINVPCID" },
8729a6f6
L
180 { "CPU_VMFUNC_FLAGS",
181 "CpuVMFUNC" },
40fb9820 182 { "CPU_3DNOW_FLAGS",
1848e567 183 "CPU_MMX_FLAGS|Cpu3dnow" },
40fb9820 184 { "CPU_3DNOWA_FLAGS",
1848e567 185 "CPU_3DNOW_FLAGS|Cpu3dnowA" },
40fb9820
L
186 { "CPU_PADLOCK_FLAGS",
187 "CpuPadLock" },
188 { "CPU_SVME_FLAGS",
189 "CpuSVME" },
190 { "CPU_SSE4A_FLAGS",
1848e567 191 "CPU_SSE3_FLAGS|CpuSSE4a" },
40fb9820 192 { "CPU_ABM_FLAGS",
3629bb00 193 "CpuABM" },
c0f3af97 194 { "CPU_AVX_FLAGS",
1848e567 195 "CPU_SSE4_2_FLAGS|CpuRegYMM|CpuAVX" },
6c30d220 196 { "CPU_AVX2_FLAGS",
1848e567
L
197 "CPU_AVX_FLAGS|CpuAVX2" },
198 /* Don't use CPU_AVX2_FLAGS on CPU_AVX512F_FLAGS since AVX512F doesn't
199 support YMM registers. */
43234a1e 200 { "CPU_AVX512F_FLAGS",
1848e567 201 "CpuVREX|CPU_SSE4_2_FLAGS|CpuRegZMM|CpuRegMask|CpuAVX|CpuAVX2|CpuAVX512F" },
43234a1e 202 { "CPU_AVX512CD_FLAGS",
1848e567 203 "CPU_AVX512F_FLAGS|CpuAVX512CD" },
43234a1e 204 { "CPU_AVX512ER_FLAGS",
1848e567 205 "CPU_AVX512F_FLAGS|CpuAVX512ER" },
43234a1e 206 { "CPU_AVX512PF_FLAGS",
1848e567 207 "CPU_AVX512F_FLAGS|CpuAVX512PF" },
f3ad7637 208 { "CPU_AVX512DQ_FLAGS",
1848e567 209 "CPU_AVX512F_FLAGS|CpuAVX512DQ" },
f3ad7637 210 { "CPU_AVX512BW_FLAGS",
1848e567 211 "CPU_AVX512F_FLAGS|CpuAVX512BW" },
f3ad7637 212 { "CPU_AVX512VL_FLAGS",
1848e567
L
213 /* Use CPU_AVX2_FLAGS on CPU_AVX512VL_FLAGS since AVX512VL supports YMM
214 registers. */
215 "CPU_AVX512F_FLAGS|CPU_AVX2_FLAGS|CpuAVX512VL" },
f3ad7637 216 { "CPU_AVX512IFMA_FLAGS",
1848e567 217 "CPU_AVX512F_FLAGS|CpuAVX512IFMA" },
f3ad7637 218 { "CPU_AVX512VBMI_FLAGS",
1848e567 219 "CPU_AVX512F_FLAGS|CpuAVX512VBMI" },
920d2ddc
IT
220 { "CPU_AVX512_4FMAPS_FLAGS",
221 "CPU_AVX512F_FLAGS|CpuAVX512_4FMAPS" },
47acf0bd
IT
222 { "CPU_AVX512_4VNNIW_FLAGS",
223 "CPU_AVX512F_FLAGS|CpuAVX512_4VNNIW" },
620214f7
IT
224 { "CPU_AVX512_VPOPCNTDQ_FLAGS",
225 "CPU_AVX512F_FLAGS|CpuAVX512_VPOPCNTDQ" },
53467f57
IT
226 { "CPU_AVX512_VBMI2_FLAGS",
227 "CPU_AVX512F_FLAGS|CpuAVX512_VBMI2" },
8a9036a4
L
228 { "CPU_L1OM_FLAGS",
229 "unknown" },
7a9068fe
L
230 { "CPU_K1OM_FLAGS",
231 "unknown" },
7b6d09fb
L
232 { "CPU_IAMCU_FLAGS",
233 "Cpu186|Cpu286|Cpu386|Cpu486|Cpu586" },
e2e1fcde
L
234 { "CPU_ADX_FLAGS",
235 "CpuADX" },
236 { "CPU_RDSEED_FLAGS",
237 "CpuRdSeed" },
238 { "CPU_PRFCHW_FLAGS",
239 "CpuPRFCHW" },
5c111e37
L
240 { "CPU_SMAP_FLAGS",
241 "CpuSMAP" },
7e8b059b
L
242 { "CPU_MPX_FLAGS",
243 "CpuMPX" },
a0046408 244 { "CPU_SHA_FLAGS",
1848e567 245 "CPU_SSE2_FLAGS|CpuSHA" },
963f3586
IT
246 { "CPU_CLFLUSHOPT_FLAGS",
247 "CpuClflushOpt" },
248 { "CPU_XSAVES_FLAGS",
1848e567 249 "CPU_XSAVE_FLAGS|CpuXSAVES" },
963f3586 250 { "CPU_XSAVEC_FLAGS",
1848e567 251 "CPU_XSAVE_FLAGS|CpuXSAVEC" },
dcf893b5
IT
252 { "CPU_PREFETCHWT1_FLAGS",
253 "CpuPREFETCHWT1" },
2cf200a4
IT
254 { "CPU_SE1_FLAGS",
255 "CpuSE1" },
c5e7287a
IT
256 { "CPU_CLWB_FLAGS",
257 "CpuCLWB" },
029f3522
GG
258 { "CPU_CLZERO_FLAGS",
259 "CpuCLZERO" },
9916071f
AP
260 { "CPU_MWAITX_FLAGS",
261 "CpuMWAITX" },
8eab4136
L
262 { "CPU_OSPKE_FLAGS",
263 "CpuOSPKE" },
8bc52696 264 { "CPU_RDPID_FLAGS",
1848e567 265 "CpuRDPID" },
6b40c462
L
266 { "CPU_PTWRITE_FLAGS",
267 "CpuPTWRITE" },
603555e5
L
268 { "CPU_CET_FLAGS",
269 "CpuCET" },
1848e567
L
270 { "CPU_ANY_X87_FLAGS",
271 "CPU_ANY_287_FLAGS|Cpu8087" },
272 { "CPU_ANY_287_FLAGS",
273 "CPU_ANY_387_FLAGS|Cpu287" },
274 { "CPU_ANY_387_FLAGS",
275 "CPU_ANY_687_FLAGS|Cpu387" },
276 { "CPU_ANY_687_FLAGS",
277 "Cpu687|CpuFISTTP" },
278 { "CPU_ANY_MMX_FLAGS",
279 "CPU_3DNOWA_FLAGS" },
280 { "CPU_ANY_SSE_FLAGS",
281 "CPU_ANY_SSE2_FLAGS|CpuSSE|CpuSSE4a" },
282 { "CPU_ANY_SSE2_FLAGS",
283 "CPU_ANY_SSE3_FLAGS|CpuSSE2" },
284 { "CPU_ANY_SSE3_FLAGS",
285 "CPU_ANY_SSSE3_FLAGS|CpuSSE3" },
286 { "CPU_ANY_SSSE3_FLAGS",
287 "CPU_ANY_SSE4_1_FLAGS|CpuSSSE3" },
288 { "CPU_ANY_SSE4_1_FLAGS",
289 "CPU_ANY_SSE4_2_FLAGS|CpuSSE4_1" },
290 { "CPU_ANY_SSE4_2_FLAGS",
291 "CpuSSE4_2" },
292 { "CPU_ANY_AVX_FLAGS",
293 "CPU_ANY_AVX2_FLAGS|CpuF16C|CpuFMA|CpuFMA4|CpuXOP|CpuAVX" },
294 { "CPU_ANY_AVX2_FLAGS",
295 "CpuAVX2" },
144b71e2 296 { "CPU_ANY_AVX512F_FLAGS",
53467f57 297 "CpuVREX|CpuRegZMM|CpuRegMask|CpuAVX512CD|CpuAVX512ER|CpuAVX512PF|CpuAVX512DQ|CpuAVX512BW|CpuAVX512VL|CpuAVX512IFMA|CpuAVX512VBMI|CpuAVX512_4FMAPS|CpuAVX512_4VNNIW|CpuAVX512_VPOPCNTDQ|CpuAVX512_VBMI2|CpuAVX512F" },
144b71e2
L
298 { "CPU_ANY_AVX512CD_FLAGS",
299 "CpuAVX512CD" },
300 { "CPU_ANY_AVX512ER_FLAGS",
301 "CpuAVX512ER" },
302 { "CPU_ANY_AVX512PF_FLAGS",
303 "CpuAVX512PF" },
304 { "CPU_ANY_AVX512DQ_FLAGS",
305 "CpuAVX512DQ" },
306 { "CPU_ANY_AVX512BW_FLAGS",
307 "CpuAVX512BW" },
308 { "CPU_ANY_AVX512VL_FLAGS",
309 "CpuAVX512VL" },
310 { "CPU_ANY_AVX512IFMA_FLAGS",
311 "CpuAVX512IFMA" },
312 { "CPU_ANY_AVX512VBMI_FLAGS",
313 "CpuAVX512VBMI" },
920d2ddc
IT
314 { "CPU_ANY_AVX512_4FMAPS_FLAGS",
315 "CpuAVX512_4FMAPS" },
47acf0bd
IT
316 { "CPU_ANY_AVX512_4VNNIW_FLAGS",
317 "CpuAVX512_4VNNIW" },
620214f7
IT
318 { "CPU_ANY_AVX512_VPOPCNTDQ_FLAGS",
319 "CpuAVX512_VPOPCNTDQ" },
53467f57
IT
320 { "CPU_ANY_AVX512_VBMI2_FLAGS",
321 "CpuAVX512_VBMI2" },
40fb9820
L
322};
323
8acd5377 324static initializer operand_type_init[] =
40fb9820
L
325{
326 { "OPERAND_TYPE_NONE",
327 "0" },
328 { "OPERAND_TYPE_REG8",
329 "Reg8" },
330 { "OPERAND_TYPE_REG16",
331 "Reg16" },
332 { "OPERAND_TYPE_REG32",
333 "Reg32" },
334 { "OPERAND_TYPE_REG64",
335 "Reg64" },
336 { "OPERAND_TYPE_IMM1",
337 "Imm1" },
338 { "OPERAND_TYPE_IMM8",
339 "Imm8" },
340 { "OPERAND_TYPE_IMM8S",
341 "Imm8S" },
342 { "OPERAND_TYPE_IMM16",
343 "Imm16" },
344 { "OPERAND_TYPE_IMM32",
345 "Imm32" },
346 { "OPERAND_TYPE_IMM32S",
347 "Imm32S" },
348 { "OPERAND_TYPE_IMM64",
349 "Imm64" },
350 { "OPERAND_TYPE_BASEINDEX",
351 "BaseIndex" },
352 { "OPERAND_TYPE_DISP8",
353 "Disp8" },
354 { "OPERAND_TYPE_DISP16",
355 "Disp16" },
356 { "OPERAND_TYPE_DISP32",
357 "Disp32" },
358 { "OPERAND_TYPE_DISP32S",
359 "Disp32S" },
360 { "OPERAND_TYPE_DISP64",
361 "Disp64" },
362 { "OPERAND_TYPE_INOUTPORTREG",
363 "InOutPortReg" },
364 { "OPERAND_TYPE_SHIFTCOUNT",
365 "ShiftCount" },
366 { "OPERAND_TYPE_CONTROL",
367 "Control" },
368 { "OPERAND_TYPE_TEST",
369 "Test" },
370 { "OPERAND_TYPE_DEBUG",
371 "FloatReg" },
372 { "OPERAND_TYPE_FLOATREG",
373 "FloatReg" },
374 { "OPERAND_TYPE_FLOATACC",
375 "FloatAcc" },
376 { "OPERAND_TYPE_SREG2",
377 "SReg2" },
378 { "OPERAND_TYPE_SREG3",
379 "SReg3" },
380 { "OPERAND_TYPE_ACC",
381 "Acc" },
382 { "OPERAND_TYPE_JUMPABSOLUTE",
383 "JumpAbsolute" },
384 { "OPERAND_TYPE_REGMMX",
385 "RegMMX" },
386 { "OPERAND_TYPE_REGXMM",
387 "RegXMM" },
c0f3af97
L
388 { "OPERAND_TYPE_REGYMM",
389 "RegYMM" },
43234a1e
L
390 { "OPERAND_TYPE_REGZMM",
391 "RegZMM" },
392 { "OPERAND_TYPE_REGMASK",
393 "RegMask" },
40fb9820
L
394 { "OPERAND_TYPE_ESSEG",
395 "EsSeg" },
396 { "OPERAND_TYPE_ACC32",
7d5e4556 397 "Reg32|Acc|Dword" },
40fb9820 398 { "OPERAND_TYPE_ACC64",
7d5e4556 399 "Reg64|Acc|Qword" },
65da13b5
L
400 { "OPERAND_TYPE_INOUTPORTREG",
401 "InOutPortReg" },
40fb9820
L
402 { "OPERAND_TYPE_REG16_INOUTPORTREG",
403 "Reg16|InOutPortReg" },
404 { "OPERAND_TYPE_DISP16_32",
405 "Disp16|Disp32" },
406 { "OPERAND_TYPE_ANYDISP",
407 "Disp8|Disp16|Disp32|Disp32S|Disp64" },
408 { "OPERAND_TYPE_IMM16_32",
409 "Imm16|Imm32" },
410 { "OPERAND_TYPE_IMM16_32S",
411 "Imm16|Imm32S" },
412 { "OPERAND_TYPE_IMM16_32_32S",
413 "Imm16|Imm32|Imm32S" },
2f81ff92
L
414 { "OPERAND_TYPE_IMM32_64",
415 "Imm32|Imm64" },
40fb9820
L
416 { "OPERAND_TYPE_IMM32_32S_DISP32",
417 "Imm32|Imm32S|Disp32" },
418 { "OPERAND_TYPE_IMM64_DISP64",
419 "Imm64|Disp64" },
420 { "OPERAND_TYPE_IMM32_32S_64_DISP32",
421 "Imm32|Imm32S|Imm64|Disp32" },
422 { "OPERAND_TYPE_IMM32_32S_64_DISP32_64",
423 "Imm32|Imm32S|Imm64|Disp32|Disp64" },
a683cc34
SP
424 { "OPERAND_TYPE_VEC_IMM4",
425 "Vec_Imm4" },
7e8b059b
L
426 { "OPERAND_TYPE_REGBND",
427 "RegBND" },
43234a1e
L
428 { "OPERAND_TYPE_VEC_DISP8",
429 "Vec_Disp8" },
40fb9820
L
430};
431
432typedef struct bitfield
433{
434 int position;
435 int value;
436 const char *name;
437} bitfield;
438
439#define BITFIELD(n) { n, 0, #n }
440
441static bitfield cpu_flags[] =
442{
443 BITFIELD (Cpu186),
444 BITFIELD (Cpu286),
445 BITFIELD (Cpu386),
446 BITFIELD (Cpu486),
447 BITFIELD (Cpu586),
448 BITFIELD (Cpu686),
bd5295b2 449 BITFIELD (CpuClflush),
22109423 450 BITFIELD (CpuNop),
bd5295b2 451 BITFIELD (CpuSYSCALL),
309d3373
JB
452 BITFIELD (Cpu8087),
453 BITFIELD (Cpu287),
454 BITFIELD (Cpu387),
455 BITFIELD (Cpu687),
456 BITFIELD (CpuFISTTP),
40fb9820 457 BITFIELD (CpuMMX),
40fb9820
L
458 BITFIELD (CpuSSE),
459 BITFIELD (CpuSSE2),
460 BITFIELD (CpuSSE3),
461 BITFIELD (CpuSSSE3),
462 BITFIELD (CpuSSE4_1),
463 BITFIELD (CpuSSE4_2),
c0f3af97 464 BITFIELD (CpuAVX),
6c30d220 465 BITFIELD (CpuAVX2),
43234a1e
L
466 BITFIELD (CpuAVX512F),
467 BITFIELD (CpuAVX512CD),
468 BITFIELD (CpuAVX512ER),
469 BITFIELD (CpuAVX512PF),
b28d1bda 470 BITFIELD (CpuAVX512VL),
90a915bf 471 BITFIELD (CpuAVX512DQ),
1ba585e8 472 BITFIELD (CpuAVX512BW),
8a9036a4 473 BITFIELD (CpuL1OM),
7a9068fe 474 BITFIELD (CpuK1OM),
7b6d09fb 475 BITFIELD (CpuIAMCU),
40fb9820
L
476 BITFIELD (CpuSSE4a),
477 BITFIELD (Cpu3dnow),
478 BITFIELD (Cpu3dnowA),
479 BITFIELD (CpuPadLock),
480 BITFIELD (CpuSVME),
481 BITFIELD (CpuVMX),
47dd174c 482 BITFIELD (CpuSMX),
40fb9820 483 BITFIELD (CpuABM),
475a2301 484 BITFIELD (CpuXsave),
c7b8aa3a 485 BITFIELD (CpuXsaveopt),
c0f3af97 486 BITFIELD (CpuAES),
594ab6a3 487 BITFIELD (CpuPCLMUL),
c0f3af97 488 BITFIELD (CpuFMA),
f88c9eb0 489 BITFIELD (CpuFMA4),
5dd85c99 490 BITFIELD (CpuXOP),
f88c9eb0 491 BITFIELD (CpuLWP),
f12dc422 492 BITFIELD (CpuBMI),
2a2a0f38 493 BITFIELD (CpuTBM),
c0f3af97 494 BITFIELD (CpuLM),
f1f8f695 495 BITFIELD (CpuMovbe),
60aa667e 496 BITFIELD (CpuCX16),
f1f8f695 497 BITFIELD (CpuEPT),
1b7f3fb0 498 BITFIELD (CpuRdtscp),
c7b8aa3a
L
499 BITFIELD (CpuFSGSBase),
500 BITFIELD (CpuRdRnd),
501 BITFIELD (CpuF16C),
6c30d220
L
502 BITFIELD (CpuBMI2),
503 BITFIELD (CpuLZCNT),
42164a71
L
504 BITFIELD (CpuHLE),
505 BITFIELD (CpuRTM),
6c30d220 506 BITFIELD (CpuINVPCID),
8729a6f6 507 BITFIELD (CpuVMFUNC),
e2e1fcde
L
508 BITFIELD (CpuRDSEED),
509 BITFIELD (CpuADX),
510 BITFIELD (CpuPRFCHW),
5c111e37 511 BITFIELD (CpuSMAP),
a0046408 512 BITFIELD (CpuSHA),
43234a1e 513 BITFIELD (CpuVREX),
963f3586
IT
514 BITFIELD (CpuClflushOpt),
515 BITFIELD (CpuXSAVES),
516 BITFIELD (CpuXSAVEC),
dcf893b5 517 BITFIELD (CpuPREFETCHWT1),
2cf200a4 518 BITFIELD (CpuSE1),
c5e7287a 519 BITFIELD (CpuCLWB),
40fb9820
L
520 BITFIELD (Cpu64),
521 BITFIELD (CpuNo64),
7e8b059b 522 BITFIELD (CpuMPX),
2cc1b5aa 523 BITFIELD (CpuAVX512IFMA),
14f195c9 524 BITFIELD (CpuAVX512VBMI),
920d2ddc 525 BITFIELD (CpuAVX512_4FMAPS),
47acf0bd 526 BITFIELD (CpuAVX512_4VNNIW),
620214f7 527 BITFIELD (CpuAVX512_VPOPCNTDQ),
53467f57 528 BITFIELD (CpuAVX512_VBMI2),
9916071f 529 BITFIELD (CpuMWAITX),
029f3522 530 BITFIELD (CpuCLZERO),
8eab4136 531 BITFIELD (CpuOSPKE),
8bc52696 532 BITFIELD (CpuRDPID),
6b40c462 533 BITFIELD (CpuPTWRITE),
603555e5 534 BITFIELD (CpuCET),
1848e567
L
535 BITFIELD (CpuRegMMX),
536 BITFIELD (CpuRegXMM),
537 BITFIELD (CpuRegYMM),
538 BITFIELD (CpuRegZMM),
539 BITFIELD (CpuRegMask),
40fb9820
L
540#ifdef CpuUnused
541 BITFIELD (CpuUnused),
542#endif
543};
544
545static bitfield opcode_modifiers[] =
546{
547 BITFIELD (D),
548 BITFIELD (W),
86fa6981 549 BITFIELD (Load),
40fb9820
L
550 BITFIELD (Modrm),
551 BITFIELD (ShortForm),
552 BITFIELD (Jump),
553 BITFIELD (JumpDword),
554 BITFIELD (JumpByte),
555 BITFIELD (JumpInterSegment),
556 BITFIELD (FloatMF),
557 BITFIELD (FloatR),
558 BITFIELD (FloatD),
559 BITFIELD (Size16),
560 BITFIELD (Size32),
561 BITFIELD (Size64),
56ffb741 562 BITFIELD (CheckRegSize),
40fb9820
L
563 BITFIELD (IgnoreSize),
564 BITFIELD (DefaultSize),
565 BITFIELD (No_bSuf),
566 BITFIELD (No_wSuf),
567 BITFIELD (No_lSuf),
568 BITFIELD (No_sSuf),
569 BITFIELD (No_qSuf),
7ce189b3 570 BITFIELD (No_ldSuf),
40fb9820
L
571 BITFIELD (FWait),
572 BITFIELD (IsString),
7e8b059b 573 BITFIELD (BNDPrefixOk),
04ef582a 574 BITFIELD (NoTrackPrefixOk),
c32fa91d 575 BITFIELD (IsLockable),
40fb9820 576 BITFIELD (RegKludge),
e2ec9d29 577 BITFIELD (FirstXmm0),
c0f3af97 578 BITFIELD (Implicit1stXmm0),
29c048b6 579 BITFIELD (RepPrefixOk),
42164a71 580 BITFIELD (HLEPrefixOk),
ca61edf2
L
581 BITFIELD (ToDword),
582 BITFIELD (ToQword),
583 BITFIELD (AddrPrefixOp0),
40fb9820
L
584 BITFIELD (IsPrefix),
585 BITFIELD (ImmExt),
586 BITFIELD (NoRex64),
587 BITFIELD (Rex64),
588 BITFIELD (Ugh),
c0f3af97 589 BITFIELD (Vex),
2426c15f 590 BITFIELD (VexVVVV),
1ef99a7b 591 BITFIELD (VexW),
7f399153 592 BITFIELD (VexOpcode),
8cd7925b 593 BITFIELD (VexSources),
c0f3af97 594 BITFIELD (VexImmExt),
6c30d220 595 BITFIELD (VecSIB),
c0f3af97 596 BITFIELD (SSE2AVX),
81f8a913 597 BITFIELD (NoAVX),
43234a1e
L
598 BITFIELD (EVex),
599 BITFIELD (Masking),
600 BITFIELD (VecESize),
601 BITFIELD (Broadcast),
602 BITFIELD (StaticRounding),
603 BITFIELD (SAE),
604 BITFIELD (Disp8MemShift),
605 BITFIELD (NoDefMask),
920d2ddc 606 BITFIELD (ImplicitQuadGroup),
1efbbeb4
L
607 BITFIELD (OldGcc),
608 BITFIELD (ATTMnemonic),
e1d4d893 609 BITFIELD (ATTSyntax),
5c07affc 610 BITFIELD (IntelSyntax),
e92bae62
L
611 BITFIELD (AMD64),
612 BITFIELD (Intel64),
40fb9820
L
613};
614
615static bitfield operand_types[] =
616{
617 BITFIELD (Reg8),
618 BITFIELD (Reg16),
619 BITFIELD (Reg32),
620 BITFIELD (Reg64),
621 BITFIELD (FloatReg),
622 BITFIELD (RegMMX),
623 BITFIELD (RegXMM),
c0f3af97 624 BITFIELD (RegYMM),
43234a1e
L
625 BITFIELD (RegZMM),
626 BITFIELD (RegMask),
94ff3a50 627 BITFIELD (Imm1),
40fb9820
L
628 BITFIELD (Imm8),
629 BITFIELD (Imm8S),
630 BITFIELD (Imm16),
631 BITFIELD (Imm32),
632 BITFIELD (Imm32S),
633 BITFIELD (Imm64),
40fb9820
L
634 BITFIELD (BaseIndex),
635 BITFIELD (Disp8),
636 BITFIELD (Disp16),
637 BITFIELD (Disp32),
638 BITFIELD (Disp32S),
639 BITFIELD (Disp64),
640 BITFIELD (InOutPortReg),
641 BITFIELD (ShiftCount),
642 BITFIELD (Control),
643 BITFIELD (Debug),
644 BITFIELD (Test),
645 BITFIELD (SReg2),
646 BITFIELD (SReg3),
647 BITFIELD (Acc),
648 BITFIELD (FloatAcc),
649 BITFIELD (JumpAbsolute),
650 BITFIELD (EsSeg),
651 BITFIELD (RegMem),
5c07affc 652 BITFIELD (Mem),
7d5e4556
L
653 BITFIELD (Byte),
654 BITFIELD (Word),
655 BITFIELD (Dword),
656 BITFIELD (Fword),
657 BITFIELD (Qword),
658 BITFIELD (Tbyte),
659 BITFIELD (Xmmword),
c0f3af97 660 BITFIELD (Ymmword),
43234a1e 661 BITFIELD (Zmmword),
7d5e4556
L
662 BITFIELD (Unspecified),
663 BITFIELD (Anysize),
a683cc34 664 BITFIELD (Vec_Imm4),
7e8b059b 665 BITFIELD (RegBND),
43234a1e 666 BITFIELD (Vec_Disp8),
40fb9820
L
667#ifdef OTUnused
668 BITFIELD (OTUnused),
669#endif
670};
671
3d4d5afa
L
672static const char *filename;
673
40fb9820
L
674static int
675compare (const void *x, const void *y)
676{
677 const bitfield *xp = (const bitfield *) x;
678 const bitfield *yp = (const bitfield *) y;
679 return xp->position - yp->position;
680}
681
40b8e679
L
682static void
683fail (const char *message, ...)
684{
685 va_list args;
29c048b6 686
40b8e679
L
687 va_start (args, message);
688 fprintf (stderr, _("%s: Error: "), program_name);
689 vfprintf (stderr, message, args);
690 va_end (args);
691 xexit (1);
692}
693
72ffa0fb
L
694static void
695process_copyright (FILE *fp)
696{
697 fprintf (fp, "/* This file is automatically generated by i386-gen. Do not edit! */\n\
2571583a 698/* Copyright (C) 2007-2017 Free Software Foundation, Inc.\n\
72ffa0fb
L
699\n\
700 This file is part of the GNU opcodes library.\n\
701\n\
702 This library is free software; you can redistribute it and/or modify\n\
703 it under the terms of the GNU General Public License as published by\n\
704 the Free Software Foundation; either version 3, or (at your option)\n\
705 any later version.\n\
706\n\
707 It is distributed in the hope that it will be useful, but WITHOUT\n\
708 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\n\
709 or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public\n\
710 License for more details.\n\
711\n\
712 You should have received a copy of the GNU General Public License\n\
713 along with this program; if not, write to the Free Software\n\
714 Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,\n\
715 MA 02110-1301, USA. */\n");
716}
717
40b8e679
L
718/* Remove leading white spaces. */
719
720static char *
721remove_leading_whitespaces (char *str)
722{
723 while (ISSPACE (*str))
724 str++;
725 return str;
726}
727
728/* Remove trailing white spaces. */
729
730static void
731remove_trailing_whitespaces (char *str)
732{
733 size_t last = strlen (str);
734
735 if (last == 0)
736 return;
737
738 do
739 {
740 last--;
741 if (ISSPACE (str [last]))
742 str[last] = '\0';
743 else
744 break;
745 }
746 while (last != 0);
747}
748
93b1ec2c 749/* Find next field separated by SEP and terminate it. Return a
40b8e679
L
750 pointer to the one after it. */
751
752static char *
c587b3f9 753next_field (char *str, char sep, char **next, char *last)
40b8e679
L
754{
755 char *p;
756
757 p = remove_leading_whitespaces (str);
93b1ec2c 758 for (str = p; *str != sep && *str != '\0'; str++);
40b8e679
L
759
760 *str = '\0';
761 remove_trailing_whitespaces (p);
762
29c048b6 763 *next = str + 1;
40b8e679 764
c587b3f9
L
765 if (p >= last)
766 abort ();
767
40b8e679
L
768 return p;
769}
770
1848e567
L
771static void set_bitfield (char *, bitfield *, int, unsigned int, int);
772
773static int
774set_bitfield_from_cpu_flag_init (char *f, bitfield *array,
775 int value, unsigned int size,
776 int lineno)
777{
778 char *str, *next, *last;
779 unsigned int i;
780
781 for (i = 0; i < ARRAY_SIZE (cpu_flag_init); i++)
782 if (strcmp (cpu_flag_init[i].name, f) == 0)
783 {
784 /* Turn on selective bits. */
785 char *init = xstrdup (cpu_flag_init[i].init);
786 last = init + strlen (init);
787 for (next = init; next && next < last; )
788 {
789 str = next_field (next, '|', &next, last);
790 if (str)
791 set_bitfield (str, array, 1, size, lineno);
792 }
793 free (init);
794 return 0;
795 }
796
797 return -1;
798}
799
40fb9820 800static void
1848e567 801set_bitfield (char *f, bitfield *array, int value,
8a9036a4 802 unsigned int size, int lineno)
40fb9820
L
803{
804 unsigned int i;
805
309d3373
JB
806 if (strcmp (f, "CpuFP") == 0)
807 {
8a9036a4
L
808 set_bitfield("Cpu387", array, value, size, lineno);
809 set_bitfield("Cpu287", array, value, size, lineno);
309d3373
JB
810 f = "Cpu8087";
811 }
812 else if (strcmp (f, "Mmword") == 0)
7d5e4556
L
813 f= "Qword";
814 else if (strcmp (f, "Oword") == 0)
815 f= "Xmmword";
40fb9820
L
816
817 for (i = 0; i < size; i++)
818 if (strcasecmp (array[i].name, f) == 0)
819 {
8a9036a4 820 array[i].value = value;
40fb9820
L
821 return;
822 }
823
2bf05e57
L
824 if (value)
825 {
826 const char *v = strchr (f, '=');
827
828 if (v)
829 {
830 size_t n = v - f;
831 char *end;
832
833 for (i = 0; i < size; i++)
834 if (strncasecmp (array[i].name, f, n) == 0)
835 {
836 value = strtol (v + 1, &end, 0);
837 if (*end == '\0')
838 {
839 array[i].value = value;
840 return;
841 }
842 break;
843 }
844 }
845 }
846
1848e567
L
847 /* Handle CPU_XXX_FLAGS. */
848 if (!set_bitfield_from_cpu_flag_init (f, array, value, size, lineno))
849 return;
850
bd5295b2
L
851 if (lineno != -1)
852 fail (_("%s: %d: Unknown bitfield: %s\n"), filename, lineno, f);
853 else
854 fail (_("Unknown bitfield: %s\n"), f);
40fb9820
L
855}
856
857static void
858output_cpu_flags (FILE *table, bitfield *flags, unsigned int size,
859 int macro, const char *comma, const char *indent)
860{
861 unsigned int i;
862
863 fprintf (table, "%s{ { ", indent);
864
865 for (i = 0; i < size - 1; i++)
866 {
10632b79
L
867 if (((i + 1) % 20) != 0)
868 fprintf (table, "%d, ", flags[i].value);
869 else
870 fprintf (table, "%d,", flags[i].value);
40fb9820
L
871 if (((i + 1) % 20) == 0)
872 {
873 /* We need \\ for macro. */
874 if (macro)
875 fprintf (table, " \\\n %s", indent);
876 else
877 fprintf (table, "\n %s", indent);
878 }
879 }
880
881 fprintf (table, "%d } }%s\n", flags[i].value, comma);
882}
883
884static void
885process_i386_cpu_flag (FILE *table, char *flag, int macro,
bd5295b2
L
886 const char *comma, const char *indent,
887 int lineno)
40fb9820
L
888{
889 char *str, *next, *last;
8a9036a4 890 unsigned int i;
40fb9820
L
891 bitfield flags [ARRAY_SIZE (cpu_flags)];
892
893 /* Copy the default cpu flags. */
894 memcpy (flags, cpu_flags, sizeof (cpu_flags));
895
896 if (strcasecmp (flag, "unknown") == 0)
897 {
40fb9820 898 /* We turn on everything except for cpu64 in case of
8a9036a4
L
899 CPU_UNKNOWN_FLAGS. */
900 for (i = 0; i < ARRAY_SIZE (flags); i++)
901 if (flags[i].position != Cpu64)
902 flags[i].value = 1;
903 }
904 else if (flag[0] == '~')
905 {
906 last = flag + strlen (flag);
907
908 if (flag[1] == '(')
909 {
910 last -= 1;
911 next = flag + 2;
912 if (*last != ')')
913 fail (_("%s: %d: Missing `)' in bitfield: %s\n"), filename,
914 lineno, flag);
915 *last = '\0';
916 }
917 else
918 next = flag + 1;
919
920 /* First we turn on everything except for cpu64. */
40fb9820
L
921 for (i = 0; i < ARRAY_SIZE (flags); i++)
922 if (flags[i].position != Cpu64)
923 flags[i].value = 1;
8a9036a4
L
924
925 /* Turn off selective bits. */
926 for (; next && next < last; )
927 {
928 str = next_field (next, '|', &next, last);
929 if (str)
930 set_bitfield (str, flags, 0, ARRAY_SIZE (flags), lineno);
931 }
40fb9820
L
932 }
933 else if (strcmp (flag, "0"))
934 {
8a9036a4 935 /* Turn on selective bits. */
40fb9820
L
936 last = flag + strlen (flag);
937 for (next = flag; next && next < last; )
938 {
c587b3f9 939 str = next_field (next, '|', &next, last);
40fb9820 940 if (str)
8a9036a4 941 set_bitfield (str, flags, 1, ARRAY_SIZE (flags), lineno);
40fb9820
L
942 }
943 }
944
945 output_cpu_flags (table, flags, ARRAY_SIZE (flags), macro,
946 comma, indent);
947}
948
949static void
950output_opcode_modifier (FILE *table, bitfield *modifier, unsigned int size)
951{
952 unsigned int i;
953
954 fprintf (table, " { ");
955
956 for (i = 0; i < size - 1; i++)
957 {
10632b79
L
958 if (((i + 1) % 20) != 0)
959 fprintf (table, "%d, ", modifier[i].value);
960 else
961 fprintf (table, "%d,", modifier[i].value);
40fb9820
L
962 if (((i + 1) % 20) == 0)
963 fprintf (table, "\n ");
964 }
965
966 fprintf (table, "%d },\n", modifier[i].value);
967}
968
969static void
bd5295b2 970process_i386_opcode_modifier (FILE *table, char *mod, int lineno)
40fb9820
L
971{
972 char *str, *next, *last;
973 bitfield modifiers [ARRAY_SIZE (opcode_modifiers)];
974
975 /* Copy the default opcode modifier. */
976 memcpy (modifiers, opcode_modifiers, sizeof (modifiers));
977
978 if (strcmp (mod, "0"))
979 {
980 last = mod + strlen (mod);
981 for (next = mod; next && next < last; )
982 {
c587b3f9 983 str = next_field (next, '|', &next, last);
40fb9820 984 if (str)
8a9036a4
L
985 set_bitfield (str, modifiers, 1, ARRAY_SIZE (modifiers),
986 lineno);
40fb9820
L
987 }
988 }
989 output_opcode_modifier (table, modifiers, ARRAY_SIZE (modifiers));
990}
991
992static void
993output_operand_type (FILE *table, bitfield *types, unsigned int size,
994 int macro, const char *indent)
995{
996 unsigned int i;
997
998 fprintf (table, "{ { ");
999
1000 for (i = 0; i < size - 1; i++)
1001 {
10632b79
L
1002 if (((i + 1) % 20) != 0)
1003 fprintf (table, "%d, ", types[i].value);
1004 else
1005 fprintf (table, "%d,", types[i].value);
40fb9820
L
1006 if (((i + 1) % 20) == 0)
1007 {
1008 /* We need \\ for macro. */
1009 if (macro)
10632b79 1010 fprintf (table, " \\\n%s", indent);
40fb9820
L
1011 else
1012 fprintf (table, "\n%s", indent);
1013 }
1014 }
1015
1016 fprintf (table, "%d } }", types[i].value);
1017}
1018
1019static void
1020process_i386_operand_type (FILE *table, char *op, int macro,
bd5295b2 1021 const char *indent, int lineno)
40fb9820
L
1022{
1023 char *str, *next, *last;
1024 bitfield types [ARRAY_SIZE (operand_types)];
1025
1026 /* Copy the default operand type. */
1027 memcpy (types, operand_types, sizeof (types));
1028
1029 if (strcmp (op, "0"))
1030 {
1031 last = op + strlen (op);
1032 for (next = op; next && next < last; )
1033 {
c587b3f9 1034 str = next_field (next, '|', &next, last);
40fb9820 1035 if (str)
8a9036a4 1036 set_bitfield (str, types, 1, ARRAY_SIZE (types), lineno);
40fb9820
L
1037 }
1038 }
1039 output_operand_type (table, types, ARRAY_SIZE (types), macro,
1040 indent);
1041}
1042
c587b3f9
L
1043static void
1044output_i386_opcode (FILE *table, const char *name, char *str,
bd5295b2 1045 char *last, int lineno)
c587b3f9
L
1046{
1047 unsigned int i;
1048 char *operands, *base_opcode, *extension_opcode, *opcode_length;
1049 char *cpu_flags, *opcode_modifier, *operand_types [MAX_OPERANDS];
1050
1051 /* Find number of operands. */
1052 operands = next_field (str, ',', &str, last);
1053
1054 /* Find base_opcode. */
1055 base_opcode = next_field (str, ',', &str, last);
1056
1057 /* Find extension_opcode. */
1058 extension_opcode = next_field (str, ',', &str, last);
1059
1060 /* Find opcode_length. */
1061 opcode_length = next_field (str, ',', &str, last);
1062
1063 /* Find cpu_flags. */
1064 cpu_flags = next_field (str, ',', &str, last);
1065
1066 /* Find opcode_modifier. */
1067 opcode_modifier = next_field (str, ',', &str, last);
1068
1069 /* Remove the first {. */
1070 str = remove_leading_whitespaces (str);
1071 if (*str != '{')
1072 abort ();
1073 str = remove_leading_whitespaces (str + 1);
1074
1075 i = strlen (str);
1076
1077 /* There are at least "X}". */
1078 if (i < 2)
1079 abort ();
1080
1081 /* Remove trailing white spaces and }. */
1082 do
1083 {
1084 i--;
1085 if (ISSPACE (str[i]) || str[i] == '}')
1086 str[i] = '\0';
1087 else
1088 break;
1089 }
1090 while (i != 0);
1091
1092 last = str + i;
1093
1094 /* Find operand_types. */
1095 for (i = 0; i < ARRAY_SIZE (operand_types); i++)
1096 {
1097 if (str >= last)
1098 {
1099 operand_types [i] = NULL;
1100 break;
1101 }
1102
1103 operand_types [i] = next_field (str, ',', &str, last);
1104 if (*operand_types[i] == '0')
1105 {
1106 if (i != 0)
1107 operand_types[i] = NULL;
1108 break;
1109 }
1110 }
1111
1112 fprintf (table, " { \"%s\", %s, %s, %s, %s,\n",
1113 name, operands, base_opcode, extension_opcode,
1114 opcode_length);
1115
bd5295b2 1116 process_i386_cpu_flag (table, cpu_flags, 0, ",", " ", lineno);
c587b3f9 1117
bd5295b2 1118 process_i386_opcode_modifier (table, opcode_modifier, lineno);
c587b3f9
L
1119
1120 fprintf (table, " { ");
1121
1122 for (i = 0; i < ARRAY_SIZE (operand_types); i++)
1123 {
1124 if (operand_types[i] == NULL || *operand_types[i] == '0')
1125 {
1126 if (i == 0)
bd5295b2 1127 process_i386_operand_type (table, "0", 0, "\t ", lineno);
c587b3f9
L
1128 break;
1129 }
1130
1131 if (i != 0)
1132 fprintf (table, ",\n ");
1133
1134 process_i386_operand_type (table, operand_types[i], 0,
bd5295b2 1135 "\t ", lineno);
c587b3f9
L
1136 }
1137 fprintf (table, " } },\n");
1138}
1139
1140struct opcode_hash_entry
1141{
1142 struct opcode_hash_entry *next;
1143 char *name;
1144 char *opcode;
bd5295b2 1145 int lineno;
c587b3f9
L
1146};
1147
1148/* Calculate the hash value of an opcode hash entry P. */
1149
1150static hashval_t
1151opcode_hash_hash (const void *p)
1152{
1153 struct opcode_hash_entry *entry = (struct opcode_hash_entry *) p;
1154 return htab_hash_string (entry->name);
1155}
1156
1157/* Compare a string Q against an opcode hash entry P. */
1158
1159static int
1160opcode_hash_eq (const void *p, const void *q)
1161{
1162 struct opcode_hash_entry *entry = (struct opcode_hash_entry *) p;
1163 const char *name = (const char *) q;
1164 return strcmp (name, entry->name) == 0;
1165}
1166
40b8e679 1167static void
72ffa0fb 1168process_i386_opcodes (FILE *table)
40b8e679 1169{
3d4d5afa 1170 FILE *fp;
40b8e679 1171 char buf[2048];
c587b3f9
L
1172 unsigned int i, j;
1173 char *str, *p, *last, *name;
1174 struct opcode_hash_entry **hash_slot, **entry, *next;
1175 htab_t opcode_hash_table;
1176 struct opcode_hash_entry **opcode_array;
1177 unsigned int opcode_array_size = 1024;
bd5295b2 1178 int lineno = 0;
40b8e679 1179
3d4d5afa
L
1180 filename = "i386-opc.tbl";
1181 fp = fopen (filename, "r");
1182
40b8e679 1183 if (fp == NULL)
34edb9ad 1184 fail (_("can't find i386-opc.tbl for reading, errno = %s\n"),
40fb9820 1185 xstrerror (errno));
40b8e679 1186
c587b3f9
L
1187 i = 0;
1188 opcode_array = (struct opcode_hash_entry **)
1189 xmalloc (sizeof (*opcode_array) * opcode_array_size);
1190
1191 opcode_hash_table = htab_create_alloc (16, opcode_hash_hash,
1192 opcode_hash_eq, NULL,
1193 xcalloc, free);
1194
34edb9ad 1195 fprintf (table, "\n/* i386 opcode table. */\n\n");
d3ce72d0 1196 fprintf (table, "const insn_template i386_optab[] =\n{\n");
40b8e679 1197
c587b3f9 1198 /* Put everything on opcode array. */
40b8e679
L
1199 while (!feof (fp))
1200 {
1201 if (fgets (buf, sizeof (buf), fp) == NULL)
1202 break;
1203
3d4d5afa
L
1204 lineno++;
1205
40b8e679
L
1206 p = remove_leading_whitespaces (buf);
1207
1208 /* Skip comments. */
1209 str = strstr (p, "//");
1210 if (str != NULL)
1211 str[0] = '\0';
1212
1213 /* Remove trailing white spaces. */
1214 remove_trailing_whitespaces (p);
1215
1216 switch (p[0])
1217 {
1218 case '#':
c587b3f9 1219 /* Ignore comments. */
40b8e679
L
1220 case '\0':
1221 continue;
1222 break;
1223 default:
1224 break;
1225 }
1226
1227 last = p + strlen (p);
1228
1229 /* Find name. */
c587b3f9 1230 name = next_field (p, ',', &str, last);
40b8e679 1231
c587b3f9
L
1232 /* Get the slot in hash table. */
1233 hash_slot = (struct opcode_hash_entry **)
1234 htab_find_slot_with_hash (opcode_hash_table, name,
1235 htab_hash_string (name),
1236 INSERT);
40b8e679 1237
c587b3f9 1238 if (*hash_slot == NULL)
40b8e679 1239 {
c587b3f9
L
1240 /* It is the new one. Put it on opcode array. */
1241 if (i >= opcode_array_size)
40b8e679 1242 {
c587b3f9
L
1243 /* Grow the opcode array when needed. */
1244 opcode_array_size += 1024;
1245 opcode_array = (struct opcode_hash_entry **)
1246 xrealloc (opcode_array,
1247 sizeof (*opcode_array) * opcode_array_size);
40b8e679
L
1248 }
1249
c587b3f9
L
1250 opcode_array[i] = (struct opcode_hash_entry *)
1251 xmalloc (sizeof (struct opcode_hash_entry));
1252 opcode_array[i]->next = NULL;
1253 opcode_array[i]->name = xstrdup (name);
1254 opcode_array[i]->opcode = xstrdup (str);
bd5295b2 1255 opcode_array[i]->lineno = lineno;
c587b3f9
L
1256 *hash_slot = opcode_array[i];
1257 i++;
40b8e679 1258 }
c587b3f9 1259 else
40b8e679 1260 {
c587b3f9
L
1261 /* Append it to the existing one. */
1262 entry = hash_slot;
1263 while ((*entry) != NULL)
1264 entry = &(*entry)->next;
1265 *entry = (struct opcode_hash_entry *)
1266 xmalloc (sizeof (struct opcode_hash_entry));
1267 (*entry)->next = NULL;
1268 (*entry)->name = (*hash_slot)->name;
1269 (*entry)->opcode = xstrdup (str);
bd5295b2 1270 (*entry)->lineno = lineno;
c587b3f9
L
1271 }
1272 }
40b8e679 1273
c587b3f9
L
1274 /* Process opcode array. */
1275 for (j = 0; j < i; j++)
1276 {
1277 for (next = opcode_array[j]; next; next = next->next)
1278 {
1279 name = next->name;
1280 str = next->opcode;
bd5295b2 1281 lineno = next->lineno;
c587b3f9 1282 last = str + strlen (str);
bd5295b2 1283 output_i386_opcode (table, name, str, last, lineno);
40b8e679 1284 }
40b8e679
L
1285 }
1286
34edb9ad
L
1287 fclose (fp);
1288
4dffcebc 1289 fprintf (table, " { NULL, 0, 0, 0, 0,\n");
40fb9820 1290
bd5295b2 1291 process_i386_cpu_flag (table, "0", 0, ",", " ", -1);
40fb9820 1292
bd5295b2 1293 process_i386_opcode_modifier (table, "0", -1);
29c048b6 1294
40fb9820 1295 fprintf (table, " { ");
bd5295b2 1296 process_i386_operand_type (table, "0", 0, "\t ", -1);
40fb9820
L
1297 fprintf (table, " } }\n");
1298
34edb9ad 1299 fprintf (table, "};\n");
40b8e679
L
1300}
1301
1302static void
72ffa0fb 1303process_i386_registers (FILE *table)
40b8e679 1304{
3d4d5afa 1305 FILE *fp;
40b8e679
L
1306 char buf[2048];
1307 char *str, *p, *last;
1308 char *reg_name, *reg_type, *reg_flags, *reg_num;
a60de03c 1309 char *dw2_32_num, *dw2_64_num;
bd5295b2 1310 int lineno = 0;
40b8e679 1311
3d4d5afa
L
1312 filename = "i386-reg.tbl";
1313 fp = fopen (filename, "r");
40b8e679 1314 if (fp == NULL)
34edb9ad 1315 fail (_("can't find i386-reg.tbl for reading, errno = %s\n"),
40fb9820 1316 xstrerror (errno));
40b8e679 1317
34edb9ad
L
1318 fprintf (table, "\n/* i386 register table. */\n\n");
1319 fprintf (table, "const reg_entry i386_regtab[] =\n{\n");
40b8e679
L
1320
1321 while (!feof (fp))
1322 {
1323 if (fgets (buf, sizeof (buf), fp) == NULL)
1324 break;
1325
3d4d5afa
L
1326 lineno++;
1327
40b8e679
L
1328 p = remove_leading_whitespaces (buf);
1329
1330 /* Skip comments. */
1331 str = strstr (p, "//");
1332 if (str != NULL)
1333 str[0] = '\0';
1334
1335 /* Remove trailing white spaces. */
1336 remove_trailing_whitespaces (p);
1337
1338 switch (p[0])
1339 {
1340 case '#':
34edb9ad 1341 fprintf (table, "%s\n", p);
40b8e679
L
1342 case '\0':
1343 continue;
1344 break;
1345 default:
1346 break;
1347 }
1348
1349 last = p + strlen (p);
1350
1351 /* Find reg_name. */
c587b3f9 1352 reg_name = next_field (p, ',', &str, last);
40b8e679
L
1353
1354 /* Find reg_type. */
c587b3f9 1355 reg_type = next_field (str, ',', &str, last);
40b8e679
L
1356
1357 /* Find reg_flags. */
c587b3f9 1358 reg_flags = next_field (str, ',', &str, last);
40b8e679
L
1359
1360 /* Find reg_num. */
c587b3f9 1361 reg_num = next_field (str, ',', &str, last);
a60de03c 1362
40fb9820
L
1363 fprintf (table, " { \"%s\",\n ", reg_name);
1364
bd5295b2 1365 process_i386_operand_type (table, reg_type, 0, "\t", lineno);
40fb9820 1366
a60de03c 1367 /* Find 32-bit Dwarf2 register number. */
c587b3f9 1368 dw2_32_num = next_field (str, ',', &str, last);
a60de03c
JB
1369
1370 /* Find 64-bit Dwarf2 register number. */
c587b3f9 1371 dw2_64_num = next_field (str, ',', &str, last);
a60de03c
JB
1372
1373 fprintf (table, ",\n %s, %s, { %s, %s } },\n",
1374 reg_flags, reg_num, dw2_32_num, dw2_64_num);
40b8e679
L
1375 }
1376
34edb9ad
L
1377 fclose (fp);
1378
1379 fprintf (table, "};\n");
40b8e679 1380
34edb9ad 1381 fprintf (table, "\nconst unsigned int i386_regtab_size = ARRAY_SIZE (i386_regtab);\n");
40b8e679
L
1382}
1383
40fb9820
L
1384static void
1385process_i386_initializers (void)
1386{
1387 unsigned int i;
1388 FILE *fp = fopen ("i386-init.h", "w");
1389 char *init;
1390
1391 if (fp == NULL)
1392 fail (_("can't create i386-init.h, errno = %s\n"),
1393 xstrerror (errno));
1394
1395 process_copyright (fp);
1396
1397 for (i = 0; i < ARRAY_SIZE (cpu_flag_init); i++)
1398 {
1399 fprintf (fp, "\n#define %s \\\n", cpu_flag_init[i].name);
1400 init = xstrdup (cpu_flag_init[i].init);
bd5295b2 1401 process_i386_cpu_flag (fp, init, 1, "", " ", -1);
40fb9820
L
1402 free (init);
1403 }
1404
1405 for (i = 0; i < ARRAY_SIZE (operand_type_init); i++)
1406 {
1407 fprintf (fp, "\n\n#define %s \\\n ", operand_type_init[i].name);
1408 init = xstrdup (operand_type_init[i].init);
bd5295b2 1409 process_i386_operand_type (fp, init, 1, " ", -1);
40fb9820
L
1410 free (init);
1411 }
1412 fprintf (fp, "\n");
1413
1414 fclose (fp);
1415}
1416
40b8e679
L
1417/* Program options. */
1418#define OPTION_SRCDIR 200
1419
29c048b6 1420struct option long_options[] =
40b8e679
L
1421{
1422 {"srcdir", required_argument, NULL, OPTION_SRCDIR},
1423 {"debug", no_argument, NULL, 'd'},
1424 {"version", no_argument, NULL, 'V'},
1425 {"help", no_argument, NULL, 'h'},
1426 {0, no_argument, NULL, 0}
1427};
1428
1429static void
1430print_version (void)
1431{
1432 printf ("%s: version 1.0\n", program_name);
1433 xexit (0);
1434}
1435
1436static void
1437usage (FILE * stream, int status)
1438{
1439 fprintf (stream, "Usage: %s [-V | --version] [-d | --debug] [--srcdir=dirname] [--help]\n",
1440 program_name);
1441 xexit (status);
1442}
1443
1444int
1445main (int argc, char **argv)
1446{
1447 extern int chdir (char *);
1448 char *srcdir = NULL;
8b40d594 1449 int c;
e92bae62 1450 unsigned int i, cpumax;
72ffa0fb 1451 FILE *table;
29c048b6 1452
40b8e679
L
1453 program_name = *argv;
1454 xmalloc_set_program_name (program_name);
1455
1456 while ((c = getopt_long (argc, argv, "vVdh", long_options, 0)) != EOF)
1457 switch (c)
1458 {
1459 case OPTION_SRCDIR:
1460 srcdir = optarg;
1461 break;
1462 case 'V':
1463 case 'v':
1464 print_version ();
1465 break;
1466 case 'd':
1467 debug = 1;
1468 break;
1469 case 'h':
1470 case '?':
1471 usage (stderr, 0);
1472 default:
1473 case 0:
1474 break;
1475 }
1476
1477 if (optind != argc)
1478 usage (stdout, 1);
1479
29c048b6 1480 if (srcdir != NULL)
40b8e679
L
1481 if (chdir (srcdir) != 0)
1482 fail (_("unable to change directory to \"%s\", errno = %s\n"),
40fb9820
L
1483 srcdir, xstrerror (errno));
1484
e92bae62
L
1485 /* cpu_flags isn't sorted by position. */
1486 cpumax = 0;
1487 for (i = 0; i < ARRAY_SIZE (cpu_flags); i++)
1488 if (cpu_flags[i].position > cpumax)
1489 cpumax = cpu_flags[i].position;
1490
40fb9820 1491 /* Check the unused bitfield in i386_cpu_flags. */
e89c5eaa 1492#ifdef CpuUnused
e92bae62
L
1493 if ((cpumax - 1) != CpuMax)
1494 fail (_("CpuMax != %d!\n"), cpumax);
e89c5eaa 1495#else
e92bae62
L
1496 if (cpumax != CpuMax)
1497 fail (_("CpuMax != %d!\n"), cpumax);
e89c5eaa 1498
8b40d594
L
1499 c = CpuNumOfBits - CpuMax - 1;
1500 if (c)
1501 fail (_("%d unused bits in i386_cpu_flags.\n"), c);
40fb9820
L
1502#endif
1503
1504 /* Check the unused bitfield in i386_operand_type. */
1505#ifndef OTUnused
8b40d594
L
1506 c = OTNumOfBits - OTMax - 1;
1507 if (c)
1508 fail (_("%d unused bits in i386_operand_type.\n"), c);
40fb9820
L
1509#endif
1510
1511 qsort (cpu_flags, ARRAY_SIZE (cpu_flags), sizeof (cpu_flags [0]),
1512 compare);
1513
1514 qsort (opcode_modifiers, ARRAY_SIZE (opcode_modifiers),
1515 sizeof (opcode_modifiers [0]), compare);
1516
1517 qsort (operand_types, ARRAY_SIZE (operand_types),
1518 sizeof (operand_types [0]), compare);
40b8e679 1519
34edb9ad
L
1520 table = fopen ("i386-tbl.h", "w");
1521 if (table == NULL)
40fb9820
L
1522 fail (_("can't create i386-tbl.h, errno = %s\n"),
1523 xstrerror (errno));
34edb9ad 1524
72ffa0fb 1525 process_copyright (table);
40b8e679 1526
72ffa0fb
L
1527 process_i386_opcodes (table);
1528 process_i386_registers (table);
40fb9820 1529 process_i386_initializers ();
40b8e679 1530
34edb9ad
L
1531 fclose (table);
1532
40b8e679
L
1533 exit (0);
1534}
This page took 0.563838 seconds and 4 git commands to generate.