diff --git a/gcc/cp/cp-tree.h b/gcc/cp/cp-tree.h
index 6e34952da99..efcd2de54e5 100644
--- a/gcc/cp/cp-tree.h
+++ b/gcc/cp/cp-tree.h
@@ -8209,9 +8209,9 @@ extern void maybe_warn_about_useless_cast       (location_t, tree, tree,
 						 tsubst_flags_t);
 extern tree cp_perform_integral_promotions      (tree, tsubst_flags_t);
 
-extern tree finish_left_unary_fold_expr      (tree, int);
-extern tree finish_right_unary_fold_expr     (tree, int);
-extern tree finish_binary_fold_expr          (tree, tree, int);
+extern tree finish_left_unary_fold_expr      (location_t, tree, int);
+extern tree finish_right_unary_fold_expr     (location_t, tree, int);
+extern tree finish_binary_fold_expr          (location_t, tree, tree, int);
 extern tree treat_lvalue_as_rvalue_p	     (tree, bool);
 extern bool decl_in_std_namespace_p	     (tree);
 extern void maybe_warn_pessimizing_move	     (tree, tree, bool);
diff --git a/gcc/cp/constraint.cc b/gcc/cp/constraint.cc
index c9e4e7043cd..64b64e17857 100644
--- a/gcc/cp/constraint.cc
+++ b/gcc/cp/constraint.cc
@@ -1607,7 +1607,8 @@ finish_shorthand_constraint (tree decl, tree constr)
 
   /* Make the check a fold-expression if needed.  */
   if (apply_to_each_p && declared_pack_p)
-    check = finish_left_unary_fold_expr (check, TRUTH_ANDIF_EXPR);
+    check = finish_left_unary_fold_expr (DECL_SOURCE_LOCATION (decl),
+					 check, TRUTH_ANDIF_EXPR);
 
   return check;
 }
diff --git a/gcc/cp/parser.cc b/gcc/cp/parser.cc
index f3abae716fe..59b9852895e 100644
--- a/gcc/cp/parser.cc
+++ b/gcc/cp/parser.cc
@@ -5533,6 +5533,8 @@ static cp_expr
 cp_parser_fold_expression (cp_parser *parser, tree expr1)
 {
   cp_id_kind pidk;
+  location_t loc = cp_lexer_peek_token (parser->lexer)->location;
+  const cp_token *token = nullptr;
 
   // Left fold.
   if (cp_lexer_next_token_is (parser->lexer, CPP_ELLIPSIS))
@@ -5540,6 +5542,7 @@ cp_parser_fold_expression (cp_parser *parser, tree expr1)
       if (expr1)
 	return error_mark_node;
       cp_lexer_consume_token (parser->lexer);
+      token = cp_lexer_peek_token (parser->lexer);
       int op = cp_parser_fold_operator (parser);
       if (op == ERROR_MARK)
         {
@@ -5551,10 +5554,11 @@ cp_parser_fold_expression (cp_parser *parser, tree expr1)
 					     false, &pidk);
       if (expr == error_mark_node)
         return error_mark_node;
-      return finish_left_unary_fold_expr (expr, op);
+      loc = make_location (token->location, loc, parser->lexer);
+      return finish_left_unary_fold_expr (loc, expr, op);
     }
 
