From c5fa0890a2a879bc6c240e83ff67036ca46e1a8d Mon Sep 17 00:00:00 2001 From: Joseph Myers Date: Fri, 12 Nov 2010 23:30:42 +0000 Subject: opts-common.c (control_warning_option): New. * opts-common.c (control_warning_option): New. * opts.c (set_default_handlers): New. (decode_options): Use set_default_handlers and control_warning_option. (common_handle_option): Update call to enable_warning_as_error. (enable_warning_as_error): Take gcc_options parameters. Use control_warning_option. * opts.h (set_default_handlers, control_warning_option): Declare. c-family: * c-common.h (c_family_lang_mask): Declare. * c-opts.c (c_family_lang_mask): Make extern. * c-pragma.c (handle_pragma_diagnostic): Use control_warning_option. testsuite: * gcc.dg/pragma-diag-2.c: New test. From-SVN: r166689 --- gcc/ChangeLog | 11 ++++++ gcc/c-family/ChangeLog | 7 ++++ gcc/c-family/c-common.h | 1 + gcc/c-family/c-opts.c | 6 ++- gcc/c-family/c-pragma.c | 15 +++----- gcc/opts-common.c | 31 ++++++++++++++++ gcc/opts.c | 72 ++++++++++++++++++------------------ gcc/opts.h | 8 ++++ gcc/testsuite/ChangeLog | 4 ++ gcc/testsuite/gcc.dg/pragma-diag-2.c | 9 +++++ 10 files changed, 118 insertions(+), 46 deletions(-) create mode 100644 gcc/testsuite/gcc.dg/pragma-diag-2.c (limited to 'gcc') diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 6839f84..28ac107 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,5 +1,16 @@ 2010-11-12 Joseph Myers + * opts-common.c (control_warning_option): New. + * opts.c (set_default_handlers): New. + (decode_options): Use set_default_handlers and + control_warning_option. + (common_handle_option): Update call to enable_warning_as_error. + (enable_warning_as_error): Take gcc_options parameters. Use + control_warning_option. + * opts.h (set_default_handlers, control_warning_option): Declare. + +2010-11-12 Joseph Myers + * Makefile.in (OPTS_H): Define. (c-decl.o, c-family/c-common.o, c-family/c-opts.o, c-family/c-pch.o, c-family/c-pragma.o, gcc.o, gccspec.o, diff --git a/gcc/c-family/ChangeLog b/gcc/c-family/ChangeLog index 1bbb957..bb0472e 100644 --- a/gcc/c-family/ChangeLog +++ b/gcc/c-family/ChangeLog @@ -1,5 +1,12 @@ 2010-11-12 Joseph Myers + * c-common.h (c_family_lang_mask): Declare. + * c-opts.c (c_family_lang_mask): Make extern. + * c-pragma.c (handle_pragma_diagnostic): Use + control_warning_option. + +2010-11-12 Joseph Myers + * c-common.c (parse_optimize_options): Update call to decode_options. * c-common.h (c_common_handle_option): Update prototype. diff --git a/gcc/c-family/c-common.h b/gcc/c-family/c-common.h index eb6cf26..a28183a9 100644 --- a/gcc/c-family/c-common.h +++ b/gcc/c-family/c-common.h @@ -762,6 +762,7 @@ extern void set_compound_literal_name (tree decl); extern tree build_va_arg (location_t, tree, tree); +extern const unsigned int c_family_lang_mask; extern unsigned int c_common_option_lang_mask (void); extern void c_common_initialize_diagnostics (diagnostic_context *); extern bool c_common_complain_wrong_lang_p (const struct cl_option *); diff --git a/gcc/c-family/c-opts.c b/gcc/c-family/c-opts.c index 7ddb754..46f6c78 100644 --- a/gcc/c-family/c-opts.c +++ b/gcc/c-family/c-opts.c @@ -132,7 +132,7 @@ static struct deferred_opt } *deferred_opts; -static const unsigned int +extern const unsigned int c_family_lang_mask = (CL_C | CL_CXX | CL_ObjC | CL_ObjCXX); /* Defer option CODE with argument ARG. */ @@ -467,6 +467,10 @@ c_common_handle_option (size_t scode, const char *arg, int value, cpp_opts->warn_invalid_pch = value; break; + case OPT_Wlong_long: + cpp_opts->cpp_warn_long_long = value; + break; + case OPT_Wmissing_include_dirs: cpp_opts->warn_missing_include_dirs = value; break; diff --git a/gcc/c-family/c-pragma.c b/gcc/c-family/c-pragma.c index 23be179..9c00983 100644 --- a/gcc/c-family/c-pragma.c +++ b/gcc/c-family/c-pragma.c @@ -720,6 +720,7 @@ handle_pragma_diagnostic(cpp_reader *ARG_UNUSED(dummy)) enum cpp_ttype token; diagnostic_t kind; tree x; + struct cl_option_handlers handlers; token = pragma_lex (&x); if (token != CPP_NAME) @@ -748,18 +749,14 @@ handle_pragma_diagnostic(cpp_reader *ARG_UNUSED(dummy)) if (token != CPP_STRING) GCC_BAD ("missing option after %<#pragma GCC diagnostic%> kind"); option_string = TREE_STRING_POINTER (x); + set_default_handlers (&handlers); for (option_index = 0; option_index < cl_options_count; option_index++) if (strcmp (cl_options[option_index].opt_text, option_string) == 0) { - void *flag_var = option_flag_var (option_index, &global_options); - - /* This overrides -Werror, for example. */ - diagnostic_classify_diagnostic (global_dc, option_index, kind, input_location); - /* This makes sure the option is enabled, like -Wfoo would do. */ - if (cl_options[option_index].var_type == CLVC_BOOLEAN - && flag_var - && kind != DK_IGNORED) - *(int *) flag_var = 1; + control_warning_option (option_index, (int) kind, kind != DK_IGNORED, + input_location, c_family_lang_mask, &handlers, + &global_options, &global_options_set, + global_dc); return; } GCC_BAD ("unknown option after %<#pragma GCC diagnostic%> kind"); diff --git a/gcc/opts-common.c b/gcc/opts-common.c index c114d4e..cc20410 100644 --- a/gcc/opts-common.c +++ b/gcc/opts-common.c @@ -977,3 +977,34 @@ option_flag_var (int opt_index, struct gcc_options *opts) return NULL; return (void *)(((char *) opts) + option->flag_var_offset); } + +/* Set a warning option OPT_INDEX (language mask LANG_MASK, option + handlers HANDLERS) to have diagnostic kind KIND for option + structures OPTS and OPTS_SET and diagnostic context DC (possibly + NULL), at location LOC (UNKNOWN_LOCATION for -Werror=). If IMPLY, + the warning option in question is implied at this point. This is + used by -Werror= and #pragma GCC diagnostic. */ + +void +control_warning_option (unsigned int opt_index, int kind, bool imply, + location_t loc, unsigned int lang_mask, + const struct cl_option_handlers *handlers, + struct gcc_options *opts, + struct gcc_options *opts_set, + diagnostic_context *dc) +{ + if (cl_options[opt_index].alias_target != N_OPTS) + opt_index = cl_options[opt_index].alias_target; + if (opt_index == OPT_SPECIAL_ignore) + return; + if (dc) + diagnostic_classify_diagnostic (dc, opt_index, (diagnostic_t) kind, loc); + if (imply) + { + /* -Werror=foo implies -Wfoo. */ + if (cl_options[opt_index].var_type == CLVC_BOOLEAN) + handle_generated_option (opts, opts_set, + opt_index, NULL, 1, lang_mask, + kind, loc, handlers, dc); + } +} diff --git a/gcc/opts.c b/gcc/opts.c index 5d8793e..d4d7f1d8 100644 --- a/gcc/opts.c +++ b/gcc/opts.c @@ -363,6 +363,8 @@ static void set_unsafe_math_optimizations_flags (struct gcc_options *opts, static void enable_warning_as_error (const char *arg, int value, unsigned int lang_mask, const struct cl_option_handlers *handlers, + struct gcc_options *opts, + struct gcc_options *opts_set, location_t loc, diagnostic_context *dc); @@ -1014,6 +1016,23 @@ default_options_optimization (struct gcc_options *opts, static void finish_options (struct gcc_options *, struct gcc_options *); +/* Set *HANDLERS to the default set of option handlers for use in the + compilers proper (not the driver). */ +void +set_default_handlers (struct cl_option_handlers *handlers) +{ + handlers->unknown_option_callback = unknown_option_callback; + handlers->wrong_lang_callback = complain_wrong_lang; + handlers->post_handling_callback = post_handling_callback; + handlers->num_handlers = 3; + handlers->handlers[0].handler = lang_handle_option; + handlers->handlers[0].mask = initial_lang_mask; + handlers->handlers[1].handler = common_handle_option; + handlers->handlers[1].mask = CL_COMMON; + handlers->handlers[2].handler = target_handle_option; + handlers->handlers[2].mask = CL_TARGET; +} + /* Parse command line options and set default flag values. Do minimal options processing. The decoded options are in *DECODED_OPTIONS and *DECODED_OPTIONS_COUNT; settings go in OPTS, OPTS_SET and DC; @@ -1030,20 +1049,12 @@ decode_options (struct gcc_options *opts, struct gcc_options *opts_set, lang_mask = initial_lang_mask; - handlers.unknown_option_callback = unknown_option_callback; - handlers.wrong_lang_callback = complain_wrong_lang; - handlers.post_handling_callback = post_handling_callback; - handlers.num_handlers = 3; - handlers.handlers[0].handler = lang_handle_option; - handlers.handlers[0].mask = lang_mask; - handlers.handlers[1].handler = common_handle_option; - handlers.handlers[1].mask = CL_COMMON; - handlers.handlers[2].handler = target_handle_option; - handlers.handlers[2].mask = CL_TARGET; - - /* Enable -Werror=coverage-mismatch by default */ - enable_warning_as_error ("coverage-mismatch", 1, lang_mask, &handlers, - loc, dc); + set_default_handlers (&handlers); + + /* Enable -Werror=coverage-mismatch by default. */ + control_warning_option (OPT_Wcoverage_mismatch, (int) DK_ERROR, true, + loc, lang_mask, + &handlers, opts, opts_set, dc); default_options_optimization (opts, opts_set, decoded_options, decoded_options_count, @@ -1778,7 +1789,8 @@ common_handle_option (struct gcc_options *opts, break; case OPT_Werror_: - enable_warning_as_error (arg, value, lang_mask, handlers, loc, dc); + enable_warning_as_error (arg, value, lang_mask, handlers, + opts, opts_set, loc, dc); break; case OPT_Wlarger_than_: @@ -2411,13 +2423,15 @@ get_option_state (struct gcc_options *opts, int option, } /* Enable (or disable if VALUE is 0) a warning option ARG (language - mask LANG_MASK, option handlers HANDLERS) as an error for - diagnostic context DC (possibly NULL), location LOC. This is used - by -Werror=. */ + mask LANG_MASK, option handlers HANDLERS) as an error for option + structures OPTS and OPTS_SET, diagnostic context DC (possibly + NULL), location LOC. This is used by -Werror=. */ static void enable_warning_as_error (const char *arg, int value, unsigned int lang_mask, const struct cl_option_handlers *handlers, + struct gcc_options *opts, + struct gcc_options *opts_set, location_t loc, diagnostic_context *dc) { char *new_option; @@ -2429,29 +2443,15 @@ enable_warning_as_error (const char *arg, int value, unsigned int lang_mask, option_index = find_opt (new_option, lang_mask); if (option_index == OPT_SPECIAL_unknown) { - error ("-Werror=%s: No option -%s", arg, new_option); + error ("-Werror=%s: no option -%s", arg, new_option); } else { - const struct cl_option *option = &cl_options[option_index]; const diagnostic_t kind = value ? DK_ERROR : DK_WARNING; - if (option->alias_target != N_OPTS) - option_index = option->alias_target; - if (option_index == OPT_SPECIAL_ignore) - return; - if (dc) - diagnostic_classify_diagnostic (dc, option_index, kind, loc); - if (kind == DK_ERROR) - { - const struct cl_option * const option = cl_options + option_index; - - /* -Werror=foo implies -Wfoo. */ - if (option->var_type == CLVC_BOOLEAN) - handle_generated_option (&global_options, &global_options_set, - option_index, NULL, value, lang_mask, - (int)kind, loc, handlers, dc); - } + control_warning_option (option_index, (int) kind, value, + loc, lang_mask, + handlers, opts, opts_set, dc); } free (new_option); } diff --git a/gcc/opts.h b/gcc/opts.h index 9d5ecb3..00422b6 100644 --- a/gcc/opts.h +++ b/gcc/opts.h @@ -223,6 +223,7 @@ extern void decode_cmdline_options_to_array_default_mask (unsigned int argc, const char **argv, struct cl_decoded_option **decoded_options, unsigned int *decoded_options_count); +extern void set_default_handlers (struct cl_option_handlers *handlers); extern void decode_options (struct gcc_options *opts, struct gcc_options *opts_set, struct cl_decoded_option *decoded_options, @@ -255,5 +256,12 @@ extern void read_cmdline_option (struct gcc_options *opts, unsigned int lang_mask, const struct cl_option_handlers *handlers, diagnostic_context *dc); +extern void control_warning_option (unsigned int opt_index, int kind, + bool imply, location_t loc, + unsigned int lang_mask, + const struct cl_option_handlers *handlers, + struct gcc_options *opts, + struct gcc_options *opts_set, + diagnostic_context *dc); extern void print_ignored_options (void); #endif diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 79efb0b..8eeb72c 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,7 @@ +2010-11-12 Joseph Myers + + * gcc.dg/pragma-diag-2.c: New test. + 2010-11-12 Jerry DeLisle PR fortran/45794 diff --git a/gcc/testsuite/gcc.dg/pragma-diag-2.c b/gcc/testsuite/gcc.dg/pragma-diag-2.c new file mode 100644 index 0000000..588d618 --- /dev/null +++ b/gcc/testsuite/gcc.dg/pragma-diag-2.c @@ -0,0 +1,9 @@ +/* { dg-do compile } */ +/* { dg-options "-std=c89 -pedantic -Wno-long-long" } */ +/* { dg-message "warnings being treated as errors" "" { target *-*-* } 0 } */ + +int i = 0LL; + +#pragma GCC diagnostic error "-Wlong-long" + +int j = 1LL; /* { dg-error "long long" } */ -- cgit v1.1