Commit 26f943fd by Neil Booth Committed by Neil Booth

c-common.c (shadow_warning): New function, moved from cp/decl.c.

	* c-common.c (shadow_warning): New function, moved from cp/decl.c.
	* c-common.h (shadow_warning): New.
	* c-decl.c: Include c-common.h.
	(warn_if_shadowing): New, broken out of pushdecl.
	(pushdecl): Use warn_if_shadowing.
	(store_parm_decls): Prevent duplicate -Wshadow warnings.
cp:
	* decl.c: Include c-common.h.
	(shadow_warning): Move to c-common.c.
testsuite:
	* gcc.dg/Wshadow-1.c: New test.

From-SVN: r47701
parent 8ca8f9a7
2001-12-05 Neil Booth <neil@daikokuya.demon.co.uk>
* c-common.c (shadow_warning): New function, moved from cp/decl.c.
* c-common.h (shadow_warning): New.
* c-decl.c: Include c-common.h.
(warn_if_shadowing): New, broken out of pushdecl.
(pushdecl): Use warn_if_shadowing.
(store_parm_decls): Prevent duplicate -Wshadow warnings.
Wed Dec 5 17:59:19 2001 Douglas B. Rupp <rupp@gnat.com> Wed Dec 5 17:59:19 2001 Douglas B. Rupp <rupp@gnat.com>
* config/alpha/vms.h (SIZE_TYPE, PTRDIFF_TYPE): Remove, were disabled. * config/alpha/vms.h (SIZE_TYPE, PTRDIFF_TYPE): Remove, were disabled.
......
...@@ -4017,3 +4017,17 @@ c_common_insert_default_attributes (decl) ...@@ -4017,3 +4017,17 @@ c_common_insert_default_attributes (decl)
#undef DEF_ATTR_TREE_LIST #undef DEF_ATTR_TREE_LIST
#undef DEF_FN_ATTR #undef DEF_FN_ATTR
} }
/* Output a -Wshadow warning MSGID about NAME, an IDENTIFIER_NODE, and
additionally give the location of the previous declaration DECL. */
void
shadow_warning (msgid, name, decl)
const char *msgid;
tree name, decl;
{
warning ("declaration of `%s' shadows %s", IDENTIFIER_POINTER (name), msgid);
warning_with_file_and_line (DECL_SOURCE_FILE (decl),
DECL_SOURCE_LINE (decl),
"shadowed declaration is here");
}
...@@ -330,6 +330,8 @@ extern tree walk_stmt_tree PARAMS ((tree *, ...@@ -330,6 +330,8 @@ extern tree walk_stmt_tree PARAMS ((tree *,
extern void prep_stmt PARAMS ((tree)); extern void prep_stmt PARAMS ((tree));
extern void expand_stmt PARAMS ((tree)); extern void expand_stmt PARAMS ((tree));
extern void mark_stmt_tree PARAMS ((void *)); extern void mark_stmt_tree PARAMS ((void *));
extern void shadow_warning PARAMS ((const char *,
tree, tree));
/* Extra information associated with a DECL. Other C dialects extend /* Extra information associated with a DECL. Other C dialects extend
this structure in various ways. The C front-end only uses this this structure in various ways. The C front-end only uses this
......
...@@ -45,6 +45,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA ...@@ -45,6 +45,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
#include "target.h" #include "target.h"
#include "debug.h" #include "debug.h"
#include "timevar.h" #include "timevar.h"
#include "c-common.h"
/* In grokdeclarator, distinguish syntactic contexts of declarators. */ /* In grokdeclarator, distinguish syntactic contexts of declarators. */
enum decl_context enum decl_context
...@@ -280,6 +281,7 @@ static tree grokparms PARAMS ((tree, int)); ...@@ -280,6 +281,7 @@ static tree grokparms PARAMS ((tree, int));
static void layout_array_type PARAMS ((tree)); static void layout_array_type PARAMS ((tree));
static tree c_make_fname_decl PARAMS ((tree, int)); static tree c_make_fname_decl PARAMS ((tree, int));
static void c_expand_body PARAMS ((tree, int, int)); static void c_expand_body PARAMS ((tree, int, int));
static void warn_if_shadowing PARAMS ((tree, tree));
/* C-specific option variables. */ /* C-specific option variables. */
...@@ -2047,6 +2049,66 @@ duplicate_decls (newdecl, olddecl, different_binding_level) ...@@ -2047,6 +2049,66 @@ duplicate_decls (newdecl, olddecl, different_binding_level)
return 1; return 1;
} }
/* Check whether decl-node X shadows an existing declaration.
OLDLOCAL is the old IDENTIFIER_LOCAL_VALUE of the DECL_NAME of X,
which might be a NULL_TREE. */
static void
warn_if_shadowing (x, oldlocal)
tree x, oldlocal;
{
tree name;
if (DECL_EXTERNAL (x))
return;
name = DECL_NAME (x);
/* Warn if shadowing an argument at the top level of the body. */
if (oldlocal != 0
/* This warning doesn't apply to the parms of a nested fcn. */
&& ! current_binding_level->parm_flag
/* Check that this is one level down from the parms. */
&& current_binding_level->level_chain->parm_flag
/* Check that the decl being shadowed
comes from the parm level, one level up. */
&& chain_member (oldlocal, current_binding_level->level_chain->names))
{
if (TREE_CODE (oldlocal) == PARM_DECL)
pedwarn ("declaration of `%s' shadows a parameter",
IDENTIFIER_POINTER (name));
else
pedwarn ("declaration of `%s' shadows a symbol from the parameter list",
IDENTIFIER_POINTER (name));
}
/* Maybe warn if shadowing something else. */
else if (warn_shadow
/* No shadow warnings for internally generated vars. */
&& DECL_SOURCE_LINE (x) != 0
/* No shadow warnings for vars made for inlining. */
&& ! DECL_FROM_INLINE (x))
{
if (TREE_CODE (x) == PARM_DECL
&& current_binding_level->level_chain->parm_flag)
/* Don't warn about the parm names in function declarator
within a function declarator.
It would be nice to avoid warning in any function
declarator in a declaration, as opposed to a definition,
but there is no way to tell it's not a definition. */
;
else if (oldlocal)
{
if (TREE_CODE (oldlocal) == PARM_DECL)
shadow_warning ("a parameter", name, oldlocal);
else
shadow_warning ("a previous local", name, oldlocal);
}
else if (IDENTIFIER_GLOBAL_VALUE (name) != 0
&& IDENTIFIER_GLOBAL_VALUE (name) != error_mark_node)
shadow_warning ("a global declaration", name,
IDENTIFIER_GLOBAL_VALUE (name));
}
}
/* Record a decl-node X as belonging to the current lexical scope. /* Record a decl-node X as belonging to the current lexical scope.
Check for errors (such as an incompatible declaration for the same Check for errors (such as an incompatible declaration for the same
name already seen in the same scope). name already seen in the same scope).
...@@ -2431,49 +2493,7 @@ pushdecl (x) ...@@ -2431,49 +2493,7 @@ pushdecl (x)
IDENTIFIER_LIMBO_VALUE (name) = x; IDENTIFIER_LIMBO_VALUE (name) = x;
} }
/* Warn if shadowing an argument at the top level of the body. */ warn_if_shadowing (x, oldlocal);
if (oldlocal != 0 && !DECL_EXTERNAL (x)
/* This warning doesn't apply to the parms of a nested fcn. */
&& ! current_binding_level->parm_flag
/* Check that this is one level down from the parms. */
&& current_binding_level->level_chain->parm_flag
/* Check that the decl being shadowed
comes from the parm level, one level up. */
&& chain_member (oldlocal, current_binding_level->level_chain->names))
{
if (TREE_CODE (oldlocal) == PARM_DECL)
pedwarn ("declaration of `%s' shadows a parameter",
IDENTIFIER_POINTER (name));
else
pedwarn ("declaration of `%s' shadows a symbol from the parameter list",
IDENTIFIER_POINTER (name));
}
/* Maybe warn if shadowing something else. */
else if (warn_shadow && !DECL_EXTERNAL (x)
/* No shadow warnings for internally generated vars. */
&& DECL_SOURCE_LINE (x) != 0
/* No shadow warnings for vars made for inlining. */
&& ! DECL_FROM_INLINE (x))
{
const char *id = IDENTIFIER_POINTER (name);
if (TREE_CODE (x) == PARM_DECL
&& current_binding_level->level_chain->parm_flag)
/* Don't warn about the parm names in function declarator
within a function declarator.
It would be nice to avoid warning in any function
declarator in a declaration, as opposed to a definition,
but there is no way to tell it's not a definition. */
;
else if (oldlocal != 0 && TREE_CODE (oldlocal) == PARM_DECL)
warning ("declaration of `%s' shadows a parameter", id);
else if (oldlocal != 0)
warning ("declaration of `%s' shadows previous local", id);
else if (IDENTIFIER_GLOBAL_VALUE (name) != 0
&& IDENTIFIER_GLOBAL_VALUE (name) != error_mark_node)
warning ("declaration of `%s' shadows global declaration", id);
}
/* If storing a local value, there may already be one (inherited). /* If storing a local value, there may already be one (inherited).
If so, record it for restoration when this binding level ends. */ If so, record it for restoration when this binding level ends. */
...@@ -6354,11 +6374,16 @@ store_parm_decls () ...@@ -6354,11 +6374,16 @@ store_parm_decls ()
then CONST_DECLs for foo and bar are put here. */ then CONST_DECLs for foo and bar are put here. */
tree nonparms = 0; tree nonparms = 0;
/* The function containing FNDECL, if any. */
tree context = decl_function_context (fndecl);
/* Nonzero if this definition is written with a prototype. */ /* Nonzero if this definition is written with a prototype. */
int prototype = 0; int prototype = 0;
/* The function containing FNDECL, if any. */ int saved_warn_shadow = warn_shadow;
tree context = decl_function_context (fndecl);
/* Don't re-emit shadow warnings. */
warn_shadow = 0;
if (specparms != 0 && TREE_CODE (specparms) != TREE_LIST) if (specparms != 0 && TREE_CODE (specparms) != TREE_LIST)
{ {
...@@ -6758,6 +6783,8 @@ store_parm_decls () ...@@ -6758,6 +6783,8 @@ store_parm_decls ()
not safe to try to expand expressions involving them. */ not safe to try to expand expressions involving them. */
immediate_size_expand = 0; immediate_size_expand = 0;
cfun->x_dont_save_pending_sizes_p = 1; cfun->x_dont_save_pending_sizes_p = 1;
warn_shadow = saved_warn_shadow;
} }
/* Finish up a function declaration and compile that function /* Finish up a function declaration and compile that function
......
2001-12-05 Neil Booth <neil@daikokuya.demon.co.uk>
* decl.c: Include c-common.h.
(shadow_warning): Move to c-common.c.
Wed Dec 5 17:00:49 2001 Richard Kenner <kenner@vlsi1.ultra.nyu.edu> Wed Dec 5 17:00:49 2001 Richard Kenner <kenner@vlsi1.ultra.nyu.edu>
* decl.c (duplicate_decls): Don't copy DECL_NO_CHECK_MEMORY_USAGE. * decl.c (duplicate_decls): Don't copy DECL_NO_CHECK_MEMORY_USAGE.
......
...@@ -45,6 +45,7 @@ Boston, MA 02111-1307, USA. */ ...@@ -45,6 +45,7 @@ Boston, MA 02111-1307, USA. */
#include "ggc.h" #include "ggc.h"
#include "tm_p.h" #include "tm_p.h"
#include "target.h" #include "target.h"
#include "c-common.h"
extern const struct attribute_spec *lang_attribute_table; extern const struct attribute_spec *lang_attribute_table;
...@@ -147,7 +148,6 @@ static tree push_cp_library_fn PARAMS ((enum tree_code, tree)); ...@@ -147,7 +148,6 @@ static tree push_cp_library_fn PARAMS ((enum tree_code, tree));
static tree build_cp_library_fn PARAMS ((tree, enum tree_code, tree)); static tree build_cp_library_fn PARAMS ((tree, enum tree_code, tree));
static void store_parm_decls PARAMS ((tree)); static void store_parm_decls PARAMS ((tree));
static int cp_missing_noreturn_ok_p PARAMS ((tree)); static int cp_missing_noreturn_ok_p PARAMS ((tree));
static void shadow_warning PARAMS ((const char *, tree, tree));
#if defined (DEBUG_CP_BINDING_LEVELS) #if defined (DEBUG_CP_BINDING_LEVELS)
static void indent PARAMS ((void)); static void indent PARAMS ((void));
...@@ -3787,20 +3787,6 @@ duplicate_decls (newdecl, olddecl) ...@@ -3787,20 +3787,6 @@ duplicate_decls (newdecl, olddecl)
return 1; return 1;
} }
/* Output a -Wshadow warning MSGID, if non-NULL, and give the location
of the previous declaration. */
static void
shadow_warning (msgid, name, decl)
const char *msgid;
tree name, decl;
{
warning ("declaration of `%s' shadows %s", IDENTIFIER_POINTER (name), msgid);
warning_with_file_and_line (DECL_SOURCE_FILE (decl),
DECL_SOURCE_LINE (decl),
"shadowed declaration is here");
}
/* Record a decl-node X as belonging to the current lexical scope. /* Record a decl-node X as belonging to the current lexical scope.
Check for errors (such as an incompatible declaration for the same Check for errors (such as an incompatible declaration for the same
name already seen in the same scope). name already seen in the same scope).
......
2001-12-05 Neil Booth <neil@daikokuya.demon.co.uk>
* gcc.dg/Wshadow-1.c: New test.
2001-12-05 Jakub Jelinek <jakub@redhat.com> 2001-12-05 Jakub Jelinek <jakub@redhat.com>
* gcc.c-torture/compile/20011130-1.c: New test. * gcc.c-torture/compile/20011130-1.c: New test.
......
/* Copyright (C) 2001 Free Software Foundation, Inc. */
/* { dg-do compile } */
/* { dg-options "-Wshadow -pedantic-errors" } */
/* Source: Neil Booth, 5 Dec 2001. */
int decl1; /* { dg-warning "shadowed declaration" } */
void foo (double decl1) /* { dg-warning "shadows a global decl" } */
{
}
void foo1 (int d)
{
double d; /* { dg-bogus "warning" "warning in place of error" } */
/* { dg-error "shadows a parameter" "" { target *-*-* } 15 } */
}
void foo2 (int d) /* { dg-warning "shadowed declaration" } */
{
{
double d; /* { dg-warning "shadows a parameter" } */
}
}
void foo3 ()
{
int local; /* { dg-warning "shadowed declaration" } */
{
int local; /* { dg-warning "shadows a previous local" } */
}
}
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