From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 32274 invoked by alias); 31 Mar 2016 20:54:28 -0000 Mailing-List: contact gcc-patches-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Id: List-Archive: List-Post: List-Help: Sender: gcc-patches-owner@gcc.gnu.org Received: (qmail 31976 invoked by uid 89); 31 Mar 2016 20:54:27 -0000 Authentication-Results: sourceware.org; auth=none X-Virus-Found: No X-Spam-SWARE-Status: No, score=-2.6 required=5.0 tests=AWL,BAYES_00,RCVD_IN_DNSWL_LOW autolearn=ham version=3.3.2 spammy=threading X-HELO: mail-qg0-f66.google.com Received: from mail-qg0-f66.google.com (HELO mail-qg0-f66.google.com) (209.85.192.66) by sourceware.org (qpsmtpd/0.93/v0.84-503-g423c35a) with (AES128-GCM-SHA256 encrypted) ESMTPS; Thu, 31 Mar 2016 20:54:13 +0000 Received: by mail-qg0-f66.google.com with SMTP id y89so9105563qge.0 for ; Thu, 31 Mar 2016 13:54:12 -0700 (PDT) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20130820; h=x-gm-message-state:from:to:cc:subject:date:message-id; bh=sNuLqFJX1Sc5rFbL7co7bxeypvNDrYX4uCXE/lCtjMg=; b=hCwbJZtlVpoD+IfmFYkoIf+xUiG5ZWCEe5XOdwuqRv5zZQSXBYB5cgQk+A//sws2ep gJfDMIdskAIbNPQMYG68reCBq3MaHKSQSUNlcMv8oJVRyPlvK/MfS2PeymOf5fpGvMm0 KCQlJnsC/N+JS+pQMuy/fj9yN0lCWB6pk2uA5KlEgw7zyVE2V8c5jjWuGdUO2B602usU 4te2fgCVb9siU2Wq2lWcg/N7BbqdcuJK6NvWZKYZXS7xbXbFEKE2M3oC41nKAWBcpmIf vLDXa5vnX6ImS0+XVrRHu3X8llZnTgaePaqH3WlxkfDYZ5OuAoTURNCl8IjwFkPndoQm TRgQ== X-Gm-Message-State: AD7BkJIHo4KXMTT//ZTcBvpmy9OCNvCFN8gjdy5vHZGGkqzn8YiWXF8g1/voFNIzfC9nlA== X-Received: by 10.140.17.54 with SMTP id 51mr9071872qgc.30.1459457650647; Thu, 31 Mar 2016 13:54:10 -0700 (PDT) Received: from localhost.localdomain (ool-4353abbc.dyn.optonline.net. [67.83.171.188]) by smtp.gmail.com with ESMTPSA id v74sm4683311qkl.36.2016.03.31.13.54.09 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Thu, 31 Mar 2016 13:54:10 -0700 (PDT) From: Patrick Palka To: gcc-patches@gcc.gnu.org Cc: jason@redhat.com, Patrick Palka Subject: [PATCH 2/2] Fix C++ side of PR c/70436 (missing -Wparentheses warnings) Date: Thu, 31 Mar 2016 21:10:00 -0000 Message-Id: <1459457644-20663-1-git-send-email-patrick@parcs.ath.cx> X-SW-Source: 2016-03/txt/msg01719.txt.bz2 -Wparentheses currently warns about an ambiguous "else" in this code if (a) if (b) bar (); else baz (); but it fails to warn if there is an iteration statement between the inner and outer ifs: if (a) for (;;) if (b) bar (); else baz (); To fix this it's sufficient to just thread the IF_P parameter in cp_parser_statement() through to cp_parser_iteration_statement() and then to cp_parser_already_scoped_statement() and finally back to cp_parser_statement(). In cp_parser_iteration_statement(), avoid passing IF_P through a do-while statement, and in cp_parser_already_scoped_statement() avoid passing IF_P through a compound statement. I think that covers all the vanilla C++ constructs that this warning has to consider. As for C++ extensions, we still fail to warn for if (a) #pragma GCC ivdep while (1) if (b) bar (); else baz (); and if (a) _Cilk_for (int i = 0; i < 10; i++) if (b) bar (); else baz (); and probably other constructs. I suppose support for this can be implemented in a subsequent patch if deemed appropriate at this stage. It would probably just involve more threading of the parameter IF_P. Is this OK to commit after bootstrap + regtesting? gcc/cp/ChangeLog: PR c/70436 * parser.c (cp_parser_iteration_statement): New parameter IF_P. Pass it through to cp_parser_already_scoped_statement. (cp_parser_already_scoped_statement): New parameter IF_P. Pass it through to cp_parser_statement. (cp_parser_statement): Pass IF_P through to cp_parser_iteration_statement. (cp_parser_pragma): Adjust call to cp_parser_iteration_statement. gcc/testsuite/ChangeLog: PR c/70436 * g++.dg/warn/Wparentheses-29.C: New test. --- gcc/cp/parser.c | 20 +++--- gcc/testsuite/g++.dg/warn/Wparentheses-29.C | 97 +++++++++++++++++++++++++++++ 2 files changed, 107 insertions(+), 10 deletions(-) create mode 100644 gcc/testsuite/g++.dg/warn/Wparentheses-29.C diff --git a/gcc/cp/parser.c b/gcc/cp/parser.c index 2f80856..af2a8f2 100644 --- a/gcc/cp/parser.c +++ b/gcc/cp/parser.c @@ -2104,7 +2104,7 @@ static tree cp_parser_selection_statement static tree cp_parser_condition (cp_parser *); static tree cp_parser_iteration_statement - (cp_parser *, bool); + (cp_parser *, bool *if_p, bool); static bool cp_parser_for_init_statement (cp_parser *, tree *decl); static tree cp_parser_for @@ -2127,7 +2127,7 @@ static void cp_parser_declaration_statement static tree cp_parser_implicitly_scoped_statement (cp_parser *, bool *, const token_indent_info &, vec * = NULL); static void cp_parser_already_scoped_statement - (cp_parser *, const token_indent_info &); + (cp_parser *, bool *if_p, const token_indent_info &); /* Declarations [gram.dcl.dcl] */ @@ -10392,7 +10392,7 @@ cp_parser_statement (cp_parser* parser, tree in_statement_expr, case RID_WHILE: case RID_DO: case RID_FOR: - statement = cp_parser_iteration_statement (parser, false); + statement = cp_parser_iteration_statement (parser, if_p, false); break; case RID_CILK_FOR: @@ -10947,7 +10947,7 @@ cp_parser_selection_statement (cp_parser* parser, bool *if_p, else { /* This if statement does not have an else clause. If - NESTED_IF is true, then the then-clause is an if + NESTED_IF is true, then the then-clause has an if statement which does have an else clause. We warn about the potential ambiguity. */ if (nested_if) @@ -11544,7 +11544,7 @@ cp_parser_range_for_member_function (tree range, tree identifier) Returns the new WHILE_STMT, DO_STMT, FOR_STMT or RANGE_FOR_STMT. */ static tree -cp_parser_iteration_statement (cp_parser* parser, bool ivdep) +cp_parser_iteration_statement (cp_parser* parser, bool *if_p, bool ivdep) { cp_token *token; enum rid keyword; @@ -11582,7 +11582,7 @@ cp_parser_iteration_statement (cp_parser* parser, bool ivdep) cp_parser_require (parser, CPP_CLOSE_PAREN, RT_CLOSE_PAREN); /* Parse the dependent statement. */ parser->in_statement = IN_ITERATION_STMT; - cp_parser_already_scoped_statement (parser, guard_tinfo); + cp_parser_already_scoped_statement (parser, if_p, guard_tinfo); parser->in_statement = in_statement; /* We're done with the while-statement. */ finish_while_stmt (statement); @@ -11627,7 +11627,7 @@ cp_parser_iteration_statement (cp_parser* parser, bool ivdep) /* Parse the body of the for-statement. */ parser->in_statement = IN_ITERATION_STMT; - cp_parser_already_scoped_statement (parser, guard_tinfo); + cp_parser_already_scoped_statement (parser, if_p, guard_tinfo); parser->in_statement = in_statement; /* We're done with the for-statement. */ @@ -11937,7 +11937,7 @@ cp_parser_implicitly_scoped_statement (cp_parser* parser, bool *if_p, scope. */ static void -cp_parser_already_scoped_statement (cp_parser* parser, +cp_parser_already_scoped_statement (cp_parser* parser, bool *if_p, const token_indent_info &guard_tinfo) { /* If the token is a `{', then we must take special action. */ @@ -11946,7 +11946,7 @@ cp_parser_already_scoped_statement (cp_parser* parser, token_indent_info body_tinfo = get_token_indent_info (cp_lexer_peek_token (parser->lexer)); - cp_parser_statement (parser, NULL_TREE, false, NULL); + cp_parser_statement (parser, NULL_TREE, false, if_p); token_indent_info next_tinfo = get_token_indent_info (cp_lexer_peek_token (parser->lexer)); warn_for_misleading_indentation (guard_tinfo, body_tinfo, next_tinfo); @@ -37312,7 +37312,7 @@ cp_parser_pragma (cp_parser *parser, enum pragma_context context) cp_parser_error (parser, "for, while or do statement expected"); return false; } - cp_parser_iteration_statement (parser, true); + cp_parser_iteration_statement (parser, NULL, true); return true; } diff --git a/gcc/testsuite/g++.dg/warn/Wparentheses-29.C b/gcc/testsuite/g++.dg/warn/Wparentheses-29.C new file mode 100644 index 0000000..125e6b4 --- /dev/null +++ b/gcc/testsuite/g++.dg/warn/Wparentheses-29.C @@ -0,0 +1,97 @@ +/* PR c/70436 */ +/* { dg-options "-Wparentheses" } */ + +int a, b; +void bar (void); +void baz (void); + +void +foo (void) +{ + if (a) /* { dg-warning "ambiguous" } */ + for (;;) + if (b) + bar (); + else + baz (); + + if (a) /* { dg-warning "ambiguous" } */ + while (1) + if (b) + bar (); + else + baz (); + + if (a) /* { dg-warning "ambiguous" } */ + while (1) + for (;;) + if (b) + bar (); + else + baz (); + + if (a) /* { dg-warning "ambiguous" } */ + for (;;) + if (b) + while (1) + if (a) + bar (); + else + baz (); + else + bar (); + + if (a) /* { dg-warning "ambiguous" } */ + for (;;) + if (b) + while (1) + { + if (a) { bar (); } else { baz (); } + } + else + bar (); + + if (a) + for (;;) + if (b) + bar (); + else + baz (); + else bar (); + + if (a) + while (1) + if (b) + bar (); + else + baz (); + else bar (); + + if (a) + for (;;) + { + if (b) + bar (); + else + baz (); + } + + if (a) + { + for (;;) + if (b) + bar (); + } + else baz (); + + if (a) + do + if (b) bar (); else baz (); + while (b); + + if (a) + do + if (b) bar (); + while (b); + else baz (); +} -- 2.8.0.rc3.27.gade0865