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