aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorJason Merrill <jason@redhat.com>2017-10-05 17:26:50 -0400
committerJason Merrill <jason@gcc.gnu.org>2017-10-05 17:26:50 -0400
commitb9760b03aaa977e865e375c69138e7bd85a7d6d3 (patch)
tree1ca1727752fbf6c32ada1a350ec602cf4cd29bf3 /gcc
parente58683fb9ffaa4dd19ee433742cf2170a76a82cc (diff)
downloadgcc-b9760b03aaa977e865e375c69138e7bd85a7d6d3.zip
gcc-b9760b03aaa977e865e375c69138e7bd85a7d6d3.tar.gz
gcc-b9760b03aaa977e865e375c69138e7bd85a7d6d3.tar.bz2
* call.c (convert_arg_to_ellipsis): Use the result of force_rvalue.
From-SVN: r253465
Diffstat (limited to 'gcc')
-rw-r--r--gcc/cp/ChangeLog4
-rw-r--r--gcc/cp/call.c24
-rw-r--r--gcc/testsuite/g++.dg/ext/varargs2.C17
3 files changed, 33 insertions, 12 deletions
diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog
index b5ae745..c5c28f4 100644
--- a/gcc/cp/ChangeLog
+++ b/gcc/cp/ChangeLog
@@ -1,3 +1,7 @@
+2017-10-05 Jason Merrill <jason@redhat.com>
+
+ * call.c (convert_arg_to_ellipsis): Use the result of force_rvalue.
+
2017-10-05 Nathan Sidwell <nathan@acm.org>
Warn on MVP declarations
diff --git a/gcc/cp/call.c b/gcc/cp/call.c
index bfd9288..9d747be 100644
--- a/gcc/cp/call.c
+++ b/gcc/cp/call.c
@@ -7165,29 +7165,24 @@ convert_arg_to_ellipsis (tree arg, tsubst_flags_t complain)
/* In a template (or ill-formed code), we can have an incomplete type
even after require_complete_type_sfinae, in which case we don't know
whether it has trivial copy or not. */
- && COMPLETE_TYPE_P (arg_type))
+ && COMPLETE_TYPE_P (arg_type)
+ && !cp_unevaluated_operand)
{
- /* Build up a real lvalue-to-rvalue conversion in case the
- copy constructor is trivial but not callable. */
- if (!cp_unevaluated_operand && CLASS_TYPE_P (arg_type))
- force_rvalue (arg, complain);
-
/* [expr.call] 5.2.2/7:
Passing a potentially-evaluated argument of class type (Clause 9)
with a non-trivial copy constructor or a non-trivial destructor
with no corresponding parameter is conditionally-supported, with
implementation-defined semantics.
- We support it as pass-by-invisible-reference to the caller's
- object. That's different to named by-value parameters, which
- construct a copy and pass a reference to that.
+ We support it as pass-by-invisible-reference, just like a normal
+ value parameter.
If the call appears in the context of a sizeof expression,
it is not potentially-evaluated. */
- if (cp_unevaluated_operand == 0
- && (type_has_nontrivial_copy_init (arg_type)
- || TYPE_HAS_NONTRIVIAL_DESTRUCTOR (arg_type)))
+ if (type_has_nontrivial_copy_init (arg_type)
+ || TYPE_HAS_NONTRIVIAL_DESTRUCTOR (arg_type))
{
+ arg = force_rvalue (arg, complain);
if (complain & tf_warning)
warning (OPT_Wconditionally_supported,
"passing objects of non-trivially-copyable "
@@ -7195,6 +7190,11 @@ convert_arg_to_ellipsis (tree arg, tsubst_flags_t complain)
arg_type);
return cp_build_addr_expr (arg, complain);
}
+ /* Build up a real lvalue-to-rvalue conversion in case the
+ copy constructor is trivial but not callable. */
+ else if (CLASS_TYPE_P (arg_type))
+ force_rvalue (arg, complain);
+
}
return arg;
diff --git a/gcc/testsuite/g++.dg/ext/varargs2.C b/gcc/testsuite/g++.dg/ext/varargs2.C
new file mode 100644
index 0000000..13ddf5b
--- /dev/null
+++ b/gcc/testsuite/g++.dg/ext/varargs2.C
@@ -0,0 +1,17 @@
+// { dg-do run }
+
+int c;
+struct X { X() {}; X(const X&) { ++c; } };
+void Foo (X, ...) {}
+void bin (X &p)
+{
+ Foo (p, p);
+}
+
+int main()
+{
+ X x;
+ bin(x);
+ if (c != 2)
+ __builtin_abort();
+}