Commit 6dfbb909 by Mark Mitchell Committed by Mark Mitchell

cp-tree.h (lang_decl): Remove pretty_function_p.

	* cp-tree.h (lang_decl): Remove pretty_function_p.
	(DECL_PRETTY_FUNCTION_P): Use TREE_LANG_FLAG_0, not a bit in the
	language-specific node.
	* decl.c (cp_make_fname_decl): Use build_decl, not
	build_lang_decl, to build the variables.
	(grokvardecl): Don't call build_lang_decl for local variables in
	templates.
	(grokdeclarator): Don't call build_lang_decl for local type
	declarations in templates.
	* lex.c (retrofit_lang_decl): Use ggc_alloc_obj to allocated
	zero'd memory, rather than calling memset.
	* pt.c: Include hashtab.h.
	(local_specializations): New variable.
	(retrieve_local_specialization): Use it.
	(register_local_specialization): Likewise.
	(tsubst_decl): Don't assume local variables have
	DECL_LANG_SPECIFIC.
	(instantiate_decl): Set up local_specializations.
	* Makefile.in (HTAB_H): New variable.

From-SVN: r33369
parent b51024fc
2000-04-23 Mark Mitchell <mark@codesourcery.com>
* cp-tree.h (lang_decl): Remove pretty_function_p.
(DECL_PRETTY_FUNCTION_P): Use TREE_LANG_FLAG_0, not a bit in the
language-specific node.
* decl.c (cp_make_fname_decl): Use build_decl, not
build_lang_decl, to build the variables.
(grokvardecl): Don't call build_lang_decl for local variables in
templates.
(grokdeclarator): Don't call build_lang_decl for local type
declarations in templates.
* lex.c (retrofit_lang_decl): Use ggc_alloc_obj to allocated
zero'd memory, rather than calling memset.
* pt.c: Include hashtab.h.
(local_specializations): New variable.
(retrieve_local_specialization): Use it.
(register_local_specialization): Likewise.
(tsubst_decl): Don't assume local variables have
DECL_LANG_SPECIFIC.
(instantiate_decl): Set up local_specializations.
* Makefile.in (HTAB_H): New variable.
2000-04-23 Richard Henderson <rth@cygnus.com> 2000-04-23 Richard Henderson <rth@cygnus.com>
* typeck.c (c_expand_asm_operands): Restore the original * typeck.c (c_expand_asm_operands): Restore the original
......
...@@ -210,6 +210,7 @@ PARSE_H = $(srcdir)/parse.h ...@@ -210,6 +210,7 @@ PARSE_H = $(srcdir)/parse.h
PARSE_C = $(srcdir)/parse.c PARSE_C = $(srcdir)/parse.c
EXPR_H = $(srcdir)/../expr.h ../insn-codes.h EXPR_H = $(srcdir)/../expr.h ../insn-codes.h
GGC_H = $(srcdir)/../ggc.h $(srcdir)/../varray.h GGC_H = $(srcdir)/../ggc.h $(srcdir)/../varray.h
HTAB_H = $(srcdir)/../../include/hashtab.h
parse.o : $(PARSE_C) $(CXX_TREE_H) $(srcdir)/../flags.h lex.h \ parse.o : $(PARSE_C) $(CXX_TREE_H) $(srcdir)/../flags.h lex.h \
$(srcdir)/../except.h $(srcdir)/../output.h $(srcdir)/../system.h \ $(srcdir)/../except.h $(srcdir)/../output.h $(srcdir)/../system.h \
...@@ -295,7 +296,7 @@ xref.o : xref.c $(CXX_TREE_H) $(srcdir)/../input.h \ ...@@ -295,7 +296,7 @@ xref.o : xref.c $(CXX_TREE_H) $(srcdir)/../input.h \
$(srcdir)/../toplev.h $(srcdir)/../toplev.h
pt.o : pt.c $(CXX_TREE_H) decl.h $(PARSE_H) lex.h \ pt.o : pt.c $(CXX_TREE_H) decl.h $(PARSE_H) lex.h \
$(srcdir)/../toplev.h $(GGC_H) $(RTL_H) \ $(srcdir)/../toplev.h $(GGC_H) $(RTL_H) \
$(srcdir)/../except.h $(srcdir)/../except.h $(HTAB_H)
error.o : error.c $(CXX_TREE_H) \ error.o : error.c $(CXX_TREE_H) \
$(srcdir)/../toplev.h $(srcdir)/../toplev.h
errfn.o : errfn.c $(CXX_TREE_H) \ errfn.o : errfn.c $(CXX_TREE_H) \
......
...@@ -43,6 +43,7 @@ Boston, MA 02111-1307, USA. */ ...@@ -43,6 +43,7 @@ Boston, MA 02111-1307, USA. */
AGGR_INIT_VIA_CTOR_P (in AGGR_INIT_EXPR) AGGR_INIT_VIA_CTOR_P (in AGGR_INIT_EXPR)
SCOPE_BEGIN_P (in SCOPE_STMT) SCOPE_BEGIN_P (in SCOPE_STMT)
CTOR_BEGIN_P (in CTOR_STMT) CTOR_BEGIN_P (in CTOR_STMT)
DECL_PRETTY_FUNCTION_P (in VAR_DECL)
1: IDENTIFIER_VIRTUAL_P. 1: IDENTIFIER_VIRTUAL_P.
TI_PENDING_TEMPLATE_FLAG. TI_PENDING_TEMPLATE_FLAG.
TEMPLATE_PARMS_FOR_INLINE. TEMPLATE_PARMS_FOR_INLINE.
...@@ -1866,7 +1867,7 @@ struct lang_decl_flags ...@@ -1866,7 +1867,7 @@ struct lang_decl_flags
unsigned static_function : 1; unsigned static_function : 1;
unsigned pure_virtual : 1; unsigned pure_virtual : 1;
unsigned has_in_charge_parm_p : 1; unsigned has_in_charge_parm_p : 1;
unsigned pretty_function_p : 1; unsigned bitfield : 1;
unsigned mutable_flag : 1; unsigned mutable_flag : 1;
unsigned deferred : 1; unsigned deferred : 1;
...@@ -1876,12 +1877,11 @@ struct lang_decl_flags ...@@ -1876,12 +1877,11 @@ struct lang_decl_flags
unsigned not_really_extern : 1; unsigned not_really_extern : 1;
unsigned needs_final_overrider : 1; unsigned needs_final_overrider : 1;
unsigned bitfield : 1;
unsigned defined_in_class : 1; unsigned defined_in_class : 1;
unsigned pending_inline_p : 1; unsigned pending_inline_p : 1;
unsigned global_ctor_p : 1; unsigned global_ctor_p : 1;
unsigned global_dtor_p : 1; unsigned global_dtor_p : 1;
unsigned dummy : 3; unsigned dummy : 4;
tree context; tree context;
...@@ -2106,7 +2106,7 @@ struct lang_decl ...@@ -2106,7 +2106,7 @@ struct lang_decl
/* Nonzero if this DECL is the __PRETTY_FUNCTION__ variable in a /* Nonzero if this DECL is the __PRETTY_FUNCTION__ variable in a
template function. */ template function. */
#define DECL_PRETTY_FUNCTION_P(NODE) \ #define DECL_PRETTY_FUNCTION_P(NODE) \
(DECL_LANG_SPECIFIC(NODE)->decl_flags.pretty_function_p) (TREE_LANG_FLAG_0 (NODE))
/* The _TYPE context in which this _DECL appears. This field holds the /* The _TYPE context in which this _DECL appears. This field holds the
class where a virtual function instance is actually defined. */ class where a virtual function instance is actually defined. */
......
...@@ -6550,7 +6550,7 @@ cp_make_fname_decl (id, name, type_dep) ...@@ -6550,7 +6550,7 @@ cp_make_fname_decl (id, name, type_dep)
(build_qualified_type (char_type_node, TYPE_QUAL_CONST), (build_qualified_type (char_type_node, TYPE_QUAL_CONST),
domain); domain);
decl = build_lang_decl (VAR_DECL, id, type); decl = build_decl (VAR_DECL, id, type);
TREE_STATIC (decl) = 1; TREE_STATIC (decl) = 1;
TREE_READONLY (decl) = 1; TREE_READONLY (decl) = 1;
DECL_SOURCE_LINE (decl) = 0; DECL_SOURCE_LINE (decl) = 0;
...@@ -8924,9 +8924,9 @@ grokvardecl (type, declarator, specbits_in, initialized, constp, in_namespace) ...@@ -8924,9 +8924,9 @@ grokvardecl (type, declarator, specbits_in, initialized, constp, in_namespace)
else else
context = NULL_TREE; context = NULL_TREE;
if (processing_template_decl) if (processing_template_decl && context)
/* If we're in a template, we need DECL_LANG_SPECIFIC so that /* For global variables, declared in a template, we need the
we can call push_template_decl. */ full lang_decl. */
decl = build_lang_decl (VAR_DECL, declarator, type); decl = build_lang_decl (VAR_DECL, declarator, type);
else else
decl = build_decl (VAR_DECL, declarator, type); decl = build_decl (VAR_DECL, declarator, type);
...@@ -10917,14 +10917,7 @@ grokdeclarator (declarator, declspecs, decl_context, initialized, attrlist) ...@@ -10917,14 +10917,7 @@ grokdeclarator (declarator, declspecs, decl_context, initialized, attrlist)
decl = build_lang_decl (TYPE_DECL, declarator, type); decl = build_lang_decl (TYPE_DECL, declarator, type);
} }
else else
{ decl = build_decl (TYPE_DECL, declarator, type);
/* Make sure this typedef lives as long as its type,
since it might be used as a template parameter. */
if (processing_template_decl)
decl = build_lang_decl (TYPE_DECL, declarator, type);
else
decl = build_decl (TYPE_DECL, declarator, type);
}
/* If the user declares "typedef struct {...} foo" then the /* If the user declares "typedef struct {...} foo" then the
struct will have an anonymous name. Fill that name in now. struct will have an anonymous name. Fill that name in now.
......
...@@ -4977,8 +4977,7 @@ retrofit_lang_decl (t) ...@@ -4977,8 +4977,7 @@ retrofit_lang_decl (t)
else else
size = sizeof (struct lang_decl_flags); size = sizeof (struct lang_decl_flags);
ld = (struct lang_decl *) ggc_alloc (size); ld = (struct lang_decl *) ggc_alloc_obj (size, 1);
memset (ld, 0, size);
DECL_LANG_SPECIFIC (t) = ld; DECL_LANG_SPECIFIC (t) = ld;
if (current_lang_name == lang_name_cplusplus) if (current_lang_name == lang_name_cplusplus)
......
...@@ -43,6 +43,7 @@ Boston, MA 02111-1307, USA. */ ...@@ -43,6 +43,7 @@ Boston, MA 02111-1307, USA. */
#include "rtl.h" #include "rtl.h"
#include "defaults.h" #include "defaults.h"
#include "ggc.h" #include "ggc.h"
#include "hashtab.h"
/* The type of functions taking a tree, and some additional data, and /* The type of functions taking a tree, and some additional data, and
returning an int. */ returning an int. */
...@@ -73,6 +74,11 @@ static tree saved_trees; ...@@ -73,6 +74,11 @@ static tree saved_trees;
static varray_type inline_parm_levels; static varray_type inline_parm_levels;
static size_t inline_parm_levels_used; static size_t inline_parm_levels_used;
/* A map from local variable declarations in the body of the template
presently being instantiated to the corresponding instantiated
local variables. */
static htab_t local_specializations;
#define obstack_chunk_alloc xmalloc #define obstack_chunk_alloc xmalloc
#define obstack_chunk_free free #define obstack_chunk_free free
...@@ -119,9 +125,9 @@ static tree build_template_parm_index PARAMS ((int, int, int, tree, tree)); ...@@ -119,9 +125,9 @@ static tree build_template_parm_index PARAMS ((int, int, int, tree, tree));
static int inline_needs_template_parms PARAMS ((tree)); static int inline_needs_template_parms PARAMS ((tree));
static void push_inline_template_parms_recursive PARAMS ((tree, int)); static void push_inline_template_parms_recursive PARAMS ((tree, int));
static tree retrieve_specialization PARAMS ((tree, tree)); static tree retrieve_specialization PARAMS ((tree, tree));
static tree retrieve_local_specialization PARAMS ((tree, tree)); static tree retrieve_local_specialization PARAMS ((tree));
static tree register_specialization PARAMS ((tree, tree, tree)); static tree register_specialization PARAMS ((tree, tree, tree));
static tree register_local_specialization PARAMS ((tree, tree, tree)); static tree register_local_specialization PARAMS ((tree, tree));
static int unregister_specialization PARAMS ((tree, tree)); static int unregister_specialization PARAMS ((tree, tree));
static tree reduce_template_parm_level PARAMS ((tree, tree, int)); static tree reduce_template_parm_level PARAMS ((tree, tree, int));
static tree build_template_decl PARAMS ((tree, tree)); static tree build_template_decl PARAMS ((tree, tree));
...@@ -709,16 +715,13 @@ retrieve_specialization (tmpl, args) ...@@ -709,16 +715,13 @@ retrieve_specialization (tmpl, args)
return NULL_TREE; return NULL_TREE;
} }
/* Like retrieve_speciailization, but for local declarations. FN is /* Like retrieve_speciailization, but for local declarations. */
the function in which we are looking for an instantiation. */
static tree static tree
retrieve_local_specialization (tmpl, fn) retrieve_local_specialization (tmpl)
tree tmpl; tree tmpl;
tree fn;
{ {
tree s = purpose_member (fn, DECL_TEMPLATE_SPECIALIZATIONS (tmpl)); return (tree) htab_find (local_specializations, tmpl);
return s ? TREE_VALUE (s) : NULL_TREE;
} }
/* Returns non-zero iff DECL is a specialization of TMPL. */ /* Returns non-zero iff DECL is a specialization of TMPL. */
...@@ -885,18 +888,18 @@ unregister_specialization (spec, tmpl) ...@@ -885,18 +888,18 @@ unregister_specialization (spec, tmpl)
return 0; return 0;
} }
/* Like register_specialization, but for local declarations. FN is /* Like register_specialization, but for local declarations. We are
the function in which we are registering SPEC, an instantiation of registering SPEC, an instantiation of TMPL. */
TMPL. */
static tree static tree
register_local_specialization (spec, tmpl, fn) register_local_specialization (spec, tmpl)
tree spec; tree spec;
tree tmpl; tree tmpl;
tree fn;
{ {
DECL_TEMPLATE_SPECIALIZATIONS (tmpl) void **slot;
= tree_cons (fn, spec, DECL_TEMPLATE_SPECIALIZATIONS (tmpl));
slot = htab_find_slot (local_specializations, tmpl, INSERT);
*slot = spec;
return spec; return spec;
} }
...@@ -3307,10 +3310,7 @@ convert_template_argument (parm, arg, args, complain, i, in_decl) ...@@ -3307,10 +3310,7 @@ convert_template_argument (parm, arg, args, complain, i, in_decl)
If REQUIRE_ALL_ARGUMENTS is non-zero, all arguments must be If REQUIRE_ALL_ARGUMENTS is non-zero, all arguments must be
provided in ARGLIST, or else trailing parameters must have default provided in ARGLIST, or else trailing parameters must have default
values. If REQUIRE_ALL_ARGUMENTS is zero, we will attempt argument values. If REQUIRE_ALL_ARGUMENTS is zero, we will attempt argument
deduction for any unspecified trailing arguments. deduction for any unspecified trailing arguments. */
The resulting TREE_VEC is allocated on a temporary obstack, and
must be explicitly copied if it will be permanent. */
static tree static tree
coerce_template_parms (parms, args, in_decl, coerce_template_parms (parms, args, in_decl,
...@@ -5857,7 +5857,8 @@ tsubst_decl (t, args, type, in_decl) ...@@ -5857,7 +5857,8 @@ tsubst_decl (t, args, type, in_decl)
r = TYPE_NAME (type); r = TYPE_NAME (type);
break; break;
} }
else if (!DECL_LANG_SPECIFIC (t)) else if (TREE_CODE (type) == TEMPLATE_TYPE_PARM
|| TREE_CODE (type) == TEMPLATE_TEMPLATE_PARM)
{ {
/* For a template type parameter, we don't have to do /* For a template type parameter, we don't have to do
anything special. */ anything special. */
...@@ -5874,28 +5875,33 @@ tsubst_decl (t, args, type, in_decl) ...@@ -5874,28 +5875,33 @@ tsubst_decl (t, args, type, in_decl)
tree spec; tree spec;
tree tmpl; tree tmpl;
tree ctx; tree ctx;
int local_p;
/* Nobody should be tsubst'ing into non-template variables. */ /* Assume this is a non-local variable. */
my_friendly_assert (DECL_LANG_SPECIFIC (t) local_p = 0;
&& DECL_TEMPLATE_INFO (t) != NULL_TREE, 0);
if (TYPE_P (CP_DECL_CONTEXT (t))) if (TYPE_P (CP_DECL_CONTEXT (t)))
ctx = tsubst_aggr_type (DECL_CONTEXT (t), args, ctx = tsubst_aggr_type (DECL_CONTEXT (t), args,
/*complain=*/1, /*complain=*/1,
in_decl, /*entering_scope=*/1); in_decl, /*entering_scope=*/1);
else else
/* Subsequent calls to pushdecl will fill this in. */ {
ctx = NULL_TREE; /* Subsequent calls to pushdecl will fill this in. */
ctx = NULL_TREE;
if (!DECL_NAMESPACE_SCOPE_P (t))
local_p = 1;
}
/* Check to see if we already have this specialization. */ /* Check to see if we already have this specialization. */
tmpl = DECL_TI_TEMPLATE (t); if (!local_p)
gen_tmpl = most_general_template (tmpl); {
argvec = tsubst (DECL_TI_ARGS (t), args, /*complain=*/1, in_decl); tmpl = DECL_TI_TEMPLATE (t);
if (ctx) gen_tmpl = most_general_template (tmpl);
spec = retrieve_specialization (gen_tmpl, argvec); argvec = tsubst (DECL_TI_ARGS (t), args, /*complain=*/1, in_decl);
spec = retrieve_specialization (gen_tmpl, argvec);
}
else else
spec = retrieve_local_specialization (gen_tmpl, spec = retrieve_local_specialization (t);
current_function_decl);
if (spec) if (spec)
{ {
...@@ -5929,19 +5935,20 @@ tsubst_decl (t, args, type, in_decl) ...@@ -5929,19 +5935,20 @@ tsubst_decl (t, args, type, in_decl)
if (TREE_CODE (r) == VAR_DECL) if (TREE_CODE (r) == VAR_DECL)
DECL_DEAD_FOR_LOCAL (r) = 0; DECL_DEAD_FOR_LOCAL (r) = 0;
/* A static data member declaration is always marked external if (!local_p)
when it is declared in-class, even if an initializer is {
present. We mimic the non-template processing here. */ /* A static data member declaration is always marked
if (ctx) external when it is declared in-class, even if an
DECL_EXTERNAL (r) = 1; initializer is present. We mimic the non-template
processing here. */
DECL_EXTERNAL (r) = 1;
DECL_TEMPLATE_INFO (r) = tree_cons (tmpl, argvec, NULL_TREE); register_specialization (r, gen_tmpl, argvec);
SET_DECL_IMPLICIT_INSTANTIATION (r); DECL_TEMPLATE_INFO (r) = tree_cons (tmpl, argvec, NULL_TREE);
if (ctx) SET_DECL_IMPLICIT_INSTANTIATION (r);
register_specialization (r, gen_tmpl, argvec); }
else else
register_local_specialization (r, gen_tmpl, register_local_specialization (r, t);
current_function_decl);
TREE_CHAIN (r) = NULL_TREE; TREE_CHAIN (r) = NULL_TREE;
if (TREE_CODE (r) == VAR_DECL && TREE_CODE (type) == VOID_TYPE) if (TREE_CODE (r) == VAR_DECL && TREE_CODE (type) == VOID_TYPE)
...@@ -9616,6 +9623,13 @@ instantiate_decl (d, defer_ok) ...@@ -9616,6 +9623,13 @@ instantiate_decl (d, defer_ok)
} }
else if (TREE_CODE (d) == FUNCTION_DECL) else if (TREE_CODE (d) == FUNCTION_DECL)
{ {
/* Set up the list of local specializations. */
my_friendly_assert (local_specializations == NULL, 20000422);
local_specializations = htab_create (37,
htab_hash_pointer,
htab_eq_pointer,
NULL);
/* Set up context. */ /* Set up context. */
start_function (NULL_TREE, d, NULL_TREE, SF_PRE_PARSED); start_function (NULL_TREE, d, NULL_TREE, SF_PRE_PARSED);
store_parm_decls (); store_parm_decls ();
...@@ -9628,6 +9642,10 @@ instantiate_decl (d, defer_ok) ...@@ -9628,6 +9642,10 @@ instantiate_decl (d, defer_ok)
tsubst_expr (DECL_SAVED_TREE (code_pattern), args, tsubst_expr (DECL_SAVED_TREE (code_pattern), args,
/*complain=*/1, tmpl); /*complain=*/1, tmpl);
/* We don't need the local specializations any more. */
htab_delete (local_specializations);
local_specializations = NULL;
/* Finish the function. */ /* Finish the function. */
expand_body (finish_function (0)); expand_body (finish_function (0));
} }
......
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