Commit b028af11 by Jason Merrill Committed by Jason Merrill

re PR c++/47080 ([C++0x] explicit conversion function return conversions not…

re PR c++/47080 ([C++0x] explicit conversion function return conversions not restricted to qualifications)

	PR c++/47080
	* call.c (rejection_reason_code): Add rr_explicit_conversion.
	(print_z_candidate): Handle it.
	(explicit_conversion_rejection): New.
	(build_user_type_conversion_1): Reject an explicit conversion
	function that requires more than a qualification conversion.

From-SVN: r175217
parent de721390
2011-06-20 Jason Merrill <jason@redhat.com>
PR c++/47080
* call.c (rejection_reason_code): Add rr_explicit_conversion.
(print_z_candidate): Handle it.
(explicit_conversion_rejection): New.
(build_user_type_conversion_1): Reject an explicit conversion
function that requires more than a qualification conversion.
PR c++/47635
* decl.c (grokdeclarator): Don't set ctype to an ENUMERAL_TYPE.
......
......@@ -429,6 +429,7 @@ struct candidate_warning {
enum rejection_reason_code {
rr_none,
rr_arity,
rr_explicit_conversion,
rr_arg_conversion,
rr_bad_arg_conversion
};
......@@ -608,6 +609,16 @@ bad_arg_conversion_rejection (tree first_arg, int n_arg, tree from, tree to)
return r;
}
static struct rejection_reason *
explicit_conversion_rejection (tree from, tree to)
{
struct rejection_reason *r = alloc_rejection (rr_explicit_conversion);
r->u.conversion.n_arg = 0;
r->u.conversion.from_type = from;
r->u.conversion.to_type = to;
return r;
}
/* Dynamically allocate a conversion. */
static conversion *
......@@ -3153,6 +3164,12 @@ print_z_candidate (const char *msgstr, struct z_candidate *candidate)
case rr_bad_arg_conversion:
print_conversion_rejection (loc, &r->u.bad_conversion);
break;
case rr_explicit_conversion:
inform (loc, " return type %qT of explicit conversion function "
"cannot be converted to %qT with a qualification "
"conversion", r->u.conversion.from_type,
r->u.conversion.to_type);
break;
case rr_none:
default:
/* This candidate didn't have any issues or we failed to
......@@ -3429,9 +3446,10 @@ build_user_type_conversion_1 (tree totype, tree expr, int flags)
for (cand = candidates; cand != old_candidates; cand = cand->next)
{
tree rettype = TREE_TYPE (TREE_TYPE (cand->fn));
conversion *ics
= implicit_conversion (totype,
TREE_TYPE (TREE_TYPE (cand->fn)),
rettype,
0,
/*c_cast_p=*/false, convflags);
......@@ -3453,14 +3471,23 @@ build_user_type_conversion_1 (tree totype, tree expr, int flags)
if (!ics)
{
tree rettype = TREE_TYPE (TREE_TYPE (cand->fn));
cand->viable = 0;
cand->reason = arg_conversion_rejection (NULL_TREE, -1,
rettype, totype);
}
else if (DECL_NONCONVERTING_P (cand->fn)
&& ics->rank > cr_exact)
{
/* 13.3.1.5: For direct-initialization, those explicit
conversion functions that are not hidden within S and
yield type T or a type that can be converted to type T
with a qualification conversion (4.4) are also candidate
functions. */
cand->viable = -1;
cand->reason = explicit_conversion_rejection (rettype, totype);
}
else if (cand->viable == 1 && ics->bad_p)
{
tree rettype = TREE_TYPE (TREE_TYPE (cand->fn));
cand->viable = -1;
cand->reason
= bad_arg_conversion_rejection (NULL_TREE, -1,
......@@ -5513,7 +5540,18 @@ convert_like_real (conversion *convs, tree expr, tree fn, int argnum,
for (; t; t = convs->u.next)
{
if (t->kind == ck_user || !t->bad_p)
if (t->kind == ck_user && t->cand->reason)
{
permerror (input_location, "invalid user-defined conversion "
"from %qT to %qT", TREE_TYPE (expr), totype);
print_z_candidate ("candidate is:", t->cand);
expr = convert_like_real (t, expr, fn, argnum, 1,
/*issue_conversion_warnings=*/false,
/*c_cast_p=*/false,
complain);
return cp_convert (totype, expr);
}
else if (t->kind == ck_user || !t->bad_p)
{
expr = convert_like_real (t, expr, fn, argnum, 1,
/*issue_conversion_warnings=*/false,
......
2011-06-20 Jason Merrill <jason@redhat.com>
PR c++/47080
* g++.dg/cpp0x/explicit6.C: New.
PR c++/47635
* g++.dg/cpp0x/enum20.C: New.
......
// PR c++/47080
// { dg-options -std=c++0x }
struct A {
explicit operator int(); // { dg-message "qualification conversion" }
};
int main() {
bool b((A())); // { dg-error "invalid user-defined" }
!A(); // { dg-error "" }
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment