Commit ce4a0391 by Mark Mitchell Committed by Mark Mitchell

cp-tree.h (finish_unary_op_expr): New function.

	* cp-tree.h (finish_unary_op_expr): New function.
	(finish_id_expr): Likewise.
	(begin_new_placement): Likewise.
	(finish_new_placement): Likewise.
	(finish_declarator): Likewise.
	(finish_translation_unit): Likewise.
	(finish_parmlist): Likewise.
	(begin_class_definition): Likewise.
	(finish_class_definition): Likewise.
	(finish_default_args): Likewise.
	(finish_inline_definitions): Likewise.
	* parse.y (GCC_ASM_KEYWORD): Remove.
	(TYPENAME_ELLIPSIS): Likewise.
	* parse.c: Regenerated.
	Use new functions in semantics.c in the actions for many rules.
	* gxx.gperf (GCC_ASM_KEYWORD): Just use ASM_KEYWORD.
	* hash.h: Regenerated.
	* semantics.c (finish_expr_stmt): Allow NULL expr.
	(finish_unary_op_expr): New function, containing
	code previously in parse.y.
	(finish_id_expr): Likewise.
	(begin_new_placement): Likewise.
	(finish_new_placement): Likewise.
	(finish_declarator): Likewise.
	(finish_translation_unit): Likewise.
	(finish_parmlist): Likewise.
	(begin_class_definition): Likewise.
	(finish_class_definition): Likewise.
	(finish_default_args): Likewise.
	(finish_inline_definitions): Likewise.

