@@ -8034,6 +8034,7 @@ cp_parser_binary_expression (cp_parser* parser, bool cast_p,
for (;;)
{
+ bool not_expr_save;
/* Get an operator token. */
token = cp_lexer_peek_token (parser->lexer);
@@ -8071,6 +8072,7 @@ cp_parser_binary_expression (cp_parser* parser, bool cast_p,
/* We used the operator token. */
cp_lexer_consume_token (parser->lexer);
+ not_expr_save = cp_lexer_next_token_is (parser->lexer, CPP_NOT);
/* For "false && x" or "true || x", x will never be executed;
disable warnings while evaluating it. */
@@ -8101,6 +8103,7 @@ cp_parser_binary_expression (cp_parser* parser, bool cast_p,
current.lhs_type = rhs_type;
current.prec = new_prec;
new_prec = lookahead_prec;
+ parenthesized_not_lhs_warn = not_expr_save;
goto get_rhs;
pop:
@@ -8126,8 +8129,17 @@ cp_parser_binary_expression (cp_parser* parser, bool cast_p,
if (warn_logical_not_paren
&& parenthesized_not_lhs_warn)
- warn_logical_not_parentheses (current.loc, current.tree_type,
- TREE_OPERAND (current.lhs, 0), rhs);
+ {
+ tree lhs;
+ /* If the LHS was !CST, we have true/false now. Convert it
+ to integer type, otherwise we wouldn't warn. */
+ if (TREE_CODE (current.lhs) == INTEGER_CST)
+ lhs = convert (integer_type_node, current.lhs);
+ else
+ lhs = TREE_OPERAND (current.lhs, 0);
+ warn_logical_not_parentheses (current.loc, current.tree_type,
+ lhs, rhs);
+ }
overload = NULL;
/* ??? Currently we pass lhs_type == ERROR_MARK and rhs_type ==
@@ -0,0 +1,22 @@
+/* PR c++/62199 */
+/* { dg-do compile } */
+/* { dg-options "-Wlogical-not-parentheses" } */
+
+int r;
+void
+foo (int a)
+{
+ r = a > 0 || !a >= 2; /* { dg-warning "19:logical not is only applied to the left hand side of comparison" } */
+ r = !a || a == 10;
+ r = !a && !a < 4; /* { dg-warning "16:logical not is only applied to the left hand side of comparison" } */
+ r = !a > 0 && a < 6; /* { dg-warning "10:logical not is only applied to the left hand side of comparison" } */
+ r = a + (!a < 12); /* { dg-warning "15:logical not is only applied to the left hand side of comparison" } */
+ r = a == 7 || !a < 12; /* { dg-warning "20:logical not is only applied to the left hand side of comparison" } */
+ r = (a == 7 * a > 0) || !a < 2; /* { dg-warning "30:logical not is only applied to the left hand side of comparison" } */
+ r = (1 > !a) || (!42 > a); /* { dg-warning "24:logical not is only applied to the left hand side of comparison" } */
+ r = (!5 > a); /* { dg-warning "11:logical not is only applied to the left hand side of comparison" } */
+ r = (!0 > a); /* { dg-warning "11:logical not is only applied to the left hand side of comparison" } */
+ r = (!-5 > a); /* { dg-warning "12:logical not is only applied to the left hand side of comparison" } */
+ r = (!(5 + 3) > a); /* { dg-warning "17:logical not is only applied to the left hand side of comparison" } */
+ r = (!(5 - a) > a); /* { dg-warning "17:logical not is only applied to the left hand side of comparison" } */
+}