1 /* Copyright (C) 1988-2023 Free Software Foundation, Inc.
3 This file is part of GCC.
5 GCC is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 3, or (at your option)
10 GCC is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with GCC; see the file COPYING3. If not see
17 <http://www.gnu.org/licenses/>. */
19 #define IN_TARGET_CODE 1
23 #include "coretypes.h"
33 #include "stringpool.h"
40 #include "diagnostic.h"
43 #include "fold-const.h"
46 #include "stor-layout.h"
49 #include "insn-attr.h"
55 #include "common/common-target.h"
56 #include "langhooks.h"
60 #include "tm-constrs.h"
62 #include "sched-int.h"
64 #include "tree-pass.h"
66 #include "pass_manager.h"
67 #include "target-globals.h"
68 #include "gimple-iterator.h"
69 #include "tree-vectorizer.h"
70 #include "shrink-wrap.h"
73 #include "tree-iterator.h"
75 #include "case-cfn-macros.h"
77 #include "fold-const-call.h"
79 #include "tree-ssanames.h"
81 #include "selftest-rtl.h"
82 #include "print-rtl.h"
85 #include "symbol-summary.h"
87 #include "ipa-fnsummary.h"
88 #include "wide-int-bitmask.h"
89 #include "tree-vector-builder.h"
91 #include "dwarf2out.h"
92 #include "i386-options.h"
94 #include "x86-tune-costs.h"
96 #ifndef SUBTARGET32_DEFAULT_CPU
97 #define SUBTARGET32_DEFAULT_CPU "i386"
100 /* Processor feature/optimization bitmasks. */
101 #define m_NONE HOST_WIDE_INT_0U
102 #define m_ALL (~HOST_WIDE_INT_0U)
103 #define m_386 (HOST_WIDE_INT_1U<<PROCESSOR_I386)
104 #define m_486 (HOST_WIDE_INT_1U<<PROCESSOR_I486)
105 #define m_PENT (HOST_WIDE_INT_1U<<PROCESSOR_PENTIUM)
106 #define m_LAKEMONT (HOST_WIDE_INT_1U<<PROCESSOR_LAKEMONT)
107 #define m_PPRO (HOST_WIDE_INT_1U<<PROCESSOR_PENTIUMPRO)
108 #define m_PENT4 (HOST_WIDE_INT_1U<<PROCESSOR_PENTIUM4)
109 #define m_NOCONA (HOST_WIDE_INT_1U<<PROCESSOR_NOCONA)
110 #define m_P4_NOCONA (m_PENT4 | m_NOCONA)
111 #define m_CORE2 (HOST_WIDE_INT_1U<<PROCESSOR_CORE2)
112 #define m_NEHALEM (HOST_WIDE_INT_1U<<PROCESSOR_NEHALEM)
113 #define m_SANDYBRIDGE (HOST_WIDE_INT_1U<<PROCESSOR_SANDYBRIDGE)
114 #define m_HASWELL (HOST_WIDE_INT_1U<<PROCESSOR_HASWELL)
115 #define m_BONNELL (HOST_WIDE_INT_1U<<PROCESSOR_BONNELL)
116 #define m_SILVERMONT (HOST_WIDE_INT_1U<<PROCESSOR_SILVERMONT)
117 #define m_KNL (HOST_WIDE_INT_1U<<PROCESSOR_KNL)
118 #define m_KNM (HOST_WIDE_INT_1U<<PROCESSOR_KNM)
119 #define m_SKYLAKE (HOST_WIDE_INT_1U<<PROCESSOR_SKYLAKE)
120 #define m_SKYLAKE_AVX512 (HOST_WIDE_INT_1U<<PROCESSOR_SKYLAKE_AVX512)
121 #define m_CANNONLAKE (HOST_WIDE_INT_1U<<PROCESSOR_CANNONLAKE)
122 #define m_ICELAKE_CLIENT (HOST_WIDE_INT_1U<<PROCESSOR_ICELAKE_CLIENT)
123 #define m_ICELAKE_SERVER (HOST_WIDE_INT_1U<<PROCESSOR_ICELAKE_SERVER)
124 #define m_CASCADELAKE (HOST_WIDE_INT_1U<<PROCESSOR_CASCADELAKE)
125 #define m_TIGERLAKE (HOST_WIDE_INT_1U<<PROCESSOR_TIGERLAKE)
126 #define m_COOPERLAKE (HOST_WIDE_INT_1U<<PROCESSOR_COOPERLAKE)
127 #define m_SAPPHIRERAPIDS (HOST_WIDE_INT_1U<<PROCESSOR_SAPPHIRERAPIDS)
128 #define m_ALDERLAKE (HOST_WIDE_INT_1U<<PROCESSOR_ALDERLAKE)
129 #define m_ROCKETLAKE (HOST_WIDE_INT_1U<<PROCESSOR_ROCKETLAKE)
130 #define m_GRANITERAPIDS (HOST_WIDE_INT_1U<<PROCESSOR_GRANITERAPIDS)
131 #define m_CORE_AVX512 (m_SKYLAKE_AVX512 | m_CANNONLAKE \
132 | m_ICELAKE_CLIENT | m_ICELAKE_SERVER | m_CASCADELAKE \
133 | m_TIGERLAKE | m_COOPERLAKE | m_SAPPHIRERAPIDS \
134 | m_ROCKETLAKE | m_GRANITERAPIDS)
135 #define m_CORE_AVX2 (m_HASWELL | m_SKYLAKE | m_CORE_AVX512)
136 #define m_CORE_ALL (m_CORE2 | m_NEHALEM | m_SANDYBRIDGE | m_CORE_AVX2)
137 #define m_GOLDMONT (HOST_WIDE_INT_1U<<PROCESSOR_GOLDMONT)
138 #define m_GOLDMONT_PLUS (HOST_WIDE_INT_1U<<PROCESSOR_GOLDMONT_PLUS)
139 #define m_TREMONT (HOST_WIDE_INT_1U<<PROCESSOR_TREMONT)
140 #define m_SIERRAFOREST (HOST_WIDE_INT_1U<<PROCESSOR_SIERRAFOREST)
141 #define m_GRANDRIDGE (HOST_WIDE_INT_1U<<PROCESSOR_GRANDRIDGE)
142 #define m_CORE_ATOM (m_SIERRAFOREST | m_GRANDRIDGE)
143 #define m_INTEL (HOST_WIDE_INT_1U<<PROCESSOR_INTEL)
145 #define m_LUJIAZUI (HOST_WIDE_INT_1U<<PROCESSOR_LUJIAZUI)
147 #define m_GEODE (HOST_WIDE_INT_1U<<PROCESSOR_GEODE)
148 #define m_K6 (HOST_WIDE_INT_1U<<PROCESSOR_K6)
149 #define m_K6_GEODE (m_K6 | m_GEODE)
150 #define m_K8 (HOST_WIDE_INT_1U<<PROCESSOR_K8)
151 #define m_ATHLON (HOST_WIDE_INT_1U<<PROCESSOR_ATHLON)
152 #define m_ATHLON_K8 (m_K8 | m_ATHLON)
153 #define m_AMDFAM10 (HOST_WIDE_INT_1U<<PROCESSOR_AMDFAM10)
154 #define m_BDVER1 (HOST_WIDE_INT_1U<<PROCESSOR_BDVER1)
155 #define m_BDVER2 (HOST_WIDE_INT_1U<<PROCESSOR_BDVER2)
156 #define m_BDVER3 (HOST_WIDE_INT_1U<<PROCESSOR_BDVER3)
157 #define m_BDVER4 (HOST_WIDE_INT_1U<<PROCESSOR_BDVER4)
158 #define m_ZNVER1 (HOST_WIDE_INT_1U<<PROCESSOR_ZNVER1)
159 #define m_ZNVER2 (HOST_WIDE_INT_1U<<PROCESSOR_ZNVER2)
160 #define m_ZNVER3 (HOST_WIDE_INT_1U<<PROCESSOR_ZNVER3)
161 #define m_ZNVER4 (HOST_WIDE_INT_1U<<PROCESSOR_ZNVER4)
162 #define m_BTVER1 (HOST_WIDE_INT_1U<<PROCESSOR_BTVER1)
163 #define m_BTVER2 (HOST_WIDE_INT_1U<<PROCESSOR_BTVER2)
164 #define m_BDVER (m_BDVER1 | m_BDVER2 | m_BDVER3 | m_BDVER4)
165 #define m_BTVER (m_BTVER1 | m_BTVER2)
166 #define m_ZNVER (m_ZNVER1 | m_ZNVER2 | m_ZNVER3 | m_ZNVER4)
167 #define m_AMD_MULTIPLE (m_ATHLON_K8 | m_AMDFAM10 | m_BDVER | m_BTVER \
170 #define m_GENERIC (HOST_WIDE_INT_1U<<PROCESSOR_GENERIC)
172 const char* ix86_tune_feature_names
[X86_TUNE_LAST
] = {
174 #define DEF_TUNE(tune, name, selector) name,
175 #include "x86-tune.def"
179 /* Feature tests against the various tunings. */
180 unsigned char ix86_tune_features
[X86_TUNE_LAST
];
182 /* Feature tests against the various tunings used to create ix86_tune_features
183 based on the processor mask. */
184 static unsigned HOST_WIDE_INT initial_ix86_tune_features
[X86_TUNE_LAST
] = {
186 #define DEF_TUNE(tune, name, selector) selector,
187 #include "x86-tune.def"
191 /* Feature tests against the various architecture variations. */
192 unsigned char ix86_arch_features
[X86_ARCH_LAST
];
194 struct ix86_target_opts
196 const char *option
; /* option string */
197 HOST_WIDE_INT mask
; /* isa mask options */
200 /* This table is ordered so that options like -msse4.2 that imply other
201 ISAs come first. Target string will be displayed in the same order. */
202 static struct ix86_target_opts isa2_opts
[] =
204 { "-mcx16", OPTION_MASK_ISA2_CX16
},
205 { "-mvaes", OPTION_MASK_ISA2_VAES
},
206 { "-mrdpid", OPTION_MASK_ISA2_RDPID
},
207 { "-mpconfig", OPTION_MASK_ISA2_PCONFIG
},
208 { "-mwbnoinvd", OPTION_MASK_ISA2_WBNOINVD
},
209 { "-mavx512vp2intersect", OPTION_MASK_ISA2_AVX512VP2INTERSECT
},
210 { "-msgx", OPTION_MASK_ISA2_SGX
},
211 { "-mavx5124vnniw", OPTION_MASK_ISA2_AVX5124VNNIW
},
212 { "-mavx5124fmaps", OPTION_MASK_ISA2_AVX5124FMAPS
},
213 { "-mhle", OPTION_MASK_ISA2_HLE
},
214 { "-mmovbe", OPTION_MASK_ISA2_MOVBE
},
215 { "-mclzero", OPTION_MASK_ISA2_CLZERO
},
216 { "-mmwaitx", OPTION_MASK_ISA2_MWAITX
},
217 { "-mmwait", OPTION_MASK_ISA2_MWAIT
},
218 { "-mmovdir64b", OPTION_MASK_ISA2_MOVDIR64B
},
219 { "-mwaitpkg", OPTION_MASK_ISA2_WAITPKG
},
220 { "-mcldemote", OPTION_MASK_ISA2_CLDEMOTE
},
221 { "-mptwrite", OPTION_MASK_ISA2_PTWRITE
},
222 { "-mavx512bf16", OPTION_MASK_ISA2_AVX512BF16
},
223 { "-menqcmd", OPTION_MASK_ISA2_ENQCMD
},
224 { "-mserialize", OPTION_MASK_ISA2_SERIALIZE
},
225 { "-mtsxldtrk", OPTION_MASK_ISA2_TSXLDTRK
},
226 { "-mamx-tile", OPTION_MASK_ISA2_AMX_TILE
},
227 { "-mamx-int8", OPTION_MASK_ISA2_AMX_INT8
},
228 { "-mamx-bf16", OPTION_MASK_ISA2_AMX_BF16
},
229 { "-muintr", OPTION_MASK_ISA2_UINTR
},
230 { "-mhreset", OPTION_MASK_ISA2_HRESET
},
231 { "-mkl", OPTION_MASK_ISA2_KL
},
232 { "-mwidekl", OPTION_MASK_ISA2_WIDEKL
},
233 { "-mavxvnni", OPTION_MASK_ISA2_AVXVNNI
},
234 { "-mavx512fp16", OPTION_MASK_ISA2_AVX512FP16
},
235 { "-mavxifma", OPTION_MASK_ISA2_AVXIFMA
},
236 { "-mavxvnniint8", OPTION_MASK_ISA2_AVXVNNIINT8
},
237 { "-mavxneconvert", OPTION_MASK_ISA2_AVXNECONVERT
},
238 { "-mcmpccxadd", OPTION_MASK_ISA2_CMPCCXADD
},
239 { "-mamx-fp16", OPTION_MASK_ISA2_AMX_FP16
},
240 { "-mprefetchi", OPTION_MASK_ISA2_PREFETCHI
},
241 { "-mraoint", OPTION_MASK_ISA2_RAOINT
}
243 static struct ix86_target_opts isa_opts
[] =
245 { "-mavx512vpopcntdq", OPTION_MASK_ISA_AVX512VPOPCNTDQ
},
246 { "-mavx512bitalg", OPTION_MASK_ISA_AVX512BITALG
},
247 { "-mvpclmulqdq", OPTION_MASK_ISA_VPCLMULQDQ
},
248 { "-mgfni", OPTION_MASK_ISA_GFNI
},
249 { "-mavx512vnni", OPTION_MASK_ISA_AVX512VNNI
},
250 { "-mavx512vbmi2", OPTION_MASK_ISA_AVX512VBMI2
},
251 { "-mavx512vbmi", OPTION_MASK_ISA_AVX512VBMI
},
252 { "-mavx512ifma", OPTION_MASK_ISA_AVX512IFMA
},
253 { "-mavx512vl", OPTION_MASK_ISA_AVX512VL
},
254 { "-mavx512bw", OPTION_MASK_ISA_AVX512BW
},
255 { "-mavx512dq", OPTION_MASK_ISA_AVX512DQ
},
256 { "-mavx512er", OPTION_MASK_ISA_AVX512ER
},
257 { "-mavx512pf", OPTION_MASK_ISA_AVX512PF
},
258 { "-mavx512cd", OPTION_MASK_ISA_AVX512CD
},
259 { "-mavx512f", OPTION_MASK_ISA_AVX512F
},
260 { "-mavx2", OPTION_MASK_ISA_AVX2
},
261 { "-mfma", OPTION_MASK_ISA_FMA
},
262 { "-mxop", OPTION_MASK_ISA_XOP
},
263 { "-mfma4", OPTION_MASK_ISA_FMA4
},
264 { "-mf16c", OPTION_MASK_ISA_F16C
},
265 { "-mavx", OPTION_MASK_ISA_AVX
},
266 /*{ "-msse4" OPTION_MASK_ISA_SSE4 }, */
267 { "-msse4.2", OPTION_MASK_ISA_SSE4_2
},
268 { "-msse4.1", OPTION_MASK_ISA_SSE4_1
},
269 { "-msse4a", OPTION_MASK_ISA_SSE4A
},
270 { "-mssse3", OPTION_MASK_ISA_SSSE3
},
271 { "-msse3", OPTION_MASK_ISA_SSE3
},
272 { "-maes", OPTION_MASK_ISA_AES
},
273 { "-msha", OPTION_MASK_ISA_SHA
},
274 { "-mpclmul", OPTION_MASK_ISA_PCLMUL
},
275 { "-msse2", OPTION_MASK_ISA_SSE2
},
276 { "-msse", OPTION_MASK_ISA_SSE
},
277 { "-m3dnowa", OPTION_MASK_ISA_3DNOW_A
},
278 { "-m3dnow", OPTION_MASK_ISA_3DNOW
},
279 { "-mmmx", OPTION_MASK_ISA_MMX
},
280 { "-mrtm", OPTION_MASK_ISA_RTM
},
281 { "-mprfchw", OPTION_MASK_ISA_PRFCHW
},
282 { "-mrdseed", OPTION_MASK_ISA_RDSEED
},
283 { "-madx", OPTION_MASK_ISA_ADX
},
284 { "-mprefetchwt1", OPTION_MASK_ISA_PREFETCHWT1
},
285 { "-mclflushopt", OPTION_MASK_ISA_CLFLUSHOPT
},
286 { "-mxsaves", OPTION_MASK_ISA_XSAVES
},
287 { "-mxsavec", OPTION_MASK_ISA_XSAVEC
},
288 { "-mxsaveopt", OPTION_MASK_ISA_XSAVEOPT
},
289 { "-mxsave", OPTION_MASK_ISA_XSAVE
},
290 { "-mabm", OPTION_MASK_ISA_ABM
},
291 { "-mbmi", OPTION_MASK_ISA_BMI
},
292 { "-mbmi2", OPTION_MASK_ISA_BMI2
},
293 { "-mlzcnt", OPTION_MASK_ISA_LZCNT
},
294 { "-mtbm", OPTION_MASK_ISA_TBM
},
295 { "-mpopcnt", OPTION_MASK_ISA_POPCNT
},
296 { "-msahf", OPTION_MASK_ISA_SAHF
},
297 { "-mcrc32", OPTION_MASK_ISA_CRC32
},
298 { "-mfsgsbase", OPTION_MASK_ISA_FSGSBASE
},
299 { "-mrdrnd", OPTION_MASK_ISA_RDRND
},
300 { "-mpku", OPTION_MASK_ISA_PKU
},
301 { "-mlwp", OPTION_MASK_ISA_LWP
},
302 { "-mfxsr", OPTION_MASK_ISA_FXSR
},
303 { "-mclwb", OPTION_MASK_ISA_CLWB
},
304 { "-mshstk", OPTION_MASK_ISA_SHSTK
},
305 { "-mmovdiri", OPTION_MASK_ISA_MOVDIRI
}
308 /* Return 1 if TRAIT NAME is present in the OpenMP context's
309 device trait set, return 0 if not present in any OpenMP context in the
310 whole translation unit, or -1 if not present in the current OpenMP context
311 but might be present in another OpenMP context in the same TU. */
314 ix86_omp_device_kind_arch_isa (enum omp_device_kind_arch_isa trait
,
319 case omp_device_kind
:
320 return strcmp (name
, "cpu") == 0;
321 case omp_device_arch
:
322 if (strcmp (name
, "x86") == 0)
327 return strcmp (name
, "x32") == 0;
329 return strcmp (name
, "x86_64") == 0;
331 if (strcmp (name
, "ia32") == 0 || strcmp (name
, "i386") == 0)
333 if (strcmp (name
, "i486") == 0)
334 return ix86_arch
!= PROCESSOR_I386
? 1 : -1;
335 if (strcmp (name
, "i586") == 0)
336 return (ix86_arch
!= PROCESSOR_I386
337 && ix86_arch
!= PROCESSOR_I486
) ? 1 : -1;
338 if (strcmp (name
, "i686") == 0)
339 return (ix86_arch
!= PROCESSOR_I386
340 && ix86_arch
!= PROCESSOR_I486
341 && ix86_arch
!= PROCESSOR_LAKEMONT
342 && ix86_arch
!= PROCESSOR_PENTIUM
) ? 1 : -1;
345 for (int i
= 0; i
< 2; i
++)
347 struct ix86_target_opts
*opts
= i
? isa2_opts
: isa_opts
;
348 size_t nopts
= i
? ARRAY_SIZE (isa2_opts
) : ARRAY_SIZE (isa_opts
);
349 HOST_WIDE_INT mask
= i
? ix86_isa_flags2
: ix86_isa_flags
;
350 for (size_t n
= 0; n
< nopts
; n
++)
352 /* Handle sse4 as an alias to sse4.2. */
353 if (opts
[n
].mask
== OPTION_MASK_ISA_SSE4_2
)
355 if (strcmp (name
, "sse4") == 0)
356 return (mask
& opts
[n
].mask
) != 0 ? 1 : -1;
358 if (strcmp (name
, opts
[n
].option
+ 2) == 0)
359 return (mask
& opts
[n
].mask
) != 0 ? 1 : -1;
368 /* Return a string that documents the current -m options. The caller is
369 responsible for freeing the string. */
372 ix86_target_string (HOST_WIDE_INT isa
, HOST_WIDE_INT isa2
,
373 int flags
, int flags2
,
374 const char *arch
, const char *tune
,
375 enum fpmath_unit fpmath
,
376 enum prefer_vector_width pvw
,
377 enum prefer_vector_width move_max
,
378 enum prefer_vector_width store_max
,
379 bool add_nl_p
, bool add_abi_p
)
382 static struct ix86_target_opts flag_opts
[] =
384 { "-m128bit-long-double", MASK_128BIT_LONG_DOUBLE
},
385 { "-mlong-double-128", MASK_LONG_DOUBLE_128
},
386 { "-mlong-double-64", MASK_LONG_DOUBLE_64
},
387 { "-m80387", MASK_80387
},
388 { "-maccumulate-outgoing-args", MASK_ACCUMULATE_OUTGOING_ARGS
},
389 { "-malign-double", MASK_ALIGN_DOUBLE
},
390 { "-mcld", MASK_CLD
},
391 { "-mfp-ret-in-387", MASK_FLOAT_RETURNS
},
392 { "-mieee-fp", MASK_IEEE_FP
},
393 { "-minline-all-stringops", MASK_INLINE_ALL_STRINGOPS
},
394 { "-minline-stringops-dynamically", MASK_INLINE_STRINGOPS_DYNAMICALLY
},
395 { "-mms-bitfields", MASK_MS_BITFIELD_LAYOUT
},
396 { "-mno-align-stringops", MASK_NO_ALIGN_STRINGOPS
},
397 { "-mno-fancy-math-387", MASK_NO_FANCY_MATH_387
},
398 { "-mno-push-args", MASK_NO_PUSH_ARGS
},
399 { "-mno-red-zone", MASK_NO_RED_ZONE
},
400 { "-momit-leaf-frame-pointer", MASK_OMIT_LEAF_FRAME_POINTER
},
401 { "-mrecip", MASK_RECIP
},
402 { "-mrtd", MASK_RTD
},
403 { "-msseregparm", MASK_SSEREGPARM
},
404 { "-mstack-arg-probe", MASK_STACK_PROBE
},
405 { "-mtls-direct-seg-refs", MASK_TLS_DIRECT_SEG_REFS
},
406 { "-mvect8-ret-in-mem", MASK_VECT8_RETURNS
},
407 { "-m8bit-idiv", MASK_USE_8BIT_IDIV
},
408 { "-mvzeroupper", MASK_VZEROUPPER
},
409 { "-mstv", MASK_STV
},
410 { "-mavx256-split-unaligned-load", MASK_AVX256_SPLIT_UNALIGNED_LOAD
},
411 { "-mavx256-split-unaligned-store", MASK_AVX256_SPLIT_UNALIGNED_STORE
},
412 { "-mcall-ms2sysv-xlogues", MASK_CALL_MS2SYSV_XLOGUES
},
413 { "-mrelax-cmpxchg-loop", MASK_RELAX_CMPXCHG_LOOP
}
416 /* Additional flag options. */
417 static struct ix86_target_opts flag2_opts
[] =
419 { "-mgeneral-regs-only", OPTION_MASK_GENERAL_REGS_ONLY
}
422 const char *opts
[ARRAY_SIZE (isa_opts
) + ARRAY_SIZE (isa2_opts
)
423 + ARRAY_SIZE (flag_opts
) + ARRAY_SIZE (flag2_opts
) + 6][2];
427 char flags_other
[40];
428 char flags2_other
[40];
438 memset (opts
, '\0', sizeof (opts
));
440 /* Add -march= option. */
443 opts
[num
][0] = "-march=";
444 opts
[num
++][1] = arch
;
447 /* Add -mtune= option. */
450 opts
[num
][0] = "-mtune=";
451 opts
[num
++][1] = tune
;
454 /* Add -m32/-m64/-mx32. */
457 if ((isa
& OPTION_MASK_ISA_64BIT
) != 0)
459 if ((isa
& OPTION_MASK_ABI_64
) != 0)
466 opts
[num
++][0] = abi
;
468 isa
&= ~(OPTION_MASK_ISA_64BIT
| OPTION_MASK_ABI_64
| OPTION_MASK_ABI_X32
);
470 /* Pick out the options in isa2 options. */
471 for (i
= 0; i
< ARRAY_SIZE (isa2_opts
); i
++)
473 if ((isa2
& isa2_opts
[i
].mask
) != 0)
475 opts
[num
++][0] = isa2_opts
[i
].option
;
476 isa2
&= ~ isa2_opts
[i
].mask
;
480 if (isa2
&& add_nl_p
)
482 opts
[num
++][0] = isa2_other
;
483 sprintf (isa2_other
, "(other isa2: %#" HOST_WIDE_INT_PRINT
"x)", isa2
);
486 /* Pick out the options in isa options. */
487 for (i
= 0; i
< ARRAY_SIZE (isa_opts
); i
++)
489 if ((isa
& isa_opts
[i
].mask
) != 0)
491 opts
[num
++][0] = isa_opts
[i
].option
;
492 isa
&= ~ isa_opts
[i
].mask
;
498 opts
[num
++][0] = isa_other
;
499 sprintf (isa_other
, "(other isa: %#" HOST_WIDE_INT_PRINT
"x)", isa
);
502 /* Add flag options. */
503 for (i
= 0; i
< ARRAY_SIZE (flag_opts
); i
++)
505 if ((flags
& flag_opts
[i
].mask
) != 0)
507 opts
[num
++][0] = flag_opts
[i
].option
;
508 flags
&= ~ flag_opts
[i
].mask
;
512 if (flags
&& add_nl_p
)
514 opts
[num
++][0] = flags_other
;
515 sprintf (flags_other
, "(other flags: %#x)", flags
);
518 /* Add additional flag options. */
519 for (i
= 0; i
< ARRAY_SIZE (flag2_opts
); i
++)
521 if ((flags2
& flag2_opts
[i
].mask
) != 0)
523 opts
[num
++][0] = flag2_opts
[i
].option
;
524 flags2
&= ~ flag2_opts
[i
].mask
;
528 if (flags2
&& add_nl_p
)
530 opts
[num
++][0] = flags2_other
;
531 sprintf (flags2_other
, "(other flags2: %#x)", flags2
);
534 /* Add -mfpmath= option. */
537 opts
[num
][0] = "-mfpmath=";
538 switch ((int) fpmath
)
541 opts
[num
++][1] = "387";
545 opts
[num
++][1] = "sse";
548 case FPMATH_387
| FPMATH_SSE
:
549 opts
[num
++][1] = "sse+387";
557 auto add_vector_width
= [&opts
, &num
] (prefer_vector_width pvw
,
564 opts
[num
++][1] = "128";
568 opts
[num
++][1] = "256";
572 opts
[num
++][1] = "512";
580 /* Add -mprefer-vector-width= option. */
582 add_vector_width (pvw
, "-mprefer-vector-width=");
584 /* Add -mmove-max= option. */
586 add_vector_width (move_max
, "-mmove-max=");
588 /* Add -mstore-max= option. */
590 add_vector_width (store_max
, "-mstore-max=");
596 gcc_assert (num
< ARRAY_SIZE (opts
));
598 /* Size the string. */
600 sep_len
= (add_nl_p
) ? 3 : 1;
601 for (i
= 0; i
< num
; i
++)
604 for (j
= 0; j
< 2; j
++)
606 len
+= strlen (opts
[i
][j
]);
609 /* Build the string. */
610 ret
= ptr
= (char *) xmalloc (len
);
613 for (i
= 0; i
< num
; i
++)
617 for (j
= 0; j
< 2; j
++)
618 len2
[j
] = (opts
[i
][j
]) ? strlen (opts
[i
][j
]) : 0;
625 if (add_nl_p
&& line_len
+ len2
[0] + len2
[1] > 70)
633 for (j
= 0; j
< 2; j
++)
636 memcpy (ptr
, opts
[i
][j
], len2
[j
]);
643 gcc_assert (ret
+ len
>= ptr
);
648 /* Function that is callable from the debugger to print the current
650 void ATTRIBUTE_UNUSED
651 ix86_debug_options (void)
653 char *opts
= ix86_target_string (ix86_isa_flags
, ix86_isa_flags2
,
654 target_flags
, ix86_target_flags
,
655 ix86_arch_string
, ix86_tune_string
,
656 ix86_fpmath
, prefer_vector_width_type
,
657 ix86_move_max
, ix86_store_max
,
662 fprintf (stderr
, "%s\n\n", opts
);
666 fputs ("<no options>\n\n", stderr
);
671 /* Save the current options */
674 ix86_function_specific_save (struct cl_target_option
*ptr
,
675 struct gcc_options
*opts
,
676 struct gcc_options */
* opts_set */
)
678 ptr
->arch
= ix86_arch
;
679 ptr
->schedule
= ix86_schedule
;
680 ptr
->prefetch_sse
= ix86_prefetch_sse
;
681 ptr
->tune
= ix86_tune
;
682 ptr
->branch_cost
= ix86_branch_cost
;
683 ptr
->tune_defaulted
= ix86_tune_defaulted
;
684 ptr
->arch_specified
= ix86_arch_specified
;
685 ptr
->x_ix86_isa_flags_explicit
= opts
->x_ix86_isa_flags_explicit
;
686 ptr
->x_ix86_isa_flags2_explicit
= opts
->x_ix86_isa_flags2_explicit
;
687 ptr
->x_recip_mask_explicit
= opts
->x_recip_mask_explicit
;
688 ptr
->x_ix86_arch_string
= opts
->x_ix86_arch_string
;
689 ptr
->x_ix86_tune_string
= opts
->x_ix86_tune_string
;
690 ptr
->x_ix86_asm_dialect
= opts
->x_ix86_asm_dialect
;
691 ptr
->x_ix86_branch_cost
= opts
->x_ix86_branch_cost
;
692 ptr
->x_ix86_dump_tunes
= opts
->x_ix86_dump_tunes
;
693 ptr
->x_ix86_force_align_arg_pointer
= opts
->x_ix86_force_align_arg_pointer
;
694 ptr
->x_ix86_force_drap
= opts
->x_ix86_force_drap
;
695 ptr
->x_ix86_recip_name
= opts
->x_ix86_recip_name
;
696 ptr
->x_ix86_section_threshold
= opts
->x_ix86_section_threshold
;
697 ptr
->x_ix86_sse2avx
= opts
->x_ix86_sse2avx
;
698 ptr
->x_ix86_stack_protector_guard
= opts
->x_ix86_stack_protector_guard
;
699 ptr
->x_ix86_stringop_alg
= opts
->x_ix86_stringop_alg
;
700 ptr
->x_ix86_tls_dialect
= opts
->x_ix86_tls_dialect
;
701 ptr
->x_ix86_tune_ctrl_string
= opts
->x_ix86_tune_ctrl_string
;
702 ptr
->x_ix86_tune_memcpy_strategy
= opts
->x_ix86_tune_memcpy_strategy
;
703 ptr
->x_ix86_tune_memset_strategy
= opts
->x_ix86_tune_memset_strategy
;
704 ptr
->x_ix86_tune_no_default
= opts
->x_ix86_tune_no_default
;
706 /* The fields are char but the variables are not; make sure the
707 values fit in the fields. */
708 gcc_assert (ptr
->arch
== ix86_arch
);
709 gcc_assert (ptr
->schedule
== ix86_schedule
);
710 gcc_assert (ptr
->tune
== ix86_tune
);
711 gcc_assert (ptr
->branch_cost
== ix86_branch_cost
);
714 /* Feature tests against the various architecture variations, used to create
715 ix86_arch_features based on the processor mask. */
716 static unsigned HOST_WIDE_INT initial_ix86_arch_features
[X86_ARCH_LAST
] = {
717 /* X86_ARCH_CMOV: Conditional move was added for pentiumpro. */
718 ~(m_386
| m_486
| m_PENT
| m_LAKEMONT
| m_K6
),
720 /* X86_ARCH_CMPXCHG: Compare and exchange was added for 80486. */
723 /* X86_ARCH_CMPXCHG8B: Compare and exchange 8 bytes was added for pentium. */
726 /* X86_ARCH_XADD: Exchange and add was added for 80486. */
729 /* X86_ARCH_BSWAP: Byteswap was added for 80486. */
733 /* This table must be in sync with enum processor_type in i386.h. */
734 static const struct processor_costs
*processor_cost_table
[] =
788 /* Guarantee that the array is aligned with enum processor_type. */
789 STATIC_ASSERT (ARRAY_SIZE (processor_cost_table
) == PROCESSOR_max
);
792 ix86_option_override_internal (bool main_args_p
,
793 struct gcc_options
*opts
,
794 struct gcc_options
*opts_set
);
796 set_ix86_tune_features (struct gcc_options
*opts
,
797 enum processor_type ix86_tune
, bool dump
);
799 /* Restore the current options */
802 ix86_function_specific_restore (struct gcc_options
*opts
,
803 struct gcc_options */
* opts_set */
,
804 struct cl_target_option
*ptr
)
806 enum processor_type old_tune
= ix86_tune
;
807 enum processor_type old_arch
= ix86_arch
;
808 unsigned HOST_WIDE_INT ix86_arch_mask
;
811 /* We don't change -fPIC. */
812 opts
->x_flag_pic
= flag_pic
;
814 ix86_arch
= (enum processor_type
) ptr
->arch
;
815 ix86_schedule
= (enum attr_cpu
) ptr
->schedule
;
816 ix86_tune
= (enum processor_type
) ptr
->tune
;
817 ix86_prefetch_sse
= ptr
->prefetch_sse
;
818 ix86_tune_defaulted
= ptr
->tune_defaulted
;
819 ix86_arch_specified
= ptr
->arch_specified
;
820 opts
->x_ix86_isa_flags_explicit
= ptr
->x_ix86_isa_flags_explicit
;
821 opts
->x_ix86_isa_flags2_explicit
= ptr
->x_ix86_isa_flags2_explicit
;
822 opts
->x_recip_mask_explicit
= ptr
->x_recip_mask_explicit
;
823 opts
->x_ix86_arch_string
= ptr
->x_ix86_arch_string
;
824 opts
->x_ix86_tune_string
= ptr
->x_ix86_tune_string
;
825 opts
->x_ix86_asm_dialect
= ptr
->x_ix86_asm_dialect
;
826 opts
->x_ix86_branch_cost
= ptr
->x_ix86_branch_cost
;
827 opts
->x_ix86_dump_tunes
= ptr
->x_ix86_dump_tunes
;
828 opts
->x_ix86_force_align_arg_pointer
= ptr
->x_ix86_force_align_arg_pointer
;
829 opts
->x_ix86_force_drap
= ptr
->x_ix86_force_drap
;
830 opts
->x_ix86_recip_name
= ptr
->x_ix86_recip_name
;
831 opts
->x_ix86_section_threshold
= ptr
->x_ix86_section_threshold
;
832 opts
->x_ix86_sse2avx
= ptr
->x_ix86_sse2avx
;
833 opts
->x_ix86_stack_protector_guard
= ptr
->x_ix86_stack_protector_guard
;
834 opts
->x_ix86_stringop_alg
= ptr
->x_ix86_stringop_alg
;
835 opts
->x_ix86_tls_dialect
= ptr
->x_ix86_tls_dialect
;
836 opts
->x_ix86_tune_ctrl_string
= ptr
->x_ix86_tune_ctrl_string
;
837 opts
->x_ix86_tune_memcpy_strategy
= ptr
->x_ix86_tune_memcpy_strategy
;
838 opts
->x_ix86_tune_memset_strategy
= ptr
->x_ix86_tune_memset_strategy
;
839 opts
->x_ix86_tune_no_default
= ptr
->x_ix86_tune_no_default
;
840 ix86_tune_cost
= processor_cost_table
[ix86_tune
];
841 /* TODO: ix86_cost should be chosen at instruction or function granuality
842 so for cold code we use size_cost even in !optimize_size compilation. */
843 if (opts
->x_optimize_size
)
844 ix86_cost
= &ix86_size_cost
;
846 ix86_cost
= ix86_tune_cost
;
848 /* Recreate the arch feature tests if the arch changed */
849 if (old_arch
!= ix86_arch
)
851 ix86_arch_mask
= HOST_WIDE_INT_1U
<< ix86_arch
;
852 for (i
= 0; i
< X86_ARCH_LAST
; ++i
)
853 ix86_arch_features
[i
]
854 = !!(initial_ix86_arch_features
[i
] & ix86_arch_mask
);
857 /* Recreate the tune optimization tests */
858 if (old_tune
!= ix86_tune
)
859 set_ix86_tune_features (opts
, ix86_tune
, false);
862 /* Adjust target options after streaming them in. This is mainly about
863 reconciling them with global options. */
866 ix86_function_specific_post_stream_in (struct cl_target_option
*ptr
)
868 /* flag_pic is a global option, but ix86_cmodel is target saved option
869 partly computed from flag_pic. If flag_pic is on, adjust x_ix86_cmodel
870 for PIC, or error out. */
872 switch (ptr
->x_ix86_cmodel
)
875 ptr
->x_ix86_cmodel
= CM_SMALL_PIC
;
879 ptr
->x_ix86_cmodel
= CM_MEDIUM_PIC
;
883 ptr
->x_ix86_cmodel
= CM_LARGE_PIC
;
887 error ("code model %s does not support PIC mode", "kernel");
894 switch (ptr
->x_ix86_cmodel
)
897 ptr
->x_ix86_cmodel
= CM_SMALL
;
901 ptr
->x_ix86_cmodel
= CM_MEDIUM
;
905 ptr
->x_ix86_cmodel
= CM_LARGE
;
913 /* Print the current options */
916 ix86_function_specific_print (FILE *file
, int indent
,
917 struct cl_target_option
*ptr
)
920 = ix86_target_string (ptr
->x_ix86_isa_flags
, ptr
->x_ix86_isa_flags2
,
921 ptr
->x_target_flags
, ptr
->x_ix86_target_flags
,
922 NULL
, NULL
, ptr
->x_ix86_fpmath
,
923 ptr
->x_prefer_vector_width_type
,
924 ptr
->x_ix86_move_max
, ptr
->x_ix86_store_max
,
927 gcc_assert (ptr
->arch
< PROCESSOR_max
);
928 fprintf (file
, "%*sarch = %d (%s)\n",
930 ptr
->arch
, processor_names
[ptr
->arch
]);
932 gcc_assert (ptr
->tune
< PROCESSOR_max
);
933 fprintf (file
, "%*stune = %d (%s)\n",
935 ptr
->tune
, processor_names
[ptr
->tune
]);
937 fprintf (file
, "%*sbranch_cost = %d\n", indent
, "", ptr
->branch_cost
);
941 fprintf (file
, "%*s%s\n", indent
, "", target_string
);
942 free (target_string
);
947 /* Inner function to process the attribute((target(...))), take an argument and
948 set the current options from the argument. If we have a list, recursively go
952 ix86_valid_target_attribute_inner_p (tree fndecl
, tree args
, char *p_strings
[],
953 struct gcc_options
*opts
,
954 struct gcc_options
*opts_set
,
955 struct gcc_options
*enum_opts_set
,
956 bool target_clone_attr
)
961 #define IX86_ATTR_ISA(S,O) { S, sizeof (S)-1, ix86_opt_isa, O, 0 }
962 #define IX86_ATTR_STR(S,O) { S, sizeof (S)-1, ix86_opt_str, O, 0 }
963 #define IX86_ATTR_ENUM(S,O) { S, sizeof (S)-1, ix86_opt_enum, O, 0 }
964 #define IX86_ATTR_YES(S,O,M) { S, sizeof (S)-1, ix86_opt_yes, O, M }
965 #define IX86_ATTR_NO(S,O,M) { S, sizeof (S)-1, ix86_opt_no, O, M }
966 #define IX86_ATTR_IX86_YES(S,O,M) \
967 { S, sizeof (S)-1, ix86_opt_ix86_yes, O, M }
968 #define IX86_ATTR_IX86_NO(S,O,M) \
969 { S, sizeof (S)-1, ix86_opt_ix86_no, O, M }
987 enum ix86_opt_type type
;
992 IX86_ATTR_ISA ("pconfig", OPT_mpconfig
),
993 IX86_ATTR_ISA ("wbnoinvd", OPT_mwbnoinvd
),
994 IX86_ATTR_ISA ("sgx", OPT_msgx
),
995 IX86_ATTR_ISA ("avx5124fmaps", OPT_mavx5124fmaps
),
996 IX86_ATTR_ISA ("avx5124vnniw", OPT_mavx5124vnniw
),
997 IX86_ATTR_ISA ("avx512vpopcntdq", OPT_mavx512vpopcntdq
),
998 IX86_ATTR_ISA ("avx512vbmi2", OPT_mavx512vbmi2
),
999 IX86_ATTR_ISA ("avx512vnni", OPT_mavx512vnni
),
1000 IX86_ATTR_ISA ("avx512bitalg", OPT_mavx512bitalg
),
1001 IX86_ATTR_ISA ("avx512vp2intersect", OPT_mavx512vp2intersect
),
1003 IX86_ATTR_ISA ("avx512vbmi", OPT_mavx512vbmi
),
1004 IX86_ATTR_ISA ("avx512ifma", OPT_mavx512ifma
),
1005 IX86_ATTR_ISA ("avx512vl", OPT_mavx512vl
),
1006 IX86_ATTR_ISA ("avx512bw", OPT_mavx512bw
),
1007 IX86_ATTR_ISA ("avx512dq", OPT_mavx512dq
),
1008 IX86_ATTR_ISA ("avx512er", OPT_mavx512er
),
1009 IX86_ATTR_ISA ("avx512pf", OPT_mavx512pf
),
1010 IX86_ATTR_ISA ("avx512cd", OPT_mavx512cd
),
1011 IX86_ATTR_ISA ("avx512f", OPT_mavx512f
),
1012 IX86_ATTR_ISA ("avx2", OPT_mavx2
),
1013 IX86_ATTR_ISA ("fma", OPT_mfma
),
1014 IX86_ATTR_ISA ("xop", OPT_mxop
),
1015 IX86_ATTR_ISA ("fma4", OPT_mfma4
),
1016 IX86_ATTR_ISA ("f16c", OPT_mf16c
),
1017 IX86_ATTR_ISA ("avx", OPT_mavx
),
1018 IX86_ATTR_ISA ("sse4", OPT_msse4
),
1019 IX86_ATTR_ISA ("sse4.2", OPT_msse4_2
),
1020 IX86_ATTR_ISA ("sse4.1", OPT_msse4_1
),
1021 IX86_ATTR_ISA ("sse4a", OPT_msse4a
),
1022 IX86_ATTR_ISA ("ssse3", OPT_mssse3
),
1023 IX86_ATTR_ISA ("sse3", OPT_msse3
),
1024 IX86_ATTR_ISA ("aes", OPT_maes
),
1025 IX86_ATTR_ISA ("sha", OPT_msha
),
1026 IX86_ATTR_ISA ("pclmul", OPT_mpclmul
),
1027 IX86_ATTR_ISA ("sse2", OPT_msse2
),
1028 IX86_ATTR_ISA ("sse", OPT_msse
),
1029 IX86_ATTR_ISA ("3dnowa", OPT_m3dnowa
),
1030 IX86_ATTR_ISA ("3dnow", OPT_m3dnow
),
1031 IX86_ATTR_ISA ("mmx", OPT_mmmx
),
1032 IX86_ATTR_ISA ("rtm", OPT_mrtm
),
1033 IX86_ATTR_ISA ("prfchw", OPT_mprfchw
),
1034 IX86_ATTR_ISA ("rdseed", OPT_mrdseed
),
1035 IX86_ATTR_ISA ("adx", OPT_madx
),
1036 IX86_ATTR_ISA ("prefetchwt1", OPT_mprefetchwt1
),
1037 IX86_ATTR_ISA ("clflushopt", OPT_mclflushopt
),
1038 IX86_ATTR_ISA ("xsaves", OPT_mxsaves
),
1039 IX86_ATTR_ISA ("xsavec", OPT_mxsavec
),
1040 IX86_ATTR_ISA ("xsaveopt", OPT_mxsaveopt
),
1041 IX86_ATTR_ISA ("xsave", OPT_mxsave
),
1042 IX86_ATTR_ISA ("abm", OPT_mabm
),
1043 IX86_ATTR_ISA ("bmi", OPT_mbmi
),
1044 IX86_ATTR_ISA ("bmi2", OPT_mbmi2
),
1045 IX86_ATTR_ISA ("lzcnt", OPT_mlzcnt
),
1046 IX86_ATTR_ISA ("tbm", OPT_mtbm
),
1047 IX86_ATTR_ISA ("popcnt", OPT_mpopcnt
),
1048 IX86_ATTR_ISA ("cx16", OPT_mcx16
),
1049 IX86_ATTR_ISA ("sahf", OPT_msahf
),
1050 IX86_ATTR_ISA ("movbe", OPT_mmovbe
),
1051 IX86_ATTR_ISA ("crc32", OPT_mcrc32
),
1052 IX86_ATTR_ISA ("fsgsbase", OPT_mfsgsbase
),
1053 IX86_ATTR_ISA ("rdrnd", OPT_mrdrnd
),
1054 IX86_ATTR_ISA ("mwaitx", OPT_mmwaitx
),
1055 IX86_ATTR_ISA ("mwait", OPT_mmwait
),
1056 IX86_ATTR_ISA ("clzero", OPT_mclzero
),
1057 IX86_ATTR_ISA ("pku", OPT_mpku
),
1058 IX86_ATTR_ISA ("lwp", OPT_mlwp
),
1059 IX86_ATTR_ISA ("hle", OPT_mhle
),
1060 IX86_ATTR_ISA ("fxsr", OPT_mfxsr
),
1061 IX86_ATTR_ISA ("clwb", OPT_mclwb
),
1062 IX86_ATTR_ISA ("rdpid", OPT_mrdpid
),
1063 IX86_ATTR_ISA ("gfni", OPT_mgfni
),
1064 IX86_ATTR_ISA ("shstk", OPT_mshstk
),
1065 IX86_ATTR_ISA ("vaes", OPT_mvaes
),
1066 IX86_ATTR_ISA ("vpclmulqdq", OPT_mvpclmulqdq
),
1067 IX86_ATTR_ISA ("movdiri", OPT_mmovdiri
),
1068 IX86_ATTR_ISA ("movdir64b", OPT_mmovdir64b
),
1069 IX86_ATTR_ISA ("waitpkg", OPT_mwaitpkg
),
1070 IX86_ATTR_ISA ("cldemote", OPT_mcldemote
),
1071 IX86_ATTR_ISA ("uintr", OPT_muintr
),
1072 IX86_ATTR_ISA ("ptwrite", OPT_mptwrite
),
1073 IX86_ATTR_ISA ("kl", OPT_mkl
),
1074 IX86_ATTR_ISA ("widekl", OPT_mwidekl
),
1075 IX86_ATTR_ISA ("avx512bf16", OPT_mavx512bf16
),
1076 IX86_ATTR_ISA ("enqcmd", OPT_menqcmd
),
1077 IX86_ATTR_ISA ("serialize", OPT_mserialize
),
1078 IX86_ATTR_ISA ("tsxldtrk", OPT_mtsxldtrk
),
1079 IX86_ATTR_ISA ("amx-tile", OPT_mamx_tile
),
1080 IX86_ATTR_ISA ("amx-int8", OPT_mamx_int8
),
1081 IX86_ATTR_ISA ("amx-bf16", OPT_mamx_bf16
),
1082 IX86_ATTR_ISA ("hreset", OPT_mhreset
),
1083 IX86_ATTR_ISA ("avxvnni", OPT_mavxvnni
),
1084 IX86_ATTR_ISA ("avx512fp16", OPT_mavx512fp16
),
1085 IX86_ATTR_ISA ("avxifma", OPT_mavxifma
),
1086 IX86_ATTR_ISA ("avxvnniint8", OPT_mavxvnniint8
),
1087 IX86_ATTR_ISA ("avxneconvert", OPT_mavxneconvert
),
1088 IX86_ATTR_ISA ("cmpccxadd", OPT_mcmpccxadd
),
1089 IX86_ATTR_ISA ("amx-fp16", OPT_mamx_fp16
),
1090 IX86_ATTR_ISA ("prefetchi", OPT_mprefetchi
),
1091 IX86_ATTR_ISA ("raoint", OPT_mraoint
),
1094 IX86_ATTR_ENUM ("fpmath=", OPT_mfpmath_
),
1095 IX86_ATTR_ENUM ("prefer-vector-width=", OPT_mprefer_vector_width_
),
1097 /* string options */
1098 IX86_ATTR_STR ("arch=", IX86_FUNCTION_SPECIFIC_ARCH
),
1099 IX86_ATTR_STR ("tune=", IX86_FUNCTION_SPECIFIC_TUNE
),
1102 IX86_ATTR_YES ("cld",
1106 IX86_ATTR_NO ("fancy-math-387",
1107 OPT_mfancy_math_387
,
1108 MASK_NO_FANCY_MATH_387
),
1110 IX86_ATTR_YES ("ieee-fp",
1114 IX86_ATTR_YES ("inline-all-stringops",
1115 OPT_minline_all_stringops
,
1116 MASK_INLINE_ALL_STRINGOPS
),
1118 IX86_ATTR_YES ("inline-stringops-dynamically",
1119 OPT_minline_stringops_dynamically
,
1120 MASK_INLINE_STRINGOPS_DYNAMICALLY
),
1122 IX86_ATTR_NO ("align-stringops",
1123 OPT_mno_align_stringops
,
1124 MASK_NO_ALIGN_STRINGOPS
),
1126 IX86_ATTR_YES ("recip",
1130 IX86_ATTR_IX86_YES ("general-regs-only",
1131 OPT_mgeneral_regs_only
,
1132 OPTION_MASK_GENERAL_REGS_ONLY
),
1134 IX86_ATTR_YES ("relax-cmpxchg-loop",
1135 OPT_mrelax_cmpxchg_loop
,
1136 MASK_RELAX_CMPXCHG_LOOP
),
1140 = fndecl
== NULL
? UNKNOWN_LOCATION
: DECL_SOURCE_LOCATION (fndecl
);
1141 const char *attr_name
= target_clone_attr
? "target_clone" : "target";
1143 /* If this is a list, recurse to get the options. */
1144 if (TREE_CODE (args
) == TREE_LIST
)
1146 for (; args
; args
= TREE_CHAIN (args
))
1147 if (TREE_VALUE (args
)
1148 && !ix86_valid_target_attribute_inner_p (fndecl
, TREE_VALUE (args
),
1149 p_strings
, opts
, opts_set
,
1157 else if (TREE_CODE (args
) != STRING_CST
)
1159 error_at (loc
, "attribute %qs argument is not a string", attr_name
);
1163 /* Handle multiple arguments separated by commas. */
1164 next_optstr
= ASTRDUP (TREE_STRING_POINTER (args
));
1166 while (next_optstr
&& *next_optstr
!= '\0')
1168 char *p
= next_optstr
;
1170 char *comma
= strchr (next_optstr
, ',');
1171 size_t len
, opt_len
;
1176 enum ix86_opt_type type
= ix86_opt_unknown
;
1182 len
= comma
- next_optstr
;
1183 next_optstr
= comma
+ 1;
1191 /* Recognize no-xxx. */
1192 if (len
> 3 && p
[0] == 'n' && p
[1] == 'o' && p
[2] == '-')
1201 /* Find the option. */
1204 for (i
= 0; i
< ARRAY_SIZE (attrs
); i
++)
1206 type
= attrs
[i
].type
;
1207 opt_len
= attrs
[i
].len
;
1208 if (ch
== attrs
[i
].string
[0]
1209 && ((type
!= ix86_opt_str
&& type
!= ix86_opt_enum
)
1212 && memcmp (p
, attrs
[i
].string
, opt_len
) == 0)
1215 mask
= attrs
[i
].mask
;
1220 /* Process the option. */
1223 error_at (loc
, "attribute %qs argument %qs is unknown",
1228 else if (type
== ix86_opt_isa
)
1230 struct cl_decoded_option decoded
;
1232 generate_option (opt
, NULL
, opt_set_p
, CL_TARGET
, &decoded
);
1233 ix86_handle_option (opts
, opts_set
,
1234 &decoded
, input_location
);
1237 else if (type
== ix86_opt_yes
|| type
== ix86_opt_no
)
1239 if (type
== ix86_opt_no
)
1240 opt_set_p
= !opt_set_p
;
1243 opts
->x_target_flags
|= mask
;
1245 opts
->x_target_flags
&= ~mask
;
1248 else if (type
== ix86_opt_ix86_yes
|| type
== ix86_opt_ix86_no
)
1250 if (mask
== OPTION_MASK_GENERAL_REGS_ONLY
)
1254 error_at (loc
, "pragma or attribute %<target(\"%s\")%> "
1255 "does not allow a negated form", p
);
1259 if (type
!= ix86_opt_ix86_yes
)
1262 opts
->x_ix86_target_flags
|= mask
;
1264 struct cl_decoded_option decoded
;
1265 generate_option (opt
, NULL
, opt_set_p
, CL_TARGET
,
1267 ix86_handle_option (opts
, opts_set
, &decoded
,
1272 if (type
== ix86_opt_ix86_no
)
1273 opt_set_p
= !opt_set_p
;
1276 opts
->x_ix86_target_flags
|= mask
;
1278 opts
->x_ix86_target_flags
&= ~mask
;
1282 else if (type
== ix86_opt_str
)
1286 error_at (loc
, "attribute value %qs was already specified "
1287 "in %qs attribute", orig_p
, attr_name
);
1292 p_strings
[opt
] = xstrdup (p
+ opt_len
);
1293 if (opt
== IX86_FUNCTION_SPECIFIC_ARCH
)
1295 /* If arch= is set, clear all bits in x_ix86_isa_flags,
1296 except for ISA_64BIT, ABI_64, ABI_X32, and CODE16
1297 and all bits in x_ix86_isa_flags2. */
1298 opts
->x_ix86_isa_flags
&= (OPTION_MASK_ISA_64BIT
1299 | OPTION_MASK_ABI_64
1300 | OPTION_MASK_ABI_X32
1301 | OPTION_MASK_CODE16
);
1302 opts
->x_ix86_isa_flags_explicit
&= (OPTION_MASK_ISA_64BIT
1303 | OPTION_MASK_ABI_64
1304 | OPTION_MASK_ABI_X32
1305 | OPTION_MASK_CODE16
);
1306 opts
->x_ix86_isa_flags2
= 0;
1307 opts
->x_ix86_isa_flags2_explicit
= 0;
1312 else if (type
== ix86_opt_enum
)
1317 arg_ok
= opt_enum_arg_to_value (opt
, p
+ opt_len
, &value
, CL_TARGET
);
1319 set_option (opts
, enum_opts_set
, opt
, value
,
1320 p
+ opt_len
, DK_UNSPECIFIED
, input_location
,
1324 error_at (loc
, "attribute value %qs is unknown in %qs attribute",
1337 /* Release allocated strings. */
1339 release_options_strings (char **option_strings
)
1341 /* Free up memory allocated to hold the strings */
1342 for (unsigned i
= 0; i
< IX86_FUNCTION_SPECIFIC_MAX
; i
++)
1343 free (option_strings
[i
]);
1346 /* Return a TARGET_OPTION_NODE tree of the target options listed or NULL. */
1349 ix86_valid_target_attribute_tree (tree fndecl
, tree args
,
1350 struct gcc_options
*opts
,
1351 struct gcc_options
*opts_set
,
1352 bool target_clone_attr
)
1354 const char *orig_arch_string
= opts
->x_ix86_arch_string
;
1355 const char *orig_tune_string
= opts
->x_ix86_tune_string
;
1356 enum fpmath_unit orig_fpmath_set
= opts_set
->x_ix86_fpmath
;
1357 enum prefer_vector_width orig_pvw_set
= opts_set
->x_prefer_vector_width_type
;
1358 enum prefer_vector_width orig_ix86_move_max_set
1359 = opts_set
->x_ix86_move_max
;
1360 enum prefer_vector_width orig_ix86_store_max_set
1361 = opts_set
->x_ix86_store_max
;
1362 int orig_tune_defaulted
= ix86_tune_defaulted
;
1363 int orig_arch_specified
= ix86_arch_specified
;
1364 char *option_strings
[IX86_FUNCTION_SPECIFIC_MAX
] = { NULL
, NULL
};
1366 struct cl_target_option
*def
1367 = TREE_TARGET_OPTION (target_option_default_node
);
1368 struct gcc_options enum_opts_set
;
1370 memset (&enum_opts_set
, 0, sizeof (enum_opts_set
));
1372 /* Process each of the options on the chain. */
1373 if (!ix86_valid_target_attribute_inner_p (fndecl
, args
, option_strings
, opts
,
1374 opts_set
, &enum_opts_set
,
1376 return error_mark_node
;
1378 /* If the changed options are different from the default, rerun
1379 ix86_option_override_internal, and then save the options away.
1380 The string options are attribute options, and will be undone
1381 when we copy the save structure. */
1382 if (opts
->x_ix86_isa_flags
!= def
->x_ix86_isa_flags
1383 || opts
->x_ix86_isa_flags2
!= def
->x_ix86_isa_flags2
1384 || opts
->x_target_flags
!= def
->x_target_flags
1385 || option_strings
[IX86_FUNCTION_SPECIFIC_ARCH
]
1386 || option_strings
[IX86_FUNCTION_SPECIFIC_TUNE
]
1387 || enum_opts_set
.x_ix86_fpmath
1388 || enum_opts_set
.x_prefer_vector_width_type
)
1390 /* If we are using the default tune= or arch=, undo the string assigned,
1391 and use the default. */
1392 if (option_strings
[IX86_FUNCTION_SPECIFIC_ARCH
])
1393 opts
->x_ix86_arch_string
1394 = ggc_strdup (option_strings
[IX86_FUNCTION_SPECIFIC_ARCH
]);
1395 else if (!orig_arch_specified
)
1396 opts
->x_ix86_arch_string
= NULL
;
1398 if (option_strings
[IX86_FUNCTION_SPECIFIC_TUNE
])
1399 opts
->x_ix86_tune_string
1400 = ggc_strdup (option_strings
[IX86_FUNCTION_SPECIFIC_TUNE
]);
1401 else if (orig_tune_defaulted
)
1402 opts
->x_ix86_tune_string
= NULL
;
1404 /* If fpmath= is not set, and we now have sse2 on 32-bit, use it. */
1405 if (enum_opts_set
.x_ix86_fpmath
)
1406 opts_set
->x_ix86_fpmath
= (enum fpmath_unit
) 1;
1407 if (enum_opts_set
.x_prefer_vector_width_type
)
1408 opts_set
->x_prefer_vector_width_type
= (enum prefer_vector_width
) 1;
1410 /* Do any overrides, such as arch=xxx, or tune=xxx support. */
1411 bool r
= ix86_option_override_internal (false, opts
, opts_set
);
1414 release_options_strings (option_strings
);
1415 return error_mark_node
;
1418 /* Add any builtin functions with the new isa if any. */
1419 ix86_add_new_builtins (opts
->x_ix86_isa_flags
, opts
->x_ix86_isa_flags2
);
1421 enum excess_precision orig_ix86_excess_precision
1422 = opts
->x_ix86_excess_precision
;
1423 bool orig_ix86_unsafe_math_optimizations
1424 = opts
->x_ix86_unsafe_math_optimizations
;
1425 opts
->x_ix86_excess_precision
= opts
->x_flag_excess_precision
;
1426 opts
->x_ix86_unsafe_math_optimizations
1427 = opts
->x_flag_unsafe_math_optimizations
;
1429 /* Save the current options unless we are validating options for
1431 t
= build_target_option_node (opts
, opts_set
);
1433 opts
->x_ix86_arch_string
= orig_arch_string
;
1434 opts
->x_ix86_tune_string
= orig_tune_string
;
1435 opts_set
->x_ix86_fpmath
= orig_fpmath_set
;
1436 opts_set
->x_prefer_vector_width_type
= orig_pvw_set
;
1437 opts_set
->x_ix86_move_max
= orig_ix86_move_max_set
;
1438 opts_set
->x_ix86_store_max
= orig_ix86_store_max_set
;
1439 opts
->x_ix86_excess_precision
= orig_ix86_excess_precision
;
1440 opts
->x_ix86_unsafe_math_optimizations
1441 = orig_ix86_unsafe_math_optimizations
;
1443 release_options_strings (option_strings
);
1449 static GTY(()) tree target_attribute_cache
[3];
1451 /* Hook to validate attribute((target("string"))). */
1454 ix86_valid_target_attribute_p (tree fndecl
,
1455 tree
ARG_UNUSED (name
),
1459 struct gcc_options func_options
, func_options_set
;
1460 tree new_target
, new_optimize
;
1463 /* attribute((target("default"))) does nothing, beyond
1464 affecting multi-versioning. */
1465 if (TREE_VALUE (args
)
1466 && TREE_CODE (TREE_VALUE (args
)) == STRING_CST
1467 && TREE_CHAIN (args
) == NULL_TREE
1468 && strcmp (TREE_STRING_POINTER (TREE_VALUE (args
)), "default") == 0)
1471 if ((DECL_FUNCTION_SPECIFIC_TARGET (fndecl
) == target_attribute_cache
[1]
1472 || DECL_FUNCTION_SPECIFIC_TARGET (fndecl
) == NULL_TREE
)
1473 && (DECL_FUNCTION_SPECIFIC_OPTIMIZATION (fndecl
)
1474 == target_attribute_cache
[2]
1475 || DECL_FUNCTION_SPECIFIC_OPTIMIZATION (fndecl
) == NULL_TREE
)
1476 && simple_cst_list_equal (args
, target_attribute_cache
[0]))
1478 DECL_FUNCTION_SPECIFIC_TARGET (fndecl
) = target_attribute_cache
[1];
1479 DECL_FUNCTION_SPECIFIC_OPTIMIZATION (fndecl
)
1480 = target_attribute_cache
[2];
1484 tree old_optimize
= build_optimization_node (&global_options
,
1485 &global_options_set
);
1487 /* Get the optimization options of the current function. */
1488 tree func_optimize
= DECL_FUNCTION_SPECIFIC_OPTIMIZATION (fndecl
);
1491 func_optimize
= old_optimize
;
1493 /* Init func_options. */
1494 memset (&func_options
, 0, sizeof (func_options
));
1495 init_options_struct (&func_options
, NULL
);
1496 lang_hooks
.init_options_struct (&func_options
);
1497 memset (&func_options_set
, 0, sizeof (func_options_set
));
1499 cl_optimization_restore (&func_options
, &func_options_set
,
1500 TREE_OPTIMIZATION (func_optimize
));
1502 /* Initialize func_options to the default before its target options can
1504 tree old_target
= DECL_FUNCTION_SPECIFIC_TARGET (fndecl
);
1505 if (old_target
== NULL_TREE
)
1506 old_target
= target_option_default_node
;
1507 cl_target_option_restore (&func_options
, &func_options_set
,
1508 TREE_TARGET_OPTION (old_target
));
1510 /* FLAGS == 1 is used for target_clones attribute. */
1512 = ix86_valid_target_attribute_tree (fndecl
, args
, &func_options
,
1513 &func_options_set
, flags
== 1);
1515 new_optimize
= build_optimization_node (&func_options
, &func_options_set
);
1517 if (new_target
== error_mark_node
)
1520 else if (new_target
)
1522 if (DECL_FUNCTION_SPECIFIC_TARGET (fndecl
) == NULL_TREE
1523 && DECL_FUNCTION_SPECIFIC_OPTIMIZATION (fndecl
) == NULL_TREE
)
1525 target_attribute_cache
[0] = copy_list (args
);
1526 target_attribute_cache
[1] = new_target
;
1527 target_attribute_cache
[2]
1528 = old_optimize
!= new_optimize
? new_optimize
: NULL_TREE
;
1531 DECL_FUNCTION_SPECIFIC_TARGET (fndecl
) = new_target
;
1533 if (old_optimize
!= new_optimize
)
1534 DECL_FUNCTION_SPECIFIC_OPTIMIZATION (fndecl
) = new_optimize
;
1540 const char *stringop_alg_names
[] = {
1541 #define DEF_ALG(alg, name) #name,
1542 #include "stringop.def"
1546 /* Parse parameter string passed to -mmemcpy-strategy= or -mmemset-strategy=.
1547 The string is of the following form (or comma separated list of it):
1549 strategy_alg:max_size:[align|noalign]
1551 where the full size range for the strategy is either [0, max_size] or
1552 [min_size, max_size], in which min_size is the max_size + 1 of the
1553 preceding range. The last size range must have max_size == -1.
1558 -mmemcpy-strategy=libcall:-1:noalign
1560 this is equivalent to (for known size memcpy) -mstringop-strategy=libcall
1564 -mmemset-strategy=rep_8byte:16:noalign,vector_loop:2048:align,libcall:-1:noalign
1566 This is to tell the compiler to use the following strategy for memset
1567 1) when the expected size is between [1, 16], use rep_8byte strategy;
1568 2) when the size is between [17, 2048], use vector_loop;
1569 3) when the size is > 2048, use libcall. */
1571 struct stringop_size_range
1579 ix86_parse_stringop_strategy_string (char *strategy_str
, bool is_memset
)
1581 const struct stringop_algs
*default_algs
;
1582 stringop_size_range input_ranges
[MAX_STRINGOP_ALGS
];
1583 char *curr_range_str
, *next_range_str
;
1584 const char *opt
= is_memset
? "-mmemset_strategy=" : "-mmemcpy_strategy=";
1588 default_algs
= &ix86_cost
->memset
[TARGET_64BIT
!= 0];
1590 default_algs
= &ix86_cost
->memcpy
[TARGET_64BIT
!= 0];
1592 curr_range_str
= strategy_str
;
1599 next_range_str
= strchr (curr_range_str
, ',');
1601 *next_range_str
++ = '\0';
1603 if (sscanf (curr_range_str
, "%20[^:]:%d:%10s", alg_name
, &maxs
,
1606 error ("wrong argument %qs to option %qs", curr_range_str
, opt
);
1610 if (n
> 0 && (maxs
< (input_ranges
[n
- 1].max
+ 1) && maxs
!= -1))
1612 error ("size ranges of option %qs should be increasing", opt
);
1616 for (i
= 0; i
< last_alg
; i
++)
1617 if (!strcmp (alg_name
, stringop_alg_names
[i
]))
1622 error ("wrong strategy name %qs specified for option %qs",
1625 auto_vec
<const char *> candidates
;
1626 for (i
= 0; i
< last_alg
; i
++)
1627 if ((stringop_alg
) i
!= rep_prefix_8_byte
|| TARGET_64BIT
)
1628 candidates
.safe_push (stringop_alg_names
[i
]);
1632 = candidates_list_and_hint (alg_name
, s
, candidates
);
1634 inform (input_location
,
1635 "valid arguments to %qs are: %s; did you mean %qs?",
1638 inform (input_location
, "valid arguments to %qs are: %s",
1644 if ((stringop_alg
) i
== rep_prefix_8_byte
1647 /* rep; movq isn't available in 32-bit code. */
1648 error ("strategy name %qs specified for option %qs "
1649 "not supported for 32-bit code", alg_name
, opt
);
1653 input_ranges
[n
].max
= maxs
;
1654 input_ranges
[n
].alg
= (stringop_alg
) i
;
1655 if (!strcmp (align
, "align"))
1656 input_ranges
[n
].noalign
= false;
1657 else if (!strcmp (align
, "noalign"))
1658 input_ranges
[n
].noalign
= true;
1661 error ("unknown alignment %qs specified for option %qs", align
, opt
);
1665 curr_range_str
= next_range_str
;
1667 while (curr_range_str
);
1669 if (input_ranges
[n
- 1].max
!= -1)
1671 error ("the max value for the last size range should be -1"
1672 " for option %qs", opt
);
1676 if (n
> MAX_STRINGOP_ALGS
)
1678 error ("too many size ranges specified in option %qs", opt
);
1682 /* Now override the default algs array. */
1683 for (i
= 0; i
< n
; i
++)
1685 *const_cast<int *>(&default_algs
->size
[i
].max
) = input_ranges
[i
].max
;
1686 *const_cast<stringop_alg
*>(&default_algs
->size
[i
].alg
)
1687 = input_ranges
[i
].alg
;
1688 *const_cast<int *>(&default_algs
->size
[i
].noalign
)
1689 = input_ranges
[i
].noalign
;
1694 /* parse -mtune-ctrl= option. When DUMP is true,
1695 print the features that are explicitly set. */
1698 parse_mtune_ctrl_str (struct gcc_options
*opts
, bool dump
)
1700 if (!opts
->x_ix86_tune_ctrl_string
)
1703 char *next_feature_string
= NULL
;
1704 char *curr_feature_string
= xstrdup (opts
->x_ix86_tune_ctrl_string
);
1705 char *orig
= curr_feature_string
;
1711 next_feature_string
= strchr (curr_feature_string
, ',');
1712 if (next_feature_string
)
1713 *next_feature_string
++ = '\0';
1714 if (*curr_feature_string
== '^')
1716 curr_feature_string
++;
1719 for (i
= 0; i
< X86_TUNE_LAST
; i
++)
1721 if (!strcmp (curr_feature_string
, ix86_tune_feature_names
[i
]))
1723 ix86_tune_features
[i
] = !clear
;
1725 fprintf (stderr
, "Explicitly %s feature %s\n",
1726 clear
? "clear" : "set", ix86_tune_feature_names
[i
]);
1730 if (i
== X86_TUNE_LAST
)
1731 error ("unknown parameter to option %<-mtune-ctrl%>: %s",
1732 clear
? curr_feature_string
- 1 : curr_feature_string
);
1733 curr_feature_string
= next_feature_string
;
1735 while (curr_feature_string
);
1739 /* Helper function to set ix86_tune_features. IX86_TUNE is the
1743 set_ix86_tune_features (struct gcc_options
*opts
,
1744 enum processor_type ix86_tune
, bool dump
)
1746 unsigned HOST_WIDE_INT ix86_tune_mask
= HOST_WIDE_INT_1U
<< ix86_tune
;
1749 for (i
= 0; i
< X86_TUNE_LAST
; ++i
)
1751 if (ix86_tune_no_default
)
1752 ix86_tune_features
[i
] = 0;
1754 ix86_tune_features
[i
]
1755 = !!(initial_ix86_tune_features
[i
] & ix86_tune_mask
);
1760 fprintf (stderr
, "List of x86 specific tuning parameter names:\n");
1761 for (i
= 0; i
< X86_TUNE_LAST
; i
++)
1762 fprintf (stderr
, "%s : %s\n", ix86_tune_feature_names
[i
],
1763 ix86_tune_features
[i
] ? "on" : "off");
1766 parse_mtune_ctrl_str (opts
, dump
);
1770 /* Default align_* from the processor table. */
1773 ix86_default_align (struct gcc_options
*opts
)
1775 /* -falign-foo without argument: supply one. */
1776 if (opts
->x_flag_align_loops
&& !opts
->x_str_align_loops
)
1777 opts
->x_str_align_loops
= processor_cost_table
[ix86_tune
]->align_loop
;
1778 if (opts
->x_flag_align_jumps
&& !opts
->x_str_align_jumps
)
1779 opts
->x_str_align_jumps
= processor_cost_table
[ix86_tune
]->align_jump
;
1780 if (opts
->x_flag_align_labels
&& !opts
->x_str_align_labels
)
1781 opts
->x_str_align_labels
= processor_cost_table
[ix86_tune
]->align_label
;
1782 if (opts
->x_flag_align_functions
&& !opts
->x_str_align_functions
)
1783 opts
->x_str_align_functions
= processor_cost_table
[ix86_tune
]->align_func
;
1786 #ifndef USE_IX86_FRAME_POINTER
1787 #define USE_IX86_FRAME_POINTER 0
1790 /* (Re)compute option overrides affected by optimization levels in
1791 target-specific ways. */
1794 ix86_recompute_optlev_based_flags (struct gcc_options
*opts
,
1795 struct gcc_options
*opts_set
)
1797 /* Set the default values for switches whose default depends on TARGET_64BIT
1798 in case they weren't overwritten by command line options. */
1799 if (TARGET_64BIT_P (opts
->x_ix86_isa_flags
))
1801 if (opts
->x_optimize
>= 1)
1802 SET_OPTION_IF_UNSET (opts
, opts_set
, flag_omit_frame_pointer
,
1803 !USE_IX86_FRAME_POINTER
);
1804 if (opts
->x_flag_asynchronous_unwind_tables
1805 && TARGET_64BIT_MS_ABI
)
1806 SET_OPTION_IF_UNSET (opts
, opts_set
, flag_unwind_tables
, 1);
1807 if (opts
->x_flag_asynchronous_unwind_tables
== 2)
1808 opts
->x_flag_unwind_tables
1809 = opts
->x_flag_asynchronous_unwind_tables
= 1;
1810 if (opts
->x_flag_pcc_struct_return
== 2)
1811 opts
->x_flag_pcc_struct_return
= 0;
1815 if (opts
->x_optimize
>= 1)
1816 SET_OPTION_IF_UNSET (opts
, opts_set
, flag_omit_frame_pointer
,
1817 !(USE_IX86_FRAME_POINTER
|| opts
->x_optimize_size
));
1818 if (opts
->x_flag_asynchronous_unwind_tables
== 2)
1819 opts
->x_flag_asynchronous_unwind_tables
= !USE_IX86_FRAME_POINTER
;
1820 if (opts
->x_flag_pcc_struct_return
== 2)
1822 /* Intel MCU psABI specifies that -freg-struct-return should
1823 be on. Instead of setting DEFAULT_PCC_STRUCT_RETURN to 0,
1824 we check -miamcu so that -freg-struct-return is always
1825 turned on if -miamcu is used. */
1826 if (TARGET_IAMCU_P (opts
->x_target_flags
))
1827 opts
->x_flag_pcc_struct_return
= 0;
1829 opts
->x_flag_pcc_struct_return
= DEFAULT_PCC_STRUCT_RETURN
;
1834 /* Implement TARGET_OVERRIDE_OPTIONS_AFTER_CHANGE hook. */
1837 ix86_override_options_after_change (void)
1839 /* Default align_* from the processor table. */
1840 ix86_default_align (&global_options
);
1842 ix86_recompute_optlev_based_flags (&global_options
, &global_options_set
);
1844 /* Disable unrolling small loops when there's explicit
1845 -f{,no}unroll-loop. */
1846 if ((OPTION_SET_P (flag_unroll_loops
))
1847 || (OPTION_SET_P (flag_unroll_all_loops
)
1848 && flag_unroll_all_loops
))
1850 if (!OPTION_SET_P (ix86_unroll_only_small_loops
))
1851 ix86_unroll_only_small_loops
= 0;
1852 /* Re-enable -frename-registers and -fweb if funroll-loops
1854 if (!OPTION_SET_P (flag_web
))
1855 flag_web
= flag_unroll_loops
;
1856 if (!OPTION_SET_P (flag_rename_registers
))
1857 flag_rename_registers
= flag_unroll_loops
;
1858 /* -fcunroll-grow-size default follws -f[no]-unroll-loops. */
1859 if (!OPTION_SET_P (flag_cunroll_grow_size
))
1860 flag_cunroll_grow_size
= flag_unroll_loops
1866 if (!OPTION_SET_P (flag_cunroll_grow_size
))
1867 flag_cunroll_grow_size
= flag_peel_loops
|| optimize
>= 3;
1872 /* Clear stack slot assignments remembered from previous functions.
1873 This is called from INIT_EXPANDERS once before RTL is emitted for each
1876 static struct machine_function
*
1877 ix86_init_machine_status (void)
1879 struct machine_function
*f
;
1881 f
= ggc_cleared_alloc
<machine_function
> ();
1882 f
->call_abi
= ix86_abi
;
1883 f
->stack_frame_required
= true;
1889 /* Override various settings based on options. If MAIN_ARGS_P, the
1890 options are from the command line, otherwise they are from
1891 attributes. Return true if there's an error related to march
1895 ix86_option_override_internal (bool main_args_p
,
1896 struct gcc_options
*opts
,
1897 struct gcc_options
*opts_set
)
1900 unsigned HOST_WIDE_INT ix86_arch_mask
;
1901 const bool ix86_tune_specified
= (opts
->x_ix86_tune_string
!= NULL
);
1903 /* -mrecip options. */
1906 const char *string
; /* option name */
1907 unsigned int mask
; /* mask bits to set */
1909 const recip_options
[] =
1911 { "all", RECIP_MASK_ALL
},
1912 { "none", RECIP_MASK_NONE
},
1913 { "div", RECIP_MASK_DIV
},
1914 { "sqrt", RECIP_MASK_SQRT
},
1915 { "vec-div", RECIP_MASK_VEC_DIV
},
1916 { "vec-sqrt", RECIP_MASK_VEC_SQRT
},
1920 /* Turn off both OPTION_MASK_ABI_64 and OPTION_MASK_ABI_X32 if
1921 TARGET_64BIT_DEFAULT is true and TARGET_64BIT is false. */
1922 if (TARGET_64BIT_DEFAULT
&& !TARGET_64BIT_P (opts
->x_ix86_isa_flags
))
1923 opts
->x_ix86_isa_flags
&= ~(OPTION_MASK_ABI_64
| OPTION_MASK_ABI_X32
);
1924 #ifdef TARGET_BI_ARCH
1927 #if TARGET_BI_ARCH == 1
1928 /* When TARGET_BI_ARCH == 1, by default, OPTION_MASK_ABI_64
1929 is on and OPTION_MASK_ABI_X32 is off. We turn off
1930 OPTION_MASK_ABI_64 if OPTION_MASK_ABI_X32 is turned on by
1932 if (TARGET_X32_P (opts
->x_ix86_isa_flags
))
1933 opts
->x_ix86_isa_flags
&= ~OPTION_MASK_ABI_64
;
1935 /* When TARGET_BI_ARCH == 2, by default, OPTION_MASK_ABI_X32 is
1936 on and OPTION_MASK_ABI_64 is off. We turn off
1937 OPTION_MASK_ABI_X32 if OPTION_MASK_ABI_64 is turned on by
1938 -m64 or OPTION_MASK_CODE16 is turned on by -m16. */
1939 if (TARGET_LP64_P (opts
->x_ix86_isa_flags
)
1940 || TARGET_16BIT_P (opts
->x_ix86_isa_flags
))
1941 opts
->x_ix86_isa_flags
&= ~OPTION_MASK_ABI_X32
;
1943 if (TARGET_64BIT_P (opts
->x_ix86_isa_flags
)
1944 && TARGET_IAMCU_P (opts
->x_target_flags
))
1945 sorry ("Intel MCU psABI isn%'t supported in %s mode",
1946 TARGET_X32_P (opts
->x_ix86_isa_flags
) ? "x32" : "64-bit");
1950 if (TARGET_X32_P (opts
->x_ix86_isa_flags
))
1952 /* Always turn on OPTION_MASK_ISA_64BIT and turn off
1953 OPTION_MASK_ABI_64 for TARGET_X32. */
1954 opts
->x_ix86_isa_flags
|= OPTION_MASK_ISA_64BIT
;
1955 opts
->x_ix86_isa_flags
&= ~OPTION_MASK_ABI_64
;
1957 else if (TARGET_16BIT_P (opts
->x_ix86_isa_flags
))
1958 opts
->x_ix86_isa_flags
&= ~(OPTION_MASK_ISA_64BIT
1959 | OPTION_MASK_ABI_X32
1960 | OPTION_MASK_ABI_64
);
1961 else if (TARGET_LP64_P (opts
->x_ix86_isa_flags
))
1963 /* Always turn on OPTION_MASK_ISA_64BIT and turn off
1964 OPTION_MASK_ABI_X32 for TARGET_LP64. */
1965 opts
->x_ix86_isa_flags
|= OPTION_MASK_ISA_64BIT
;
1966 opts
->x_ix86_isa_flags
&= ~OPTION_MASK_ABI_X32
;
1969 #ifdef SUBTARGET_OVERRIDE_OPTIONS
1970 SUBTARGET_OVERRIDE_OPTIONS
;
1973 #ifdef SUBSUBTARGET_OVERRIDE_OPTIONS
1974 SUBSUBTARGET_OVERRIDE_OPTIONS
;
1977 #ifdef HAVE_LD_BROKEN_PE_DWARF5
1978 /* If the PE linker has broken DWARF 5 support, make
1979 DWARF 4 the default. */
1981 SET_OPTION_IF_UNSET (opts
, opts_set
, dwarf_version
, 4);
1984 /* -fPIC is the default for x86_64. */
1985 if (TARGET_MACHO
&& TARGET_64BIT_P (opts
->x_ix86_isa_flags
))
1986 opts
->x_flag_pic
= 2;
1988 /* Need to check -mtune=generic first. */
1989 if (opts
->x_ix86_tune_string
)
1991 /* As special support for cross compilers we read -mtune=native
1992 as -mtune=generic. With native compilers we won't see the
1993 -mtune=native, as it was changed by the driver. */
1994 if (!strcmp (opts
->x_ix86_tune_string
, "native"))
1995 opts
->x_ix86_tune_string
= "generic";
1996 else if (!strcmp (opts
->x_ix86_tune_string
, "x86-64"))
1997 warning (OPT_Wdeprecated
,
1999 ? G_("%<-mtune=x86-64%> is deprecated; use %<-mtune=k8%> "
2000 "or %<-mtune=generic%> instead as appropriate")
2001 : G_("%<target(\"tune=x86-64\")%> is deprecated; use "
2002 "%<target(\"tune=k8\")%> or %<target(\"tune=generic\")%>"
2003 " instead as appropriate"));
2007 if (opts
->x_ix86_arch_string
)
2008 opts
->x_ix86_tune_string
= opts
->x_ix86_arch_string
;
2009 if (!opts
->x_ix86_tune_string
)
2011 opts
->x_ix86_tune_string
= processor_names
[TARGET_CPU_DEFAULT
];
2012 ix86_tune_defaulted
= 1;
2015 /* opts->x_ix86_tune_string is set to opts->x_ix86_arch_string
2016 or defaulted. We need to use a sensible tune option. */
2017 if (startswith (opts
->x_ix86_tune_string
, "x86-64")
2018 && (opts
->x_ix86_tune_string
[6] == '\0'
2019 || (!strcmp (opts
->x_ix86_tune_string
+ 6, "-v2")
2020 || !strcmp (opts
->x_ix86_tune_string
+ 6, "-v3")
2021 || !strcmp (opts
->x_ix86_tune_string
+ 6, "-v4"))))
2022 opts
->x_ix86_tune_string
= "generic";
2025 if (opts
->x_ix86_stringop_alg
== rep_prefix_8_byte
2026 && !TARGET_64BIT_P (opts
->x_ix86_isa_flags
))
2028 /* rep; movq isn't available in 32-bit code. */
2029 error ("%<-mstringop-strategy=rep_8byte%> not supported for 32-bit code");
2030 opts
->x_ix86_stringop_alg
= no_stringop
;
2033 if (TARGET_UINTR
&& !TARGET_64BIT
)
2034 error ("%<-muintr%> not supported for 32-bit code");
2036 if (ix86_lam_type
&& !TARGET_LP64
)
2037 error ("%<-mlam=%> option: [u48|u57] not supported for 32-bit code");
2039 if (!opts
->x_ix86_arch_string
)
2040 opts
->x_ix86_arch_string
2041 = TARGET_64BIT_P (opts
->x_ix86_isa_flags
)
2042 ? "x86-64" : SUBTARGET32_DEFAULT_CPU
;
2044 ix86_arch_specified
= 1;
2046 if (opts_set
->x_ix86_pmode
)
2048 if ((TARGET_LP64_P (opts
->x_ix86_isa_flags
)
2049 && opts
->x_ix86_pmode
== PMODE_SI
)
2050 || (!TARGET_64BIT_P (opts
->x_ix86_isa_flags
)
2051 && opts
->x_ix86_pmode
== PMODE_DI
))
2052 error ("address mode %qs not supported in the %s bit mode",
2053 TARGET_64BIT_P (opts
->x_ix86_isa_flags
) ? "short" : "long",
2054 TARGET_64BIT_P (opts
->x_ix86_isa_flags
) ? "64" : "32");
2057 opts
->x_ix86_pmode
= TARGET_LP64_P (opts
->x_ix86_isa_flags
)
2058 ? PMODE_DI
: PMODE_SI
;
2060 SET_OPTION_IF_UNSET (opts
, opts_set
, ix86_abi
, DEFAULT_ABI
);
2062 if (opts
->x_ix86_abi
== MS_ABI
&& TARGET_X32_P (opts
->x_ix86_isa_flags
))
2063 error ("%<-mabi=ms%> not supported with X32 ABI");
2064 gcc_assert (opts
->x_ix86_abi
== SYSV_ABI
|| opts
->x_ix86_abi
== MS_ABI
);
2066 const char *abi_name
= opts
->x_ix86_abi
== MS_ABI
? "ms" : "sysv";
2067 if ((opts
->x_flag_sanitize
& SANITIZE_USER_ADDRESS
)
2068 && opts
->x_ix86_abi
!= DEFAULT_ABI
)
2069 error ("%<-mabi=%s%> not supported with %<-fsanitize=address%>", abi_name
);
2070 if ((opts
->x_flag_sanitize
& SANITIZE_KERNEL_ADDRESS
)
2071 && opts
->x_ix86_abi
!= DEFAULT_ABI
)
2072 error ("%<-mabi=%s%> not supported with %<-fsanitize=kernel-address%>",
2074 if ((opts
->x_flag_sanitize
& SANITIZE_THREAD
)
2075 && opts
->x_ix86_abi
!= DEFAULT_ABI
)
2076 error ("%<-mabi=%s%> not supported with %<-fsanitize=thread%>", abi_name
);
2078 /* For targets using ms ABI enable ms-extensions, if not
2079 explicit turned off. For non-ms ABI we turn off this
2081 SET_OPTION_IF_UNSET (opts
, opts_set
, flag_ms_extensions
,
2082 (MS_ABI
== DEFAULT_ABI
));
2084 if (opts_set
->x_ix86_cmodel
)
2086 switch (opts
->x_ix86_cmodel
)
2090 if (opts
->x_flag_pic
)
2091 opts
->x_ix86_cmodel
= CM_SMALL_PIC
;
2092 if (!TARGET_64BIT_P (opts
->x_ix86_isa_flags
))
2093 error ("code model %qs not supported in the %s bit mode",
2099 if (opts
->x_flag_pic
)
2100 opts
->x_ix86_cmodel
= CM_MEDIUM_PIC
;
2101 if (!TARGET_64BIT_P (opts
->x_ix86_isa_flags
))
2102 error ("code model %qs not supported in the %s bit mode",
2104 else if (TARGET_X32_P (opts
->x_ix86_isa_flags
))
2105 error ("code model %qs not supported in x32 mode",
2111 if (opts
->x_flag_pic
)
2112 opts
->x_ix86_cmodel
= CM_LARGE_PIC
;
2113 if (!TARGET_64BIT_P (opts
->x_ix86_isa_flags
))
2114 error ("code model %qs not supported in the %s bit mode",
2116 else if (TARGET_X32_P (opts
->x_ix86_isa_flags
))
2117 error ("code model %qs not supported in x32 mode",
2122 if (opts
->x_flag_pic
)
2123 error ("code model %s does not support PIC mode", "32");
2124 if (TARGET_64BIT_P (opts
->x_ix86_isa_flags
))
2125 error ("code model %qs not supported in the %s bit mode",
2130 if (opts
->x_flag_pic
)
2132 error ("code model %s does not support PIC mode", "kernel");
2133 opts
->x_ix86_cmodel
= CM_32
;
2135 if (!TARGET_64BIT_P (opts
->x_ix86_isa_flags
))
2136 error ("code model %qs not supported in the %s bit mode",
2146 /* For TARGET_64BIT and MS_ABI, force pic on, in order to enable the
2147 use of rip-relative addressing. This eliminates fixups that
2148 would otherwise be needed if this object is to be placed in a
2149 DLL, and is essentially just as efficient as direct addressing. */
2150 if (TARGET_64BIT_P (opts
->x_ix86_isa_flags
)
2151 && (TARGET_RDOS
|| TARGET_PECOFF
))
2152 opts
->x_ix86_cmodel
= CM_MEDIUM_PIC
, opts
->x_flag_pic
= 1;
2153 else if (TARGET_64BIT_P (opts
->x_ix86_isa_flags
))
2154 opts
->x_ix86_cmodel
= opts
->x_flag_pic
? CM_SMALL_PIC
: CM_SMALL
;
2156 opts
->x_ix86_cmodel
= CM_32
;
2158 if (TARGET_MACHO
&& opts
->x_ix86_asm_dialect
== ASM_INTEL
)
2160 error ("%<-masm=intel%> not supported in this configuration");
2161 opts
->x_ix86_asm_dialect
= ASM_ATT
;
2163 if ((TARGET_64BIT_P (opts
->x_ix86_isa_flags
) != 0)
2164 != ((opts
->x_ix86_isa_flags
& OPTION_MASK_ISA_64BIT
) != 0))
2165 sorry ("%i-bit mode not compiled in",
2166 (opts
->x_ix86_isa_flags
& OPTION_MASK_ISA_64BIT
) ? 64 : 32);
2168 /* Last processor_alias_table must point to "generic" entry. */
2169 gcc_checking_assert (strcmp (processor_alias_table
[pta_size
- 1].name
,
2171 for (i
= 0; i
< pta_size
; i
++)
2172 if (! strcmp (opts
->x_ix86_arch_string
, processor_alias_table
[i
].name
))
2174 if (!strcmp (opts
->x_ix86_arch_string
, "generic"))
2177 ? G_("%<generic%> CPU can be used only for %<-mtune=%> "
2179 : G_("%<generic%> CPU can be used only for "
2180 "%<target(\"tune=\")%> attribute"));
2183 else if (!strcmp (opts
->x_ix86_arch_string
, "intel"))
2186 ? G_("%<intel%> CPU can be used only for %<-mtune=%> "
2188 : G_("%<intel%> CPU can be used only for "
2189 "%<target(\"tune=\")%> attribute"));
2193 if (TARGET_64BIT_P (opts
->x_ix86_isa_flags
)
2194 && !((processor_alias_table
[i
].flags
& PTA_64BIT
) != 0))
2196 error ("CPU you selected does not support x86-64 "
2201 ix86_schedule
= processor_alias_table
[i
].schedule
;
2202 ix86_arch
= processor_alias_table
[i
].processor
;
2204 /* Default cpu tuning to the architecture, unless the table
2205 entry requests not to do this. Used by the x86-64 psABI
2206 micro-architecture levels. */
2207 if ((processor_alias_table
[i
].flags
& PTA_NO_TUNE
) == 0)
2208 ix86_tune
= ix86_arch
;
2210 ix86_tune
= PROCESSOR_GENERIC
;
2212 /* Enable PTA flags that are enabled by default by a -march option. */
2213 #define TARGET_EXPLICIT_NO_SAHF_P(opts) (false)
2214 #define SET_TARGET_NO_SAHF(opts) {}
2215 #define TARGET_EXPLICIT_PREFETCH_SSE_P(opts) (false)
2216 #define SET_TARGET_PREFETCH_SSE(opts) {}
2217 #define TARGET_EXPLICIT_NO_TUNE_P(opts) (false)
2218 #define SET_TARGET_NO_TUNE(opts) {}
2219 #define TARGET_EXPLICIT_NO_80387_P(opts) (false)
2220 #define SET_TARGET_NO_80387(opts) {}
2222 #define DEF_PTA(NAME) \
2223 if (((processor_alias_table[i].flags & PTA_ ## NAME) != 0) \
2224 && PTA_ ## NAME != PTA_64BIT \
2225 && (TARGET_64BIT || PTA_ ## NAME != PTA_UINTR) \
2226 && !TARGET_EXPLICIT_ ## NAME ## _P (opts)) \
2227 SET_TARGET_ ## NAME (opts);
2228 #include "i386-isa.def"
2232 if (!(TARGET_64BIT_P (opts
->x_ix86_isa_flags
)
2233 && ((processor_alias_table
[i
].flags
& PTA_NO_SAHF
) != 0))
2234 && !TARGET_EXPLICIT_SAHF_P (opts
))
2235 SET_TARGET_SAHF (opts
);
2237 if (((processor_alias_table
[i
].flags
& PTA_ABM
) != 0)
2238 && !TARGET_EXPLICIT_ABM_P (opts
))
2240 if (!TARGET_EXPLICIT_LZCNT_P (opts
))
2241 SET_TARGET_LZCNT (opts
);
2242 if (!TARGET_EXPLICIT_POPCNT_P (opts
))
2243 SET_TARGET_POPCNT (opts
);
2246 if ((processor_alias_table
[i
].flags
2247 & (PTA_PREFETCH_SSE
| PTA_SSE
)) != 0)
2248 ix86_prefetch_sse
= true;
2250 /* Don't enable x87 instructions if only general registers are
2251 allowed by target("general-regs-only") function attribute or
2252 -mgeneral-regs-only. */
2253 if (!(opts
->x_ix86_target_flags
& OPTION_MASK_GENERAL_REGS_ONLY
)
2254 && !(opts_set
->x_target_flags
& MASK_80387
))
2256 if (((processor_alias_table
[i
].flags
& PTA_NO_80387
) != 0))
2257 opts
->x_target_flags
&= ~MASK_80387
;
2259 opts
->x_target_flags
|= MASK_80387
;
2267 ? G_("bad value %qs for %<-march=%> switch")
2268 : G_("bad value %qs for %<target(\"arch=\")%> attribute"),
2269 opts
->x_ix86_arch_string
);
2271 auto_vec
<const char *> candidates
;
2272 for (i
= 0; i
< pta_size
; i
++)
2273 if (strcmp (processor_alias_table
[i
].name
, "generic")
2274 && strcmp (processor_alias_table
[i
].name
, "intel")
2275 && (!TARGET_64BIT_P (opts
->x_ix86_isa_flags
)
2276 || ((processor_alias_table
[i
].flags
& PTA_64BIT
) != 0)))
2277 candidates
.safe_push (processor_alias_table
[i
].name
);
2279 #ifdef HAVE_LOCAL_CPU_DETECT
2280 /* Add also "native" as possible value. */
2281 candidates
.safe_push ("native");
2286 = candidates_list_and_hint (opts
->x_ix86_arch_string
, s
, candidates
);
2288 inform (input_location
,
2290 ? G_("valid arguments to %<-march=%> switch are: "
2291 "%s; did you mean %qs?")
2292 : G_("valid arguments to %<target(\"arch=\")%> attribute are: "
2293 "%s; did you mean %qs?"), s
, hint
);
2295 inform (input_location
,
2297 ? G_("valid arguments to %<-march=%> switch are: %s")
2298 : G_("valid arguments to %<target(\"arch=\")%> attribute "
2303 ix86_arch_mask
= HOST_WIDE_INT_1U
<< ix86_arch
;
2304 for (i
= 0; i
< X86_ARCH_LAST
; ++i
)
2305 ix86_arch_features
[i
] = !!(initial_ix86_arch_features
[i
] & ix86_arch_mask
);
2307 for (i
= 0; i
< pta_size
; i
++)
2308 if (! strcmp (opts
->x_ix86_tune_string
, processor_alias_table
[i
].name
)
2309 && (processor_alias_table
[i
].flags
& PTA_NO_TUNE
) == 0)
2311 ix86_schedule
= processor_alias_table
[i
].schedule
;
2312 ix86_tune
= processor_alias_table
[i
].processor
;
2313 if (TARGET_64BIT_P (opts
->x_ix86_isa_flags
))
2315 if (!((processor_alias_table
[i
].flags
& PTA_64BIT
) != 0))
2317 if (ix86_tune_defaulted
)
2319 opts
->x_ix86_tune_string
= "x86-64";
2320 for (i
= 0; i
< pta_size
; i
++)
2321 if (! strcmp (opts
->x_ix86_tune_string
,
2322 processor_alias_table
[i
].name
))
2324 ix86_schedule
= processor_alias_table
[i
].schedule
;
2325 ix86_tune
= processor_alias_table
[i
].processor
;
2328 error ("CPU you selected does not support x86-64 "
2332 /* Intel CPUs have always interpreted SSE prefetch instructions as
2333 NOPs; so, we can enable SSE prefetch instructions even when
2334 -mtune (rather than -march) points us to a processor that has them.
2335 However, the VIA C3 gives a SIGILL, so we only do that for i686 and
2336 higher processors. */
2338 && ((processor_alias_table
[i
].flags
2339 & (PTA_PREFETCH_SSE
| PTA_SSE
)) != 0))
2340 ix86_prefetch_sse
= true;
2344 if (ix86_tune_specified
&& i
== pta_size
)
2347 ? G_("bad value %qs for %<-mtune=%> switch")
2348 : G_("bad value %qs for %<target(\"tune=\")%> attribute"),
2349 opts
->x_ix86_tune_string
);
2351 auto_vec
<const char *> candidates
;
2352 for (i
= 0; i
< pta_size
; i
++)
2353 if ((!TARGET_64BIT_P (opts
->x_ix86_isa_flags
)
2354 || ((processor_alias_table
[i
].flags
& PTA_64BIT
) != 0))
2355 && (processor_alias_table
[i
].flags
& PTA_NO_TUNE
) == 0)
2356 candidates
.safe_push (processor_alias_table
[i
].name
);
2358 #ifdef HAVE_LOCAL_CPU_DETECT
2359 /* Add also "native" as possible value. */
2360 candidates
.safe_push ("native");
2365 = candidates_list_and_hint (opts
->x_ix86_tune_string
, s
, candidates
);
2367 inform (input_location
,
2369 ? G_("valid arguments to %<-mtune=%> switch are: "
2370 "%s; did you mean %qs?")
2371 : G_("valid arguments to %<target(\"tune=\")%> attribute are: "
2372 "%s; did you mean %qs?"), s
, hint
);
2374 inform (input_location
,
2376 ? G_("valid arguments to %<-mtune=%> switch are: %s")
2377 : G_("valid arguments to %<target(\"tune=\")%> attribute "
2382 set_ix86_tune_features (opts
, ix86_tune
, opts
->x_ix86_dump_tunes
);
2384 ix86_override_options_after_change ();
2386 ix86_tune_cost
= processor_cost_table
[ix86_tune
];
2387 /* TODO: ix86_cost should be chosen at instruction or function granuality
2388 so for cold code we use size_cost even in !optimize_size compilation. */
2389 if (opts
->x_optimize_size
)
2390 ix86_cost
= &ix86_size_cost
;
2392 ix86_cost
= ix86_tune_cost
;
2394 /* Arrange to set up i386_stack_locals for all functions. */
2395 init_machine_status
= ix86_init_machine_status
;
2397 /* Validate -mregparm= value. */
2398 if (opts_set
->x_ix86_regparm
)
2400 if (TARGET_64BIT_P (opts
->x_ix86_isa_flags
))
2401 warning (0, "%<-mregparm%> is ignored in 64-bit mode");
2402 else if (TARGET_IAMCU_P (opts
->x_target_flags
))
2403 warning (0, "%<-mregparm%> is ignored for Intel MCU psABI");
2404 if (opts
->x_ix86_regparm
> REGPARM_MAX
)
2406 error ("%<-mregparm=%d%> is not between 0 and %d",
2407 opts
->x_ix86_regparm
, REGPARM_MAX
);
2408 opts
->x_ix86_regparm
= 0;
2411 if (TARGET_IAMCU_P (opts
->x_target_flags
)
2412 || TARGET_64BIT_P (opts
->x_ix86_isa_flags
))
2413 opts
->x_ix86_regparm
= REGPARM_MAX
;
2415 /* Provide default for -mbranch-cost= value. */
2416 SET_OPTION_IF_UNSET (opts
, opts_set
, ix86_branch_cost
,
2417 ix86_tune_cost
->branch_cost
);
2419 if (TARGET_64BIT_P (opts
->x_ix86_isa_flags
))
2421 opts
->x_target_flags
2422 |= TARGET_SUBTARGET64_DEFAULT
& ~opts_set
->x_target_flags
;
2424 if (!ix86_arch_specified
)
2425 opts
->x_ix86_isa_flags
2426 |= TARGET_SUBTARGET64_ISA_DEFAULT
& ~opts
->x_ix86_isa_flags_explicit
;
2428 if (!TARGET_128BIT_LONG_DOUBLE_P (opts
->x_target_flags
))
2429 error ("%<-m96bit-long-double%> is not compatible with this target");
2431 if (TARGET_RTD_P (opts
->x_target_flags
))
2434 ? G_("%<-mrtd%> is ignored in 64bit mode")
2435 : G_("%<target(\"rtd\")%> is ignored in 64bit mode"));
2439 opts
->x_target_flags
2440 |= TARGET_SUBTARGET32_DEFAULT
& ~opts_set
->x_target_flags
;
2442 if (!ix86_arch_specified
)
2443 opts
->x_ix86_isa_flags
2444 |= TARGET_SUBTARGET32_ISA_DEFAULT
& ~opts
->x_ix86_isa_flags_explicit
;
2446 /* i386 ABI does not specify red zone. It still makes sense to use it
2447 when programmer takes care to stack from being destroyed. */
2448 if (!(opts_set
->x_target_flags
& MASK_NO_RED_ZONE
))
2449 opts
->x_target_flags
|= MASK_NO_RED_ZONE
;
2452 /* Keep nonleaf frame pointers. */
2453 if (opts
->x_flag_omit_frame_pointer
)
2454 opts
->x_target_flags
&= ~MASK_OMIT_LEAF_FRAME_POINTER
;
2455 else if (TARGET_OMIT_LEAF_FRAME_POINTER_P (opts
->x_target_flags
))
2456 opts
->x_flag_omit_frame_pointer
= 1;
2458 /* If we're doing fast math, we don't care about comparison order
2459 wrt NaNs. This lets us use a shorter comparison sequence. */
2460 if (opts
->x_flag_finite_math_only
)
2461 opts
->x_target_flags
&= ~MASK_IEEE_FP
;
2463 /* If the architecture always has an FPU, turn off NO_FANCY_MATH_387,
2464 since the insns won't need emulation. */
2465 if (ix86_tune_features
[X86_TUNE_ALWAYS_FANCY_MATH_387
])
2466 opts
->x_target_flags
&= ~MASK_NO_FANCY_MATH_387
;
2468 /* Likewise, if the target doesn't have a 387, or we've specified
2469 software floating point, don't use 387 inline intrinsics. */
2470 if (!TARGET_80387_P (opts
->x_target_flags
))
2471 opts
->x_target_flags
|= MASK_NO_FANCY_MATH_387
;
2473 /* Turn on MMX builtins for -msse. */
2474 if (TARGET_SSE_P (opts
->x_ix86_isa_flags
))
2475 opts
->x_ix86_isa_flags
2476 |= OPTION_MASK_ISA_MMX
& ~opts
->x_ix86_isa_flags_explicit
;
2478 /* Enable SSE prefetch. */
2479 if (TARGET_SSE_P (opts
->x_ix86_isa_flags
)
2480 || (TARGET_PRFCHW_P (opts
->x_ix86_isa_flags
)
2481 && !TARGET_3DNOW_P (opts
->x_ix86_isa_flags
))
2482 || TARGET_PREFETCHWT1_P (opts
->x_ix86_isa_flags
))
2483 ix86_prefetch_sse
= true;
2485 /* Enable mwait/monitor instructions for -msse3. */
2486 if (TARGET_SSE3_P (opts
->x_ix86_isa_flags
))
2487 opts
->x_ix86_isa_flags2
2488 |= OPTION_MASK_ISA2_MWAIT
& ~opts
->x_ix86_isa_flags2_explicit
;
2490 /* Enable popcnt instruction for -msse4.2 or -mabm. */
2491 if (TARGET_SSE4_2_P (opts
->x_ix86_isa_flags
)
2492 || TARGET_ABM_P (opts
->x_ix86_isa_flags
))
2493 opts
->x_ix86_isa_flags
2494 |= OPTION_MASK_ISA_POPCNT
& ~opts
->x_ix86_isa_flags_explicit
;
2496 /* Enable crc32 instruction for -msse4.2. */
2497 if (TARGET_SSE4_2_P (opts
->x_ix86_isa_flags
))
2498 opts
->x_ix86_isa_flags
2499 |= OPTION_MASK_ISA_CRC32
& ~opts
->x_ix86_isa_flags_explicit
;
2501 /* Enable lzcnt instruction for -mabm. */
2502 if (TARGET_ABM_P(opts
->x_ix86_isa_flags
))
2503 opts
->x_ix86_isa_flags
2504 |= OPTION_MASK_ISA_LZCNT
& ~opts
->x_ix86_isa_flags_explicit
;
2506 /* Disable BMI, BMI2 and TBM instructions for -m16. */
2507 if (TARGET_16BIT_P(opts
->x_ix86_isa_flags
))
2508 opts
->x_ix86_isa_flags
2509 &= ~((OPTION_MASK_ISA_BMI
| OPTION_MASK_ISA_BMI2
| OPTION_MASK_ISA_TBM
)
2510 & ~opts
->x_ix86_isa_flags_explicit
);
2512 /* Validate -mpreferred-stack-boundary= value or default it to
2513 PREFERRED_STACK_BOUNDARY_DEFAULT. */
2514 ix86_preferred_stack_boundary
= PREFERRED_STACK_BOUNDARY_DEFAULT
;
2515 if (opts_set
->x_ix86_preferred_stack_boundary_arg
)
2517 int min
= TARGET_64BIT_P (opts
->x_ix86_isa_flags
)? 3 : 2;
2518 int max
= TARGET_SEH
? 4 : 12;
2520 if (opts
->x_ix86_preferred_stack_boundary_arg
< min
2521 || opts
->x_ix86_preferred_stack_boundary_arg
> max
)
2524 error ("%<-mpreferred-stack-boundary%> is not supported "
2527 error ("%<-mpreferred-stack-boundary=%d%> is not between %d and %d",
2528 opts
->x_ix86_preferred_stack_boundary_arg
, min
, max
);
2531 ix86_preferred_stack_boundary
2532 = (1 << opts
->x_ix86_preferred_stack_boundary_arg
) * BITS_PER_UNIT
;
2535 /* Set the default value for -mstackrealign. */
2536 SET_OPTION_IF_UNSET (opts
, opts_set
, ix86_force_align_arg_pointer
,
2537 STACK_REALIGN_DEFAULT
);
2539 ix86_default_incoming_stack_boundary
= PREFERRED_STACK_BOUNDARY
;
2541 /* Validate -mincoming-stack-boundary= value or default it to
2542 MIN_STACK_BOUNDARY/PREFERRED_STACK_BOUNDARY. */
2543 ix86_incoming_stack_boundary
= ix86_default_incoming_stack_boundary
;
2544 if (opts_set
->x_ix86_incoming_stack_boundary_arg
)
2546 int min
= TARGET_64BIT_P (opts
->x_ix86_isa_flags
) ? 3 : 2;
2548 if (opts
->x_ix86_incoming_stack_boundary_arg
< min
2549 || opts
->x_ix86_incoming_stack_boundary_arg
> 12)
2550 error ("%<-mincoming-stack-boundary=%d%> is not between %d and 12",
2551 opts
->x_ix86_incoming_stack_boundary_arg
, min
);
2554 ix86_user_incoming_stack_boundary
2555 = (1 << opts
->x_ix86_incoming_stack_boundary_arg
) * BITS_PER_UNIT
;
2556 ix86_incoming_stack_boundary
2557 = ix86_user_incoming_stack_boundary
;
2561 #ifndef NO_PROFILE_COUNTERS
2562 if (flag_nop_mcount
)
2563 error ("%<-mnop-mcount%> is not compatible with this target");
2565 if (flag_nop_mcount
&& flag_pic
)
2566 error ("%<-mnop-mcount%> is not implemented for %<-fPIC%>");
2568 /* Accept -msseregparm only if at least SSE support is enabled. */
2569 if (TARGET_SSEREGPARM_P (opts
->x_target_flags
)
2570 && ! TARGET_SSE_P (opts
->x_ix86_isa_flags
))
2572 ? G_("%<-msseregparm%> used without SSE enabled")
2573 : G_("%<target(\"sseregparm\")%> used without SSE enabled"));
2575 if (opts_set
->x_ix86_fpmath
)
2577 if (opts
->x_ix86_fpmath
& FPMATH_SSE
)
2579 if (!TARGET_SSE_P (opts
->x_ix86_isa_flags
))
2581 if (TARGET_80387_P (opts
->x_target_flags
))
2583 warning (0, "SSE instruction set disabled, using 387 arithmetics");
2584 opts
->x_ix86_fpmath
= FPMATH_387
;
2587 else if ((opts
->x_ix86_fpmath
& FPMATH_387
)
2588 && !TARGET_80387_P (opts
->x_target_flags
))
2590 warning (0, "387 instruction set disabled, using SSE arithmetics");
2591 opts
->x_ix86_fpmath
= FPMATH_SSE
;
2595 /* For all chips supporting SSE2, -mfpmath=sse performs better than
2596 fpmath=387. The second is however default at many targets since the
2597 extra 80bit precision of temporaries is considered to be part of ABI.
2598 Overwrite the default at least for -ffast-math.
2599 TODO: -mfpmath=both seems to produce same performing code with bit
2600 smaller binaries. It is however not clear if register allocation is
2601 ready for this setting.
2602 Also -mfpmath=387 is overall a lot more compact (bout 4-5%) than SSE
2603 codegen. We may switch to 387 with -ffast-math for size optimized
2605 else if (fast_math_flags_set_p (&global_options
)
2606 && TARGET_SSE2_P (opts
->x_ix86_isa_flags
))
2607 opts
->x_ix86_fpmath
= FPMATH_SSE
;
2609 opts
->x_ix86_fpmath
= TARGET_FPMATH_DEFAULT_P (opts
->x_ix86_isa_flags
);
2611 /* Use external vectorized library in vectorizing intrinsics. */
2612 if (opts_set
->x_ix86_veclibabi_type
)
2613 switch (opts
->x_ix86_veclibabi_type
)
2615 case ix86_veclibabi_type_svml
:
2616 ix86_veclib_handler
= &ix86_veclibabi_svml
;
2619 case ix86_veclibabi_type_acml
:
2620 ix86_veclib_handler
= &ix86_veclibabi_acml
;
2627 if (ix86_tune_features
[X86_TUNE_ACCUMULATE_OUTGOING_ARGS
]
2628 && !(opts_set
->x_target_flags
& MASK_ACCUMULATE_OUTGOING_ARGS
))
2629 opts
->x_target_flags
|= MASK_ACCUMULATE_OUTGOING_ARGS
;
2631 /* If stack probes are required, the space used for large function
2632 arguments on the stack must also be probed, so enable
2633 -maccumulate-outgoing-args so this happens in the prologue. */
2634 if (TARGET_STACK_PROBE_P (opts
->x_target_flags
)
2635 && !(opts
->x_target_flags
& MASK_ACCUMULATE_OUTGOING_ARGS
))
2637 if (opts_set
->x_target_flags
& MASK_ACCUMULATE_OUTGOING_ARGS
)
2640 ? G_("stack probing requires %<-maccumulate-outgoing-args%> "
2642 : G_("stack probing requires "
2643 "%<target(\"accumulate-outgoing-args\")%> for "
2645 opts
->x_target_flags
|= MASK_ACCUMULATE_OUTGOING_ARGS
;
2648 /* Stack realignment without -maccumulate-outgoing-args requires %ebp,
2649 so enable -maccumulate-outgoing-args when %ebp is fixed. */
2650 if (fixed_regs
[BP_REG
]
2651 && !(opts
->x_target_flags
& MASK_ACCUMULATE_OUTGOING_ARGS
))
2653 if (opts_set
->x_target_flags
& MASK_ACCUMULATE_OUTGOING_ARGS
)
2656 ? G_("fixed ebp register requires "
2657 "%<-maccumulate-outgoing-args%>")
2658 : G_("fixed ebp register requires "
2659 "%<target(\"accumulate-outgoing-args\")%>"));
2660 opts
->x_target_flags
|= MASK_ACCUMULATE_OUTGOING_ARGS
;
2663 /* Figure out what ASM_GENERATE_INTERNAL_LABEL builds as a prefix. */
2666 ASM_GENERATE_INTERNAL_LABEL (internal_label_prefix
, "LX", 0);
2667 p
= strchr (internal_label_prefix
, 'X');
2668 internal_label_prefix_len
= p
- internal_label_prefix
;
2672 /* When scheduling description is not available, disable scheduler pass
2673 so it won't slow down the compilation and make x87 code slower. */
2674 if (!TARGET_SCHEDULE
)
2675 opts
->x_flag_schedule_insns_after_reload
= opts
->x_flag_schedule_insns
= 0;
2677 SET_OPTION_IF_UNSET (opts
, opts_set
, param_simultaneous_prefetches
,
2678 ix86_tune_cost
->simultaneous_prefetches
);
2679 SET_OPTION_IF_UNSET (opts
, opts_set
, param_l1_cache_line_size
,
2680 ix86_tune_cost
->prefetch_block
);
2681 SET_OPTION_IF_UNSET (opts
, opts_set
, param_l1_cache_size
,
2682 ix86_tune_cost
->l1_cache_size
);
2683 SET_OPTION_IF_UNSET (opts
, opts_set
, param_l2_cache_size
,
2684 ix86_tune_cost
->l2_cache_size
);
2686 /* 64B is the accepted value for these for all x86. */
2687 SET_OPTION_IF_UNSET (&global_options
, &global_options_set
,
2688 param_destruct_interfere_size
, 64);
2689 SET_OPTION_IF_UNSET (&global_options
, &global_options_set
,
2690 param_construct_interfere_size
, 64);
2692 /* Enable sw prefetching at -O3 for CPUS that prefetching is helpful. */
2693 if (opts
->x_flag_prefetch_loop_arrays
< 0
2695 && (opts
->x_optimize
>= 3 || opts
->x_flag_profile_use
)
2696 && !opts
->x_optimize_size
2697 && TARGET_SOFTWARE_PREFETCHING_BENEFICIAL
)
2698 opts
->x_flag_prefetch_loop_arrays
= 1;
2700 /* If using typedef char *va_list, signal that __builtin_va_start (&ap, 0)
2701 can be opts->x_optimized to ap = __builtin_next_arg (0). */
2702 if (!TARGET_64BIT_P (opts
->x_ix86_isa_flags
) && !opts
->x_flag_split_stack
)
2703 targetm
.expand_builtin_va_start
= NULL
;
2706 /* Use -mcld by default for 32-bit code if configured with --enable-cld. */
2707 if (!TARGET_64BIT_P (opts
->x_ix86_isa_flags
))
2708 opts
->x_target_flags
|= MASK_CLD
& ~opts_set
->x_target_flags
;
2711 /* Set the default value for -mfentry. */
2712 if (!opts_set
->x_flag_fentry
)
2713 opts
->x_flag_fentry
= TARGET_SEH
;
2716 if (!TARGET_64BIT_P (opts
->x_ix86_isa_flags
) && opts
->x_flag_pic
2717 && opts
->x_flag_fentry
)
2718 sorry ("%<-mfentry%> isn%'t supported for 32-bit in combination "
2720 else if (TARGET_SEH
&& !opts
->x_flag_fentry
)
2721 sorry ("%<-mno-fentry%> isn%'t compatible with SEH");
2724 if (TARGET_SEH
&& TARGET_CALL_MS2SYSV_XLOGUES
)
2725 sorry ("%<-mcall-ms2sysv-xlogues%> isn%'t currently supported with SEH");
2727 if (!(opts_set
->x_target_flags
& MASK_VZEROUPPER
)
2728 && TARGET_EMIT_VZEROUPPER
)
2729 opts
->x_target_flags
|= MASK_VZEROUPPER
;
2730 if (!(opts_set
->x_target_flags
& MASK_STV
))
2731 opts
->x_target_flags
|= MASK_STV
;
2732 /* Disable STV if -mpreferred-stack-boundary={2,3} or
2733 -mincoming-stack-boundary={2,3} or -mstackrealign - the needed
2734 stack realignment will be extra cost the pass doesn't take into
2735 account and the pass can't realign the stack. */
2736 if (ix86_preferred_stack_boundary
< 128
2737 || ix86_incoming_stack_boundary
< 128
2738 || opts
->x_ix86_force_align_arg_pointer
)
2739 opts
->x_target_flags
&= ~MASK_STV
;
2740 if (!ix86_tune_features
[X86_TUNE_AVX256_UNALIGNED_LOAD_OPTIMAL
]
2741 && !(opts_set
->x_target_flags
& MASK_AVX256_SPLIT_UNALIGNED_LOAD
))
2742 opts
->x_target_flags
|= MASK_AVX256_SPLIT_UNALIGNED_LOAD
;
2743 else if (!main_args_p
2744 && ix86_tune_features
[X86_TUNE_AVX256_UNALIGNED_LOAD_OPTIMAL
])
2745 opts
->x_target_flags
&= ~MASK_AVX256_SPLIT_UNALIGNED_LOAD
;
2747 if (!ix86_tune_features
[X86_TUNE_AVX256_UNALIGNED_STORE_OPTIMAL
]
2748 && !(opts_set
->x_target_flags
& MASK_AVX256_SPLIT_UNALIGNED_STORE
))
2749 opts
->x_target_flags
|= MASK_AVX256_SPLIT_UNALIGNED_STORE
;
2750 else if (!main_args_p
2751 && ix86_tune_features
[X86_TUNE_AVX256_UNALIGNED_STORE_OPTIMAL
])
2752 opts
->x_target_flags
&= ~MASK_AVX256_SPLIT_UNALIGNED_STORE
;
2754 /* Enable 128-bit AVX instruction generation
2755 for the auto-vectorizer. */
2756 if (ix86_tune_features
[X86_TUNE_AVX128_OPTIMAL
]
2757 && (opts_set
->x_prefer_vector_width_type
== PVW_NONE
))
2758 opts
->x_prefer_vector_width_type
= PVW_AVX128
;
2760 /* Use 256-bit AVX instruction generation
2761 in the auto-vectorizer. */
2762 if (ix86_tune_features
[X86_TUNE_AVX256_OPTIMAL
]
2763 && (opts_set
->x_prefer_vector_width_type
== PVW_NONE
))
2764 opts
->x_prefer_vector_width_type
= PVW_AVX256
;
2766 if (opts_set
->x_ix86_move_max
== PVW_NONE
)
2768 /* Set the maximum number of bits can be moved from memory to
2769 memory efficiently. */
2770 if (ix86_tune_features
[X86_TUNE_AVX512_MOVE_BY_PIECES
])
2771 opts
->x_ix86_move_max
= PVW_AVX512
;
2772 else if (ix86_tune_features
[X86_TUNE_AVX256_MOVE_BY_PIECES
])
2773 opts
->x_ix86_move_max
= PVW_AVX256
;
2776 opts
->x_ix86_move_max
= opts
->x_prefer_vector_width_type
;
2777 if (opts_set
->x_ix86_move_max
== PVW_NONE
)
2779 if (TARGET_AVX512F_P (opts
->x_ix86_isa_flags
))
2780 opts
->x_ix86_move_max
= PVW_AVX512
;
2782 opts
->x_ix86_move_max
= PVW_AVX128
;
2787 if (opts_set
->x_ix86_store_max
== PVW_NONE
)
2789 /* Set the maximum number of bits can be stored to memory
2791 if (ix86_tune_features
[X86_TUNE_AVX512_STORE_BY_PIECES
])
2792 opts
->x_ix86_store_max
= PVW_AVX512
;
2793 else if (ix86_tune_features
[X86_TUNE_AVX256_STORE_BY_PIECES
])
2794 opts
->x_ix86_store_max
= PVW_AVX256
;
2797 opts
->x_ix86_store_max
= opts
->x_prefer_vector_width_type
;
2798 if (opts_set
->x_ix86_store_max
== PVW_NONE
)
2800 if (TARGET_AVX512F_P (opts
->x_ix86_isa_flags
))
2801 opts
->x_ix86_store_max
= PVW_AVX512
;
2803 opts
->x_ix86_store_max
= PVW_AVX128
;
2808 if (opts
->x_ix86_recip_name
)
2810 char *p
= ASTRDUP (opts
->x_ix86_recip_name
);
2815 while ((q
= strtok (p
, ",")) != NULL
)
2826 if (!strcmp (q
, "default"))
2827 mask
= RECIP_MASK_ALL
;
2830 for (i
= 0; i
< ARRAY_SIZE (recip_options
); i
++)
2831 if (!strcmp (q
, recip_options
[i
].string
))
2833 mask
= recip_options
[i
].mask
;
2837 if (i
== ARRAY_SIZE (recip_options
))
2839 error ("unknown option for %<-mrecip=%s%>", q
);
2841 mask
= RECIP_MASK_NONE
;
2845 opts
->x_recip_mask_explicit
|= mask
;
2847 opts
->x_recip_mask
&= ~mask
;
2849 opts
->x_recip_mask
|= mask
;
2853 if (TARGET_RECIP_P (opts
->x_target_flags
))
2854 opts
->x_recip_mask
|= RECIP_MASK_ALL
& ~opts
->x_recip_mask_explicit
;
2855 else if (opts_set
->x_target_flags
& MASK_RECIP
)
2856 opts
->x_recip_mask
&= ~(RECIP_MASK_ALL
& ~opts
->x_recip_mask_explicit
);
2858 /* Default long double to 64-bit for 32-bit Bionic and to __float128
2859 for 64-bit Bionic. Also default long double to 64-bit for Intel
2861 if ((TARGET_HAS_BIONIC
|| TARGET_IAMCU
)
2862 && !(opts_set
->x_target_flags
2863 & (MASK_LONG_DOUBLE_64
| MASK_LONG_DOUBLE_128
)))
2864 opts
->x_target_flags
|= (TARGET_64BIT
2865 ? MASK_LONG_DOUBLE_128
2866 : MASK_LONG_DOUBLE_64
);
2868 /* Only one of them can be active. */
2869 gcc_assert ((opts
->x_target_flags
& MASK_LONG_DOUBLE_64
) == 0
2870 || (opts
->x_target_flags
& MASK_LONG_DOUBLE_128
) == 0);
2872 /* Handle stack protector */
2873 if (!opts_set
->x_ix86_stack_protector_guard
)
2875 #ifdef TARGET_THREAD_SSP_OFFSET
2876 if (!TARGET_HAS_BIONIC
)
2877 opts
->x_ix86_stack_protector_guard
= SSP_TLS
;
2880 opts
->x_ix86_stack_protector_guard
= SSP_GLOBAL
;
2883 if (opts_set
->x_ix86_stack_protector_guard_offset_str
)
2886 const char *str
= opts
->x_ix86_stack_protector_guard_offset_str
;
2891 #if defined(INT64_T_IS_LONG)
2892 offset
= strtol (str
, &endp
, 0);
2894 offset
= strtoll (str
, &endp
, 0);
2897 if (!*str
|| *endp
|| errno
)
2898 error ("%qs is not a valid number "
2899 "in %<-mstack-protector-guard-offset=%>", str
);
2901 if (!IN_RANGE (offset
, HOST_WIDE_INT_C (-0x80000000),
2902 HOST_WIDE_INT_C (0x7fffffff)))
2903 error ("%qs is not a valid offset "
2904 "in %<-mstack-protector-guard-offset=%>", str
);
2906 opts
->x_ix86_stack_protector_guard_offset
= offset
;
2908 #ifdef TARGET_THREAD_SSP_OFFSET
2910 opts
->x_ix86_stack_protector_guard_offset
= TARGET_THREAD_SSP_OFFSET
;
2913 if (opts_set
->x_ix86_stack_protector_guard_reg_str
)
2915 const char *str
= opts
->x_ix86_stack_protector_guard_reg_str
;
2916 addr_space_t seg
= ADDR_SPACE_GENERIC
;
2918 /* Discard optional register prefix. */
2922 if (strlen (str
) == 2 && str
[1] == 's')
2925 seg
= ADDR_SPACE_SEG_FS
;
2926 else if (str
[0] == 'g')
2927 seg
= ADDR_SPACE_SEG_GS
;
2930 if (seg
== ADDR_SPACE_GENERIC
)
2931 error ("%qs is not a valid base register "
2932 "in %<-mstack-protector-guard-reg=%>",
2933 opts
->x_ix86_stack_protector_guard_reg_str
);
2935 opts
->x_ix86_stack_protector_guard_reg
= seg
;
2939 opts
->x_ix86_stack_protector_guard_reg
= DEFAULT_TLS_SEG_REG
;
2941 /* The kernel uses a different segment register for performance
2942 reasons; a system call would not have to trash the userspace
2943 segment register, which would be expensive. */
2944 if (opts
->x_ix86_cmodel
== CM_KERNEL
)
2945 opts
->x_ix86_stack_protector_guard_reg
= ADDR_SPACE_SEG_GS
;
2948 /* Handle -mmemcpy-strategy= and -mmemset-strategy= */
2949 if (opts
->x_ix86_tune_memcpy_strategy
)
2951 char *str
= xstrdup (opts
->x_ix86_tune_memcpy_strategy
);
2952 ix86_parse_stringop_strategy_string (str
, false);
2956 if (opts
->x_ix86_tune_memset_strategy
)
2958 char *str
= xstrdup (opts
->x_ix86_tune_memset_strategy
);
2959 ix86_parse_stringop_strategy_string (str
, true);
2963 /* Save the initial options in case the user does function specific
2967 opts
->x_ix86_excess_precision
2968 = opts
->x_flag_excess_precision
;
2969 opts
->x_ix86_unsafe_math_optimizations
2970 = opts
->x_flag_unsafe_math_optimizations
;
2971 target_option_default_node
= target_option_current_node
2972 = build_target_option_node (opts
, opts_set
);
2975 if (opts
->x_flag_cf_protection
!= CF_NONE
)
2977 if ((opts
->x_flag_cf_protection
& CF_BRANCH
) == CF_BRANCH
2978 && !TARGET_64BIT
&& !TARGET_CMOV
)
2979 error ("%<-fcf-protection%> is not compatible with this target");
2981 opts
->x_flag_cf_protection
2982 = (cf_protection_level
) (opts
->x_flag_cf_protection
| CF_SET
);
2985 if (ix86_tune_features
[X86_TUNE_AVOID_256FMA_CHAINS
])
2986 SET_OPTION_IF_UNSET (opts
, opts_set
, param_avoid_fma_max_bits
, 512);
2987 else if (ix86_tune_features
[X86_TUNE_AVOID_256FMA_CHAINS
])
2988 SET_OPTION_IF_UNSET (opts
, opts_set
, param_avoid_fma_max_bits
, 256);
2989 else if (ix86_tune_features
[X86_TUNE_AVOID_128FMA_CHAINS
])
2990 SET_OPTION_IF_UNSET (opts
, opts_set
, param_avoid_fma_max_bits
, 128);
2992 /* PR86952: jump table usage with retpolines is slow.
2993 The PR provides some numbers about the slowness. */
2994 if (ix86_indirect_branch
!= indirect_branch_keep
)
2995 SET_OPTION_IF_UNSET (opts
, opts_set
, flag_jump_tables
, 0);
2997 SET_OPTION_IF_UNSET (opts
, opts_set
, param_ira_consider_dup_in_all_alts
, 0);
2999 /* Fully masking the main or the epilogue vectorized loop is not
3000 profitable generally so leave it disabled until we get more
3001 fine grained control & costing. */
3002 SET_OPTION_IF_UNSET (opts
, opts_set
, param_vect_partial_vector_usage
, 0);
3007 /* Implement the TARGET_OPTION_OVERRIDE hook. */
3010 ix86_option_override (void)
3012 ix86_option_override_internal (true, &global_options
, &global_options_set
);
3015 /* Remember the last target of ix86_set_current_function. */
3016 static GTY(()) tree ix86_previous_fndecl
;
3018 /* Set targets globals to the default (or current #pragma GCC target
3019 if active). Invalidate ix86_previous_fndecl cache. */
3022 ix86_reset_previous_fndecl (void)
3024 tree new_tree
= target_option_current_node
;
3025 cl_target_option_restore (&global_options
, &global_options_set
,
3026 TREE_TARGET_OPTION (new_tree
));
3027 if (TREE_TARGET_GLOBALS (new_tree
))
3028 restore_target_globals (TREE_TARGET_GLOBALS (new_tree
));
3029 else if (new_tree
== target_option_default_node
)
3030 restore_target_globals (&default_target_globals
);
3032 TREE_TARGET_GLOBALS (new_tree
) = save_target_globals_default_opts ();
3033 ix86_previous_fndecl
= NULL_TREE
;
3036 /* Add target attribute to SIMD clone NODE if needed. */
3039 ix86_simd_clone_adjust (struct cgraph_node
*node
)
3041 const char *str
= NULL
;
3043 /* Attributes need to be adjusted for definitions, not declarations. */
3044 if (!node
->definition
)
3047 gcc_assert (node
->decl
== cfun
->decl
);
3048 switch (node
->simdclone
->vecsize_mangle
)
3055 if (TARGET_PREFER_AVX128
)
3058 str
= "avx,prefer-vector-width=256";
3060 str
= "prefer-vector-width=256";
3062 else if (!TARGET_AVX
)
3066 if (TARGET_PREFER_AVX128
)
3069 str
= "avx2,prefer-vector-width=256";
3071 str
= "prefer-vector-width=256";
3073 else if (!TARGET_AVX2
)
3077 if (TARGET_PREFER_AVX256
)
3079 if (!TARGET_AVX512F
)
3080 str
= "avx512f,prefer-vector-width=512";
3082 str
= "prefer-vector-width=512";
3084 else if (!TARGET_AVX512F
)
3093 tree args
= build_tree_list (NULL_TREE
, build_string (strlen (str
), str
));
3094 bool ok
= ix86_valid_target_attribute_p (node
->decl
, NULL
, args
, 0);
3097 ix86_reset_previous_fndecl ();
3098 ix86_set_current_function (node
->decl
);
3103 /* Set the func_type field from the function FNDECL. */
3106 ix86_set_func_type (tree fndecl
)
3108 if (cfun
->machine
->func_type
== TYPE_UNKNOWN
)
3110 if (lookup_attribute ("interrupt",
3111 TYPE_ATTRIBUTES (TREE_TYPE (fndecl
))))
3113 if (ix86_function_naked (fndecl
))
3114 error_at (DECL_SOURCE_LOCATION (fndecl
),
3115 "interrupt and naked attributes are not compatible");
3118 for (tree arg
= DECL_ARGUMENTS (fndecl
);
3120 arg
= TREE_CHAIN (arg
))
3122 cfun
->machine
->no_caller_saved_registers
= true;
3123 cfun
->machine
->func_type
3124 = nargs
== 2 ? TYPE_EXCEPTION
: TYPE_INTERRUPT
;
3126 ix86_optimize_mode_switching
[X86_DIRFLAG
] = 1;
3128 /* Only dwarf2out.cc can handle -WORD(AP) as a pointer argument. */
3129 if (write_symbols
!= NO_DEBUG
&& write_symbols
!= DWARF2_DEBUG
)
3130 sorry ("only DWARF debug format is supported for interrupt "
3135 cfun
->machine
->func_type
= TYPE_NORMAL
;
3136 if (lookup_attribute ("no_caller_saved_registers",
3137 TYPE_ATTRIBUTES (TREE_TYPE (fndecl
))))
3138 cfun
->machine
->no_caller_saved_registers
= true;
3143 /* Set the indirect_branch_type field from the function FNDECL. */
3146 ix86_set_indirect_branch_type (tree fndecl
)
3148 if (cfun
->machine
->indirect_branch_type
== indirect_branch_unset
)
3150 tree attr
= lookup_attribute ("indirect_branch",
3151 DECL_ATTRIBUTES (fndecl
));
3154 tree args
= TREE_VALUE (attr
);
3157 tree cst
= TREE_VALUE (args
);
3158 if (strcmp (TREE_STRING_POINTER (cst
), "keep") == 0)
3159 cfun
->machine
->indirect_branch_type
= indirect_branch_keep
;
3160 else if (strcmp (TREE_STRING_POINTER (cst
), "thunk") == 0)
3161 cfun
->machine
->indirect_branch_type
= indirect_branch_thunk
;
3162 else if (strcmp (TREE_STRING_POINTER (cst
), "thunk-inline") == 0)
3163 cfun
->machine
->indirect_branch_type
= indirect_branch_thunk_inline
;
3164 else if (strcmp (TREE_STRING_POINTER (cst
), "thunk-extern") == 0)
3165 cfun
->machine
->indirect_branch_type
= indirect_branch_thunk_extern
;
3170 cfun
->machine
->indirect_branch_type
= ix86_indirect_branch
;
3172 /* -mcmodel=large is not compatible with -mindirect-branch=thunk
3173 nor -mindirect-branch=thunk-extern. */
3174 if ((ix86_cmodel
== CM_LARGE
|| ix86_cmodel
== CM_LARGE_PIC
)
3175 && ((cfun
->machine
->indirect_branch_type
3176 == indirect_branch_thunk_extern
)
3177 || (cfun
->machine
->indirect_branch_type
3178 == indirect_branch_thunk
)))
3179 error ("%<-mindirect-branch=%s%> and %<-mcmodel=large%> are not "
3181 ((cfun
->machine
->indirect_branch_type
3182 == indirect_branch_thunk_extern
)
3183 ? "thunk-extern" : "thunk"));
3185 if (cfun
->machine
->indirect_branch_type
!= indirect_branch_keep
3186 && (cfun
->machine
->indirect_branch_type
3187 != indirect_branch_thunk_extern
)
3188 && (flag_cf_protection
& CF_RETURN
))
3189 error ("%<-mindirect-branch%> and %<-fcf-protection%> are not "
3193 if (cfun
->machine
->function_return_type
== indirect_branch_unset
)
3195 tree attr
= lookup_attribute ("function_return",
3196 DECL_ATTRIBUTES (fndecl
));
3199 tree args
= TREE_VALUE (attr
);
3202 tree cst
= TREE_VALUE (args
);
3203 if (strcmp (TREE_STRING_POINTER (cst
), "keep") == 0)
3204 cfun
->machine
->function_return_type
= indirect_branch_keep
;
3205 else if (strcmp (TREE_STRING_POINTER (cst
), "thunk") == 0)
3206 cfun
->machine
->function_return_type
= indirect_branch_thunk
;
3207 else if (strcmp (TREE_STRING_POINTER (cst
), "thunk-inline") == 0)
3208 cfun
->machine
->function_return_type
= indirect_branch_thunk_inline
;
3209 else if (strcmp (TREE_STRING_POINTER (cst
), "thunk-extern") == 0)
3210 cfun
->machine
->function_return_type
= indirect_branch_thunk_extern
;
3215 cfun
->machine
->function_return_type
= ix86_function_return
;
3217 /* -mcmodel=large is not compatible with -mfunction-return=thunk
3218 nor -mfunction-return=thunk-extern. */
3219 if ((ix86_cmodel
== CM_LARGE
|| ix86_cmodel
== CM_LARGE_PIC
)
3220 && ((cfun
->machine
->function_return_type
3221 == indirect_branch_thunk_extern
)
3222 || (cfun
->machine
->function_return_type
3223 == indirect_branch_thunk
)))
3224 error ("%<-mfunction-return=%s%> and %<-mcmodel=large%> are not "
3226 ((cfun
->machine
->function_return_type
3227 == indirect_branch_thunk_extern
)
3228 ? "thunk-extern" : "thunk"));
3230 if (cfun
->machine
->function_return_type
!= indirect_branch_keep
3231 && (cfun
->machine
->function_return_type
3232 != indirect_branch_thunk_extern
)
3233 && (flag_cf_protection
& CF_RETURN
))
3234 error ("%<-mfunction-return%> and %<-fcf-protection%> are not "
3239 /* Establish appropriate back-end context for processing the function
3240 FNDECL. The argument might be NULL to indicate processing at top
3241 level, outside of any function scope. */
3243 ix86_set_current_function (tree fndecl
)
3245 /* Only change the context if the function changes. This hook is called
3246 several times in the course of compiling a function, and we don't want to
3247 slow things down too much or call target_reinit when it isn't safe. */
3248 if (fndecl
== ix86_previous_fndecl
)
3250 /* There may be 2 function bodies for the same function FNDECL,
3251 one is extern inline and one isn't. Call ix86_set_func_type
3252 to set the func_type field. */
3253 if (fndecl
!= NULL_TREE
)
3255 ix86_set_func_type (fndecl
);
3256 ix86_set_indirect_branch_type (fndecl
);
3262 if (ix86_previous_fndecl
== NULL_TREE
)
3263 old_tree
= target_option_current_node
;
3264 else if (DECL_FUNCTION_SPECIFIC_TARGET (ix86_previous_fndecl
))
3265 old_tree
= DECL_FUNCTION_SPECIFIC_TARGET (ix86_previous_fndecl
);
3267 old_tree
= target_option_default_node
;
3269 if (fndecl
== NULL_TREE
)
3271 if (old_tree
!= target_option_current_node
)
3272 ix86_reset_previous_fndecl ();
3276 ix86_set_func_type (fndecl
);
3277 ix86_set_indirect_branch_type (fndecl
);
3279 tree new_tree
= DECL_FUNCTION_SPECIFIC_TARGET (fndecl
);
3280 if (new_tree
== NULL_TREE
)
3281 new_tree
= target_option_default_node
;
3284 = (flag_unsafe_math_optimizations
3285 != TREE_TARGET_OPTION (new_tree
)->x_ix86_unsafe_math_optimizations
3286 || (flag_excess_precision
3287 != TREE_TARGET_OPTION (new_tree
)->x_ix86_excess_precision
));
3288 if (old_tree
!= new_tree
|| fp_flag_change
)
3290 cl_target_option_restore (&global_options
, &global_options_set
,
3291 TREE_TARGET_OPTION (new_tree
));
3294 ix86_excess_precision
= flag_excess_precision
;
3295 ix86_unsafe_math_optimizations
= flag_unsafe_math_optimizations
;
3296 DECL_FUNCTION_SPECIFIC_TARGET (fndecl
) = new_tree
3297 = build_target_option_node (&global_options
, &global_options_set
);
3299 if (TREE_TARGET_GLOBALS (new_tree
))
3300 restore_target_globals (TREE_TARGET_GLOBALS (new_tree
));
3301 else if (new_tree
== target_option_default_node
)
3302 restore_target_globals (&default_target_globals
);
3304 TREE_TARGET_GLOBALS (new_tree
) = save_target_globals_default_opts ();
3306 ix86_previous_fndecl
= fndecl
;
3308 static bool prev_no_caller_saved_registers
;
3310 /* 64-bit MS and SYSV ABI have different set of call used registers.
3311 Avoid expensive re-initialization of init_regs each time we switch
3312 function context. */
3314 && (call_used_or_fixed_reg_p (SI_REG
)
3315 == (cfun
->machine
->call_abi
== MS_ABI
)))
3317 /* Need to re-initialize init_regs if caller-saved registers are
3319 else if (prev_no_caller_saved_registers
3320 != cfun
->machine
->no_caller_saved_registers
)
3323 if (cfun
->machine
->func_type
!= TYPE_NORMAL
3324 || cfun
->machine
->no_caller_saved_registers
)
3326 /* Don't allow SSE, MMX nor x87 instructions since they
3327 may change processor state. */
3331 else if (TARGET_MMX
)
3333 else if (TARGET_80387
)
3339 if (cfun
->machine
->func_type
!= TYPE_NORMAL
)
3340 sorry (cfun
->machine
->func_type
== TYPE_EXCEPTION
3341 ? G_("%s instructions aren%'t allowed in an"
3342 " exception service routine")
3343 : G_("%s instructions aren%'t allowed in an"
3344 " interrupt service routine"),
3347 sorry ("%s instructions aren%'t allowed in a function with "
3348 "the %<no_caller_saved_registers%> attribute", isa
);
3349 /* Don't issue the same error twice. */
3350 cfun
->machine
->func_type
= TYPE_NORMAL
;
3351 cfun
->machine
->no_caller_saved_registers
= false;
3355 prev_no_caller_saved_registers
3356 = cfun
->machine
->no_caller_saved_registers
;
3359 /* Implement the TARGET_OFFLOAD_OPTIONS hook. */
3361 ix86_offload_options (void)
3364 return xstrdup ("-foffload-abi=lp64");
3365 return xstrdup ("-foffload-abi=ilp32");
3368 /* Handle "cdecl", "stdcall", "fastcall", "regparm", "thiscall",
3369 and "sseregparm" calling convention attributes;
3370 arguments as in struct attribute_spec.handler. */
3373 ix86_handle_cconv_attribute (tree
*node
, tree name
, tree args
, int,
3376 if (TREE_CODE (*node
) != FUNCTION_TYPE
3377 && TREE_CODE (*node
) != METHOD_TYPE
3378 && TREE_CODE (*node
) != FIELD_DECL
3379 && TREE_CODE (*node
) != TYPE_DECL
)
3381 warning (OPT_Wattributes
, "%qE attribute only applies to functions",
3383 *no_add_attrs
= true;
3387 /* Can combine regparm with all attributes but fastcall, and thiscall. */
3388 if (is_attribute_p ("regparm", name
))
3392 if (lookup_attribute ("fastcall", TYPE_ATTRIBUTES (*node
)))
3394 error ("fastcall and regparm attributes are not compatible");
3397 if (lookup_attribute ("thiscall", TYPE_ATTRIBUTES (*node
)))
3399 error ("regparam and thiscall attributes are not compatible");
3402 cst
= TREE_VALUE (args
);
3403 if (TREE_CODE (cst
) != INTEGER_CST
)
3405 warning (OPT_Wattributes
,
3406 "%qE attribute requires an integer constant argument",
3408 *no_add_attrs
= true;
3410 else if (compare_tree_int (cst
, REGPARM_MAX
) > 0)
3412 warning (OPT_Wattributes
, "argument to %qE attribute larger than %d",
3414 *no_add_attrs
= true;
3422 /* Do not warn when emulating the MS ABI. */
3423 if ((TREE_CODE (*node
) != FUNCTION_TYPE
3424 && TREE_CODE (*node
) != METHOD_TYPE
)
3425 || ix86_function_type_abi (*node
) != MS_ABI
)
3426 warning (OPT_Wattributes
, "%qE attribute ignored",
3428 *no_add_attrs
= true;
3432 /* Can combine fastcall with stdcall (redundant) and sseregparm. */
3433 if (is_attribute_p ("fastcall", name
))
3435 if (lookup_attribute ("cdecl", TYPE_ATTRIBUTES (*node
)))
3437 error ("fastcall and cdecl attributes are not compatible");
3439 if (lookup_attribute ("stdcall", TYPE_ATTRIBUTES (*node
)))
3441 error ("fastcall and stdcall attributes are not compatible");
3443 if (lookup_attribute ("regparm", TYPE_ATTRIBUTES (*node
)))
3445 error ("fastcall and regparm attributes are not compatible");
3447 if (lookup_attribute ("thiscall", TYPE_ATTRIBUTES (*node
)))
3449 error ("fastcall and thiscall attributes are not compatible");
3453 /* Can combine stdcall with fastcall (redundant), regparm and
3455 else if (is_attribute_p ("stdcall", name
))
3457 if (lookup_attribute ("cdecl", TYPE_ATTRIBUTES (*node
)))
3459 error ("stdcall and cdecl attributes are not compatible");
3461 if (lookup_attribute ("fastcall", TYPE_ATTRIBUTES (*node
)))
3463 error ("stdcall and fastcall attributes are not compatible");
3465 if (lookup_attribute ("thiscall", TYPE_ATTRIBUTES (*node
)))
3467 error ("stdcall and thiscall attributes are not compatible");
3471 /* Can combine cdecl with regparm and sseregparm. */
3472 else if (is_attribute_p ("cdecl", name
))
3474 if (lookup_attribute ("stdcall", TYPE_ATTRIBUTES (*node
)))
3476 error ("stdcall and cdecl attributes are not compatible");
3478 if (lookup_attribute ("fastcall", TYPE_ATTRIBUTES (*node
)))
3480 error ("fastcall and cdecl attributes are not compatible");
3482 if (lookup_attribute ("thiscall", TYPE_ATTRIBUTES (*node
)))
3484 error ("cdecl and thiscall attributes are not compatible");
3487 else if (is_attribute_p ("thiscall", name
))
3489 if (TREE_CODE (*node
) != METHOD_TYPE
&& pedantic
)
3490 warning (OPT_Wattributes
, "%qE attribute is used for non-class method",
3492 if (lookup_attribute ("stdcall", TYPE_ATTRIBUTES (*node
)))
3494 error ("stdcall and thiscall attributes are not compatible");
3496 if (lookup_attribute ("fastcall", TYPE_ATTRIBUTES (*node
)))
3498 error ("fastcall and thiscall attributes are not compatible");
3500 if (lookup_attribute ("cdecl", TYPE_ATTRIBUTES (*node
)))
3502 error ("cdecl and thiscall attributes are not compatible");
3506 /* Can combine sseregparm with all attributes. */
3511 #ifndef CHECK_STACK_LIMIT
3512 #define CHECK_STACK_LIMIT (-1)
3515 /* The transactional memory builtins are implicitly regparm or fastcall
3516 depending on the ABI. Override the generic do-nothing attribute that
3517 these builtins were declared with, and replace it with one of the two
3518 attributes that we expect elsewhere. */
3521 ix86_handle_tm_regparm_attribute (tree
*node
, tree
, tree
,
3522 int flags
, bool *no_add_attrs
)
3526 /* In no case do we want to add the placeholder attribute. */
3527 *no_add_attrs
= true;
3529 /* The 64-bit ABI is unchanged for transactional memory. */
3533 /* ??? Is there a better way to validate 32-bit windows? We have
3534 cfun->machine->call_abi, but that seems to be set only for 64-bit. */
3535 if (CHECK_STACK_LIMIT
> 0)
3536 alt
= tree_cons (get_identifier ("fastcall"), NULL
, NULL
);
3539 alt
= tree_cons (NULL
, build_int_cst (NULL
, 2), NULL
);
3540 alt
= tree_cons (get_identifier ("regparm"), alt
, NULL
);
3542 decl_attributes (node
, alt
, flags
);
3547 /* Handle a "force_align_arg_pointer" attribute. */
3550 ix86_handle_force_align_arg_pointer_attribute (tree
*node
, tree name
,
3551 tree
, int, bool *no_add_attrs
)
3553 if (TREE_CODE (*node
) != FUNCTION_TYPE
3554 && TREE_CODE (*node
) != METHOD_TYPE
3555 && TREE_CODE (*node
) != FIELD_DECL
3556 && TREE_CODE (*node
) != TYPE_DECL
)
3558 warning (OPT_Wattributes
, "%qE attribute only applies to functions",
3560 *no_add_attrs
= true;
3566 /* Handle a "ms_struct" or "gcc_struct" attribute; arguments as in
3567 struct attribute_spec.handler. */
3570 ix86_handle_struct_attribute (tree
*node
, tree name
, tree
, int,
3576 if (TREE_CODE (*node
) == TYPE_DECL
)
3577 type
= &TREE_TYPE (*node
);
3582 if (!(type
&& RECORD_OR_UNION_TYPE_P (*type
)))
3584 warning (OPT_Wattributes
, "%qE attribute ignored",
3586 *no_add_attrs
= true;
3589 else if ((is_attribute_p ("ms_struct", name
)
3590 && lookup_attribute ("gcc_struct", TYPE_ATTRIBUTES (*type
)))
3591 || ((is_attribute_p ("gcc_struct", name
)
3592 && lookup_attribute ("ms_struct", TYPE_ATTRIBUTES (*type
)))))
3594 warning (OPT_Wattributes
, "%qE incompatible attribute ignored",
3596 *no_add_attrs
= true;
3602 /* Handle a "callee_pop_aggregate_return" attribute; arguments as
3603 in struct attribute_spec handler. */
3606 ix86_handle_callee_pop_aggregate_return (tree
*node
, tree name
, tree args
, int,
3609 if (TREE_CODE (*node
) != FUNCTION_TYPE
3610 && TREE_CODE (*node
) != METHOD_TYPE
3611 && TREE_CODE (*node
) != FIELD_DECL
3612 && TREE_CODE (*node
) != TYPE_DECL
)
3614 warning (OPT_Wattributes
, "%qE attribute only applies to functions",
3616 *no_add_attrs
= true;
3621 warning (OPT_Wattributes
, "%qE attribute only available for 32-bit",
3623 *no_add_attrs
= true;
3626 if (is_attribute_p ("callee_pop_aggregate_return", name
))
3630 cst
= TREE_VALUE (args
);
3631 if (TREE_CODE (cst
) != INTEGER_CST
)
3633 warning (OPT_Wattributes
,
3634 "%qE attribute requires an integer constant argument",
3636 *no_add_attrs
= true;
3638 else if (compare_tree_int (cst
, 0) != 0
3639 && compare_tree_int (cst
, 1) != 0)
3641 warning (OPT_Wattributes
,
3642 "argument to %qE attribute is neither zero, nor one",
3644 *no_add_attrs
= true;
3653 /* Handle a "ms_abi" or "sysv" attribute; arguments as in
3654 struct attribute_spec.handler. */
3657 ix86_handle_abi_attribute (tree
*node
, tree name
, tree
, int,
3660 if (TREE_CODE (*node
) != FUNCTION_TYPE
3661 && TREE_CODE (*node
) != METHOD_TYPE
3662 && TREE_CODE (*node
) != FIELD_DECL
3663 && TREE_CODE (*node
) != TYPE_DECL
)
3665 warning (OPT_Wattributes
, "%qE attribute only applies to functions",
3667 *no_add_attrs
= true;
3671 /* Can combine regparm with all attributes but fastcall. */
3672 if (is_attribute_p ("ms_abi", name
))
3674 if (lookup_attribute ("sysv_abi", TYPE_ATTRIBUTES (*node
)))
3676 error ("%qs and %qs attributes are not compatible",
3677 "ms_abi", "sysv_abi");
3682 else if (is_attribute_p ("sysv_abi", name
))
3684 if (lookup_attribute ("ms_abi", TYPE_ATTRIBUTES (*node
)))
3686 error ("%qs and %qs attributes are not compatible",
3687 "ms_abi", "sysv_abi");
3697 ix86_handle_fndecl_attribute (tree
*node
, tree name
, tree args
, int,
3700 if (TREE_CODE (*node
) != FUNCTION_DECL
)
3702 warning (OPT_Wattributes
, "%qE attribute only applies to functions",
3704 *no_add_attrs
= true;
3707 if (is_attribute_p ("indirect_branch", name
))
3709 tree cst
= TREE_VALUE (args
);
3710 if (TREE_CODE (cst
) != STRING_CST
)
3712 warning (OPT_Wattributes
,
3713 "%qE attribute requires a string constant argument",
3715 *no_add_attrs
= true;
3717 else if (strcmp (TREE_STRING_POINTER (cst
), "keep") != 0
3718 && strcmp (TREE_STRING_POINTER (cst
), "thunk") != 0
3719 && strcmp (TREE_STRING_POINTER (cst
), "thunk-inline") != 0
3720 && strcmp (TREE_STRING_POINTER (cst
), "thunk-extern") != 0)
3722 warning (OPT_Wattributes
,
3723 "argument to %qE attribute is not "
3724 "(keep|thunk|thunk-inline|thunk-extern)", name
);
3725 *no_add_attrs
= true;
3729 if (is_attribute_p ("function_return", name
))
3731 tree cst
= TREE_VALUE (args
);
3732 if (TREE_CODE (cst
) != STRING_CST
)
3734 warning (OPT_Wattributes
,
3735 "%qE attribute requires a string constant argument",
3737 *no_add_attrs
= true;
3739 else if (strcmp (TREE_STRING_POINTER (cst
), "keep") != 0
3740 && strcmp (TREE_STRING_POINTER (cst
), "thunk") != 0
3741 && strcmp (TREE_STRING_POINTER (cst
), "thunk-inline") != 0
3742 && strcmp (TREE_STRING_POINTER (cst
), "thunk-extern") != 0)
3744 warning (OPT_Wattributes
,
3745 "argument to %qE attribute is not "
3746 "(keep|thunk|thunk-inline|thunk-extern)", name
);
3747 *no_add_attrs
= true;
3755 ix86_handle_no_caller_saved_registers_attribute (tree
*, tree
, tree
,
3762 ix86_handle_interrupt_attribute (tree
*node
, tree
, tree
, int, bool *)
3764 /* DECL_RESULT and DECL_ARGUMENTS do not exist there yet,
3765 but the function type contains args and return type data. */
3766 tree func_type
= *node
;
3767 tree return_type
= TREE_TYPE (func_type
);
3770 tree current_arg_type
= TYPE_ARG_TYPES (func_type
);
3771 while (current_arg_type
3772 && ! VOID_TYPE_P (TREE_VALUE (current_arg_type
)))
3776 if (! POINTER_TYPE_P (TREE_VALUE (current_arg_type
)))
3777 error ("interrupt service routine should have a pointer "
3778 "as the first argument");
3780 else if (nargs
== 1)
3782 if (TREE_CODE (TREE_VALUE (current_arg_type
)) != INTEGER_TYPE
3783 || TYPE_MODE (TREE_VALUE (current_arg_type
)) != word_mode
)
3784 error ("interrupt service routine should have %qs "
3785 "as the second argument",
3787 ? (TARGET_X32
? "unsigned long long int"
3788 : "unsigned long int")
3792 current_arg_type
= TREE_CHAIN (current_arg_type
);
3794 if (!nargs
|| nargs
> 2)
3795 error ("interrupt service routine can only have a pointer argument "
3796 "and an optional integer argument");
3797 if (! VOID_TYPE_P (return_type
))
3798 error ("interrupt service routine must return %<void%>");
3803 /* Handle fentry_name / fentry_section attribute. */
3806 ix86_handle_fentry_name (tree
*node
, tree name
, tree args
,
3807 int, bool *no_add_attrs
)
3809 if (TREE_CODE (*node
) == FUNCTION_DECL
3810 && TREE_CODE (TREE_VALUE (args
)) == STRING_CST
)
3811 /* Do nothing else, just set the attribute. We'll get at
3812 it later with lookup_attribute. */
3816 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
3817 *no_add_attrs
= true;
3823 /* Handle a "nodirect_extern_access" attribute; arguments as in
3824 struct attribute_spec.handler. */
3827 handle_nodirect_extern_access_attribute (tree
*pnode
, tree name
,
3828 tree
ARG_UNUSED (args
),
3829 int ARG_UNUSED (flags
),
3834 if (VAR_OR_FUNCTION_DECL_P (node
))
3836 if ((!TREE_STATIC (node
) && TREE_CODE (node
) != FUNCTION_DECL
3837 && !DECL_EXTERNAL (node
)) || !TREE_PUBLIC (node
))
3839 warning (OPT_Wattributes
,
3840 "%qE attribute have effect only on public objects", name
);
3841 *no_add_attrs
= true;
3846 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
3847 *no_add_attrs
= true;
3853 /* Table of valid machine attributes. */
3854 const struct attribute_spec ix86_attribute_table
[] =
3856 /* { name, min_len, max_len, decl_req, type_req, fn_type_req,
3857 affects_type_identity, handler, exclude } */
3858 /* Stdcall attribute says callee is responsible for popping arguments
3859 if they are not variable. */
3860 { "stdcall", 0, 0, false, true, true, true, ix86_handle_cconv_attribute
,
3862 /* Fastcall attribute says callee is responsible for popping arguments
3863 if they are not variable. */
3864 { "fastcall", 0, 0, false, true, true, true, ix86_handle_cconv_attribute
,
3866 /* Thiscall attribute says callee is responsible for popping arguments
3867 if they are not variable. */
3868 { "thiscall", 0, 0, false, true, true, true, ix86_handle_cconv_attribute
,
3870 /* Cdecl attribute says the callee is a normal C declaration */
3871 { "cdecl", 0, 0, false, true, true, true, ix86_handle_cconv_attribute
,
3873 /* Regparm attribute specifies how many integer arguments are to be
3874 passed in registers. */
3875 { "regparm", 1, 1, false, true, true, true, ix86_handle_cconv_attribute
,
3877 /* Sseregparm attribute says we are using x86_64 calling conventions
3878 for FP arguments. */
3879 { "sseregparm", 0, 0, false, true, true, true, ix86_handle_cconv_attribute
,
3881 /* The transactional memory builtins are implicitly regparm or fastcall
3882 depending on the ABI. Override the generic do-nothing attribute that
3883 these builtins were declared with. */
3884 { "*tm regparm", 0, 0, false, true, true, true,
3885 ix86_handle_tm_regparm_attribute
, NULL
},
3886 /* force_align_arg_pointer says this function realigns the stack at entry. */
3887 { "force_align_arg_pointer", 0, 0,
3888 false, true, true, false, ix86_handle_force_align_arg_pointer_attribute
,
3890 #if TARGET_DLLIMPORT_DECL_ATTRIBUTES
3891 { "dllimport", 0, 0, false, false, false, false, handle_dll_attribute
,
3893 { "dllexport", 0, 0, false, false, false, false, handle_dll_attribute
,
3895 { "shared", 0, 0, true, false, false, false,
3896 ix86_handle_shared_attribute
, NULL
},
3898 { "ms_struct", 0, 0, false, false, false, false,
3899 ix86_handle_struct_attribute
, NULL
},
3900 { "gcc_struct", 0, 0, false, false, false, false,
3901 ix86_handle_struct_attribute
, NULL
},
3902 #ifdef SUBTARGET_ATTRIBUTE_TABLE
3903 SUBTARGET_ATTRIBUTE_TABLE
,
3905 /* ms_abi and sysv_abi calling convention function attributes. */
3906 { "ms_abi", 0, 0, false, true, true, true, ix86_handle_abi_attribute
, NULL
},
3907 { "sysv_abi", 0, 0, false, true, true, true, ix86_handle_abi_attribute
,
3909 { "ms_abi va_list", 0, 0, false, false, false, false, NULL
, NULL
},
3910 { "sysv_abi va_list", 0, 0, false, false, false, false, NULL
, NULL
},
3911 { "ms_hook_prologue", 0, 0, true, false, false, false,
3912 ix86_handle_fndecl_attribute
, NULL
},
3913 { "callee_pop_aggregate_return", 1, 1, false, true, true, true,
3914 ix86_handle_callee_pop_aggregate_return
, NULL
},
3915 { "interrupt", 0, 0, false, true, true, false,
3916 ix86_handle_interrupt_attribute
, NULL
},
3917 { "no_caller_saved_registers", 0, 0, false, true, true, false,
3918 ix86_handle_no_caller_saved_registers_attribute
, NULL
},
3919 { "naked", 0, 0, true, false, false, false,
3920 ix86_handle_fndecl_attribute
, NULL
},
3921 { "indirect_branch", 1, 1, true, false, false, false,
3922 ix86_handle_fndecl_attribute
, NULL
},
3923 { "function_return", 1, 1, true, false, false, false,
3924 ix86_handle_fndecl_attribute
, NULL
},
3925 { "indirect_return", 0, 0, false, true, true, false,
3927 { "fentry_name", 1, 1, true, false, false, false,
3928 ix86_handle_fentry_name
, NULL
},
3929 { "fentry_section", 1, 1, true, false, false, false,
3930 ix86_handle_fentry_name
, NULL
},
3931 { "cf_check", 0, 0, true, false, false, false,
3932 ix86_handle_fndecl_attribute
, NULL
},
3933 { "nodirect_extern_access", 0, 0, true, false, false, false,
3934 handle_nodirect_extern_access_attribute
, NULL
},
3937 { NULL
, 0, 0, false, false, false, false, NULL
, NULL
}
3940 #include "gt-i386-options.h"