aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorNathan Sidwell <nathan@codesourcery.com>2000-03-05 10:22:16 +0000
committerNathan Sidwell <nathan@gcc.gnu.org>2000-03-05 10:22:16 +0000
commitc3f082287cde52571c84a7c18f455bdc2e34f7fe (patch)
tree5ff56b9f3a4de9b423c89fa746c6586c5497c90e /gcc
parent18ca9ce7234bb110f3a8aaaae334955cf49d17e5 (diff)
downloadgcc-c3f082287cde52571c84a7c18f455bdc2e34f7fe.zip
gcc-c3f082287cde52571c84a7c18f455bdc2e34f7fe.tar.gz
gcc-c3f082287cde52571c84a7c18f455bdc2e34f7fe.tar.bz2
call.c (convert_like): Macrofy.
* call.c (convert_like): Macrofy. (convert_like_with_context): New macro. (convert_like_real): Renamed from convert_like. Add calling context parameters, for diagnostics. Add recursive flag. Call dubious_conversion_warnings for outer conversion. (build_user_type_conversion): Use convert_like_with_context. (build_over_call): Likewise. Don't warn about dubious conversions here. Adjust convert_default_arg calls. (convert_default_arg): Add context parameters for diagnostics. Pass throught to convert_like_with_context. * cp-tree.h (convert_default_arg): Add context parameters. (dubious_conversion_warnings): Prototype new function. * typeck.c (convert_arguments): Adjust convert_default_arg call. (dubious_conversion_warnings): New function, broken out of convert_for_assignment. (convert_for_assignment): Adjust. From-SVN: r32341
Diffstat (limited to 'gcc')
-rw-r--r--gcc/cp/ChangeLog19
-rw-r--r--gcc/cp/call.c58
-rw-r--r--gcc/cp/cp-tree.h3
-rw-r--r--gcc/cp/typeck.c90
4 files changed, 111 insertions, 59 deletions
diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog
index b97b555..2213278 100644
--- a/gcc/cp/ChangeLog
+++ b/gcc/cp/ChangeLog
@@ -1,3 +1,22 @@
+2000-03-05 Nathan Sidwell <nathan@codesourcery.com>
+
+ * call.c (convert_like): Macrofy.
+ (convert_like_with_context): New macro.
+ (convert_like_real): Renamed from convert_like. Add calling
+ context parameters, for diagnostics. Add recursive flag. Call
+ dubious_conversion_warnings for outer conversion.
+ (build_user_type_conversion): Use convert_like_with_context.
+ (build_over_call): Likewise. Don't warn about dubious
+ conversions here. Adjust convert_default_arg calls.
+ (convert_default_arg): Add context parameters for diagnostics.
+ Pass throught to convert_like_with_context.
+ * cp-tree.h (convert_default_arg): Add context parameters.
+ (dubious_conversion_warnings): Prototype new function.
+ * typeck.c (convert_arguments): Adjust convert_default_arg call.
+ (dubious_conversion_warnings): New function, broken
+ out of convert_for_assignment.
+ (convert_for_assignment): Adjust.
+
2000-03-03 Jason Merrill <jason@casey.cygnus.com>
* decl2.c (key_method): Break out from...
diff --git a/gcc/cp/call.c b/gcc/cp/call.c
index 72c4ccb..0589cfd 100644
--- a/gcc/cp/call.c
+++ b/gcc/cp/call.c
@@ -49,7 +49,9 @@ static int equal_functions PARAMS ((tree, tree));
static int joust PARAMS ((struct z_candidate *, struct z_candidate *, int));
static int compare_ics PARAMS ((tree, tree));
static tree build_over_call PARAMS ((struct z_candidate *, tree, int));
-static tree convert_like PARAMS ((tree, tree));
+#define convert_like(CONV, EXPR) convert_like_real (CONV, EXPR, NULL_TREE, 0, 0)
+#define convert_like_with_context(CONV, EXPR, FN, ARGNO) convert_like_real (CONV, EXPR, FN, ARGNO, 0)
+static tree convert_like_real PARAMS ((tree, tree, tree, int, int));
static void op_error PARAMS ((enum tree_code, enum tree_code, tree, tree,
tree, const char *));
static tree build_object_call PARAMS ((tree, tree));
@@ -2450,7 +2452,9 @@ build_user_type_conversion (totype, expr, flags)
{
if (TREE_CODE (cand->second_conv) == AMBIG_CONV)
return error_mark_node;
- return convert_from_reference (convert_like (cand->second_conv, expr));
+ return convert_from_reference
+ (convert_like_with_context
+ (cand->second_conv, expr, cand->fn, 0));
}
return NULL_TREE;
}
@@ -2654,7 +2658,8 @@ build_object_call (obj, args)
&& DECL_NAME (cand->fn) == ansi_opname [CALL_EXPR])
return build_over_call (cand, mem_args, LOOKUP_NORMAL);
- obj = convert_like (TREE_VEC_ELT (cand->convs, 0), obj);
+ obj = convert_like_with_context
+ (TREE_VEC_ELT (cand->convs, 0), obj, cand->fn, -1);
/* FIXME */
return build_function_call (obj, args);
@@ -3593,11 +3598,17 @@ enforce_access (basetype_path, decl)
return 1;
}
-/* Perform the conversions in CONVS on the expression EXPR. */
+/* Perform the conversions in CONVS on the expression EXPR.
+ FN and ARGNUM are used for diagnostics. ARGNUM is zero based, -1
+ indicates the `this' argument of a method. INNER is non-zero when
+ being called to continue a conversion chain. */
static tree
-convert_like (convs, expr)
+convert_like_real (convs, expr, fn, argnum, inner)
tree convs, expr;
+ tree fn;
+ int argnum;
+ int inner;
{
if (ICS_BAD_FLAG (convs)
&& TREE_CODE (convs) != USER_CONV
@@ -3609,19 +3620,22 @@ convert_like (convs, expr)
{
if (TREE_CODE (t) == USER_CONV)
{
- expr = convert_like (t, expr);
+ expr = convert_like_real (t, expr, fn, argnum, 1);
break;
}
else if (TREE_CODE (t) == AMBIG_CONV)
- return convert_like (t, expr);
+ return convert_like_real (t, expr, fn, argnum, 1);
else if (TREE_CODE (t) == IDENTITY_CONV)
break;
}
return convert_for_initialization
(NULL_TREE, TREE_TYPE (convs), expr, LOOKUP_NORMAL,
- "conversion", NULL_TREE, 0);
+ "conversion", fn, argnum);
}
-
+
+ if (!inner)
+ expr = dubious_conversion_warnings
+ (TREE_TYPE (convs), expr, "argument", fn, argnum);
switch (TREE_CODE (convs))
{
case USER_CONV:
@@ -3665,7 +3679,7 @@ convert_like (convs, expr)
break;
};
- expr = convert_like (TREE_OPERAND (convs, 0), expr);
+ expr = convert_like_real (TREE_OPERAND (convs, 0), expr, fn, argnum, 1);
if (expr == error_mark_node)
return error_mark_node;
@@ -3840,10 +3854,11 @@ convert_type_from_ellipsis (type)
conversions. Return the converted value. */
tree
-convert_default_arg (type, arg, fn)
+convert_default_arg (type, arg, fn, parmnum)
tree type;
tree arg;
tree fn;
+ int parmnum;
{
if (fn && DECL_TEMPLATE_INFO (fn))
arg = tsubst_default_argument (fn, type, arg);
@@ -3854,7 +3869,7 @@ convert_default_arg (type, arg, fn)
{
arg = digest_init (type, arg, 0);
arg = convert_for_initialization (0, type, arg, LOOKUP_NORMAL,
- "default argument", 0, 0);
+ "default argument", fn, parmnum);
}
else
{
@@ -3863,7 +3878,7 @@ convert_default_arg (type, arg, fn)
arg = copy_node (arg);
arg = convert_for_initialization (0, type, arg, LOOKUP_NORMAL,
- "default argument", 0, 0);
+ "default argument", fn, parmnum);
if (PROMOTE_PROTOTYPES
&& (TREE_CODE (type) == INTEGER_TYPE
|| TREE_CODE (type) == ENUMERAL_TYPE)
@@ -3956,7 +3971,7 @@ build_over_call (cand, args, flags)
if (TREE_CODE (t) == USER_CONV
|| TREE_CODE (t) == AMBIG_CONV)
{
- val = convert_like (t, val);
+ val = convert_like_with_context (t, val, fn, i - is_method);
break;
}
else if (TREE_CODE (t) == IDENTITY_CONV)
@@ -3964,16 +3979,13 @@ build_over_call (cand, args, flags)
}
val = convert_for_initialization
(NULL_TREE, type, val, LOOKUP_NORMAL,
- "argument passing", fn, i - is_method);
+ "argument", fn, i - is_method);
}
else
{
- /* Issue warnings about peculiar, but legal, uses of NULL. */
- if (ARITHMETIC_TYPE_P (TREE_VALUE (parm))
- && TREE_VALUE (arg) == null_node)
- cp_warning ("converting NULL to non-pointer type");
-
- val = convert_like (conv, TREE_VALUE (arg));
+ val = TREE_VALUE (arg);
+ val = convert_like_with_context
+ (conv, TREE_VALUE (arg), fn, i - is_method);
}
if (PROMOTE_PROTOTYPES
@@ -3985,12 +3997,12 @@ build_over_call (cand, args, flags)
}
/* Default arguments */
- for (; parm && parm != void_list_node; parm = TREE_CHAIN (parm))
+ for (; parm && parm != void_list_node; parm = TREE_CHAIN (parm), i++)
converted_args
= tree_cons (NULL_TREE,
convert_default_arg (TREE_VALUE (parm),
TREE_PURPOSE (parm),
- fn),
+ fn, i - is_method),
converted_args);
/* Ellipsis */
diff --git a/gcc/cp/cp-tree.h b/gcc/cp/cp-tree.h
index ce2b94c..9086292 100644
--- a/gcc/cp/cp-tree.h
+++ b/gcc/cp/cp-tree.h
@@ -3616,7 +3616,7 @@ extern tree build_op_delete_call PARAMS ((enum tree_code, tree, tree, int, tree
extern int can_convert PARAMS ((tree, tree));
extern int can_convert_arg PARAMS ((tree, tree, tree));
extern int enforce_access PARAMS ((tree, tree));
-extern tree convert_default_arg PARAMS ((tree, tree, tree));
+extern tree convert_default_arg PARAMS ((tree, tree, tree, int));
extern tree convert_arg_to_ellipsis PARAMS ((tree));
extern tree build_x_va_arg PARAMS ((tree, tree));
extern tree convert_type_from_ellipsis PARAMS ((tree));
@@ -4407,6 +4407,7 @@ extern tree build_const_cast PARAMS ((tree, tree));
extern tree build_c_cast PARAMS ((tree, tree));
extern tree build_x_modify_expr PARAMS ((tree, enum tree_code, tree));
extern tree build_modify_expr PARAMS ((tree, enum tree_code, tree));
+extern tree dubious_conversion_warnings PARAMS ((tree, tree, const char *, tree, int));
extern tree convert_for_initialization PARAMS ((tree, tree, tree, int, const char *, tree, int));
extern void c_expand_asm_operands PARAMS ((tree, tree, tree, tree, int, char *, int));
extern void c_expand_return PARAMS ((tree));
diff --git a/gcc/cp/typeck.c b/gcc/cp/typeck.c
index 400d930..219ca39 100644
--- a/gcc/cp/typeck.c
+++ b/gcc/cp/typeck.c
@@ -3215,7 +3215,7 @@ convert_arguments (typelist, values, fndecl, flags)
tree parmval
= convert_default_arg (TREE_VALUE (typetail),
TREE_PURPOSE (typetail),
- fndecl);
+ fndecl, i);
if (parmval == error_mark_node)
return error_mark_node;
@@ -6421,6 +6421,59 @@ pfn_from_ptrmemfunc (t)
pfn_identifier, NULL_TREE, 0));
}
+/* Expression EXPR is about to be implicitly converted to TYPE. Warn
+ if this is a potentially dangerous thing to do. Returns a possibly
+ marked EXPR. */
+
+tree
+dubious_conversion_warnings (type, expr, errtype, fndecl, parmnum)
+ tree type;
+ tree expr;
+ const char *errtype;
+ tree fndecl;
+ int parmnum;
+{
+ /* Issue warnings about peculiar, but legal, uses of NULL. */
+ if (ARITHMETIC_TYPE_P (type) && expr == null_node)
+ {
+ if (fndecl)
+ cp_warning ("passing NULL used for non-pointer %s %P of `%D'",
+ errtype, parmnum, fndecl);
+ else
+ cp_warning ("%s to non-pointer type `%T' from NULL", errtype, type);
+ }
+
+ /* Warn about assigning a floating-point type to an integer type. */
+ if (TREE_CODE (TREE_TYPE (expr)) == REAL_TYPE
+ && TREE_CODE (type) == INTEGER_TYPE)
+ {
+ if (fndecl)
+ cp_warning ("passing `%T' for %s %P of `%D'",
+ TREE_TYPE (expr), errtype, parmnum, fndecl);
+ else
+ cp_warning ("%s to `%T' from `%T'", errtype, type, TREE_TYPE (expr));
+ }
+ /* And warn about assigning a negative value to an unsigned
+ variable. */
+ else if (TREE_UNSIGNED (type) && TREE_CODE (type) != BOOLEAN_TYPE)
+ {
+ if (TREE_CODE (expr) == INTEGER_CST
+ && TREE_NEGATED_INT (expr))
+ {
+ if (fndecl)
+ cp_warning ("passing negative value `%E' for %s %P of `%D'",
+ expr, errtype, parmnum, fndecl);
+ else
+ cp_warning ("%s of negative value `%E' to `%T'",
+ errtype, expr, type);
+ }
+ overflow_warning (expr);
+ if (TREE_CONSTANT (expr))
+ expr = fold (expr);
+ }
+ return expr;
+}
+
/* Convert value RHS to type TYPE as preparation for an assignment to
an lvalue of type TYPE. ERRTYPE is a string to use in error
messages: "assignment", "return", etc. If FNDECL is non-NULL, we
@@ -6456,12 +6509,7 @@ convert_for_assignment (type, rhs, errtype, fndecl, parmnum)
if (TREE_CODE (rhs) == TREE_LIST && TREE_VALUE (rhs) == error_mark_node)
return error_mark_node;
- /* Issue warnings about peculiar, but legal, uses of NULL. We
- do this *before* the call to decl_constant_value so as to
- avoid duplicate warnings on code like `const int I = NULL;
- f(I);'. */
- if (ARITHMETIC_TYPE_P (type) && rhs == null_node)
- cp_warning ("converting NULL to non-pointer type");
+ rhs = dubious_conversion_warnings (type, rhs, errtype, fndecl, parmnum);
/* The RHS of an assignment cannot have void type. */
if (coder == VOID_TYPE)
@@ -6476,34 +6524,6 @@ convert_for_assignment (type, rhs, errtype, fndecl, parmnum)
else if (TREE_READONLY_DECL_P (rhs))
rhs = decl_constant_value (rhs);
- /* Warn about assigning a floating-point type to an integer type. */
- if (coder == REAL_TYPE && codel == INTEGER_TYPE)
- {
- if (fndecl)
- cp_warning ("`%T' used for argument %P of `%D'",
- rhstype, parmnum, fndecl);
- else
- cp_warning ("%s to `%T' from `%T'", errtype, type, rhstype);
- }
- /* And warn about assigning a negative value to an unsigned
- variable. */
- else if (TREE_UNSIGNED (type) && codel != BOOLEAN_TYPE)
- {
- if (TREE_CODE (rhs) == INTEGER_CST
- && TREE_NEGATED_INT (rhs))
- {
- if (fndecl)
- cp_warning ("negative value `%E' passed as argument %P of `%D'",
- rhs, parmnum, fndecl);
- else
- cp_warning ("%s of negative value `%E' to `%T'",
- errtype, rhs, type);
- }
- overflow_warning (rhs);
- if (TREE_CONSTANT (rhs))
- rhs = fold (rhs);
- }
-
/* [expr.ass]
The expression is implicitly converted (clause _conv_) to the