/* Warn if a variable shadows a non-function, or the variable
is a function or a pointer-to-function. */
- if (!OVL_P (member)
- || TREE_CODE (decl) == FUNCTION_DECL
- || (TREE_TYPE (decl)
- && (TYPE_PTRFN_P (TREE_TYPE (decl))
- || TYPE_PTRMEMFUNC_P (TREE_TYPE (decl)))))
+ if ((!OVL_P (member)
+ || TREE_CODE (decl) == FUNCTION_DECL
+ || (TREE_TYPE (decl)
+ && (TYPE_PTRFN_P (TREE_TYPE (decl))
+ || TYPE_PTRMEMFUNC_P (TREE_TYPE (decl)))))
+ && !warning_suppressed_p (decl, OPT_Wshadow))
{
auto_diagnostic_group d;
if (warning_at (DECL_SOURCE_LOCATION (decl), OPT_Wshadow,
"declaration of %qD shadows a member of %qT",
decl, current_nonlambda_class_type ())
&& DECL_P (member))
- inform_shadowed (member);
+ {
+ inform_shadowed (member);
+ suppress_warning (decl, OPT_Wshadow);
+ }
}
return;
}
|| (TREE_CODE (old) == TYPE_DECL
&& (!DECL_ARTIFICIAL (old)
|| TREE_CODE (decl) == TYPE_DECL)))
- && !instantiating_current_function_p ())
+ && !instantiating_current_function_p ()
+ && !warning_suppressed_p (decl, OPT_Wshadow))
/* XXX shadow warnings in outer-more namespaces */
{
auto_diagnostic_group d;
if (warning_at (DECL_SOURCE_LOCATION (decl), OPT_Wshadow,
"declaration of %qD shadows a global declaration",
decl))
- inform_shadowed (old);
+ {
+ inform_shadowed (old);
+ suppress_warning (decl, OPT_Wshadow);
+ }
return;
}
--- /dev/null
+// PR c++/104379
+// { dg-do compile }
+// { dg-options "-Wshadow" }
+
+int x;
+
+template<typename T>
+struct S
+{
+ int i;
+ S(int i) { (void) i; } // { dg-warning "declaration of 'i' shadows a member of 'S<T>'" }
+ S(float x) { (void) x; } // { dg-warning "declaration of 'x' shadows a global declaration" }
+ S(int *p) { int a = 1; (void) p; (void) a;
+ { int a = 2; (void) a; } } // { dg-warning "declaration of 'a' shadows a previous local" }
+};
+
+S<int> i(1);
+S<long> j(1);
+S<int> k(1.0f);
+S<long> l(1.0f);
+S<int> m(&x);
+S<int> n(&x);