diff options
author | Richard Guenther <rguenther@suse.de> | 2008-04-24 16:18:46 +0000 |
---|---|---|
committer | Richard Biener <rguenth@gcc.gnu.org> | 2008-04-24 16:18:46 +0000 |
commit | 833229510cb13aa643a6005f60882daec616e2b7 (patch) | |
tree | 35dd8b11788bce7a6dab65c4d291872b84068f45 /gcc/c-common.c | |
parent | 194ac52ab4a35f22abafaec46ac22ac303a61ab8 (diff) | |
download | gcc-833229510cb13aa643a6005f60882daec616e2b7.zip gcc-833229510cb13aa643a6005f60882daec616e2b7.tar.gz gcc-833229510cb13aa643a6005f60882daec616e2b7.tar.bz2 |
c-common.h (check_builtin_function_arguments): Declare.
2008-04-24 Richard Guenther <rguenther@suse.de>
* c-common.h (check_builtin_function_arguments): Declare.
* c-common.c (validate_nargs): New function.
(check_builtin_function_arguments): Likewise.
* c-typeck.c (build_function_call): Call
check_builtin_function_arguments.
* builtins.c (fold_builtin_classify): Remove error reporting code.
(fold_builtin_unordered_cmp): Likewise.
(fold_builtin_1): Likewise.
(fold_builtin_n): Likewise.
cp/
* typeck.c (cp_build_function_call): Call
check_builtin_function_arguments.
* gcc.dg/builtin-constant_p-1.c: New testcase.
* gcc.dg/builtin-errors.c: Adjust expected error.
From-SVN: r134635
Diffstat (limited to 'gcc/c-common.c')
-rw-r--r-- | gcc/c-common.c | 79 |
1 files changed, 79 insertions, 0 deletions
diff --git a/gcc/c-common.c b/gcc/c-common.c index 6db6f3e..36e1c3d 100644 --- a/gcc/c-common.c +++ b/gcc/c-common.c @@ -6631,6 +6631,85 @@ check_function_arguments_recurse (void (*callback) (*callback) (ctx, param, param_num); } +/* Checks the number of arguments NARGS against the required number + REQUIRED and issues an error if there is a mismatch. Returns true + if the number of arguments is correct, otherwise false. */ + +static bool +validate_nargs (tree fndecl, int nargs, int required) +{ + if (nargs < required) + { + error ("not enough arguments to function %qE", fndecl); + return false; + } + else if (nargs > required) + { + error ("too many arguments to function %qE", fndecl); + return false; + } + return true; +} + +/* Verifies the NARGS arguments ARGS to the builtin function FNDECL. + Returns false if there was an error, otherwise true. */ + +bool +check_builtin_function_arguments (tree fndecl, int nargs, tree *args) +{ + if (!DECL_BUILT_IN (fndecl) + || DECL_BUILT_IN_CLASS (fndecl) != BUILT_IN_NORMAL) + return true; + + switch (DECL_FUNCTION_CODE (fndecl)) + { + case BUILT_IN_CONSTANT_P: + return validate_nargs (fndecl, nargs, 1); + + case BUILT_IN_ISFINITE: + case BUILT_IN_ISINF: + case BUILT_IN_ISNAN: + case BUILT_IN_ISNORMAL: + if (validate_nargs (fndecl, nargs, 1)) + { + if (TREE_CODE (TREE_TYPE (args[0])) != REAL_TYPE) + { + error ("non-floating-point argument in call to " + "function %qE", fndecl); + return false; + } + return true; + } + return false; + + case BUILT_IN_ISGREATER: + case BUILT_IN_ISGREATEREQUAL: + case BUILT_IN_ISLESS: + case BUILT_IN_ISLESSEQUAL: + case BUILT_IN_ISLESSGREATER: + case BUILT_IN_ISUNORDERED: + if (validate_nargs (fndecl, nargs, 2)) + { + enum tree_code code0, code1; + code0 = TREE_CODE (TREE_TYPE (args[0])); + code1 = TREE_CODE (TREE_TYPE (args[1])); + if (!((code0 == REAL_TYPE && code1 == REAL_TYPE) + || (code0 == REAL_TYPE && code1 == INTEGER_TYPE) + || (code0 == INTEGER_TYPE && code1 == REAL_TYPE))) + { + error ("non-floating-point arguments in call to " + "function %qE", fndecl); + return false; + } + return true; + } + return false; + + default: + return true; + } +} + /* Function to help qsort sort FIELD_DECLs by name order. */ int |