Add GCC_EXTRA_DIAGNOSTIC_OUTPUT environment variable for fix-it hints
[official-gcc.git] / gcc / opts.c
blob389797d29bdc652366b06ff014c0f054acd6dea0
1 /* Command line option handling.
2 Copyright (C) 2002-2021 Free Software Foundation, Inc.
3 Contributed by Neil Booth.
5 This file is part of GCC.
7 GCC is free software; you can redistribute it and/or modify it under
8 the terms of the GNU General Public License as published by the Free
9 Software Foundation; either version 3, or (at your option) any later
10 version.
12 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
13 WARRANTY; without even the implied warranty of MERCHANTABILITY or
14 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
15 for more details.
17 You should have received a copy of the GNU General Public License
18 along with GCC; see the file COPYING3. If not see
19 <http://www.gnu.org/licenses/>. */
21 #include "config.h"
22 #include "system.h"
23 #include "intl.h"
24 #include "coretypes.h"
25 #include "opts.h"
26 #include "tm.h"
27 #include "flags.h"
28 #include "diagnostic.h"
29 #include "opts-diagnostic.h"
30 #include "insn-attr-common.h"
31 #include "common/common-target.h"
32 #include "spellcheck.h"
33 #include "opt-suggestions.h"
34 #include "diagnostic-color.h"
35 #include "version.h"
36 #include "selftest.h"
38 static void set_Wstrict_aliasing (struct gcc_options *opts, int onoff);
40 /* Indexed by enum debug_info_type. */
41 const char *const debug_type_names[] =
43 "none", "stabs", "dwarf-2", "xcoff", "vms"
46 /* Parse the -femit-struct-debug-detailed option value
47 and set the flag variables. */
49 #define MATCH( prefix, string ) \
50 ((strncmp (prefix, string, sizeof prefix - 1) == 0) \
51 ? ((string += sizeof prefix - 1), 1) : 0)
53 void
54 set_struct_debug_option (struct gcc_options *opts, location_t loc,
55 const char *spec)
57 /* various labels for comparison */
58 static const char dfn_lbl[] = "dfn:", dir_lbl[] = "dir:", ind_lbl[] = "ind:";
59 static const char ord_lbl[] = "ord:", gen_lbl[] = "gen:";
60 static const char none_lbl[] = "none", any_lbl[] = "any";
61 static const char base_lbl[] = "base", sys_lbl[] = "sys";
63 enum debug_struct_file files = DINFO_STRUCT_FILE_ANY;
64 /* Default is to apply to as much as possible. */
65 enum debug_info_usage usage = DINFO_USAGE_NUM_ENUMS;
66 int ord = 1, gen = 1;
68 /* What usage? */
69 if (MATCH (dfn_lbl, spec))
70 usage = DINFO_USAGE_DFN;
71 else if (MATCH (dir_lbl, spec))
72 usage = DINFO_USAGE_DIR_USE;
73 else if (MATCH (ind_lbl, spec))
74 usage = DINFO_USAGE_IND_USE;
76 /* Generics or not? */
77 if (MATCH (ord_lbl, spec))
78 gen = 0;
79 else if (MATCH (gen_lbl, spec))
80 ord = 0;
82 /* What allowable environment? */
83 if (MATCH (none_lbl, spec))
84 files = DINFO_STRUCT_FILE_NONE;
85 else if (MATCH (any_lbl, spec))
86 files = DINFO_STRUCT_FILE_ANY;
87 else if (MATCH (sys_lbl, spec))
88 files = DINFO_STRUCT_FILE_SYS;
89 else if (MATCH (base_lbl, spec))
90 files = DINFO_STRUCT_FILE_BASE;
91 else
92 error_at (loc,
93 "argument %qs to %<-femit-struct-debug-detailed%> "
94 "not recognized",
95 spec);
97 /* Effect the specification. */
98 if (usage == DINFO_USAGE_NUM_ENUMS)
100 if (ord)
102 opts->x_debug_struct_ordinary[DINFO_USAGE_DFN] = files;
103 opts->x_debug_struct_ordinary[DINFO_USAGE_DIR_USE] = files;
104 opts->x_debug_struct_ordinary[DINFO_USAGE_IND_USE] = files;
106 if (gen)
108 opts->x_debug_struct_generic[DINFO_USAGE_DFN] = files;
109 opts->x_debug_struct_generic[DINFO_USAGE_DIR_USE] = files;
110 opts->x_debug_struct_generic[DINFO_USAGE_IND_USE] = files;
113 else
115 if (ord)
116 opts->x_debug_struct_ordinary[usage] = files;
117 if (gen)
118 opts->x_debug_struct_generic[usage] = files;
121 if (*spec == ',')
122 set_struct_debug_option (opts, loc, spec+1);
123 else
125 /* No more -femit-struct-debug-detailed specifications.
126 Do final checks. */
127 if (*spec != '\0')
128 error_at (loc,
129 "argument %qs to %<-femit-struct-debug-detailed%> unknown",
130 spec);
131 if (opts->x_debug_struct_ordinary[DINFO_USAGE_DIR_USE]
132 < opts->x_debug_struct_ordinary[DINFO_USAGE_IND_USE]
133 || opts->x_debug_struct_generic[DINFO_USAGE_DIR_USE]
134 < opts->x_debug_struct_generic[DINFO_USAGE_IND_USE])
135 error_at (loc,
136 "%<-femit-struct-debug-detailed=dir:...%> must allow "
137 "at least as much as "
138 "%<-femit-struct-debug-detailed=ind:...%>");
142 /* Strip off a legitimate source ending from the input string NAME of
143 length LEN. Rather than having to know the names used by all of
144 our front ends, we strip off an ending of a period followed by
145 up to fource characters. (C++ uses ".cpp".) */
147 void
148 strip_off_ending (char *name, int len)
150 int i;
151 for (i = 2; i < 5 && len > i; i++)
153 if (name[len - i] == '.')
155 name[len - i] = '\0';
156 break;
161 /* Find the base name of a path, stripping off both directories and
162 a single final extension. */
164 base_of_path (const char *path, const char **base_out)
166 const char *base = path;
167 const char *dot = 0;
168 const char *p = path;
169 char c = *p;
170 while (c)
172 if (IS_DIR_SEPARATOR (c))
174 base = p + 1;
175 dot = 0;
177 else if (c == '.')
178 dot = p;
179 c = *++p;
181 if (!dot)
182 dot = p;
183 *base_out = base;
184 return dot - base;
187 /* What to print when a switch has no documentation. */
188 static const char undocumented_msg[] = N_("This option lacks documentation.");
189 static const char use_diagnosed_msg[] = N_("Uses of this option are diagnosed.");
191 typedef char *char_p; /* For DEF_VEC_P. */
193 static void set_debug_level (enum debug_info_type type, int extended,
194 const char *arg, struct gcc_options *opts,
195 struct gcc_options *opts_set,
196 location_t loc);
197 static void set_fast_math_flags (struct gcc_options *opts, int set);
198 static void decode_d_option (const char *arg, struct gcc_options *opts,
199 location_t loc, diagnostic_context *dc);
200 static void set_unsafe_math_optimizations_flags (struct gcc_options *opts,
201 int set);
202 static void enable_warning_as_error (const char *arg, int value,
203 unsigned int lang_mask,
204 const struct cl_option_handlers *handlers,
205 struct gcc_options *opts,
206 struct gcc_options *opts_set,
207 location_t loc,
208 diagnostic_context *dc);
210 /* Handle a back-end option; arguments and return value as for
211 handle_option. */
213 bool
214 target_handle_option (struct gcc_options *opts,
215 struct gcc_options *opts_set,
216 const struct cl_decoded_option *decoded,
217 unsigned int lang_mask ATTRIBUTE_UNUSED, int kind,
218 location_t loc,
219 const struct cl_option_handlers *handlers ATTRIBUTE_UNUSED,
220 diagnostic_context *dc, void (*) (void))
222 gcc_assert (dc == global_dc);
223 gcc_assert (kind == DK_UNSPECIFIED);
224 return targetm_common.handle_option (opts, opts_set, decoded, loc);
227 /* Add comma-separated strings to a char_p vector. */
229 static void
230 add_comma_separated_to_vector (void **pvec, const char *arg)
232 char *tmp;
233 char *r;
234 char *w;
235 char *token_start;
236 vec<char_p> *v = (vec<char_p> *) *pvec;
238 vec_check_alloc (v, 1);
240 /* We never free this string. */
241 tmp = xstrdup (arg);
243 r = tmp;
244 w = tmp;
245 token_start = tmp;
247 while (*r != '\0')
249 if (*r == ',')
251 *w++ = '\0';
252 ++r;
253 v->safe_push (token_start);
254 token_start = w;
256 if (*r == '\\' && r[1] == ',')
258 *w++ = ',';
259 r += 2;
261 else
262 *w++ = *r++;
265 *w = '\0';
266 if (*token_start != '\0')
267 v->safe_push (token_start);
269 *pvec = v;
272 /* Initialize opts_obstack. */
274 void
275 init_opts_obstack (void)
277 gcc_obstack_init (&opts_obstack);
280 /* Initialize OPTS and OPTS_SET before using them in parsing options. */
282 void
283 init_options_struct (struct gcc_options *opts, struct gcc_options *opts_set)
285 /* Ensure that opts_obstack has already been initialized by the time
286 that we initialize any gcc_options instances (PR jit/68446). */
287 gcc_assert (opts_obstack.chunk_size > 0);
289 *opts = global_options_init;
291 if (opts_set)
292 memset (opts_set, 0, sizeof (*opts_set));
294 /* Initialize whether `char' is signed. */
295 opts->x_flag_signed_char = DEFAULT_SIGNED_CHAR;
296 /* Set this to a special "uninitialized" value. The actual default
297 is set after target options have been processed. */
298 opts->x_flag_short_enums = 2;
300 /* Initialize target_flags before default_options_optimization
301 so the latter can modify it. */
302 opts->x_target_flags = targetm_common.default_target_flags;
304 /* Some targets have ABI-specified unwind tables. */
305 opts->x_flag_unwind_tables = targetm_common.unwind_tables_default;
307 /* Some targets have other target-specific initialization. */
308 targetm_common.option_init_struct (opts);
311 /* If indicated by the optimization level LEVEL (-Os if SIZE is set,
312 -Ofast if FAST is set, -Og if DEBUG is set), apply the option DEFAULT_OPT
313 to OPTS and OPTS_SET, diagnostic context DC, location LOC, with language
314 mask LANG_MASK and option handlers HANDLERS. */
316 static void
317 maybe_default_option (struct gcc_options *opts,
318 struct gcc_options *opts_set,
319 const struct default_options *default_opt,
320 int level, bool size, bool fast, bool debug,
321 unsigned int lang_mask,
322 const struct cl_option_handlers *handlers,
323 location_t loc,
324 diagnostic_context *dc)
326 const struct cl_option *option = &cl_options[default_opt->opt_index];
327 bool enabled;
329 if (size)
330 gcc_assert (level == 2);
331 if (fast)
332 gcc_assert (level == 3);
333 if (debug)
334 gcc_assert (level == 1);
336 switch (default_opt->levels)
338 case OPT_LEVELS_ALL:
339 enabled = true;
340 break;
342 case OPT_LEVELS_0_ONLY:
343 enabled = (level == 0);
344 break;
346 case OPT_LEVELS_1_PLUS:
347 enabled = (level >= 1);
348 break;
350 case OPT_LEVELS_1_PLUS_SPEED_ONLY:
351 enabled = (level >= 1 && !size && !debug);
352 break;
354 case OPT_LEVELS_1_PLUS_NOT_DEBUG:
355 enabled = (level >= 1 && !debug);
356 break;
358 case OPT_LEVELS_2_PLUS:
359 enabled = (level >= 2);
360 break;
362 case OPT_LEVELS_2_PLUS_SPEED_ONLY:
363 enabled = (level >= 2 && !size && !debug);
364 break;
366 case OPT_LEVELS_3_PLUS:
367 enabled = (level >= 3);
368 break;
370 case OPT_LEVELS_3_PLUS_AND_SIZE:
371 enabled = (level >= 3 || size);
372 break;
374 case OPT_LEVELS_SIZE:
375 enabled = size;
376 break;
378 case OPT_LEVELS_FAST:
379 enabled = fast;
380 break;
382 case OPT_LEVELS_NONE:
383 default:
384 gcc_unreachable ();
387 if (enabled)
388 handle_generated_option (opts, opts_set, default_opt->opt_index,
389 default_opt->arg, default_opt->value,
390 lang_mask, DK_UNSPECIFIED, loc,
391 handlers, true, dc);
392 else if (default_opt->arg == NULL
393 && !option->cl_reject_negative
394 && !(option->flags & CL_PARAMS))
395 handle_generated_option (opts, opts_set, default_opt->opt_index,
396 default_opt->arg, !default_opt->value,
397 lang_mask, DK_UNSPECIFIED, loc,
398 handlers, true, dc);
401 /* As indicated by the optimization level LEVEL (-Os if SIZE is set,
402 -Ofast if FAST is set), apply the options in array DEFAULT_OPTS to
403 OPTS and OPTS_SET, diagnostic context DC, location LOC, with
404 language mask LANG_MASK and option handlers HANDLERS. */
406 static void
407 maybe_default_options (struct gcc_options *opts,
408 struct gcc_options *opts_set,
409 const struct default_options *default_opts,
410 int level, bool size, bool fast, bool debug,
411 unsigned int lang_mask,
412 const struct cl_option_handlers *handlers,
413 location_t loc,
414 diagnostic_context *dc)
416 size_t i;
418 for (i = 0; default_opts[i].levels != OPT_LEVELS_NONE; i++)
419 maybe_default_option (opts, opts_set, &default_opts[i],
420 level, size, fast, debug,
421 lang_mask, handlers, loc, dc);
424 /* Table of options enabled by default at different levels.
425 Please keep this list sorted by level and alphabetized within
426 each level; this makes it easier to keep the documentation
427 in sync. */
429 static const struct default_options default_options_table[] =
431 /* -O1 and -Og optimizations. */
432 { OPT_LEVELS_1_PLUS, OPT_fcombine_stack_adjustments, NULL, 1 },
433 { OPT_LEVELS_1_PLUS, OPT_fcompare_elim, NULL, 1 },
434 { OPT_LEVELS_1_PLUS, OPT_fcprop_registers, NULL, 1 },
435 { OPT_LEVELS_1_PLUS, OPT_fdefer_pop, NULL, 1 },
436 { OPT_LEVELS_1_PLUS, OPT_fforward_propagate, NULL, 1 },
437 { OPT_LEVELS_1_PLUS, OPT_fguess_branch_probability, NULL, 1 },
438 { OPT_LEVELS_1_PLUS, OPT_fipa_profile, NULL, 1 },
439 { OPT_LEVELS_1_PLUS, OPT_fipa_pure_const, NULL, 1 },
440 { OPT_LEVELS_1_PLUS, OPT_fipa_reference, NULL, 1 },
441 { OPT_LEVELS_1_PLUS, OPT_fipa_reference_addressable, NULL, 1 },
442 { OPT_LEVELS_1_PLUS, OPT_fmerge_constants, NULL, 1 },
443 { OPT_LEVELS_1_PLUS, OPT_fomit_frame_pointer, NULL, 1 },
444 { OPT_LEVELS_1_PLUS, OPT_freorder_blocks, NULL, 1 },
445 { OPT_LEVELS_1_PLUS, OPT_fshrink_wrap, NULL, 1 },
446 { OPT_LEVELS_1_PLUS, OPT_fsplit_wide_types, NULL, 1 },
447 { OPT_LEVELS_1_PLUS, OPT_ftree_builtin_call_dce, NULL, 1 },
448 { OPT_LEVELS_1_PLUS, OPT_ftree_ccp, NULL, 1 },
449 { OPT_LEVELS_1_PLUS, OPT_ftree_ch, NULL, 1 },
450 { OPT_LEVELS_1_PLUS, OPT_ftree_coalesce_vars, NULL, 1 },
451 { OPT_LEVELS_1_PLUS, OPT_ftree_copy_prop, NULL, 1 },
452 { OPT_LEVELS_1_PLUS, OPT_ftree_dce, NULL, 1 },
453 { OPT_LEVELS_1_PLUS, OPT_ftree_dominator_opts, NULL, 1 },
454 { OPT_LEVELS_1_PLUS, OPT_ftree_fre, NULL, 1 },
455 { OPT_LEVELS_1_PLUS, OPT_ftree_sink, NULL, 1 },
456 { OPT_LEVELS_1_PLUS, OPT_ftree_slsr, NULL, 1 },
457 { OPT_LEVELS_1_PLUS, OPT_ftree_ter, NULL, 1 },
459 /* -O1 (and not -Og) optimizations. */
460 { OPT_LEVELS_1_PLUS_NOT_DEBUG, OPT_fbranch_count_reg, NULL, 1 },
461 #if DELAY_SLOTS
462 { OPT_LEVELS_1_PLUS_NOT_DEBUG, OPT_fdelayed_branch, NULL, 1 },
463 #endif
464 { OPT_LEVELS_1_PLUS_NOT_DEBUG, OPT_fdse, NULL, 1 },
465 { OPT_LEVELS_1_PLUS_NOT_DEBUG, OPT_fif_conversion, NULL, 1 },
466 { OPT_LEVELS_1_PLUS_NOT_DEBUG, OPT_fif_conversion2, NULL, 1 },
467 { OPT_LEVELS_1_PLUS_NOT_DEBUG, OPT_finline_functions_called_once, NULL, 1 },
468 { OPT_LEVELS_1_PLUS_NOT_DEBUG, OPT_fmove_loop_invariants, NULL, 1 },
469 { OPT_LEVELS_1_PLUS_NOT_DEBUG, OPT_fssa_phiopt, NULL, 1 },
470 { OPT_LEVELS_1_PLUS_NOT_DEBUG, OPT_fipa_modref, NULL, 1 },
471 { OPT_LEVELS_1_PLUS_NOT_DEBUG, OPT_ftree_bit_ccp, NULL, 1 },
472 { OPT_LEVELS_1_PLUS_NOT_DEBUG, OPT_ftree_dse, NULL, 1 },
473 { OPT_LEVELS_1_PLUS_NOT_DEBUG, OPT_ftree_pta, NULL, 1 },
474 { OPT_LEVELS_1_PLUS_NOT_DEBUG, OPT_ftree_sra, NULL, 1 },
476 /* -O2 and -Os optimizations. */
477 { OPT_LEVELS_2_PLUS, OPT_fcaller_saves, NULL, 1 },
478 { OPT_LEVELS_2_PLUS, OPT_fcode_hoisting, NULL, 1 },
479 { OPT_LEVELS_2_PLUS, OPT_fcrossjumping, NULL, 1 },
480 { OPT_LEVELS_2_PLUS, OPT_fcse_follow_jumps, NULL, 1 },
481 { OPT_LEVELS_2_PLUS, OPT_fdevirtualize, NULL, 1 },
482 { OPT_LEVELS_2_PLUS, OPT_fdevirtualize_speculatively, NULL, 1 },
483 { OPT_LEVELS_2_PLUS, OPT_fexpensive_optimizations, NULL, 1 },
484 { OPT_LEVELS_2_PLUS, OPT_fgcse, NULL, 1 },
485 { OPT_LEVELS_2_PLUS, OPT_fhoist_adjacent_loads, NULL, 1 },
486 { OPT_LEVELS_2_PLUS, OPT_findirect_inlining, NULL, 1 },
487 { OPT_LEVELS_2_PLUS, OPT_finline_small_functions, NULL, 1 },
488 { OPT_LEVELS_2_PLUS, OPT_fipa_bit_cp, NULL, 1 },
489 { OPT_LEVELS_2_PLUS, OPT_fipa_cp, NULL, 1 },
490 { OPT_LEVELS_2_PLUS, OPT_fipa_icf, NULL, 1 },
491 { OPT_LEVELS_2_PLUS, OPT_fipa_ra, NULL, 1 },
492 { OPT_LEVELS_2_PLUS, OPT_fipa_sra, NULL, 1 },
493 { OPT_LEVELS_2_PLUS, OPT_fipa_vrp, NULL, 1 },
494 { OPT_LEVELS_2_PLUS, OPT_fisolate_erroneous_paths_dereference, NULL, 1 },
495 { OPT_LEVELS_2_PLUS, OPT_flra_remat, NULL, 1 },
496 { OPT_LEVELS_2_PLUS, OPT_foptimize_sibling_calls, NULL, 1 },
497 { OPT_LEVELS_2_PLUS, OPT_fpartial_inlining, NULL, 1 },
498 { OPT_LEVELS_2_PLUS, OPT_fpeephole2, NULL, 1 },
499 { OPT_LEVELS_2_PLUS, OPT_freorder_functions, NULL, 1 },
500 { OPT_LEVELS_2_PLUS, OPT_frerun_cse_after_loop, NULL, 1 },
501 #ifdef INSN_SCHEDULING
502 { OPT_LEVELS_2_PLUS, OPT_fschedule_insns2, NULL, 1 },
503 #endif
504 { OPT_LEVELS_2_PLUS, OPT_fstrict_aliasing, NULL, 1 },
505 { OPT_LEVELS_2_PLUS, OPT_fstore_merging, NULL, 1 },
506 { OPT_LEVELS_2_PLUS, OPT_fthread_jumps, NULL, 1 },
507 { OPT_LEVELS_2_PLUS, OPT_ftree_pre, NULL, 1 },
508 { OPT_LEVELS_2_PLUS, OPT_ftree_switch_conversion, NULL, 1 },
509 { OPT_LEVELS_2_PLUS, OPT_ftree_tail_merge, NULL, 1 },
510 { OPT_LEVELS_2_PLUS, OPT_ftree_vrp, NULL, 1 },
511 { OPT_LEVELS_2_PLUS, OPT_fvect_cost_model_, NULL, VECT_COST_MODEL_CHEAP },
512 { OPT_LEVELS_2_PLUS, OPT_finline_functions, NULL, 1 },
513 { OPT_LEVELS_2_PLUS, OPT_ftree_loop_distribute_patterns, NULL, 1 },
515 /* -O2 and above optimizations, but not -Os or -Og. */
516 { OPT_LEVELS_2_PLUS_SPEED_ONLY, OPT_falign_functions, NULL, 1 },
517 { OPT_LEVELS_2_PLUS_SPEED_ONLY, OPT_falign_jumps, NULL, 1 },
518 { OPT_LEVELS_2_PLUS_SPEED_ONLY, OPT_falign_labels, NULL, 1 },
519 { OPT_LEVELS_2_PLUS_SPEED_ONLY, OPT_falign_loops, NULL, 1 },
520 { OPT_LEVELS_2_PLUS_SPEED_ONLY, OPT_foptimize_strlen, NULL, 1 },
521 { OPT_LEVELS_2_PLUS_SPEED_ONLY, OPT_freorder_blocks_algorithm_, NULL,
522 REORDER_BLOCKS_ALGORITHM_STC },
523 #ifdef INSN_SCHEDULING
524 /* Only run the pre-regalloc scheduling pass if optimizing for speed. */
525 { OPT_LEVELS_2_PLUS_SPEED_ONLY, OPT_fschedule_insns, NULL, 1 },
526 #endif
528 /* -O3 and -Os optimizations. */
530 /* -O3 optimizations. */
531 { OPT_LEVELS_3_PLUS, OPT_fgcse_after_reload, NULL, 1 },
532 { OPT_LEVELS_3_PLUS, OPT_fipa_cp_clone, NULL, 1 },
533 { OPT_LEVELS_3_PLUS, OPT_floop_interchange, NULL, 1 },
534 { OPT_LEVELS_3_PLUS, OPT_floop_unroll_and_jam, NULL, 1 },
535 { OPT_LEVELS_3_PLUS, OPT_fpeel_loops, NULL, 1 },
536 { OPT_LEVELS_3_PLUS, OPT_fpredictive_commoning, NULL, 1 },
537 { OPT_LEVELS_3_PLUS, OPT_fsplit_loops, NULL, 1 },
538 { OPT_LEVELS_3_PLUS, OPT_fsplit_paths, NULL, 1 },
539 { OPT_LEVELS_3_PLUS, OPT_ftree_loop_distribution, NULL, 1 },
540 { OPT_LEVELS_3_PLUS, OPT_ftree_loop_vectorize, NULL, 1 },
541 { OPT_LEVELS_3_PLUS, OPT_ftree_partial_pre, NULL, 1 },
542 { OPT_LEVELS_3_PLUS, OPT_ftree_slp_vectorize, NULL, 1 },
543 { OPT_LEVELS_3_PLUS, OPT_funswitch_loops, NULL, 1 },
544 { OPT_LEVELS_3_PLUS, OPT_fvect_cost_model_, NULL, VECT_COST_MODEL_DYNAMIC },
545 { OPT_LEVELS_3_PLUS, OPT_fversion_loops_for_strides, NULL, 1 },
547 /* -O3 parameters. */
548 { OPT_LEVELS_3_PLUS, OPT__param_max_inline_insns_auto_, NULL, 30 },
549 { OPT_LEVELS_3_PLUS, OPT__param_early_inlining_insns_, NULL, 14 },
550 { OPT_LEVELS_3_PLUS, OPT__param_inline_heuristics_hint_percent_, NULL, 600 },
551 { OPT_LEVELS_3_PLUS, OPT__param_inline_min_speedup_, NULL, 15 },
552 { OPT_LEVELS_3_PLUS, OPT__param_max_inline_insns_single_, NULL, 200 },
554 /* -Ofast adds optimizations to -O3. */
555 { OPT_LEVELS_FAST, OPT_ffast_math, NULL, 1 },
556 { OPT_LEVELS_FAST, OPT_fallow_store_data_races, NULL, 1 },
558 { OPT_LEVELS_NONE, 0, NULL, 0 }
561 /* Default the options in OPTS and OPTS_SET based on the optimization
562 settings in DECODED_OPTIONS and DECODED_OPTIONS_COUNT. */
563 void
564 default_options_optimization (struct gcc_options *opts,
565 struct gcc_options *opts_set,
566 struct cl_decoded_option *decoded_options,
567 unsigned int decoded_options_count,
568 location_t loc,
569 unsigned int lang_mask,
570 const struct cl_option_handlers *handlers,
571 diagnostic_context *dc)
573 unsigned int i;
574 int opt2;
575 bool openacc_mode = false;
577 /* Scan to see what optimization level has been specified. That will
578 determine the default value of many flags. */
579 for (i = 1; i < decoded_options_count; i++)
581 struct cl_decoded_option *opt = &decoded_options[i];
582 switch (opt->opt_index)
584 case OPT_O:
585 if (*opt->arg == '\0')
587 opts->x_optimize = 1;
588 opts->x_optimize_size = 0;
589 opts->x_optimize_fast = 0;
590 opts->x_optimize_debug = 0;
592 else
594 const int optimize_val = integral_argument (opt->arg);
595 if (optimize_val == -1)
596 error_at (loc, "argument to %<-O%> should be a non-negative "
597 "integer, %<g%>, %<s%> or %<fast%>");
598 else
600 opts->x_optimize = optimize_val;
601 if ((unsigned int) opts->x_optimize > 255)
602 opts->x_optimize = 255;
603 opts->x_optimize_size = 0;
604 opts->x_optimize_fast = 0;
605 opts->x_optimize_debug = 0;
608 break;
610 case OPT_Os:
611 opts->x_optimize_size = 1;
613 /* Optimizing for size forces optimize to be 2. */
614 opts->x_optimize = 2;
615 opts->x_optimize_fast = 0;
616 opts->x_optimize_debug = 0;
617 break;
619 case OPT_Ofast:
620 /* -Ofast only adds flags to -O3. */
621 opts->x_optimize_size = 0;
622 opts->x_optimize = 3;
623 opts->x_optimize_fast = 1;
624 opts->x_optimize_debug = 0;
625 break;
627 case OPT_Og:
628 /* -Og selects optimization level 1. */
629 opts->x_optimize_size = 0;
630 opts->x_optimize = 1;
631 opts->x_optimize_fast = 0;
632 opts->x_optimize_debug = 1;
633 break;
635 case OPT_fopenacc:
636 if (opt->value)
637 openacc_mode = true;
638 break;
640 default:
641 /* Ignore other options in this prescan. */
642 break;
646 maybe_default_options (opts, opts_set, default_options_table,
647 opts->x_optimize, opts->x_optimize_size,
648 opts->x_optimize_fast, opts->x_optimize_debug,
649 lang_mask, handlers, loc, dc);
651 /* -O2 param settings. */
652 opt2 = (opts->x_optimize >= 2);
654 if (openacc_mode)
655 SET_OPTION_IF_UNSET (opts, opts_set, flag_ipa_pta, true);
657 /* Track fields in field-sensitive alias analysis. */
658 if (opt2)
659 SET_OPTION_IF_UNSET (opts, opts_set, param_max_fields_for_field_sensitive,
660 100);
662 if (opts->x_optimize_size)
663 /* We want to crossjump as much as possible. */
664 SET_OPTION_IF_UNSET (opts, opts_set, param_min_crossjump_insns, 1);
666 /* Restrict the amount of work combine does at -Og while retaining
667 most of its useful transforms. */
668 if (opts->x_optimize_debug)
669 SET_OPTION_IF_UNSET (opts, opts_set, param_max_combine_insns, 2);
671 /* Allow default optimizations to be specified on a per-machine basis. */
672 maybe_default_options (opts, opts_set,
673 targetm_common.option_optimization_table,
674 opts->x_optimize, opts->x_optimize_size,
675 opts->x_optimize_fast, opts->x_optimize_debug,
676 lang_mask, handlers, loc, dc);
679 /* Control IPA optimizations based on different live patching LEVEL. */
680 static void
681 control_options_for_live_patching (struct gcc_options *opts,
682 struct gcc_options *opts_set,
683 enum live_patching_level level,
684 location_t loc)
686 gcc_assert (level > LIVE_PATCHING_NONE);
688 switch (level)
690 case LIVE_PATCHING_INLINE_ONLY_STATIC:
691 if (opts_set->x_flag_ipa_cp_clone && opts->x_flag_ipa_cp_clone)
692 error_at (loc, "%qs is incompatible with %qs",
693 "-fipa-cp-clone", "-flive-patching=inline-only-static");
694 else
695 opts->x_flag_ipa_cp_clone = 0;
697 if (opts_set->x_flag_ipa_sra && opts->x_flag_ipa_sra)
698 error_at (loc, "%qs is incompatible with %qs",
699 "-fipa-sra", "-flive-patching=inline-only-static");
700 else
701 opts->x_flag_ipa_sra = 0;
703 if (opts_set->x_flag_partial_inlining && opts->x_flag_partial_inlining)
704 error_at (loc, "%qs is incompatible with %qs",
705 "-fpartial-inlining", "-flive-patching=inline-only-static");
706 else
707 opts->x_flag_partial_inlining = 0;
709 if (opts_set->x_flag_ipa_cp && opts->x_flag_ipa_cp)
710 error_at (loc, "%qs is incompatible with %qs",
711 "-fipa-cp", "-flive-patching=inline-only-static");
712 else
713 opts->x_flag_ipa_cp = 0;
715 /* FALLTHROUGH. */
716 case LIVE_PATCHING_INLINE_CLONE:
717 /* live patching should disable whole-program optimization. */
718 if (opts_set->x_flag_whole_program && opts->x_flag_whole_program)
719 error_at (loc, "%qs is incompatible with %qs",
720 "-fwhole-program",
721 "-flive-patching=inline-only-static|inline-clone");
722 else
723 opts->x_flag_whole_program = 0;
725 /* visibility change should be excluded by !flag_whole_program
726 && !in_lto_p && !flag_ipa_cp_clone && !flag_ipa_sra
727 && !flag_partial_inlining. */
729 if (opts_set->x_flag_ipa_pta && opts->x_flag_ipa_pta)
730 error_at (loc, "%qs is incompatible with %qs",
731 "-fipa-pta",
732 "-flive-patching=inline-only-static|inline-clone");
733 else
734 opts->x_flag_ipa_pta = 0;
736 if (opts_set->x_flag_ipa_reference && opts->x_flag_ipa_reference)
737 error_at (loc, "%qs is incompatible with %qs",
738 "-fipa-reference",
739 "-flive-patching=inline-only-static|inline-clone");
740 else
741 opts->x_flag_ipa_reference = 0;
743 if (opts_set->x_flag_ipa_ra && opts->x_flag_ipa_ra)
744 error_at (loc, "%qs is incompatible with %qs",
745 "-fipa-ra",
746 "-flive-patching=inline-only-static|inline-clone");
747 else
748 opts->x_flag_ipa_ra = 0;
750 if (opts_set->x_flag_ipa_icf && opts->x_flag_ipa_icf)
751 error_at (loc, "%qs is incompatible with %qs",
752 "-fipa-icf",
753 "-flive-patching=inline-only-static|inline-clone");
754 else
755 opts->x_flag_ipa_icf = 0;
757 if (opts_set->x_flag_ipa_icf_functions && opts->x_flag_ipa_icf_functions)
758 error_at (loc, "%qs is incompatible with %qs",
759 "-fipa-icf-functions",
760 "-flive-patching=inline-only-static|inline-clone");
761 else
762 opts->x_flag_ipa_icf_functions = 0;
764 if (opts_set->x_flag_ipa_icf_variables && opts->x_flag_ipa_icf_variables)
765 error_at (loc, "%qs is incompatible with %qs",
766 "-fipa-icf-variables",
767 "-flive-patching=inline-only-static|inline-clone");
768 else
769 opts->x_flag_ipa_icf_variables = 0;
771 if (opts_set->x_flag_ipa_bit_cp && opts->x_flag_ipa_bit_cp)
772 error_at (loc, "%qs is incompatible with %qs",
773 "-fipa-bit-cp",
774 "-flive-patching=inline-only-static|inline-clone");
775 else
776 opts->x_flag_ipa_bit_cp = 0;
778 if (opts_set->x_flag_ipa_vrp && opts->x_flag_ipa_vrp)
779 error_at (loc, "%qs is incompatible with %qs",
780 "-fipa-vrp",
781 "-flive-patching=inline-only-static|inline-clone");
782 else
783 opts->x_flag_ipa_vrp = 0;
785 if (opts_set->x_flag_ipa_pure_const && opts->x_flag_ipa_pure_const)
786 error_at (loc, "%qs is incompatible with %qs",
787 "-fipa-pure-const",
788 "-flive-patching=inline-only-static|inline-clone");
789 else
790 opts->x_flag_ipa_pure_const = 0;
792 if (opts_set->x_flag_ipa_modref && opts->x_flag_ipa_modref)
793 error_at (loc,
794 "%<-fipa-modref%> is incompatible with "
795 "%<-flive-patching=inline-only-static|inline-clone%>");
796 else
797 opts->x_flag_ipa_modref = 0;
799 /* FIXME: disable unreachable code removal. */
801 /* discovery of functions/variables with no address taken. */
802 if (opts_set->x_flag_ipa_reference_addressable
803 && opts->x_flag_ipa_reference_addressable)
804 error_at (loc, "%qs is incompatible with %qs",
805 "-fipa-reference-addressable",
806 "-flive-patching=inline-only-static|inline-clone");
807 else
808 opts->x_flag_ipa_reference_addressable = 0;
810 /* ipa stack alignment propagation. */
811 if (opts_set->x_flag_ipa_stack_alignment
812 && opts->x_flag_ipa_stack_alignment)
813 error_at (loc, "%qs is incompatible with %qs",
814 "-fipa-stack-alignment",
815 "-flive-patching=inline-only-static|inline-clone");
816 else
817 opts->x_flag_ipa_stack_alignment = 0;
818 break;
819 default:
820 gcc_unreachable ();
824 /* --help option argument if set. */
825 vec<const char *> help_option_arguments;
827 /* Return the string name describing a sanitizer argument which has been
828 provided on the command line and has set this particular flag. */
829 const char *
830 find_sanitizer_argument (struct gcc_options *opts, unsigned int flags)
832 for (int i = 0; sanitizer_opts[i].name != NULL; ++i)
834 /* Need to find the sanitizer_opts element which:
835 a) Could have set the flags requested.
836 b) Has been set on the command line.
838 Can have (a) without (b) if the flag requested is e.g.
839 SANITIZE_ADDRESS, since both -fsanitize=address and
840 -fsanitize=kernel-address set this flag.
842 Can have (b) without (a) by requesting more than one sanitizer on the
843 command line. */
844 if ((sanitizer_opts[i].flag & opts->x_flag_sanitize)
845 != sanitizer_opts[i].flag)
846 continue;
847 if ((sanitizer_opts[i].flag & flags) != flags)
848 continue;
849 return sanitizer_opts[i].name;
851 return NULL;
855 /* Report an error to the user about sanitizer options they have requested
856 which have set conflicting flags.
858 LEFT and RIGHT indicate sanitizer flags which conflict with each other, this
859 function reports an error if both have been set in OPTS->x_flag_sanitize and
860 ensures the error identifies the requested command line options that have
861 set these flags. */
862 static void
863 report_conflicting_sanitizer_options (struct gcc_options *opts, location_t loc,
864 unsigned int left, unsigned int right)
866 unsigned int left_seen = (opts->x_flag_sanitize & left);
867 unsigned int right_seen = (opts->x_flag_sanitize & right);
868 if (left_seen && right_seen)
870 const char* left_arg = find_sanitizer_argument (opts, left_seen);
871 const char* right_arg = find_sanitizer_argument (opts, right_seen);
872 gcc_assert (left_arg && right_arg);
873 error_at (loc,
874 "%<-fsanitize=%s%> is incompatible with %<-fsanitize=%s%>",
875 left_arg, right_arg);
879 /* After all options at LOC have been read into OPTS and OPTS_SET,
880 finalize settings of those options and diagnose incompatible
881 combinations. */
882 void
883 finish_options (struct gcc_options *opts, struct gcc_options *opts_set,
884 location_t loc)
886 enum unwind_info_type ui_except;
888 if (opts->x_dump_base_name
889 && ! opts->x_dump_base_name_prefixed)
891 const char *sep = opts->x_dump_base_name;
893 for (; *sep; sep++)
894 if (IS_DIR_SEPARATOR (*sep))
895 break;
897 if (*sep)
898 /* If dump_base_path contains subdirectories, don't prepend
899 anything. */;
900 else if (opts->x_dump_dir_name)
901 /* We have a DUMP_DIR_NAME, prepend that. */
902 opts->x_dump_base_name = opts_concat (opts->x_dump_dir_name,
903 opts->x_dump_base_name, NULL);
905 /* It is definitely prefixed now. */
906 opts->x_dump_base_name_prefixed = true;
909 /* Handle related options for unit-at-a-time, toplevel-reorder, and
910 section-anchors. */
911 if (!opts->x_flag_unit_at_a_time)
913 if (opts->x_flag_section_anchors && opts_set->x_flag_section_anchors)
914 error_at (loc, "section anchors must be disabled when unit-at-a-time "
915 "is disabled");
916 opts->x_flag_section_anchors = 0;
917 if (opts->x_flag_toplevel_reorder == 1)
918 error_at (loc, "toplevel reorder must be disabled when unit-at-a-time "
919 "is disabled");
920 opts->x_flag_toplevel_reorder = 0;
923 /* -fself-test depends on the state of the compiler prior to
924 compiling anything. Ideally it should be run on an empty source
925 file. However, in case we get run with actual source, assume
926 -fsyntax-only which will inhibit any compiler initialization
927 which may confuse the self tests. */
928 if (opts->x_flag_self_test)
929 opts->x_flag_syntax_only = 1;
931 if (opts->x_flag_tm && opts->x_flag_non_call_exceptions)
932 sorry ("transactional memory is not supported with non-call exceptions");
934 /* Unless the user has asked for section anchors, we disable toplevel
935 reordering at -O0 to disable transformations that might be surprising
936 to end users and to get -fno-toplevel-reorder tested. */
937 if (!opts->x_optimize
938 && opts->x_flag_toplevel_reorder == 2
939 && !(opts->x_flag_section_anchors && opts_set->x_flag_section_anchors))
941 opts->x_flag_toplevel_reorder = 0;
942 opts->x_flag_section_anchors = 0;
944 if (!opts->x_flag_toplevel_reorder)
946 if (opts->x_flag_section_anchors && opts_set->x_flag_section_anchors)
947 error_at (loc, "section anchors must be disabled when toplevel reorder"
948 " is disabled");
949 opts->x_flag_section_anchors = 0;
952 if (!opts->x_flag_opts_finished)
954 /* We initialize opts->x_flag_pie to -1 so that targets can set a
955 default value. */
956 if (opts->x_flag_pie == -1)
958 /* We initialize opts->x_flag_pic to -1 so that we can tell if
959 -fpic, -fPIC, -fno-pic or -fno-PIC is used. */
960 if (opts->x_flag_pic == -1)
961 opts->x_flag_pie = DEFAULT_FLAG_PIE;
962 else
963 opts->x_flag_pie = 0;
965 /* If -fPIE or -fpie is used, turn on PIC. */
966 if (opts->x_flag_pie)
967 opts->x_flag_pic = opts->x_flag_pie;
968 else if (opts->x_flag_pic == -1)
969 opts->x_flag_pic = 0;
970 if (opts->x_flag_pic && !opts->x_flag_pie)
971 opts->x_flag_shlib = 1;
972 opts->x_flag_opts_finished = true;
975 /* We initialize opts->x_flag_stack_protect to -1 so that targets
976 can set a default value. */
977 if (opts->x_flag_stack_protect == -1)
978 opts->x_flag_stack_protect = DEFAULT_FLAG_SSP;
980 if (opts->x_optimize == 0)
982 /* Inlining does not work if not optimizing,
983 so force it not to be done. */
984 opts->x_warn_inline = 0;
985 opts->x_flag_no_inline = 1;
988 /* The optimization to partition hot and cold basic blocks into separate
989 sections of the .o and executable files does not work (currently)
990 with exception handling. This is because there is no support for
991 generating unwind info. If opts->x_flag_exceptions is turned on
992 we need to turn off the partitioning optimization. */
994 ui_except = targetm_common.except_unwind_info (opts);
996 if (opts->x_flag_exceptions
997 && opts->x_flag_reorder_blocks_and_partition
998 && (ui_except == UI_SJLJ || ui_except >= UI_TARGET))
1000 if (opts_set->x_flag_reorder_blocks_and_partition)
1001 inform (loc,
1002 "%<-freorder-blocks-and-partition%> does not work "
1003 "with exceptions on this architecture");
1004 opts->x_flag_reorder_blocks_and_partition = 0;
1005 opts->x_flag_reorder_blocks = 1;
1008 /* If user requested unwind info, then turn off the partitioning
1009 optimization. */
1011 if (opts->x_flag_unwind_tables
1012 && !targetm_common.unwind_tables_default
1013 && opts->x_flag_reorder_blocks_and_partition
1014 && (ui_except == UI_SJLJ || ui_except >= UI_TARGET))
1016 if (opts_set->x_flag_reorder_blocks_and_partition)
1017 inform (loc,
1018 "%<-freorder-blocks-and-partition%> does not support "
1019 "unwind info on this architecture");
1020 opts->x_flag_reorder_blocks_and_partition = 0;
1021 opts->x_flag_reorder_blocks = 1;
1024 /* If the target requested unwind info, then turn off the partitioning
1025 optimization with a different message. Likewise, if the target does not
1026 support named sections. */
1028 if (opts->x_flag_reorder_blocks_and_partition
1029 && (!targetm_common.have_named_sections
1030 || (opts->x_flag_unwind_tables
1031 && targetm_common.unwind_tables_default
1032 && (ui_except == UI_SJLJ || ui_except >= UI_TARGET))))
1034 if (opts_set->x_flag_reorder_blocks_and_partition)
1035 inform (loc,
1036 "%<-freorder-blocks-and-partition%> does not work "
1037 "on this architecture");
1038 opts->x_flag_reorder_blocks_and_partition = 0;
1039 opts->x_flag_reorder_blocks = 1;
1043 /* Pipelining of outer loops is only possible when general pipelining
1044 capabilities are requested. */
1045 if (!opts->x_flag_sel_sched_pipelining)
1046 opts->x_flag_sel_sched_pipelining_outer_loops = 0;
1048 if (opts->x_flag_conserve_stack)
1050 SET_OPTION_IF_UNSET (opts, opts_set, param_large_stack_frame, 100);
1051 SET_OPTION_IF_UNSET (opts, opts_set, param_stack_frame_growth, 40);
1054 if (opts->x_flag_lto)
1056 #ifdef ENABLE_LTO
1057 opts->x_flag_generate_lto = 1;
1059 /* When generating IL, do not operate in whole-program mode.
1060 Otherwise, symbols will be privatized too early, causing link
1061 errors later. */
1062 opts->x_flag_whole_program = 0;
1063 #else
1064 error_at (loc, "LTO support has not been enabled in this configuration");
1065 #endif
1066 if (!opts->x_flag_fat_lto_objects
1067 && (!HAVE_LTO_PLUGIN
1068 || (opts_set->x_flag_use_linker_plugin
1069 && !opts->x_flag_use_linker_plugin)))
1071 if (opts_set->x_flag_fat_lto_objects)
1072 error_at (loc, "%<-fno-fat-lto-objects%> are supported only with "
1073 "linker plugin");
1074 opts->x_flag_fat_lto_objects = 1;
1077 /* -gsplit-dwarf isn't compatible with LTO, see PR88389. */
1078 if (opts->x_dwarf_split_debug_info)
1080 inform (loc, "%<-gsplit-dwarf%> is not supported with LTO,"
1081 " disabling");
1082 opts->x_dwarf_split_debug_info = 0;
1086 /* We initialize opts->x_flag_split_stack to -1 so that targets can set a
1087 default value if they choose based on other options. */
1088 if (opts->x_flag_split_stack == -1)
1089 opts->x_flag_split_stack = 0;
1090 else if (opts->x_flag_split_stack)
1092 if (!targetm_common.supports_split_stack (true, opts))
1094 error_at (loc, "%<-fsplit-stack%> is not supported by "
1095 "this compiler configuration");
1096 opts->x_flag_split_stack = 0;
1100 /* If stack splitting is turned on, and the user did not explicitly
1101 request function partitioning, turn off partitioning, as it
1102 confuses the linker when trying to handle partitioned split-stack
1103 code that calls a non-split-stack functions. But if partitioning
1104 was turned on explicitly just hope for the best. */
1105 if (opts->x_flag_split_stack
1106 && opts->x_flag_reorder_blocks_and_partition)
1107 SET_OPTION_IF_UNSET (opts, opts_set, flag_reorder_blocks_and_partition, 0);
1109 if (opts->x_flag_reorder_blocks_and_partition)
1110 SET_OPTION_IF_UNSET (opts, opts_set, flag_reorder_functions, 1);
1112 /* The -gsplit-dwarf option requires -ggnu-pubnames. */
1113 if (opts->x_dwarf_split_debug_info)
1114 opts->x_debug_generate_pub_sections = 2;
1116 if ((opts->x_flag_sanitize
1117 & (SANITIZE_USER_ADDRESS | SANITIZE_KERNEL_ADDRESS)) == 0)
1119 if (opts->x_flag_sanitize & SANITIZE_POINTER_COMPARE)
1120 error_at (loc,
1121 "%<-fsanitize=pointer-compare%> must be combined with "
1122 "%<-fsanitize=address%> or %<-fsanitize=kernel-address%>");
1123 if (opts->x_flag_sanitize & SANITIZE_POINTER_SUBTRACT)
1124 error_at (loc,
1125 "%<-fsanitize=pointer-subtract%> must be combined with "
1126 "%<-fsanitize=address%> or %<-fsanitize=kernel-address%>");
1129 /* Address sanitizers conflict with the thread sanitizer. */
1130 report_conflicting_sanitizer_options (opts, loc, SANITIZE_THREAD,
1131 SANITIZE_ADDRESS | SANITIZE_HWADDRESS);
1132 /* The leak sanitizer conflicts with the thread sanitizer. */
1133 report_conflicting_sanitizer_options (opts, loc, SANITIZE_LEAK,
1134 SANITIZE_THREAD);
1136 /* No combination of HWASAN and ASAN work together. */
1137 report_conflicting_sanitizer_options (opts, loc,
1138 SANITIZE_HWADDRESS, SANITIZE_ADDRESS);
1140 /* The userspace and kernel address sanitizers conflict with each other. */
1141 report_conflicting_sanitizer_options (opts, loc, SANITIZE_USER_HWADDRESS,
1142 SANITIZE_KERNEL_HWADDRESS);
1143 report_conflicting_sanitizer_options (opts, loc, SANITIZE_USER_ADDRESS,
1144 SANITIZE_KERNEL_ADDRESS);
1146 /* Check error recovery for -fsanitize-recover option. */
1147 for (int i = 0; sanitizer_opts[i].name != NULL; ++i)
1148 if ((opts->x_flag_sanitize_recover & sanitizer_opts[i].flag)
1149 && !sanitizer_opts[i].can_recover)
1150 error_at (loc, "%<-fsanitize-recover=%s%> is not supported",
1151 sanitizer_opts[i].name);
1153 /* When instrumenting the pointers, we don't want to remove
1154 the null pointer checks. */
1155 if (opts->x_flag_sanitize & (SANITIZE_NULL | SANITIZE_NONNULL_ATTRIBUTE
1156 | SANITIZE_RETURNS_NONNULL_ATTRIBUTE))
1157 opts->x_flag_delete_null_pointer_checks = 0;
1159 /* Aggressive compiler optimizations may cause false negatives. */
1160 if (opts->x_flag_sanitize & ~(SANITIZE_LEAK | SANITIZE_UNREACHABLE))
1161 opts->x_flag_aggressive_loop_optimizations = 0;
1163 /* Enable -fsanitize-address-use-after-scope if either address sanitizer is
1164 enabled. */
1165 if (opts->x_flag_sanitize
1166 & (SANITIZE_USER_ADDRESS | SANITIZE_USER_HWADDRESS))
1167 SET_OPTION_IF_UNSET (opts, opts_set, flag_sanitize_address_use_after_scope,
1168 true);
1170 /* Force -fstack-reuse=none in case -fsanitize-address-use-after-scope
1171 is enabled. */
1172 if (opts->x_flag_sanitize_address_use_after_scope)
1174 if (opts->x_flag_stack_reuse != SR_NONE
1175 && opts_set->x_flag_stack_reuse != SR_NONE)
1176 error_at (loc,
1177 "%<-fsanitize-address-use-after-scope%> requires "
1178 "%<-fstack-reuse=none%> option");
1180 opts->x_flag_stack_reuse = SR_NONE;
1183 if ((opts->x_flag_sanitize & SANITIZE_USER_ADDRESS) && opts->x_flag_tm)
1184 sorry ("transactional memory is not supported with %<-fsanitize=address%>");
1186 if ((opts->x_flag_sanitize & SANITIZE_KERNEL_ADDRESS) && opts->x_flag_tm)
1187 sorry ("transactional memory is not supported with "
1188 "%<-fsanitize=kernel-address%>");
1190 /* Currently live patching is not support for LTO. */
1191 if (opts->x_flag_live_patching && opts->x_flag_lto)
1192 sorry ("live patching is not supported with LTO");
1194 /* Currently vtable verification is not supported for LTO */
1195 if (opts->x_flag_vtable_verify && opts->x_flag_lto)
1196 sorry ("vtable verification is not supported with LTO");
1198 /* Control IPA optimizations based on different -flive-patching level. */
1199 if (opts->x_flag_live_patching)
1200 control_options_for_live_patching (opts, opts_set,
1201 opts->x_flag_live_patching,
1202 loc);
1204 /* Unrolling all loops implies that standard loop unrolling must also
1205 be done. */
1206 if (opts->x_flag_unroll_all_loops)
1207 opts->x_flag_unroll_loops = 1;
1209 /* Allow cunroll to grow size accordingly. */
1210 if (!opts_set->x_flag_cunroll_grow_size)
1211 opts->x_flag_cunroll_grow_size
1212 = (opts->x_flag_unroll_loops
1213 || opts->x_flag_peel_loops
1214 || opts->x_optimize >= 3);
1217 #define LEFT_COLUMN 27
1219 /* Output ITEM, of length ITEM_WIDTH, in the left column,
1220 followed by word-wrapped HELP in a second column. */
1221 static void
1222 wrap_help (const char *help,
1223 const char *item,
1224 unsigned int item_width,
1225 unsigned int columns)
1227 unsigned int col_width = LEFT_COLUMN;
1228 unsigned int remaining, room, len;
1230 remaining = strlen (help);
1234 room = columns - 3 - MAX (col_width, item_width);
1235 if (room > columns)
1236 room = 0;
1237 len = remaining;
1239 if (room < len)
1241 unsigned int i;
1243 for (i = 0; help[i]; i++)
1245 if (i >= room && len != remaining)
1246 break;
1247 if (help[i] == ' ')
1248 len = i;
1249 else if ((help[i] == '-' || help[i] == '/')
1250 && help[i + 1] != ' '
1251 && i > 0 && ISALPHA (help[i - 1]))
1252 len = i + 1;
1256 printf (" %-*.*s %.*s\n", col_width, item_width, item, len, help);
1257 item_width = 0;
1258 while (help[len] == ' ')
1259 len++;
1260 help += len;
1261 remaining -= len;
1263 while (remaining);
1266 /* Data structure used to print list of valid option values. */
1268 class option_help_tuple
1270 public:
1271 option_help_tuple (int code, vec<const char *> values):
1272 m_code (code), m_values (values)
1275 /* Code of an option. */
1276 int m_code;
1278 /* List of possible values. */
1279 vec<const char *> m_values;
1282 /* Print help for a specific front-end, etc. */
1283 static void
1284 print_filtered_help (unsigned int include_flags,
1285 unsigned int exclude_flags,
1286 unsigned int any_flags,
1287 unsigned int columns,
1288 struct gcc_options *opts,
1289 unsigned int lang_mask)
1291 unsigned int i;
1292 const char *help;
1293 bool found = false;
1294 bool displayed = false;
1295 char new_help[256];
1297 if (!opts->x_help_printed)
1298 opts->x_help_printed = XCNEWVAR (char, cl_options_count);
1300 if (!opts->x_help_enum_printed)
1301 opts->x_help_enum_printed = XCNEWVAR (char, cl_enums_count);
1303 auto_vec<option_help_tuple> help_tuples;
1305 for (i = 0; i < cl_options_count; i++)
1307 const struct cl_option *option = cl_options + i;
1308 unsigned int len;
1309 const char *opt;
1310 const char *tab;
1312 if (include_flags == 0
1313 || ((option->flags & include_flags) != include_flags))
1315 if ((option->flags & any_flags) == 0)
1316 continue;
1319 /* Skip unwanted switches. */
1320 if ((option->flags & exclude_flags) != 0)
1321 continue;
1323 /* The driver currently prints its own help text. */
1324 if ((option->flags & CL_DRIVER) != 0
1325 && (option->flags & (((1U << cl_lang_count) - 1)
1326 | CL_COMMON | CL_TARGET)) == 0)
1327 continue;
1329 /* If an option contains a language specification,
1330 exclude it from common unless all languages are present. */
1331 if ((include_flags & CL_COMMON)
1332 && !(option->flags & CL_DRIVER)
1333 && (option->flags & CL_LANG_ALL)
1334 && (option->flags & CL_LANG_ALL) != CL_LANG_ALL)
1335 continue;
1337 found = true;
1338 /* Skip switches that have already been printed. */
1339 if (opts->x_help_printed[i])
1340 continue;
1342 opts->x_help_printed[i] = true;
1344 help = option->help;
1345 if (help == NULL)
1347 if (exclude_flags & CL_UNDOCUMENTED)
1348 continue;
1350 help = undocumented_msg;
1353 /* Get the translation. */
1354 help = _(help);
1356 if (option->alias_target < N_OPTS
1357 && cl_options [option->alias_target].help)
1359 const struct cl_option *target = cl_options + option->alias_target;
1360 if (option->help == NULL)
1362 /* The option is undocumented but is an alias for an option that
1363 is documented. If the option has alias arguments, then its
1364 purpose is to provide certain arguments to the other option, so
1365 inform the reader of this. Otherwise, point the reader to the
1366 other option in preference to the former. */
1368 if (option->alias_arg)
1370 if (option->neg_alias_arg)
1371 snprintf (new_help, sizeof new_help,
1372 _("Same as %s%s (or, in negated form, %s%s)."),
1373 target->opt_text, option->alias_arg,
1374 target->opt_text, option->neg_alias_arg);
1375 else
1376 snprintf (new_help, sizeof new_help,
1377 _("Same as %s%s."),
1378 target->opt_text, option->alias_arg);
1380 else
1381 snprintf (new_help, sizeof new_help,
1382 _("Same as %s."),
1383 target->opt_text);
1385 else
1387 /* For documented options with aliases, mention the aliased
1388 option's name for reference. */
1389 snprintf (new_help, sizeof new_help,
1390 _("%s Same as %s."),
1391 help, cl_options [option->alias_target].opt_text);
1394 help = new_help;
1397 if (option->warn_message)
1399 /* Mention that the use of the option will trigger a warning. */
1400 if (help == new_help)
1401 snprintf (new_help + strlen (new_help),
1402 sizeof new_help - strlen (new_help),
1403 " %s", _(use_diagnosed_msg));
1404 else
1405 snprintf (new_help, sizeof new_help,
1406 "%s %s", help, _(use_diagnosed_msg));
1408 help = new_help;
1411 /* Find the gap between the name of the
1412 option and its descriptive text. */
1413 tab = strchr (help, '\t');
1414 if (tab)
1416 len = tab - help;
1417 opt = help;
1418 help = tab + 1;
1420 else
1422 opt = option->opt_text;
1423 len = strlen (opt);
1426 /* With the -Q option enabled we change the descriptive text associated
1427 with an option to be an indication of its current setting. */
1428 if (!opts->x_quiet_flag)
1430 void *flag_var = option_flag_var (i, opts);
1432 if (len < (LEFT_COLUMN + 2))
1433 strcpy (new_help, "\t\t");
1434 else
1435 strcpy (new_help, "\t");
1437 /* Set to print whether the option is enabled or disabled,
1438 or, if it's an alias for another option, the name of
1439 the aliased option. */
1440 bool print_state = false;
1442 if (flag_var != NULL
1443 && option->var_type != CLVC_DEFER)
1445 /* If OPTION is only available for a specific subset
1446 of languages other than this one, mention them. */
1447 bool avail_for_lang = true;
1448 if (unsigned langset = option->flags & CL_LANG_ALL)
1450 if (!(langset & lang_mask))
1452 avail_for_lang = false;
1453 strcat (new_help, _("[available in "));
1454 for (unsigned i = 0, n = 0; (1U << i) < CL_LANG_ALL; ++i)
1455 if (langset & (1U << i))
1457 if (n++)
1458 strcat (new_help, ", ");
1459 strcat (new_help, lang_names[i]);
1461 strcat (new_help, "]");
1464 if (!avail_for_lang)
1465 ; /* Print nothing else if the option is not available
1466 in the current language. */
1467 else if (option->flags & CL_JOINED)
1469 if (option->var_type == CLVC_STRING)
1471 if (* (const char **) flag_var != NULL)
1472 snprintf (new_help + strlen (new_help),
1473 sizeof (new_help) - strlen (new_help),
1474 "%s", * (const char **) flag_var);
1476 else if (option->var_type == CLVC_ENUM)
1478 const struct cl_enum *e = &cl_enums[option->var_enum];
1479 int value;
1480 const char *arg = NULL;
1482 value = e->get (flag_var);
1483 enum_value_to_arg (e->values, &arg, value, lang_mask);
1484 if (arg == NULL)
1485 arg = _("[default]");
1486 snprintf (new_help + strlen (new_help),
1487 sizeof (new_help) - strlen (new_help),
1488 "%s", arg);
1490 else
1492 if (option->cl_host_wide_int)
1493 sprintf (new_help + strlen (new_help),
1494 _("%llu bytes"), (unsigned long long)
1495 *(unsigned HOST_WIDE_INT *) flag_var);
1496 else
1497 sprintf (new_help + strlen (new_help),
1498 "%i", * (int *) flag_var);
1501 else
1502 print_state = true;
1504 else
1505 /* When there is no argument, print the option state only
1506 if the option takes no argument. */
1507 print_state = !(option->flags & CL_JOINED);
1509 if (print_state)
1511 if (option->alias_target < N_OPTS
1512 && option->alias_target != OPT_SPECIAL_warn_removed
1513 && option->alias_target != OPT_SPECIAL_ignore
1514 && option->alias_target != OPT_SPECIAL_input_file
1515 && option->alias_target != OPT_SPECIAL_program_name
1516 && option->alias_target != OPT_SPECIAL_unknown)
1518 const struct cl_option *target
1519 = &cl_options[option->alias_target];
1520 sprintf (new_help + strlen (new_help), "%s%s",
1521 target->opt_text,
1522 option->alias_arg ? option->alias_arg : "");
1524 else if (option->alias_target == OPT_SPECIAL_ignore)
1525 strcat (new_help, ("[ignored]"));
1526 else
1528 /* Print the state for an on/off option. */
1529 int ena = option_enabled (i, lang_mask, opts);
1530 if (ena > 0)
1531 strcat (new_help, _("[enabled]"));
1532 else if (ena == 0)
1533 strcat (new_help, _("[disabled]"));
1537 help = new_help;
1540 if (option->range_max != -1)
1542 char b[128];
1543 snprintf (b, sizeof (b), "<%d,%d>", option->range_min,
1544 option->range_max);
1545 opt = concat (opt, b, NULL);
1546 len += strlen (b);
1549 wrap_help (help, opt, len, columns);
1550 displayed = true;
1552 if (option->var_type == CLVC_ENUM
1553 && opts->x_help_enum_printed[option->var_enum] != 2)
1554 opts->x_help_enum_printed[option->var_enum] = 1;
1555 else
1557 vec<const char *> option_values
1558 = targetm_common.get_valid_option_values (i, NULL);
1559 if (!option_values.is_empty ())
1560 help_tuples.safe_push (option_help_tuple (i, option_values));
1564 if (! found)
1566 unsigned int langs = include_flags & CL_LANG_ALL;
1568 if (langs == 0)
1569 printf (_(" No options with the desired characteristics were found\n"));
1570 else
1572 unsigned int i;
1574 /* PR 31349: Tell the user how to see all of the
1575 options supported by a specific front end. */
1576 for (i = 0; (1U << i) < CL_LANG_ALL; i ++)
1577 if ((1U << i) & langs)
1578 printf (_(" None found. Use --help=%s to show *all* the options supported by the %s front-end.\n"),
1579 lang_names[i], lang_names[i]);
1583 else if (! displayed)
1584 printf (_(" All options with the desired characteristics have already been displayed\n"));
1586 putchar ('\n');
1588 /* Print details of enumerated option arguments, if those
1589 enumerations have help text headings provided. If no help text
1590 is provided, presume that the possible values are listed in the
1591 help text for the relevant options. */
1592 for (i = 0; i < cl_enums_count; i++)
1594 unsigned int j, pos;
1596 if (opts->x_help_enum_printed[i] != 1)
1597 continue;
1598 if (cl_enums[i].help == NULL)
1599 continue;
1600 printf (" %s\n ", _(cl_enums[i].help));
1601 pos = 4;
1602 for (j = 0; cl_enums[i].values[j].arg != NULL; j++)
1604 unsigned int len = strlen (cl_enums[i].values[j].arg);
1606 if (pos > 4 && pos + 1 + len <= columns)
1608 printf (" %s", cl_enums[i].values[j].arg);
1609 pos += 1 + len;
1611 else
1613 if (pos > 4)
1615 printf ("\n ");
1616 pos = 4;
1618 printf ("%s", cl_enums[i].values[j].arg);
1619 pos += len;
1622 printf ("\n\n");
1623 opts->x_help_enum_printed[i] = 2;
1626 for (unsigned i = 0; i < help_tuples.length (); i++)
1628 const struct cl_option *option = cl_options + help_tuples[i].m_code;
1629 printf (_(" Known valid arguments for %s option:\n "),
1630 option->opt_text);
1631 for (unsigned j = 0; j < help_tuples[i].m_values.length (); j++)
1632 printf (" %s", help_tuples[i].m_values[j]);
1633 printf ("\n\n");
1637 /* Display help for a specified type of option.
1638 The options must have ALL of the INCLUDE_FLAGS set
1639 ANY of the flags in the ANY_FLAGS set
1640 and NONE of the EXCLUDE_FLAGS set. The current option state is in
1641 OPTS; LANG_MASK is used for interpreting enumerated option state. */
1642 static void
1643 print_specific_help (unsigned int include_flags,
1644 unsigned int exclude_flags,
1645 unsigned int any_flags,
1646 struct gcc_options *opts,
1647 unsigned int lang_mask)
1649 unsigned int all_langs_mask = (1U << cl_lang_count) - 1;
1650 const char * description = NULL;
1651 const char * descrip_extra = "";
1652 size_t i;
1653 unsigned int flag;
1655 /* Sanity check: Make sure that we do not have more
1656 languages than we have bits available to enumerate them. */
1657 gcc_assert ((1U << cl_lang_count) <= CL_MIN_OPTION_CLASS);
1659 /* If we have not done so already, obtain
1660 the desired maximum width of the output. */
1661 if (opts->x_help_columns == 0)
1663 opts->x_help_columns = get_terminal_width ();
1664 if (opts->x_help_columns == INT_MAX)
1665 /* Use a reasonable default. */
1666 opts->x_help_columns = 80;
1669 /* Decide upon the title for the options that we are going to display. */
1670 for (i = 0, flag = 1; flag <= CL_MAX_OPTION_CLASS; flag <<= 1, i ++)
1672 switch (flag & include_flags)
1674 case 0:
1675 case CL_DRIVER:
1676 break;
1678 case CL_TARGET:
1679 description = _("The following options are target specific");
1680 break;
1681 case CL_WARNING:
1682 description = _("The following options control compiler warning messages");
1683 break;
1684 case CL_OPTIMIZATION:
1685 description = _("The following options control optimizations");
1686 break;
1687 case CL_COMMON:
1688 description = _("The following options are language-independent");
1689 break;
1690 case CL_PARAMS:
1691 description = _("The following options control parameters");
1692 break;
1693 default:
1694 if (i >= cl_lang_count)
1695 break;
1696 if (exclude_flags & all_langs_mask)
1697 description = _("The following options are specific to just the language ");
1698 else
1699 description = _("The following options are supported by the language ");
1700 descrip_extra = lang_names [i];
1701 break;
1705 if (description == NULL)
1707 if (any_flags == 0)
1709 if (include_flags & CL_UNDOCUMENTED)
1710 description = _("The following options are not documented");
1711 else if (include_flags & CL_SEPARATE)
1712 description = _("The following options take separate arguments");
1713 else if (include_flags & CL_JOINED)
1714 description = _("The following options take joined arguments");
1715 else
1717 internal_error ("unrecognized %<include_flags 0x%x%> passed "
1718 "to %<print_specific_help%>",
1719 include_flags);
1720 return;
1723 else
1725 if (any_flags & all_langs_mask)
1726 description = _("The following options are language-related");
1727 else
1728 description = _("The following options are language-independent");
1732 printf ("%s%s:\n", description, descrip_extra);
1733 print_filtered_help (include_flags, exclude_flags, any_flags,
1734 opts->x_help_columns, opts, lang_mask);
1737 /* Enable FDO-related flags. */
1739 static void
1740 enable_fdo_optimizations (struct gcc_options *opts,
1741 struct gcc_options *opts_set,
1742 int value)
1744 SET_OPTION_IF_UNSET (opts, opts_set, flag_branch_probabilities, value);
1745 SET_OPTION_IF_UNSET (opts, opts_set, flag_profile_values, value);
1746 SET_OPTION_IF_UNSET (opts, opts_set, flag_unroll_loops, value);
1747 SET_OPTION_IF_UNSET (opts, opts_set, flag_peel_loops, value);
1748 SET_OPTION_IF_UNSET (opts, opts_set, flag_tracer, value);
1749 SET_OPTION_IF_UNSET (opts, opts_set, flag_value_profile_transformations,
1750 value);
1751 SET_OPTION_IF_UNSET (opts, opts_set, flag_inline_functions, value);
1752 SET_OPTION_IF_UNSET (opts, opts_set, flag_ipa_cp, value);
1753 if (value)
1755 SET_OPTION_IF_UNSET (opts, opts_set, flag_ipa_cp_clone, 1);
1756 SET_OPTION_IF_UNSET (opts, opts_set, flag_ipa_bit_cp, 1);
1758 SET_OPTION_IF_UNSET (opts, opts_set, flag_predictive_commoning, value);
1759 SET_OPTION_IF_UNSET (opts, opts_set, flag_split_loops, value);
1760 SET_OPTION_IF_UNSET (opts, opts_set, flag_unswitch_loops, value);
1761 SET_OPTION_IF_UNSET (opts, opts_set, flag_gcse_after_reload, value);
1762 SET_OPTION_IF_UNSET (opts, opts_set, flag_tree_loop_vectorize, value);
1763 SET_OPTION_IF_UNSET (opts, opts_set, flag_tree_slp_vectorize, value);
1764 SET_OPTION_IF_UNSET (opts, opts_set, flag_version_loops_for_strides, value);
1765 SET_OPTION_IF_UNSET (opts, opts_set, flag_vect_cost_model,
1766 VECT_COST_MODEL_DYNAMIC);
1767 SET_OPTION_IF_UNSET (opts, opts_set, flag_tree_loop_distribute_patterns,
1768 value);
1769 SET_OPTION_IF_UNSET (opts, opts_set, flag_loop_interchange, value);
1770 SET_OPTION_IF_UNSET (opts, opts_set, flag_unroll_jam, value);
1771 SET_OPTION_IF_UNSET (opts, opts_set, flag_tree_loop_distribution, value);
1774 /* -f{,no-}sanitize{,-recover}= suboptions. */
1775 const struct sanitizer_opts_s sanitizer_opts[] =
1777 #define SANITIZER_OPT(name, flags, recover) \
1778 { #name, flags, sizeof #name - 1, recover }
1779 SANITIZER_OPT (address, (SANITIZE_ADDRESS | SANITIZE_USER_ADDRESS), true),
1780 SANITIZER_OPT (hwaddress, (SANITIZE_HWADDRESS | SANITIZE_USER_HWADDRESS),
1781 true),
1782 SANITIZER_OPT (kernel-address, (SANITIZE_ADDRESS | SANITIZE_KERNEL_ADDRESS),
1783 true),
1784 SANITIZER_OPT (kernel-hwaddress,
1785 (SANITIZE_HWADDRESS | SANITIZE_KERNEL_HWADDRESS),
1786 true),
1787 SANITIZER_OPT (pointer-compare, SANITIZE_POINTER_COMPARE, true),
1788 SANITIZER_OPT (pointer-subtract, SANITIZE_POINTER_SUBTRACT, true),
1789 SANITIZER_OPT (thread, SANITIZE_THREAD, false),
1790 SANITIZER_OPT (leak, SANITIZE_LEAK, false),
1791 SANITIZER_OPT (shift, SANITIZE_SHIFT, true),
1792 SANITIZER_OPT (shift-base, SANITIZE_SHIFT_BASE, true),
1793 SANITIZER_OPT (shift-exponent, SANITIZE_SHIFT_EXPONENT, true),
1794 SANITIZER_OPT (integer-divide-by-zero, SANITIZE_DIVIDE, true),
1795 SANITIZER_OPT (undefined, SANITIZE_UNDEFINED, true),
1796 SANITIZER_OPT (unreachable, SANITIZE_UNREACHABLE, false),
1797 SANITIZER_OPT (vla-bound, SANITIZE_VLA, true),
1798 SANITIZER_OPT (return, SANITIZE_RETURN, false),
1799 SANITIZER_OPT (null, SANITIZE_NULL, true),
1800 SANITIZER_OPT (signed-integer-overflow, SANITIZE_SI_OVERFLOW, true),
1801 SANITIZER_OPT (bool, SANITIZE_BOOL, true),
1802 SANITIZER_OPT (enum, SANITIZE_ENUM, true),
1803 SANITIZER_OPT (float-divide-by-zero, SANITIZE_FLOAT_DIVIDE, true),
1804 SANITIZER_OPT (float-cast-overflow, SANITIZE_FLOAT_CAST, true),
1805 SANITIZER_OPT (bounds, SANITIZE_BOUNDS, true),
1806 SANITIZER_OPT (bounds-strict, SANITIZE_BOUNDS | SANITIZE_BOUNDS_STRICT, true),
1807 SANITIZER_OPT (alignment, SANITIZE_ALIGNMENT, true),
1808 SANITIZER_OPT (nonnull-attribute, SANITIZE_NONNULL_ATTRIBUTE, true),
1809 SANITIZER_OPT (returns-nonnull-attribute, SANITIZE_RETURNS_NONNULL_ATTRIBUTE,
1810 true),
1811 SANITIZER_OPT (object-size, SANITIZE_OBJECT_SIZE, true),
1812 SANITIZER_OPT (vptr, SANITIZE_VPTR, true),
1813 SANITIZER_OPT (pointer-overflow, SANITIZE_POINTER_OVERFLOW, true),
1814 SANITIZER_OPT (builtin, SANITIZE_BUILTIN, true),
1815 SANITIZER_OPT (all, ~0U, true),
1816 #undef SANITIZER_OPT
1817 { NULL, 0U, 0UL, false }
1820 /* -f{,no-}sanitize-coverage= suboptions. */
1821 const struct sanitizer_opts_s coverage_sanitizer_opts[] =
1823 #define COVERAGE_SANITIZER_OPT(name, flags) \
1824 { #name, flags, sizeof #name - 1, true }
1825 COVERAGE_SANITIZER_OPT (trace-pc, SANITIZE_COV_TRACE_PC),
1826 COVERAGE_SANITIZER_OPT (trace-cmp, SANITIZE_COV_TRACE_CMP),
1827 #undef COVERAGE_SANITIZER_OPT
1828 { NULL, 0U, 0UL, false }
1831 /* -fzero-call-used-regs= suboptions. */
1832 const struct zero_call_used_regs_opts_s zero_call_used_regs_opts[] =
1834 #define ZERO_CALL_USED_REGS_OPT(name, flags) \
1835 { #name, flags }
1836 ZERO_CALL_USED_REGS_OPT (skip, zero_regs_flags::SKIP),
1837 ZERO_CALL_USED_REGS_OPT (used-gpr-arg, zero_regs_flags::USED_GPR_ARG),
1838 ZERO_CALL_USED_REGS_OPT (used-gpr, zero_regs_flags::USED_GPR),
1839 ZERO_CALL_USED_REGS_OPT (used-arg, zero_regs_flags::USED_ARG),
1840 ZERO_CALL_USED_REGS_OPT (used, zero_regs_flags::USED),
1841 ZERO_CALL_USED_REGS_OPT (all-gpr-arg, zero_regs_flags::ALL_GPR_ARG),
1842 ZERO_CALL_USED_REGS_OPT (all-gpr, zero_regs_flags::ALL_GPR),
1843 ZERO_CALL_USED_REGS_OPT (all-arg, zero_regs_flags::ALL_ARG),
1844 ZERO_CALL_USED_REGS_OPT (all, zero_regs_flags::ALL),
1845 #undef ZERO_CALL_USED_REGS_OPT
1846 {NULL, 0U}
1849 /* A struct for describing a run of chars within a string. */
1851 class string_fragment
1853 public:
1854 string_fragment (const char *start, size_t len)
1855 : m_start (start), m_len (len) {}
1857 const char *m_start;
1858 size_t m_len;
1861 /* Specialization of edit_distance_traits for string_fragment,
1862 for use by get_closest_sanitizer_option. */
1864 template <>
1865 struct edit_distance_traits<const string_fragment &>
1867 static size_t get_length (const string_fragment &fragment)
1869 return fragment.m_len;
1872 static const char *get_string (const string_fragment &fragment)
1874 return fragment.m_start;
1878 /* Given ARG, an unrecognized sanitizer option, return the best
1879 matching sanitizer option, or NULL if there isn't one.
1880 OPTS is array of candidate sanitizer options.
1881 CODE is OPT_fsanitize_, OPT_fsanitize_recover_ or
1882 OPT_fsanitize_coverage_.
1883 VALUE is non-zero for the regular form of the option, zero
1884 for the "no-" form (e.g. "-fno-sanitize-recover="). */
1886 static const char *
1887 get_closest_sanitizer_option (const string_fragment &arg,
1888 const struct sanitizer_opts_s *opts,
1889 enum opt_code code, int value)
1891 best_match <const string_fragment &, const char*> bm (arg);
1892 for (int i = 0; opts[i].name != NULL; ++i)
1894 /* -fsanitize=all is not valid, so don't offer it. */
1895 if (code == OPT_fsanitize_
1896 && opts[i].flag == ~0U
1897 && value)
1898 continue;
1900 /* For -fsanitize-recover= (and not -fno-sanitize-recover=),
1901 don't offer the non-recoverable options. */
1902 if (code == OPT_fsanitize_recover_
1903 && !opts[i].can_recover
1904 && value)
1905 continue;
1907 bm.consider (opts[i].name);
1909 return bm.get_best_meaningful_candidate ();
1912 /* Parse comma separated sanitizer suboptions from P for option SCODE,
1913 adjust previous FLAGS and return new ones. If COMPLAIN is false,
1914 don't issue diagnostics. */
1916 unsigned int
1917 parse_sanitizer_options (const char *p, location_t loc, int scode,
1918 unsigned int flags, int value, bool complain)
1920 enum opt_code code = (enum opt_code) scode;
1922 const struct sanitizer_opts_s *opts;
1923 if (code == OPT_fsanitize_coverage_)
1924 opts = coverage_sanitizer_opts;
1925 else
1926 opts = sanitizer_opts;
1928 while (*p != 0)
1930 size_t len, i;
1931 bool found = false;
1932 const char *comma = strchr (p, ',');
1934 if (comma == NULL)
1935 len = strlen (p);
1936 else
1937 len = comma - p;
1938 if (len == 0)
1940 p = comma + 1;
1941 continue;
1944 /* Check to see if the string matches an option class name. */
1945 for (i = 0; opts[i].name != NULL; ++i)
1946 if (len == opts[i].len && memcmp (p, opts[i].name, len) == 0)
1948 /* Handle both -fsanitize and -fno-sanitize cases. */
1949 if (value && opts[i].flag == ~0U)
1951 if (code == OPT_fsanitize_)
1953 if (complain)
1954 error_at (loc, "%<-fsanitize=all%> option is not valid");
1956 else
1957 flags |= ~(SANITIZE_THREAD | SANITIZE_LEAK
1958 | SANITIZE_UNREACHABLE | SANITIZE_RETURN);
1960 else if (value)
1962 /* Do not enable -fsanitize-recover=unreachable and
1963 -fsanitize-recover=return if -fsanitize-recover=undefined
1964 is selected. */
1965 if (code == OPT_fsanitize_recover_
1966 && opts[i].flag == SANITIZE_UNDEFINED)
1967 flags |= (SANITIZE_UNDEFINED
1968 & ~(SANITIZE_UNREACHABLE | SANITIZE_RETURN));
1969 else
1970 flags |= opts[i].flag;
1972 else
1973 flags &= ~opts[i].flag;
1974 found = true;
1975 break;
1978 if (! found && complain)
1980 const char *hint
1981 = get_closest_sanitizer_option (string_fragment (p, len),
1982 opts, code, value);
1984 const char *suffix;
1985 if (code == OPT_fsanitize_recover_)
1986 suffix = "-recover";
1987 else if (code == OPT_fsanitize_coverage_)
1988 suffix = "-coverage";
1989 else
1990 suffix = "";
1992 if (hint)
1993 error_at (loc,
1994 "unrecognized argument to %<-f%ssanitize%s=%> "
1995 "option: %q.*s; did you mean %qs?",
1996 value ? "" : "no-",
1997 suffix, (int) len, p, hint);
1998 else
1999 error_at (loc,
2000 "unrecognized argument to %<-f%ssanitize%s=%> option: "
2001 "%q.*s", value ? "" : "no-",
2002 suffix, (int) len, p);
2005 if (comma == NULL)
2006 break;
2007 p = comma + 1;
2009 return flags;
2012 /* Parse string values of no_sanitize attribute passed in VALUE.
2013 Values are separated with comma. */
2015 unsigned int
2016 parse_no_sanitize_attribute (char *value)
2018 unsigned int flags = 0;
2019 unsigned int i;
2020 char *q = strtok (value, ",");
2022 while (q != NULL)
2024 for (i = 0; sanitizer_opts[i].name != NULL; ++i)
2025 if (strcmp (sanitizer_opts[i].name, q) == 0)
2027 flags |= sanitizer_opts[i].flag;
2028 if (sanitizer_opts[i].flag == SANITIZE_UNDEFINED)
2029 flags |= SANITIZE_UNDEFINED_NONDEFAULT;
2030 break;
2033 if (sanitizer_opts[i].name == NULL)
2034 warning (OPT_Wattributes,
2035 "%qs attribute directive ignored", q);
2037 q = strtok (NULL, ",");
2040 return flags;
2043 /* Parse -fzero-call-used-regs suboptions from ARG, return the FLAGS. */
2045 unsigned int
2046 parse_zero_call_used_regs_options (const char *arg)
2048 unsigned int flags = 0;
2050 /* Check to see if the string matches a sub-option name. */
2051 for (unsigned int i = 0; zero_call_used_regs_opts[i].name != NULL; ++i)
2052 if (strcmp (arg, zero_call_used_regs_opts[i].name) == 0)
2054 flags = zero_call_used_regs_opts[i].flag;
2055 break;
2058 if (!flags)
2059 error ("unrecognized argument to %<-fzero-call-used-regs=%>: %qs", arg);
2061 return flags;
2064 /* Parse -falign-NAME format for a FLAG value. Return individual
2065 parsed integer values into RESULT_VALUES array. If REPORT_ERROR is
2066 set, print error message at LOC location. */
2068 bool
2069 parse_and_check_align_values (const char *flag,
2070 const char *name,
2071 auto_vec<unsigned> &result_values,
2072 bool report_error,
2073 location_t loc)
2075 char *str = xstrdup (flag);
2076 for (char *p = strtok (str, ":"); p; p = strtok (NULL, ":"))
2078 char *end;
2079 int v = strtol (p, &end, 10);
2080 if (*end != '\0' || v < 0)
2082 if (report_error)
2083 error_at (loc, "invalid arguments for %<-falign-%s%> option: %qs",
2084 name, flag);
2086 return false;
2089 result_values.safe_push ((unsigned)v);
2092 free (str);
2094 /* Check that we have a correct number of values. */
2095 if (result_values.is_empty () || result_values.length () > 4)
2097 if (report_error)
2098 error_at (loc, "invalid number of arguments for %<-falign-%s%> "
2099 "option: %qs", name, flag);
2100 return false;
2103 for (unsigned i = 0; i < result_values.length (); i++)
2104 if (result_values[i] > MAX_CODE_ALIGN_VALUE)
2106 if (report_error)
2107 error_at (loc, "%<-falign-%s%> is not between 0 and %d",
2108 name, MAX_CODE_ALIGN_VALUE);
2109 return false;
2112 return true;
2115 /* Check that alignment value FLAG for -falign-NAME is valid at a given
2116 location LOC. OPT_STR points to the stored -falign-NAME=argument and
2117 OPT_FLAG points to the associated -falign-NAME on/off flag. */
2119 static void
2120 check_alignment_argument (location_t loc, const char *flag, const char *name,
2121 int *opt_flag, const char **opt_str)
2123 auto_vec<unsigned> align_result;
2124 parse_and_check_align_values (flag, name, align_result, true, loc);
2126 if (align_result.length() >= 1 && align_result[0] == 0)
2128 *opt_flag = 1;
2129 *opt_str = NULL;
2133 /* Print help when OPT__help_ is set. */
2135 void
2136 print_help (struct gcc_options *opts, unsigned int lang_mask,
2137 const char *help_option_argument)
2139 const char *a = help_option_argument;
2140 unsigned int include_flags = 0;
2141 /* Note - by default we include undocumented options when listing
2142 specific classes. If you only want to see documented options
2143 then add ",^undocumented" to the --help= option. E.g.:
2145 --help=target,^undocumented */
2146 unsigned int exclude_flags = 0;
2148 if (lang_mask == CL_DRIVER)
2149 return;
2151 /* Walk along the argument string, parsing each word in turn.
2152 The format is:
2153 arg = [^]{word}[,{arg}]
2154 word = {optimizers|target|warnings|undocumented|
2155 params|common|<language>} */
2156 while (*a != 0)
2158 static const struct
2160 const char *string;
2161 unsigned int flag;
2163 specifics[] =
2165 { "optimizers", CL_OPTIMIZATION },
2166 { "target", CL_TARGET },
2167 { "warnings", CL_WARNING },
2168 { "undocumented", CL_UNDOCUMENTED },
2169 { "params", CL_PARAMS },
2170 { "joined", CL_JOINED },
2171 { "separate", CL_SEPARATE },
2172 { "common", CL_COMMON },
2173 { NULL, 0 }
2175 unsigned int *pflags;
2176 const char *comma;
2177 unsigned int lang_flag, specific_flag;
2178 unsigned int len;
2179 unsigned int i;
2181 if (*a == '^')
2183 ++a;
2184 if (*a == '\0')
2186 error ("missing argument to %qs", "--help=^");
2187 break;
2189 pflags = &exclude_flags;
2191 else
2192 pflags = &include_flags;
2194 comma = strchr (a, ',');
2195 if (comma == NULL)
2196 len = strlen (a);
2197 else
2198 len = comma - a;
2199 if (len == 0)
2201 a = comma + 1;
2202 continue;
2205 /* Check to see if the string matches an option class name. */
2206 for (i = 0, specific_flag = 0; specifics[i].string != NULL; i++)
2207 if (strncasecmp (a, specifics[i].string, len) == 0)
2209 specific_flag = specifics[i].flag;
2210 break;
2213 /* Check to see if the string matches a language name.
2214 Note - we rely upon the alpha-sorted nature of the entries in
2215 the lang_names array, specifically that shorter names appear
2216 before their longer variants. (i.e. C before C++). That way
2217 when we are attempting to match --help=c for example we will
2218 match with C first and not C++. */
2219 for (i = 0, lang_flag = 0; i < cl_lang_count; i++)
2220 if (strncasecmp (a, lang_names[i], len) == 0)
2222 lang_flag = 1U << i;
2223 break;
2226 if (specific_flag != 0)
2228 if (lang_flag == 0)
2229 *pflags |= specific_flag;
2230 else
2232 /* The option's argument matches both the start of a
2233 language name and the start of an option class name.
2234 We have a special case for when the user has
2235 specified "--help=c", but otherwise we have to issue
2236 a warning. */
2237 if (strncasecmp (a, "c", len) == 0)
2238 *pflags |= lang_flag;
2239 else
2240 warning (0,
2241 "%<--help%> argument %q.*s is ambiguous, "
2242 "please be more specific",
2243 len, a);
2246 else if (lang_flag != 0)
2247 *pflags |= lang_flag;
2248 else
2249 warning (0,
2250 "unrecognized argument to %<--help=%> option: %q.*s",
2251 len, a);
2253 if (comma == NULL)
2254 break;
2255 a = comma + 1;
2258 /* We started using PerFunction/Optimization for parameters and
2259 a warning. We should exclude these from optimization options. */
2260 if (include_flags & CL_OPTIMIZATION)
2261 exclude_flags |= CL_WARNING;
2262 if (!(include_flags & CL_PARAMS))
2263 exclude_flags |= CL_PARAMS;
2265 if (include_flags)
2266 print_specific_help (include_flags, exclude_flags, 0, opts,
2267 lang_mask);
2270 /* Handle target- and language-independent options. Return zero to
2271 generate an "unknown option" message. Only options that need
2272 extra handling need to be listed here; if you simply want
2273 DECODED->value assigned to a variable, it happens automatically. */
2275 bool
2276 common_handle_option (struct gcc_options *opts,
2277 struct gcc_options *opts_set,
2278 const struct cl_decoded_option *decoded,
2279 unsigned int lang_mask, int kind ATTRIBUTE_UNUSED,
2280 location_t loc,
2281 const struct cl_option_handlers *handlers,
2282 diagnostic_context *dc,
2283 void (*target_option_override_hook) (void))
2285 size_t scode = decoded->opt_index;
2286 const char *arg = decoded->arg;
2287 HOST_WIDE_INT value = decoded->value;
2288 enum opt_code code = (enum opt_code) scode;
2290 gcc_assert (decoded->canonical_option_num_elements <= 2);
2292 switch (code)
2294 case OPT__help:
2296 unsigned int all_langs_mask = (1U << cl_lang_count) - 1;
2297 unsigned int undoc_mask;
2298 unsigned int i;
2300 if (lang_mask == CL_DRIVER)
2301 break;
2303 undoc_mask = ((opts->x_verbose_flag | opts->x_extra_warnings)
2305 : CL_UNDOCUMENTED);
2306 target_option_override_hook ();
2307 /* First display any single language specific options. */
2308 for (i = 0; i < cl_lang_count; i++)
2309 print_specific_help
2310 (1U << i, (all_langs_mask & (~ (1U << i))) | undoc_mask, 0, opts,
2311 lang_mask);
2312 /* Next display any multi language specific options. */
2313 print_specific_help (0, undoc_mask, all_langs_mask, opts, lang_mask);
2314 /* Then display any remaining, non-language options. */
2315 for (i = CL_MIN_OPTION_CLASS; i <= CL_MAX_OPTION_CLASS; i <<= 1)
2316 if (i != CL_DRIVER)
2317 print_specific_help (i, undoc_mask, 0, opts, lang_mask);
2318 opts->x_exit_after_options = true;
2319 break;
2322 case OPT__target_help:
2323 if (lang_mask == CL_DRIVER)
2324 break;
2326 target_option_override_hook ();
2327 print_specific_help (CL_TARGET, CL_UNDOCUMENTED, 0, opts, lang_mask);
2328 opts->x_exit_after_options = true;
2329 break;
2331 case OPT__help_:
2333 help_option_arguments.safe_push (arg);
2334 opts->x_exit_after_options = true;
2335 break;
2338 case OPT__version:
2339 if (lang_mask == CL_DRIVER)
2340 break;
2342 opts->x_exit_after_options = true;
2343 break;
2345 case OPT__completion_:
2346 break;
2348 case OPT_fsanitize_:
2349 opts->x_flag_sanitize
2350 = parse_sanitizer_options (arg, loc, code,
2351 opts->x_flag_sanitize, value, true);
2353 /* Kernel ASan implies normal ASan but does not yet support
2354 all features. */
2355 if (opts->x_flag_sanitize & SANITIZE_KERNEL_ADDRESS)
2357 SET_OPTION_IF_UNSET (opts, opts_set,
2358 param_asan_instrumentation_with_call_threshold,
2360 SET_OPTION_IF_UNSET (opts, opts_set, param_asan_globals, 0);
2361 SET_OPTION_IF_UNSET (opts, opts_set, param_asan_stack, 0);
2362 SET_OPTION_IF_UNSET (opts, opts_set, param_asan_protect_allocas, 0);
2363 SET_OPTION_IF_UNSET (opts, opts_set, param_asan_use_after_return, 0);
2365 if (opts->x_flag_sanitize & SANITIZE_KERNEL_HWADDRESS)
2367 SET_OPTION_IF_UNSET (opts, opts_set,
2368 param_hwasan_instrument_stack, 0);
2369 SET_OPTION_IF_UNSET (opts, opts_set,
2370 param_hwasan_random_frame_tag, 0);
2371 SET_OPTION_IF_UNSET (opts, opts_set,
2372 param_hwasan_instrument_allocas, 0);
2374 break;
2376 case OPT_fsanitize_recover_:
2377 opts->x_flag_sanitize_recover
2378 = parse_sanitizer_options (arg, loc, code,
2379 opts->x_flag_sanitize_recover, value, true);
2380 break;
2382 case OPT_fasan_shadow_offset_:
2383 /* Deferred. */
2384 break;
2386 case OPT_fsanitize_address_use_after_scope:
2387 opts->x_flag_sanitize_address_use_after_scope = value;
2388 break;
2390 case OPT_fsanitize_recover:
2391 if (value)
2392 opts->x_flag_sanitize_recover
2393 |= (SANITIZE_UNDEFINED | SANITIZE_UNDEFINED_NONDEFAULT)
2394 & ~(SANITIZE_UNREACHABLE | SANITIZE_RETURN);
2395 else
2396 opts->x_flag_sanitize_recover
2397 &= ~(SANITIZE_UNDEFINED | SANITIZE_UNDEFINED_NONDEFAULT);
2398 break;
2400 case OPT_fsanitize_coverage_:
2401 opts->x_flag_sanitize_coverage
2402 = parse_sanitizer_options (arg, loc, code,
2403 opts->x_flag_sanitize_coverage, value, true);
2404 break;
2406 case OPT_O:
2407 case OPT_Os:
2408 case OPT_Ofast:
2409 case OPT_Og:
2410 /* Currently handled in a prescan. */
2411 break;
2413 case OPT_Werror:
2414 dc->warning_as_error_requested = value;
2415 break;
2417 case OPT_Werror_:
2418 if (lang_mask == CL_DRIVER)
2419 break;
2421 enable_warning_as_error (arg, value, lang_mask, handlers,
2422 opts, opts_set, loc, dc);
2423 break;
2425 case OPT_Wfatal_errors:
2426 dc->fatal_errors = value;
2427 break;
2429 case OPT_Wstack_usage_:
2430 opts->x_flag_stack_usage_info = value != -1;
2431 break;
2433 case OPT_Wstrict_aliasing:
2434 set_Wstrict_aliasing (opts, value);
2435 break;
2437 case OPT_Wstrict_overflow:
2438 opts->x_warn_strict_overflow = (value
2439 ? (int) WARN_STRICT_OVERFLOW_CONDITIONAL
2440 : 0);
2441 break;
2443 case OPT_Wsystem_headers:
2444 dc->dc_warn_system_headers = value;
2445 break;
2447 case OPT_aux_info:
2448 opts->x_flag_gen_aux_info = 1;
2449 break;
2451 case OPT_d:
2452 decode_d_option (arg, opts, loc, dc);
2453 break;
2455 case OPT_fcall_used_:
2456 case OPT_fcall_saved_:
2457 /* Deferred. */
2458 break;
2460 case OPT_fdbg_cnt_:
2461 /* Deferred. */
2462 break;
2464 case OPT_fdebug_prefix_map_:
2465 case OPT_ffile_prefix_map_:
2466 /* Deferred. */
2467 break;
2469 case OPT_fcallgraph_info:
2470 opts->x_flag_callgraph_info = CALLGRAPH_INFO_NAKED;
2471 break;
2473 case OPT_fcallgraph_info_:
2475 char *my_arg, *p;
2476 my_arg = xstrdup (arg);
2477 p = strtok (my_arg, ",");
2478 while (p)
2480 if (strcmp (p, "su") == 0)
2482 opts->x_flag_callgraph_info |= CALLGRAPH_INFO_STACK_USAGE;
2483 opts->x_flag_stack_usage_info = true;
2485 else if (strcmp (p, "da") == 0)
2486 opts->x_flag_callgraph_info |= CALLGRAPH_INFO_DYNAMIC_ALLOC;
2487 else
2488 return 0;
2489 p = strtok (NULL, ",");
2491 free (my_arg);
2493 break;
2495 case OPT_fdiagnostics_show_location_:
2496 diagnostic_prefixing_rule (dc) = (diagnostic_prefixing_rule_t) value;
2497 break;
2499 case OPT_fdiagnostics_show_caret:
2500 dc->show_caret = value;
2501 break;
2503 case OPT_fdiagnostics_show_labels:
2504 dc->show_labels_p = value;
2505 break;
2507 case OPT_fdiagnostics_show_line_numbers:
2508 dc->show_line_numbers_p = value;
2509 break;
2511 case OPT_fdiagnostics_color_:
2512 diagnostic_color_init (dc, value);
2513 break;
2515 case OPT_fdiagnostics_urls_:
2516 diagnostic_urls_init (dc, value);
2517 break;
2519 case OPT_fdiagnostics_format_:
2520 diagnostic_output_format_init (dc,
2521 (enum diagnostics_output_format)value);
2522 break;
2524 case OPT_fdiagnostics_parseable_fixits:
2525 dc->extra_output_kind = (value
2526 ? EXTRA_DIAGNOSTIC_OUTPUT_fixits_v1
2527 : EXTRA_DIAGNOSTIC_OUTPUT_none);
2528 break;
2530 case OPT_fdiagnostics_column_unit_:
2531 dc->column_unit = (enum diagnostics_column_unit)value;
2532 break;
2534 case OPT_fdiagnostics_column_origin_:
2535 dc->column_origin = value;
2536 break;
2538 case OPT_fdiagnostics_show_cwe:
2539 dc->show_cwe = value;
2540 break;
2542 case OPT_fdiagnostics_path_format_:
2543 dc->path_format = (enum diagnostic_path_format)value;
2544 break;
2546 case OPT_fdiagnostics_show_path_depths:
2547 dc->show_path_depths = value;
2548 break;
2550 case OPT_fdiagnostics_show_option:
2551 dc->show_option_requested = value;
2552 break;
2554 case OPT_fdiagnostics_minimum_margin_width_:
2555 dc->min_margin_width = value;
2556 break;
2558 case OPT_fdump_:
2559 /* Deferred. */
2560 break;
2562 case OPT_ffast_math:
2563 set_fast_math_flags (opts, value);
2564 break;
2566 case OPT_funsafe_math_optimizations:
2567 set_unsafe_math_optimizations_flags (opts, value);
2568 break;
2570 case OPT_ffixed_:
2571 /* Deferred. */
2572 break;
2574 case OPT_finline_limit_:
2575 SET_OPTION_IF_UNSET (opts, opts_set, param_max_inline_insns_single,
2576 value / 2);
2577 SET_OPTION_IF_UNSET (opts, opts_set, param_max_inline_insns_auto,
2578 value / 2);
2579 break;
2581 case OPT_finstrument_functions_exclude_function_list_:
2582 add_comma_separated_to_vector
2583 (&opts->x_flag_instrument_functions_exclude_functions, arg);
2584 break;
2586 case OPT_finstrument_functions_exclude_file_list_:
2587 add_comma_separated_to_vector
2588 (&opts->x_flag_instrument_functions_exclude_files, arg);
2589 break;
2591 case OPT_fmessage_length_:
2592 pp_set_line_maximum_length (dc->printer, value);
2593 diagnostic_set_caret_max_width (dc, value);
2594 break;
2596 case OPT_fopt_info:
2597 case OPT_fopt_info_:
2598 /* Deferred. */
2599 break;
2601 case OPT_foffload_:
2602 /* Deferred. */
2603 break;
2605 #ifndef ACCEL_COMPILER
2606 case OPT_foffload_abi_:
2607 error_at (loc, "%<-foffload-abi%> option can be specified only for "
2608 "offload compiler");
2609 break;
2610 #endif
2612 case OPT_fpack_struct_:
2613 if (value <= 0 || (value & (value - 1)) || value > 16)
2614 error_at (loc,
2615 "structure alignment must be a small power of two, not %wu",
2616 value);
2617 else
2618 opts->x_initial_max_fld_align = value;
2619 break;
2621 case OPT_fplugin_:
2622 case OPT_fplugin_arg_:
2623 /* Deferred. */
2624 break;
2626 case OPT_fprofile_use_:
2627 opts->x_profile_data_prefix = xstrdup (arg);
2628 opts->x_flag_profile_use = true;
2629 value = true;
2630 /* No break here - do -fprofile-use processing. */
2631 /* FALLTHRU */
2632 case OPT_fprofile_use:
2633 enable_fdo_optimizations (opts, opts_set, value);
2634 SET_OPTION_IF_UNSET (opts, opts_set, flag_profile_reorder_functions,
2635 value);
2636 /* Indirect call profiling should do all useful transformations
2637 speculative devirtualization does. */
2638 if (opts->x_flag_value_profile_transformations)
2639 SET_OPTION_IF_UNSET (opts, opts_set, flag_devirtualize_speculatively,
2640 false);
2641 break;
2643 case OPT_fauto_profile_:
2644 opts->x_auto_profile_file = xstrdup (arg);
2645 opts->x_flag_auto_profile = true;
2646 value = true;
2647 /* No break here - do -fauto-profile processing. */
2648 /* FALLTHRU */
2649 case OPT_fauto_profile:
2650 enable_fdo_optimizations (opts, opts_set, value);
2651 SET_OPTION_IF_UNSET (opts, opts_set, flag_profile_correction, value);
2652 SET_OPTION_IF_UNSET (opts, opts_set,
2653 param_early_inliner_max_iterations, 10);
2654 break;
2656 case OPT_fprofile_generate_:
2657 opts->x_profile_data_prefix = xstrdup (arg);
2658 value = true;
2659 /* No break here - do -fprofile-generate processing. */
2660 /* FALLTHRU */
2661 case OPT_fprofile_generate:
2662 SET_OPTION_IF_UNSET (opts, opts_set, profile_arc_flag, value);
2663 SET_OPTION_IF_UNSET (opts, opts_set, flag_profile_values, value);
2664 SET_OPTION_IF_UNSET (opts, opts_set, flag_inline_functions, value);
2665 SET_OPTION_IF_UNSET (opts, opts_set, flag_ipa_bit_cp, value);
2666 break;
2668 case OPT_fprofile_info_section:
2669 opts->x_profile_info_section = ".gcov_info";
2670 break;
2672 case OPT_fpatchable_function_entry_:
2674 char *patch_area_arg = xstrdup (arg);
2675 char *comma = strchr (patch_area_arg, ',');
2676 if (comma)
2678 *comma = '\0';
2679 function_entry_patch_area_size =
2680 integral_argument (patch_area_arg);
2681 function_entry_patch_area_start =
2682 integral_argument (comma + 1);
2684 else
2686 function_entry_patch_area_size =
2687 integral_argument (patch_area_arg);
2688 function_entry_patch_area_start = 0;
2690 if (function_entry_patch_area_size < 0
2691 || function_entry_patch_area_size > USHRT_MAX
2692 || function_entry_patch_area_start < 0
2693 || function_entry_patch_area_start > USHRT_MAX
2694 || function_entry_patch_area_size
2695 < function_entry_patch_area_start)
2696 error ("invalid arguments for %<-fpatchable-function-entry%>");
2697 free (patch_area_arg);
2699 break;
2701 case OPT_ftree_vectorize:
2702 /* Automatically sets -ftree-loop-vectorize and
2703 -ftree-slp-vectorize. Nothing more to do here. */
2704 break;
2705 case OPT_fzero_call_used_regs_:
2706 opts->x_flag_zero_call_used_regs
2707 = parse_zero_call_used_regs_options (arg);
2708 break;
2710 case OPT_fshow_column:
2711 dc->show_column = value;
2712 break;
2714 case OPT_frandom_seed:
2715 /* The real switch is -fno-random-seed. */
2716 if (value)
2717 return false;
2718 /* Deferred. */
2719 break;
2721 case OPT_frandom_seed_:
2722 /* Deferred. */
2723 break;
2725 case OPT_fsched_verbose_:
2726 #ifdef INSN_SCHEDULING
2727 /* Handled with Var in common.opt. */
2728 break;
2729 #else
2730 return false;
2731 #endif
2733 case OPT_fsched_stalled_insns_:
2734 opts->x_flag_sched_stalled_insns = value;
2735 if (opts->x_flag_sched_stalled_insns == 0)
2736 opts->x_flag_sched_stalled_insns = -1;
2737 break;
2739 case OPT_fsched_stalled_insns_dep_:
2740 opts->x_flag_sched_stalled_insns_dep = value;
2741 break;
2743 case OPT_fstack_check_:
2744 if (!strcmp (arg, "no"))
2745 opts->x_flag_stack_check = NO_STACK_CHECK;
2746 else if (!strcmp (arg, "generic"))
2747 /* This is the old stack checking method. */
2748 opts->x_flag_stack_check = STACK_CHECK_BUILTIN
2749 ? FULL_BUILTIN_STACK_CHECK
2750 : GENERIC_STACK_CHECK;
2751 else if (!strcmp (arg, "specific"))
2752 /* This is the new stack checking method. */
2753 opts->x_flag_stack_check = STACK_CHECK_BUILTIN
2754 ? FULL_BUILTIN_STACK_CHECK
2755 : STACK_CHECK_STATIC_BUILTIN
2756 ? STATIC_BUILTIN_STACK_CHECK
2757 : GENERIC_STACK_CHECK;
2758 else
2759 warning_at (loc, 0, "unknown stack check parameter %qs", arg);
2760 break;
2762 case OPT_fstack_limit:
2763 /* The real switch is -fno-stack-limit. */
2764 if (value)
2765 return false;
2766 /* Deferred. */
2767 break;
2769 case OPT_fstack_limit_register_:
2770 case OPT_fstack_limit_symbol_:
2771 /* Deferred. */
2772 break;
2774 case OPT_fstack_usage:
2775 opts->x_flag_stack_usage = value;
2776 opts->x_flag_stack_usage_info = value != 0;
2777 break;
2779 case OPT_g:
2780 set_debug_level (NO_DEBUG, DEFAULT_GDB_EXTENSIONS, arg, opts, opts_set,
2781 loc);
2782 break;
2784 case OPT_gdwarf:
2785 if (arg && strlen (arg) != 0)
2787 error_at (loc, "%<-gdwarf%s%> is ambiguous; "
2788 "use %<-gdwarf-%s%> for DWARF version "
2789 "or %<-gdwarf%> %<-g%s%> for debug level", arg, arg, arg);
2790 break;
2792 else
2793 value = opts->x_dwarf_version;
2795 /* FALLTHRU */
2796 case OPT_gdwarf_:
2797 if (value < 2 || value > 5)
2798 error_at (loc, "dwarf version %wu is not supported", value);
2799 else
2800 opts->x_dwarf_version = value;
2801 set_debug_level (DWARF2_DEBUG, false, "", opts, opts_set, loc);
2802 break;
2804 case OPT_ggdb:
2805 set_debug_level (NO_DEBUG, 2, arg, opts, opts_set, loc);
2806 break;
2808 case OPT_gstabs:
2809 case OPT_gstabs_:
2810 set_debug_level (DBX_DEBUG, code == OPT_gstabs_, arg, opts, opts_set,
2811 loc);
2812 break;
2814 case OPT_gvms:
2815 set_debug_level (VMS_DEBUG, false, arg, opts, opts_set, loc);
2816 break;
2818 case OPT_gxcoff:
2819 case OPT_gxcoff_:
2820 set_debug_level (XCOFF_DEBUG, code == OPT_gxcoff_, arg, opts, opts_set,
2821 loc);
2822 break;
2824 case OPT_gz:
2825 case OPT_gz_:
2826 /* Handled completely via specs. */
2827 break;
2829 case OPT_pedantic_errors:
2830 dc->pedantic_errors = 1;
2831 control_warning_option (OPT_Wpedantic, DK_ERROR, NULL, value,
2832 loc, lang_mask,
2833 handlers, opts, opts_set,
2834 dc);
2835 break;
2837 case OPT_flto:
2838 opts->x_flag_lto = value ? "" : NULL;
2839 break;
2841 case OPT_flto_:
2842 if (strcmp (arg, "none") != 0
2843 && strcmp (arg, "jobserver") != 0
2844 && strcmp (arg, "auto") != 0
2845 && atoi (arg) == 0)
2846 error_at (loc,
2847 "unrecognized argument to %<-flto=%> option: %qs", arg);
2848 break;
2850 case OPT_w:
2851 dc->dc_inhibit_warnings = true;
2852 break;
2854 case OPT_fmax_errors_:
2855 dc->max_errors = value;
2856 break;
2858 case OPT_fuse_ld_bfd:
2859 case OPT_fuse_ld_gold:
2860 case OPT_fuse_ld_lld:
2861 case OPT_fuse_linker_plugin:
2862 /* No-op. Used by the driver and passed to us because it starts with f.*/
2863 break;
2865 case OPT_fwrapv:
2866 if (value)
2867 opts->x_flag_trapv = 0;
2868 break;
2870 case OPT_ftrapv:
2871 if (value)
2872 opts->x_flag_wrapv = 0;
2873 break;
2875 case OPT_fstrict_overflow:
2876 opts->x_flag_wrapv = !value;
2877 opts->x_flag_wrapv_pointer = !value;
2878 if (!value)
2879 opts->x_flag_trapv = 0;
2880 break;
2882 case OPT_fipa_icf:
2883 opts->x_flag_ipa_icf_functions = value;
2884 opts->x_flag_ipa_icf_variables = value;
2885 break;
2887 case OPT_falign_loops_:
2888 check_alignment_argument (loc, arg, "loops",
2889 &opts->x_flag_align_loops,
2890 &opts->x_str_align_loops);
2891 break;
2893 case OPT_falign_jumps_:
2894 check_alignment_argument (loc, arg, "jumps",
2895 &opts->x_flag_align_jumps,
2896 &opts->x_str_align_jumps);
2897 break;
2899 case OPT_falign_labels_:
2900 check_alignment_argument (loc, arg, "labels",
2901 &opts->x_flag_align_labels,
2902 &opts->x_str_align_labels);
2903 break;
2905 case OPT_falign_functions_:
2906 check_alignment_argument (loc, arg, "functions",
2907 &opts->x_flag_align_functions,
2908 &opts->x_str_align_functions);
2909 break;
2911 case OPT_ftabstop_:
2912 /* It is documented that we silently ignore silly values. */
2913 if (value >= 1 && value <= 100)
2914 dc->tabstop = value;
2915 break;
2917 default:
2918 /* If the flag was handled in a standard way, assume the lack of
2919 processing here is intentional. */
2920 gcc_assert (option_flag_var (scode, opts));
2921 break;
2924 common_handle_option_auto (opts, opts_set, decoded, lang_mask, kind,
2925 loc, handlers, dc);
2926 return true;
2929 /* Used to set the level of strict aliasing warnings in OPTS,
2930 when no level is specified (i.e., when -Wstrict-aliasing, and not
2931 -Wstrict-aliasing=level was given).
2932 ONOFF is assumed to take value 1 when -Wstrict-aliasing is specified,
2933 and 0 otherwise. After calling this function, wstrict_aliasing will be
2934 set to the default value of -Wstrict_aliasing=level, currently 3. */
2935 static void
2936 set_Wstrict_aliasing (struct gcc_options *opts, int onoff)
2938 gcc_assert (onoff == 0 || onoff == 1);
2939 if (onoff != 0)
2940 opts->x_warn_strict_aliasing = 3;
2941 else
2942 opts->x_warn_strict_aliasing = 0;
2945 /* The following routines are useful in setting all the flags that
2946 -ffast-math and -fno-fast-math imply. */
2947 static void
2948 set_fast_math_flags (struct gcc_options *opts, int set)
2950 if (!opts->frontend_set_flag_unsafe_math_optimizations)
2952 opts->x_flag_unsafe_math_optimizations = set;
2953 set_unsafe_math_optimizations_flags (opts, set);
2955 if (!opts->frontend_set_flag_finite_math_only)
2956 opts->x_flag_finite_math_only = set;
2957 if (!opts->frontend_set_flag_errno_math)
2958 opts->x_flag_errno_math = !set;
2959 if (set)
2961 if (opts->frontend_set_flag_excess_precision == EXCESS_PRECISION_DEFAULT)
2962 opts->x_flag_excess_precision
2963 = set ? EXCESS_PRECISION_FAST : EXCESS_PRECISION_DEFAULT;
2964 if (!opts->frontend_set_flag_signaling_nans)
2965 opts->x_flag_signaling_nans = 0;
2966 if (!opts->frontend_set_flag_rounding_math)
2967 opts->x_flag_rounding_math = 0;
2968 if (!opts->frontend_set_flag_cx_limited_range)
2969 opts->x_flag_cx_limited_range = 1;
2973 /* When -funsafe-math-optimizations is set the following
2974 flags are set as well. */
2975 static void
2976 set_unsafe_math_optimizations_flags (struct gcc_options *opts, int set)
2978 if (!opts->frontend_set_flag_trapping_math)
2979 opts->x_flag_trapping_math = !set;
2980 if (!opts->frontend_set_flag_signed_zeros)
2981 opts->x_flag_signed_zeros = !set;
2982 if (!opts->frontend_set_flag_associative_math)
2983 opts->x_flag_associative_math = set;
2984 if (!opts->frontend_set_flag_reciprocal_math)
2985 opts->x_flag_reciprocal_math = set;
2988 /* Return true iff flags in OPTS are set as if -ffast-math. */
2989 bool
2990 fast_math_flags_set_p (const struct gcc_options *opts)
2992 return (!opts->x_flag_trapping_math
2993 && opts->x_flag_unsafe_math_optimizations
2994 && opts->x_flag_finite_math_only
2995 && !opts->x_flag_signed_zeros
2996 && !opts->x_flag_errno_math
2997 && opts->x_flag_excess_precision == EXCESS_PRECISION_FAST);
3000 /* Return true iff flags are set as if -ffast-math but using the flags stored
3001 in the struct cl_optimization structure. */
3002 bool
3003 fast_math_flags_struct_set_p (struct cl_optimization *opt)
3005 return (!opt->x_flag_trapping_math
3006 && opt->x_flag_unsafe_math_optimizations
3007 && opt->x_flag_finite_math_only
3008 && !opt->x_flag_signed_zeros
3009 && !opt->x_flag_errno_math);
3012 /* Handle a debug output -g switch for options OPTS
3013 (OPTS_SET->x_write_symbols storing whether a debug type was passed
3014 explicitly), location LOC. EXTENDED is true or false to support
3015 extended output (2 is special and means "-ggdb" was given). */
3016 static void
3017 set_debug_level (enum debug_info_type type, int extended, const char *arg,
3018 struct gcc_options *opts, struct gcc_options *opts_set,
3019 location_t loc)
3021 opts->x_use_gnu_debug_info_extensions = extended;
3023 if (type == NO_DEBUG)
3025 if (opts->x_write_symbols == NO_DEBUG)
3027 opts->x_write_symbols = PREFERRED_DEBUGGING_TYPE;
3029 if (extended == 2)
3031 #if defined DWARF2_DEBUGGING_INFO || defined DWARF2_LINENO_DEBUGGING_INFO
3032 opts->x_write_symbols = DWARF2_DEBUG;
3033 #elif defined DBX_DEBUGGING_INFO
3034 opts->x_write_symbols = DBX_DEBUG;
3035 #endif
3038 if (opts->x_write_symbols == NO_DEBUG)
3039 warning_at (loc, 0, "target system does not support debug output");
3042 else
3044 /* Does it conflict with an already selected type? */
3045 if (opts_set->x_write_symbols != NO_DEBUG
3046 && opts->x_write_symbols != NO_DEBUG
3047 && type != opts->x_write_symbols)
3048 error_at (loc, "debug format %qs conflicts with prior selection",
3049 debug_type_names[type]);
3050 opts->x_write_symbols = type;
3051 opts_set->x_write_symbols = type;
3054 /* A debug flag without a level defaults to level 2.
3055 If off or at level 1, set it to level 2, but if already
3056 at level 3, don't lower it. */
3057 if (*arg == '\0')
3059 if (opts->x_debug_info_level < DINFO_LEVEL_NORMAL)
3060 opts->x_debug_info_level = DINFO_LEVEL_NORMAL;
3062 else
3064 int argval = integral_argument (arg);
3065 if (argval == -1)
3066 error_at (loc, "unrecognized debug output level %qs", arg);
3067 else if (argval > 3)
3068 error_at (loc, "debug output level %qs is too high", arg);
3069 else
3070 opts->x_debug_info_level = (enum debug_info_levels) argval;
3074 /* Arrange to dump core on error for diagnostic context DC. (The
3075 regular error message is still printed first, except in the case of
3076 abort ().) */
3078 static void
3079 setup_core_dumping (diagnostic_context *dc)
3081 #ifdef SIGABRT
3082 signal (SIGABRT, SIG_DFL);
3083 #endif
3084 #if defined(HAVE_SETRLIMIT)
3086 struct rlimit rlim;
3087 if (getrlimit (RLIMIT_CORE, &rlim) != 0)
3088 fatal_error (input_location, "getting core file size maximum limit: %m");
3089 rlim.rlim_cur = rlim.rlim_max;
3090 if (setrlimit (RLIMIT_CORE, &rlim) != 0)
3091 fatal_error (input_location,
3092 "setting core file size limit to maximum: %m");
3094 #endif
3095 diagnostic_abort_on_error (dc);
3098 /* Parse a -d<ARG> command line switch for OPTS, location LOC,
3099 diagnostic context DC. */
3101 static void
3102 decode_d_option (const char *arg, struct gcc_options *opts,
3103 location_t loc, diagnostic_context *dc)
3105 int c;
3107 while (*arg)
3108 switch (c = *arg++)
3110 case 'A':
3111 opts->x_flag_debug_asm = 1;
3112 break;
3113 case 'p':
3114 opts->x_flag_print_asm_name = 1;
3115 break;
3116 case 'P':
3117 opts->x_flag_dump_rtl_in_asm = 1;
3118 opts->x_flag_print_asm_name = 1;
3119 break;
3120 case 'x':
3121 opts->x_rtl_dump_and_exit = 1;
3122 break;
3123 case 'D': /* These are handled by the preprocessor. */
3124 case 'I':
3125 case 'M':
3126 case 'N':
3127 case 'U':
3128 break;
3129 case 'H':
3130 setup_core_dumping (dc);
3131 break;
3132 case 'a':
3133 opts->x_flag_dump_all_passed = true;
3134 break;
3136 default:
3137 warning_at (loc, 0, "unrecognized gcc debugging option: %c", c);
3138 break;
3142 /* Enable (or disable if VALUE is 0) a warning option ARG (language
3143 mask LANG_MASK, option handlers HANDLERS) as an error for option
3144 structures OPTS and OPTS_SET, diagnostic context DC (possibly
3145 NULL), location LOC. This is used by -Werror=. */
3147 static void
3148 enable_warning_as_error (const char *arg, int value, unsigned int lang_mask,
3149 const struct cl_option_handlers *handlers,
3150 struct gcc_options *opts,
3151 struct gcc_options *opts_set,
3152 location_t loc, diagnostic_context *dc)
3154 char *new_option;
3155 int option_index;
3157 new_option = XNEWVEC (char, strlen (arg) + 2);
3158 new_option[0] = 'W';
3159 strcpy (new_option + 1, arg);
3160 option_index = find_opt (new_option, lang_mask);
3161 if (option_index == OPT_SPECIAL_unknown)
3163 option_proposer op;
3164 const char *hint = op.suggest_option (new_option);
3165 if (hint)
3166 error_at (loc, "%<-W%serror=%s%>: no option %<-%s%>;"
3167 " did you mean %<-%s%>?", value ? "" : "no-",
3168 arg, new_option, hint);
3169 else
3170 error_at (loc, "%<-W%serror=%s%>: no option %<-%s%>",
3171 value ? "" : "no-", arg, new_option);
3173 else if (!(cl_options[option_index].flags & CL_WARNING))
3174 error_at (loc, "%<-Werror=%s%>: %<-%s%> is not an option that "
3175 "controls warnings", arg, new_option);
3176 else
3178 const diagnostic_t kind = value ? DK_ERROR : DK_WARNING;
3179 const char *arg = NULL;
3181 if (cl_options[option_index].flags & CL_JOINED)
3182 arg = new_option + cl_options[option_index].opt_len;
3183 control_warning_option (option_index, (int) kind, arg, value,
3184 loc, lang_mask,
3185 handlers, opts, opts_set, dc);
3187 free (new_option);
3190 /* Return malloced memory for the name of the option OPTION_INDEX
3191 which enabled a diagnostic (context CONTEXT), originally of type
3192 ORIG_DIAG_KIND but possibly converted to DIAG_KIND by options such
3193 as -Werror. */
3195 char *
3196 option_name (diagnostic_context *context, int option_index,
3197 diagnostic_t orig_diag_kind, diagnostic_t diag_kind)
3199 if (option_index)
3201 /* A warning classified as an error. */
3202 if ((orig_diag_kind == DK_WARNING || orig_diag_kind == DK_PEDWARN)
3203 && diag_kind == DK_ERROR)
3204 return concat (cl_options[OPT_Werror_].opt_text,
3205 /* Skip over "-W". */
3206 cl_options[option_index].opt_text + 2,
3207 NULL);
3208 /* A warning with option. */
3209 else
3210 return xstrdup (cl_options[option_index].opt_text);
3212 /* A warning without option classified as an error. */
3213 else if ((orig_diag_kind == DK_WARNING || orig_diag_kind == DK_PEDWARN
3214 || diag_kind == DK_WARNING)
3215 && context->warning_as_error_requested)
3216 return xstrdup (cl_options[OPT_Werror].opt_text);
3217 else
3218 return NULL;
3221 /* Get the page within the documentation for this option. */
3223 static const char *
3224 get_option_html_page (int option_index)
3226 const cl_option *cl_opt = &cl_options[option_index];
3228 /* Analyzer options are on their own page. */
3229 if (strstr(cl_opt->opt_text, "analyzer-"))
3230 return "gcc/Static-Analyzer-Options.html";
3232 #ifdef CL_Fortran
3233 if ((cl_opt->flags & CL_Fortran) != 0
3234 /* If it is option common to both C/C++ and Fortran, it is documented
3235 in gcc/ rather than gfortran/ docs. */
3236 && (cl_opt->flags & CL_C) == 0
3237 #ifdef CL_CXX
3238 && (cl_opt->flags & CL_CXX) == 0
3239 #endif
3241 return "gfortran/Error-and-Warning-Options.html";
3242 #endif
3244 return "gcc/Warning-Options.html";
3247 /* Return malloced memory for a URL describing the option OPTION_INDEX
3248 which enabled a diagnostic (context CONTEXT). */
3250 char *
3251 get_option_url (diagnostic_context *, int option_index)
3253 if (option_index)
3254 return concat (/* DOCUMENTATION_ROOT_URL should be supplied via -D by
3255 the Makefile (see --with-documentation-root-url), and
3256 should have a trailing slash. */
3257 DOCUMENTATION_ROOT_URL,
3259 /* get_option_html_page will return something like
3260 "gcc/Warning-Options.html". */
3261 get_option_html_page (option_index),
3263 /* Expect an anchor of the form "index-Wfoo" e.g.
3264 <a name="index-Wformat"></a>, and thus an id within
3265 the URL of "#index-Wformat". */
3266 "#index", cl_options[option_index].opt_text,
3267 NULL);
3268 else
3269 return NULL;
3272 /* Return a heap allocated producer with command line options. */
3274 char *
3275 gen_command_line_string (cl_decoded_option *options,
3276 unsigned int options_count)
3278 auto_vec<const char *> switches;
3279 char *options_string, *tail;
3280 const char *p;
3281 size_t len = 0;
3283 for (unsigned i = 0; i < options_count; i++)
3284 switch (options[i].opt_index)
3286 case OPT_o:
3287 case OPT_d:
3288 case OPT_dumpbase:
3289 case OPT_dumpdir:
3290 case OPT_quiet:
3291 case OPT_version:
3292 case OPT_v:
3293 case OPT_w:
3294 case OPT_L:
3295 case OPT_D:
3296 case OPT_I:
3297 case OPT_U:
3298 case OPT_SPECIAL_unknown:
3299 case OPT_SPECIAL_ignore:
3300 case OPT_SPECIAL_warn_removed:
3301 case OPT_SPECIAL_program_name:
3302 case OPT_SPECIAL_input_file:
3303 case OPT_grecord_gcc_switches:
3304 case OPT_frecord_gcc_switches:
3305 case OPT__output_pch_:
3306 case OPT_fdiagnostics_show_location_:
3307 case OPT_fdiagnostics_show_option:
3308 case OPT_fdiagnostics_show_caret:
3309 case OPT_fdiagnostics_show_labels:
3310 case OPT_fdiagnostics_show_line_numbers:
3311 case OPT_fdiagnostics_color_:
3312 case OPT_fdiagnostics_format_:
3313 case OPT_fverbose_asm:
3314 case OPT____:
3315 case OPT__sysroot_:
3316 case OPT_nostdinc:
3317 case OPT_nostdinc__:
3318 case OPT_fpreprocessed:
3319 case OPT_fltrans_output_list_:
3320 case OPT_fresolution_:
3321 case OPT_fdebug_prefix_map_:
3322 case OPT_fmacro_prefix_map_:
3323 case OPT_ffile_prefix_map_:
3324 case OPT_fcompare_debug:
3325 case OPT_fchecking:
3326 case OPT_fchecking_:
3327 /* Ignore these. */
3328 continue;
3329 case OPT_flto_:
3331 const char *lto_canonical = "-flto";
3332 switches.safe_push (lto_canonical);
3333 len += strlen (lto_canonical) + 1;
3334 break;
3336 default:
3337 if (cl_options[options[i].opt_index].flags
3338 & CL_NO_DWARF_RECORD)
3339 continue;
3340 gcc_checking_assert (options[i].canonical_option[0][0] == '-');
3341 switch (options[i].canonical_option[0][1])
3343 case 'M':
3344 case 'i':
3345 case 'W':
3346 continue;
3347 case 'f':
3348 if (strncmp (options[i].canonical_option[0] + 2,
3349 "dump", 4) == 0)
3350 continue;
3351 break;
3352 default:
3353 break;
3355 switches.safe_push (options[i].orig_option_with_args_text);
3356 len += strlen (options[i].orig_option_with_args_text) + 1;
3357 break;
3360 options_string = XNEWVEC (char, len + 1);
3361 tail = options_string;
3363 unsigned i;
3364 FOR_EACH_VEC_ELT (switches, i, p)
3366 len = strlen (p);
3367 memcpy (tail, p, len);
3368 tail += len;
3369 if (i != switches.length () - 1)
3371 *tail = ' ';
3372 ++tail;
3376 *tail = '\0';
3377 return options_string;
3380 /* Return a heap allocated producer string including command line options. */
3382 char *
3383 gen_producer_string (const char *language_string, cl_decoded_option *options,
3384 unsigned int options_count)
3386 return concat (language_string, " ", version_string, " ",
3387 gen_command_line_string (options, options_count), NULL);
3390 #if CHECKING_P
3392 namespace selftest {
3394 /* Verify that get_option_html_page works as expected. */
3396 static void
3397 test_get_option_html_page ()
3399 ASSERT_STREQ (get_option_html_page (OPT_Wcpp), "gcc/Warning-Options.html");
3400 ASSERT_STREQ (get_option_html_page (OPT_Wanalyzer_double_free),
3401 "gcc/Static-Analyzer-Options.html");
3402 #ifdef CL_Fortran
3403 ASSERT_STREQ (get_option_html_page (OPT_Wline_truncation),
3404 "gfortran/Error-and-Warning-Options.html");
3405 #endif
3408 /* Run all of the selftests within this file. */
3410 void
3411 opts_c_tests ()
3413 test_get_option_html_page ();
3416 } // namespace selftest
3418 #endif /* #if CHECKING_P */