diff options
Diffstat (limited to 'gcc')
-rw-r--r-- | gcc/ChangeLog | 15 | ||||
-rw-r--r-- | gcc/builtin-attrs.def | 45 | ||||
-rw-r--r-- | gcc/c-format.c | 5 | ||||
-rw-r--r-- | gcc/testsuite/gcc.dg/format/null-1.c | 27 |
4 files changed, 70 insertions, 22 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index e5f063f..83b976d 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,18 @@ +2002-05-23 Jason Thorpe <thorpej@wasabisystems.com> + + * builtin-attrs.def: Update copyright years. + (ATTR_NONNULL): New attribute identifier. + (ATTR_NONNULL_1, ATTR_NONNULL_2, ATTR_NONNULL_3): New + attribute tree lists. + (DEF_FORMAT_ATTRIBUTE): Chain a nonnull attribute for the + format operand. + (ATTR_FORMAT_ARG_1, ATTR_FORMAT_ARG_2): Use... + (DEF_FORMAT_ARG_ATTRIBUTE): ...this to generate format_arg + attribute lists. Chain the appropriate nonnull attribute. + * c-format.c (check_format_arg): Remove null format string + warning. + * testsuite/gcc.dg/format/null-1.c: New test. + 2002-05-23 Rainer Orth <ro@TechFak.Uni-Bielefeld.DE> * Makefile.in (ADAC): Define. diff --git a/gcc/builtin-attrs.def b/gcc/builtin-attrs.def index 10b3708..56081d1 100644 --- a/gcc/builtin-attrs.def +++ b/gcc/builtin-attrs.def @@ -1,4 +1,4 @@ -/* Copyright (C) 2001 Free Software Foundation, Inc. +/* Copyright (C) 2001, 2002 Free Software Foundation, Inc. Contributed by Joseph Myers <jsm28@cam.ac.uk>. This file is part of GCC. @@ -85,28 +85,39 @@ DEF_ATTR_IDENT (ATTR_STRFMON, "strfmon") DEF_ATTR_IDENT (ATTR_FORMAT, "format") DEF_ATTR_IDENT (ATTR_FORMAT_ARG, "format_arg") +DEF_ATTR_IDENT (ATTR_NONNULL, "nonnull") + +DEF_ATTR_TREE_LIST (ATTR_NONNULL_1, ATTR_NONNULL, ATTR_LIST_1, ATTR_NULL) +DEF_ATTR_TREE_LIST (ATTR_NONNULL_2, ATTR_NONNULL, ATTR_LIST_2, ATTR_NULL) +DEF_ATTR_TREE_LIST (ATTR_NONNULL_3, ATTR_NONNULL, ATTR_LIST_3, ATTR_NULL) + /* Construct a tree for a format attribute. */ -#define DEF_FORMAT_ATTRIBUTE(TYPE, VALUES) \ +#define DEF_FORMAT_ATTRIBUTE(TYPE, FA, VALUES) \ DEF_ATTR_TREE_LIST (CONCAT4 (ATTR_,TYPE,_,VALUES), ATTR_NULL, \ CONCAT2 (ATTR_,TYPE), CONCAT2 (ATTR_LIST_,VALUES)) \ DEF_ATTR_TREE_LIST (CONCAT4 (ATTR_FORMAT_,TYPE,_,VALUES), ATTR_FORMAT, \ - CONCAT4 (ATTR_,TYPE,_,VALUES), ATTR_NULL) -DEF_FORMAT_ATTRIBUTE(PRINTF,1_0) -DEF_FORMAT_ATTRIBUTE(PRINTF,1_2) -DEF_FORMAT_ATTRIBUTE(PRINTF,2_0) -DEF_FORMAT_ATTRIBUTE(PRINTF,2_3) -DEF_FORMAT_ATTRIBUTE(PRINTF,3_0) -DEF_FORMAT_ATTRIBUTE(PRINTF,3_4) -DEF_FORMAT_ATTRIBUTE(SCANF,1_0) -DEF_FORMAT_ATTRIBUTE(SCANF,1_2) -DEF_FORMAT_ATTRIBUTE(SCANF,2_0) -DEF_FORMAT_ATTRIBUTE(SCANF,2_3) -DEF_FORMAT_ATTRIBUTE(STRFTIME,3_0) -DEF_FORMAT_ATTRIBUTE(STRFMON,3_4) + CONCAT4 (ATTR_,TYPE,_,VALUES), CONCAT2 (ATTR_NONNULL_,FA)) +DEF_FORMAT_ATTRIBUTE(PRINTF,1,1_0) +DEF_FORMAT_ATTRIBUTE(PRINTF,1,1_2) +DEF_FORMAT_ATTRIBUTE(PRINTF,2,2_0) +DEF_FORMAT_ATTRIBUTE(PRINTF,2,2_3) +DEF_FORMAT_ATTRIBUTE(PRINTF,3,3_0) +DEF_FORMAT_ATTRIBUTE(PRINTF,3,3_4) +DEF_FORMAT_ATTRIBUTE(SCANF,1,1_0) +DEF_FORMAT_ATTRIBUTE(SCANF,1,1_2) +DEF_FORMAT_ATTRIBUTE(SCANF,2,2_0) +DEF_FORMAT_ATTRIBUTE(SCANF,2,2_3) +DEF_FORMAT_ATTRIBUTE(STRFTIME,3,3_0) +DEF_FORMAT_ATTRIBUTE(STRFMON,3,3_4) #undef DEF_FORMAT_ATTRIBUTE -DEF_ATTR_TREE_LIST (ATTR_FORMAT_ARG_1, ATTR_FORMAT_ARG, ATTR_LIST_1, ATTR_NULL) -DEF_ATTR_TREE_LIST (ATTR_FORMAT_ARG_2, ATTR_FORMAT_ARG, ATTR_LIST_2, ATTR_NULL) +/* Construct a tree for a format_arg attribute. */ +#define DEF_FORMAT_ARG_ATTRIBUTE(FA) \ + DEF_ATTR_TREE_LIST (CONCAT2 (ATTR_FORMAT_ARG_,FA), ATTR_FORMAT_ARG, \ + CONCAT2 (ATTR_LIST_,FA), CONCAT2 (ATTR_NONNULL_,FA)) +DEF_FORMAT_ARG_ATTRIBUTE(1) +DEF_FORMAT_ARG_ATTRIBUTE(2) +#undef DEF_FORMAT_ARG_ATTRIBUTE /* Define an attribute for a function, along with the IDENTIFIER_NODE. */ #define DEF_FN_ATTR_IDENT(NAME, ATTRS, PREDICATE) \ diff --git a/gcc/c-format.c b/gcc/c-format.c index b3640c5..7e8b137 100644 --- a/gcc/c-format.c +++ b/gcc/c-format.c @@ -1418,11 +1418,6 @@ check_format_arg (ctx, format_tree, arg_num) if (integer_zerop (format_tree)) { - /* FIXME: instead of warning about a null format string here, - functions for which we want to perform this check should be - marked with the "nonnull" attribute on the appropriate arguments. */ - status_warning (status, "null format string"); - /* Skip to first argument to check, so we can see if this format has any arguments (it shouldn't). */ while (arg_num + 1 < info->first_arg_num) diff --git a/gcc/testsuite/gcc.dg/format/null-1.c b/gcc/testsuite/gcc.dg/format/null-1.c new file mode 100644 index 0000000..63501a39 --- /dev/null +++ b/gcc/testsuite/gcc.dg/format/null-1.c @@ -0,0 +1,27 @@ +/* Test for some aspects of null format string handling. */ +/* Origin: Jason Thorpe <thorpej@wasabisystems.com> */ +/* { dg-do compile } */ +/* { dg-options "-std=gnu99 -Wformat" } */ + +#include "format.h" + +extern void my_printf (const char *, ...) __attribute__((format(printf,1,2))); +extern const char *my_format (const char *, const char *) + __attribute__((format_arg(2))); + +void +foo (int i1) +{ + /* Warning about a null format string has been decoupled from the actual + format check. However, we still expect to be warned about any excess + arguments after a null format string. */ + my_printf (NULL); + my_printf (NULL, i1); /* { dg-warning "too many" "null format with arguments" } */ + + my_printf (my_format ("", NULL)); + my_printf (my_format ("", NULL), i1); /* { dg-warning "too many" "null format_arg with arguments" } */ + + /* While my_printf allows a null argument, dgettext does not, so we expect + a null argument warning here. */ + my_printf (dgettext ("", NULL)); /* { dg-warning "null" "null format with dgettext" } */ +} |