This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
C++ PATCH: PR 20145
- From: Mark Mitchell <mark at codesourcery dot com>
- To: gcc-patches at gcc dot gnu dot org
- Date: Fri, 8 Apr 2005 12:41:14 -0700
- Subject: C++ PATCH: PR 20145
- Reply-to: mark at codesourcery dot com
This patch fixes PR c++/20145, a warning regression in 4.0. When we
enter/exit template contexts we need to save/restore in_system_header.
Tested on x86_64-unknown-linux-gnu, applied on the mainline and the
4.0 branch.
--
Mark Mitchell
CodeSourcery, LLC
mark@codesourcery.com
2005-04-08 Mark Mitchell <mark@codesourcery.com>
* cp-tree.def (TINST_LEVEL): Document TINST_IN_SYSTEM_HEADER_P.
* cp-tree.h (struct tinst_level): Add in_system_header_p.
(TINST_IN_SYSTEM_HEADER_P): New macro.
(make_tinst_level): Remove.
* pt.c (lookup_template_class): Preserve DECL_IN_SYSTEM_HEADER on
the instantiated class.
(push_tinst_level): Do not use make_tinst_level. Set
TINST_IN_SYSTEM_HEADER_P.
(pop_tinst_level): Likewise.
(instantiate_class_template): Set in_system_header.
(instantiate_pending_templates): Likewise.
* tree.c (make_tinst_level): Remove.
2005-04-08 Mark Mitchell <mark@codesourcery.com>
PR c++/20145
* g++.dg/warn/Wdtor1.C: New test.
Index: testsuite/g++.dg/warn/Wdtor1.C
===================================================================
RCS file: testsuite/g++.dg/warn/Wdtor1.C
diff -N testsuite/g++.dg/warn/Wdtor1.C
*** /dev/null 1 Jan 1970 00:00:00 -0000
--- testsuite/g++.dg/warn/Wdtor1.C 8 Apr 2005 19:30:49 -0000
***************
*** 0 ****
--- 1,18 ----
+ // PR c++/20145
+ // { dg-options "-Wnon-virtual-dtor" }
+ # 1 "t.cc"
+ # 1 "<built-in>"
+ # 1 "<command line>"
+ # 1 "t.cc"
+ # 1 "include/t.h" 1 3 4
+ template <int> class t
+ {
+ virtual void f();
+ };
+ # 2 "t.cc" 2
+
+ void f(void)
+ {
+ t<1> h;
+ }
+
Index: cp/cp-tree.def
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/cp-tree.def,v
retrieving revision 1.95
diff -c -5 -p -r1.95 cp-tree.def
*** cp/cp-tree.def 6 Apr 2005 05:38:23 -0000 1.95
--- cp/cp-tree.def 8 Apr 2005 19:30:49 -0000
*************** DEFTREECODE (TAG_DEFN, "tag_defn", tcc_e
*** 287,296 ****
--- 287,297 ----
/* Template instantiation level node.
TINST_DECL contains the original DECL node.
TINST_LOCATION contains the location where the template is instantiated.
+ TINST_IN_SYSTEM_HEADER_P is true if the location is in a system header.
A stack of template instantiation nodes is kept through the TREE_CHAIN
fields of these nodes. */
DEFTREECODE (TINST_LEVEL, "TINST_LEVEL", tcc_exceptional, 0)
Index: cp/cp-tree.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/cp-tree.h,v
retrieving revision 1.1116
diff -c -5 -p -r1.1116 cp-tree.h
*** cp/cp-tree.h 1 Apr 2005 08:29:50 -0000 1.1116
--- cp/cp-tree.h 8 Apr 2005 19:30:50 -0000
*************** typedef struct template_parm_index_s tem
*** 219,228 ****
--- 219,229 ----
struct tinst_level_s GTY(())
{
struct tree_common common;
tree decl;
location_t locus;
+ int in_system_header_p;
};
typedef struct tinst_level_s * tinst_level_t;
struct ptrmem_cst GTY(())
{
*************** typedef enum unification_kind_t {
*** 3119,3128 ****
--- 3120,3131 ----
#define TINST_DECL(NODE) \
(((tinst_level_t) TINST_LEVEL_CHECK (NODE))->decl)
#define TINST_LOCATION(NODE) \
(((tinst_level_t) TINST_LEVEL_CHECK (NODE))->locus)
+ #define TINST_IN_SYSTEM_HEADER_P(NODE) \
+ (((tinst_level_t) TINST_LEVEL_CHECK (NODE))->in_system_header_p)
/* in class.c */
extern int current_class_depth;
*************** extern tree no_linkage_check (tree, bo
*** 4242,4252 ****
extern void debug_binfo (tree);
extern tree build_dummy_object (tree);
extern tree maybe_dummy_object (tree, tree *);
extern int is_dummy_object (tree);
extern const struct attribute_spec cxx_attribute_table[];
- extern tree make_tinst_level (tree, location_t);
extern tree make_ptrmem_cst (tree, tree);
extern tree cp_build_type_attribute_variant (tree, tree);
extern tree cp_build_qualified_type_real (tree, int, tsubst_flags_t);
#define cp_build_qualified_type(TYPE, QUALS) \
cp_build_qualified_type_real ((TYPE), (QUALS), tf_error | tf_warning)
--- 4245,4254 ----
Index: cp/pt.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/pt.c,v
retrieving revision 1.991
diff -c -5 -p -r1.991 pt.c
*** cp/pt.c 6 Apr 2005 15:54:42 -0000 1.991
--- cp/pt.c 8 Apr 2005 19:30:50 -0000
*************** lookup_template_class (tree d1,
*** 4607,4616 ****
--- 4607,4618 ----
TREE_PRIVATE (type_decl)
= TREE_PRIVATE (TYPE_STUB_DECL (template_type));
TREE_PROTECTED (type_decl)
= TREE_PROTECTED (TYPE_STUB_DECL (template_type));
+ DECL_IN_SYSTEM_HEADER (type_decl)
+ = DECL_IN_SYSTEM_HEADER (template);
/* Set up the template information. We have to figure out which
template is the immediate parent if this is a full
instantiation. */
if (parm_depth == 1 || is_partial_instantiation
*************** push_tinst_level (tree d)
*** 4999,5009 ****
print_instantiation_context ();
return 0;
}
! new = make_tinst_level (d, input_location);
TREE_CHAIN (new) = current_tinst_level;
current_tinst_level = new;
++tinst_depth;
#ifdef GATHER_STATISTICS
--- 5001,5014 ----
print_instantiation_context ();
return 0;
}
! new = make_node (TINST_LEVEL);
! TINST_DECL (new) = d;
! TINST_LOCATION (new) = input_location;
! TINST_IN_SYSTEM_HEADER_P (new) = in_system_header;
TREE_CHAIN (new) = current_tinst_level;
current_tinst_level = new;
++tinst_depth;
#ifdef GATHER_STATISTICS
*************** pop_tinst_level (void)
*** 5024,5033 ****
--- 5029,5039 ----
tree old = current_tinst_level;
/* Restore the filename and line number stashed away when we started
this instantiation. */
input_location = TINST_LOCATION (old);
+ in_system_header = TINST_IN_SYSTEM_HEADER_P (old);
current_tinst_level = TREE_CHAIN (old);
--tinst_depth;
++tinst_level_tick;
}
*************** instantiate_class_template (tree type)
*** 5502,5512 ****
SET_CLASSTYPE_INTERFACE_UNKNOWN (type);
/* Set the input location to the template definition. This is needed
if tsubsting causes an error. */
! input_location = DECL_SOURCE_LOCATION (TYPE_NAME (pattern));
TYPE_HAS_CONSTRUCTOR (type) = TYPE_HAS_CONSTRUCTOR (pattern);
TYPE_HAS_NEW_OPERATOR (type) = TYPE_HAS_NEW_OPERATOR (pattern);
TYPE_HAS_ARRAY_NEW_OPERATOR (type) = TYPE_HAS_ARRAY_NEW_OPERATOR (pattern);
TYPE_GETS_DELETE (type) = TYPE_GETS_DELETE (pattern);
--- 5508,5520 ----
SET_CLASSTYPE_INTERFACE_UNKNOWN (type);
/* Set the input location to the template definition. This is needed
if tsubsting causes an error. */
! typedecl = TYPE_MAIN_DECL (type);
! input_location = DECL_SOURCE_LOCATION (typedecl);
! in_system_header = DECL_IN_SYSTEM_HEADER (typedecl);
TYPE_HAS_CONSTRUCTOR (type) = TYPE_HAS_CONSTRUCTOR (pattern);
TYPE_HAS_NEW_OPERATOR (type) = TYPE_HAS_NEW_OPERATOR (pattern);
TYPE_HAS_ARRAY_NEW_OPERATOR (type) = TYPE_HAS_ARRAY_NEW_OPERATOR (pattern);
TYPE_GETS_DELETE (type) = TYPE_GETS_DELETE (pattern);
*************** instantiate_class_template (tree type)
*** 5841,5851 ****
/* Set the file and line number information to whatever is given for
the class itself. This puts error messages involving generated
implicit functions at a predictable point, and the same point
that would be used for non-template classes. */
- typedecl = TYPE_MAIN_DECL (type);
input_location = DECL_SOURCE_LOCATION (typedecl);
unreverse_member_declarations (type);
finish_struct_1 (type);
TYPE_BEING_DEFINED (type) = 0;
--- 5849,5858 ----
*************** instantiate_pending_templates (int retri
*** 11588,11597 ****
--- 11595,11605 ----
{
tree *t;
tree last = NULL_TREE;
int reconsider;
location_t saved_loc = input_location;
+ int saved_in_system_header = in_system_header;
/* Instantiating templates may trigger vtable generation. This in turn
may require further template instantiations. We place a limit here
to avoid infinite loop. */
if (pending_templates && retries >= max_tinst_depth)
*************** instantiate_pending_templates (int retri
*** 11672,11681 ****
--- 11680,11690 ----
last_pending_template = last;
}
while (reconsider);
input_location = saved_loc;
+ in_system_header = saved_in_system_header;
}
/* Substitute ARGVEC into T, which is a list of initializers for
either base class or a non-static data member. The TREE_PURPOSEs
are DECLs, and the TREE_VALUEs are the initializer values. Used by
Index: cp/tree.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/tree.c,v
retrieving revision 1.430
diff -c -5 -p -r1.430 tree.c
*** cp/tree.c 6 Apr 2005 04:57:38 -0000 1.430
--- cp/tree.c 8 Apr 2005 19:30:50 -0000
*************** handle_init_priority_attribute (tree* no
*** 1849,1869 ****
*no_add_attrs = true;
return NULL_TREE;
}
}
- /* Return a new TINST_LEVEL for DECL at location locus. */
- tree
- make_tinst_level (tree decl, location_t locus)
- {
- tree tinst_level = make_node (TINST_LEVEL);
- TREE_CHAIN (tinst_level) = NULL_TREE;
- TINST_DECL (tinst_level) = decl;
- TINST_LOCATION (tinst_level) = locus;
- return tinst_level;
- }
-
/* Return a new PTRMEM_CST of the indicated TYPE. The MEMBER is the
thing pointed to by the constant. */
tree
make_ptrmem_cst (tree type, tree member)
--- 1849,1858 ----