GCC-3.4.6源代码学习笔记(132)
2010-12-15 10:13
363 查看
5.12.5.2.2.2.1.2.
构建
VAR_DECL
接下来在
cp_parser_simple_declaration
中,调用
cp_parser_init_declarator
来解析声明符部分。调用栈
cp_parser_declarator
à
cp_parser_direct_declarator
à
cp_parser_declarator_id
à
cp_parser_id_expression
à
cp_parser_unqualified_id
à
cp_parser_identifier
,为“
object_
”构建了一个
IDENTIFIER_NODE
。接着在
cp_parser_init_declarator
中,以下代码片段将被执行。
cp_parser_init_declarator (continue)
10095
/* Enter the newly
declared entry in the symbol table. If we're
10096
processing a declaration in a
class-specifier, we wait until
10097
after processing the initializer.
*/
10098
if (!member_p)
10099
{
10100
if
(parser->in_unbraced_linkage_specification_p)
10101
{
10102
decl_specifiers = tree_cons
(error_mark_node,
10103
get_identifier
("extern"),
10104
decl_specifiers);
10105
have_extern_spec
= false;
10106
}
10107
decl = start_decl
(declarator, decl_specifiers,
10108
is_initialized, attributes,
prefix_attributes);
10109
}
“
SmallObject<> object_
”是一个变量声明。一个新的树节点需要在中间树中创建来代表这个实体。在这次调用中,实参
intialized
是
false
,
attributes
及
prefix_attributes
都是
NULL
。
3670
tree
3671
start_decl
(tree declarator,
in decl.c
3672
tree declspecs,
3673
int initialized,
3674
tree attributes,
3675
tree prefix_attributes)
3676
{
3677
tree decl;
3678
tree type, tem;
3679
tree context;
3680
3681
/* This should only
be done once on the top most decl.
*/
3682
if (have_extern_spec
)
3683
{
3684
declspecs = tree_cons (NULL_TREE,
get_identifier ("extern"),
3685
declspecs);
3686
have_extern_spec
= false;
3687
}
3688
3689
/* An object
declared as __attribute__((deprecated)) suppresses
3690
warnings of uses of other
deprecated items.
*/
3691
if (lookup_attribute ("deprecated",
attributes))
3692
deprecated_state
= DEPRECATED_SUPPRESS;
3693
3694
attributes = chainon (attributes,
prefix_attributes);
3695
3696
decl = grokdeclarator (declarator, declspecs,
NORMAL,
initialized,
3697
&attributes);
3698
3699
deprecated_state
= DEPRECATED_NORMAL;
3700
3701
if (decl == NULL_TREE || TREE_CODE (decl) ==
VOID_TYPE)
3702
return
error_mark_node;
3703
3704
type = TREE_TYPE (decl);
3705
3706
if (type == error_mark_node)
3707
return
error_mark_node;
3708
3709
context = DECL_CONTEXT (decl);
3710
3711
if (initialized && context &&
TREE_CODE (context) == NAMESPACE_DECL
3712
&& context != current_namespace
&& TREE_CODE (decl) == VAR_DECL)
3713
{
3714
/* When parsing the initializer, lookup should use the
object's
3715
namespace.
*/
3716
push_decl_namespace (context);
3717
}
3718
3719
/* We are only
interested in class contexts, later.
*/
3720
if (context && TREE_CODE (context) ==
NAMESPACE_DECL)
3721
context = NULL_TREE;
作为声明的一种,期望的是某种
DECL
节点,因此需要
grokdeclarator
分析
decl-specifiers
及声明符部分来构成这个节点。
6462
tree
6463
grokdeclarator
(tree declarator,
in decl.c
6464
tree declspecs,
6465
enum
decl_context decl_context,
6466
int initialized,
6467
tree* attrlist)
6468
{
6469
RID_BIT_TYPE specbits;
6470
int nclasses = 0;
6471
tree spec;
6472
tree type = NULL_TREE;
6473
int longlong = 0;
6474
int type_quals;
6475
int virtualp, explicitp, friendp, inlinep,
staticp;
6476
int
explicit_int = 0;
6477
int explicit_char = 0;
6478
int defaulted_int = 0;
6479
int extern_langp = 0;
6480
tree dependant_name = NULL_TREE;
6481
6482
tree typedef_decl = NULL_TREE;
6483
const
char
*name;
6484
tree typedef_type = NULL_TREE;
6485
int funcdef_flag = 0;
6486
enum
tree_code innermost_code = ERROR_MARK;
6487
int bitfield = 0;
6488
#if
0
6489
/* See the code
below that used this.
*/
6490
tree decl_attr = NULL_TREE;
6491
#endif
6492
6493
/* Keep track of
what sort of function is being processed
6494
so that we can warn about
default return values, or explicit
6495
return values which do not
match prescribed defaults.
*/
6496
special_function_kind sfk = sfk_none;
6497
6498
tree dname = NULL_TREE;
6499
tree ctype = current_class_type;
6500
tree ctor_return_type = NULL_TREE;
6501
enum
overload_flags flags = NO_SPECIAL;
6502
tree quals = NULL_TREE;
6503
tree raises = NULL_TREE;
6504
int template_count = 0;
6505
tree in_namespace = NULL_TREE;
6506
tree returned_attrs = NULL_TREE;
6507
tree scope = NULL_TREE;
6508
tree parms = NULL_TREE;
6509
6510
RIDBIT_RESET_ALL (specbits);
6511
if (decl_context == FUNCDEF)
6512
funcdef_flag = 1, decl_context = NORMAL;
6513
else if (decl_context == MEMFUNCDEF)
6514
funcdef_flag = -1, decl_context = FIELD;
6515
else if (decl_context == BITFIELD)
6516
bitfield = 1, decl_context = FIELD;
6517
6518
/* Look inside a
declarator for the name being declared
6519
and get it as a string, for an
error message.
*/
6520
{
6521
tree *next = &declarator;
6522
tree decl;
6523
name = NULL;
6524
6525
while
(next
&& *next)
6526
{
6527
decl = *next;
6528
switch
(TREE_CODE
(decl))
6529
{
…
6629
case
IDENTIFIER_NODE:
6630
if (TREE_CODE (decl) == IDENTIFIER_NODE)
6631
dname = decl;
6632
6633
next =
0;
6634
6635
if (C_IS_RESERVED_WORD (dname))
6636
{
…
6640
}
6641
else if (!IDENTIFIER_TYPENAME_P (dname))
6642
name = IDENTIFIER_POINTER (dname);
…
6654
break
;
6655
6656
}
6657
}
6658
}
…
6828
/* Look through the
decl specs and record which ones appear.
6829
Some typespecs are defined as
built-in typenames.
6830
Others, the ones that are
modifiers of other types,
6831
are represented by bits in
SPECBITS: set the bits for
6832
the modifiers that appear.
Storage class keywords are also in SPECBITS.
6833
6834
If there is a typedef name or
a type, store the type in TYPE.
6835
This includes builtin typedefs
such as `int'.
6836
6837
Set EXPLICIT_INT if the type is
`int' or `char' and did not
6838
come from a user typedef.
6839
6840
Set LONGLONG if `long' is
mentioned twice.
6841
6842
For C++, constructors and
destructors have their own fast treatment.
*/
6843
6844
for
(spec =
declspecs; spec; spec = TREE_CHAIN (spec))
6845
{
6846
int i;
6847
tree id;
6848
6849
/* Certain parse
errors slip through. For example,
6850
`int class;' is not caught
by the parser. Try
6851
weakly to recover here.
*/
6852
if (TREE_CODE (spec) != TREE_LIST)
6853
return
0;
6854
6855
id = TREE_VALUE (spec);
6856
6857
/* If the entire
declaration is itself tagged as deprecated then
6858
suppress reports of
deprecated items.
*/
6859
if (!adding_implicit_members
&& id &&
TREE_DEPRECATED (id))
6860
{
6861
if (deprecated_state
!= DEPRECATED_SUPPRESS)
6862
warn_deprecated_use (id);
6863
}
6864
6865
if (TREE_CODE (id) == IDENTIFIER_NODE)
6866
{
…
6933
}
6934
else if (TREE_CODE (id) == TYPE_DECL)
6935
{
6936
if (type)
6937
error ("multiple declarations `%T'
and `%T'", type,
6938
TREE_TYPE (id));
6939
else
6940
{
6941
type = TREE_TYPE (id);
6942
TREE_VALUE (spec) = type;
6943
typedef_decl = id;
6944
}
6945
goto
found;
6946
}
6947
if (type)
6948
error ("two or more data types in
declaration of `%s'", name);
6949
else if (TREE_CODE (id) == IDENTIFIER_NODE)
6950
{
…
6960
}
6961
else if (id != error_mark_node)
6962
/* Can't change
CLASS nodes into RECORD nodes here!
*/
6963
type = id;
6964
6965
found: ;
6966
}
6967
6968
#if
0
6969
/* See the code
below that used this.
*/
6970
if (typedef_decl)
6971
decl_attr = DECL_ATTRIBUTES (typedef_decl);
6972
#endif
6973
typedef_type = type;
…
7019
ctype = NULL_TREE;
…
7337
scope = get_scope_of_declarator (declarator);
7338
7339
/* Now figure out
the structure of the declarator proper.
7340
Descend through it, creating
more complex types, until we reach
7341
the declared identifier (or
NULL_TREE, in an abstract declarator).
*/
7342
7343
while
(declarator && TREE_CODE (declarator) != IDENTIFIER_NODE
7344
&& TREE_CODE (declarator) !=
TEMPLATE_ID_EXPR)
7345
{
…
7840
}
…
8163
{
8164
tree decl;
8165
8166
if (decl_context == PARM)
8167
{
…
8172
}
8173
else if (decl_context == FIELD)
8174
{
…
8427
}
8428
else if (TREE_CODE (type) == FUNCTION_TYPE
8429
|| TREE_CODE (type) == METHOD_TYPE)
8430
{
…
8514
}
8515
else
8516
{
8517
/* It's a
variable.
*/
8518
8519
/* An
uninitialized decl with `extern' is a reference.
*/
8520
decl = grokvardecl
(type, declarator, &specbits,
8521
initialized,
8522
(type_quals &
TYPE_QUAL_CONST) != 0,
8523
ctype ? ctype :
in_namespace);
8524
bad_specifiers
(decl, "variable", virtualp, quals != NULL_TREE,
8525
inlinep, friendp, raises !=
NULL_TREE);
8526
8527
if (ctype)
8528
{
…
8547
}
8548
}
8549
8550
my_friendly_assert (!RIDBIT_SETP
(RID_MUTABLE, specbits), 19990927);
8551
8552
/* Record
`register' declaration for warnings on &
8553
and in case doing stupid
register allocation.
*/
8554
8555
if (RIDBIT_SETP (RID_REGISTER, specbits))
8556
DECL_REGISTER (decl) = 1;
8557
8558
if (RIDBIT_SETP (RID_EXTERN, specbits))
8559
DECL_THIS_EXTERN (decl) = 1;
8560
8561
if (RIDBIT_SETP (RID_STATIC, specbits))
8562
DECL_THIS_STATIC (decl) = 1;
8563
8564
/* Record
constancy and volatility. There's no need to do this
8565
when processing a template;
we'll do this for the instantiated
8566
declaration based on the
type of DECL.
*/
8567
if (!processing_template_decl)
8568
c_apply_type_quals_to_decl (type_quals, decl);
8569
8570
return
decl;
8571
}
8572
}
在上面的代码中,显然
6525
行的
WHILE
块验证声明符部分;而
6844
行的
FOR
块验证并提前对应的
type-specifier
。注意到在
6941
行,
type
指向上一节中所构建的
RECORD_TYPE
。
接着
type
及
declarator
将被组合起来由
grokvardecl
来构成期望的
VAR_DECL
。注意到对于我们的情形,在调用期间,参数
scope
是
NULL
,
constp
是
false
,
initialized
是
false
,而
specbits_in
包含了
0
。
5885
static
tree
5886
grokvardecl
(tree type,
in decl.c
5887
tree name,
5888
RID_BIT_TYPE * specbits_in,
5889
int initialized,
5890
int constp,
5891
tree scope)
5892
{
5893
tree decl;
5894
tree explicit_scope;
5895
RID_BIT_TYPE specbits;
5896
5897
my_friendly_assert (!name || TREE_CODE (name)
== IDENTIFIER_NODE,
5898
20020808);
5899
5900
specbits = *specbits_in;
5901
5902
/* Compute the
scope in which to place the variable, but remember
5903
whether or not that scope was
explicitly specified by the user.
*/
5904
explicit_scope = scope;
5905
if (!scope)
5906
{
5907
/* An explicit
"extern" specifier indicates a namespace-scope
5908
variable.
*/
5909
if (RIDBIT_SETP (RID_EXTERN, specbits))
5910
scope = current_namespace;
5911
else if (!at_function_scope_p ())
5912
{
5913
scope = current_scope ();
5914
if (!scope)
5915
scope = current_namespace;
5916
}
5917
}
5918
5919
if (scope
5920
&& (/*
If the variable is a namespace-scope variable declared in a
5921
template, we need
DECL_LANG_SPECIFIC.
*/
5922
(TREE_CODE (scope) == NAMESPACE_DECL
&& processing_template_decl)
5923
/*
Similarly for namespace-scope variables with language linkage
5924
other than C++.
*/
5925
|| (TREE_CODE (scope) ==
NAMESPACE_DECL
5926
&& current_lang_name !=
lang_name_cplusplus)
5927
/*
Similarly for static data members.
*/
5928
|| TYPE_P (scope)))
5929
decl = build_lang_decl (VAR_DECL, name,
type);
5930
else
5931
decl = build_decl
(VAR_DECL, name, type);
5932
5933
if (explicit_scope && TREE_CODE
(explicit_scope) == NAMESPACE_DECL)
5934
set_decl_namespace (decl, explicit_scope,
0);
5935
else
5936
DECL_CONTEXT (decl) = scope;
5937
5938
if (name && scope && current_lang_name
!= lang_name_c)
5939
/* We can't mangle lazily here because we
don't have any
5940
way to recover whether or
not a variable was `extern
5941
"C"' later.
*/
5942
mangle_decl (decl);
5943
5944
if (RIDBIT_SETP (RID_EXTERN, specbits))
5945
{
5946
DECL_THIS_EXTERN (decl) = 1;
5947
DECL_EXTERNAL (decl) = !initialized;
5948
}
5949
5950
/* In class
context, static means one per class,
5951
public access, and static
storage.
*/
5952
if (DECL_CLASS_SCOPE_P (decl))
5953
{
5954
TREE_PUBLIC (decl) = 1;
5955
TREE_STATIC (decl) = 1;
5956
DECL_EXTERNAL (decl) = 0;
5957
}
5958
/* At top level,
either `static' or no s.c.
makes a definition
5959
(perhaps tentative), and
absence of `static' makes it public.
*/
5960
else if (toplevel_bindings_p ())
5961
{
5962
TREE_PUBLIC (decl) = (RIDBIT_NOTSETP
(RID_STATIC, specbits)
5963
&&
(DECL_THIS_EXTERN (decl) || ! constp));
5964
TREE_STATIC (decl) = ! DECL_EXTERNAL
(decl);
5965
}
5966
/* Not at top
level, only `static' makes a static definition.
*/
5967
else
5968
{
5969
TREE_STATIC (decl) = !! RIDBIT_SETP
(RID_STATIC, specbits);
5970
TREE_PUBLIC (decl) = DECL_EXTERNAL (decl);
5971
}
5972
5973
if (RIDBIT_SETP (RID_THREAD, specbits))
5974
{
5975
if (targetm
.have_tls)
5976
DECL_THREAD_LOCAL (decl) = 1;
5977
else
5978
/* A mere
warning is sure to result in improper semantics
5979
at runtime. Don't bother
to allow this to compile.
*/
5980
error ("thread-local storage not
supported for this target");
5981
}
5982
5983
if (TREE_PUBLIC (decl))
5984
{
5985
/* [basic.link]:
A name with no linkage (notably, the name of a class
5986
or enumeration declared in a
local scope) shall not be used to
5987
declare an entity with
linkage.
5988
5989
Only check this for public
decls for now.
*/
5990
tree t = no_linkage_check (TREE_TYPE
(decl));
5991
if (t)
5992
{
5993
if (TYPE_ANONYMOUS_P (t))
5994
/* Ignore for
now; `enum { foo } e' is pretty common.
*/;
5995
else
5996
pedwarn ("non-local variable `%#D'
uses local type `%T'",
5997
decl, t);
5998
}
5999
}
6000
6001
return
decl;
6002
}
在这一步之后,我们得到下图中的
VAR_DECL
。看到该节点的
context
域是
NULL
,因为我们不在类作用域中。
(
点此打开
)
start_decl (continue)
3832
/* Enter this
declaration into the symbol table.
*/
3833
tem = maybe_push_decl (decl);
3834
3835
if (processing_template_decl)
3836
tem = push_template_decl (tem);
3837
if (tem == error_mark_node)
3838
return
error_mark_node;
3839
3840
#if ! defined (
ASM_OUTPUT_BSS) && ! defined
(ASM_OUTPUT_ALIGNED_BSS)
3841
/* Tell the
back-end to use or not use .common as appropriate. If we say
3842
-fconserve-space, we want this
to save .data space, at the expense of
3843
wrong semantics. If we say
-fno-conserve-space, we want this to
3844
produce errors about redefs;
to do this we force variables into the
3845
data segment.
*/
3846
DECL_COMMON (tem) = ((TREE_CODE (tem) !=
VAR_DECL
3847
||
!DECL_THREAD_LOCAL (tem))
3848
&& (flag_conserve_space
|| ! TREE_PUBLIC (tem)));
3849
#endif
3850
3851
if (! processing_template_decl)
3852
start_decl_1 (tem);
3853
3854
return
tem;
3855
}
作为一个
context
域为
NULL
的
VAR_DECL
节点,
maybe_push_decl
为
decl
调用
pushdecl
。而对于我们的例子,在
3852
行的
start_decl_1
不做任何事。
566
tree
567
pushdecl (tree
x)
in name-lookup.c
568
{
569
tree t;
570
tree name;
571
int need_new_binding;
572
573
timevar_push (TV_NAME_LOOKUP);
574
575
need_new_binding = 1;
576
577
if (DECL_TEMPLATE_PARM_P (x))
578
/* Template
parameters have no context; they are not X::T even
579
when declared
within a class or namespace.
*/
580
;
581
else
582
{
583
if (current_function_decl
&& x != current_function_decl
584
/* A local
declaration for a function doesn't constitute
585
nesting.
*/
586
&& TREE_CODE (x) !=
FUNCTION_DECL
587
/* A local
declaration for an `extern' variable is in the
588
scope of the
current namespace, not the current
589
function.
*/
590
&& !(TREE_CODE (x) == VAR_DECL
&& DECL_EXTERNAL (x))
591
&& !DECL_CONTEXT (x))
592
DECL_CONTEXT (x) = current_function_decl
;
…
602
}
603
604
name = DECL_NAME (x);
605
if (name)
606
{
607
int different_binding_level = 0;
…
615
/* In case this
decl was explicitly namespace-qualified, look it
616
up in its
namespace context.
*/
617
if (DECL_NAMESPACE_SCOPE_P (x) &&
namespace_bindings_p ())
618
t = namespace_binding (name, DECL_CONTEXT
(x));
619
else
620
t = lookup_name_current_level (name);
…
828
/* This name is
new in its binding level.
829
Install the new
declaration and return it.
*/
830
if (namespace_bindings_p
())
831
{
…
872
}
873
else
874
{
875
/* Here to
install a non-global value.
*/
876
tree oldlocal = IDENTIFIER_VALUE (name);
877
tree oldglobal =
IDENTIFIER_NAMESPACE_VALUE (name);
878
879
if (need_new_binding)
880
{
881
push_local_binding (name, x, 0);
882
/* Because
push_local_binding will hook X on to the
883
current_binding_level's name list, we don't want to
884
do that
again below.
*/
885
need_new_binding = 0;
886
}
…
1003
}
1004
1005
if (TREE_CODE (x) == VAR_DECL)
1006
maybe_register_incomplete_var (x);
1007
}
…
1015
POP_TIMEVAR_AND_RETURN (TV_NAME_LOOKUP, x);
1016
}
我们已经多次看过
pushdecl
;再次我们在上面给出该函数得到执行部分的代码。看到在
1006
行的
maybe_register_incomplete_var
对非外部的
VAR_DECL
不做处理。在退出
start_decl
时,我们得到如下的中间树。
(
点此打开
)
cp_parser_init_declarator (continue)
10111
/* Enter the SCOPE.
That way unqualified names appearing in the
10112
initializer will be looked up in
SCOPE.
*/
10113
if (scope)
10114
pop_p = push_scope (scope);
10115
10116
/* Perform deferred
access control checks, now that we know in which
10117
SCOPE the declared entity resides.
*/
10118
if (!member_p && decl)
10119
{
10120
tree saved_current_function_decl =
NULL_TREE;
10121
10122
/* If the entity
being declared is a function, pretend that we
10123
are in its scope. If it is a `friend', it
may have access to
10124
things that would not otherwise be
accessible.
*/
10125
if (TREE_CODE (decl) == FUNCTION_DECL)
10126
{
10127
saved_current_function_decl = current_function_decl
;
10128
current_function_decl
= decl;
10129
}
10130
10131
/* Perform the
access control checks for the declarator and the
10132
the decl-specifiers.
*/
10133
perform_deferred_access_checks
();
10134
10135
/* Restore the saved
value.
*/
10136
if (TREE_CODE (decl) == FUNCTION_DECL)
10137
current_function_decl
=
saved_current_function_decl;
10138
}
10139
10140
/* Parse the
initializer.
*/
10141
if (is_initialized)
10142
initializer = cp_parser_initializer
(parser,
10143
&is_parenthesized_init,
10144
&is_non_constant_init);
10145
else
10146
{
10147
initializer = NULL_TREE;
10148
is_parenthesized_init = false;
10149
is_non_constant_init = true;
10150
}
…
10178
/* Finish processing the declaration. But,
skip friend
10179
declarations.
*/
10180
if (!friend_p && decl)
10181
cp_finish_decl
(decl,
10182
initializer,
10183
asm_specification,
10184
/* If
the initializer is in parentheses, then this is
10185
a direct-initialization, which means that an
10186
`explicit' constructor is OK.
Otherwise, an
10187
`explicit' constructor
cannot be used.
*/
10188
((is_parenthesized_init ||
!is_initialized)
10189
? 0 : LOOKUP_ONLYCONVERTING));
10190
10191
/* Remember whether
or not variables were initialized by
10192
constant-expressions.
*/
10193
if (decl && TREE_CODE (decl) ==
VAR_DECL
10194
&& is_initialized &&
!is_non_constant_init)
10195
DECL_INITIALIZED_BY_CONSTANT_EXPRESSION_P
(decl) = true;
10196
10197
return
decl;
10198
}
注意到在为
template-id
及
VAR_DECL
构建了节点之后,正是为相关声明符及
decl-specifier
执行延迟访问检查的时机。看到访问控制检查失败不会停止解析器。
构建
VAR_DECL
接下来在
cp_parser_simple_declaration
中,调用
cp_parser_init_declarator
来解析声明符部分。调用栈
cp_parser_declarator
à
cp_parser_direct_declarator
à
cp_parser_declarator_id
à
cp_parser_id_expression
à
cp_parser_unqualified_id
à
cp_parser_identifier
,为“
object_
”构建了一个
IDENTIFIER_NODE
。接着在
cp_parser_init_declarator
中,以下代码片段将被执行。
cp_parser_init_declarator (continue)
10095
/* Enter the newly
declared entry in the symbol table. If we're
10096
processing a declaration in a
class-specifier, we wait until
10097
after processing the initializer.
*/
10098
if (!member_p)
10099
{
10100
if
(parser->in_unbraced_linkage_specification_p)
10101
{
10102
decl_specifiers = tree_cons
(error_mark_node,
10103
get_identifier
("extern"),
10104
decl_specifiers);
10105
have_extern_spec
= false;
10106
}
10107
decl = start_decl
(declarator, decl_specifiers,
10108
is_initialized, attributes,
prefix_attributes);
10109
}
“
SmallObject<> object_
”是一个变量声明。一个新的树节点需要在中间树中创建来代表这个实体。在这次调用中,实参
intialized
是
false
,
attributes
及
prefix_attributes
都是
NULL
。
3670
tree
3671
start_decl
(tree declarator,
in decl.c
3672
tree declspecs,
3673
int initialized,
3674
tree attributes,
3675
tree prefix_attributes)
3676
{
3677
tree decl;
3678
tree type, tem;
3679
tree context;
3680
3681
/* This should only
be done once on the top most decl.
*/
3682
if (have_extern_spec
)
3683
{
3684
declspecs = tree_cons (NULL_TREE,
get_identifier ("extern"),
3685
declspecs);
3686
have_extern_spec
= false;
3687
}
3688
3689
/* An object
declared as __attribute__((deprecated)) suppresses
3690
warnings of uses of other
deprecated items.
*/
3691
if (lookup_attribute ("deprecated",
attributes))
3692
deprecated_state
= DEPRECATED_SUPPRESS;
3693
3694
attributes = chainon (attributes,
prefix_attributes);
3695
3696
decl = grokdeclarator (declarator, declspecs,
NORMAL,
initialized,
3697
&attributes);
3698
3699
deprecated_state
= DEPRECATED_NORMAL;
3700
3701
if (decl == NULL_TREE || TREE_CODE (decl) ==
VOID_TYPE)
3702
return
error_mark_node;
3703
3704
type = TREE_TYPE (decl);
3705
3706
if (type == error_mark_node)
3707
return
error_mark_node;
3708
3709
context = DECL_CONTEXT (decl);
3710
3711
if (initialized && context &&
TREE_CODE (context) == NAMESPACE_DECL
3712
&& context != current_namespace
&& TREE_CODE (decl) == VAR_DECL)
3713
{
3714
/* When parsing the initializer, lookup should use the
object's
3715
namespace.
*/
3716
push_decl_namespace (context);
3717
}
3718
3719
/* We are only
interested in class contexts, later.
*/
3720
if (context && TREE_CODE (context) ==
NAMESPACE_DECL)
3721
context = NULL_TREE;
作为声明的一种,期望的是某种
DECL
节点,因此需要
grokdeclarator
分析
decl-specifiers
及声明符部分来构成这个节点。
6462
tree
6463
grokdeclarator
(tree declarator,
in decl.c
6464
tree declspecs,
6465
enum
decl_context decl_context,
6466
int initialized,
6467
tree* attrlist)
6468
{
6469
RID_BIT_TYPE specbits;
6470
int nclasses = 0;
6471
tree spec;
6472
tree type = NULL_TREE;
6473
int longlong = 0;
6474
int type_quals;
6475
int virtualp, explicitp, friendp, inlinep,
staticp;
6476
int
explicit_int = 0;
6477
int explicit_char = 0;
6478
int defaulted_int = 0;
6479
int extern_langp = 0;
6480
tree dependant_name = NULL_TREE;
6481
6482
tree typedef_decl = NULL_TREE;
6483
const
char
*name;
6484
tree typedef_type = NULL_TREE;
6485
int funcdef_flag = 0;
6486
enum
tree_code innermost_code = ERROR_MARK;
6487
int bitfield = 0;
6488
#if
0
6489
/* See the code
below that used this.
*/
6490
tree decl_attr = NULL_TREE;
6491
#endif
6492
6493
/* Keep track of
what sort of function is being processed
6494
so that we can warn about
default return values, or explicit
6495
return values which do not
match prescribed defaults.
*/
6496
special_function_kind sfk = sfk_none;
6497
6498
tree dname = NULL_TREE;
6499
tree ctype = current_class_type;
6500
tree ctor_return_type = NULL_TREE;
6501
enum
overload_flags flags = NO_SPECIAL;
6502
tree quals = NULL_TREE;
6503
tree raises = NULL_TREE;
6504
int template_count = 0;
6505
tree in_namespace = NULL_TREE;
6506
tree returned_attrs = NULL_TREE;
6507
tree scope = NULL_TREE;
6508
tree parms = NULL_TREE;
6509
6510
RIDBIT_RESET_ALL (specbits);
6511
if (decl_context == FUNCDEF)
6512
funcdef_flag = 1, decl_context = NORMAL;
6513
else if (decl_context == MEMFUNCDEF)
6514
funcdef_flag = -1, decl_context = FIELD;
6515
else if (decl_context == BITFIELD)
6516
bitfield = 1, decl_context = FIELD;
6517
6518
/* Look inside a
declarator for the name being declared
6519
and get it as a string, for an
error message.
*/
6520
{
6521
tree *next = &declarator;
6522
tree decl;
6523
name = NULL;
6524
6525
while
(next
&& *next)
6526
{
6527
decl = *next;
6528
switch
(TREE_CODE
(decl))
6529
{
…
6629
case
IDENTIFIER_NODE:
6630
if (TREE_CODE (decl) == IDENTIFIER_NODE)
6631
dname = decl;
6632
6633
next =
0;
6634
6635
if (C_IS_RESERVED_WORD (dname))
6636
{
…
6640
}
6641
else if (!IDENTIFIER_TYPENAME_P (dname))
6642
name = IDENTIFIER_POINTER (dname);
…
6654
break
;
6655
6656
}
6657
}
6658
}
…
6828
/* Look through the
decl specs and record which ones appear.
6829
Some typespecs are defined as
built-in typenames.
6830
Others, the ones that are
modifiers of other types,
6831
are represented by bits in
SPECBITS: set the bits for
6832
the modifiers that appear.
Storage class keywords are also in SPECBITS.
6833
6834
If there is a typedef name or
a type, store the type in TYPE.
6835
This includes builtin typedefs
such as `int'.
6836
6837
Set EXPLICIT_INT if the type is
`int' or `char' and did not
6838
come from a user typedef.
6839
6840
Set LONGLONG if `long' is
mentioned twice.
6841
6842
For C++, constructors and
destructors have their own fast treatment.
*/
6843
6844
for
(spec =
declspecs; spec; spec = TREE_CHAIN (spec))
6845
{
6846
int i;
6847
tree id;
6848
6849
/* Certain parse
errors slip through. For example,
6850
`int class;' is not caught
by the parser. Try
6851
weakly to recover here.
*/
6852
if (TREE_CODE (spec) != TREE_LIST)
6853
return
0;
6854
6855
id = TREE_VALUE (spec);
6856
6857
/* If the entire
declaration is itself tagged as deprecated then
6858
suppress reports of
deprecated items.
*/
6859
if (!adding_implicit_members
&& id &&
TREE_DEPRECATED (id))
6860
{
6861
if (deprecated_state
!= DEPRECATED_SUPPRESS)
6862
warn_deprecated_use (id);
6863
}
6864
6865
if (TREE_CODE (id) == IDENTIFIER_NODE)
6866
{
…
6933
}
6934
else if (TREE_CODE (id) == TYPE_DECL)
6935
{
6936
if (type)
6937
error ("multiple declarations `%T'
and `%T'", type,
6938
TREE_TYPE (id));
6939
else
6940
{
6941
type = TREE_TYPE (id);
6942
TREE_VALUE (spec) = type;
6943
typedef_decl = id;
6944
}
6945
goto
found;
6946
}
6947
if (type)
6948
error ("two or more data types in
declaration of `%s'", name);
6949
else if (TREE_CODE (id) == IDENTIFIER_NODE)
6950
{
…
6960
}
6961
else if (id != error_mark_node)
6962
/* Can't change
CLASS nodes into RECORD nodes here!
*/
6963
type = id;
6964
6965
found: ;
6966
}
6967
6968
#if
0
6969
/* See the code
below that used this.
*/
6970
if (typedef_decl)
6971
decl_attr = DECL_ATTRIBUTES (typedef_decl);
6972
#endif
6973
typedef_type = type;
…
7019
ctype = NULL_TREE;
…
7337
scope = get_scope_of_declarator (declarator);
7338
7339
/* Now figure out
the structure of the declarator proper.
7340
Descend through it, creating
more complex types, until we reach
7341
the declared identifier (or
NULL_TREE, in an abstract declarator).
*/
7342
7343
while
(declarator && TREE_CODE (declarator) != IDENTIFIER_NODE
7344
&& TREE_CODE (declarator) !=
TEMPLATE_ID_EXPR)
7345
{
…
7840
}
…
8163
{
8164
tree decl;
8165
8166
if (decl_context == PARM)
8167
{
…
8172
}
8173
else if (decl_context == FIELD)
8174
{
…
8427
}
8428
else if (TREE_CODE (type) == FUNCTION_TYPE
8429
|| TREE_CODE (type) == METHOD_TYPE)
8430
{
…
8514
}
8515
else
8516
{
8517
/* It's a
variable.
*/
8518
8519
/* An
uninitialized decl with `extern' is a reference.
*/
8520
decl = grokvardecl
(type, declarator, &specbits,
8521
initialized,
8522
(type_quals &
TYPE_QUAL_CONST) != 0,
8523
ctype ? ctype :
in_namespace);
8524
bad_specifiers
(decl, "variable", virtualp, quals != NULL_TREE,
8525
inlinep, friendp, raises !=
NULL_TREE);
8526
8527
if (ctype)
8528
{
…
8547
}
8548
}
8549
8550
my_friendly_assert (!RIDBIT_SETP
(RID_MUTABLE, specbits), 19990927);
8551
8552
/* Record
`register' declaration for warnings on &
8553
and in case doing stupid
register allocation.
*/
8554
8555
if (RIDBIT_SETP (RID_REGISTER, specbits))
8556
DECL_REGISTER (decl) = 1;
8557
8558
if (RIDBIT_SETP (RID_EXTERN, specbits))
8559
DECL_THIS_EXTERN (decl) = 1;
8560
8561
if (RIDBIT_SETP (RID_STATIC, specbits))
8562
DECL_THIS_STATIC (decl) = 1;
8563
8564
/* Record
constancy and volatility. There's no need to do this
8565
when processing a template;
we'll do this for the instantiated
8566
declaration based on the
type of DECL.
*/
8567
if (!processing_template_decl)
8568
c_apply_type_quals_to_decl (type_quals, decl);
8569
8570
return
decl;
8571
}
8572
}
在上面的代码中,显然
6525
行的
WHILE
块验证声明符部分;而
6844
行的
FOR
块验证并提前对应的
type-specifier
。注意到在
6941
行,
type
指向上一节中所构建的
RECORD_TYPE
。
接着
type
及
declarator
将被组合起来由
grokvardecl
来构成期望的
VAR_DECL
。注意到对于我们的情形,在调用期间,参数
scope
是
NULL
,
constp
是
false
,
initialized
是
false
,而
specbits_in
包含了
0
。
5885
static
tree
5886
grokvardecl
(tree type,
in decl.c
5887
tree name,
5888
RID_BIT_TYPE * specbits_in,
5889
int initialized,
5890
int constp,
5891
tree scope)
5892
{
5893
tree decl;
5894
tree explicit_scope;
5895
RID_BIT_TYPE specbits;
5896
5897
my_friendly_assert (!name || TREE_CODE (name)
== IDENTIFIER_NODE,
5898
20020808);
5899
5900
specbits = *specbits_in;
5901
5902
/* Compute the
scope in which to place the variable, but remember
5903
whether or not that scope was
explicitly specified by the user.
*/
5904
explicit_scope = scope;
5905
if (!scope)
5906
{
5907
/* An explicit
"extern" specifier indicates a namespace-scope
5908
variable.
*/
5909
if (RIDBIT_SETP (RID_EXTERN, specbits))
5910
scope = current_namespace;
5911
else if (!at_function_scope_p ())
5912
{
5913
scope = current_scope ();
5914
if (!scope)
5915
scope = current_namespace;
5916
}
5917
}
5918
5919
if (scope
5920
&& (/*
If the variable is a namespace-scope variable declared in a
5921
template, we need
DECL_LANG_SPECIFIC.
*/
5922
(TREE_CODE (scope) == NAMESPACE_DECL
&& processing_template_decl)
5923
/*
Similarly for namespace-scope variables with language linkage
5924
other than C++.
*/
5925
|| (TREE_CODE (scope) ==
NAMESPACE_DECL
5926
&& current_lang_name !=
lang_name_cplusplus)
5927
/*
Similarly for static data members.
*/
5928
|| TYPE_P (scope)))
5929
decl = build_lang_decl (VAR_DECL, name,
type);
5930
else
5931
decl = build_decl
(VAR_DECL, name, type);
5932
5933
if (explicit_scope && TREE_CODE
(explicit_scope) == NAMESPACE_DECL)
5934
set_decl_namespace (decl, explicit_scope,
0);
5935
else
5936
DECL_CONTEXT (decl) = scope;
5937
5938
if (name && scope && current_lang_name
!= lang_name_c)
5939
/* We can't mangle lazily here because we
don't have any
5940
way to recover whether or
not a variable was `extern
5941
"C"' later.
*/
5942
mangle_decl (decl);
5943
5944
if (RIDBIT_SETP (RID_EXTERN, specbits))
5945
{
5946
DECL_THIS_EXTERN (decl) = 1;
5947
DECL_EXTERNAL (decl) = !initialized;
5948
}
5949
5950
/* In class
context, static means one per class,
5951
public access, and static
storage.
*/
5952
if (DECL_CLASS_SCOPE_P (decl))
5953
{
5954
TREE_PUBLIC (decl) = 1;
5955
TREE_STATIC (decl) = 1;
5956
DECL_EXTERNAL (decl) = 0;
5957
}
5958
/* At top level,
either `static' or no s.c.
makes a definition
5959
(perhaps tentative), and
absence of `static' makes it public.
*/
5960
else if (toplevel_bindings_p ())
5961
{
5962
TREE_PUBLIC (decl) = (RIDBIT_NOTSETP
(RID_STATIC, specbits)
5963
&&
(DECL_THIS_EXTERN (decl) || ! constp));
5964
TREE_STATIC (decl) = ! DECL_EXTERNAL
(decl);
5965
}
5966
/* Not at top
level, only `static' makes a static definition.
*/
5967
else
5968
{
5969
TREE_STATIC (decl) = !! RIDBIT_SETP
(RID_STATIC, specbits);
5970
TREE_PUBLIC (decl) = DECL_EXTERNAL (decl);
5971
}
5972
5973
if (RIDBIT_SETP (RID_THREAD, specbits))
5974
{
5975
if (targetm
.have_tls)
5976
DECL_THREAD_LOCAL (decl) = 1;
5977
else
5978
/* A mere
warning is sure to result in improper semantics
5979
at runtime. Don't bother
to allow this to compile.
*/
5980
error ("thread-local storage not
supported for this target");
5981
}
5982
5983
if (TREE_PUBLIC (decl))
5984
{
5985
/* [basic.link]:
A name with no linkage (notably, the name of a class
5986
or enumeration declared in a
local scope) shall not be used to
5987
declare an entity with
linkage.
5988
5989
Only check this for public
decls for now.
*/
5990
tree t = no_linkage_check (TREE_TYPE
(decl));
5991
if (t)
5992
{
5993
if (TYPE_ANONYMOUS_P (t))
5994
/* Ignore for
now; `enum { foo } e' is pretty common.
*/;
5995
else
5996
pedwarn ("non-local variable `%#D'
uses local type `%T'",
5997
decl, t);
5998
}
5999
}
6000
6001
return
decl;
6002
}
在这一步之后,我们得到下图中的
VAR_DECL
。看到该节点的
context
域是
NULL
,因为我们不在类作用域中。
(
点此打开
)
start_decl (continue)
3832
/* Enter this
declaration into the symbol table.
*/
3833
tem = maybe_push_decl (decl);
3834
3835
if (processing_template_decl)
3836
tem = push_template_decl (tem);
3837
if (tem == error_mark_node)
3838
return
error_mark_node;
3839
3840
#if ! defined (
ASM_OUTPUT_BSS) && ! defined
(ASM_OUTPUT_ALIGNED_BSS)
3841
/* Tell the
back-end to use or not use .common as appropriate. If we say
3842
-fconserve-space, we want this
to save .data space, at the expense of
3843
wrong semantics. If we say
-fno-conserve-space, we want this to
3844
produce errors about redefs;
to do this we force variables into the
3845
data segment.
*/
3846
DECL_COMMON (tem) = ((TREE_CODE (tem) !=
VAR_DECL
3847
||
!DECL_THREAD_LOCAL (tem))
3848
&& (flag_conserve_space
|| ! TREE_PUBLIC (tem)));
3849
#endif
3850
3851
if (! processing_template_decl)
3852
start_decl_1 (tem);
3853
3854
return
tem;
3855
}
作为一个
context
域为
NULL
的
VAR_DECL
节点,
maybe_push_decl
为
decl
调用
pushdecl
。而对于我们的例子,在
3852
行的
start_decl_1
不做任何事。
566
tree
567
pushdecl (tree
x)
in name-lookup.c
568
{
569
tree t;
570
tree name;
571
int need_new_binding;
572
573
timevar_push (TV_NAME_LOOKUP);
574
575
need_new_binding = 1;
576
577
if (DECL_TEMPLATE_PARM_P (x))
578
/* Template
parameters have no context; they are not X::T even
579
when declared
within a class or namespace.
*/
580
;
581
else
582
{
583
if (current_function_decl
&& x != current_function_decl
584
/* A local
declaration for a function doesn't constitute
585
nesting.
*/
586
&& TREE_CODE (x) !=
FUNCTION_DECL
587
/* A local
declaration for an `extern' variable is in the
588
scope of the
current namespace, not the current
589
function.
*/
590
&& !(TREE_CODE (x) == VAR_DECL
&& DECL_EXTERNAL (x))
591
&& !DECL_CONTEXT (x))
592
DECL_CONTEXT (x) = current_function_decl
;
…
602
}
603
604
name = DECL_NAME (x);
605
if (name)
606
{
607
int different_binding_level = 0;
…
615
/* In case this
decl was explicitly namespace-qualified, look it
616
up in its
namespace context.
*/
617
if (DECL_NAMESPACE_SCOPE_P (x) &&
namespace_bindings_p ())
618
t = namespace_binding (name, DECL_CONTEXT
(x));
619
else
620
t = lookup_name_current_level (name);
…
828
/* This name is
new in its binding level.
829
Install the new
declaration and return it.
*/
830
if (namespace_bindings_p
())
831
{
…
872
}
873
else
874
{
875
/* Here to
install a non-global value.
*/
876
tree oldlocal = IDENTIFIER_VALUE (name);
877
tree oldglobal =
IDENTIFIER_NAMESPACE_VALUE (name);
878
879
if (need_new_binding)
880
{
881
push_local_binding (name, x, 0);
882
/* Because
push_local_binding will hook X on to the
883
current_binding_level's name list, we don't want to
884
do that
again below.
*/
885
need_new_binding = 0;
886
}
…
1003
}
1004
1005
if (TREE_CODE (x) == VAR_DECL)
1006
maybe_register_incomplete_var (x);
1007
}
…
1015
POP_TIMEVAR_AND_RETURN (TV_NAME_LOOKUP, x);
1016
}
我们已经多次看过
pushdecl
;再次我们在上面给出该函数得到执行部分的代码。看到在
1006
行的
maybe_register_incomplete_var
对非外部的
VAR_DECL
不做处理。在退出
start_decl
时,我们得到如下的中间树。
(
点此打开
)
cp_parser_init_declarator (continue)
10111
/* Enter the SCOPE.
That way unqualified names appearing in the
10112
initializer will be looked up in
SCOPE.
*/
10113
if (scope)
10114
pop_p = push_scope (scope);
10115
10116
/* Perform deferred
access control checks, now that we know in which
10117
SCOPE the declared entity resides.
*/
10118
if (!member_p && decl)
10119
{
10120
tree saved_current_function_decl =
NULL_TREE;
10121
10122
/* If the entity
being declared is a function, pretend that we
10123
are in its scope. If it is a `friend', it
may have access to
10124
things that would not otherwise be
accessible.
*/
10125
if (TREE_CODE (decl) == FUNCTION_DECL)
10126
{
10127
saved_current_function_decl = current_function_decl
;
10128
current_function_decl
= decl;
10129
}
10130
10131
/* Perform the
access control checks for the declarator and the
10132
the decl-specifiers.
*/
10133
perform_deferred_access_checks
();
10134
10135
/* Restore the saved
value.
*/
10136
if (TREE_CODE (decl) == FUNCTION_DECL)
10137
current_function_decl
=
saved_current_function_decl;
10138
}
10139
10140
/* Parse the
initializer.
*/
10141
if (is_initialized)
10142
initializer = cp_parser_initializer
(parser,
10143
&is_parenthesized_init,
10144
&is_non_constant_init);
10145
else
10146
{
10147
initializer = NULL_TREE;
10148
is_parenthesized_init = false;
10149
is_non_constant_init = true;
10150
}
…
10178
/* Finish processing the declaration. But,
skip friend
10179
declarations.
*/
10180
if (!friend_p && decl)
10181
cp_finish_decl
(decl,
10182
initializer,
10183
asm_specification,
10184
/* If
the initializer is in parentheses, then this is
10185
a direct-initialization, which means that an
10186
`explicit' constructor is OK.
Otherwise, an
10187
`explicit' constructor
cannot be used.
*/
10188
((is_parenthesized_init ||
!is_initialized)
10189
? 0 : LOOKUP_ONLYCONVERTING));
10190
10191
/* Remember whether
or not variables were initialized by
10192
constant-expressions.
*/
10193
if (decl && TREE_CODE (decl) ==
VAR_DECL
10194
&& is_initialized &&
!is_non_constant_init)
10195
DECL_INITIALIZED_BY_CONSTANT_EXPRESSION_P
(decl) = true;
10196
10197
return
decl;
10198
}
注意到在为
template-id
及
VAR_DECL
构建了节点之后,正是为相关声明符及
decl-specifier
执行延迟访问检查的时机。看到访问控制检查失败不会停止解析器。
相关文章推荐
- GCC-3.4.6源代码学习笔记(118)
- GCC-3.4.6源代码学习笔记(47)
- GCC-3.4.6源代码学习笔记(20)
- GCC-3.4.6源代码学习笔记(131)
- GCC-3.4.6源代码学习笔记(154)
- GCC-3.4.6源代码学习笔记(78)
- GCC-3.4.6源代码学习笔记(179)
- GCC-3.4.6源代码学习笔记(57)
- GCC-3.4.6源代码学习笔记(139-续1)
- GCC-3.4.6源代码学习笔记(140)
- GCC-3.4.6源代码学习笔记(12)
- GCC-3.4.6源代码学习笔记(115)
- GCC-3.4.6源代码学习笔记(33)
- GCC-3.4.6源代码学习笔记(143)
- GCC-3.4.6源代码学习笔记(147-续2)
- GCC-3.4.6源代码学习笔记(133)
- GCC-3.4.6源代码学习笔记(23)
- GCC-3.4.6源代码学习笔记(1)
- GCC-3.4.6源代码学习笔记(137)
- GCC-3.4.6源代码学习笔记(163)