-  const cp_token* token = cp_lexer_peek_token (parser->lexer);
+  token = cp_lexer_peek_token (parser->lexer);
   int op = cp_parser_fold_operator (parser);
   if (op == ERROR_MARK)
     {
@@ -5585,7 +5589,10 @@ cp_parser_fold_expression (cp_parser *parser, tree expr1)
 
   // Right fold.
   if (cp_lexer_next_token_is (parser->lexer, CPP_CLOSE_PAREN))
-    return finish_right_unary_fold_expr (expr1, op);
+    {
+      loc = make_location (token->location, loc, parser->lexer);
+      return finish_right_unary_fold_expr (loc, expr1, op);
+    }
 
   if (cp_lexer_next_token_is_not (parser->lexer, token->type))
     {
@@ -5598,7 +5605,8 @@ cp_parser_fold_expression (cp_parser *parser, tree expr1)
   tree expr2 = cp_parser_cast_expression (parser, false, false, false, &pidk);
   if (expr2 == error_mark_node)
     return error_mark_node;
-  return finish_binary_fold_expr (expr1, expr2, op);
+  loc = make_location (token->location, loc, parser->lexer);
+  return finish_binary_fold_expr (loc, expr1, expr2, op);
 }
 
 /* Parse a primary-expression.
diff --git a/gcc/cp/pt.cc b/gcc/cp/pt.cc
index 73ac1cb597c..7cbf903ae29 100644
--- a/gcc/cp/pt.cc
+++ b/gcc/cp/pt.cc
@@ -31423,7 +31423,9 @@ convert_generic_types_to_packs (tree parm, int start_idx, int end_idx)
 	{
 	  tree id = unpack_concept_check (constr);
 	  TREE_VEC_ELT (TREE_OPERAND (id, 1), 0) = t;
-	  tree fold = finish_left_unary_fold_expr (constr, TRUTH_ANDIF_EXPR);
+	  location_t loc = DECL_SOURCE_LOCATION (TYPE_NAME (t));
+	  tree fold = finish_left_unary_fold_expr (loc, constr,
+						   TRUTH_ANDIF_EXPR);
 	  TEMPLATE_PARM_CONSTRAINTS (node) = fold;
 
 	  /* If there was a constraint, we also need to replace that in
diff --git a/gcc/cp/semantics.cc b/gcc/cp/semantics.cc
index 80ef1364e33..2a0cf963e91 100644
--- a/gcc/cp/semantics.cc
+++ b/gcc/cp/semantics.cc
@@ -12605,7 +12605,7 @@ capture_decltype (tree decl)
    this is a right unary fold. Otherwise it is a left unary fold. */
 
 static tree
-finish_unary_fold_expr (tree expr, int op, tree_code dir)
+finish_unary_fold_expr (location_t loc, tree expr, int op, tree_code dir)
 {
   /* Build a pack expansion (assuming expr has pack type).  */
   if (!uses_parameter_packs (expr))
@@ -12618,7 +12618,7 @@ finish_unary_fold_expr (tree expr, int op, tree_code dir)
 
   /* Build the fold expression.  */
   tree code = build_int_cstu (integer_type_node, abs (op));
-  tree fold = build_min_nt_loc (input_location, dir, code, pack);
+  tree fold = build_min_nt_loc (loc, dir, code, pack);
   FOLD_EXPR_MODIFY_P (fold) = (op < 0);
   TREE_TYPE (fold) = build_dependent_operator_type (NULL_TREE,
 						    FOLD_EXPR_OP (fold),
@@ -12627,27 +12627,28 @@ finish_unary_fold_expr (tree expr, int op, tree_code dir)
 }
 
 tree
-finish_left_unary_fold_expr (tree expr, int op)
+finish_left_unary_fold_expr (location_t loc, tree expr, int op)
 {
-  return finish_unary_fold_expr (expr, op, UNARY_LEFT_FOLD_EXPR);
+  return finish_unary_fold_expr (loc, expr, op, UNARY_LEFT_FOLD_EXPR);
 }
 
 tree
-finish_right_unary_fold_expr (tree expr, int op)
+finish_right_unary_fold_expr (location_t loc, tree expr, int op)
 {
-  return finish_unary_fold_expr (expr, op, UNARY_RIGHT_FOLD_EXPR);
+  return finish_unary_fold_expr (loc, expr, op, UNARY_RIGHT_FOLD_EXPR);
 }
 
 /* Build a binary fold expression over EXPR1 and EXPR2. The
    associativity of the fold is determined by EXPR1 and EXPR2 (whichever
    has an unexpanded parameter pack). */
 
-tree
-finish_binary_fold_expr (tree pack, tree init, int op, tree_code dir)
+static tree
+finish_binary_fold_expr (location_t loc, tree pack, tree init,
+			 int op, tree_code dir)
 {
   pack = make_pack_expansion (pack);
   tree code = build_int_cstu (integer_type_node, abs (op));
-  tree fold = build_min_nt_loc (input_location, dir, code, pack, init);
+  tree fold = build_min_nt_loc (loc, dir, code, pack, init);
   FOLD_EXPR_MODIFY_P (fold) = (op < 0);
   TREE_TYPE (fold) = build_dependent_operator_type (NULL_TREE,
 						    FOLD_EXPR_OP (fold),
@@ -12656,16 +12657,16 @@ finish_binary_fold_expr (tree pack, tree init, int op, tree_code dir)
 }
 
 tree
-finish_binary_fold_expr (tree expr1, tree expr2, int op)
+finish_binary_fold_expr (location_t loc, tree expr1, tree expr2, int op)
 {
   // Determine which expr has an unexpanded parameter pack and
   // set the pack and initial term.
   bool pack1 = uses_parameter_packs (expr1);
   bool pack2 = uses_parameter_packs (expr2);
   if (pack1 && !pack2)
-    return finish_binary_fold_expr (expr1, expr2, op, BINARY_RIGHT_FOLD_EXPR);
+    return finish_binary_fold_expr (loc, expr1, expr2, op, BINARY_RIGHT_FOLD_EXPR);
   else if (pack2 && !pack1)
-    return finish_binary_fold_expr (expr2, expr1, op, BINARY_LEFT_FOLD_EXPR);
+    return finish_binary_fold_expr (loc, expr2, expr1, op, BINARY_LEFT_FOLD_EXPR);
   else
     {
       if (pack1)
diff --git a/gcc/testsuite/g++.dg/concepts/diagnostic3.C b/gcc/testsuite/g++.dg/concepts/diagnostic3.C
index 410651a9c1a..52b2f23c95e 100644
--- a/gcc/testsuite/g++.dg/concepts/diagnostic3.C
+++ b/gcc/testsuite/g++.dg/concepts/diagnostic3.C
@@ -7,7 +7,7 @@ template<typename T>
   concept foo = (bool)(foo_v<T> | foo_v<T&>);
 
 template<typename... Ts>
-requires (foo<Ts> && ...) // { dg-message "with Ts = .int, char... evaluated to .false." }
+requires (foo<Ts> && ...) // { dg-message "19:with Ts = .int, char... evaluated to .false." }
 void
 bar()
 { }
@@ -16,7 +16,7 @@ template<int>
 struct S { };
 
 template<int... Is>
-requires (foo<S<Is>> && ...) // { dg-message "with Is = .2, 3, 4... evaluated to .false." }
+requires (foo<S<Is>> && ...) // { dg-message "22:with Is = .2, 3, 4... evaluated to .false." }
 void
 baz()
 { }
diff --git a/gcc/testsuite/g++.dg/cpp1z/fold3.C b/gcc/testsuite/g++.dg/cpp1z/fold3.C
index 787bf792be9..a2561410ec4 100644
--- a/gcc/testsuite/g++.dg/cpp1z/fold3.C
+++ b/gcc/testsuite/g++.dg/cpp1z/fold3.C
@@ -7,44 +7,44 @@
 
 #define MAKE_FN(name, op) \
   template<typename... Ts> \
-    constexpr auto name (Ts... ts) { return (... op ts); } // { dg-error "empty" }
+    constexpr auto name (Ts... ts) { return (... op ts); } // { dg-message "" }
 
-MAKE_FN (add, +);
-MAKE_FN (sub, -);
-MAKE_FN (mul, *);
-MAKE_FN (div, /);
-MAKE_FN (mod, %);
-MAKE_FN (bxor, ^);
-MAKE_FN (bor, |);
-MAKE_FN (band, &);
-MAKE_FN (lsh, <<);
-MAKE_FN (rsh, >>);
+MAKE_FN (add, +);		// { dg-message "" }
+MAKE_FN (sub, -);		// { dg-message "" }
+MAKE_FN (mul, *);		// { dg-message "" }
+MAKE_FN (div, /);		// { dg-message "" }
+MAKE_FN (mod, %);		// { dg-message "" }
+MAKE_FN (bxor, ^);		// { dg-message "" }
+MAKE_FN (bor, |);		// { dg-message "" }
+MAKE_FN (band, &);		// { dg-message "" }
+MAKE_FN (lsh, <<);		// { dg-message "" }
+MAKE_FN (rsh, >>);		// { dg-message "" }
 
-MAKE_FN (assign, =);
-MAKE_FN (addi, +=);
-MAKE_FN (subi, -=);
-MAKE_FN (muli, *=);
-MAKE_FN (divi, /=);
-MAKE_FN (modi, %=);
-MAKE_FN (bxori, ^=);
-MAKE_FN (bori, |=);
-MAKE_FN (bandi, &=);
-MAKE_FN (lshi, <<=);
-MAKE_FN (rshi, >>=);
+MAKE_FN (assign, =);		// { dg-message "" }
+MAKE_FN (addi, +=);		// { dg-message "" }
+MAKE_FN (subi, -=);		// { dg-message "" }
+MAKE_FN (muli, *=);		// { dg-message "" }
+MAKE_FN (divi, /=);		// { dg-message "" }
+MAKE_FN (modi, %=);		// { dg-message "" }
+MAKE_FN (bxori, ^=);		// { dg-message "" }
+MAKE_FN (bori, |=);		// { dg-message "" }
+MAKE_FN (bandi, &=);		// { dg-message "" }
+MAKE_FN (lshi, <<=);		// { dg-message "" }
+MAKE_FN (rshi, >>=);		// { dg-message "" }
 
-MAKE_FN (eq, ==);
-MAKE_FN (ne, !=);
-MAKE_FN (lt, <);
-MAKE_FN (gt, >);
-MAKE_FN (le, <);
-MAKE_FN (ge, >);
+MAKE_FN (eq, ==);		// { dg-message "" }
+MAKE_FN (ne, !=);		// { dg-message "" }
+MAKE_FN (lt, <);		// { dg-message "" }
+MAKE_FN (gt, >);		// { dg-message "" }
+MAKE_FN (le, <);		// { dg-message "" }
+MAKE_FN (ge, >);		// { dg-message "" }
 
 MAKE_FN (land, &&);
 MAKE_FN (lor, ||);
 
 MAKE_FN (comma, COMMA);
-MAKE_FN (dot_star, .*);
-MAKE_FN (arrow_star, ->*);
+MAKE_FN (dot_star, .*);		// { dg-message "" }
+MAKE_FN (arrow_star, ->*);	// { dg-message "" }
 
 int main() {
   static_assert(land() == true, "");
@@ -52,7 +52,7 @@ int main() {
   comma(); // No value to theck
 
   // These are all errors, but the error is emitted at the point
-  // of instantiation (line 10).
+  // of macro definition or expansion above.
   add();			// { dg-message "required from here" }
   mul();			// { dg-message "required from here" }
   bor();			// { dg-message "required from here" }
