PR c++/82728 - wrong -Wunused-but-set-variable
authorJason Merrill <jason@redhat.com>
Thu, 11 Jan 2018 19:08:41 +0000 (14:08 -0500)
committerJason Merrill <jason@gcc.gnu.org>
Thu, 11 Jan 2018 19:08:41 +0000 (14:08 -0500)
PR c++/82799
PR c++/83690
* call.c (perform_implicit_conversion_flags): Call mark_rvalue_use.
* decl.c (case_conversion): Likewise.
* semantics.c (finish_static_assert): Call
perform_implicit_conversion_flags.

From-SVN: r256550

gcc/cp/ChangeLog
gcc/cp/call.c
gcc/cp/decl.c
gcc/cp/semantics.c
gcc/testsuite/g++.dg/cpp0x/lambda/lambda-switch2.C [new file with mode: 0644]
gcc/testsuite/g++.dg/warn/Wunused-var-27.C [new file with mode: 0644]
gcc/testsuite/g++.dg/warn/Wunused-var-28.C [new file with mode: 0644]
gcc/testsuite/g++.dg/warn/Wunused-var-29.C [new file with mode: 0644]

index 8731982779f6cdd3db4cd75803a5470cd66bf4f7..840cbd4f3e1205d8af50473ab9d3ab2c90e2c57e 100644 (file)
@@ -1,3 +1,13 @@
+2018-01-11  Jason Merrill  <jason@redhat.com>
+
+       PR c++/82728 - wrong -Wunused-but-set-variable
+       PR c++/82799
+       PR c++/83690
+       * call.c (perform_implicit_conversion_flags): Call mark_rvalue_use.
+       * decl.c (case_conversion): Likewise.
+       * semantics.c (finish_static_assert): Call
+       perform_implicit_conversion_flags.
+
 2018-01-11  Nathan Sidwell  <nathan@acm.org>
 
        * method.c (enum mangling_flags): Delete long-dead enum.
index c822a70a017668b3aedff2dfa50eba3962bfa02b..5f2c6becb350591e373b58a5a248ea4ccc9dde9a 100644 (file)
@@ -10514,6 +10514,11 @@ perform_implicit_conversion_flags (tree type, tree expr,
   void *p;
   location_t loc = EXPR_LOC_OR_LOC (expr, input_location);
 
+  if (TREE_CODE (type) == REFERENCE_TYPE)
+    expr = mark_lvalue_use (expr);
+  else
+    expr = mark_rvalue_use (expr);
+
   if (error_operand_p (expr))
     return error_mark_node;
 
index 6ba657801d9a9f752aa687cd43d93f7a530a1001..ee469d35137001733be648262c96a93590b1767b 100644 (file)
@@ -3541,6 +3541,8 @@ case_conversion (tree type, tree value)
   if (value == NULL_TREE)
     return value;
 
+  value = mark_rvalue_use (value);
+
   if (cxx_dialect >= cxx11
       && (SCOPED_ENUM_P (type)
          || !INTEGRAL_OR_UNSCOPED_ENUMERATION_TYPE_P (TREE_TYPE (value))))
index 60608c797f25f019d8e9becc426d5e004e9be3eb..f9c5285f724e72e5c7083a9a7b5bbdcc29071629 100644 (file)
@@ -8608,6 +8608,8 @@ void
 finish_static_assert (tree condition, tree message, location_t location, 
                       bool member_p)
 {
+  tsubst_flags_t complain = tf_warning_or_error;
+
   if (message == NULL_TREE
       || message == error_mark_node
       || condition == NULL_TREE
@@ -8640,9 +8642,9 @@ finish_static_assert (tree condition, tree message, location_t location,
     }
 
   /* Fold the expression and convert it to a boolean value. */
-  condition = instantiate_non_dependent_expr (condition);
-  condition = cp_convert (boolean_type_node, condition, tf_warning_or_error);
-  condition = maybe_constant_value (condition);
+  condition = perform_implicit_conversion_flags (boolean_type_node, condition,
+                                                complain, LOOKUP_NORMAL);
+  condition = fold_non_dependent_expr (condition);
 
   if (TREE_CODE (condition) == INTEGER_CST && !integer_zerop (condition))
     /* Do nothing; the condition is satisfied. */
diff --git a/gcc/testsuite/g++.dg/cpp0x/lambda/lambda-switch2.C b/gcc/testsuite/g++.dg/cpp0x/lambda/lambda-switch2.C
new file mode 100644 (file)
index 0000000..677f305
--- /dev/null
@@ -0,0 +1,18 @@
+// PR c++/82728
+// { dg-do compile { target c++11 } }
+
+void
+foo ()
+{
+  const int i = 1;
+
+  [=]()
+    {
+      switch (0)
+       {
+       case i:
+         break;
+       }
+      static_assert (i, "i");
+    };
+}
diff --git a/gcc/testsuite/g++.dg/warn/Wunused-var-27.C b/gcc/testsuite/g++.dg/warn/Wunused-var-27.C
new file mode 100644 (file)
index 0000000..0ef7153
--- /dev/null
@@ -0,0 +1,14 @@
+// PR c++/82728
+// { dg-do compile }
+// { dg-options "-Wunused-but-set-variable" }
+
+void
+foo ()
+{
+  const int i = 1;             // { dg-bogus "set but not used" }
+  switch (0)
+    {
+    case i:
+      break;
+    }
+}
diff --git a/gcc/testsuite/g++.dg/warn/Wunused-var-28.C b/gcc/testsuite/g++.dg/warn/Wunused-var-28.C
new file mode 100644 (file)
index 0000000..6960167
--- /dev/null
@@ -0,0 +1,15 @@
+// PR c++/82799
+// { dg-do compile }
+// { dg-options "-Wunused-but-set-variable" }
+
+enum E { b };     
+struct C {
+  template <E>
+  int foo ()
+  {
+    const bool i = 0;          // { dg-bogus "set but not used" }
+    const int r = i ? 7 : 9;
+    return r;
+  }
+  void bar () { foo <b> (); }
+};
diff --git a/gcc/testsuite/g++.dg/warn/Wunused-var-29.C b/gcc/testsuite/g++.dg/warn/Wunused-var-29.C
new file mode 100644 (file)
index 0000000..24eeb95
--- /dev/null
@@ -0,0 +1,10 @@
+// PR c++/83690
+// { dg-do compile { target c++11 } }
+// { dg-options "-Wunused-but-set-variable" }
+
+void
+foo ()
+{
+  constexpr bool foo = true;           // { dg-bogus "set but not used" }
+  static_assert (foo, "foo");
+}