diff options
author | Joseph Myers <jsm@polyomino.org.uk> | 2004-10-06 23:16:29 +0100 |
---|---|---|
committer | Joseph Myers <jsm28@gcc.gnu.org> | 2004-10-06 23:16:29 +0100 |
commit | 03dafa610868e97f890319ff7d7ee64a227132b2 (patch) | |
tree | ff95ee85f5ed2d17d86ce971abc3122aa4733e9f | |
parent | 75917fc03241362a4e81490273c6d4c445183817 (diff) | |
download | gcc-03dafa610868e97f890319ff7d7ee64a227132b2.zip gcc-03dafa610868e97f890319ff7d7ee64a227132b2.tar.gz gcc-03dafa610868e97f890319ff7d7ee64a227132b2.tar.bz2 |
c-typeck.c (convert_arguments): Take expression for called function rather than its name.
* c-typeck.c (convert_arguments): Take expression for called
function rather than its name. Handle ObjC selectors directly
rather than relying on warn_for_assignment to do so. Call warning
directly rather than warn_for_assignment. Use %qE in diagnostics.
Say "argument" rather than "arg" in diagnostics.
(build_function_call): Update call to convert_arguments.
testsuite:
* gcc.dg/Wconversion-2.c, gcc.dg/func-args-1.c: New tests.
From-SVN: r88630
-rw-r--r-- | gcc/ChangeLog | 9 | ||||
-rw-r--r-- | gcc/c-typeck.c | 82 | ||||
-rw-r--r-- | gcc/testsuite/ChangeLog | 4 | ||||
-rw-r--r-- | gcc/testsuite/gcc.dg/Wconversion-2.c | 64 | ||||
-rw-r--r-- | gcc/testsuite/gcc.dg/func-args-1.c | 53 |
5 files changed, 185 insertions, 27 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 6ed9e99..d05f93d 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,12 @@ +2004-10-06 Joseph S. Myers <jsm@polyomino.org.uk> + + * c-typeck.c (convert_arguments): Take expression for called + function rather than its name. Handle ObjC selectors directly + rather than relying on warn_for_assignment to do so. Call warning + directly rather than warn_for_assignment. Use %qE in diagnostics. + Say "argument" rather than "arg" in diagnostics. + (build_function_call): Update call to convert_arguments. + 2004-10-06 Andrew Pinski <pinskia@physics.uc.edu> PR debug/17787 diff --git a/gcc/c-typeck.c b/gcc/c-typeck.c index 27c8cd4..6d77233 100644 --- a/gcc/c-typeck.c +++ b/gcc/c-typeck.c @@ -1976,7 +1976,7 @@ build_function_call (tree function, tree params) function prototype, or apply default promotions. */ coerced_params - = convert_arguments (TYPE_ARG_TYPES (fntype), params, name, fundecl); + = convert_arguments (TYPE_ARG_TYPES (fntype), params, function, fundecl); /* Check that the arguments to the function are valid. */ @@ -2014,7 +2014,8 @@ build_function_call (tree function, tree params) It may be 0, if that info is not available. It is used only for generating error messages. - NAME is an IDENTIFIER_NODE or 0. It is used only for error messages. + FUNCTION is a tree for the called function. It is used only for + error messages, where it is formatted with %qE. This is also where warnings about wrong number of args are generated. @@ -2022,11 +2023,25 @@ build_function_call (tree function, tree params) with the elements of the list in the TREE_VALUE slots of those nodes. */ static tree -convert_arguments (tree typelist, tree values, tree name, tree fundecl) +convert_arguments (tree typelist, tree values, tree function, tree fundecl) { tree typetail, valtail; tree result = NULL; int parmnum; + tree selector; + tree name = NULL_TREE; + + /* Determine the function name for the use of convert_for_assignment + and warn_for_assignment called from there. */ + if (TREE_CODE (function) == ADDR_EXPR + && TREE_CODE (TREE_OPERAND (function, 0)) == FUNCTION_DECL) + { + function = TREE_OPERAND (function, 0); + name = DECL_NAME (function); + } + + /* Handle an ObjC selector specially for diagnostics. */ + selector = objc_message_selector (); /* Scan the given expressions and types, producing individual converted arguments and pushing them on RESULT in reverse order. */ @@ -2037,17 +2052,21 @@ convert_arguments (tree typelist, tree values, tree name, tree fundecl) { tree type = typetail ? TREE_VALUE (typetail) : 0; tree val = TREE_VALUE (valtail); + tree rname = function; + int argnum = parmnum + 1; if (type == void_type_node) { - if (name) - error ("too many arguments to function %qs", - IDENTIFIER_POINTER (name)); - else - error ("too many arguments to function"); + error ("too many arguments to function %qE", function); break; } + if (selector && argnum > 2) + { + rname = selector; + argnum -= 2; + } + /* Strip NON_LVALUE_EXPRs since we aren't using as an lvalue. */ /* Do not use STRIP_NOPS here! We do not want an enumerator with value 0 to convert automatically to a pointer. */ @@ -2078,22 +2097,34 @@ convert_arguments (tree typelist, tree values, tree name, tree fundecl) if (INTEGRAL_TYPE_P (type) && TREE_CODE (TREE_TYPE (val)) == REAL_TYPE) - warn_for_assignment ("%s as integer rather than floating due to prototype", (char *) 0, name, parmnum + 1); + warning ("passing argument %d of %qE as integer " + "rather than floating due to prototype", + argnum, rname); if (INTEGRAL_TYPE_P (type) && TREE_CODE (TREE_TYPE (val)) == COMPLEX_TYPE) - warn_for_assignment ("%s as integer rather than complex due to prototype", (char *) 0, name, parmnum + 1); + warning ("passing argument %d of %qE as integer " + "rather than complex due to prototype", + argnum, rname); else if (TREE_CODE (type) == COMPLEX_TYPE && TREE_CODE (TREE_TYPE (val)) == REAL_TYPE) - warn_for_assignment ("%s as complex rather than floating due to prototype", (char *) 0, name, parmnum + 1); + warning ("passing argument %d of %qE as complex " + "rather than floating due to prototype", + argnum, rname); else if (TREE_CODE (type) == REAL_TYPE && INTEGRAL_TYPE_P (TREE_TYPE (val))) - warn_for_assignment ("%s as floating rather than integer due to prototype", (char *) 0, name, parmnum + 1); + warning ("passing argument %d of %qE as floating " + "rather than integer due to prototype", + argnum, rname); else if (TREE_CODE (type) == COMPLEX_TYPE && INTEGRAL_TYPE_P (TREE_TYPE (val))) - warn_for_assignment ("%s as complex rather than integer due to prototype", (char *) 0, name, parmnum + 1); + warning ("passing argument %d of %qE as complex " + "rather than integer due to prototype", + argnum, rname); else if (TREE_CODE (type) == REAL_TYPE && TREE_CODE (TREE_TYPE (val)) == COMPLEX_TYPE) - warn_for_assignment ("%s as floating rather than complex due to prototype", (char *) 0, name, parmnum + 1); + warning ("passing argument %d of %qE as floating " + "rather than complex due to prototype", + argnum, rname); /* ??? At some point, messages should be written about conversions between complex types, but that's too messy to do now. */ @@ -2103,9 +2134,9 @@ convert_arguments (tree typelist, tree values, tree name, tree fundecl) /* Warn if any argument is passed as `float', since without a prototype it would be `double'. */ if (formal_prec == TYPE_PRECISION (float_type_node)) - warn_for_assignment ("%s as %<float%> rather than " - "%<double%> due to prototype", - (char *) 0, name, parmnum + 1); + warning ("passing argument %d of %qE as %<float%> " + "rather than %<double%> due to prototype", + argnum, rname); } /* Detect integer changing in width or signedness. These warnings are only activated with @@ -2123,7 +2154,8 @@ convert_arguments (tree typelist, tree values, tree name, tree fundecl) and the actual arg is that enum type. */ ; else if (formal_prec != TYPE_PRECISION (type1)) - warn_for_assignment ("%s with different width due to prototype", (char *) 0, name, parmnum + 1); + warning ("passing argument %d of %qE with different " + "width due to prototype", argnum, rname); else if (TYPE_UNSIGNED (type) == TYPE_UNSIGNED (type1)) ; /* Don't complain if the formal parameter type @@ -2149,9 +2181,11 @@ convert_arguments (tree typelist, tree values, tree name, tree fundecl) && TYPE_UNSIGNED (TREE_TYPE (val))) ; else if (TYPE_UNSIGNED (type)) - warn_for_assignment ("%s as unsigned due to prototype", (char *) 0, name, parmnum + 1); + warning ("passing argument %d of %qE as unsigned " + "due to prototype", argnum, rname); else - warn_for_assignment ("%s as signed due to prototype", (char *) 0, name, parmnum + 1); + warning ("passing argument %d of %qE as signed " + "due to prototype", argnum, rname); } } @@ -2180,13 +2214,7 @@ convert_arguments (tree typelist, tree values, tree name, tree fundecl) } if (typetail != 0 && TREE_VALUE (typetail) != void_type_node) - { - if (name) - error ("too few arguments to function %qs", - IDENTIFIER_POINTER (name)); - else - error ("too few arguments to function"); - } + error ("too few arguments to function %qE", function); return nreverse (result); } diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 8e23309..b867e20 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,7 @@ +2004-10-06 Joseph S. Myers <jsm@polyomino.org.uk> + + * gcc.dg/Wconversion-2.c, gcc.dg/func-args-1.c: New tests. + 2004-10-06 Andrew Pinski <pinskia@physics.uc.edu> PR c++/17368 diff --git a/gcc/testsuite/gcc.dg/Wconversion-2.c b/gcc/testsuite/gcc.dg/Wconversion-2.c new file mode 100644 index 0000000..320f41f --- /dev/null +++ b/gcc/testsuite/gcc.dg/Wconversion-2.c @@ -0,0 +1,64 @@ +/* Test messages for -Wconversion, including that they are not + pedwarns. */ +/* Origin: Joseph Myers <jsm@polyomino.org.uk> */ +/* { dg-do compile } */ +/* { dg-options "-std=c99 -pedantic-errors -Wconversion" } */ + +void fsc(signed char); +void fsi(signed int); +void fsll(signed long long); +void fuc(unsigned char); +void fui(unsigned int); +void full(unsigned long long); +void ff(float); +void fld(long double); +void fcf(_Complex float); + +struct s { + void (*fsc)(signed char); + void (*fsi)(signed int); + void (*fsll)(signed long long); + void (*fuc)(unsigned char); + void (*fui)(unsigned int); + void (*full)(unsigned long long); + void (*ff)(float); + void (*fld)(long double); + void (*fcf)(_Complex float); +} x; + +signed char sc; +signed int si; +signed long long sll; +unsigned char uc; +unsigned int ui; +unsigned long long ull; +float f; +long double ld; +_Complex float cf; + +void +g (void) +{ + fsi(f); /* { dg-warning "warning: passing argument 1 of 'fsi' as integer rather than floating due to prototype" } */ + x.fsi(f); /* { dg-warning "warning: passing argument 1 of 'x.fsi' as integer rather than floating due to prototype" } */ + fsi(cf); /* { dg-warning "warning: passing argument 1 of 'fsi' as integer rather than complex due to prototype" } */ + x.fsi(cf); /* { dg-warning "warning: passing argument 1 of 'x.fsi' as integer rather than complex due to prototype" } */ + fcf(f); /* { dg-warning "warning: passing argument 1 of 'fcf' as complex rather than floating due to prototype" } */ + x.fcf(f); /* { dg-warning "warning: passing argument 1 of 'x.fcf' as complex rather than floating due to prototype" } */ + fcf(si); /* { dg-warning "warning: passing argument 1 of 'fcf' as complex rather than integer due to prototype" } */ + x.fcf(si); /* { dg-warning "warning: passing argument 1 of 'x.fcf' as complex rather than integer due to prototype" } */ + ff(sc); /* { dg-warning "warning: passing argument 1 of 'ff' as floating rather than integer due to prototype" } */ + x.ff(sc); /* { dg-warning "warning: passing argument 1 of 'x.ff' as floating rather than integer due to prototype" } */ + ff(cf); /* { dg-warning "warning: passing argument 1 of 'ff' as floating rather than complex due to prototype" } */ + x.ff(cf); /* { dg-warning "warning: passing argument 1 of 'x.ff' as floating rather than complex due to prototype" } */ + ff(1.0); /* { dg-warning "warning: passing argument 1 of 'ff' as 'float' rather than 'double' due to prototype" } */ + x.ff(1.0); /* { dg-warning "warning: passing argument 1 of 'x.ff' as 'float' rather than 'double' due to prototype" } */ + fsll(sc); /* { dg-warning "warning: passing argument 1 of 'fsll' with different width due to prototype" } */ + x.fsll(sc); /* { dg-warning "warning: passing argument 1 of 'x.fsll' with different width due to prototype" } */ + fsc(sll); /* { dg-warning "warning: passing argument 1 of 'fsc' with different width due to prototype" } */ + x.fsc(sll); /* { dg-warning "warning: passing argument 1 of 'x.fsc' with different width due to prototype" } */ + fsi(ui); /* { dg-warning "warning: passing argument 1 of 'fsi' as signed due to prototype" } */ + x.fsi(ui); /* { dg-warning "warning: passing argument 1 of 'x.fsi' as signed due to prototype" } */ + full(sll); /* { dg-warning "warning: passing argument 1 of 'full' as unsigned due to prototype" } */ + x.full(sll); /* { dg-warning "warning: passing argument 1 of 'x.full' as unsigned due to prototype" } */ +} diff --git a/gcc/testsuite/gcc.dg/func-args-1.c b/gcc/testsuite/gcc.dg/func-args-1.c new file mode 100644 index 0000000..306a5df --- /dev/null +++ b/gcc/testsuite/gcc.dg/func-args-1.c @@ -0,0 +1,53 @@ +/* Test messages for wrong number of arguments to function. */ +/* Origin: Joseph Myers <jsm@polyomino.org.uk> */ +/* { dg-do compile } */ +/* { dg-options "" } */ + +void f0(void); +void f1(int); +void f1v(int, ...); +void f2(int, int); +void f2v(int, int, ...); + +struct s { + void (*f0)(void); + void (*f1)(int); + void (*f1v)(int, ...); + void (*f2)(int, int); + void (*f2v)(int, int, ...); +} x; + +void +g (int a) +{ + f0(); + x.f0(); + f0(a); /* { dg-error "error: too many arguments to function 'f0'" } */ + x.f0(a); /* { dg-error "error: too many arguments to function 'x.f0'" } */ + f0(a, a); /* { dg-error "error: too many arguments to function 'f0'" } */ + x.f0(a, a); /* { dg-error "error: too many arguments to function 'x.f0'" } */ + f1(); /* { dg-error "error: too few arguments to function 'f1'" } */ + x.f1(); /* { dg-error "error: too few arguments to function 'x.f1'" } */ + f1(a); + x.f1(a); + f1(a, a); /* { dg-error "error: too many arguments to function 'f1'" } */ + x.f1(a, a); /* { dg-error "error: too many arguments to function 'x.f1'" } */ + f1v(); /* { dg-error "error: too few arguments to function 'f1v'" } */ + x.f1v(); /* { dg-error "error: too few arguments to function 'x.f1v'" } */ + f1v(a); + x.f1v(a); + f1v(a, a); + x.f1v(a, a); + f2(a); /* { dg-error "error: too few arguments to function 'f2'" } */ + x.f2(a); /* { dg-error "error: too few arguments to function 'x.f2'" } */ + f2(a, a); + x.f2(a, a); + f2(a, a, a); /* { dg-error "error: too many arguments to function 'f2'" } */ + x.f2(a, a, a); /* { dg-error "error: too many arguments to function 'x.f2'" } */ + f2v(a); /* { dg-error "error: too few arguments to function 'f2v'" } */ + x.f2v(a); /* { dg-error "error: too few arguments to function 'x.f2v'" } */ + f2v(a, a); + x.f2v(a, a); + f2v(a, a, a); + x.f2v(a, a, a); +} |