From-SVN: r19660
parent 4785faf1
Mon May 11 00:03:34 1998 Mark Mitchell <mmitchell@usa.net>
* cp-tree.h (finish_unary_op_expr): New function.
(finish_id_expr): Likewise.
(begin_new_placement): Likewise.
(finish_new_placement): Likewise.
(finish_declarator): Likewise.
(finish_translation_unit): Likewise.
(finish_parmlist): Likewise.
(begin_class_definition): Likewise.
(finish_class_definition): Likewise.
(finish_default_args): Likewise.
(finish_inline_definitions): Likewise.
* parse.y (GCC_ASM_KEYWORD): Remove.
(TYPENAME_ELLIPSIS): Likewise.
* parse.c: Regenerated.
Use new functions in semantics.c in the actions for many rules.
* gxx.gperf (GCC_ASM_KEYWORD): Just use ASM_KEYWORD.
* hash.h: Regenerated.
* semantics.c (finish_expr_stmt): Allow NULL expr.
(finish_unary_op_expr): New function, containing
code previously in parse.y.
(finish_id_expr): Likewise.
(begin_new_placement): Likewise.
(finish_new_placement): Likewise.
(finish_declarator): Likewise.
(finish_translation_unit): Likewise.
(finish_parmlist): Likewise.
(begin_class_definition): Likewise.
(finish_class_definition): Likewise.
(finish_default_args): Likewise.
(finish_inline_definitions): Likewise.
Sun May 10 23:43:13 1998 Mark Mitchell <mmitchell@usa.net> Sun May 10 23:43:13 1998 Mark Mitchell <mmitchell@usa.net>
* typeck.c (build_c_cast): Don't decay arrays and functions to * typeck.c (build_c_cast): Don't decay arrays and functions to
......
...@@ -2634,10 +2634,21 @@ extern tree finish_qualified_object_call_expr PROTO((tree, tree, tree)); ...@@ -2634,10 +2634,21 @@ extern tree finish_qualified_object_call_expr PROTO((tree, tree, tree));
extern tree finish_pseudo_destructor_call_expr PROTO((tree, tree, tree)); extern tree finish_pseudo_destructor_call_expr PROTO((tree, tree, tree));
extern tree finish_globally_qualified_member_call_expr PROTO ((tree, tree)); extern tree finish_globally_qualified_member_call_expr PROTO ((tree, tree));
extern tree finish_label_address_expr PROTO((tree)); extern tree finish_label_address_expr PROTO((tree));
extern tree finish_unary_op_expr PROTO((enum tree_code, tree));
extern tree finish_id_expr PROTO((tree));
extern int begin_new_placement PROTO((void));
extern tree finish_new_placement PROTO((tree, int));
extern int begin_function_definition PROTO((tree, tree)); extern int begin_function_definition PROTO((tree, tree));
extern tree begin_constructor_declarator PROTO((tree, tree)); extern tree begin_constructor_declarator PROTO((tree, tree));
extern tree finish_declarator PROTO((tree, tree, tree, tree, int));
extern void finish_translation_unit PROTO((void));
extern tree finish_template_type_parm PROTO((tree, tree)); extern tree finish_template_type_parm PROTO((tree, tree));
extern tree finish_template_template_parm PROTO((tree, tree)); extern tree finish_template_template_parm PROTO((tree, tree));
extern tree finish_parmlist PROTO((tree, int));
extern tree begin_class_definition PROTO((tree));
extern tree finish_class_definition PROTO((tree, tree, tree, int));
extern void finish_default_args PROTO((void));
extern void begin_inline_definitions PROTO((void));
/* in sig.c */ /* in sig.c */
extern tree build_signature_pointer_type PROTO((tree, int, int)); extern tree build_signature_pointer_type PROTO((tree, int, int));
......
...@@ -5,8 +5,8 @@ struct resword { char *name; short token; enum rid rid;}; ...@@ -5,8 +5,8 @@ struct resword { char *name; short token; enum rid rid;};
%% %%
__alignof, ALIGNOF, NORID __alignof, ALIGNOF, NORID
__alignof__, ALIGNOF, NORID __alignof__, ALIGNOF, NORID
__asm, GCC_ASM_KEYWORD, NORID __asm, ASM_KEYWORD, NORID
__asm__, GCC_ASM_KEYWORD, NORID __asm__, ASM_KEYWORD, NORID
__attribute, ATTRIBUTE, NORID __attribute, ATTRIBUTE, NORID
__attribute__, ATTRIBUTE, NORID __attribute__, ATTRIBUTE, NORID
__complex, TYPESPEC, RID_COMPLEX __complex, TYPESPEC, RID_COMPLEX
......
/* C code produced by gperf version 2.5 (GNU C++ version) */ /* C code produced by gperf version 2.5 (GNU C++ version) */
/* Command-line: gperf -p -j1 -g -o -t -N is_reserved_word -k1,4,$,7 gxx.gperf */ /* Command-line: gperf -p -j1 -g -o -t -N is_reserved_word -k1,4,7,$ ../../../gcc/cp/gxx.gperf */
/* Command-line: gperf -p -j1 -g -o -t -N is_reserved_word -k1,4,$,7 gplus.gperf */
struct resword { char *name; short token; enum rid rid;}; struct resword { char *name; short token; enum rid rid;};
#define TOTAL_KEYWORDS 103 #define TOTAL_KEYWORDS 103
...@@ -72,7 +73,7 @@ is_reserved_word (str, len) ...@@ -72,7 +73,7 @@ is_reserved_word (str, len)
{"",}, {"",},
{"true", CXX_TRUE, NORID,}, {"true", CXX_TRUE, NORID,},
{"",}, {"",},
{"__asm__", GCC_ASM_KEYWORD, NORID}, {"__asm__", ASM_KEYWORD, NORID},
{"",}, {"",}, {"",}, {"",}, {"",}, {"",}, {"",}, {"",}, {"",}, {"",}, {"",}, {"",}, {"",}, {"",},
{"this", THIS, NORID,}, {"this", THIS, NORID,},
{"",}, {"",},
...@@ -104,7 +105,7 @@ is_reserved_word (str, len) ...@@ -104,7 +105,7 @@ is_reserved_word (str, len)
{"short", TYPESPEC, RID_SHORT,}, {"short", TYPESPEC, RID_SHORT,},
{"__imag__", IMAGPART, NORID}, {"__imag__", IMAGPART, NORID},
{"delete", DELETE, NORID,}, {"delete", DELETE, NORID,},
{"__asm", GCC_ASM_KEYWORD, NORID}, {"__asm", ASM_KEYWORD, NORID},
{"xor", '^', NORID,}, {"xor", '^', NORID,},
{"not_eq", EQCOMPARE, NORID,}, {"not_eq", EQCOMPARE, NORID,},
{"xor_eq", ASSIGN, NORID,}, {"xor_eq", ASSIGN, NORID,},
......
...@@ -129,7 +129,7 @@ empty_parms () ...@@ -129,7 +129,7 @@ empty_parms ()
/* the reserved words */ /* the reserved words */
/* SCO include files test "ASM", so use something else. */ /* SCO include files test "ASM", so use something else. */
%token SIZEOF ENUM /* STRUCT UNION */ IF ELSE WHILE DO FOR SWITCH CASE DEFAULT %token SIZEOF ENUM /* STRUCT UNION */ IF ELSE WHILE DO FOR SWITCH CASE DEFAULT
%token BREAK CONTINUE RETURN GOTO ASM_KEYWORD GCC_ASM_KEYWORD TYPEOF ALIGNOF %token BREAK CONTINUE RETURN GOTO ASM_KEYWORD TYPEOF ALIGNOF
%token SIGOF %token SIGOF
%token ATTRIBUTE EXTENSION LABEL %token ATTRIBUTE EXTENSION LABEL
%token REALPART IMAGPART %token REALPART IMAGPART
...@@ -228,7 +228,7 @@ empty_parms () ...@@ -228,7 +228,7 @@ empty_parms ()
%type <ftype> structsp typespecqual_reserved parm named_parm full_parm %type <ftype> structsp typespecqual_reserved parm named_parm full_parm
/* C++ extensions */ /* C++ extensions */
%token <ttype> TYPENAME_ELLIPSIS PTYPENAME %token <ttype> PTYPENAME
%token <ttype> PRE_PARSED_FUNCTION_DECL EXTERN_LANG_STRING ALL %token <ttype> PRE_PARSED_FUNCTION_DECL EXTERN_LANG_STRING ALL
%token <ttype> PRE_PARSED_CLASS_DECL DEFARG DEFARG_MARKER %token <ttype> PRE_PARSED_CLASS_DECL DEFARG DEFARG_MARKER
%type <ttype> component_constructor_declarator %type <ttype> component_constructor_declarator
...@@ -328,15 +328,7 @@ parse_decl(declarator, specs_attrs, attributes, initialized, decl) ...@@ -328,15 +328,7 @@ parse_decl(declarator, specs_attrs, attributes, initialized, decl)
program: program:
/* empty */ /* empty */
| extdefs | extdefs
{ { finish_translation_unit (); }
/* In case there were missing closebraces,
get us back to the global binding level. */
while (! toplevel_bindings_p ())
poplevel (0, 0, 0);
while (current_namespace != global_namespace)
pop_namespace ();
finish_file ();
}
; ;
/* the reason for the strange actions in this rule /* the reason for the strange actions in this rule
...@@ -373,7 +365,6 @@ extension: ...@@ -373,7 +365,6 @@ extension:
asm_keyword: asm_keyword:
ASM_KEYWORD ASM_KEYWORD
| GCC_ASM_KEYWORD
; ;
lang_extdef: lang_extdef:
...@@ -1010,11 +1001,7 @@ unary_expr: ...@@ -1010,11 +1001,7 @@ unary_expr:
| '~' cast_expr | '~' cast_expr
{ $$ = build_x_unary_op (BIT_NOT_EXPR, $2); } { $$ = build_x_unary_op (BIT_NOT_EXPR, $2); }
| unop cast_expr %prec UNARY | unop cast_expr %prec UNARY
{ $$ = build_x_unary_op ($1, $2); { $$ = finish_unary_op_expr ($1, $2); }
if ($1 == NEGATE_EXPR && TREE_CODE ($2) == INTEGER_CST)
TREE_NEGATED_INT ($$) = 1;
overflow_warning ($$);
}
/* Refer to the address of a label as a pointer. */ /* Refer to the address of a label as a pointer. */
| ANDAND identifier | ANDAND identifier
{ if (pedantic) { if (pedantic)
...@@ -1075,13 +1062,15 @@ unary_expr: ...@@ -1075,13 +1062,15 @@ unary_expr:
; ;
new_placement: new_placement:
'(' nonnull_exprlist ')' '('
{ $$ = $2; } { $<itype>$ = begin_new_placement (); }
| '{' nonnull_exprlist '}' nonnull_exprlist ')'
{ { $$ = finish_new_placement ($3, $<itype>1); }
$$ = $2; | '{'
pedwarn ("old style placement syntax, use () instead"); { cp_pedwarn ("old style placement syntax, use () instead");
} $<itype>$ = begin_new_placement (); }
nonnull_exprlist '}'
{ $$ = finish_new_placement ($3, $<itype>1); }
; ;
new_initializer: new_initializer:
...@@ -1112,13 +1101,11 @@ new_initializer: ...@@ -1112,13 +1101,11 @@ new_initializer:
/* This is necessary to postpone reduction of `int ((int)(int)(int))'. */ /* This is necessary to postpone reduction of `int ((int)(int)(int))'. */
regcast_or_absdcl: regcast_or_absdcl:
'(' type_id ')' %prec EMPTY '(' type_id ')' %prec EMPTY
{ $2.t = tree_cons (NULL_TREE, $2.t, void_list_node); { $2.t = finish_parmlist (build_tree_list (NULL_TREE, $2.t), 0);
TREE_PARMLIST ($2.t) = 1;
$$ = make_call_declarator (NULL_TREE, $2.t, NULL_TREE, NULL_TREE); $$ = make_call_declarator (NULL_TREE, $2.t, NULL_TREE, NULL_TREE);
check_for_new_type ("cast", $2); } check_for_new_type ("cast", $2); }
| regcast_or_absdcl '(' type_id ')' %prec EMPTY | regcast_or_absdcl '(' type_id ')' %prec EMPTY
{ $3.t = tree_cons (NULL_TREE, $3.t, void_list_node); { $3.t = finish_parmlist (build_tree_list (NULL_TREE, $3.t), 0);
TREE_PARMLIST ($3.t) = 1;
$$ = make_call_declarator ($$, $3.t, NULL_TREE, NULL_TREE); $$ = make_call_declarator ($$, $3.t, NULL_TREE, NULL_TREE);
check_for_new_type ("cast", $3); } check_for_new_type ("cast", $3); }
; ;
...@@ -1272,10 +1259,10 @@ direct_notype_declarator: ...@@ -1272,10 +1259,10 @@ direct_notype_declarator:
primary: primary:
notype_unqualified_id notype_unqualified_id
{ {
if (TREE_CODE ($$) == BIT_NOT_EXPR) if (TREE_CODE ($1) == BIT_NOT_EXPR)
$$ = build_x_unary_op (BIT_NOT_EXPR, TREE_OPERAND ($$, 0)); $$ = build_x_unary_op (BIT_NOT_EXPR, TREE_OPERAND ($1, 0));
else if (TREE_CODE ($$) != TEMPLATE_ID_EXPR) else
$$ = do_identifier ($$, 1); $$ = finish_id_expr ($1);
} }
| CONSTANT | CONSTANT
| boolean.literal | boolean.literal
...@@ -2005,54 +1992,21 @@ structsp: ...@@ -2005,54 +1992,21 @@ structsp:
/* C++ extensions, merged with C to avoid shift/reduce conflicts */ /* C++ extensions, merged with C to avoid shift/reduce conflicts */
| class_head left_curly | class_head left_curly
opt.component_decl_list '}' maybe_attribute opt.component_decl_list '}' maybe_attribute
{ {
int semi; int semi;
$<ttype>$ = $1;
#if 0
/* Need to rework class nesting in the
presence of nested classes, etc. */
shadow_tag (CLASSTYPE_AS_LIST ($1)); */
#endif
if (yychar == YYEMPTY) if (yychar == YYEMPTY)
yychar = YYLEX; yychar = YYLEX;
semi = yychar == ';'; semi = yychar == ';';
/* finish_struct nukes this anyway; if
finish_exception does too, then it can go. */
if (semi)
note_got_semicolon ($1);
if (TREE_CODE ($1) == ENUMERAL_TYPE)
;
else
{
$<ttype>$ = finish_struct ($1, $3, $5, semi);
if (semi) note_got_semicolon ($<ttype>$);
}
pop_obstacks ();
if (! semi) $<ttype>$ = finish_class_definition ($1, $3, $5, semi);
check_for_missing_semicolon ($1);
if (current_scope () == current_function_decl)
do_pending_defargs ();
} }
pending_defargs pending_defargs
{ { finish_default_args (); }
if (pending_inlines
&& current_scope () == current_function_decl)
do_pending_inlines ();
}
pending_inlines pending_inlines
{ { $$.t = $<ttype>6;
$$.t = $<ttype>6;
$$.new_type_flag = 1; $$.new_type_flag = 1;
if (current_class_type == NULL_TREE) begin_inline_definitions (); }
clear_inline_text_obstack ();
/* Undo the begin_tree in left_curly. */
end_tree ();
}
| class_head %prec EMPTY | class_head %prec EMPTY
{ {
$$.new_type_flag = 0; $$.new_type_flag = 0;
...@@ -2334,92 +2288,7 @@ base_class_access_list: ...@@ -2334,92 +2288,7 @@ base_class_access_list:
left_curly: left_curly:
'{' '{'
{ tree t = $<ttype>0; { $<ttype>0 = begin_class_definition ($<ttype>0); }
push_obstacks_nochange ();
end_temporary_allocation ();
if (t == error_mark_node
|| ! IS_AGGR_TYPE (t))
{
t = $<ttype>0 = make_lang_type (RECORD_TYPE);
pushtag (make_anon_name (), t, 0);
}
if (TYPE_SIZE (t))
duplicate_tag_error (t);
if (TYPE_SIZE (t) || TYPE_BEING_DEFINED (t))
{
t = make_lang_type (TREE_CODE (t));
pushtag (TYPE_IDENTIFIER ($<ttype>0), t, 0);
$<ttype>0 = t;
}
if (processing_template_decl && TYPE_CONTEXT (t)
&& TREE_CODE (TYPE_CONTEXT (t)) != NAMESPACE_DECL
&& ! current_class_type)
push_template_decl (TYPE_STUB_DECL (t));
pushclass (t, 0);
TYPE_BEING_DEFINED (t) = 1;
if (IS_AGGR_TYPE (t) && CLASSTYPE_USE_TEMPLATE (t))
{
if (CLASSTYPE_IMPLICIT_INSTANTIATION (t)
&& TYPE_SIZE (t) == NULL_TREE)
{
SET_CLASSTYPE_TEMPLATE_SPECIALIZATION (t);
if (processing_template_decl)
push_template_decl (TYPE_MAIN_DECL (t));
}
else if (CLASSTYPE_TEMPLATE_INSTANTIATION (t))
cp_error ("specialization after instantiation of `%T'", t);
}
/* Reset the interface data, at the earliest possible
moment, as it might have been set via a class foo;
before. */
/* Don't change signatures. */
if (! IS_SIGNATURE (t))
{
extern tree pending_vtables;
int needs_writing;
tree name = TYPE_IDENTIFIER (t);
if (! ANON_AGGRNAME_P (name))
{
CLASSTYPE_INTERFACE_ONLY (t) = interface_only;
SET_CLASSTYPE_INTERFACE_UNKNOWN_X
(t, interface_unknown);
}
/* Record how to set the access of this class's
virtual functions. If write_virtuals == 2 or 3, then
inline virtuals are ``extern inline''. */
switch (write_virtuals)
{
case 0:
case 1:
needs_writing = 1;
break;
case 2:
needs_writing = !! value_member (name, pending_vtables);
break;
case 3:
needs_writing = ! CLASSTYPE_INTERFACE_ONLY (t)
&& CLASSTYPE_INTERFACE_KNOWN (t);
break;
default:
needs_writing = 0;
}
CLASSTYPE_VTABLE_NEEDS_WRITING (t) = needs_writing;
}
#if 0
t = TYPE_IDENTIFIER ($<ttype>0);
if (t && IDENTIFIER_TEMPLATE (t))
overload_template_name (t, 1);
#endif
reset_specialization();
/* In case this is a local class within a template
function, we save the current tree structure so
that we can get it back later. */
begin_tree ();
}
; ;
self_reference: self_reference:
...@@ -3497,8 +3366,7 @@ parmlist: ...@@ -3497,8 +3366,7 @@ parmlist:
} }
| complex_parmlist | complex_parmlist
| type_id | type_id
{ $$ = tree_cons (NULL_TREE, $1.t, void_list_node); { $$ = finish_parmlist (build_tree_list (NULL_TREE, $1.t), 0);
TREE_PARMLIST ($$) = 1;
check_for_new_type ("inside parameter list", $1); } check_for_new_type ("inside parameter list", $1); }
; ;
...@@ -3506,49 +3374,24 @@ parmlist: ...@@ -3506,49 +3374,24 @@ parmlist:
as it is ambiguous and must be disambiguated elsewhere. */ as it is ambiguous and must be disambiguated elsewhere. */
complex_parmlist: complex_parmlist:
parms parms
{ { $$ = finish_parmlist ($$, 0); }
$$ = chainon ($$, void_list_node);
TREE_PARMLIST ($$) = 1;
}
| parms_comma ELLIPSIS | parms_comma ELLIPSIS
{ { $$ = finish_parmlist ($1, 1); }
TREE_PARMLIST ($$) = 1;
}
/* C++ allows an ellipsis without a separating ',' */ /* C++ allows an ellipsis without a separating ',' */
| parms ELLIPSIS | parms ELLIPSIS
{ { $$ = finish_parmlist ($1, 1); }
TREE_PARMLIST ($$) = 1;
}
| type_id ELLIPSIS | type_id ELLIPSIS
{ { $$ = finish_parmlist (build_tree_list (NULL_TREE,
$$ = build_tree_list (NULL_TREE, $1.t); $1.t), 1); }
TREE_PARMLIST ($$) = 1;
}
| ELLIPSIS | ELLIPSIS
{ { $$ = finish_parmlist (NULL_TREE, 1); }
$$ = NULL_TREE;
}
| TYPENAME_ELLIPSIS
{
TREE_PARMLIST ($$) = 1;
}
| parms TYPENAME_ELLIPSIS
{
TREE_PARMLIST ($$) = 1;
}
| type_id TYPENAME_ELLIPSIS
{
$$ = build_tree_list (NULL_TREE, $1.t);
TREE_PARMLIST ($$) = 1;
}
| parms ':' | parms ':'
{ {
/* This helps us recover from really nasty /* This helps us recover from really nasty
parse errors, for example, a missing right parse errors, for example, a missing right
parenthesis. */ parenthesis. */
yyerror ("possibly missing ')'"); yyerror ("possibly missing ')'");
$$ = chainon ($$, void_list_node); $$ = finish_parmlist ($1, 0);
TREE_PARMLIST ($$) = 1;
yyungetc (':', 0); yyungetc (':', 0);
yychar = ')'; yychar = ')';
} }
...@@ -3558,8 +3401,8 @@ complex_parmlist: ...@@ -3558,8 +3401,8 @@ complex_parmlist:
parse errors, for example, a missing right parse errors, for example, a missing right
parenthesis. */ parenthesis. */
yyerror ("possibly missing ')'"); yyerror ("possibly missing ')'");
$$ = tree_cons (NULL_TREE, $1.t, void_list_node); $$ = finish_parmlist (build_tree_list (NULL_TREE,
TREE_PARMLIST ($$) = 1; $1.t), 0);
yyungetc (':', 0); yyungetc (':', 0);
yychar = ')'; yychar = ')';
} }
......
...@@ -66,19 +66,23 @@ void ...@@ -66,19 +66,23 @@ void
finish_expr_stmt (expr) finish_expr_stmt (expr)
tree expr; tree expr;
{ {
if (!processing_template_decl) if (expr != NULL_TREE)
{ {
emit_line_note (input_filename, lineno); if (!processing_template_decl)
/* Do default conversion if safe and possibly important, {
in case within ({...}). */ emit_line_note (input_filename, lineno);
if ((TREE_CODE (TREE_TYPE (expr)) == ARRAY_TYPE /* Do default conversion if safe and possibly important,
&& lvalue_p (expr)) in case within ({...}). */
|| TREE_CODE (TREE_TYPE (expr)) == FUNCTION_TYPE) if ((TREE_CODE (TREE_TYPE (expr)) == ARRAY_TYPE
expr = default_conversion (expr); && lvalue_p (expr))
|| TREE_CODE (TREE_TYPE (expr)) == FUNCTION_TYPE)
expr = default_conversion (expr);
}
cplus_expand_expr_stmt (expr);
clear_momentary ();
} }
cplus_expand_expr_stmt (expr);
clear_momentary ();
finish_stmt (); finish_stmt ();
} }
...@@ -993,6 +997,58 @@ finish_label_address_expr (label) ...@@ -993,6 +997,58 @@ finish_label_address_expr (label)
return result; return result;
} }
/* Finish an expression of the form CODE EXPR. */
tree
finish_unary_op_expr (code, expr)
enum tree_code code;
tree expr;
{
tree result = build_x_unary_op (code, expr);
if (code == NEGATE_EXPR && TREE_CODE (expr) == INTEGER_CST)
TREE_NEGATED_INT (result) = 1;
overflow_warning (result);
return result;
}
/* Finish an id-expression. */
tree
finish_id_expr (expr)
tree expr;
{
if (TREE_CODE (expr) == IDENTIFIER_NODE)
expr = do_identifier (expr, 1);
return expr;
}
/* Begin a new-placement. */
int
begin_new_placement ()
{
/* The arguments to a placement new might be passed to a
deallocation function, in the event that the allocation throws an
exception. Since we don't expand exception handlers until the
end of a function, we must make sure the arguments stay around
that long. */
return suspend_momentary ();
}
/* Finish a new-placement. The ARGS are the placement arguments. The
COOKIE is the value returned by the previous call to
begin_new_placement. */
tree
finish_new_placement (args, cookie)
tree args;
int cookie;
{
resume_momentary (cookie);
return args;
}
/* Begin a function defniition declared with DECL_SPECS and /* Begin a function defniition declared with DECL_SPECS and
DECLARATOR. Returns non-zero if the function-declaration is DECLARATOR. Returns non-zero if the function-declaration is
legal. */ legal. */
...@@ -1031,6 +1087,35 @@ begin_constructor_declarator (scope, name) ...@@ -1031,6 +1087,35 @@ begin_constructor_declarator (scope, name)
return result; return result;
} }
/* Finish an init-declarator. Returns a DECL. */
tree
finish_declarator (declarator, declspecs, attributes,
prefix_attributes, initialized)
tree declarator;
tree declspecs;
tree attributes;
tree prefix_attributes;
int initialized;
{
return start_decl (declarator, declspecs, initialized, attributes,
prefix_attributes);
}
/* Finish a transltation unit. */
void
finish_translation_unit ()
{
/* In case there were missing closebraces,
get us back to the global binding level. */
while (! toplevel_bindings_p ())
poplevel (0, 0, 0);
while (current_namespace != global_namespace)
pop_namespace ();
finish_file ();
}
/* Finish a template type parameter, specified as AGGR IDENTIFIER. /* Finish a template type parameter, specified as AGGR IDENTIFIER.
Returns the parameter. */ Returns the parameter. */
...@@ -1067,3 +1152,182 @@ finish_template_template_parm (aggr, identifier) ...@@ -1067,3 +1152,182 @@ finish_template_template_parm (aggr, identifier)
return finish_template_type_parm (aggr, tmpl); return finish_template_type_parm (aggr, tmpl);
} }
/* Finish a parameter list, indicated by PARMS. If ELLIPSIS is
non-zero, the parameter list was terminated by a `...'. */
tree
finish_parmlist (parms, ellipsis)
tree parms;
int ellipsis;
{
if (!ellipsis)
chainon (parms, void_list_node);
/* We mark the PARMS as a parmlist so that declarator processing can
disambiguate certain constructs. */
if (parms != NULL_TREE)
TREE_PARMLIST (parms) = 1;
return parms;
}
/* Begin a class definition, as indicated by T. */
tree
begin_class_definition (t)
tree t;
{
tree new_type = t;
push_obstacks_nochange ();
end_temporary_allocation ();
if (t == error_mark_node
|| ! IS_AGGR_TYPE (t))
{
t = new_type = make_lang_type (RECORD_TYPE);
pushtag (make_anon_name (), t, 0);
}
if (TYPE_SIZE (t))
duplicate_tag_error (t);
if (TYPE_SIZE (t) || TYPE_BEING_DEFINED (t))
{
t = make_lang_type (TREE_CODE (t));
pushtag (TYPE_IDENTIFIER (t), t, 0);
new_type = t;
}
if (processing_template_decl && TYPE_CONTEXT (t)
&& TREE_CODE (TYPE_CONTEXT (t)) != NAMESPACE_DECL
&& ! current_class_type)
push_template_decl (TYPE_STUB_DECL (t));
pushclass (t, 0);
TYPE_BEING_DEFINED (t) = 1;
if (IS_AGGR_TYPE (t) && CLASSTYPE_USE_TEMPLATE (t))
{
if (CLASSTYPE_IMPLICIT_INSTANTIATION (t)
&& TYPE_SIZE (t) == NULL_TREE)
{
SET_CLASSTYPE_TEMPLATE_SPECIALIZATION (t);
if (processing_template_decl)
push_template_decl (TYPE_MAIN_DECL (t));
}
else if (CLASSTYPE_TEMPLATE_INSTANTIATION (t))
cp_error ("specialization after instantiation of `%T'", t);
}
/* Reset the interface data, at the earliest possible
moment, as it might have been set via a class foo;
before. */
/* Don't change signatures. */
if (! IS_SIGNATURE (t))
{
extern tree pending_vtables;
int needs_writing;
tree name = TYPE_IDENTIFIER (t);
if (! ANON_AGGRNAME_P (name))
{
CLASSTYPE_INTERFACE_ONLY (t) = interface_only;
SET_CLASSTYPE_INTERFACE_UNKNOWN_X
(t, interface_unknown);
}
/* Record how to set the access of this class's
virtual functions. If write_virtuals == 2 or 3, then
inline virtuals are ``extern inline''. */
switch (write_virtuals)
{
case 0:
case 1:
needs_writing = 1;
break;
case 2:
needs_writing = !! value_member (name, pending_vtables);
break;
case 3:
needs_writing = ! CLASSTYPE_INTERFACE_ONLY (t)
&& CLASSTYPE_INTERFACE_KNOWN (t);
break;
default:
needs_writing = 0;
}
CLASSTYPE_VTABLE_NEEDS_WRITING (t) = needs_writing;
}
#if 0
t = TYPE_IDENTIFIER ($<ttype>0);
if (t && IDENTIFIER_TEMPLATE (t))
overload_template_name (t, 1);
#endif
reset_specialization();
/* In case this is a local class within a template
function, we save the current tree structure so
that we can get it back later. */
begin_tree ();
return new_type;
}
/* Finish a class definition T, with the indicated COMPONENTS, and
with the indicate ATTRIBUTES. If SEMI, the definition is
immediately followed by a semicolon. Returns the type. */
tree
finish_class_definition (t, components, attributes, semi)
tree t;
tree components;
tree attributes;
int semi;
{
#if 0
/* Need to rework class nesting in the presence of nested classes,
etc. */
shadow_tag (CLASSTYPE_AS_LIST (t)); */
#endif
/* finish_struct nukes this anyway; if finish_exception does too,
then it can go. */
if (semi)
note_got_semicolon (t);
if (TREE_CODE (t) == ENUMERAL_TYPE)
;
else
{
t = finish_struct (t, components, attributes, semi);
if (semi)
note_got_semicolon (t);
}
pop_obstacks ();
if (! semi)
check_for_missing_semicolon (t);
if (current_scope () == current_function_decl)
do_pending_defargs ();
return t;
}
/* Finish processing the default argument expressions cached during
the processing of a class definition. */
void
finish_default_args ()
{
if (pending_inlines
&& current_scope () == current_function_decl)
do_pending_inlines ();
}
/* Finish processing the inline function definitions cached during the
processing of a class definition. */
void
begin_inline_definitions ()
{
if (current_class_type == NULL_TREE)
clear_inline_text_obstack ();
/* Undo the begin_tree in begin_class_definition. */
end_tree ();
}
// Build don't link:
typedef unsigned int size_t;
inline void *
operator new(size_t alloc_sz, const char *fname, unsigned lineno)
{
}
inline void *
operator new[](size_t alloc_sz, const char *fname, unsigned lineno)
{
}
inline void
operator delete(void *ptr, const char *fname, unsigned lineno)
{
}
inline void
operator delete[](void *ptr, const char *fname, unsigned lineno)
{
}
class DEF {
public:
DEF( DEF *parent=0, const char *name=0 );
};
class ABC
{
public:
enum stuff { ID0, ID1 };
ABC( stuff, DEF *parent=0, const char *name=0 );
};
class GHI : public DEF
{
};
class LMNFrame;
class LMN : public DEF
{
friend class LMNFrame;
public:
public:
LMN();
private:
LMNFrame *draw_area;
ABC *scroll_h;
};
class LMNFrame : public GHI {
};
LMN::LMN()
{
draw_area = new ("abc", 69) LMNFrame;
scroll_h = new ("def", 71) ABC(ABC::ID0, this);
}
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