From: Mike Stump Date: Tue, 31 Jan 1995 22:18:02 +0000 (+0000) Subject: 54th Cygnus<->FSF merge X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=d18c083e31a30476f8646ca18dc852052c49f1da;p=platform%2Fupstream%2Fgcc.git 54th Cygnus<->FSF merge From-SVN: r8844 --- diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index 9eea3c7..7422a38 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -3,6 +3,128 @@ Wed Jan 25 15:02:09 1995 David S. Miller (davem@nadzieja.rutgers.edu) * class.c (instantiate_type): Change error message text. * typeck2.c (store_init_value): Likewise. +Tue Jan 31 13:28:56 1995 Mike Stump + + * gc.c (get_typeid): Pawn off error messages to build_t_desc. + (build_t_desc): Inform the user here if they try and build + with -frtti and don't include . + + * decl2.c (finish_prevtable_vardecl): Support rescanning. + (finish_file): Move finish_prevtable_vardecl up to before the global + initializers are done as tdecls are initialized in the global + initializer. Also Pick up any new tdecls or vtables needed by + synthesized methods. + + * class.c (finish_struct): Simplify. We have to do rtti scanning at + end, so we might as well do all of it there. + +Tue Jan 31 05:35:02 1995 Jason Merrill + + * call.c (build_method_call): Fix -fthis-is-variable for 32-bit + targets, too. + +Tue Jan 31 00:11:04 1995 Mike Stump + + * decl2.c (finish_prevtable_vardecl): New routine, mostly split from + finish_vtable_vardecl. It has the first half functionality from + that routine. + * decl2.c (finish_vtable_vardecl): Update to not include stuff not + in finish_prevtable_vardecl. + * decl2.c (finish_file): Call finish_prevtable_vardecl. + * gc.c (build_generic_desc): Allow it to be called when not at the + global binding layer, but behave as if we were. + (build_t_desc): Rearrange a bit so that it really works and is + easier to follow. + * class.c (finish_struct): Don't decide on tdecls here, as we have + to wait until the end of the file in general to decide whether or + not they come out. + +Mon Jan 30 01:00:40 1995 Jason Merrill + + * init.c (build_delete): Check access to operator delete before + calling the destructor. + * method.c (build_opfncall, DELETE_EXPR): build_method is allowed to + return error_mark_node. + * call.c (build_method_call): Use the one-argument op delete even if + it's an error. + + * init.c (build_new): Fix -fthis-is-variable support. + * call.c (build_method_call): Ditto. + + * call.c (convert_harshness): Make conversion from a pointer to bool + worse than conversion to another pointer. + +Sat Jan 28 16:46:10 1995 Jason Merrill + + * init.c (build_new): Check new return value if -fcheck-new. + + * lex.c (check_newline): Clear end_of_file when we're done, too. + +Sat Jan 28 10:38:39 1995 Mike Stump + + * decl2.c (finish_vtable_vardecl): Make rtti TD tables follow + vtables whereever they go. + + * gc.c (build_t_desc): Remove old way of setting it up, as it wasn't + right. + +Sat Jan 28 09:10:44 1995 Mike Stump + + * decl2.c (finish_vtable_vardecl): Now set the + interface/implementation of vtables on the first virtual function, + if one exists, otherwise we use the old method. This is a major win + in terms of cutting down the size of objects and executables in + terms of text space and data space. Now most of the savings that + #pragma interface/implementation gives is automatic in a fair number + of cases. + +Sat Jan 28 04:57:33 1995 Jason Merrill + + * decl.c (grokdeclarator): Discard the template parameters in a + template constructor declaration so that the function is always + named constructor_name (ctype). + + * lex.c (check_newline): Use ungetc to put back the character before + calling HANDLE_PRAGMA. + +Fri Jan 27 17:23:47 1995 Mike Stump + + * decl2.c (check_classfn): If the cname is T and fn_name is T, + make sure we still match them. + +Fri Jan 27 16:32:10 1995 Jason Merrill + + * parse.y: Add END_OF_LINE token. + + * lex.c (check_newline): Set linemode when we see a # directive, and + unset it when we're done. Turn all 'return's into 'goto skipline'. + Fix all uses of '\n', since we won't see it anymore. Put back the + character we read before checking for a sysv or target pragma. + (real_yylex): If we see an EOF in linemode, return END_OF_LINE. + (handle_sysv_pragma): Don't look at the input stream; quit when we + see an END_OF_LINE token. + + * input.c (getch): Return EOF if we're in line mode and at the end + of a line. + (put_back): Don't put back an EOF. + +Thu Jan 26 19:26:34 1995 Mike Stump + + * except.c (expand_throw): Do the newing of the exception object + before we load the type descriptor or the address so that we don't + wipe any of the values out. + +Thu Jan 26 19:20:00 1995 Mike Stump + + * except.c (init_exception_processing): Don't use r12 on the rs6000. + +Tue Jan 24 16:36:31 1995 Jason Merrill + + * decl.c (grokparms): Don't try to build up a reference at this point. + + * typeck2.c (build_functional_cast): Don't assume that a NOP_EXPR + will suffice to convert from integer_zero_node. + Mon Jan 23 21:57:14 1995 Mike Stump * pt.c (tsubst): When we copy a node, don't forget to copy diff --git a/gcc/cp/call.c b/gcc/cp/call.c index 7a71f40..ee3e8bf 100644 --- a/gcc/cp/call.c +++ b/gcc/cp/call.c @@ -309,9 +309,16 @@ convert_harshness (type, parmtype, parm) if (codel == BOOLEAN_TYPE) { - if (INTEGRAL_CODE_P (coder) || coder == REAL_TYPE - || coder == POINTER_TYPE || coder == OFFSET_TYPE) + if (INTEGRAL_CODE_P (coder) || coder == REAL_TYPE) return STD_RETURN (h); + else if (coder == POINTER_TYPE || coder == OFFSET_TYPE) + { + /* Make this worse than any conversion to another pointer. + FIXME this is how I think the language should work, but it may not + end up being how the language is standardized (jason 1/30/95). */ + h.distance = 32767; + return STD_RETURN (h); + } return EVIL_RETURN (h); } @@ -1547,8 +1554,8 @@ build_method_call (instance, name, parms, basetype_path, flags) result = build_method_call (instance, name, parms, basetype_path, (LOOKUP_SPECULATIVELY|flags) &~LOOKUP_COMPLAIN); - /* If it works, return it. */ - if (result && result != error_mark_node) + /* If it finds a match, return it. */ + if (result) return build_method_call (instance, name, parms, basetype_path, flags); /* If it doesn't work, two argument delete must work */ TREE_CHAIN (parms) = save_last; @@ -1896,9 +1903,9 @@ build_method_call (instance, name, parms, basetype_path, flags) { constp = 0; volatilep = 0; - parms = tree_cons (NULL_TREE, - build1 (NOP_EXPR, TYPE_POINTER_TO (basetype), - integer_zero_node), parms); + instance_ptr = build_int_2 (0, 0); + TREE_TYPE (instance_ptr) = TYPE_POINTER_TO (basetype); + parms = tree_cons (NULL_TREE, instance_ptr, parms); } else { diff --git a/gcc/cp/class.c b/gcc/cp/class.c index 51bc827..ec624b9 100644 --- a/gcc/cp/class.c +++ b/gcc/cp/class.c @@ -4062,47 +4062,6 @@ finish_struct (t, list_of_fieldlists, warn_anon) TYPE_BEING_DEFINED (t) = 0; hack_incomplete_structures (t); - if (flag_rtti && TYPE_VIRTUAL_P (t) && CLASSTYPE_VTABLE_NEEDS_WRITING (t)) - { - tree variants; - tree tdecl, td; - - /* Now instantiate its type descriptors. */ - td = build_t_desc (t, 1); - if (td == NULL_TREE) - { - cp_error ("failed to build type descriptor node of '%T', maybe typeinfo.h not included", t); - tdecl = NULL_TREE; - } - else - tdecl = TREE_OPERAND (td, 0); - -#if 0 - /* I see no need for building the following TD */ - variants = TYPE_POINTER_TO (t); - build_type_variant (variants, 1, 0); - while (variants) - { - build_t_desc (variants, 1); - variants = TYPE_NEXT_VARIANT (variants); - } -#endif - variants = build_reference_type (t); - build_type_variant (variants, 1, 0); - while (variants) - { - build_t_desc (variants, 1); - variants = TYPE_NEXT_VARIANT (variants); - } - if (tdecl != NULL_TREE) - DECL_CONTEXT (tdecl) = t; - } -#if 0 - /* Still need to instantiate this C struct's type descriptor. */ - else if (flag_rtti && ! CLASSTYPE_RTTI (t)) - build_t_desc (t, 1); -#endif - #if 0 if (TYPE_NAME (t) && TYPE_IDENTIFIER (t)) undo_template_name_overload (TYPE_IDENTIFIER (t), 1); diff --git a/gcc/cp/decl.c b/gcc/cp/decl.c index 2bdb535..1cda932 100644 --- a/gcc/cp/decl.c +++ b/gcc/cp/decl.c @@ -7239,9 +7239,12 @@ grokdeclarator (declarator, declspecs, decl_context, initialized, raises) return 0; } innermost_code = TREE_CODE (decl); - decl = TREE_OPERAND (decl, 0); if (decl_context == FIELD && ctype == NULL_TREE) ctype = current_class_type; + if (ctype + && TREE_OPERAND (decl, 0) == constructor_name_full (ctype)) + TREE_OPERAND (decl, 0) = constructor_name (ctype); + decl = TREE_OPERAND (decl, 0); if (ctype != NULL_TREE && decl != NULL_TREE && flags != DTOR_FLAG && decl == constructor_name (ctype)) @@ -7335,6 +7338,9 @@ grokdeclarator (declarator, declspecs, decl_context, initialized, raises) } } + if (ctype + && TREE_OPERAND (decl, 1) == constructor_name_full (ctype)) + TREE_OPERAND (decl, 1) = constructor_name (ctype); decl = TREE_OPERAND (decl, 1); if (ctype) { @@ -7346,12 +7352,13 @@ grokdeclarator (declarator, declspecs, decl_context, initialized, raises) } else if (TREE_CODE (decl) == BIT_NOT_EXPR && TREE_CODE (TREE_OPERAND (decl, 0)) == IDENTIFIER_NODE - && constructor_name (ctype) == TREE_OPERAND (decl, 0)) + && (constructor_name (ctype) == TREE_OPERAND (decl, 0) + || constructor_name_full (ctype) == TREE_OPERAND (decl, 0))) { return_type = return_dtor; ctor_return_type = ctype; flags = DTOR_FLAG; - decl = TREE_OPERAND (decl, 0); + decl = TREE_OPERAND (decl, 0) = constructor_name (ctype); } } } @@ -9552,9 +9559,15 @@ grokparms (first_parm, funcdef_flag) else init = require_instantiated_type (type, init, integer_zero_node); - init = convert_for_initialization - (NULL_TREE, type, init, LOOKUP_NORMAL, - "argument passing", 0, 0); + /* Don't actually try to build up a reference here. */ + { + tree t = type; + if (TREE_CODE (t) == REFERENCE_TYPE) + t = TREE_TYPE (t); + init = convert_for_initialization + (NULL_TREE, t, init, LOOKUP_NORMAL, + "argument passing", 0, 0); + } } #if 0 /* This is too early to check; trailing parms might be merged in by duplicate_decls. */ diff --git a/gcc/cp/decl2.c b/gcc/cp/decl2.c index ce51b9f..abbcead 100644 --- a/gcc/cp/decl2.c +++ b/gcc/cp/decl2.c @@ -351,6 +351,11 @@ int flag_access_control = 1; int flag_operator_names; +/* Nonzero if we want to check the return value of new and avoid calling + constructors if it is a null pointer. */ + +int flag_check_new; + /* Table of language-dependent -f options. STRING is the option name. VARIABLE is the address of the variable. ON_VALUE is the value to store in VARIABLE @@ -395,7 +400,8 @@ static struct { char *string; int *variable; int on_value;} lang_f_options[] = {"access-control", &flag_access_control, 1}, {"nonansi-builtins", &flag_no_nonansi_builtin, 0}, {"gnu-keywords", &flag_no_gnu_keywords, 0}, - {"operator-names", &flag_operator_names, 1} + {"operator-names", &flag_operator_names, 1}, + {"check-new", &flag_check_new, 1} }; /* Decode the string P as a language-specific option. @@ -1154,7 +1160,8 @@ check_classfn (ctype, cname, function) end = TREE_VEC_END (method_vec); /* First suss out ctors and dtors. */ - if (*methods && fn_name == cname) + if (*methods + && (fn_name == cname || fn_name == DECL_NAME (*methods))) goto got_it; while (++methods != end) @@ -2430,7 +2437,7 @@ mark_vtable_entries (decl) } } -/* Set TREE_PUBLIC and/or TREE_EXTERN on the vtable DECL, +/* Set TREE_PUBLIC and/or DECL_EXTERN on the vtable DECL, based on TYPE and other static flags. Note that anything public is tagged TREE_PUBLIC, whether @@ -2472,14 +2479,14 @@ import_export_template (type) } static void -finish_vtable_vardecl (prev, vars) +finish_prevtable_vardecl (prev, vars) tree prev, vars; { tree ctype = DECL_CONTEXT (vars); import_export_template (ctype); import_export_vtable (vars, ctype); - if (flag_vtable_thunks && !CLASSTYPE_INTERFACE_KNOWN (ctype)) + if (CLASSTYPE_INTERFACE_UNKNOWN (ctype)) { tree method; for (method = CLASSTYPE_METHODS (ctype); method != NULL_TREE; @@ -2489,6 +2496,7 @@ finish_vtable_vardecl (prev, vars) && !DECL_ABSTRACT_VIRTUAL_P (method)) { SET_CLASSTYPE_INTERFACE_KNOWN (ctype); + CLASSTYPE_VTABLE_NEEDS_WRITING (ctype) = ! DECL_EXTERNAL (method); CLASSTYPE_INTERFACE_ONLY (ctype) = DECL_EXTERNAL (method); TREE_PUBLIC (vars) = 1; DECL_EXTERNAL (vars) = DECL_EXTERNAL (method); @@ -2502,20 +2510,50 @@ finish_vtable_vardecl (prev, vars) { extern tree the_null_vtable_entry; - /* Stuff this virtual function table's size into - `pfn' slot of `the_null_vtable_entry'. */ -#if 0 - /* we do not put size as first entry any more */ - tree nelts = array_type_nelts (TREE_TYPE (vars)); - if (flag_vtable_thunks) - TREE_VALUE (CONSTRUCTOR_ELTS (DECL_INITIAL (vars))) = nelts; - else - SET_FNADDR_FROM_VTABLE_ENTRY (the_null_vtable_entry, nelts); -#endif - /* Kick out the type descriptor before writing out the vtable. */ if (flag_rtti) - rest_of_decl_compilation (TREE_OPERAND (FNADDR_FROM_VTABLE_ENTRY (TREE_VALUE (CONSTRUCTOR_ELTS (DECL_INITIAL (vars)))), 0), 0, 1, 1); + { + build_t_desc (ctype, 1); + } + + /* Write it out. */ + mark_vtable_entries (vars); + } +} + +static void +finish_vtable_vardecl (prev, vars) + tree prev, vars; +{ + tree ctype = DECL_CONTEXT (vars); + import_export_template (ctype); + import_export_vtable (vars, ctype); + + if (CLASSTYPE_INTERFACE_UNKNOWN (ctype)) + { + tree method; + for (method = CLASSTYPE_METHODS (ctype); method != NULL_TREE; + method = DECL_NEXT_METHOD (method)) + { + if (DECL_VINDEX (method) != NULL_TREE && !DECL_SAVED_INSNS (method) + && !DECL_ABSTRACT_VIRTUAL_P (method)) + { + SET_CLASSTYPE_INTERFACE_KNOWN (ctype); + CLASSTYPE_VTABLE_NEEDS_WRITING (ctype) = ! DECL_EXTERNAL (method); + CLASSTYPE_INTERFACE_ONLY (ctype) = DECL_EXTERNAL (method); + TREE_PUBLIC (vars) = 1; + DECL_EXTERNAL (vars) = DECL_EXTERNAL (method); + if (flag_rtti) + cp_warning ("compiler error: rtti entry for `%T' decided too late", ctype); + break; + } + } + } + + if (write_virtuals >= 0 + && ! DECL_EXTERNAL (vars) && (TREE_PUBLIC (vars) || TREE_USED (vars))) + { + extern tree the_null_vtable_entry; /* Write it out. */ mark_vtable_entries (vars); @@ -2714,13 +2752,31 @@ finish_file () needs_messing_up |= TYPE_NEEDS_CONSTRUCTING (type); vars = TREE_CHAIN (vars); } - if (needs_cleaning == 0) - goto mess_up; /* Otherwise, GDB can get confused, because in only knows about source for LINENO-1 lines. */ lineno -= 1; + interface_unknown = 1; + interface_only = 0; + + /* Walk to mark the inline functions we need, then output them so + that we can pick up any other tdecls that those routines need. */ + walk_vtables ((void (*)())0, finish_prevtable_vardecl); + for (vars = saved_inlines; vars; vars = TREE_CHAIN (vars)) + { + tree decl = TREE_VALUE (vars); + + if (DECL_ARTIFICIAL (decl) + && ! DECL_INITIAL (decl) + && (TREE_USED (decl) || ! DECL_EXTERNAL (decl))) + synthesize_method (decl); + } + walk_vtables ((void (*)())0, finish_prevtable_vardecl); + + if (needs_cleaning == 0) + goto mess_up; + fnname = get_file_function_name ('D'); start_function (void_list_node, build_parse_node (CALL_EXPR, fnname, void_list_node, NULL_TREE), 0, 0); fnname = DECL_ASSEMBLER_NAME (current_function_decl); @@ -2950,19 +3006,6 @@ finish_file () pushdecl (vars); #endif - interface_unknown = 1; - interface_only = 0; - - for (vars = saved_inlines; vars; vars = TREE_CHAIN (vars)) - { - tree decl = TREE_VALUE (vars); - - if (DECL_ARTIFICIAL (decl) - && ! DECL_INITIAL (decl) - && (TREE_USED (decl) || ! DECL_EXTERNAL (decl))) - synthesize_method (decl); - } - walk_vtables ((void (*)())0, finish_vtable_vardecl); if (flag_handle_signatures) walk_sigtables ((void (*)())0, finish_sigtable_vardecl); diff --git a/gcc/cp/except.c b/gcc/cp/except.c index 1490f6f..218818d 100644 --- a/gcc/cp/except.c +++ b/gcc/cp/except.c @@ -1528,7 +1528,6 @@ expand_throw (exp) exception, so that the matching routine knows to search out. */ label = gen_label_rtx (); emit_label (label); - emit_move_insn (saved_pc, gen_rtx (LABEL_REF, Pmode, label)); if (exp) { @@ -1543,7 +1542,6 @@ expand_throw (exp) rtx throw_type_rtx = expand_expr (throw_type, NULL_RTX, VOIDmode, 0); rtx throw_value_rtx; - emit_move_insn (saved_throw_type, throw_type_rtx); exp = convert_to_reference (build_reference_type (build_type_variant (TREE_TYPE (exp), 1, 0)), exp, CONV_STATIC, LOOKUP_COMPLAIN, error_mark_node); /* Make a copy of the thrown object. WP 15.1.5 */ @@ -1553,6 +1551,7 @@ expand_throw (exp) error (" in thrown expression"); throw_value_rtx = expand_expr (exp, NULL_RTX, VOIDmode, 0); emit_move_insn (saved_throw_value, throw_value_rtx); + emit_move_insn (saved_throw_type, throw_type_rtx); } } else @@ -1561,6 +1560,7 @@ expand_throw (exp) /* This part is easy, as we dont' have to do anything else. */ } + emit_move_insn (saved_pc, gen_rtx (LABEL_REF, Pmode, label)); make_first_label(throw_label); emit_jump (throw_label); } diff --git a/gcc/cp/init.c b/gcc/cp/init.c index 02469d4..fd8bf2b 100644 --- a/gcc/cp/init.c +++ b/gcc/cp/init.c @@ -2787,6 +2787,8 @@ build_builtin_call (type, node, arglist) PLACEMENT is the `placement' list for user-defined operator new (). */ +extern int flag_check_new; + tree build_new (placement, decl, init, use_global_new) tree placement; @@ -2795,6 +2797,7 @@ build_new (placement, decl, init, use_global_new) { tree type, true_type, size, rval; tree nelts; + tree alloc_expr; int has_array = 0; enum tree_code code = NEW_EXPR; @@ -3026,6 +3029,13 @@ build_new (placement, decl, init, use_global_new) TREE_CALLS_NEW (rval) = 1; } + if (flag_check_new) + { + if (rval) + rval = save_expr (rval); + alloc_expr = rval; + } + /* if rval is NULL_TREE I don't have to allocate it, but are we totally sure we have some extra bytes in that case for the BI_header_size cookies? And how does that interact with the code below? (mrs) */ @@ -3081,7 +3091,7 @@ build_new (placement, decl, init, use_global_new) { tree tmp = rval; - if (TREE_CODE (TREE_TYPE (tmp)) == POINTER_TYPE) + if (tmp && TREE_CODE (TREE_TYPE (tmp)) == POINTER_TYPE) tmp = build_indirect_ref (tmp, NULL_PTR); newrval = build_method_call (tmp, constructor_name_full (true_type), @@ -3176,6 +3186,14 @@ build_new (placement, decl, init, use_global_new) } } done: + + if (flag_check_new && alloc_expr && rval != alloc_expr) + { + tree ifexp = build_binary_op (NE_EXPR, alloc_expr, integer_zero_node, 1); + rval = build_conditional_expr (ifexp, rval, convert (TREE_TYPE (rval), + integer_zero_node)); + } + if (rval && TREE_TYPE (rval) != build_pointer_type (type)) { /* The type of new int [3][3] is not int *, but int [3] * */ @@ -3572,7 +3590,18 @@ build_delete (type, addr, auto_delete, flags, use_global_delete) auto_delete, integer_two_node)); } else - passed_auto_delete = auto_delete; + { + if (TYPE_GETS_REG_DELETE (type)) + { + /* Only do access checking here; we'll be calling op delete + from the destructor. */ + tree t = build_opfncall (DELETE_EXPR, LOOKUP_NORMAL, addr, + size_zero_node, NULL_TREE); + if (t == error_mark_node) + return error_mark_node; + } + passed_auto_delete = auto_delete; + } if (flags & LOOKUP_PROTECT) { diff --git a/gcc/cp/input.c b/gcc/cp/input.c index 1570489..378521e 100644 --- a/gcc/cp/input.c +++ b/gcc/cp/input.c @@ -128,8 +128,8 @@ feed_input (str, len, delete) struct pending_input *to_be_restored; /* XXX */ extern int end_of_file; -int -getch () +static inline int +sub_getch () { if (putback_char != -1) { @@ -172,8 +172,25 @@ void put_back (ch) int ch; { - my_friendly_assert (putback_char == -1, 224); - putback_char = ch; + if (ch != EOF) + { + my_friendly_assert (putback_char == -1, 224); + putback_char = ch; + } +} + +extern int linemode; + +int +getch () +{ + int ch = sub_getch (); + if (linemode && ch == '\n') + { + put_back (ch); + ch = EOF; + } + return ch; } inline diff --git a/gcc/cp/lex.c b/gcc/cp/lex.c index 09424b0..d61de50 100644 --- a/gcc/cp/lex.c +++ b/gcc/cp/lex.c @@ -2319,6 +2319,8 @@ get_last_nonwhite_on_line () If the line is a #-directive, read the entire line and return a newline. Otherwise, return the line's first non-whitespace character. */ +int linemode; + int check_newline () { @@ -2340,6 +2342,9 @@ check_newline () return c; } + /* Don't read beyond this line. */ + linemode = 1; + /* Read first nonwhite char after the `#'. */ do @@ -2372,7 +2377,7 @@ check_newline () && getch () == 'b' && getch () == 'l' && getch () == 'e' - && ((c = getch ()) == ' ' || c == '\t' || c == '\n')) + && ((c = getch ()) == ' ' || c == '\t')) { extern tree pending_vtables; @@ -2392,14 +2397,14 @@ check_newline () if (nextchar < 0) nextchar = getch (); c = nextchar; - if (c != '\n') + if (c != EOF) warning ("trailing characters ignored"); } else if (c == 'u' && getch () == 'n' && getch () == 'i' && getch () == 't' - && ((c = getch ()) == ' ' || c == '\t' || c == '\n')) + && ((c = getch ()) == ' ' || c == '\t')) { /* More follows: it must be a string constant (unit name). */ token = real_yylex (); @@ -2413,7 +2418,7 @@ check_newline () if (nextchar < 0) nextchar = getch (); c = nextchar; - if (c != '\n') + if (c != EOF) warning ("trailing characters ignored"); } else if (c == 'i') @@ -2429,7 +2434,7 @@ check_newline () && getch () == 'a' && getch () == 'c' && getch () == 'e' - && ((c = getch ()) == ' ' || c == '\t' || c == '\n')) + && ((c = getch ()) == ' ' || c == '\t' || c == EOF)) { int warned_already = 0; char *main_filename = input_filename; @@ -2437,7 +2442,7 @@ check_newline () main_filename = FILE_NAME_NONDIRECTORY (main_filename); while (c == ' ' || c == '\t') c = getch (); - if (c != '\n') + if (c != EOF) { put_back (c); token = real_yylex (); @@ -2455,10 +2460,10 @@ check_newline () while (c == ' ' || c == '\t') c = getch (); - while (c != '\n') + while (c != EOF) { if (!warned_already && extra_warnings - && c != ' ' && c != '\t' && c != '\n') + && c != ' ' && c != '\t') { warning ("garbage after `#pragma interface' ignored"); warned_already = 1; @@ -2506,7 +2511,7 @@ check_newline () && getch () == 'i' && getch () == 'o' && getch () == 'n' - && ((c = getch ()) == ' ' || c == '\t' || c == '\n')) + && ((c = getch ()) == ' ' || c == '\t' || c == EOF)) { int warned_already = 0; char *main_filename = main_input_filename ? main_input_filename : input_filename; @@ -2514,7 +2519,7 @@ check_newline () main_filename = FILE_NAME_NONDIRECTORY (main_filename); while (c == ' ' || c == '\t') c = getch (); - if (c != '\n') + if (c != EOF) { put_back (c); token = real_yylex (); @@ -2532,10 +2537,10 @@ check_newline () while (c == ' ' || c == '\t') c = getch (); - while (c != '\n') + while (c != EOF) { if (!warned_already && extra_warnings - && c != ' ' && c != '\t' && c != '\n') + && c != ' ' && c != '\t') { warning ("garbage after `#pragma implementation' ignored"); warned_already = 1; @@ -2591,11 +2596,19 @@ check_newline () } #ifdef HANDLE_SYSV_PRAGMA else - return handle_sysv_pragma (finput, c); + { + put_back (c); + handle_sysv_pragma (); + } #else #ifdef HANDLE_PRAGMA + /* FIXME: This will break if we're doing any of the C++ input + tricks. */ else - HANDLE_PRAGMA (finput); + { + ungetc (c, finput); + HANDLE_PRAGMA (finput); + } #endif #endif } @@ -2608,7 +2621,7 @@ check_newline () && getch () == 'i' && getch () == 'n' && getch () == 'e' - && ((c = getch ()) == ' ' || c == '\t' || c == '\n')) + && ((c = getch ()) == ' ' || c == '\t')) { #ifdef DWARF_DEBUGGING_INFO if ((debug_info_level == DINFO_LEVEL_VERBOSE) @@ -2624,7 +2637,7 @@ check_newline () && getch () == 'd' && getch () == 'e' && getch () == 'f' - && ((c = getch ()) == ' ' || c == '\t' || c == '\n')) + && ((c = getch ()) == ' ' || c == '\t')) { #ifdef DWARF_DEBUGGING_INFO if ((debug_info_level == DINFO_LEVEL_VERBOSE) @@ -2662,8 +2675,8 @@ check_newline () c = getch (); /* If no argument, ignore the line. */ - if (c == '\n') - return c; + if (c == EOF) + goto skipline; put_back (c); token = real_yylex (); @@ -2715,8 +2728,8 @@ linenum: /* If the # is the only nonwhite char on the line, just ignore it. Check the new newline. */ - if (c == '\n') - return c; + if (c == EOF) + goto skipline; /* Something follows the #; read a token. */ @@ -2736,11 +2749,11 @@ linenum: int l = TREE_INT_CST_LOW (yylval.ttype) - 1; c = get_last_nonwhite_on_line (); - if (c == '\n') + if (c == EOF) { /* No more: store the line number and check following line. */ lineno = l; - return c; + goto skipline; } put_back (c); @@ -2799,7 +2812,7 @@ linenum: extract_interface_info (); c = get_last_nonwhite_on_line (); - if (c != '\n') + if (c != EOF) { put_back (c); @@ -2819,7 +2832,7 @@ linenum: if (action) { c = get_last_nonwhite_on_line (); - if (c != '\n') + if (c != EOF) { put_back (c); token = real_yylex (); @@ -2836,7 +2849,7 @@ linenum: entering_system_header = 1; c = get_last_nonwhite_on_line (); - if (c != '\n') + if (c != EOF) { put_back (c); token = real_yylex (); @@ -2852,7 +2865,7 @@ linenum: entering_c_header = 1; c = get_last_nonwhite_on_line (); - if (c != '\n') + if (c != EOF) { put_back (c); token = real_yylex (); @@ -2927,16 +2940,16 @@ linenum: } /* If NEXTCHAR is not end of line, we don't care what it is. */ - if (nextchar == '\n') - return '\n'; + if (nextchar == EOF) + c = EOF; } else error ("invalid #-line"); /* skip the rest of this line. */ skipline: - if (c == '\n') - return c; + linemode = 0; + end_of_file = 0; while ((c = getch ()) != EOF && c != '\n'); return c; } @@ -3343,6 +3356,8 @@ real_yylex () end_of_file = 1; if (input_redirected ()) value = END_OF_SAVED_INPUT; + else if (linemode) + value = END_OF_LINE; else if (do_pending_expansions ()) /* this will set yychar for us */ return yychar; @@ -4906,21 +4921,10 @@ yyerror (string) /* This function has to be in this file, in order to get at the token types. */ -int -handle_sysv_pragma (input, c) - FILE *input; - int c; +handle_sysv_pragma () { for (;;) { - while (c == ' ' || c == '\t') - c = getc (input); - if (c == '\n' || c == EOF) - { - handle_pragma_token (0, 0); - return c; - } - ungetc (c, input); switch (yylex ()) { case IDENTIFIER: @@ -4929,13 +4933,12 @@ handle_sysv_pragma (input, c) case CONSTANT: handle_pragma_token (token_buffer, yylval.ttype); break; + case END_OF_LINE: + handle_pragma_token (0, 0); + return; default: handle_pragma_token (token_buffer, 0); } - if (nextchar >= 0) - c = nextchar, nextchar = -1; - else - c = getc (input); } } #endif /* HANDLE_SYSV_PRAGMA */ diff --git a/gcc/cp/method.c b/gcc/cp/method.c index 92610ff..5a646a5 100644 --- a/gcc/cp/method.c +++ b/gcc/cp/method.c @@ -1220,10 +1220,11 @@ build_opfncall (code, flags, xarg1, xarg2, arg3) fnname, tree_cons (NULL_TREE, xarg1, build_tree_list (NULL_TREE, xarg2)), NULL_TREE, flags); - /* This happens when the user mis-declares `operator delete'. - Should now be impossible. */ +#if 0 + /* This can happen when operator delete is protected. */ my_friendly_assert (rval != error_mark_node, 250); TREE_TYPE (rval) = void_type_node; +#endif return rval; } break; diff --git a/gcc/cp/parse.y b/gcc/cp/parse.y index 882c2fd..6a4420c 100644 --- a/gcc/cp/parse.y +++ b/gcc/cp/parse.y @@ -277,6 +277,9 @@ empty_parms () %type .pushlevel +/* Used in lex.c for parsing pragmas. */ +%token END_OF_LINE + /* spew.c depends on this being the last token. Define any new tokens before this one! */ %token END_OF_SAVED_INPUT diff --git a/gcc/cp/typeck2.c b/gcc/cp/typeck2.c index fabba84..5a52fd3 100644 --- a/gcc/cp/typeck2.c +++ b/gcc/cp/typeck2.c @@ -1424,7 +1424,7 @@ build_functional_cast (exp, parms) { /* this must build a C cast */ if (parms == NULL_TREE) - return build1 (NOP_EXPR, type, integer_zero_node); + parms = integer_zero_node; else if (TREE_CHAIN (parms) != NULL_TREE) { pedwarn ("initializer list being treated as compound expression");