On Fri, Aug 10, 2012 at 1:30 PM, Richard Guenther <rguent...@suse.de> wrote: > > This adds a new optimization level, -Og, as previously discussed. > It aims at providing fast compilation, a superior debugging > experience and reasonable runtime performance. Instead of making > -O1 this optimization level this adds a new -Og. > > It's a first cut, highlighting that our fixed pass pipeline and > simply enabling/disabling individual passes (but not pass copies > for example) doesn't scale to properly differentiate between > -Og and -O[23]. -O1 should get similar treatment, eventually > just building on -Og but not focusing on debugging experience. > That is, I expect that in the end we will at least have two post-IPA > optimization pipelines. It also means that you cannot enable > PRE or VRP with -Og at the moment because these passes are not > anywhere scheduled (similar to the situation with -O0). > > It has some funny effect on dump-file naming of the pass copies > though, which hints at that the current setup is too static. > For that reason the new queue comes after the old, to not confuse > too many testcases. > > It also does not yet disable any of the early optimizations that > make debugging harder (SRA comes to my mind here, as does > switch-conversion and partial inlining). > > The question arises if we want to support in any reasonable > way using profile-feedback or LTO for -O[01g], thus if we > rather want to delay some of the early opts to after IPA > optimizations. > > Not bootstrapped or fully tested, but it works for the compile > torture. > > Comments welcome,
No comments? Then I'll drop this idea for 4.8. Richard. > Thanks, > Richard. > > 2012-08-10 Richard Guenther <rguent...@suse.de> > > PR other/53316 > * common.opt (optimize_debug): New variable. > (Og): New optimization level. > * doc/invoke.texi (Og): Document. > * opts.c (maybe_default_option): Add debug parameter. > (maybe_default_options): Likewise. > (default_options_optimization): Handle -Og. > (common_handle_option): Likewise. > * passes.c (gate_all_optimizations): Do not run with -Og. > (gate_all_optimizations_g): New gate, run with -Og. > (pass_all_optimizations_g): New container pass, run with -Og. > (init_optimization_passes): Schedule pass_all_optimizations_g > alongside pass_all_optimizations. > > * gcc/testsuite/lib/c-torture.exp: Add -Og -g to default > TORTURE_OPTIONS. > > Index: trunk/gcc/common.opt > =================================================================== > *** trunk.orig/gcc/common.opt 2012-07-19 10:39:47.000000000 +0200 > --- trunk/gcc/common.opt 2012-08-10 11:58:22.218122816 +0200 > *************** int optimize > *** 32,37 **** > --- 32,40 ---- > Variable > int optimize_size > > + Variable > + int optimize_debug > + > ; Not used directly to control optimizations, only to save -Ofast > ; setting for "optimize" attributes. > Variable > *************** Ofast > *** 446,451 **** > --- 449,458 ---- > Common Optimization > Optimize for speed disregarding exact standards compliance > > + Og > + Common Optimization > + Optimize for debugging experience rather than speed or size > + > Q > Driver > > Index: trunk/gcc/opts.c > =================================================================== > *** trunk.orig/gcc/opts.c 2012-07-24 10:35:57.000000000 +0200 > --- trunk/gcc/opts.c 2012-08-10 12:48:38.986018411 +0200 > *************** init_options_struct (struct gcc_options > *** 314,328 **** > } > > /* If indicated by the optimization level LEVEL (-Os if SIZE is set, > ! -Ofast if FAST is set), apply the option DEFAULT_OPT to OPTS and > ! OPTS_SET, diagnostic context DC, location LOC, with language mask > ! LANG_MASK and option handlers HANDLERS. */ > > static void > maybe_default_option (struct gcc_options *opts, > struct gcc_options *opts_set, > const struct default_options *default_opt, > ! int level, bool size, bool fast, > unsigned int lang_mask, > const struct cl_option_handlers *handlers, > location_t loc, > --- 314,328 ---- > } > > /* If indicated by the optimization level LEVEL (-Os if SIZE is set, > ! -Ofast if FAST is set, -Og if DEBUG is set), apply the option DEFAULT_OPT > ! to OPTS and OPTS_SET, diagnostic context DC, location LOC, with language > ! mask LANG_MASK and option handlers HANDLERS. */ > > static void > maybe_default_option (struct gcc_options *opts, > struct gcc_options *opts_set, > const struct default_options *default_opt, > ! int level, bool size, bool fast, bool debug, > unsigned int lang_mask, > const struct cl_option_handlers *handlers, > location_t loc, > *************** maybe_default_option (struct gcc_options > *** 335,340 **** > --- 335,342 ---- > gcc_assert (level == 2); > if (fast) > gcc_assert (level == 3); > + if (debug) > + gcc_assert (level == 1); > > switch (default_opt->levels) > { > *************** maybe_default_option (struct gcc_options > *** 351,357 **** > break; > > case OPT_LEVELS_1_PLUS_SPEED_ONLY: > ! enabled = (level >= 1 && !size); > break; > > case OPT_LEVELS_2_PLUS: > --- 353,359 ---- > break; > > case OPT_LEVELS_1_PLUS_SPEED_ONLY: > ! enabled = (level >= 1 && !size && !debug); > break; > > case OPT_LEVELS_2_PLUS: > *************** maybe_default_option (struct gcc_options > *** 359,365 **** > break; > > case OPT_LEVELS_2_PLUS_SPEED_ONLY: > ! enabled = (level >= 2 && !size); > break; > > case OPT_LEVELS_3_PLUS: > --- 361,367 ---- > break; > > case OPT_LEVELS_2_PLUS_SPEED_ONLY: > ! enabled = (level >= 2 && !size && !debug); > break; > > case OPT_LEVELS_3_PLUS: > *************** static void > *** 405,411 **** > maybe_default_options (struct gcc_options *opts, > struct gcc_options *opts_set, > const struct default_options *default_opts, > ! int level, bool size, bool fast, > unsigned int lang_mask, > const struct cl_option_handlers *handlers, > location_t loc, > --- 407,413 ---- > maybe_default_options (struct gcc_options *opts, > struct gcc_options *opts_set, > const struct default_options *default_opts, > ! int level, bool size, bool fast, bool debug, > unsigned int lang_mask, > const struct cl_option_handlers *handlers, > location_t loc, > *************** maybe_default_options (struct gcc_option > *** 415,421 **** > > for (i = 0; default_opts[i].levels != OPT_LEVELS_NONE; i++) > maybe_default_option (opts, opts_set, &default_opts[i], > ! level, size, fast, lang_mask, handlers, loc, dc); > } > > /* Table of options enabled by default at different levels. */ > --- 417,424 ---- > > for (i = 0; default_opts[i].levels != OPT_LEVELS_NONE; i++) > maybe_default_option (opts, opts_set, &default_opts[i], > ! level, size, fast, debug, > ! lang_mask, handlers, loc, dc); > } > > /* Table of options enabled by default at different levels. */ > *************** default_options_optimization (struct gcc > *** 540,545 **** > --- 543,549 ---- > opts->x_optimize = 1; > opts->x_optimize_size = 0; > opts->x_optimize_fast = 0; > + opts->x_optimize_debug = 0; > } > else > { > *************** default_options_optimization (struct gcc > *** 555,560 **** > --- 559,565 ---- > opts->x_optimize = 255; > opts->x_optimize_size = 0; > opts->x_optimize_fast = 0; > + opts->x_optimize_debug = 0; > } > } > break; > *************** default_options_optimization (struct gcc > *** 565,570 **** > --- 570,576 ---- > /* Optimizing for size forces optimize to be 2. */ > opts->x_optimize = 2; > opts->x_optimize_fast = 0; > + opts->x_optimize_debug = 0; > break; > > case OPT_Ofast: > *************** default_options_optimization (struct gcc > *** 572,577 **** > --- 578,592 ---- > opts->x_optimize_size = 0; > opts->x_optimize = 3; > opts->x_optimize_fast = 1; > + opts->x_optimize_debug = 0; > + break; > + > + case OPT_Og: > + /* -Og selects optimization level 1. */ > + opts->x_optimize_size = 0; > + opts->x_optimize = 1; > + opts->x_optimize_fast = 0; > + opts->x_optimize_debug = 1; > break; > > default: > *************** default_options_optimization (struct gcc > *** 582,588 **** > > maybe_default_options (opts, opts_set, default_options_table, > opts->x_optimize, opts->x_optimize_size, > ! opts->x_optimize_fast, lang_mask, handlers, loc, dc); > > /* -O2 param settings. */ > opt2 = (opts->x_optimize >= 2); > --- 597,604 ---- > > maybe_default_options (opts, opts_set, default_options_table, > opts->x_optimize, opts->x_optimize_size, > ! opts->x_optimize_fast, opts->x_optimize_debug, > ! lang_mask, handlers, loc, dc); > > /* -O2 param settings. */ > opt2 = (opts->x_optimize >= 2); > *************** default_options_optimization (struct gcc > *** 612,618 **** > maybe_default_options (opts, opts_set, > targetm_common.option_optimization_table, > opts->x_optimize, opts->x_optimize_size, > ! opts->x_optimize_fast, lang_mask, handlers, loc, dc); > } > > /* After all options at LOC have been read into OPTS and OPTS_SET, > --- 628,635 ---- > maybe_default_options (opts, opts_set, > targetm_common.option_optimization_table, > opts->x_optimize, opts->x_optimize_size, > ! opts->x_optimize_fast, opts->x_optimize_debug, > ! lang_mask, handlers, loc, dc); > } > > /* After all options at LOC have been read into OPTS and OPTS_SET, > *************** common_handle_option (struct gcc_options > *** 1408,1413 **** > --- 1425,1431 ---- > case OPT_O: > case OPT_Os: > case OPT_Ofast: > + case OPT_Og: > /* Currently handled in a prescan. */ > break; > > Index: trunk/gcc/passes.c > =================================================================== > *** trunk.orig/gcc/passes.c 2012-08-03 10:54:00.000000000 +0200 > --- trunk/gcc/passes.c 2012-08-10 12:45:16.449025382 +0200 > *************** static struct gimple_opt_pass pass_all_e > *** 337,346 **** > static bool > gate_all_optimizations (void) > { > ! return (optimize >= 1 > ! /* Don't bother doing anything if the program has errors. > ! We have to pass down the queue if we already went into SSA */ > ! && (!seen_error () || gimple_in_ssa_p (cfun))); > } > > static struct gimple_opt_pass pass_all_optimizations = > --- 337,343 ---- > static bool > gate_all_optimizations (void) > { > ! return optimize >= 1 && !optimize_debug; > } > > static struct gimple_opt_pass pass_all_optimizations = > *************** static struct gimple_opt_pass pass_all_o > *** 362,367 **** > --- 359,391 ---- > } > }; > > + /* Gate: execute, or not, all of the non-trivial optimizations. */ > + > + static bool > + gate_all_optimizations_g (void) > + { > + return optimize >= 1 && optimize_debug; > + } > + > + static struct gimple_opt_pass pass_all_optimizations_g = > + { > + { > + GIMPLE_PASS, > + "*all_optimizations_g", /* name */ > + gate_all_optimizations_g, /* gate */ > + NULL, /* execute */ > + NULL, /* sub */ > + NULL, /* next */ > + 0, /* static_pass_number */ > + TV_OPTIMIZE, /* tv_id */ > + 0, /* properties_required */ > + 0, /* properties_provided */ > + 0, /* properties_destroyed */ > + 0, /* todo_flags_start */ > + 0 /* todo_flags_finish */ > + } > + }; > + > static bool > gate_rest_of_compilation (void) > { > *************** init_optimization_passes (void) > *** 1493,1498 **** > --- 1517,1545 ---- > NEXT_PASS (pass_uncprop); > NEXT_PASS (pass_local_pure_const); > } > + NEXT_PASS (pass_all_optimizations_g); > + { > + struct opt_pass **p = &pass_all_optimizations_g.pass.sub; > + NEXT_PASS (pass_remove_cgraph_callee_edges); > + NEXT_PASS (pass_strip_predict_hints); > + /* Lower remaining pieces of GIMPLE. */ > + NEXT_PASS (pass_lower_complex); > + NEXT_PASS (pass_lower_vector_ssa); > + /* Perform simple scalar cleanup which is constant/copy propagation. > */ > + NEXT_PASS (pass_ccp); > + NEXT_PASS (pass_copy_prop); > + NEXT_PASS (pass_rename_ssa_copies); > + NEXT_PASS (pass_dce); > + /* Fold remaining builtins. */ > + NEXT_PASS (pass_object_sizes); > + NEXT_PASS (pass_fold_builtins); > + /* ??? We do want some kind of loop invariant motion, but we possibly > + need to adjust LIM to be more friendly towards preserving accurate > + debug information here. */ > + NEXT_PASS (pass_late_warn_uninitialized); > + NEXT_PASS (pass_uncprop); > + NEXT_PASS (pass_local_pure_const); > + } > NEXT_PASS (pass_tm_init); > { > struct opt_pass **p = &pass_tm_init.pass.sub; > Index: trunk/gcc/testsuite/lib/c-torture.exp > =================================================================== > *** trunk.orig/gcc/testsuite/lib/c-torture.exp 2011-10-24 10:18:31.000000000 > +0200 > --- trunk/gcc/testsuite/lib/c-torture.exp 2012-08-10 12:27:25.494062458 > +0200 > *************** if [info exists TORTURE_OPTIONS] { > *** 42,48 **** > { -O3 -fomit-frame-pointer -funroll-loops } \ > { -O3 -fomit-frame-pointer -funroll-all-loops -finline-functions } \ > { -O3 -g } \ > ! { -Os } ] > } > > if [info exists ADDITIONAL_TORTURE_OPTIONS] { > --- 42,49 ---- > { -O3 -fomit-frame-pointer -funroll-loops } \ > { -O3 -fomit-frame-pointer -funroll-all-loops -finline-functions } \ > { -O3 -g } \ > ! { -Os } \ > ! { -Og -g } ] > } > > if [info exists ADDITIONAL_TORTURE_OPTIONS] { > Index: trunk/gcc/doc/invoke.texi > =================================================================== > *** trunk.orig/gcc/doc/invoke.texi 2012-08-06 12:36:44.000000000 +0200 > --- trunk/gcc/doc/invoke.texi 2012-08-10 13:18:40.760955978 +0200 > *************** Objective-C and Objective-C++ Dialects}. > *** 422,428 **** > -fvariable-expansion-in-unroller -fvect-cost-model -fvpt -fweb @gol > -fwhole-program -fwpa -fuse-linker-plugin @gol > --param @var{name}=@var{value} > ! -O -O0 -O1 -O2 -O3 -Os -Ofast} > > @item Preprocessor Options > @xref{Preprocessor Options,,Options Controlling the Preprocessor}. > --- 422,428 ---- > -fvariable-expansion-in-unroller -fvect-cost-model -fvpt -fweb @gol > -fwhole-program -fwpa -fuse-linker-plugin @gol > --param @var{name}=@var{value} > ! -O -O0 -O1 -O2 -O3 -Os -Ofast -Og} > > @item Preprocessor Options > @xref{Preprocessor Options,,Options Controlling the Preprocessor}. > *************** valid for all standard compliant program > *** 6344,6349 **** > --- 6344,6357 ---- > It turns on @option{-ffast-math} and the Fortran-specific > @option{-fno-protect-parens} and @option{-fstack-arrays}. > > + @item -Og > + @opindex Og > + Optimize debugging experience. @option{-Og} enables optimizations > + that do not interfere with debugging. It should be the optimization > + level of choice for the standard edit-compile-debug cycle, offering > + a reasonable level of optimization while maintaining fast compilation > + and a good debugging experience. > + > If you use multiple @option{-O} options, with or without level numbers, > the last such option is the one that is effective. > @end table