Commit 5c824000 by Jason Merrill Committed by Jason Merrill

call.c (add_candidates): Add first_arg and return_type parms.

	* call.c (add_candidates): Add first_arg and return_type parms.
	Add special constructor/conversion op handling.
	(convert_class_to_reference): Use it.
	(build_user_type_conversion_1): Likewise.
	(build_op_call): Likewise.
	(build_new_method_call): Likewise.
	(build_new_op): Adjust.
	(perform_overload_resolution): Adjust.

From-SVN: r159332
parent 1df43907
2010-05-12 Jason Merrill <jason@redhat.com>
* call.c (add_candidates): Add first_arg and return_type parms.
Add special constructor/conversion op handling.
(convert_class_to_reference): Use it.
(build_user_type_conversion_1): Likewise.
(build_op_call): Likewise.
(build_new_method_call): Likewise.
(build_new_op): Adjust.
(perform_overload_resolution): Adjust.
2010-05-11 Paolo Carlini <paolo.carlini@oracle.com> 2010-05-11 Paolo Carlini <paolo.carlini@oracle.com>
PR c++/34272 PR c++/34272
......
...@@ -197,8 +197,8 @@ static bool promoted_arithmetic_type_p (tree); ...@@ -197,8 +197,8 @@ static bool promoted_arithmetic_type_p (tree);
static conversion *conditional_conversion (tree, tree); static conversion *conditional_conversion (tree, tree);
static char *name_as_c_string (tree, tree, bool *); static char *name_as_c_string (tree, tree, bool *);
static tree prep_operand (tree); static tree prep_operand (tree);
static void add_candidates (tree, const VEC(tree,gc) *, tree, bool, tree, tree, static void add_candidates (tree, tree, const VEC(tree,gc) *, tree, tree, bool,
int, struct z_candidate **); tree, tree, int, struct z_candidate **);
static conversion *merge_conversion_sequences (conversion *, conversion *); static conversion *merge_conversion_sequences (conversion *, conversion *);
static bool magic_varargs_p (tree); static bool magic_varargs_p (tree);
static tree build_temp (tree, tree, int, diagnostic_t *); static tree build_temp (tree, tree, int, diagnostic_t *);
...@@ -1056,57 +1056,28 @@ convert_class_to_reference (tree reference_type, tree s, tree expr, int flags) ...@@ -1056,57 +1056,28 @@ convert_class_to_reference (tree reference_type, tree s, tree expr, int flags)
for (; conversions; conversions = TREE_CHAIN (conversions)) for (; conversions; conversions = TREE_CHAIN (conversions))
{ {
tree fns = TREE_VALUE (conversions); tree fns = TREE_VALUE (conversions);
tree binfo = TREE_PURPOSE (conversions);
struct z_candidate *old_candidates = candidates;;
for (; fns; fns = OVL_NEXT (fns)) add_candidates (fns, first_arg, NULL, reference_type,
NULL_TREE, false,
binfo, TYPE_BINFO (s),
flags, &candidates);
for (cand = candidates; cand != old_candidates; cand = cand->next)
{ {
tree f = OVL_CURRENT (fns); /* Now, see if the conversion function really returns
an lvalue of the appropriate type. From the
point of view of unification, simply returning an
rvalue of the right type is good enough. */
tree f = cand->fn;
tree t2 = TREE_TYPE (TREE_TYPE (f)); tree t2 = TREE_TYPE (TREE_TYPE (f));
if (TREE_CODE (t2) != REFERENCE_TYPE
if (DECL_NONCONVERTING_P (f) || !reference_compatible_p (t, TREE_TYPE (t2)))
&& (flags & LOOKUP_ONLYCONVERTING))
continue;
cand = NULL;
/* If this is a template function, try to get an exact
match. */
if (TREE_CODE (f) == TEMPLATE_DECL)
{ {
cand = add_template_candidate (&candidates, cand->viable = 0;
f, s,
NULL_TREE,
first_arg,
NULL,
reference_type,
TYPE_BINFO (s),
TREE_PURPOSE (conversions),
LOOKUP_NORMAL,
DEDUCE_CONV);
if (cand)
{
/* Now, see if the conversion function really returns
an lvalue of the appropriate type. From the
point of view of unification, simply returning an
rvalue of the right type is good enough. */
f = cand->fn;
t2 = TREE_TYPE (TREE_TYPE (f));
if (TREE_CODE (t2) != REFERENCE_TYPE
|| !reference_compatible_p (t, TREE_TYPE (t2)))
{
candidates = candidates->next;
cand = NULL;
}
}
} }
else if (TREE_CODE (t2) == REFERENCE_TYPE else
&& reference_compatible_p (t, TREE_TYPE (t2)))
cand = add_function_candidate (&candidates, f, s, first_arg,
NULL, TYPE_BINFO (s),
TREE_PURPOSE (conversions),
LOOKUP_NORMAL);
if (cand)
{ {
conversion *identity_conv; conversion *identity_conv;
/* Build a standard conversion sequence indicating the /* Build a standard conversion sequence indicating the
...@@ -2874,6 +2845,8 @@ build_user_type_conversion_1 (tree totype, tree expr, int flags) ...@@ -2874,6 +2845,8 @@ build_user_type_conversion_1 (tree totype, tree expr, int flags)
candidates = 0; candidates = 0;
flags |= LOOKUP_NO_CONVERSION; flags |= LOOKUP_NO_CONVERSION;
if (BRACE_ENCLOSED_INITIALIZER_P (expr))
flags |= LOOKUP_NO_NARROWING;
/* It's OK to bind a temporary for converting constructor arguments, but /* It's OK to bind a temporary for converting constructor arguments, but
not in converting the return value of a conversion operator. */ not in converting the return value of a conversion operator. */
...@@ -2882,18 +2855,25 @@ build_user_type_conversion_1 (tree totype, tree expr, int flags) ...@@ -2882,18 +2855,25 @@ build_user_type_conversion_1 (tree totype, tree expr, int flags)
if (ctors) if (ctors)
{ {
int ctorflags = flags;
ctors = BASELINK_FUNCTIONS (ctors); ctors = BASELINK_FUNCTIONS (ctors);
first_arg = build_int_cst (build_pointer_type (totype), 0); first_arg = build_int_cst (build_pointer_type (totype), 0);
if (BRACE_ENCLOSED_INITIALIZER_P (expr) if (BRACE_ENCLOSED_INITIALIZER_P (expr))
&& !TYPE_HAS_LIST_CTOR (totype))
{ {
args = ctor_to_vec (expr); /* For list-initialization we consider explicit constructors, but
/* We still allow more conversions within an init-list. */ give an error if one is selected. */
flags = ((flags & ~LOOKUP_NO_CONVERSION) ctorflags &= ~LOOKUP_ONLYCONVERTING;
/* But not for the copy ctor. */ if (TYPE_HAS_LIST_CTOR (totype))
|LOOKUP_NO_COPY_CTOR_CONVERSION args = make_tree_vector_single (expr);
|LOOKUP_NO_NARROWING); else
{
args = ctor_to_vec (expr);
/* We still allow more conversions within an init-list. */
ctorflags &= ~LOOKUP_NO_CONVERSION;
/* But not for the copy ctor. */
ctorflags |= LOOKUP_NO_COPY_CTOR_CONVERSION;
}
} }
else else
args = make_tree_vector_single (expr); args = make_tree_vector_single (expr);
...@@ -2902,28 +2882,12 @@ build_user_type_conversion_1 (tree totype, tree expr, int flags) ...@@ -2902,28 +2882,12 @@ build_user_type_conversion_1 (tree totype, tree expr, int flags)
from here. */ from here. */
gcc_assert (!DECL_HAS_IN_CHARGE_PARM_P (OVL_CURRENT (ctors)) gcc_assert (!DECL_HAS_IN_CHARGE_PARM_P (OVL_CURRENT (ctors))
&& !DECL_HAS_VTT_PARM_P (OVL_CURRENT (ctors))); && !DECL_HAS_VTT_PARM_P (OVL_CURRENT (ctors)));
}
for (; ctors; ctors = OVL_NEXT (ctors))
{
tree ctor = OVL_CURRENT (ctors);
if (DECL_NONCONVERTING_P (ctor)
&& !BRACE_ENCLOSED_INITIALIZER_P (expr))
continue;
if (TREE_CODE (ctor) == TEMPLATE_DECL) add_candidates (ctors, first_arg, args, NULL_TREE, NULL_TREE, false,
cand = add_template_candidate (&candidates, ctor, totype, TYPE_BINFO (totype), TYPE_BINFO (totype),
NULL_TREE, first_arg, args, NULL_TREE, ctorflags, &candidates);
TYPE_BINFO (totype),
TYPE_BINFO (totype),
flags,
DEDUCE_CALL);
else
cand = add_function_candidate (&candidates, ctor, totype,
first_arg, args, TYPE_BINFO (totype),
TYPE_BINFO (totype),
flags);
if (cand) for (cand = candidates; cand; cand = cand->next)
{ {
cand->second_conv = build_identity_conv (totype, NULL_TREE); cand->second_conv = build_identity_conv (totype, NULL_TREE);
...@@ -2947,8 +2911,8 @@ build_user_type_conversion_1 (tree totype, tree expr, int flags) ...@@ -2947,8 +2911,8 @@ build_user_type_conversion_1 (tree totype, tree expr, int flags)
for (; conv_fns; conv_fns = TREE_CHAIN (conv_fns)) for (; conv_fns; conv_fns = TREE_CHAIN (conv_fns))
{ {
tree fns;
tree conversion_path = TREE_PURPOSE (conv_fns); tree conversion_path = TREE_PURPOSE (conv_fns);
struct z_candidate *old_candidates;
/* If we are called to convert to a reference type, we are trying to /* If we are called to convert to a reference type, we are trying to
find an lvalue binding, so don't even consider temporaries. If find an lvalue binding, so don't even consider temporaries. If
...@@ -2957,65 +2921,40 @@ build_user_type_conversion_1 (tree totype, tree expr, int flags) ...@@ -2957,65 +2921,40 @@ build_user_type_conversion_1 (tree totype, tree expr, int flags)
if (TREE_CODE (totype) == REFERENCE_TYPE) if (TREE_CODE (totype) == REFERENCE_TYPE)
convflags |= LOOKUP_NO_TEMP_BIND; convflags |= LOOKUP_NO_TEMP_BIND;
for (fns = TREE_VALUE (conv_fns); fns; fns = OVL_NEXT (fns)) old_candidates = candidates;
add_candidates (TREE_VALUE (conv_fns), first_arg, NULL, totype,
NULL_TREE, false,
conversion_path, TYPE_BINFO (fromtype),
flags, &candidates);
for (cand = candidates; cand != old_candidates; cand = cand->next)
{ {
tree fn = OVL_CURRENT (fns); conversion *ics
= implicit_conversion (totype,
if (DECL_NONCONVERTING_P (fn) TREE_TYPE (TREE_TYPE (cand->fn)),
&& (flags & LOOKUP_ONLYCONVERTING)) 0,
continue; /*c_cast_p=*/false, convflags);
/* [over.match.funcs] For conversion functions, the function
is considered to be a member of the class of the implicit
object argument for the purpose of defining the type of
the implicit object parameter.
So we pass fromtype as CTYPE to add_*_candidate. */
if (TREE_CODE (fn) == TEMPLATE_DECL)
cand = add_template_candidate (&candidates, fn, fromtype,
NULL_TREE,
first_arg, NULL, totype,
TYPE_BINFO (fromtype),
conversion_path,
flags,
DEDUCE_CONV);
else
cand = add_function_candidate (&candidates, fn, fromtype,
first_arg, NULL,
TYPE_BINFO (fromtype),
conversion_path,
flags);
if (cand) /* If LOOKUP_NO_TEMP_BIND isn't set, then this is
{ copy-initialization. In that case, "The result of the
conversion *ics call is then used to direct-initialize the object that is
= implicit_conversion (totype, the destination of the copy-initialization." [dcl.init]
TREE_TYPE (TREE_TYPE (cand->fn)),
0, We represent this in the conversion sequence with an
/*c_cast_p=*/false, convflags); rvalue conversion, which means a constructor call. But
don't add a second rvalue conversion if there's already
/* If LOOKUP_NO_TEMP_BIND isn't set, then this is one there. Which there really shouldn't be, but it's
copy-initialization. In that case, "The result of the harmless since we'd add it here anyway. */
call is then used to direct-initialize the object that is if (ics && MAYBE_CLASS_TYPE_P (totype) && ics->kind != ck_rvalue
the destination of the copy-initialization." [dcl.init] && !(convflags & LOOKUP_NO_TEMP_BIND))
ics = build_conv (ck_rvalue, totype, ics);
We represent this in the conversion sequence with an
rvalue conversion, which means a constructor call. But cand->second_conv = ics;
don't add a second rvalue conversion if there's already
one there. Which there really shouldn't be, but it's if (!ics)
harmless since we'd add it here anyway. */ cand->viable = 0;
if (ics && MAYBE_CLASS_TYPE_P (totype) && ics->kind != ck_rvalue else if (cand->viable == 1 && ics->bad_p)
&& !(convflags & LOOKUP_NO_TEMP_BIND)) cand->viable = -1;
ics = build_conv (ck_rvalue, totype, ics);
cand->second_conv = ics;
if (!ics)
cand->viable = 0;
else if (candidates->viable == 1 && ics->bad_p)
cand->viable = -1;
}
} }
} }
...@@ -3145,7 +3084,8 @@ perform_overload_resolution (tree fn, ...@@ -3145,7 +3084,8 @@ perform_overload_resolution (tree fn,
} }
/* Add the various candidate functions. */ /* Add the various candidate functions. */
add_candidates (fn, args, explicit_targs, template_only, add_candidates (fn, NULL_TREE, args, NULL_TREE,
explicit_targs, template_only,
/*conversion_path=*/NULL_TREE, /*conversion_path=*/NULL_TREE,
/*access_path=*/NULL_TREE, /*access_path=*/NULL_TREE,
LOOKUP_NORMAL, LOOKUP_NORMAL,
...@@ -3383,24 +3323,13 @@ build_op_call (tree obj, VEC(tree,gc) **args, tsubst_flags_t complain) ...@@ -3383,24 +3323,13 @@ build_op_call (tree obj, VEC(tree,gc) **args, tsubst_flags_t complain)
if (fns) if (fns)
{ {
tree base = BINFO_TYPE (BASELINK_BINFO (fns));
first_mem_arg = build_this (obj); first_mem_arg = build_this (obj);
for (fns = BASELINK_FUNCTIONS (fns); fns; fns = OVL_NEXT (fns)) add_candidates (BASELINK_FUNCTIONS (fns),
{ first_mem_arg, *args, NULL_TREE,
tree fn = OVL_CURRENT (fns); NULL_TREE, false,
BASELINK_BINFO (fns), BASELINK_ACCESS_BINFO (fns),
if (TREE_CODE (fn) == TEMPLATE_DECL) LOOKUP_NORMAL, &candidates);
add_template_candidate (&candidates, fn, base, NULL_TREE,
first_mem_arg, *args, NULL_TREE,
TYPE_BINFO (type),
TYPE_BINFO (type),
LOOKUP_NORMAL, DEDUCE_CALL);
else
add_function_candidate
(&candidates, fn, base, first_mem_arg, *args, TYPE_BINFO (type),
TYPE_BINFO (type), LOOKUP_NORMAL);
}
} }
convs = lookup_conversions (type, /*lookup_template_convs_p=*/true); convs = lookup_conversions (type, /*lookup_template_convs_p=*/true);
...@@ -4058,53 +3987,86 @@ prep_operand (tree operand) ...@@ -4058,53 +3987,86 @@ prep_operand (tree operand)
/* Add each of the viable functions in FNS (a FUNCTION_DECL or /* Add each of the viable functions in FNS (a FUNCTION_DECL or
OVERLOAD) to the CANDIDATES, returning an updated list of OVERLOAD) to the CANDIDATES, returning an updated list of
CANDIDATES. The ARGS are the arguments provided to the call, CANDIDATES. The ARGS are the arguments provided to the call;
without any implicit object parameter. This may change ARGS. The if FIRST_ARG is non-null it is the implicit object argument,
otherwise the first element of ARGS is used if needed. The
EXPLICIT_TARGS are explicit template arguments provided. EXPLICIT_TARGS are explicit template arguments provided.
TEMPLATE_ONLY is true if only template functions should be TEMPLATE_ONLY is true if only template functions should be
considered. CONVERSION_PATH, ACCESS_PATH, and FLAGS are as for considered. CONVERSION_PATH, ACCESS_PATH, and FLAGS are as for
add_function_candidate. */ add_function_candidate. */
static void static void
add_candidates (tree fns, const VEC(tree,gc) *args, add_candidates (tree fns, tree first_arg, const VEC(tree,gc) *args,
tree return_type,
tree explicit_targs, bool template_only, tree explicit_targs, bool template_only,
tree conversion_path, tree access_path, tree conversion_path, tree access_path,
int flags, int flags,
struct z_candidate **candidates) struct z_candidate **candidates)
{ {
tree ctype; tree ctype;
VEC(tree,gc) *non_static_args; const VEC(tree,gc) *non_static_args;
tree first_arg; bool check_converting;
unification_kind_t strict;
tree fn;
if (!fns)
return;
/* Precalculate special handling of constructors and conversion ops. */
fn = OVL_CURRENT (fns);
if (DECL_CONV_FN_P (fn))
{
check_converting = !!(flags & LOOKUP_ONLYCONVERTING);
strict = DEDUCE_CONV;
/* [over.match.funcs] For conversion functions, the function
is considered to be a member of the class of the implicit
object argument for the purpose of defining the type of
the implicit object parameter. */
ctype = TYPE_MAIN_VARIANT (TREE_TYPE (TREE_TYPE (first_arg)));
}
else
{
if (DECL_CONSTRUCTOR_P (fn))
check_converting = !!(flags & LOOKUP_ONLYCONVERTING);
else
check_converting = false;
strict = DEDUCE_CALL;
ctype = conversion_path ? BINFO_TYPE (conversion_path) : NULL_TREE;
}
ctype = conversion_path ? BINFO_TYPE (conversion_path) : NULL_TREE; if (first_arg)
/* Delay creating the implicit this parameter until it is needed. */ non_static_args = args;
non_static_args = NULL; else
first_arg = NULL_TREE; /* Delay creating the implicit this parameter until it is needed. */
non_static_args = NULL;
while (fns) for (; fns; fns = OVL_NEXT (fns))
{ {
tree fn;
tree fn_first_arg; tree fn_first_arg;
const VEC(tree,gc) *fn_args; const VEC(tree,gc) *fn_args;
fn = OVL_CURRENT (fns); fn = OVL_CURRENT (fns);
if (check_converting && DECL_NONCONVERTING_P (fn))
continue;
/* Figure out which set of arguments to use. */ /* Figure out which set of arguments to use. */
if (DECL_NONSTATIC_MEMBER_FUNCTION_P (fn)) if (DECL_NONSTATIC_MEMBER_FUNCTION_P (fn))
{ {
/* If this function is a non-static member, prepend the implicit /* If this function is a non-static member and we didn't get an
object parameter. */ implicit object argument, move it out of args. */
if (non_static_args == NULL) if (first_arg == NULL_TREE)
{ {
unsigned int ix; unsigned int ix;
tree arg; tree arg;
VEC(tree,gc) *tempvec
non_static_args = VEC_alloc (tree, gc, = VEC_alloc (tree, gc, VEC_length (tree, args) - 1);
VEC_length (tree, args) - 1);
for (ix = 1; VEC_iterate (tree, args, ix, arg); ++ix) for (ix = 1; VEC_iterate (tree, args, ix, arg); ++ix)
VEC_quick_push (tree, non_static_args, arg); VEC_quick_push (tree, tempvec, arg);
non_static_args = tempvec;
first_arg = build_this (VEC_index (tree, args, 0));
} }
if (first_arg == NULL_TREE)
first_arg = build_this (VEC_index (tree, args, 0));
fn_first_arg = first_arg; fn_first_arg = first_arg;
fn_args = non_static_args; fn_args = non_static_args;
} }
...@@ -4122,11 +4084,11 @@ add_candidates (tree fns, const VEC(tree,gc) *args, ...@@ -4122,11 +4084,11 @@ add_candidates (tree fns, const VEC(tree,gc) *args,
explicit_targs, explicit_targs,
fn_first_arg, fn_first_arg,
fn_args, fn_args,
NULL_TREE, return_type,
access_path, access_path,
conversion_path, conversion_path,
flags, flags,
DEDUCE_CALL); strict);
else if (!template_only) else if (!template_only)
add_function_candidate (candidates, add_function_candidate (candidates,
fn, fn,
...@@ -4136,7 +4098,6 @@ add_candidates (tree fns, const VEC(tree,gc) *args, ...@@ -4136,7 +4098,6 @@ add_candidates (tree fns, const VEC(tree,gc) *args,
access_path, access_path,
conversion_path, conversion_path,
flags); flags);
fns = OVL_NEXT (fns);
} }
} }
...@@ -4247,7 +4208,8 @@ build_new_op (enum tree_code code, int flags, tree arg1, tree arg2, tree arg3, ...@@ -4247,7 +4208,8 @@ build_new_op (enum tree_code code, int flags, tree arg1, tree arg2, tree arg3,
/* Add namespace-scope operators to the list of functions to /* Add namespace-scope operators to the list of functions to
consider. */ consider. */
add_candidates (lookup_function_nonclass (fnname, arglist, /*block_p=*/true), add_candidates (lookup_function_nonclass (fnname, arglist, /*block_p=*/true),
arglist, NULL_TREE, false, NULL_TREE, NULL_TREE, NULL_TREE, arglist, NULL_TREE,
NULL_TREE, false, NULL_TREE, NULL_TREE,
flags, &candidates); flags, &candidates);
/* Add class-member operators to the candidate set. */ /* Add class-member operators to the candidate set. */
if (CLASS_TYPE_P (TREE_TYPE (arg1))) if (CLASS_TYPE_P (TREE_TYPE (arg1)))
...@@ -4261,10 +4223,11 @@ build_new_op (enum tree_code code, int flags, tree arg1, tree arg2, tree arg3, ...@@ -4261,10 +4223,11 @@ build_new_op (enum tree_code code, int flags, tree arg1, tree arg2, tree arg3,
goto user_defined_result_ready; goto user_defined_result_ready;
} }
if (fns) if (fns)
add_candidates (BASELINK_FUNCTIONS (fns), arglist, add_candidates (BASELINK_FUNCTIONS (fns),
NULL_TREE, arglist, NULL_TREE,
NULL_TREE, false, NULL_TREE, false,
BASELINK_BINFO (fns), BASELINK_BINFO (fns),
TYPE_BINFO (TREE_TYPE (arg1)), BASELINK_ACCESS_BINFO (fns),
flags, &candidates); flags, &candidates);
} }
...@@ -6210,7 +6173,6 @@ build_new_method_call (tree instance, tree fns, VEC(tree,gc) **args, ...@@ -6210,7 +6173,6 @@ build_new_method_call (tree instance, tree fns, VEC(tree,gc) **args,
VEC(tree,gc) *user_args; VEC(tree,gc) *user_args;
tree call; tree call;
tree fn; tree fn;
tree class_type;
int template_only = 0; int template_only = 0;
bool any_viable_p; bool any_viable_p;
tree orig_instance; tree orig_instance;
...@@ -6340,48 +6302,14 @@ build_new_method_call (tree instance, tree fns, VEC(tree,gc) **args, ...@@ -6340,48 +6302,14 @@ build_new_method_call (tree instance, tree fns, VEC(tree,gc) **args,
*args = ctor_to_vec (VEC_index (tree, *args, 0)); *args = ctor_to_vec (VEC_index (tree, *args, 0));
} }
class_type = (conversion_path ? BINFO_TYPE (conversion_path) : NULL_TREE);
first_mem_arg = instance_ptr; first_mem_arg = instance_ptr;
/* Get the high-water mark for the CONVERSION_OBSTACK. */ /* Get the high-water mark for the CONVERSION_OBSTACK. */
p = conversion_obstack_alloc (0); p = conversion_obstack_alloc (0);
for (fn = fns; fn; fn = OVL_NEXT (fn)) add_candidates (fns, first_mem_arg, args ? *args : NULL, optype,
{ explicit_targs, template_only, conversion_path,
tree t = OVL_CURRENT (fn); access_binfo, flags, &candidates);
tree this_first_arg;
/* We can end up here for copy-init of same or base class. */
if ((flags & LOOKUP_ONLYCONVERTING)
&& DECL_NONCONVERTING_P (t))
continue;
if (DECL_NONSTATIC_MEMBER_FUNCTION_P (t))
this_first_arg = first_mem_arg;
else
this_first_arg = NULL_TREE;
if (TREE_CODE (t) == TEMPLATE_DECL)
/* A member template. */
add_template_candidate (&candidates, t,
class_type,
explicit_targs,
this_first_arg,
args == NULL ? NULL : *args,
optype,
access_binfo,
conversion_path,
flags,
DEDUCE_CALL);
else if (! template_only)
add_function_candidate (&candidates, t,
class_type,
this_first_arg,
args == NULL ? NULL : *args,
access_binfo,
conversion_path,
flags);
}
candidates = splice_viable (candidates, pedantic, &any_viable_p); candidates = splice_viable (candidates, pedantic, &any_viable_p);
if (!any_viable_p) if (!any_viable_p)
......
2010-05-12 Jason Merrill <jason@redhat.com>
* g++.old-deja/g++.robertl/eb43.C: Prune "candidates" messages.
2010-05-12 H.J. Lu <hongjiu.lu@intel.com> 2010-05-12 H.J. Lu <hongjiu.lu@intel.com>
PR target/44088 PR target/44088
......
...@@ -4,6 +4,8 @@ ...@@ -4,6 +4,8 @@
// The first one should still fail because it requires an implicit conversion // The first one should still fail because it requires an implicit conversion
// to pointer_to_binary_function, which has an `explicit' constructor. // to pointer_to_binary_function, which has an `explicit' constructor.
// { dg-prune-output "note" }
#include <vector> #include <vector>
#include <algorithm> #include <algorithm>
#include <functional> #include <functional>
......
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