From patchwork Mon May 24 22:16:45 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Martin Sebor X-Patchwork-Id: 1482992 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=gcc.gnu.org (client-ip=8.43.85.97; helo=sourceware.org; envelope-from=gcc-patches-bounces@gcc.gnu.org; receiver=) Authentication-Results: ozlabs.org; dkim=pass (1024-bit key; unprotected) header.d=gcc.gnu.org header.i=@gcc.gnu.org header.a=rsa-sha256 header.s=default header.b=kXEEEThx; dkim-atps=neutral Received: from sourceware.org (ip-8-43-85-97.sourceware.org [8.43.85.97]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 4Fps566p9Hz9s24 for ; Tue, 25 May 2021 08:16:58 +1000 (AEST) Received: from server2.sourceware.org (localhost [IPv6:::1]) by sourceware.org (Postfix) with ESMTP id E433A383581E; Mon, 24 May 2021 22:16:56 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org E433A383581E DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gcc.gnu.org; s=default; t=1621894617; bh=+3i8DD6ta7Qe+iOaus23TMm1jq81ZU82jkDf5KE962E=; h=Subject:To:References:Date:In-Reply-To:List-Id:List-Unsubscribe: List-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To: From; b=kXEEEThxekNLKhRs4km0BhEa/6fxKX3NRrlsxGBDPJ9DrWJZx+pFP3u0VhBcBjDt/ e7FDZjl1mVVN4vHEZetYYTFojcc+cKmNdxwcR5iMem7vFb5RCxBRTyfszkTDEPQllk mHAGhfKzWNE3m6gdNe7lZ9xDpAYU4N5bXkZM7WAo= X-Original-To: gcc-patches@gcc.gnu.org Delivered-To: gcc-patches@gcc.gnu.org Received: from us-smtp-delivery-124.mimecast.com (us-smtp-delivery-124.mimecast.com [170.10.133.124]) by sourceware.org (Postfix) with ESMTP id 6EE98385481A for ; Mon, 24 May 2021 22:16:49 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.3.2 sourceware.org 6EE98385481A Received: from mimecast-mx01.redhat.com (mimecast-mx01.redhat.com [209.132.183.4]) (Using TLS) by relay.mimecast.com with ESMTP id us-mta-364-4Wiw8iYnNRSYhO8s_S3zkw-1; Mon, 24 May 2021 18:16:46 -0400 X-MC-Unique: 4Wiw8iYnNRSYhO8s_S3zkw-1 Received: from smtp.corp.redhat.com (int-mx02.intmail.prod.int.phx2.redhat.com [10.5.11.12]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mimecast-mx01.redhat.com (Postfix) with ESMTPS id 03768107ACC7 for ; Mon, 24 May 2021 22:16:46 +0000 (UTC) Received: from [10.3.114.34] (ovpn-114-34.phx2.redhat.com [10.3.114.34]) by smtp.corp.redhat.com (Postfix) with ESMTP id 7843C60C05 for ; Mon, 24 May 2021 22:16:45 +0000 (UTC) Subject: [PATCH 11/11] use xxx_no_warning APIs in the middle end To: gcc-patches References: <92db3776-af59-fa20-483b-aa67b17d0751@gmail.com> <535d1b55-fc0a-63c3-08b5-48a017674d1e@gmail.com> Message-ID: <9abe39b2-68cb-8381-68f8-c1a1ec73f108@redhat.com> Date: Mon, 24 May 2021 16:16:45 -0600 User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:68.0) Gecko/20100101 Thunderbird/68.2.2 MIME-Version: 1.0 In-Reply-To: <535d1b55-fc0a-63c3-08b5-48a017674d1e@gmail.com> X-Scanned-By: MIMEDefang 2.79 on 10.5.11.12 X-Mimecast-Spam-Score: 0 X-Mimecast-Originator: redhat.com Content-Language: en-US X-Spam-Status: No, score=-10.6 required=5.0 tests=BAYES_00, DKIMWL_WL_HIGH, DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, DKIM_VALID_EF, GIT_PATCH_0, KAM_STOCKTIP, RCVD_IN_DNSWL_LOW, RCVD_IN_MSPIKE_H4, RCVD_IN_MSPIKE_WL, SPF_HELO_NONE, SPF_PASS, TXREP, T_FILL_THIS_FORM_SHORT autolearn=ham autolearn_force=no version=3.4.2 X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on server2.sourceware.org X-BeenThere: gcc-patches@gcc.gnu.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Gcc-patches mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Martin Sebor via Gcc-patches From: Martin Sebor Reply-To: Martin Sebor Errors-To: gcc-patches-bounces@gcc.gnu.org Sender: "Gcc-patches" The attached patch replaces TREE_NO_WARNING, gimple_get_no_warning_p and gimple_set_no_warning with the new APIs, get_no_warning, set_no_warning, and copy_no_warning. Add support for per-location warning groups. gcc/ChangeLog: * builtins.c (warn_string_no_nul): Replace uses of TREE_NO_WARNING, gimple_no_warning_p and gimple_set_no_warning with get_no_warning, and set_no_warning. (c_strlen): Same. (maybe_warn_for_bound): Same. (warn_for_access): Same. (check_access): Same. (expand_builtin_strncmp): Same. (fold_builtin_varargs): Same. * calls.c (maybe_warn_nonstring_arg): Same. (maybe_warn_rdwr_sizes): Same. * cfgexpand.c (expand_call_stmt): Same. * cgraphunit.c (check_global_declaration): Same. * fold-const.c (fold_undefer_overflow_warnings): Same. (fold_truth_not_expr): Same. (fold_unary_loc): Same. (fold_checksum_tree): Same. * gengtype.c (open_base_files): Same. * gimple-array-bounds.cc (array_bounds_checker::check_array_ref): Same. (array_bounds_checker::check_mem_ref): Same. (array_bounds_checker::check_addr_expr): Same. (array_bounds_checker::check_array_bounds): Same. * gimple-expr.c (copy_var_decl): Same. * gimple-fold.c (gimple_fold_builtin_strcpy): Same. (gimple_fold_builtin_strncat): Same. (gimple_fold_builtin_stxcpy_chk): Same. (gimple_fold_builtin_stpcpy): Same. (gimple_fold_builtin_sprintf): Same. (fold_stmt_1): Same. * gimple-ssa-isolate-paths.c (diag_returned_locals): Same. * gimple-ssa-nonnull-compare.c (do_warn_nonnull_compare): Same. * gimple-ssa-sprintf.c (handle_printf_call): Same. * gimple-ssa-store-merging.c (imm_store_chain_info::output_merged_store): Same. * gimple-ssa-warn-restrict.c (maybe_diag_overlap): Same. (maybe_diag_access_bounds): Same. (check_call): Same. (check_bounds_or_overlap): Same. * gimple.c (gimple_build_call_from_tree): Same. * gimplify.c (gimplify_return_expr): Same. (gimplify_cond_expr): Same. (gimplify_modify_expr_complex_part): Same. (gimplify_modify_expr): Same. (gimple_push_cleanup): Same. (gimplify_expr): Same. * omp-expand.c (expand_omp_for_generic): Same. (expand_omp_taskloop_for_outer): Same. * omp-low.c (lower_rec_input_clauses): Same. (lower_lastprivate_clauses): Same. (lower_send_clauses): Same. (lower_omp_target): Same. * tree-cfg.c (pass_warn_function_return::execute): Same. * tree-complex.c (create_one_component_var): Same. * tree-inline.c (remap_gimple_op_r): Same. (copy_tree_body_r): Same. (declare_return_variable): Same. (expand_call_inline): Same. * tree-nested.c (lookup_field_for_decl): Same. * tree-sra.c (create_access_replacement): Same. (generate_subtree_copies): Same. * tree-ssa-ccp.c (pass_post_ipa_warn::execute): Same. * tree-ssa-forwprop.c (combine_cond_expr_cond): Same. * tree-ssa-loop-ch.c (ch_base::copy_headers): Same. * tree-ssa-loop-im.c (execute_sm): Same. * tree-ssa-phiopt.c (cond_store_replacement): Same. * tree-ssa-strlen.c (maybe_warn_overflow): Same. (handle_builtin_strcpy): Same. (maybe_diag_stxncpy_trunc): Same. (handle_builtin_stxncpy_strncat): Same. (handle_builtin_strcat): Same. * tree-ssa-uninit.c (get_no_uninit_warning): Same. (set_no_uninit_warning): Same. (uninit_undefined_value_p): Same. (warn_uninit): Same. (maybe_warn_operand): Same. * tree-vrp.c (compare_values_warnv): Same. * vr-values.c (vr_values::extract_range_for_var_from_comparison_expr): Same. (test_for_singularity): Same. * gimple.h (get_no_warning): New. (set_no_warning): Same. (copy_no_warning): Same. (gimple_set_block): Call gimple_set_location. (gimple_set_location): Call copy_warning. (gimple_no_warning_p): Remove. (gimple_set_no_warning): Same. * tree.h (TREE_NO_WARNING): Remove. (get_no_warning): New. (set_no_warning): Same. (copy_no_warning): Same. diff --git a/gcc/builtins.c b/gcc/builtins.c index b0c880dc3b5..105deadd42b 100644 --- a/gcc/builtins.c +++ b/gcc/builtins.c @@ -1094,7 +1094,9 @@ warn_string_no_nul (location_t loc, tree expr, const char *fname, bool exact /* = false */, const wide_int bndrng[2] /* = NULL */) { - if ((expr && TREE_NO_WARNING (expr)) || TREE_NO_WARNING (arg)) + const int opt = OPT_Wstringop_overread; + if ((expr && get_no_warning (expr, opt)) + || get_no_warning (arg, opt)) return; loc = expansion_point_location_if_in_system_header (loc); @@ -1122,14 +1124,14 @@ warn_string_no_nul (location_t loc, tree expr, const char *fname, if (bndrng) { if (wi::ltu_p (maxsiz, bndrng[0])) - warned = warning_at (loc, OPT_Wstringop_overread, + warned = warning_at (loc, opt, "%K%qD specified bound %s exceeds " "maximum object size %E", expr, func, bndstr, maxobjsize); else { bool maybe = wi::to_wide (size) == bndrng[0]; - warned = warning_at (loc, OPT_Wstringop_overread, + warned = warning_at (loc, opt, exact ? G_("%K%qD specified bound %s exceeds " "the size %E of unterminated array") @@ -1144,7 +1146,7 @@ warn_string_no_nul (location_t loc, tree expr, const char *fname, } } else - warned = warning_at (loc, OPT_Wstringop_overread, + warned = warning_at (loc, opt, "%K%qD argument missing terminating nul", expr, func); } @@ -1153,14 +1155,14 @@ warn_string_no_nul (location_t loc, tree expr, const char *fname, if (bndrng) { if (wi::ltu_p (maxsiz, bndrng[0])) - warned = warning_at (loc, OPT_Wstringop_overread, + warned = warning_at (loc, opt, "%qs specified bound %s exceeds " "maximum object size %E", fname, bndstr, maxobjsize); else { bool maybe = wi::to_wide (size) == bndrng[0]; - warned = warning_at (loc, OPT_Wstringop_overread, + warned = warning_at (loc, opt, exact ? G_("%qs specified bound %s exceeds " "the size %E of unterminated array") @@ -1175,7 +1177,7 @@ warn_string_no_nul (location_t loc, tree expr, const char *fname, } } else - warned = warning_at (loc, OPT_Wstringop_overread, + warned = warning_at (loc, opt, "%qs argument missing terminating nul", fname); } @@ -1184,9 +1186,9 @@ warn_string_no_nul (location_t loc, tree expr, const char *fname, { inform (DECL_SOURCE_LOCATION (decl), "referenced argument declared here"); - TREE_NO_WARNING (arg) = 1; + set_no_warning (arg, opt); if (expr) - TREE_NO_WARNING (expr) = 1; + set_no_warning (expr, opt); } } @@ -1443,14 +1445,14 @@ c_strlen (tree arg, int only_value, c_strlen_data *data, unsigned eltsize) { /* Suppress multiple warnings for propagated constant strings. */ if (only_value != 2 - && !TREE_NO_WARNING (arg) + && !get_no_warning (arg/*, OPT_Warray_bounds*/) && warning_at (loc, OPT_Warray_bounds, "offset %qwi outside bounds of constant string", eltoff)) { if (decl) inform (DECL_SOURCE_LOCATION (decl), "%qE declared here", decl); - TREE_NO_WARNING (arg) = 1; + set_no_warning (arg, OPT_Warray_bounds); } return NULL_TREE; } @@ -3936,7 +3938,7 @@ static bool maybe_warn_for_bound (int opt, location_t loc, tree exp, tree func, tree bndrng[2], tree size, const access_data *pad = NULL) { - if (!bndrng[0] || TREE_NO_WARNING (exp)) + if (!bndrng[0] || get_no_warning (exp, opt)) return false; tree maxobjsize = max_object_size (); @@ -4028,7 +4030,7 @@ maybe_warn_for_bound (int opt, location_t loc, tree exp, tree func, inform (EXPR_LOCATION (pad->src.ref), "source object allocated here"); } - TREE_NO_WARNING (exp) = true; + set_no_warning (exp, opt); } return warned; @@ -4075,14 +4077,14 @@ maybe_warn_for_bound (int opt, location_t loc, tree exp, tree func, return false; else if (tree_int_cst_equal (bndrng[0], bndrng[1])) warned = (func - ? warning_at (loc, OPT_Wstringop_overflow_, + ? warning_at (loc, opt, (maybe ? G_("%K%qD specified bound %E may exceed " "destination size %E") : G_("%K%qD specified bound %E exceeds " "destination size %E")), exp, func, bndrng[0], size) - : warning_at (loc, OPT_Wstringop_overflow_, + : warning_at (loc, opt, (maybe ? G_("%Kspecified bound %E may exceed " "destination size %E") @@ -4091,14 +4093,14 @@ maybe_warn_for_bound (int opt, location_t loc, tree exp, tree func, exp, bndrng[0], size)); else warned = (func - ? warning_at (loc, OPT_Wstringop_overflow_, + ? warning_at (loc, opt, (maybe ? G_("%K%qD specified bound [%E, %E] may exceed " "destination size %E") : G_("%K%qD specified bound [%E, %E] exceeds " "destination size %E")), exp, func, bndrng[0], bndrng[1], size) - : warning_at (loc, OPT_Wstringop_overflow_, + : warning_at (loc, opt, (maybe ? G_("%Kspecified bound [%E, %E] exceeds " "destination size %E") @@ -4117,7 +4119,7 @@ maybe_warn_for_bound (int opt, location_t loc, tree exp, tree func, inform (EXPR_LOCATION (pad->dst.ref), "destination object allocated here"); } - TREE_NO_WARNING (exp) = true; + set_no_warning (exp, opt); } return warned; @@ -4343,7 +4345,7 @@ warn_for_access (location_t loc, tree func, tree exp, int opt, tree range[2], exp, range[0], range[1], size)); if (warned) - TREE_NO_WARNING (exp) = true; + set_no_warning (exp, OPT_Wstringop_overread); return warned; } @@ -4386,7 +4388,7 @@ warn_for_access (location_t loc, tree func, tree exp, int opt, tree range[2], exp, range[0], range[1], size)); if (warned) - TREE_NO_WARNING (exp) = true; + set_no_warning (exp, OPT_Wstringop_overread); return warned; } @@ -4765,8 +4767,10 @@ check_access (tree exp, tree dstwrite, && tree_fits_uhwi_p (dstwrite) && tree_int_cst_lt (dstwrite, range[0])))) { - if (TREE_NO_WARNING (exp) - || (pad && pad->dst.ref && TREE_NO_WARNING (pad->dst.ref))) + const int opt = OPT_Wstringop_overflow_; + if (get_no_warning (exp, opt) + || (pad && pad->dst.ref + && get_no_warning (pad->dst.ref, opt))) return false; location_t loc = tree_inlined_location (exp); @@ -4777,12 +4781,12 @@ check_access (tree exp, tree dstwrite, and a source of unknown length. The call will write at least one byte past the end of the destination. */ warned = (func - ? warning_at (loc, OPT_Wstringop_overflow_, + ? warning_at (loc, opt, "%K%qD writing %E or more bytes into " "a region of size %E overflows " "the destination", exp, func, range[0], dstsize) - : warning_at (loc, OPT_Wstringop_overflow_, + : warning_at (loc, opt, "%Kwriting %E or more bytes into " "a region of size %E overflows " "the destination", @@ -4803,7 +4807,7 @@ check_access (tree exp, tree dstwrite, if (warned) { - TREE_NO_WARNING (exp) = true; + set_no_warning (exp, OPT_Wstringop_overflow_); if (pad) pad->dst.inform_access (pad->mode); } @@ -4876,19 +4880,21 @@ check_access (tree exp, tree dstwrite, if (overread) { - if (TREE_NO_WARNING (exp) - || (srcstr && TREE_NO_WARNING (srcstr)) - || (pad && pad->src.ref && TREE_NO_WARNING (pad->src.ref))) + const int opt = OPT_Wstringop_overread; + if (get_no_warning (exp, opt) + || (srcstr && get_no_warning (srcstr, opt)) + || (pad && pad->src.ref + && get_no_warning (pad->src.ref, opt))) return false; location_t loc = tree_inlined_location (exp); const bool read = mode == access_read_only || mode == access_read_write; const bool maybe = pad && pad->dst.parmarray; - if (warn_for_access (loc, func, exp, OPT_Wstringop_overread, range, - slen, false, read, maybe)) + if (warn_for_access (loc, func, exp, opt, range, slen, false, read, + maybe)) { - TREE_NO_WARNING (exp) = true; + set_no_warning (exp, opt); if (pad) pad->src.inform_access (access_read_only); } @@ -7413,8 +7419,7 @@ expand_builtin_strncmp (tree exp, ATTRIBUTE_UNUSED rtx target, /* Expand the library call ourselves using a stabilized argument list to avoid re-evaluating the function's arguments twice. */ tree call = build_call_nofold_loc (loc, fndecl, 3, arg1, arg2, len); - if (TREE_NO_WARNING (exp)) - TREE_NO_WARNING (call) = true; + copy_no_warning (call, exp); gcc_assert (TREE_CODE (call) == CALL_EXPR); CALL_EXPR_TAILCALL (call) = CALL_EXPR_TAILCALL (exp); return expand_call (call, target, target == const0_rtx); @@ -13953,7 +13958,7 @@ fold_builtin_varargs (location_t loc, tree fndecl, tree *args, int nargs) { ret = build1 (NOP_EXPR, TREE_TYPE (ret), ret); SET_EXPR_LOCATION (ret, loc); - TREE_NO_WARNING (ret) = 1; + set_no_warning (ret); return ret; } return NULL_TREE; diff --git a/gcc/calls.c b/gcc/calls.c index f3da1839dc5..47e2a2b54de 100644 --- a/gcc/calls.c +++ b/gcc/calls.c @@ -1622,7 +1622,7 @@ maybe_warn_nonstring_arg (tree fndecl, tree exp) if (!fndecl || !fndecl_built_in_p (fndecl, BUILT_IN_NORMAL)) return false; - if (TREE_NO_WARNING (exp) || !warn_stringop_overread) + if (!warn_stringop_overread || get_no_warning (exp, OPT_Wstringop_overread)) return false; /* Avoid clearly invalid calls (more checking done below). */ @@ -1738,7 +1738,7 @@ maybe_warn_nonstring_arg (tree fndecl, tree exp) exp, fndecl, bndrng[0], bndrng[1], maxobjsize); if (warned) - TREE_NO_WARNING (exp) = true; + set_no_warning (exp, OPT_Wstringop_overread); return warned; } @@ -1915,7 +1915,7 @@ maybe_warn_nonstring_arg (tree fndecl, tree exp) } if (any_arg_warned) - TREE_NO_WARNING (exp) = true; + set_no_warning (exp, OPT_Wstringop_overread); return any_arg_warned; } @@ -1978,7 +1978,7 @@ maybe_warn_rdwr_sizes (rdwr_map *rwm, tree fndecl, tree fntype, tree exp) /* Set if a warning has been issued for any argument (used to decide whether to emit an informational note at the end). */ - bool any_warned = false; + int opt_warned = false; /* A string describing the attributes that the warnings issued by this function apply to. Used to print one informational note per function @@ -2053,7 +2053,7 @@ maybe_warn_rdwr_sizes (rdwr_map *rwm, tree fndecl, tree fntype, tree exp) *sizstr = '\0'; /* Set if a warning has been issued for the current argument. */ - bool arg_warned = false; + int arg_warned = 0; location_t loc = EXPR_LOCATION (exp); tree ptr = access.second.ptr; if (*sizstr @@ -2066,24 +2066,25 @@ maybe_warn_rdwr_sizes (rdwr_map *rwm, tree fndecl, tree fntype, tree exp) const std::string argtypestr = access.second.array_as_string (ptrtype); - arg_warned = warning_at (loc, OPT_Wstringop_overflow_, - "%Kbound argument %i value %s is " - "negative for a variable length array " - "argument %i of type %s", - exp, sizidx + 1, sizstr, - ptridx + 1, argtypestr.c_str ()); + if (warning_at (loc, OPT_Wstringop_overflow_, + "%Kbound argument %i value %s is " + "negative for a variable length array " + "argument %i of type %s", + exp, sizidx + 1, sizstr, + ptridx + 1, argtypestr.c_str ())) + arg_warned = OPT_Wstringop_overflow_; } - else - arg_warned = warning_at (loc, OPT_Wstringop_overflow_, - "%Kargument %i value %s is negative", - exp, sizidx + 1, sizstr); + else if (warning_at (loc, OPT_Wstringop_overflow_, + "%Kargument %i value %s is negative", + exp, sizidx + 1, sizstr)) + arg_warned = OPT_Wstringop_overflow_; if (arg_warned) { append_attrname (access, attrstr, sizeof attrstr); /* Remember a warning has been issued and avoid warning again below for the same attribute. */ - any_warned = true; + opt_warned = arg_warned; continue; } } @@ -2121,31 +2122,33 @@ maybe_warn_rdwr_sizes (rdwr_map *rwm, tree fndecl, tree fntype, tree exp) const std::string argtypestr = access.second.array_as_string (ptrtype); - arg_warned = warning_at (loc, OPT_Wnonnull, - "%Kargument %i of variable length " - "array %s is null but " - "the corresponding bound argument " - "%i value is %s", - exp, sizidx + 1, argtypestr.c_str (), - ptridx + 1, sizstr); + if (warning_at (loc, OPT_Wnonnull, + "%Kargument %i of variable length " + "array %s is null but " + "the corresponding bound argument " + "%i value is %s", + exp, sizidx + 1, argtypestr.c_str (), + ptridx + 1, sizstr)) + arg_warned = OPT_Wnonnull; } - else - arg_warned = warning_at (loc, OPT_Wnonnull, - "%Kargument %i is null but " - "the corresponding size argument " - "%i value is %s", - exp, ptridx + 1, sizidx + 1, - sizstr); + else if (warning_at (loc, OPT_Wnonnull, + "%Kargument %i is null but " + "the corresponding size argument " + "%i value is %s", + exp, ptridx + 1, sizidx + 1, + sizstr)) + arg_warned = OPT_Wnonnull; } else if (access_size && access.second.static_p) { /* Warn about null pointers for [static N] array arguments but do not warn for ordinary (i.e., nonstatic) arrays. */ - arg_warned = warning_at (loc, OPT_Wnonnull, - "%Kargument %i to %<%T[static %E]%> " - "is null where non-null expected", - exp, ptridx + 1, argtype, - access_size); + if (warning_at (loc, OPT_Wnonnull, + "%Kargument %i to %<%T[static %E]%> " + "is null where non-null expected", + exp, ptridx + 1, argtype, + access_size)) + arg_warned = OPT_Wnonnull; } if (arg_warned) @@ -2153,7 +2156,7 @@ maybe_warn_rdwr_sizes (rdwr_map *rwm, tree fndecl, tree fntype, tree exp) append_attrname (access, attrstr, sizeof attrstr); /* Remember a warning has been issued and avoid warning again below for the same attribute. */ - any_warned = true; + opt_warned = OPT_Wnonnull; continue; } } @@ -2189,17 +2192,17 @@ maybe_warn_rdwr_sizes (rdwr_map *rwm, tree fndecl, tree fntype, tree exp) /* Clear the no-warning bit in case it was set by check_access in a prior iteration so that accesses via different arguments are diagnosed. */ - TREE_NO_WARNING (exp) = false; + set_no_warning (exp, OPT_Wstringop_overflow_, false); access_mode mode = data.mode; if (mode == access_deferred) mode = TYPE_READONLY (argtype) ? access_read_only : access_read_write; check_access (exp, access_size, /*maxread=*/ NULL_TREE, srcsize, dstsize, mode, &data); - if (TREE_NO_WARNING (exp)) + if (get_no_warning (exp, OPT_Wstringop_overflow_)) + opt_warned = OPT_Wstringop_overflow_; + if (opt_warned) { - any_warned = true; - if (access.second.internal_p) inform (loc, "referencing argument %u of type %qT", ptridx + 1, ptrtype); @@ -2221,7 +2224,7 @@ maybe_warn_rdwr_sizes (rdwr_map *rwm, tree fndecl, tree fntype, tree exp) "in a call with type %qT and attribute %qs", fntype, attrstr); } - else if (any_warned) + else if (opt_warned) { if (fndecl) inform (DECL_SOURCE_LOCATION (fndecl), @@ -2232,7 +2235,7 @@ maybe_warn_rdwr_sizes (rdwr_map *rwm, tree fndecl, tree fntype, tree exp) } /* Set the bit in case if was cleared and not set above. */ - TREE_NO_WARNING (exp) = true; + set_no_warning (exp, opt_warned); } /* Fill in ARGS_SIZE and ARGS array based on the parameters found in diff --git a/gcc/cfgexpand.c b/gcc/cfgexpand.c index 39e5b040427..fcc7cfd3b59 100644 --- a/gcc/cfgexpand.c +++ b/gcc/cfgexpand.c @@ -2807,9 +2807,6 @@ expand_call_stmt (gcall *stmt) if (gimple_call_nothrow_p (stmt)) TREE_NOTHROW (exp) = 1; - if (gimple_no_warning_p (stmt)) - TREE_NO_WARNING (exp) = 1; - CALL_EXPR_TAILCALL (exp) = gimple_call_tail_p (stmt); CALL_EXPR_MUST_TAIL_CALL (exp) = gimple_call_must_tail_p (stmt); CALL_EXPR_RETURN_SLOT_OPT (exp) = gimple_call_return_slot_opt_p (stmt); @@ -2823,6 +2820,9 @@ expand_call_stmt (gcall *stmt) CALL_EXPR_BY_DESCRIPTOR (exp) = gimple_call_by_descriptor_p (stmt); SET_EXPR_LOCATION (exp, gimple_location (stmt)); + /* Must come after copying location. */ + copy_no_warning (exp, stmt); + /* Ensure RTL is created for debug args. */ if (decl && DECL_HAS_DEBUG_ARGS_P (decl)) { diff --git a/gcc/cgraphunit.c b/gcc/cgraphunit.c index 098eb99dc95..40489aab525 100644 --- a/gcc/cgraphunit.c +++ b/gcc/cgraphunit.c @@ -1074,7 +1074,7 @@ check_global_declaration (symtab_node *snode) && ! DECL_ARTIFICIAL (decl) && ! TREE_PUBLIC (decl)) { - if (TREE_NO_WARNING (decl)) + if (get_no_warning (decl, OPT_Wunused)) ; else if (snode->referred_to_p (/*include_self=*/false)) pedwarn (input_location, 0, "%q+F used but never defined", decl); diff --git a/gcc/fold-const.c b/gcc/fold-const.c index 3be9c15e6b2..f3bc9ede30c 100644 --- a/gcc/fold-const.c +++ b/gcc/fold-const.c @@ -249,7 +249,7 @@ fold_undefer_overflow_warnings (bool issue, const gimple *stmt, int code) if (!issue || warnmsg == NULL) return; - if (gimple_no_warning_p (stmt)) + if (get_no_warning (stmt, OPT_Wstrict_overflow)) return; /* Use the smallest code level when deciding to issue the @@ -4249,8 +4249,7 @@ fold_truth_not_expr (location_t loc, tree arg) tree ret = build2_loc (loc, code, type, TREE_OPERAND (arg, 0), TREE_OPERAND (arg, 1)); - if (TREE_NO_WARNING (arg)) - TREE_NO_WARNING (ret) = 1; + copy_no_warning (ret, arg); return ret; } @@ -9341,7 +9340,7 @@ fold_unary_loc (location_t loc, enum tree_code code, tree type, tree op0) tem = fold_build1_loc (loc, code, type, TREE_OPERAND (op0, 1)); /* First do the assignment, then return converted constant. */ tem = build2_loc (loc, COMPOUND_EXPR, TREE_TYPE (tem), op0, tem); - TREE_NO_WARNING (tem) = 1; + set_no_warning (tem /* What warning? */); TREE_USED (tem) = 1; return tem; } @@ -13509,10 +13508,10 @@ fold_checksum_tree (const_tree expr, struct md5_ctx *ctx, TYPE_CACHED_VALUES (tmp) = NULL; } } - else if (TREE_NO_WARNING (expr) && (DECL_P (expr) || EXPR_P (expr))) + else if (get_no_warning (expr) && (DECL_P (expr) || EXPR_P (expr))) { - /* Allow TREE_NO_WARNING to be set. Perhaps we shouldn't allow that - and change builtins.c etc. instead - see PR89543. */ + /* Allow the no-warning bit to be set. Perhaps we shouldn't allow + that and change builtins.c etc. instead - see PR89543. */ size_t sz = tree_size (expr); buf = XALLOCAVAR (union tree_node, sz); memcpy ((char *) buf, expr, sz); diff --git a/gcc/gengtype.c b/gcc/gengtype.c index b94e2f126ec..c1fa6d35c87 100644 --- a/gcc/gengtype.c +++ b/gcc/gengtype.c @@ -1727,7 +1727,7 @@ open_base_files (void) "target-globals.h", "ipa-ref.h", "cgraph.h", "symbol-summary.h", "ipa-prop.h", "ipa-fnsummary.h", "dwarf2out.h", "omp-general.h", "omp-offload.h", "ipa-modref-tree.h", "ipa-modref.h", "symtab-thunks.h", - "symtab-clones.h", + "symtab-clones.h", "diagnostic-spec.h", NULL }; const char *const *ifp; diff --git a/gcc/gimple-array-bounds.cc b/gcc/gimple-array-bounds.cc index 199d9f5d216..41615002594 100644 --- a/gcc/gimple-array-bounds.cc +++ b/gcc/gimple-array-bounds.cc @@ -175,7 +175,7 @@ bool array_bounds_checker::check_array_ref (location_t location, tree ref, bool ignore_off_by_one) { - if (TREE_NO_WARNING (ref)) + if (get_no_warning (ref, OPT_Warray_bounds)) /* Return true to have the caller prevent warnings for enclosing refs. */ return true; @@ -346,7 +346,7 @@ array_bounds_checker::check_array_ref (location_t location, tree ref, /* Avoid more warnings when checking more significant subscripts of the same expression. */ ref = TREE_OPERAND (ref, 0); - TREE_NO_WARNING (ref) = 1; + set_no_warning (ref, OPT_Warray_bounds); if (decl) ref = decl; @@ -411,7 +411,7 @@ bool array_bounds_checker::check_mem_ref (location_t location, tree ref, bool ignore_off_by_one) { - if (TREE_NO_WARNING (ref)) + if (get_no_warning (ref, OPT_Warray_bounds)) return false; tree arg = TREE_OPERAND (ref, 0); @@ -770,7 +770,7 @@ array_bounds_checker::check_mem_ref (location_t location, tree ref, } } - TREE_NO_WARNING (ref) = 1; + set_no_warning (ref, OPT_Warray_bounds); return true; } @@ -787,7 +787,7 @@ array_bounds_checker::check_mem_ref (location_t location, tree ref, "intermediate array offset %wi is outside array bounds " "of %qT", tmpidx, reftype)) { - TREE_NO_WARNING (ref) = 1; + set_no_warning (ref, OPT_Warray_bounds); return true; } } @@ -818,7 +818,7 @@ array_bounds_checker::check_addr_expr (location_t location, tree t) warned = check_mem_ref (location, t, ignore_off_by_one); if (warned) - TREE_NO_WARNING (t) = true; + set_no_warning (t, OPT_Warray_bounds); t = TREE_OPERAND (t, 0); } @@ -826,7 +826,7 @@ array_bounds_checker::check_addr_expr (location_t location, tree t) if (TREE_CODE (t) != MEM_REF || TREE_CODE (TREE_OPERAND (t, 0)) != ADDR_EXPR - || TREE_NO_WARNING (t)) + || get_no_warning (t, OPT_Warray_bounds)) return; tree tem = TREE_OPERAND (TREE_OPERAND (t, 0), 0); @@ -886,7 +886,7 @@ array_bounds_checker::check_addr_expr (location_t location, tree t) if (DECL_P (t)) inform (DECL_SOURCE_LOCATION (t), "while referencing %qD", t); - TREE_NO_WARNING (t) = 1; + set_no_warning (t, OPT_Warray_bounds); } } @@ -980,9 +980,10 @@ array_bounds_checker::check_array_bounds (tree *tp, int *walk_subtree, See pr98266 and pr97595. */ *walk_subtree = false; - /* Propagate the no-warning bit to the outer expression. */ + /* Propagate the no-warning bit to the outer statement to avoid also + issuing -Wstringop-overflow/-overread for the out-of-bounds accesses. */ if (warned) - TREE_NO_WARNING (t) = true; + set_no_warning (wi->stmt, OPT_Warray_bounds); return NULL_TREE; } diff --git a/gcc/gimple-expr.c b/gcc/gimple-expr.c index b8c732b632a..80fba56ead4 100644 --- a/gcc/gimple-expr.c +++ b/gcc/gimple-expr.c @@ -377,7 +377,6 @@ copy_var_decl (tree var, tree name, tree type) DECL_ARTIFICIAL (copy) = DECL_ARTIFICIAL (var); DECL_IGNORED_P (copy) = DECL_IGNORED_P (var); DECL_CONTEXT (copy) = DECL_CONTEXT (var); - TREE_NO_WARNING (copy) = TREE_NO_WARNING (var); TREE_USED (copy) = 1; DECL_SEEN_IN_BIND_EXPR_P (copy) = 1; DECL_ATTRIBUTES (copy) = DECL_ATTRIBUTES (var); @@ -387,6 +386,7 @@ copy_var_decl (tree var, tree name, tree type) DECL_USER_ALIGN (copy) = 1; } + copy_no_warning (copy, var); return copy; } diff --git a/gcc/gimple-fold.c b/gcc/gimple-fold.c index 68717cf1542..29dd361370a 100644 --- a/gcc/gimple-fold.c +++ b/gcc/gimple-fold.c @@ -2039,7 +2039,7 @@ gimple_fold_builtin_strcpy (gimple_stmt_iterator *gsi, not point to objects and so do not indicate an overlap; such calls could be the result of sanitization and jump threading). */ - if (!integer_zerop (dest) && !gimple_no_warning_p (stmt)) + if (!integer_zerop (dest) && !get_no_warning (stmt, OPT_Wrestrict)) { tree func = gimple_call_fndecl (stmt); @@ -2066,9 +2066,9 @@ gimple_fold_builtin_strcpy (gimple_stmt_iterator *gsi, if (nonstr) { /* Avoid folding calls with unterminated arrays. */ - if (!gimple_no_warning_p (stmt)) + if (!get_no_warning (stmt, OPT_Wstringop_overread)) warn_string_no_nul (loc, NULL_TREE, "strcpy", src, nonstr); - gimple_set_no_warning (stmt, true); + set_no_warning (stmt, OPT_Wstringop_overread); return false; } @@ -2476,7 +2476,7 @@ gimple_fold_builtin_strncat (gimple_stmt_iterator *gsi) unsigned HOST_WIDE_INT dstsize; - bool nowarn = gimple_no_warning_p (stmt); + bool nowarn = get_no_warning (stmt, OPT_Wstringop_overflow_); if (!nowarn && compute_builtin_object_size (dst, 1, &dstsize)) { @@ -2499,7 +2499,7 @@ gimple_fold_builtin_strncat (gimple_stmt_iterator *gsi) "destination size %wu"), stmt, fndecl, len, dstsize); if (nowarn) - gimple_set_no_warning (stmt, true); + set_no_warning (stmt, OPT_Wstringop_overflow_); } } @@ -2515,7 +2515,7 @@ gimple_fold_builtin_strncat (gimple_stmt_iterator *gsi) if (warning_at (loc, OPT_Wstringop_overflow_, "%G%qD specified bound %E equals source length", stmt, fndecl, len)) - gimple_set_no_warning (stmt, true); + set_no_warning (stmt, OPT_Wstringop_overflow_); } tree fn = builtin_decl_implicit (BUILT_IN_STRCAT); @@ -3100,7 +3100,8 @@ gimple_fold_builtin_stxcpy_chk (gimple_stmt_iterator *gsi, not point to objects and so do not indicate an overlap; such calls could be the result of sanitization and jump threading). */ - if (!integer_zerop (dest) && !gimple_no_warning_p (stmt)) + if (!integer_zerop (dest) + && !get_no_warning (stmt, OPT_Wrestrict)) { tree func = gimple_call_fndecl (stmt); @@ -3283,10 +3284,10 @@ gimple_fold_builtin_stpcpy (gimple_stmt_iterator *gsi) if (data.decl) { /* Avoid folding calls with unterminated arrays. */ - if (!gimple_no_warning_p (stmt)) + if (!get_no_warning (stmt, OPT_Wstringop_overread)) warn_string_no_nul (loc, NULL_TREE, "stpcpy", src, data.decl, size, exact); - gimple_set_no_warning (stmt, true); + set_no_warning (stmt, OPT_Wstringop_overread); return false; } @@ -3550,8 +3551,7 @@ gimple_fold_builtin_sprintf (gimple_stmt_iterator *gsi) /* Propagate the NO_WARNING bit to avoid issuing the same warning more than once. */ - if (gimple_no_warning_p (stmt)) - gimple_set_no_warning (repl, true); + copy_no_warning (repl, stmt); gimple_seq_add_stmt_without_update (&stmts, repl); if (tree lhs = gimple_call_lhs (stmt)) @@ -3603,8 +3603,7 @@ gimple_fold_builtin_sprintf (gimple_stmt_iterator *gsi) /* Propagate the NO_WARNING bit to avoid issuing the same warning more than once. */ - if (gimple_no_warning_p (stmt)) - gimple_set_no_warning (repl, true); + copy_no_warning (repl, stmt); gimple_seq_add_stmt_without_update (&stmts, repl); if (tree lhs = gimple_call_lhs (stmt)) @@ -6062,7 +6061,7 @@ fold_stmt_1 (gimple_stmt_iterator *gsi, bool inplace, tree (*valueize) (tree)) { bool changed = false; gimple *stmt = gsi_stmt (*gsi); - bool nowarning = gimple_no_warning_p (stmt); + bool nowarning = get_no_warning (stmt, OPT_Wstrict_overflow); unsigned i; fold_defer_overflow_warnings (); diff --git a/gcc/gimple-ssa-isolate-paths.c b/gcc/gimple-ssa-isolate-paths.c index eb23cd41f4b..2dafe849ad3 100644 --- a/gcc/gimple-ssa-isolate-paths.c +++ b/gcc/gimple-ssa-isolate-paths.c @@ -400,6 +400,11 @@ diag_returned_locals (bool maybe, const locmap_t &locmap) gimple *stmt = (*it).first; const args_loc_t &argsloc = (*it).second; location_t stmtloc = gimple_location (stmt); + if (stmtloc == UNKNOWN_LOCATION) + /* When multiple return statements are merged into one it + may not have an associated location. Use the location + of the closing brace instead. */ + stmtloc = cfun->function_end_locus; auto_diagnostic_group d; unsigned nargs = argsloc.locvec.length (); diff --git a/gcc/gimple-ssa-nonnull-compare.c b/gcc/gimple-ssa-nonnull-compare.c index 9d7894633dc..517e791204f 100644 --- a/gcc/gimple-ssa-nonnull-compare.c +++ b/gcc/gimple-ssa-nonnull-compare.c @@ -97,7 +97,7 @@ do_warn_nonnull_compare (function *fun, tree arg) if (op && (POINTER_TYPE_P (TREE_TYPE (arg)) ? integer_zerop (op) : integer_minus_onep (op)) - && !gimple_no_warning_p (stmt)) + && !get_no_warning (stmt, OPT_Wnonnull_compare)) warning_at (loc, OPT_Wnonnull_compare, "% argument %qD compared to NULL", arg); } diff --git a/gcc/gimple-ssa-sprintf.c b/gcc/gimple-ssa-sprintf.c index fc744669e4b..ed69a73c183 100644 --- a/gcc/gimple-ssa-sprintf.c +++ b/gcc/gimple-ssa-sprintf.c @@ -4680,7 +4680,7 @@ handle_printf_call (gimple_stmt_iterator *gsi, pointer_query &ptr_qry) bool success = compute_format_length (info, &res, ptr_qry.rvals); if (res.warned) - gimple_set_no_warning (info.callstmt, true); + set_no_warning (info.callstmt, info.warnopt ()); /* When optimizing and the printf return value optimization is enabled, attempt to substitute the computed result for the return value of diff --git a/gcc/gimple-ssa-store-merging.c b/gcc/gimple-ssa-store-merging.c index 123c92d9b44..51128f4482b 100644 --- a/gcc/gimple-ssa-store-merging.c +++ b/gcc/gimple-ssa-store-merging.c @@ -4348,10 +4348,12 @@ imm_store_chain_info::output_merged_store (merged_store_group *group) MR_DEPENDENCE_BASE (ops[j]) = base; } if (!integer_zerop (mask)) - /* The load might load some bits (that will be masked off - later on) uninitialized, avoid -W*uninitialized - warnings in that case. */ - TREE_NO_WARNING (ops[j]) = 1; + { + /* The load might load some bits (that will be masked + off later on) uninitialized, avoid -W*uninitialized + warnings in that case. */ + set_no_warning (ops[j], OPT_Wuninitialized); + } stmt = gimple_build_assign (make_ssa_name (dest_type), ops[j]); gimple_set_location (stmt, load_loc); @@ -4533,7 +4535,7 @@ imm_store_chain_info::output_merged_store (merged_store_group *group) provably uninitialized (no stores at all yet or previous store a CLOBBER) we'd optimize away the load and replace it e.g. with 0. */ - TREE_NO_WARNING (load_src) = 1; + set_no_warning (load_src, OPT_Wuninitialized); stmt = gimple_build_assign (tem, load_src); gimple_set_location (stmt, loc); gimple_set_vuse (stmt, new_vuse); diff --git a/gcc/gimple-ssa-warn-restrict.c b/gcc/gimple-ssa-warn-restrict.c index ad37f20afaa..c4a773a45ff 100644 --- a/gcc/gimple-ssa-warn-restrict.c +++ b/gcc/gimple-ssa-warn-restrict.c @@ -1425,7 +1425,7 @@ maybe_diag_overlap (location_t loc, gimple *call, builtin_access &acs) if (!acs.overlap ()) return false; - if (gimple_no_warning_p (call)) + if (get_no_warning (call, OPT_Wrestrict)) return true; /* For convenience. */ @@ -1677,7 +1677,7 @@ maybe_diag_overlap (location_t loc, gimple *call, builtin_access &acs) validated. Return true if the offsets are not valid and a diagnostic has been issued, or would have been issued if DO_WARN had been true. */ -static bool +static int maybe_diag_access_bounds (gimple *call, tree func, int strict, const builtin_memref &ref, offset_int wroff, bool do_warn) @@ -1689,28 +1689,31 @@ maybe_diag_access_bounds (gimple *call, tree func, int strict, since the result is used to make codegen decisions. */ if (ref.sizrange[0] > maxobjsize) { + const int opt = OPT_Wstringop_overflow_; /* Return true without issuing a warning. */ if (!do_warn) - return true; + return opt; - if (ref.ref && TREE_NO_WARNING (ref.ref)) - return false; + if (ref.ref && get_no_warning (ref.ref, OPT_Wstringop_overflow_)) + return 0; + bool warned = false; if (warn_stringop_overflow) { if (ref.sizrange[0] == ref.sizrange[1]) - return warning_at (loc, OPT_Wstringop_overflow_, - "%G%qD specified bound %wu " - "exceeds maximum object size %wu", - call, func, ref.sizrange[0].to_uhwi (), - maxobjsize.to_uhwi ()); - - return warning_at (loc, OPT_Wstringop_overflow_, - "%G%qD specified bound between %wu and %wu " - "exceeds maximum object size %wu", - call, func, ref.sizrange[0].to_uhwi (), - ref.sizrange[1].to_uhwi (), - maxobjsize.to_uhwi ()); + warned = warning_at (loc, opt, + "%G%qD specified bound %wu " + "exceeds maximum object size %wu", + call, func, ref.sizrange[0].to_uhwi (), + maxobjsize.to_uhwi ()); + else + warned = warning_at (loc, opt, + "%G%qD specified bound between %wu and %wu " + "exceeds maximum object size %wu", + call, func, ref.sizrange[0].to_uhwi (), + ref.sizrange[1].to_uhwi (), + maxobjsize.to_uhwi ()); + return warned ? opt : 0; } } @@ -1732,8 +1735,8 @@ maybe_diag_access_bounds (gimple *call, tree func, int strict, if (!warn_array_bounds) return false; - if (TREE_NO_WARNING (ref.ptr) - || (ref.ref && TREE_NO_WARNING (ref.ref))) + if (get_no_warning (ref.ptr, OPT_Warray_bounds ) + || (ref.ref && get_no_warning (ref.ref, OPT_Warray_bounds))) return false; char rangestr[2][64]; @@ -1877,7 +1880,7 @@ maybe_diag_access_bounds (gimple *call, tree func, int strict, } } - return warned; + return warned ? OPT_Warray_bounds : 0; } /* Check a CALL statement for restrict-violations and issue warnings @@ -1888,7 +1891,7 @@ check_call (range_query *query, gimple *call) { /* Avoid checking the call if it has already been diagnosed for some reason. */ - if (gimple_no_warning_p (call)) + if (get_no_warning (call, OPT_Wrestrict)) return; tree func = gimple_call_fndecl (call); @@ -1974,11 +1977,12 @@ check_call (range_query *query, gimple *call) || (dstwr && !INTEGRAL_TYPE_P (TREE_TYPE (dstwr)))) return; - if (!check_bounds_or_overlap (query, call, dst, src, dstwr, NULL_TREE)) + int opt = check_bounds_or_overlap (query, call, dst, src, dstwr, NULL_TREE); + if (!opt) return; /* Avoid diagnosing the call again. */ - gimple_set_no_warning (call, true); + set_no_warning (call, OPT_Wrestrict); } } /* anonymous namespace */ @@ -2026,12 +2030,16 @@ check_bounds_or_overlap (range_query *query, /* Validate offsets to each reference before the access first to make sure they are within the bounds of the destination object if its size is known, or PTRDIFF_MAX otherwise. */ - if (maybe_diag_access_bounds (call, func, strict, dstref, wroff, do_warn) - || maybe_diag_access_bounds (call, func, strict, srcref, 0, do_warn)) + int opt + = maybe_diag_access_bounds (call, func, strict, dstref, wroff, do_warn); + if (!opt) + opt = maybe_diag_access_bounds (call, func, strict, srcref, 0, do_warn); + + if (opt) { if (do_warn) - gimple_set_no_warning (call, true); - return OPT_Warray_bounds; + set_no_warning (call, OPT_Wrestrict); + return opt; } if (!warn_restrict || bounds_only || !src) @@ -2058,12 +2066,12 @@ check_bounds_or_overlap (range_query *query, not point to objects and so do not indicate an overlap; such calls could be the result of sanitization and jump threading). */ - if (!integer_zerop (dst) && !gimple_no_warning_p (call)) + if (!integer_zerop (dst) && !get_no_warning (call, OPT_Wrestrict)) { warning_at (loc, OPT_Wrestrict, "%G%qD source argument is the same as destination", call, func); - gimple_set_no_warning (call, true); + set_no_warning (call, OPT_Wrestrict); return OPT_Wrestrict; } @@ -2073,7 +2081,7 @@ check_bounds_or_overlap (range_query *query, /* Return false when overlap has been detected. */ if (maybe_diag_overlap (loc, call, acs)) { - gimple_set_no_warning (call, true); + set_no_warning (call, OPT_Wrestrict); return OPT_Wrestrict; } diff --git a/gcc/gimple.c b/gcc/gimple.c index f1044e9c630..0ff1e9ab304 100644 --- a/gcc/gimple.c +++ b/gcc/gimple.c @@ -399,7 +399,7 @@ gimple_build_call_from_tree (tree t, tree fnptrtype) gimple_call_set_va_arg_pack (call, CALL_EXPR_VA_ARG_PACK (t)); gimple_call_set_nothrow (call, TREE_NOTHROW (t)); gimple_call_set_by_descriptor (call, CALL_EXPR_BY_DESCRIPTOR (t)); - gimple_set_no_warning (call, TREE_NO_WARNING (t)); + copy_no_warning (call, t); if (fnptrtype) { diff --git a/gcc/gimple.h b/gcc/gimple.h index 91b92b4a4d1..f95ce872cb5 100644 --- a/gcc/gimple.h +++ b/gcc/gimple.h @@ -1634,6 +1634,21 @@ extern bool gimple_inexpensive_call_p (gcall *); extern bool stmt_can_terminate_bb_p (gimple *); extern location_t gimple_or_expr_nonartificial_location (gimple *, tree); +/* Return true if a warning is enabled for the statement. */ +extern bool get_no_warning (const gimple *, int = -1) + ATTRIBUTE_NONNULL (1); +/* Enable, or by default disable, a warning for the statement. */ +extern void set_no_warning (gimple *, int = -1, bool = true) + ATTRIBUTE_NONNULL (1); +/* Copy the warning disposition mapping from one statement to another. */ +extern void copy_no_warning (gimple *, const gimple *) + ATTRIBUTE_NONNULL (1) ATTRIBUTE_NONNULL (2); +/* Copy the warning disposition mapping from an expression to a statement. */ +extern void copy_no_warning (gimple *, const_tree) + ATTRIBUTE_NONNULL (1) ATTRIBUTE_NONNULL (2); +/* Copy the warning disposition mapping from a statement to an expression. */ +extern void copy_no_warning (tree, const gimple *) + ATTRIBUTE_NONNULL (1) ATTRIBUTE_NONNULL (2); /* Formal (expression) temporary table handling: multiple occurrences of the same scalar expression are evaluated into the same temporary. */ @@ -1854,16 +1869,17 @@ gimple_block (const gimple *g) return LOCATION_BLOCK (g->location); } +/* Forward declare. */ +static inline void gimple_set_location (gimple *, location_t); /* Set BLOCK to be the lexical scope block holding statement G. */ static inline void gimple_set_block (gimple *g, tree block) { - g->location = set_block (g->location, block); + gimple_set_location (g, set_block (g->location, block)); } - /* Return location information for statement G. */ static inline location_t @@ -1886,6 +1902,8 @@ gimple_location_safe (const gimple *g) static inline void gimple_set_location (gimple *g, location_t location) { + /* Copy the no-warning data to the statement location. */ + copy_no_warning (location, g->location); g->location = location; } @@ -1948,22 +1966,6 @@ gimple_seq_singleton_p (gimple_seq seq) && (gimple_seq_first (seq) == gimple_seq_last (seq))); } -/* Return true if no warnings should be emitted for statement STMT. */ - -static inline bool -gimple_no_warning_p (const gimple *stmt) -{ - return stmt->no_warning; -} - -/* Set the no_warning flag of STMT to NO_WARNING. */ - -static inline void -gimple_set_no_warning (gimple *stmt, bool no_warning) -{ - stmt->no_warning = (unsigned) no_warning; -} - /* Set the visited status on statement STMT to VISITED_P. Please note that this 'visited' property of the gimple statement is diff --git a/gcc/gimplify.c b/gcc/gimplify.c index 719a4e16391..20445b89e27 100644 --- a/gcc/gimplify.c +++ b/gcc/gimplify.c @@ -1596,7 +1596,7 @@ gimplify_return_expr (tree stmt, gimple_seq *pre_p) { maybe_add_early_return_predict_stmt (pre_p); greturn *ret = gimple_build_return (ret_expr); - gimple_set_no_warning (ret, TREE_NO_WARNING (stmt)); + copy_no_warning (ret, stmt); gimplify_seq_add_stmt (pre_p, ret); return GS_ALL_DONE; } @@ -1658,7 +1658,7 @@ gimplify_return_expr (tree stmt, gimple_seq *pre_p) we can wind up warning about an uninitialized value for this. Due to how this variable is constructed and initialized, this is never true. Give up and never warn. */ - TREE_NO_WARNING (result) = 1; + set_no_warning (result, OPT_Wuninitialized); gimplify_ctxp->return_temp = result; } @@ -1672,7 +1672,7 @@ gimplify_return_expr (tree stmt, gimple_seq *pre_p) maybe_add_early_return_predict_stmt (pre_p); ret = gimple_build_return (result); - gimple_set_no_warning (ret, TREE_NO_WARNING (stmt)); + copy_no_warning (ret, stmt); gimplify_seq_add_stmt (pre_p, ret); return GS_ALL_DONE; @@ -4244,7 +4244,8 @@ gimplify_cond_expr (tree *expr_p, gimple_seq *pre_p, fallback_t fallback) &arm2); cond_stmt = gimple_build_cond (pred_code, arm1, arm2, label_true, label_false); - gimple_set_no_warning (cond_stmt, TREE_NO_WARNING (COND_EXPR_COND (expr))); + gimple_set_location (cond_stmt, EXPR_LOCATION (expr)); + copy_no_warning (cond_stmt, COND_EXPR_COND (expr)); gimplify_seq_add_stmt (&seq, cond_stmt); gimple_stmt_iterator gsi = gsi_last (seq); maybe_fold_stmt (&gsi); @@ -5694,7 +5695,7 @@ gimplify_modify_expr_complex_part (tree *expr_p, gimple_seq *pre_p, ocode = code == REALPART_EXPR ? IMAGPART_EXPR : REALPART_EXPR; other = build1 (ocode, TREE_TYPE (rhs), lhs); - TREE_NO_WARNING (other) = 1; + set_no_warning (other); other = get_formal_tmp_var (other, pre_p); realpart = code == REALPART_EXPR ? rhs : other; @@ -5979,7 +5980,7 @@ gimplify_modify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p, assign = gimple_build_assign (*to_p, *from_p); gimple_set_location (assign, EXPR_LOCATION (*expr_p)); if (COMPARISON_CLASS_P (*from_p)) - gimple_set_no_warning (assign, TREE_NO_WARNING (*from_p)); + copy_no_warning (assign, *from_p); } if (gimplify_ctxp->into_ssa && is_gimple_reg (*to_p)) @@ -6738,7 +6739,7 @@ gimple_push_cleanup (tree var, tree cleanup, bool eh_only, gimple_seq *pre_p, /* Because of this manipulation, and the EH edges that jump threading cannot redirect, the temporary (VAR) will appear to be used uninitialized. Don't warn. */ - TREE_NO_WARNING (var) = 1; + set_no_warning (var, OPT_Wuninitialized); } } else @@ -14470,7 +14471,7 @@ gimplify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p, gimplify_and_add (EH_FILTER_FAILURE (*expr_p), &failure); ehf = gimple_build_eh_filter (EH_FILTER_TYPES (*expr_p), failure); - gimple_set_no_warning (ehf, TREE_NO_WARNING (*expr_p)); + copy_no_warning (ehf, *expr_p); gimplify_seq_add_stmt (pre_p, ehf); ret = GS_ALL_DONE; break; diff --git a/gcc/omp-expand.c b/gcc/omp-expand.c index 0f843bad79a..dbccbfdeefa 100644 --- a/gcc/omp-expand.c +++ b/gcc/omp-expand.c @@ -3845,7 +3845,7 @@ expand_omp_for_generic (struct omp_region *region, for (i = first_zero_iter1; i < (fd->ordered ? fd->ordered : fd->collapse); i++) if (SSA_VAR_P (counts[i])) - TREE_NO_WARNING (counts[i]) = 1; + set_no_warning (counts[i], OPT_Wuninitialized); gsi_prev (&gsi); e = split_block (entry_bb, gsi_stmt (gsi)); entry_bb = e->dest; @@ -3862,7 +3862,7 @@ expand_omp_for_generic (struct omp_region *region, be executed in that case, so just avoid uninit warnings. */ for (i = first_zero_iter2; i < fd->ordered; i++) if (SSA_VAR_P (counts[i])) - TREE_NO_WARNING (counts[i]) = 1; + set_no_warning (counts[i], OPT_Wuninitialized); if (zero_iter1_bb) make_edge (zero_iter2_bb, entry_bb, EDGE_FALLTHRU); else @@ -7051,7 +7051,7 @@ expand_omp_taskloop_for_outer (struct omp_region *region, be executed in that case, so just avoid uninit warnings. */ for (i = first_zero_iter; i < fd->collapse; i++) if (SSA_VAR_P (counts[i])) - TREE_NO_WARNING (counts[i]) = 1; + set_no_warning (counts[i], OPT_Wuninitialized); gsi_prev (&gsi); edge e = split_block (entry_bb, gsi_stmt (gsi)); entry_bb = e->dest; diff --git a/gcc/omp-low.c b/gcc/omp-low.c index d1136d181b3..cb20fdf7609 100644 --- a/gcc/omp-low.c +++ b/gcc/omp-low.c @@ -5614,7 +5614,7 @@ lower_rec_input_clauses (tree clauses, gimple_seq *ilist, gimple_seq *dlist, able to notice this and not store anything at all, but we're generating code too early. Suppress the warning. */ if (!by_ref) - TREE_NO_WARNING (var) = 1; + set_no_warning (var, OPT_Wuninitialized); break; case OMP_CLAUSE__CONDTEMP_: @@ -6575,7 +6575,7 @@ lower_rec_input_clauses (tree clauses, gimple_seq *ilist, gimple_seq *dlist, uid = create_tmp_var (ptr_type_node, "simduid"); /* Don't want uninit warnings on simduid, it is always uninitialized, but we use it not for the value, but for the DECL_UID only. */ - TREE_NO_WARNING (uid) = 1; + set_no_warning (uid, OPT_Wuninitialized); c = build_omp_clause (UNKNOWN_LOCATION, OMP_CLAUSE__SIMDUID_); OMP_CLAUSE__SIMDUID__DECL (c) = uid; OMP_CLAUSE_CHAIN (c) = gimple_omp_for_clauses (ctx->stmt); @@ -7003,7 +7003,7 @@ lower_lastprivate_clauses (tree clauses, tree predicate, gimple_seq *body_p, if (predicate && (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LASTPRIVATE || OMP_CLAUSE_LINEAR_NO_COPYIN (c))) - TREE_NO_WARNING (new_var) = 1; + set_no_warning (new_var, OPT_Wuninitialized); } if (!maybe_simt && simduid && DECL_HAS_VALUE_EXPR_P (new_var)) @@ -7834,7 +7834,7 @@ lower_send_clauses (tree clauses, gimple_seq *ilist, gimple_seq *olist, if (OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (c) && !by_ref && is_task_ctx (ctx)) - TREE_NO_WARNING (var) = 1; + set_no_warning (var); do_in = true; break; @@ -12388,7 +12388,7 @@ lower_omp_target (gimple_stmt_iterator *gsi_p, omp_context *ctx) { if (is_gimple_reg (var) && OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (c)) - TREE_NO_WARNING (var) = 1; + set_no_warning (var); var = build_fold_addr_expr (var); } else @@ -12412,7 +12412,7 @@ lower_omp_target (gimple_stmt_iterator *gsi_p, omp_context *ctx) we'll get a warning for the store to avar. Don't warn in that case, the mapping might be implicit. */ - TREE_NO_WARNING (var) = 1; + set_no_warning (var, OPT_Wuninitialized); gimplify_assign (avar, var, &ilist); } avar = build_fold_addr_expr (avar); @@ -12566,7 +12566,7 @@ lower_omp_target (gimple_stmt_iterator *gsi_p, omp_context *ctx) if (omp_is_reference (var)) t = build_simple_mem_ref (var); else if (OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (c)) - TREE_NO_WARNING (var) = 1; + set_no_warning (var); if (TREE_CODE (type) != POINTER_TYPE) t = fold_convert (pointer_sized_int_node, t); t = fold_convert (TREE_TYPE (x), t); @@ -12579,7 +12579,7 @@ lower_omp_target (gimple_stmt_iterator *gsi_p, omp_context *ctx) tree avar = create_tmp_var (TREE_TYPE (var)); mark_addressable (avar); if (OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (c)) - TREE_NO_WARNING (var) = 1; + set_no_warning (var); gimplify_assign (avar, var, &ilist); avar = build_fold_addr_expr (avar); gimplify_assign (x, avar, &ilist); diff --git a/gcc/tree-cfg.c b/gcc/tree-cfg.c index 02256580c98..c85e9146508 100644 --- a/gcc/tree-cfg.c +++ b/gcc/tree-cfg.c @@ -9428,7 +9428,7 @@ pass_warn_function_return::execute (function *fun) /* If we see "return;" in some basic block, then we do reach the end without returning a value. */ else if (warn_return_type > 0 - && !TREE_NO_WARNING (fun->decl) + && !get_no_warning (fun->decl, OPT_Wreturn_type) && !VOID_TYPE_P (TREE_TYPE (TREE_TYPE (fun->decl)))) { FOR_EACH_EDGE (e, ei, EXIT_BLOCK_PTR_FOR_FN (fun)->preds) @@ -9437,14 +9437,14 @@ pass_warn_function_return::execute (function *fun) greturn *return_stmt = dyn_cast (last); if (return_stmt && gimple_return_retval (return_stmt) == NULL - && !gimple_no_warning_p (last)) + && !get_no_warning (last, OPT_Wreturn_type)) { location = gimple_location (last); if (LOCATION_LOCUS (location) == UNKNOWN_LOCATION) location = fun->function_end_locus; if (warning_at (location, OPT_Wreturn_type, "control reaches end of non-void function")) - TREE_NO_WARNING (fun->decl) = 1; + set_no_warning (fun->decl, OPT_Wreturn_type); break; } } @@ -9452,7 +9452,7 @@ pass_warn_function_return::execute (function *fun) into __builtin_unreachable () call with BUILTINS_LOCATION. Recognize those too. */ basic_block bb; - if (!TREE_NO_WARNING (fun->decl)) + if (!get_no_warning (fun->decl, OPT_Wreturn_type)) FOR_EACH_BB_FN (bb, fun) if (EDGE_COUNT (bb->succs) == 0) { @@ -9476,7 +9476,7 @@ pass_warn_function_return::execute (function *fun) location = fun->function_end_locus; if (warning_at (location, OPT_Wreturn_type, "control reaches end of non-void function")) - TREE_NO_WARNING (fun->decl) = 1; + set_no_warning (fun->decl, OPT_Wreturn_type); break; } } diff --git a/gcc/tree-complex.c b/gcc/tree-complex.c index d7d991714de..c5d57346023 100644 --- a/gcc/tree-complex.c +++ b/gcc/tree-complex.c @@ -456,12 +456,12 @@ create_one_component_var (tree type, tree orig, const char *prefix, SET_DECL_DEBUG_EXPR (r, build1 (code, type, orig)); DECL_HAS_DEBUG_EXPR_P (r) = 1; DECL_IGNORED_P (r) = 0; - TREE_NO_WARNING (r) = TREE_NO_WARNING (orig); + copy_no_warning (r, orig); } else { DECL_IGNORED_P (r) = 1; - TREE_NO_WARNING (r) = 1; + set_no_warning (r); } return r; diff --git a/gcc/tree-inline.c b/gcc/tree-inline.c index 8f945b88c12..2fea85c34bf 100644 --- a/gcc/tree-inline.c +++ b/gcc/tree-inline.c @@ -1116,7 +1116,7 @@ remap_gimple_op_r (tree *tp, int *walk_subtrees, void *data) *tp = fold_build2 (MEM_REF, type, ptr, TREE_OPERAND (*tp, 1)); TREE_THIS_VOLATILE (*tp) = TREE_THIS_VOLATILE (old); TREE_SIDE_EFFECTS (*tp) = TREE_SIDE_EFFECTS (old); - TREE_NO_WARNING (*tp) = TREE_NO_WARNING (old); + copy_no_warning (*tp, old); if (MR_DEPENDENCE_CLIQUE (old) != 0) { MR_DEPENDENCE_CLIQUE (*tp) @@ -1375,7 +1375,7 @@ copy_tree_body_r (tree *tp, int *walk_subtrees, void *data) *tp = fold_build2 (MEM_REF, type, ptr, TREE_OPERAND (*tp, 1)); TREE_THIS_VOLATILE (*tp) = TREE_THIS_VOLATILE (old); TREE_SIDE_EFFECTS (*tp) = TREE_SIDE_EFFECTS (old); - TREE_NO_WARNING (*tp) = TREE_NO_WARNING (old); + copy_no_warning (*tp, old); if (MR_DEPENDENCE_CLIQUE (old) != 0) { MR_DEPENDENCE_CLIQUE (*tp) @@ -3753,7 +3753,7 @@ declare_return_variable (copy_body_data *id, tree return_slot, tree modify_dest, /* Do not have the rest of GCC warn about this variable as it should not be visible to the user. */ - TREE_NO_WARNING (var) = 1; + set_no_warning (var /* OPT_Wuninitialized? */); declare_inline_vars (id->block, var); @@ -5018,7 +5018,7 @@ expand_call_inline (basic_block bb, gimple *stmt, copy_body_data *id, initialized. We do not want to issue a warning about that uninitialized variable. */ if (DECL_P (modify_dest)) - TREE_NO_WARNING (modify_dest) = 1; + set_no_warning (modify_dest, OPT_Wuninitialized); if (gimple_call_return_slot_opt_p (call_stmt)) { diff --git a/gcc/tree-nested.c b/gcc/tree-nested.c index cea917a4d58..5d9e59134d2 100644 --- a/gcc/tree-nested.c +++ b/gcc/tree-nested.c @@ -411,8 +411,8 @@ lookup_field_for_decl (struct nesting_info *info, tree decl, DECL_USER_ALIGN (field) = DECL_USER_ALIGN (decl); DECL_IGNORED_P (field) = DECL_IGNORED_P (decl); DECL_NONADDRESSABLE_P (field) = !TREE_ADDRESSABLE (decl); - TREE_NO_WARNING (field) = TREE_NO_WARNING (decl); TREE_THIS_VOLATILE (field) = TREE_THIS_VOLATILE (decl); + copy_no_warning (field, decl); /* Declare the transformation and adjust the original DECL. For a variable or for a parameter when not optimizing, we make it point diff --git a/gcc/tree-sra.c b/gcc/tree-sra.c index 8dfc923ed7e..2e3efc31666 100644 --- a/gcc/tree-sra.c +++ b/gcc/tree-sra.c @@ -2240,12 +2240,12 @@ create_access_replacement (struct access *access, tree reg_type = NULL_TREE) DECL_HAS_DEBUG_EXPR_P (repl) = 1; } if (access->grp_no_warning) - TREE_NO_WARNING (repl) = 1; + set_no_warning (repl /* Be more selective! */); else - TREE_NO_WARNING (repl) = TREE_NO_WARNING (access->base); + copy_no_warning (repl, access->base); } else - TREE_NO_WARNING (repl) = 1; + set_no_warning (repl /* Be more selective! */); if (dump_file) { @@ -3556,7 +3556,7 @@ generate_subtree_copies (struct access *access, tree agg, } else { - TREE_NO_WARNING (repl) = 1; + set_no_warning (repl /* Be more selective! */); if (access->grp_partial_lhs) repl = force_gimple_operand_gsi (gsi, repl, true, NULL_TREE, !insert_after, diff --git a/gcc/tree-ssa-ccp.c b/gcc/tree-ssa-ccp.c index 3834212b867..f0303492f8e 100644 --- a/gcc/tree-ssa-ccp.c +++ b/gcc/tree-ssa-ccp.c @@ -3527,7 +3527,7 @@ pass_post_ipa_warn::execute (function *fun) for (gsi = gsi_start_bb (bb); !gsi_end_p (gsi); gsi_next (&gsi)) { gimple *stmt = gsi_stmt (gsi); - if (!is_gimple_call (stmt) || gimple_no_warning_p (stmt)) + if (!is_gimple_call (stmt) || get_no_warning (stmt, OPT_Wnonnull)) continue; tree fntype = gimple_call_fntype (stmt); diff --git a/gcc/tree-ssa-forwprop.c b/gcc/tree-ssa-forwprop.c index 0706fd862de..fa72ff007a2 100644 --- a/gcc/tree-ssa-forwprop.c +++ b/gcc/tree-ssa-forwprop.c @@ -403,7 +403,8 @@ combine_cond_expr_cond (gimple *stmt, enum tree_code code, tree type, return NULL_TREE; } - fold_undefer_overflow_warnings (!gimple_no_warning_p (stmt), stmt, 0); + bool nowarn = get_no_warning (stmt, OPT_Wstrict_overflow); + fold_undefer_overflow_warnings (!nowarn, stmt, 0); return t; } diff --git a/gcc/tree-ssa-loop-ch.c b/gcc/tree-ssa-loop-ch.c index 08caa83b4b4..9051820c8a7 100644 --- a/gcc/tree-ssa-loop-ch.c +++ b/gcc/tree-ssa-loop-ch.c @@ -458,7 +458,7 @@ ch_base::copy_headers (function *fun) && gimple_cond_code (stmt) != NE_EXPR && INTEGRAL_TYPE_P (TREE_TYPE (lhs)) && TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (lhs))) - gimple_set_no_warning (stmt, true); + set_no_warning (stmt, OPT_Wstrict_overflow_); } else if (is_gimple_assign (stmt)) { @@ -469,7 +469,7 @@ ch_base::copy_headers (function *fun) && rhs_code != NE_EXPR && INTEGRAL_TYPE_P (TREE_TYPE (rhs1)) && TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (rhs1))) - gimple_set_no_warning (stmt, true); + set_no_warning (stmt, OPT_Wstrict_overflow_); } } } diff --git a/gcc/tree-ssa-loop-im.c b/gcc/tree-ssa-loop-im.c index 8034cf68d27..64c63c6ee8b 100644 --- a/gcc/tree-ssa-loop-im.c +++ b/gcc/tree-ssa-loop-im.c @@ -2143,7 +2143,7 @@ execute_sm (class loop *loop, im_mem_ref *ref, /* If not emitting a load mark the uninitialized state on the loop entry as not to be warned for. */ tree uninit = create_tmp_reg (TREE_TYPE (aux->tmp_var)); - TREE_NO_WARNING (uninit) = 1; + set_no_warning (uninit, OPT_Wuninitialized); load = gimple_build_assign (aux->tmp_var, uninit); } lim_data = init_lim_data (load); diff --git a/gcc/tree-ssa-phiopt.c b/gcc/tree-ssa-phiopt.c index 8e8a08bc679..58b764991ff 100644 --- a/gcc/tree-ssa-phiopt.c +++ b/gcc/tree-ssa-phiopt.c @@ -3014,9 +3014,12 @@ cond_store_replacement (basic_block middle_bb, basic_block join_bb, new_stmt = gimple_build_assign (name, lhs); gimple_set_location (new_stmt, locus); lhs = unshare_expr (lhs); - /* Set TREE_NO_WARNING on the rhs of the load to avoid uninit - warnings. */ - TREE_NO_WARNING (gimple_assign_rhs1 (new_stmt)) = 1; + { + /* Set the no-warning bit on the rhs of the load to avoid uninit + warnings. */ + tree rhs1 = gimple_assign_rhs1 (new_stmt); + set_no_warning (rhs1, OPT_Wuninitialized); + } gsi_insert_on_edge (e1, new_stmt); /* 3) Create a PHI node at the join block, with one argument diff --git a/gcc/tree-ssa-strlen.c b/gcc/tree-ssa-strlen.c index c7b5e2c6e6b..88728a2c7f2 100644 --- a/gcc/tree-ssa-strlen.c +++ b/gcc/tree-ssa-strlen.c @@ -1918,7 +1918,7 @@ maybe_warn_overflow (gimple *stmt, tree len, pointer_query &ptr_qry, strinfo *si = NULL, bool plus_one = false, bool rawmem = false) { - if (!len || gimple_no_warning_p (stmt)) + if (!len || get_no_warning (stmt, OPT_Wstringop_overflow_)) return; /* The DECL of the function performing the write if it is done @@ -1937,7 +1937,7 @@ maybe_warn_overflow (gimple *stmt, tree len, pointer_query &ptr_qry, else return; - if (TREE_NO_WARNING (dest)) + if (get_no_warning (dest, OPT_Wstringop_overflow_)) return; const int ostype = rawmem ? 0 : 1; @@ -2081,7 +2081,7 @@ maybe_warn_overflow (gimple *stmt, tree len, pointer_query &ptr_qry, if (!warned) return; - gimple_set_no_warning (stmt, true); + set_no_warning (stmt, OPT_Wstringop_overflow_); aref.inform_access (access_write_only); } @@ -2605,15 +2605,15 @@ handle_builtin_strcpy (enum built_in_function bcode, gimple_stmt_iterator *gsi, len = fold_build2_loc (loc, PLUS_EXPR, type, len, build_int_cst (type, 1)); /* Set the no-warning bit on the transformed statement? */ - bool set_no_warning = false; + int no_warning_opt = 0; - if (const strinfo *chksi = olddsi ? olddsi : dsi) - if (si - && check_bounds_or_overlap (stmt, chksi->ptr, si->ptr, NULL_TREE, len)) - { - gimple_set_no_warning (stmt, true); - set_no_warning = true; - } + if (const strinfo *chksi = si ? olddsi ? olddsi : dsi : NULL) + { + no_warning_opt = check_bounds_or_overlap (stmt, chksi->ptr, si->ptr, + NULL_TREE, len); + if (no_warning_opt) + set_no_warning (stmt, no_warning_opt); + } if (fn == NULL_TREE) return; @@ -2647,8 +2647,8 @@ handle_builtin_strcpy (enum built_in_function bcode, gimple_stmt_iterator *gsi, else if (dump_file && (dump_flags & TDF_DETAILS) != 0) fprintf (dump_file, "not possible.\n"); - if (set_no_warning) - gimple_set_no_warning (stmt, true); + if (no_warning_opt) + set_no_warning (stmt, no_warning_opt); } /* Check the size argument to the built-in forms of stpncpy and strncpy @@ -2776,7 +2776,7 @@ maybe_diag_stxncpy_trunc (gimple_stmt_iterator gsi, tree src, tree cnt, pointer_query *ptr_qry /* = NULL */) { gimple *stmt = gsi_stmt (gsi); - if (gimple_no_warning_p (stmt)) + if (get_no_warning (stmt, OPT_Wstringop_truncation)) return false; wide_int cntrange[2]; @@ -3135,9 +3135,9 @@ handle_builtin_stxncpy_strncat (bool append_p, gimple_stmt_iterator *gsi) else srclenp1 = NULL_TREE; - if (check_bounds_or_overlap (stmt, dst, src, dstlenp1, srclenp1)) + if (int opt = check_bounds_or_overlap (stmt, dst, src, dstlenp1, srclenp1)) { - gimple_set_no_warning (stmt, true); + set_no_warning (stmt, opt); return; } @@ -3148,7 +3148,7 @@ handle_builtin_stxncpy_strncat (bool append_p, gimple_stmt_iterator *gsi) if (!pss || pss->first <= 0) { if (maybe_diag_stxncpy_trunc (*gsi, src, len)) - gimple_set_no_warning (stmt, true); + set_no_warning (stmt, OPT_Wstringop_truncation); return; } @@ -3428,7 +3428,7 @@ handle_builtin_strcat (enum built_in_function bcode, gimple_stmt_iterator *gsi, } /* Set the no-warning bit on the transformed statement? */ - bool set_no_warning = false; + int no_warning_opt = 0; if (dsi == NULL || get_string_length (dsi) == NULL_TREE) { @@ -3445,12 +3445,10 @@ handle_builtin_strcat (enum built_in_function bcode, gimple_stmt_iterator *gsi, } tree sptr = si && si->ptr ? si->ptr : src; - - if (check_bounds_or_overlap (stmt, dst, sptr, NULL_TREE, slen)) - { - gimple_set_no_warning (stmt, true); - set_no_warning = true; - } + no_warning_opt = check_bounds_or_overlap (stmt, dst, sptr, NULL_TREE, + slen); + if (no_warning_opt) + set_no_warning (stmt, no_warning_opt); } /* strcat (p, q) can be transformed into @@ -3557,11 +3555,10 @@ handle_builtin_strcat (enum built_in_function bcode, gimple_stmt_iterator *gsi, tree dstsize = fold_build2 (PLUS_EXPR, type, dstlen, one); tree sptr = si && si->ptr ? si->ptr : src; - if (check_bounds_or_overlap (stmt, dst, sptr, dstsize, srcsize)) - { - gimple_set_no_warning (stmt, true); - set_no_warning = true; - } + no_warning_opt = check_bounds_or_overlap (stmt, dst, sptr, dstsize, + srcsize); + if (no_warning_opt) + set_no_warning (stmt, no_warning_opt); } tree len = NULL_TREE; @@ -3627,8 +3624,8 @@ handle_builtin_strcat (enum built_in_function bcode, gimple_stmt_iterator *gsi, else if (dump_file && (dump_flags & TDF_DETAILS) != 0) fprintf (dump_file, "not possible.\n"); - if (set_no_warning) - gimple_set_no_warning (stmt, true); + if (no_warning_opt) + set_no_warning (stmt, no_warning_opt); } /* Handle a call to an allocation function like alloca, malloc or calloc, diff --git a/gcc/tree-ssa-uninit.c b/gcc/tree-ssa-uninit.c index f55ce1939ac..e1d50ab92a7 100644 --- a/gcc/tree-ssa-uninit.c +++ b/gcc/tree-ssa-uninit.c @@ -86,17 +86,33 @@ has_undefined_value_p (tree t) && possibly_undefined_names->contains (t))); } -/* Like has_undefined_value_p, but don't return true if TREE_NO_WARNING - is set on SSA_NAME_VAR. */ +/* Return true if EXPR should suppress either uninitialized warning. */ + +static inline bool +get_no_uninit_warning (tree expr) +{ + return get_no_warning (expr, OPT_Wuninitialized); +} + +/* Suppress both uninitialized warnings for EXPR. */ + +static inline void +set_no_uninit_warning (tree expr) +{ + set_no_warning (expr, OPT_Wuninitialized); +} + +/* Like has_undefined_value_p, but don't return true if the no-warning + bit is set on SSA_NAME_VAR for either uninit warning. */ static inline bool uninit_undefined_value_p (tree t) { if (!has_undefined_value_p (t)) return false; - if (SSA_NAME_VAR (t) && TREE_NO_WARNING (SSA_NAME_VAR (t))) - return false; - return true; + if (!SSA_NAME_VAR (t)) + return true; + return !get_no_uninit_warning (SSA_NAME_VAR (t)); } /* Emit warnings for uninitialized variables. This is done in two passes. @@ -164,10 +180,10 @@ warn_uninit (enum opt_code wc, tree t, tree expr, tree var, /* TREE_NO_WARNING either means we already warned, or the front end wishes to suppress the warning. */ if ((context - && (gimple_no_warning_p (context) + && (get_no_warning (context, OPT_Wuninitialized) || (gimple_assign_single_p (context) - && TREE_NO_WARNING (gimple_assign_rhs1 (context))))) - || TREE_NO_WARNING (expr)) + && get_no_uninit_warning (gimple_assign_rhs1 (context))))) + || get_no_uninit_warning (expr)) return; if (context != NULL && gimple_has_location (context)) @@ -184,7 +200,7 @@ warn_uninit (enum opt_code wc, tree t, tree expr, tree var, auto_diagnostic_group d; if (warning_at (location, wc, gmsgid, expr)) { - TREE_NO_WARNING (expr) = 1; + set_no_warning (expr, wc); if (location == DECL_SOURCE_LOCATION (var)) return; @@ -259,7 +275,7 @@ maybe_warn_operand (ao_ref &ref, gimple *stmt, tree lhs, tree rhs, use_operand_p luse_p; imm_use_iterator liter; - if (TREE_NO_WARNING (rhs)) + if (get_no_uninit_warning (rhs)) return NULL_TREE; /* Do not warn if the base was marked so or this is a @@ -267,7 +283,7 @@ maybe_warn_operand (ao_ref &ref, gimple *stmt, tree lhs, tree rhs, tree base = ao_ref_base (&ref); if ((VAR_P (base) && DECL_HARD_REGISTER (base)) - || TREE_NO_WARNING (base)) + || get_no_uninit_warning (base)) return NULL_TREE; /* Do not warn if the access is fully outside of the variable. */ @@ -406,7 +422,7 @@ maybe_warn_operand (ao_ref &ref, gimple *stmt, tree lhs, tree rhs, rhs = TREE_OPERAND (rhs, 0); /* Check again since RHS may have changed above. */ - if (TREE_NO_WARNING (rhs)) + if (get_no_uninit_warning (rhs)) return NULL_TREE; /* Avoid warning about empty types such as structs with no members. @@ -434,7 +450,7 @@ maybe_warn_operand (ao_ref &ref, gimple *stmt, tree lhs, tree rhs, uses or accesses by functions as it may hide important locations. */ if (lhs) - TREE_NO_WARNING (rhs) = 1; + set_no_uninit_warning (rhs); warned = true; } } diff --git a/gcc/tree-vrp.c b/gcc/tree-vrp.c index 12e6e6f3e22..d9aede22d6e 100644 --- a/gcc/tree-vrp.c +++ b/gcc/tree-vrp.c @@ -406,10 +406,10 @@ compare_values_warnv (tree val1, tree val2, bool *strict_overflow_p) return -2; if (strict_overflow_p != NULL - /* Symbolic range building sets TREE_NO_WARNING to declare + /* Symbolic range building sets the no-warning bit to declare that overflow doesn't happen. */ - && (!inv1 || !TREE_NO_WARNING (val1)) - && (!inv2 || !TREE_NO_WARNING (val2))) + && (!inv1 || !get_no_warning (val1, OPT_Woverflow)) + && (!inv2 || !get_no_warning (val2, OPT_Woverflow))) *strict_overflow_p = true; if (!inv1) @@ -432,10 +432,10 @@ compare_values_warnv (tree val1, tree val2, bool *strict_overflow_p) return -2; if (strict_overflow_p != NULL - /* Symbolic range building sets TREE_NO_WARNING to declare + /* Symbolic range building sets the no-warning bit to declare that overflow doesn't happen. */ - && (!sym1 || !TREE_NO_WARNING (val1)) - && (!sym2 || !TREE_NO_WARNING (val2))) + && (!sym1 || !get_no_warning (val1, OPT_Woverflow)) + && (!sym2 || !get_no_warning (val2, OPT_Woverflow))) *strict_overflow_p = true; const signop sgn = TYPE_SIGN (TREE_TYPE (val1)); diff --git a/gcc/tree.h b/gcc/tree.h index 64612cfa368..37593d0a3d8 100644 --- a/gcc/tree.h +++ b/gcc/tree.h @@ -699,13 +699,6 @@ extern void omp_clause_range_check_failed (const_tree, const char *, int, /* Determines whether an ENUMERAL_TYPE has defined the list of constants. */ #define ENUM_IS_OPAQUE(NODE) (ENUMERAL_TYPE_CHECK (NODE)->base.private_flag) -/* In an expr node (usually a conversion) this means the node was made - implicitly and should not lead to any sort of warning. In a decl node, - warnings concerning the decl should be suppressed. This is used at - least for used-before-set warnings, and it set after one warning is - emitted. */ -#define TREE_NO_WARNING(NODE) ((NODE)->base.nowarning_flag) - /* Nonzero if we should warn about the change in empty class parameter passing ABI in this TU. */ #define TRANSLATION_UNIT_WARN_EMPTY_P(NODE) \ @@ -6430,4 +6423,22 @@ public: operator location_t () const { return m_combined_loc; } }; +/* Return true if a warning is enabled for the decl/expression. */ +extern bool get_no_warning (const_tree, int = -1) ATTRIBUTE_NONNULL (1); +/* Enable, or by default disable, a warning for the expression. */ +extern void set_no_warning (tree, int = -1, bool = true) + ATTRIBUTE_NONNULL (1); +/* Copy the warning disposition mapping from one expression to another. */ +extern void copy_no_warning (tree, const_tree) + ATTRIBUTE_NONNULL (1) ATTRIBUTE_NONNULL (2); + +/* Return the disposition for a warning (or all warnings by default) + at a location. */ +extern bool get_no_warning (location_t, int = -1); +/* Set the disposition for a warning (or all warnings by default) + at a location to disabled by default. */ +extern bool set_no_warning (location_t, int = -1, bool = true); +/* Copy warning disposition from one location to another. */ +extern void copy_no_warning (location_t, location_t); + #endif /* GCC_TREE_H */ diff --git a/gcc/vr-values.c b/gcc/vr-values.c index 02bc0db9088..67c0e35033a 100644 --- a/gcc/vr-values.c +++ b/gcc/vr-values.c @@ -697,7 +697,7 @@ vr_values::extract_range_for_var_from_comparison_expr (tree var, build_int_cst (TREE_TYPE (max), 1)); /* Signal to compare_values_warnv this expr doesn't overflow. */ if (EXPR_P (max)) - TREE_NO_WARNING (max) = 1; + set_no_warning (max, OPT_Woverflow); } vr_p->update (min, max); @@ -737,7 +737,7 @@ vr_values::extract_range_for_var_from_comparison_expr (tree var, build_int_cst (TREE_TYPE (min), 1)); /* Signal to compare_values_warnv this expr doesn't overflow. */ if (EXPR_P (min)) - TREE_NO_WARNING (min) = 1; + set_no_warning (min, OPT_Woverflow); } vr_p->update (min, max); @@ -3353,7 +3353,7 @@ test_for_singularity (enum tree_code cond_code, tree op0, max = fold_build2 (MINUS_EXPR, TREE_TYPE (op0), max, one); /* Signal to compare_values_warnv this expr doesn't overflow. */ if (EXPR_P (max)) - TREE_NO_WARNING (max) = 1; + set_no_warning (max, OPT_Woverflow); } } else if (cond_code == GE_EXPR || cond_code == GT_EXPR) @@ -3367,7 +3367,7 @@ test_for_singularity (enum tree_code cond_code, tree op0, min = fold_build2 (PLUS_EXPR, TREE_TYPE (op0), min, one); /* Signal to compare_values_warnv this expr doesn't overflow. */ if (EXPR_P (min)) - TREE_NO_WARNING (min) = 1; + set_no_warning (min, OPT_Woverflow); } }