Check non-dependent conversion in return from template fn.
authorJason Merrill <jason@redhat.com>
Tue, 10 Oct 2017 18:03:22 +0000 (14:03 -0400)
committerJason Merrill <jason@gcc.gnu.org>
Tue, 10 Oct 2017 18:03:22 +0000 (14:03 -0400)
* typeck.c (check_return_expr): Check non-dependent conversion in
templates.
* constraint.cc (check_function_concept): Don't complain about an
empty concept if seen_error.

From-SVN: r253599

gcc/cp/ChangeLog
gcc/cp/constraint.cc
gcc/cp/typeck.c
gcc/testsuite/g++.dg/concepts/req6.C
gcc/testsuite/g++.old-deja/g++.pt/crash3.C

index 0d69bda285d0ec826024a888a10c005076378c61..fe0315c88e0dc6fc88c10a9d8af38bc76b9d6adc 100644 (file)
@@ -1,3 +1,10 @@
+2017-10-10  Jason Merrill  <jason@redhat.com>
+
+       * typeck.c (check_return_expr): Check non-dependent conversion in
+       templates.
+       * constraint.cc (check_function_concept): Don't complain about an
+       empty concept if seen_error.
+
 2017-10-10  Richard Sandiford  <richard.sandiford@linaro.org>
 
        * cvt.c (ignore_overflows): Use wi::to_wide when
index 64a8ea926d2a170642c5f90cbee85b51207b6731..8b49455a526349bc01b511a6b9d2dd2770754565 100644 (file)
@@ -2504,7 +2504,12 @@ check_function_concept (tree fn)
     {
       location_t loc = DECL_SOURCE_LOCATION (fn);
       if (TREE_CODE (body) == STATEMENT_LIST && !STATEMENT_LIST_HEAD (body))
-        error_at (loc, "definition of concept %qD is empty", fn);
+       {
+         if (seen_error ())
+           /* The definition was probably erroneous, not empty.  */;
+         else
+           error_at (loc, "definition of concept %qD is empty", fn);
+       }
       else
         error_at (loc, "definition of concept %qD has multiple statements", fn);
     }
index c3310db7b3b68d7ae7e8721b1b9895ef8e178727..01647d04bc8b8ce3f6e9cc7631767f350f9c731e 100644 (file)
@@ -8957,10 +8957,14 @@ check_return_expr (tree retval, bool *no_warning)
       if (check_for_bare_parameter_packs (retval))
        return error_mark_node;
 
-      if (WILDCARD_TYPE_P (TREE_TYPE (DECL_RESULT (current_function_decl)))
+      /* If one of the types might be void, we can't tell whether we're
+        returning a value.  */
+      if ((WILDCARD_TYPE_P (TREE_TYPE (DECL_RESULT (current_function_decl)))
+          && !current_function_auto_return_pattern)
          || (retval != NULL_TREE
-             && type_dependent_expression_p (retval)))
-        return retval;
+             && (TREE_TYPE (retval) == NULL_TREE
+                 || WILDCARD_TYPE_P (TREE_TYPE (retval)))))
+       goto dependent;
     }
 
   functype = TREE_TYPE (TREE_TYPE (current_function_decl));
@@ -9098,8 +9102,10 @@ check_return_expr (tree retval, bool *no_warning)
        warning (OPT_Weffc__, "%<operator=%> should return a reference to %<*this%>");
     }
 
-  if (processing_template_decl)
+  if (dependent_type_p (functype)
+      || type_dependent_expression_p (retval))
     {
+    dependent:
       /* We should not have changed the return value.  */
       gcc_assert (retval == saved_retval);
       return retval;
@@ -9126,6 +9132,7 @@ check_return_expr (tree retval, bool *no_warning)
 
   named_return_value_okay_p = 
     (retval != NULL_TREE
+     && !processing_template_decl
      /* Must be a local, automatic variable.  */
      && VAR_P (retval)
      && DECL_CONTEXT (retval) == current_function_decl
@@ -9222,6 +9229,9 @@ check_return_expr (tree retval, bool *no_warning)
                         build_zero_cst (TREE_TYPE (retval)));
     }
 
+  if (processing_template_decl)
+    return saved_retval;
+
   /* Actually copy the value returned into the appropriate location.  */
   if (retval && retval != result)
     retval = build2 (INIT_EXPR, TREE_TYPE (result), result, retval);
index 670fd542f6f0cc01e619e0d9d845358af5cc527a..50fa3b4daddf112dc6945067e03be634a80ea31a 100644 (file)
@@ -4,7 +4,7 @@ struct X { };
 int operator==(X, X) { return 0; }
 
 template<typename T>
-  concept bool C1() { return X(); }
+  concept bool C1() { return X(); } // { dg-error "bool" }
 
 template<C1 T>
   void h(T) { } // OK until used.
index 160cbe541a112a1b433ae6114900315bfec3264a..e5b3f25b5303b15e65bf08e00234dc50d473365d 100644 (file)
@@ -6,11 +6,11 @@ public:
     CVector<int> f() const
     {
        CVector<int> v();
-       return v;
+       return v;               // { dg-error "convert" }
     }
     CVector<long> g() const
     {
        CVector<long> v();
-       return v;
+       return v;               // { dg-error "convert" }
     }
 };