summaryrefslogtreecommitdiff
path: root/gnu/usr.bin
diff options
context:
space:
mode:
authorMarc Espie <espie@cvs.openbsd.org>1998-12-23 01:14:03 +0000
committerMarc Espie <espie@cvs.openbsd.org>1998-12-23 01:14:03 +0000
commita6d97e68900690be9aa7f290418a28d5902962ff (patch)
treeaa6e409e708c6b25aa8376eed0aba44c6f6aeb4d /gnu/usr.bin
parent9c7e624e4dfc4212e5c7e0bea0af080174cc130f (diff)
2.7.2 -> 2.8.1 cruft. Takes care of remaining files, except
config and fortran. g++.c: is now generated automatically edsel.c: obsolete gc.c: part of rtti
Diffstat (limited to 'gnu/usr.bin')
-rw-r--r--gnu/usr.bin/gcc/cp/edsel.c928
-rw-r--r--gnu/usr.bin/gcc/cp/g++.c584
-rw-r--r--gnu/usr.bin/gcc/cp/gc.c1550
3 files changed, 0 insertions, 3062 deletions
diff --git a/gnu/usr.bin/gcc/cp/edsel.c b/gnu/usr.bin/gcc/cp/edsel.c
deleted file mode 100644
index 35099d523f7..00000000000
--- a/gnu/usr.bin/gcc/cp/edsel.c
+++ /dev/null
@@ -1,928 +0,0 @@
-/* Interface to LUCID Cadillac system for GNU compiler.
- Copyright (C) 1988, 1992, 1993 Free Software Foundation, Inc.
-
-This file is part of GNU CC.
-
-GNU CC is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2, or (at your option)
-any later version.
-
-GNU CC is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with GNU CC; see the file COPYING. If not, write to
-the Free Software Foundation, 59 Temple Place - Suite 330,
-Boston, MA 02111-1307, USA. */
-
-#include "config.h"
-
-#include "tree.h"
-#include "flags.h"
-#include <stdio.h>
-#include "cp-tree.h"
-#include "obstack.h"
-
-#ifdef CADILLAC
-#include <compilerreq.h>
-#include <compilerconn.h>
-#include <sys/time.h>
-#include <sys/types.h>
-#include <errno.h>
-#include <sys/file.h>
-
-#define obstack_chunk_alloc xmalloc
-#define obstack_chunk_free free
-
-void init_cadillac ();
-
-extern char *input_filename;
-extern int lineno;
-
-/* Put random information we might want to get back from
- Cadillac here. */
-typedef struct
-{
- /* The connection to the Cadillac kernel. */
- Connection *conn;
-
- /* Input and output file descriptors for Cadillac. */
- short fd_input, fd_output;
-
- /* #include nesting of current file. */
- short depth;
-
- /* State variables for the connection. */
- char messages;
- char conversion;
- char emission;
- char process_until;
-
- /* #if level of current file. */
- int iflevel;
-
- /* Line number that starts current source file. */
- int lineno;
-
- /* Name of current file. */
- char *filename;
-
- /* Where to stop processing (if process_until is set). */
- char *end_filename;
- int end_position;
-
-} cadillac_struct;
-static cadillac_struct cadillacObj;
-
-/* Nonzero if in the process of exiting. */
-static int exiting;
-
-void cadillac_note_source ();
-static void CWriteLanguageDecl ();
-static void CWriteLanguageType ();
-static void CWriteTopLevel ();
-static void cadillac_note_filepos ();
-static void cadillac_process_request (), cadillac_process_requests ();
-static void cadillac_switch_source ();
-static void exit_cadillac ();
-
-/* Blocking test. */
-static int
-readable_p (fd)
- int fd;
-{
- fd_set f;
-
- FD_ZERO (&f);
- FD_SET (fd, &f);
-
- return select (32, &f, NULL, NULL, 0) == 1;
-}
-
-static CObjectType *tree_to_cadillac_map;
-struct obstack cadillac_obstack;
-
-
-#include "stack.h"
-
-struct context_level
-{
- struct stack_level base;
-
- tree context;
-};
-
-/* Stack for maintaining contexts (in case functions or types are nested).
- When defining a struct type, the `context' field is the RECORD_TYPE.
- When defining a function, the `context' field is the FUNCTION_DECL. */
-
-static struct context_level *context_stack;
-
-static struct context_level *
-push_context_level (stack, obstack)
- struct stack_level *stack;
- struct obstack *obstack;
-{
- struct context_level tem;
-
- tem.base.prev = stack;
- return (struct context_level *)push_stack_level (obstack, &tem, sizeof (tem));
-}
-
-/* Discard a level of search allocation. */
-
-static struct context_level *
-pop_context_level (stack)
- struct context_level *stack;
-{
- stack = (struct context_level *)pop_stack_level (stack);
- return stack;
-}
-
-void
-init_cadillac ()
-{
- extern FILE *finput;
- extern int errno;
- CCompilerMessage* req;
- cadillac_struct *cp = &cadillacObj;
- int i;
-
- if (! flag_cadillac)
- return;
-
- tree_to_cadillac_map = (CObjectType*) xmalloc (sizeof (CObjectType) * LAST_CPLUS_TREE_CODE);
- for (i = 0; i < LAST_CPLUS_TREE_CODE; i++)
- tree_to_cadillac_map[i] = MiscOType;
- tree_to_cadillac_map[RECORD_TYPE] = StructOType;
- tree_to_cadillac_map[UNION_TYPE] = UnionOType;
- tree_to_cadillac_map[ENUMERAL_TYPE] = EnumTypeOType;
- tree_to_cadillac_map[TYPE_DECL] = TypedefOType;
- tree_to_cadillac_map[VAR_DECL] = VariableOType;
- tree_to_cadillac_map[CONST_DECL] = EnumConstantOType;
- tree_to_cadillac_map[FUNCTION_DECL] = FunctionOType;
- tree_to_cadillac_map[FIELD_DECL] = FieldOType;
-
-#ifdef sun
- on_exit (&exit_cadillac, 0);
-#endif
-
- gcc_obstack_init (&cadillac_obstack);
-
- /* Yow! This is the way Cadillac was designed to deal with
- Oregon C++ compiler! */
- cp->fd_input = flag_cadillac;
- cp->fd_output = flag_cadillac;
-
- /* Start in "turned-on" state. */
- cp->messages = 1;
- cp->conversion = 1;
- cp->emission = 1;
-
- /* Establish a connection with Cadillac here. */
- cp->conn = NewConnection (cp, cp->fd_input, cp->fd_output);
-
- CWriteHeader (cp->conn, WaitingMType, 0);
- CWriteRequestBuffer (cp->conn);
-
- if (!readable_p (cp->fd_input))
- ;
-
- req = CReadCompilerMessage (cp->conn);
-
- if (!req)
- switch (errno)
- {
- case EWOULDBLOCK:
- sleep (5);
- return;
-
- case 0:
- fatal ("init_cadillac: EOF on connection to kernel, exiting\n");
- break;
-
- default:
- perror ("Editor to kernel connection");
- exit (0);
- }
-}
-
-static void
-cadillac_process_requests (conn)
- Connection *conn;
-{
- CCompilerMessage *req;
- while (req = (CCompilerMessage*) CPeekNextRequest (conn))
- {
- req = CReadCompilerMessage (conn);
- cadillac_process_request (&cadillacObj, req);
- }
-}
-
-static void
-cadillac_process_request (cp, req)
- cadillac_struct *cp;
- CCompilerMessage *req;
-{
- if (! req)
- return;
-
- switch (req->reqType)
- {
- case ProcessUntilMType:
- if (cp->process_until)
- my_friendly_abort (23);
- cp->process_until = 1;
- /* This is not really right. */
- cp->end_position = ((CCompilerCommand*)req)->processuntil.position;
-#if 0
- cp->end_filename = req->processuntil.filename;
-#endif
- break;
-
- case CommandMType:
- switch (req->header.data)
- {
- case MessagesOnCType:
- cp->messages = 1;
- break;
- case MessagesOffCType:
- cp->messages = 0;
- break;
- case ConversionOnCType:
- cp->conversion = 1;
- break;
- case ConversionOffCType:
- cp->conversion = 0;
- break;
- case EmissionOnCType:
- cp->emission = 1;
- break;
- case EmissionOffCType:
- cp->emission = 0;
- break;
-
- case FinishAnalysisCType:
- return;
-
- case PuntAnalysisCType:
- case ContinueAnalysisCType:
- case GotoFileposCType:
- case OpenSucceededCType:
- case OpenFailedCType:
- fprintf (stderr, "request type %d not implemented\n", req->reqType);
- return;
-
- case DieCType:
- if (! exiting)
- my_friendly_abort (24);
- return;
-
- }
- break;
-
- default:
- fatal ("unknown request type %d", req->reqType);
- }
-}
-
-void
-cadillac_start ()
-{
- Connection *conn = cadillacObj.conn;
- CCompilerMessage *req;
-
- /* Let Cadillac know that we start in C++ language scope. */
- CWriteHeader (conn, ForeignLinkageMType, LinkCPlus);
- CWriteLength (conn);
- CWriteRequestBuffer (conn);
-
- cadillac_process_requests (conn);
-}
-
-static void
-cadillac_printf (msg, name)
-{
- if (cadillacObj.messages)
- printf ("[%s,%4d] %s `%s'\n", input_filename, lineno, msg, name);
-}
-
-void
-cadillac_start_decl (decl)
- tree decl;
-{
- Connection *conn = cadillacObj.conn;
- CObjectType object_type = tree_to_cadillac_map [TREE_CODE (decl)];
-
- if (context_stack)
- switch (TREE_CODE (context_stack->context))
- {
- case FUNCTION_DECL:
- /* Currently, cadillac only implements top-level forms. */
- return;
- case RECORD_TYPE:
- case UNION_TYPE:
- cadillac_printf ("start class-level decl", IDENTIFIER_POINTER (DECL_NAME (decl)));
- break;
- default:
- my_friendly_abort (25);
- }
- else
- {
- cadillac_printf ("start top-level decl", IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl)));
- CWriteTopLevel (conn, StartMType);
- }
-
- CWriteLanguageDecl (conn, decl, tree_to_cadillac_map[TREE_CODE (decl)]);
- CWriteRequestBuffer (conn);
- cadillac_process_requests (conn);
-}
-
-void
-cadillac_finish_decl (decl)
- tree decl;
-{
- Connection *conn = cadillacObj.conn;
-
- if (context_stack)
- switch (TREE_CODE (context_stack->context))
- {
- case FUNCTION_DECL:
- return;
- case RECORD_TYPE:
- case UNION_TYPE:
- cadillac_printf ("end class-level decl", IDENTIFIER_POINTER (DECL_NAME (decl)));
- CWriteHeader (conn, EndDefMType, 0);
- CWriteLength (conn);
- break;
- default:
- my_friendly_abort (26);
- }
- else
- {
- cadillac_printf ("end top-level decl", IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl)));
- CWriteHeader (conn, EndDefMType, 0);
- CWriteLength (conn);
- CWriteTopLevel (conn, StopMType);
- }
-
- CWriteRequestBuffer (conn);
- cadillac_process_requests (conn);
-}
-
-void
-cadillac_start_function (fndecl)
- tree fndecl;
-{
- Connection *conn = cadillacObj.conn;
-
- if (context_stack)
- /* nested functions not yet handled. */
- my_friendly_abort (27);
-
- cadillac_printf ("start top-level function", lang_printable_name (fndecl));
- context_stack = push_context_level (context_stack, &cadillac_obstack);
- context_stack->context = fndecl;
-
- CWriteTopLevel (conn, StartMType);
- my_friendly_assert (TREE_CODE (fndecl) == FUNCTION_DECL, 202);
- CWriteLanguageDecl (conn, fndecl,
- (TREE_CODE (TREE_TYPE (fndecl)) == METHOD_TYPE
- ? MemberFnOType : FunctionOType));
- CWriteRequestBuffer (conn);
- cadillac_process_requests (conn);
-}
-
-void
-cadillac_finish_function (fndecl)
- tree fndecl;
-{
- Connection *conn = cadillacObj.conn;
-
- cadillac_printf ("end top-level function", lang_printable_name (fndecl));
- context_stack = pop_context_level (context_stack);
-
- if (context_stack)
- /* nested functions not yet implemented. */
- my_friendly_abort (28);
-
- CWriteHeader (conn, EndDefMType, 0);
- CWriteLength (conn);
- CWriteTopLevel (conn, StopMType);
- CWriteRequestBuffer (conn);
- cadillac_process_requests (conn);
-}
-
-void
-cadillac_finish_anon_union (decl)
- tree decl;
-{
- Connection *conn = cadillacObj.conn;
-
- if (! global_bindings_p ())
- return;
- cadillac_printf ("finish top-level anon union", "");
- CWriteHeader (conn, EndDefMType, 0);
- CWriteLength (conn);
- CWriteTopLevel (conn, StopMType);
- CWriteRequestBuffer (conn);
- cadillac_process_requests (conn);
-}
-
-void
-cadillac_start_enum (type)
- tree type;
-{
- Connection *conn = cadillacObj.conn;
-
- tree name = TYPE_NAME (type);
-
- if (TREE_CODE (name) == TYPE_DECL)
- name = DECL_NAME (name);
-
- if (context_stack)
- switch (TREE_CODE (context_stack->context))
- {
- case FUNCTION_DECL:
- return;
- case RECORD_TYPE:
- case UNION_TYPE:
- break;
- default:
- my_friendly_abort (29);
- }
- else
- {
- cadillac_printf ("start top-level enum", IDENTIFIER_POINTER (name));
- CWriteTopLevel (conn, StartMType);
- }
-
- CWriteLanguageType (conn, type, tree_to_cadillac_map[ENUMERAL_TYPE]);
-}
-
-void
-cadillac_finish_enum (type)
- tree type;
-{
- Connection *conn = cadillacObj.conn;
- tree name = TYPE_NAME (type);
-
- if (TREE_CODE (name) == TYPE_DECL)
- name = DECL_NAME (name);
-
- if (context_stack)
- switch (TREE_CODE (context_stack->context))
- {
- case FUNCTION_DECL:
- return;
- case RECORD_TYPE:
- case UNION_TYPE:
- CWriteHeader (conn, EndDefMType, 0);
- CWriteLength (conn);
- break;
- default:
- my_friendly_abort (30);
- }
- else
- {
- CWriteHeader (conn, EndDefMType, 0);
- CWriteLength (conn);
- cadillac_printf ("finish top-level enum", IDENTIFIER_POINTER (name));
- CWriteTopLevel (conn, StopMType);
- }
-
- CWriteRequestBuffer (conn);
- cadillac_process_requests (conn);
-}
-
-void
-cadillac_start_struct (type)
- tree type;
-{
- Connection *conn = cadillacObj.conn;
- tree name = TYPE_NAME (type);
-
- if (TREE_CODE (name) == TYPE_DECL)
- name = DECL_NAME (name);
-
- if (context_stack)
- switch (TREE_CODE (context_stack->context))
- {
- case FUNCTION_DECL:
- return;
- case RECORD_TYPE:
- case UNION_TYPE:
- return;
- default:
- my_friendly_abort (31);
- }
- else
- {
- cadillac_printf ("start struct", IDENTIFIER_POINTER (name));
- CWriteTopLevel (conn, StartMType);
- }
-
- context_stack = push_context_level (context_stack, &cadillac_obstack);
- context_stack->context = type;
-
- CWriteLanguageType (conn, type,
- TYPE_LANG_SPECIFIC (type) && CLASSTYPE_DECLARED_CLASS (type) ? ClassOType : tree_to_cadillac_map[TREE_CODE (type)]);
-}
-
-void
-cadillac_finish_struct (type)
- tree type;
-{
- Connection *conn = cadillacObj.conn;
- tree name = TYPE_NAME (type);
-
- if (TREE_CODE (name) == TYPE_DECL)
- name = DECL_NAME (name);
-
- context_stack = pop_context_level (context_stack);
- if (context_stack)
- return;
-
- cadillac_printf ("finish struct", IDENTIFIER_POINTER (name));
- CWriteHeader (conn, EndDefMType, 0);
- CWriteLength (conn);
- CWriteTopLevel (conn, StopMType);
- CWriteRequestBuffer (conn);
- cadillac_process_requests (conn);
-}
-
-void
-cadillac_finish_exception (type)
- tree type;
-{
- Connection *conn = cadillacObj.conn;
-
- fatal ("cadillac_finish_exception");
- CWriteHeader (conn, EndDefMType, 0);
- CWriteLength (conn);
- CWriteTopLevel (conn, StopMType);
- CWriteRequestBuffer (conn);
- cadillac_process_requests (conn);
-}
-
-void
-cadillac_push_class (type)
- tree type;
-{
-}
-
-void
-cadillac_pop_class ()
-{
-}
-
-void
-cadillac_push_lang (name)
- tree name;
-{
- Connection *conn = cadillacObj.conn;
- CLinkLanguageType m;
-
- if (name == lang_name_cplusplus)
- m = LinkCPlus;
- else if (name == lang_name_c)
- m = LinkC;
- else
- my_friendly_abort (32);
- CWriteHeader (conn, ForeignLinkageMType, m);
- CWriteRequestBuffer (conn);
- cadillac_process_requests (conn);
-}
-
-void
-cadillac_pop_lang ()
-{
- Connection *conn = cadillacObj.conn;
-
- CWriteHeader (conn, ForeignLinkageMType, LinkPop);
- CWriteRequestBuffer (conn);
- cadillac_process_requests (conn);
-}
-
-void
-cadillac_finish_stmt ()
-{
-}
-
-void
-cadillac_note_source ()
-{
- cadillacObj.lineno = lineno;
- cadillacObj.filename = input_filename;
-}
-
-static void
-CWriteTopLevel (conn, m)
- Connection *conn;
- CMessageSubType m;
-{
- static context_id = 0;
- CWriteHeader (conn, TopLevelFormMType, m);
- cadillac_note_filepos ();
-
- /* Eventually, this will point somewhere into the digest file. */
- context_id += 1;
- CWriteSomething (conn, &context_id, sizeof (BITS32));
-
- CWriteSomething (conn, &cadillacObj.iflevel, sizeof (BITS32));
- CWriteLength (conn);
-}
-
-static void
-cadillac_note_filepos ()
-{
- extern FILE *finput;
- int pos = ftell (finput);
- CWriteSomething (cadillacObj.conn, &pos, sizeof (BITS32));
-}
-
-void
-cadillac_switch_source (startflag)
- int startflag;
-{
- Connection *conn = cadillacObj.conn;
- /* Send out the name of the source file being compiled. */
-
- CWriteHeader (conn, SourceFileMType, startflag ? StartMType : StopMType);
- CWriteSomething (conn, &cadillacObj.depth, sizeof (BITS16));
- CWriteVstring0 (conn, input_filename);
- CWriteLength (conn);
- CWriteRequestBuffer (conn);
- cadillac_process_requests (conn);
-}
-
-void
-cadillac_push_source ()
-{
- cadillacObj.depth += 1;
- cadillac_switch_source (1);
-}
-
-void
-cadillac_pop_source ()
-{
- cadillacObj.depth -= 1;
- cadillac_switch_source (0);
-}
-
-struct cadillac_mdep
-{
- short object_type;
- char linkage;
- char access;
- short length;
-};
-
-static void
-CWriteLanguageElem (conn, p, name)
- Connection *conn;
- struct cadillac_mdep *p;
- char *name;
-{
- CWriteSomething (conn, &p->object_type, sizeof (BITS16));
- CWriteSomething (conn, &p->linkage, sizeof (BITS8));
- CWriteSomething (conn, &p->access, sizeof (BITS8));
- CWriteSomething (conn, &p->length, sizeof (BITS16));
- CWriteVstring0 (conn, name);
-
-#if 0
- /* Don't write date_type. */
- CWriteVstring0 (conn, "");
-#endif
- CWriteLength (conn);
-}
-
-static void
-CWriteLanguageDecl (conn, decl, object_type)
- Connection *conn;
- tree decl;
- CObjectType object_type;
-{
- struct cadillac_mdep foo;
- tree name;
-
- CWriteHeader (conn, LanguageElementMType, StartDefineMType);
- foo.object_type = object_type;
- if (decl_type_context (decl))
- {
- foo.linkage = ParentLinkage;
- if (TREE_PRIVATE (decl))
- foo.access = PrivateAccess;
- else if (TREE_PROTECTED (decl))
- foo.access = ProtectedAccess;
- else
- foo.access = PublicAccess;
- }
- else
- {
- if (TREE_PUBLIC (decl))
- foo.linkage = GlobalLinkage;
- else
- foo.linkage = FileLinkage;
- foo.access = PublicAccess;
- }
- name = DECL_NAME (decl);
- foo.length = IDENTIFIER_LENGTH (name);
-
- CWriteLanguageElem (conn, &foo, IDENTIFIER_POINTER (name));
- CWriteRequestBuffer (conn);
- cadillac_process_requests (conn);
-}
-
-static void
-CWriteLanguageType (conn, type, object_type)
- Connection *conn;
- tree type;
- CObjectType object_type;
-{
- struct cadillac_mdep foo;
- tree name = TYPE_NAME (type);
-
- CWriteHeader (conn, LanguageElementMType, StartDefineMType);
- foo.object_type = object_type;
- if (current_class_type)
- {
- foo.linkage = ParentLinkage;
- if (TREE_PRIVATE (type))
- foo.access = PrivateAccess;
- else if (TREE_PROTECTED (type))
- foo.access = ProtectedAccess;
- else
- foo.access = PublicAccess;
- }
- else
- {
- foo.linkage = NoLinkage;
- foo.access = PublicAccess;
- }
- if (TREE_CODE (name) == TYPE_DECL)
- name = DECL_NAME (name);
-
- foo.length = IDENTIFIER_LENGTH (name);
-
- CWriteLanguageElem (conn, &foo, IDENTIFIER_POINTER (name));
- CWriteRequestBuffer (conn);
- cadillac_process_requests (conn);
-}
-
-static void
-CWriteUseObject (conn, type, object_type, use)
- Connection *conn;
- tree type;
- CObjectType object_type;
- CMessageSubType use;
-{
- struct cadillac_mdep foo;
- tree name = NULL_TREE;
-
- CWriteHeader (conn, LanguageElementMType, use);
- foo.object_type = object_type;
- if (current_class_type)
- {
- foo.linkage = ParentLinkage;
- if (TREE_PRIVATE (type))
- foo.access = PrivateAccess;
- else if (TREE_PROTECTED (type))
- foo.access = ProtectedAccess;
- else
- foo.access = PublicAccess;
- }
- else
- {
- foo.linkage = NoLinkage;
- foo.access = PublicAccess;
- }
- switch (TREE_CODE (type))
- {
- case VAR_DECL:
- case FIELD_DECL:
- case TYPE_DECL:
- case CONST_DECL:
- case FUNCTION_DECL:
- name = DECL_NAME (type);
- break;
-
- default:
- my_friendly_abort (33);
- }
-
- foo.length = IDENTIFIER_LENGTH (name);
-
- CWriteLanguageElem (conn, &foo, IDENTIFIER_POINTER (name));
- CWriteRequestBuffer (conn);
- cadillac_process_requests (conn);
-}
-
-/* Here's how we exit under cadillac. */
-
-static void
-exit_cadillac ()
-{
- extern int errorcount;
-
- Connection *conn = cadillacObj.conn;
-
- if (flag_cadillac)
- {
- CCompilerMessage *req;
-
- CWriteHeader (conn, FinishedMType,
- errorcount ? 0 : CsObjectWritten | CsComplete);
- /* Bye, bye! */
- CWriteRequestBuffer (conn);
-
- /* Block on read. */
- while (! readable_p (cadillacObj.fd_input))
- {
- if (exiting)
- my_friendly_abort (34);
- exiting = 1;
- }
- exiting = 1;
-
- req = CReadCompilerMessage (conn);
- cadillac_process_request (&cadillacObj, req);
- }
-}
-
-#else
-/* Stubs. */
-void init_cadillac () {}
-void cadillac_start () {}
-void cadillac_start_decl (decl)
- tree decl;
-{}
-void
-cadillac_finish_decl (decl)
- tree decl;
-{}
-void
-cadillac_start_function (fndecl)
- tree fndecl;
-{}
-void
-cadillac_finish_function (fndecl)
- tree fndecl;
-{}
-void
-cadillac_finish_anon_union (decl)
- tree decl;
-{}
-void
-cadillac_start_enum (type)
- tree type;
-{}
-void
-cadillac_finish_enum (type)
- tree type;
-{}
-void
-cadillac_start_struct (type)
- tree type;
-{}
-void
-cadillac_finish_struct (type)
- tree type;
-{}
-void
-cadillac_finish_exception (type)
- tree type;
-{}
-void
-cadillac_push_class (type)
- tree type;
-{}
-void
-cadillac_pop_class ()
-{}
-void
-cadillac_push_lang (name)
- tree name;
-{}
-void
-cadillac_pop_lang ()
-{}
-void
-cadillac_note_source ()
-{}
-void
-cadillac_finish_stmt ()
-{}
-void
-cadillac_switch_source ()
-{}
-void
-cadillac_push_source ()
-{}
-void
-cadillac_pop_source ()
-{}
-#endif
diff --git a/gnu/usr.bin/gcc/cp/g++.c b/gnu/usr.bin/gcc/cp/g++.c
deleted file mode 100644
index 46a0552e824..00000000000
--- a/gnu/usr.bin/gcc/cp/g++.c
+++ /dev/null
@@ -1,584 +0,0 @@
-/* G++ preliminary semantic processing for the compiler driver.
- Copyright (C) 1993, 1994, 1995 Free Software Foundation, Inc.
- Contributed by Brendan Kehoe (brendan@cygnus.com).
-
-This file is part of GNU CC.
-
-GNU CC is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2, or (at your option)
-any later version.
-
-GNU CC is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with GNU CC; see the file COPYING. If not, write to
-the Free Software Foundation, 59 Temple Place - Suite 330,
-Boston, MA 02111-1307, USA. */
-
-/* This program is a wrapper to the main `gcc' driver. For GNU C++,
- we need to do two special things: a) append `-lg++' in situations
- where it's appropriate, to link in libg++, and b) add `-xc++'..`-xnone'
- around file arguments named `foo.c' or `foo.i'. So, we do all of
- this semantic processing then just exec gcc with the new argument
- list.
-
- We used to do all of this in a small shell script, but many users
- found the performance of this as a shell script to be unacceptable.
- In situations where your PATH has a lot of NFS-mounted directories,
- using a script that runs sed and other things would be a nasty
- performance hit. With this program, we never search the PATH at all. */
-
-#include "config.h"
-#ifdef __STDC__
-#include <stdarg.h>
-#else
-#include <varargs.h>
-#endif
-#include <stdio.h>
-#include <sys/types.h>
-#if !defined(_WIN32)
-#include <sys/file.h> /* May get R_OK, etc. on some systems. */
-#else
-#include <process.h>
-#endif
-#include <errno.h>
-
-/* Defined to the name of the compiler; if using a cross compiler, the
- Makefile should compile this file with the proper name
- (e.g., "i386-aout-gcc"). */
-#ifndef GCC_NAME
-#define GCC_NAME "gcc"
-#endif
-
-/* This bit is set if we saw a `-xfoo' language specification. */
-#define LANGSPEC (1<<1)
-/* This bit is set if they did `-lm' or `-lmath'. */
-#define MATHLIB (1<<2)
-
-#ifndef MATH_LIBRARY
-#define MATH_LIBRARY "-lm"
-#endif
-
-/* On MSDOS, write temp files in current dir
- because there's no place else we can expect to use. */
-#ifdef __MSDOS__
-#ifndef P_tmpdir
-#define P_tmpdir "."
-#endif
-#ifndef R_OK
-#define R_OK 4
-#define W_OK 2
-#define X_OK 1
-#endif
-#endif
-
-#ifndef VPROTO
-#ifdef __STDC__
-#define PVPROTO(ARGS) ARGS
-#define VPROTO(ARGS) ARGS
-#define VA_START(va_list,var) va_start(va_list,var)
-#else
-#define PVPROTO(ARGS) ()
-#define VPROTO(ARGS) (va_alist) va_dcl
-#define VA_START(va_list,var) va_start(va_list)
-#endif
-#endif
-
-#ifndef errno
-extern int errno;
-#endif
-
-extern int sys_nerr;
-#ifndef HAVE_STRERROR
-#if defined(bsd4_4)
-extern const char *const sys_errlist[];
-#else
-extern char *sys_errlist[];
-#endif
-#else
-extern char *strerror();
-#endif
-
-/* Name with which this program was invoked. */
-static char *programname;
-
-char *
-my_strerror(e)
- int e;
-{
-
-#ifdef HAVE_STRERROR
- return strerror(e);
-
-#else
-
- static char buffer[30];
- if (!e)
- return "";
-
- if (e > 0 && e < sys_nerr)
- return sys_errlist[e];
-
- sprintf (buffer, "Unknown error %d", e);
- return buffer;
-#endif
-}
-
-#ifdef HAVE_VPRINTF
-/* Output an error message and exit */
-
-static void
-fatal VPROTO((char *format, ...))
-{
-#ifndef __STDC__
- char *format;
-#endif
- va_list ap;
-
- VA_START (ap, format);
-
-#ifndef __STDC__
- format = va_arg (ap, char*);
-#endif
-
- fprintf (stderr, "%s: ", programname);
- vfprintf (stderr, format, ap);
- va_end (ap);
- fprintf (stderr, "\n");
-#if 0
- /* XXX Not needed for g++ driver. */
- delete_temp_files ();
-#endif
- exit (1);
-}
-
-static void
-error VPROTO((char *format, ...))
-{
-#ifndef __STDC__
- char *format;
-#endif
- va_list ap;
-
- VA_START (ap, format);
-
-#ifndef __STDC__
- format = va_arg (ap, char*);
-#endif
-
- fprintf (stderr, "%s: ", programname);
- vfprintf (stderr, format, ap);
- va_end (ap);
-
- fprintf (stderr, "\n");
-}
-
-#else /* not HAVE_VPRINTF */
-
-static void
-error (msg, arg1, arg2)
- char *msg, *arg1, *arg2;
-{
- fprintf (stderr, "%s: ", programname);
- fprintf (stderr, msg, arg1, arg2);
- fprintf (stderr, "\n");
-}
-
-static void
-fatal (msg, arg1, arg2)
- char *msg, *arg1, *arg2;
-{
- error (msg, arg1, arg2);
-#if 0
- /* XXX Not needed for g++ driver. */
- delete_temp_files ();
-#endif
- exit (1);
-}
-
-#endif /* not HAVE_VPRINTF */
-
-/* More 'friendly' abort that prints the line and file.
- config.h can #define abort fancy_abort if you like that sort of thing. */
-
-void
-fancy_abort ()
-{
- fatal ("Internal g++ abort.");
-}
-
-char *
-xmalloc (size)
- unsigned size;
-{
- register char *value = (char *) malloc (size);
- if (value == 0)
- fatal ("virtual memory exhausted");
- return value;
-}
-
-/* Return a newly-allocated string whose contents concatenate those
- of s1, s2, s3. */
-static char *
-concat (s1, s2, s3)
- char *s1, *s2, *s3;
-{
- int len1 = strlen (s1), len2 = strlen (s2), len3 = strlen (s3);
- char *result = xmalloc (len1 + len2 + len3 + 1);
-
- strcpy (result, s1);
- strcpy (result + len1, s2);
- strcpy (result + len1 + len2, s3);
- *(result + len1 + len2 + len3) = 0;
-
- return result;
-}
-
-static void
-pfatal_with_name (name)
- char *name;
-{
- fatal (concat ("%s: ", my_strerror (errno), ""), name);
-}
-
-#ifdef __MSDOS__
-/* This is the common prefix we use to make temp file names. */
-char *temp_filename;
-
-/* Length of the prefix. */
-int temp_filename_length;
-
-/* Compute a string to use as the base of all temporary file names. */
-static char *
-choose_temp_base_try (try, base)
-char *try;
-char *base;
-{
- char *rv;
- if (base)
- rv = base;
- else if (try == (char *)0)
- rv = 0;
- else if (access (try, R_OK | W_OK) != 0)
- rv = 0;
- else
- rv = try;
- return rv;
-}
-
-static void
-choose_temp_base ()
-{
- char *base = 0;
- int len;
-
- base = choose_temp_base_try (getenv ("TMPDIR"), base);
- base = choose_temp_base_try (getenv ("TMP"), base);
- base = choose_temp_base_try (getenv ("TEMP"), base);
-
-#if 0 /* XXX - P_tmpdir is not /tmp - etheisen */
-#ifdef P_tmpdir
- base = choose_temp_base_try (P_tmpdir, base);
-#endif
-#endif /* XXX */
-
- base = choose_temp_base_try ("/usr/tmp", base);
- base = choose_temp_base_try ("/tmp", base);
-
- /* If all else fails, use the current directory! */
- if (base == (char *)0)
- base = "./";
-
- len = strlen (base);
- temp_filename = xmalloc (len + sizeof("/ccXXXXXX"));
- strcpy (temp_filename, base);
- if (len > 0 && temp_filename[len-1] != '/')
- temp_filename[len++] = '/';
- strcpy (temp_filename + len, "ccXXXXXX");
-
- mktemp (temp_filename);
- temp_filename_length = strlen (temp_filename);
- if (temp_filename_length == 0)
- abort ();
-}
-
-static void
-perror_exec (name)
- char *name;
-{
- char *s;
-
- if (errno < sys_nerr)
- s = concat ("installation problem, cannot exec %s: ",
- my_strerror( errno ), "");
- else
- s = "installation problem, cannot exec %s";
- error (s, name);
-}
-
-/* This is almost exactly what's in gcc.c:pexecute for MSDOS. */
-void
-run_dos (program, argv)
- char *program;
- char *argv[];
-{
- char *scmd, *rf;
- FILE *argfile;
- int i;
-
- choose_temp_base (); /* not in gcc.c */
-
- scmd = (char *) malloc (strlen (program) + strlen (temp_filename) + 10);
- rf = scmd + strlen (program) + 6;
- sprintf (scmd, "%s.exe @%s.gp", program, temp_filename);
-
- argfile = fopen (rf, "w");
- if (argfile == 0)
- pfatal_with_name (rf);
-
- for (i=1; argv[i]; i++)
- {
- char *cp;
- for (cp = argv[i]; *cp; cp++)
- {
- if (*cp == '"' || *cp == '\'' || *cp == '\\' || isspace (*cp))
- fputc ('\\', argfile);
- fputc (*cp, argfile);
- }
- fputc ('\n', argfile);
- }
- fclose (argfile);
-
- i = system (scmd);
-
- remove (rf);
-
- if (i == -1)
- perror_exec (program);
-}
-#endif /* __MSDOS__ */
-
-int
-main (argc, argv)
- int argc;
- char **argv;
-{
- register int i, j = 0;
- register char *p;
- int verbose = 0;
-
- /* This will be 0 if we encounter a situation where we should not
- link in libstdc++, or 2 if we should link in libg++ as well. */
- int library = 1;
-
- /* Used to track options that take arguments, so we don't go wrapping
- those with -xc++/-xnone. */
- char *quote = NULL;
-
- /* The new argument list will be contained in this. */
- char **arglist;
-
- /* The name of the compiler we will want to run---by default, it
- will be the definition of `GCC_NAME', e.g., `gcc'. */
- char *gcc = GCC_NAME;
-
- /* Non-zero if we saw a `-xfoo' language specification on the
- command line. Used to avoid adding our own -xc++ if the user
- already gave a language for the file. */
- int saw_speclang = 0;
-
- /* Non-zero if we saw `-lm' or `-lmath' on the command line. */
- char *saw_math = 0;
-
- /* The number of arguments being added to what's in argv, other than
- libraries. We use this to track the number of times we've inserted
- -xc++/-xnone. */
- int added = 0;
-
- /* An array used to flag each argument that needs a bit set for
- LANGSPEC or MATHLIB. */
- int *args;
-
- p = argv[0] + strlen (argv[0]);
-
- /* If we're called as g++ (or i386-aout-g++), link in libg++ as well. */
-
- if (strcmp (p - 3, "g++") == 0)
- {
- library = 2;
- }
-
- while (p != argv[0] && p[-1] != '/')
- --p;
- programname = p;
-
- if (argc == 1)
- fatal ("No input files specified.\n");
-
-#ifndef __MSDOS__
- /* We do a little magic to find out where the main gcc executable
- is. If they ran us as /usr/local/bin/g++, then we will look
- for /usr/local/bin/gcc; similarly, if they just ran us as `g++',
- we'll just look for `gcc'. */
- if (p != argv[0])
- {
- *--p = '\0';
- gcc = (char *) malloc ((strlen (argv[0]) + 1 + strlen (GCC_NAME) + 1)
- * sizeof (char));
- sprintf (gcc, "%s/%s", argv[0], GCC_NAME);
- }
-#endif
-
- args = (int *) malloc (argc * sizeof (int));
- bzero ((char *) args, argc * sizeof (int));
-
- for (i = 1; i < argc; i++)
- {
- /* If the previous option took an argument, we swallow it here. */
- if (quote)
- {
- quote = NULL;
- continue;
- }
-
- if (argv[i][0] == '\0' || argv[i][1] == '\0')
- continue;
-
- if (argv[i][0] == '-')
- {
- if (library != 0 && strcmp (argv[i], "-nostdlib") == 0)
- {
- library = 0;
- }
- else if (strcmp (argv[i], "-lm") == 0
- || strcmp (argv[i], "-lmath") == 0)
- args[i] |= MATHLIB;
- else if (strcmp (argv[i], "-v") == 0)
- {
- verbose = 1;
- if (argc == 2)
- {
- /* If they only gave us `-v', don't try to link
- in libg++. */
- library = 0;
- }
- }
- else if (strncmp (argv[i], "-x", 2) == 0)
- saw_speclang = 1;
- else if (((argv[i][2] == '\0'
- && (char *)strchr ("bBVDUoeTuIYmLiA", argv[i][1]) != NULL)
- || strcmp (argv[i], "-Tdata") == 0))
- quote = argv[i];
- else if (library != 0 && ((argv[i][2] == '\0'
- && (char *) strchr ("cSEM", argv[i][1]) != NULL)
- || strcmp (argv[i], "-MM") == 0))
- {
- /* Don't specify libraries if we won't link, since that would
- cause a warning. */
- library = 0;
- }
- else
- /* Pass other options through. */
- continue;
- }
- else
- {
- int len;
-
- if (saw_speclang)
- {
- saw_speclang = 0;
- continue;
- }
-
- /* If the filename ends in .c or .i, put options around it.
- But not if a specified -x option is currently active. */
- len = strlen (argv[i]);
- if (len > 2
- && (argv[i][len - 1] == 'c' || argv[i][len - 1] == 'i')
- && argv[i][len - 2] == '.')
- {
- args[i] |= LANGSPEC;
- added += 2;
- }
- }
- }
-
- if (quote)
- fatal ("argument to `%s' missing\n", quote);
-
- if (added || library)
- {
- arglist = (char **) malloc ((argc + added + 4) * sizeof (char *));
-
- for (i = 1, j = 1; i < argc; i++, j++)
- {
- arglist[j] = argv[i];
-
- /* Make sure -lg++ is before the math library, since libg++
- itself uses those math routines. */
- if (!saw_math && (args[i] & MATHLIB) && library)
- {
- --j;
- saw_math = argv[i];
- }
-
- /* Wrap foo.c and foo.i files in a language specification to
- force the gcc compiler driver to run cc1plus on them. */
- if (args[i] & LANGSPEC)
- {
- int len = strlen (argv[i]);
- if (argv[i][len - 1] == 'i')
- arglist[j++] = "-xc++-cpp-output";
- else
- arglist[j++] = "-xc++";
- arglist[j++] = argv[i];
- arglist[j] = "-xnone";
- }
- }
-
- /* Add `-lg++' if we haven't already done so. */
- if (library == 2)
- arglist[j++] = "-lg++";
- if (library)
- arglist[j++] = "-lstdc++";
- if (saw_math)
- arglist[j++] = saw_math;
- else if (library)
- arglist[j++] = MATH_LIBRARY;
-
- arglist[j] = NULL;
- }
- else
- /* No need to copy 'em all. */
- arglist = argv;
-
- arglist[0] = gcc;
-
- if (verbose)
- {
- if (j == 0)
- j = argc;
-
- for (i = 0; i < j; i++)
- fprintf (stderr, " %s", arglist[i]);
- fprintf (stderr, "\n");
- }
-#if !defined(OS2) && !defined (_WIN32)
-#ifdef __MSDOS__
- run_dos (gcc, arglist);
-#else /* !__MSDOS__ */
- if (execvp (gcc, arglist) < 0)
- pfatal_with_name (gcc);
-#endif /* __MSDOS__ */
-#else /* OS2 or _WIN32 */
- if (spawnvp (1, gcc, arglist) < 0)
- pfatal_with_name (gcc);
-#endif
-
- return 0;
-}
diff --git a/gnu/usr.bin/gcc/cp/gc.c b/gnu/usr.bin/gcc/cp/gc.c
deleted file mode 100644
index cff1635f53a..00000000000
--- a/gnu/usr.bin/gcc/cp/gc.c
+++ /dev/null
@@ -1,1550 +0,0 @@
-/* Garbage collection primitives for GNU C++.
- Copyright (C) 1992, 1993, 1994, 1995 Free Software Foundation, Inc.
- Contributed by Michael Tiemann (tiemann@cygnus.com)
-
-This file is part of GNU CC.
-
-GNU CC is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2, or (at your option)
-any later version.
-
-GNU CC is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with GNU CC; see the file COPYING. If not, write to
-the Free Software Foundation, 59 Temple Place - Suite 330,
-Boston, MA 02111-1307, USA. */
-
-
-#include "config.h"
-#include "tree.h"
-#include "cp-tree.h"
-#include "flags.h"
-#include "output.h"
-
-#undef NULL
-#define NULL 0
-
-extern tree define_function ();
-extern tree build_t_desc_overload ();
-extern struct obstack *permanent_obstack;
-
-/* This is the function decl for the (pseudo-builtin) __gc_protect
- function. Args are (class *value, int index); Returns value. */
-tree gc_protect_fndecl;
-
-/* This is the function decl for the (pseudo-builtin) __gc_unprotect
- function. Args are (int index); void return. */
-tree gc_unprotect_fndecl;
-
-/* This is the function decl for the (pseudo-builtin) __gc_push
- function. Args are (int length); void return. */
-tree gc_push_fndecl;
-
-/* This is the function decl for the (pseudo-builtin) __gc_pop
- function. Args are void; void return. */
-tree gc_pop_fndecl;
-
-/* Special integers that are used to represent bits in gc-safe objects. */
-tree gc_nonobject;
-tree gc_visible;
-tree gc_white;
-tree gc_offwhite;
-tree gc_grey;
-tree gc_black;
-
-/* in c-common.c */
-extern tree combine_strings PROTO((tree));
-
-/* Predicate that returns non-zero if TYPE needs some kind of
- entry for the GC. Returns zero otherwise. */
-int
-type_needs_gc_entry (type)
- tree type;
-{
- tree ttype = type;
-
- if (! flag_gc || type == error_mark_node)
- return 0;
-
- /* Aggregate types need gc entries if any of their members
- need gc entries. */
- if (IS_AGGR_TYPE (type))
- {
- tree binfos;
- tree fields = TYPE_FIELDS (type);
- int i;
-
- /* We don't care about certain pointers. Pointers
- to virtual baseclasses are always up front. We also
- cull out virtual function table pointers because it's
- easy, and it simplifies the logic.*/
- while (fields
- && (DECL_NAME (fields) == NULL_TREE
- || VFIELD_NAME_P (DECL_NAME (fields))
- || VBASE_NAME_P (DECL_NAME (fields))
- || !strcmp (IDENTIFIER_POINTER (DECL_NAME (fields)), "__bits")))
- fields = TREE_CHAIN (fields);
-
- while (fields)
- {
- if (type_needs_gc_entry (TREE_TYPE (fields)))
- return 1;
- fields = TREE_CHAIN (fields);
- }
-
- binfos = TYPE_BINFO_BASETYPES (type);
- if (binfos)
- for (i = TREE_VEC_LENGTH (binfos)-1; i >= 0; i--)
- if (type_needs_gc_entry (BINFO_TYPE (TREE_VEC_ELT (binfos, i))))
- return 1;
-
- return 0;
- }
-
- while (TREE_CODE (ttype) == ARRAY_TYPE
- && TREE_CODE (TREE_TYPE (ttype)) == ARRAY_TYPE)
- ttype = TREE_TYPE (ttype);
- if ((TREE_CODE (ttype) == POINTER_TYPE
- || TREE_CODE (ttype) == ARRAY_TYPE
- || TREE_CODE (ttype) == REFERENCE_TYPE)
- && IS_AGGR_TYPE (TREE_TYPE (ttype))
- && CLASSTYPE_RTTI (TREE_TYPE (ttype)))
- return 1;
-
- return 0;
-}
-
-/* Predicate that returns non-zero iff FROM is safe from the GC.
-
- If TO is nonzero, it means we know that FROM is being stored
- in TO, which make make it safe. */
-int
-value_safe_from_gc (to, from)
- tree to, from;
-{
- /* First, return non-zero for easy cases: parameters,
- static variables. */
- if (TREE_CODE (from) == PARM_DECL
- || (TREE_CODE (from) == VAR_DECL
- && TREE_STATIC (from)))
- return 1;
-
- /* If something has its address taken, it cannot be
- in the heap, so it doesn't need to be protected. */
- if (TREE_CODE (from) == ADDR_EXPR || TREE_REFERENCE_EXPR (from))
- return 1;
-
- /* If we are storing into a static variable, then what
- we store will be safe from the gc. */
- if (to && TREE_CODE (to) == VAR_DECL
- && TREE_STATIC (to))
- return 1;
-
- /* Now recurse on structure of FROM. */
- switch (TREE_CODE (from))
- {
- case COMPONENT_REF:
- /* These guys are special, and safe. */
- if (TREE_CODE (TREE_OPERAND (from, 1)) == FIELD_DECL
- && (VFIELD_NAME_P (DECL_NAME (TREE_OPERAND (from, 1)))
- || VBASE_NAME_P (DECL_NAME (TREE_OPERAND (from, 1)))))
- return 1;
- /* fall through... */
- case NOP_EXPR:
- case CONVERT_EXPR:
- case NON_LVALUE_EXPR:
- case WITH_CLEANUP_EXPR:
- case SAVE_EXPR:
- case PREDECREMENT_EXPR:
- case PREINCREMENT_EXPR:
- case POSTDECREMENT_EXPR:
- case POSTINCREMENT_EXPR:
- if (value_safe_from_gc (to, TREE_OPERAND (from, 0)))
- return 1;
- break;
-
- case VAR_DECL:
- case PARM_DECL:
- /* We can safely pass these things as parameters to functions. */
- if (to == 0)
- return 1;
-
- case ARRAY_REF:
- case INDIRECT_REF:
- case RESULT_DECL:
- case OFFSET_REF:
- case CALL_EXPR:
- case METHOD_CALL_EXPR:
- break;
-
- case COMPOUND_EXPR:
- case TARGET_EXPR:
- if (value_safe_from_gc (to, TREE_OPERAND (from, 1)))
- return 1;
- break;
-
- case COND_EXPR:
- if (value_safe_from_gc (to, TREE_OPERAND (from, 1))
- && value_safe_from_gc (to, TREE_OPERAND (from, 2)))
- return 1;
- break;
-
- case PLUS_EXPR:
- case MINUS_EXPR:
- if ((type_needs_gc_entry (TREE_TYPE (TREE_OPERAND (from, 0)))
- || value_safe_from_gc (to, TREE_OPERAND (from, 0)))
- && (type_needs_gc_entry (TREE_TYPE (TREE_OPERAND (from, 1))) == 0
- || value_safe_from_gc (to, TREE_OPERAND (from, 1))))
- return 1;
- break;
-
- case RTL_EXPR:
- /* Every time we build an RTL_EXPR in the front-end, we must
- ensure that everything in it is safe from the garbage collector.
- ??? This has only been done for `build_new'. */
- return 1;
-
- default:
- my_friendly_abort (41);
- }
-
- if (to == 0)
- return 0;
-
- /* FROM wasn't safe. But other properties of TO might make it safe. */
- switch (TREE_CODE (to))
- {
- case VAR_DECL:
- case PARM_DECL:
- /* We already culled out static VAR_DECLs above. */
- return 0;
-
- case COMPONENT_REF:
- /* These guys are special, and safe. */
- if (TREE_CODE (TREE_OPERAND (to, 1)) == FIELD_DECL
- && (VFIELD_NAME_P (DECL_NAME (TREE_OPERAND (to, 1)))
- || VBASE_NAME_P (DECL_NAME (TREE_OPERAND (to, 1)))))
- return 1;
- /* fall through... */
-
- case NOP_EXPR:
- case NON_LVALUE_EXPR:
- case WITH_CLEANUP_EXPR:
- case SAVE_EXPR:
- case PREDECREMENT_EXPR:
- case PREINCREMENT_EXPR:
- case POSTDECREMENT_EXPR:
- case POSTINCREMENT_EXPR:
- return value_safe_from_gc (TREE_OPERAND (to, 0), from);
-
- case COMPOUND_EXPR:
- case TARGET_EXPR:
- return value_safe_from_gc (TREE_OPERAND (to, 1), from);
-
- case COND_EXPR:
- return (value_safe_from_gc (TREE_OPERAND (to, 1), from)
- && value_safe_from_gc (TREE_OPERAND (to, 2), from));
-
- case INDIRECT_REF:
- case ARRAY_REF:
- /* This used to be 0, but our current restricted model
- allows this to be 1. We'll never get arrays this way. */
- return 1;
-
- default:
- my_friendly_abort (42);
- }
-
- /* Catch-all case is that TO/FROM is not safe. */
- return 0;
-}
-
-/* Function to build a static GC entry for DECL. TYPE is DECL's type.
-
- For objects of type `class *', this is just an entry in the
- static vector __PTR_LIST__.
-
- For objects of type `class[]', this requires building an entry
- in the static vector __ARR_LIST__.
-
- For aggregates, this records all fields of type `class *'
- and `class[]' in the respective lists above. */
-void
-build_static_gc_entry (decl, type)
- tree decl;
- tree type;
-{
- /* Now, figure out what sort of entry to build. */
- if (TREE_CODE (type) == POINTER_TYPE
- || TREE_CODE (type) == REFERENCE_TYPE)
- assemble_gc_entry (IDENTIFIER_POINTER (DECL_NAME (decl)));
- else if (TREE_CODE (type) == RECORD_TYPE)
- {
- tree ref = get_temp_name (build_reference_type (type), 1);
- DECL_INITIAL (ref) = build1 (ADDR_EXPR, TREE_TYPE (ref), decl);
- TREE_CONSTANT (DECL_INITIAL (ref)) = 1;
- cp_finish_decl (ref, DECL_INITIAL (ref), NULL_TREE, 0, 0);
- }
- else
- {
- /* Not yet implemented.
-
- Cons up a static variable that holds address and length info
- and add that to ___ARR_LIST__. */
- my_friendly_abort (43);
- }
-}
-
-/* Protect FROM from the GC, assuming FROM is going to be
- stored into TO. We handle three cases for TO here:
-
- case 1: TO is a stack variable.
- case 2: TO is zero (which means it is a parameter).
- case 3: TO is a return value. */
-
-tree
-protect_value_from_gc (to, from)
- tree to, from;
-{
- if (to == 0)
- {
- tree cleanup;
-
- to = get_temp_regvar (TREE_TYPE (from), from);
-
- /* Convert from integer to list form since we'll use it twice. */
- DECL_GC_OFFSET (to) = build_tree_list (NULL_TREE, DECL_GC_OFFSET (to));
- cleanup = build_function_call (gc_unprotect_fndecl,
- DECL_GC_OFFSET (to));
-
- if (! cp_expand_decl_cleanup (to, cleanup))
- {
- compiler_error ("cannot unprotect parameter in this scope");
- return error_mark_node;
- }
- }
-
- /* Should never need to protect a value that's headed for static storage. */
- if (TREE_STATIC (to))
- my_friendly_abort (44);
-
- switch (TREE_CODE (to))
- {
- case COMPONENT_REF:
- case INDIRECT_REF:
- return protect_value_from_gc (TREE_OPERAND (to, 0), from);
-
- case VAR_DECL:
- case PARM_DECL:
- {
- tree rval;
- if (DECL_GC_OFFSET (to) == NULL_TREE)
- {
- /* Because of a cast or a conversion, we might stick
- a value into a variable that would not normally
- have a GC entry. */
- DECL_GC_OFFSET (to) = size_int (++current_function_obstack_index);
- }
-
- if (TREE_CODE (DECL_GC_OFFSET (to)) != TREE_LIST)
- {
- DECL_GC_OFFSET (to)
- = build_tree_list (NULL_TREE, DECL_GC_OFFSET (to));
- }
-
- current_function_obstack_usage = 1;
- rval = build_function_call (gc_protect_fndecl,
- tree_cons (NULL_TREE, from,
- DECL_GC_OFFSET (to)));
- TREE_TYPE (rval) = TREE_TYPE (from);
- return rval;
- }
- }
-
- /* If we fall through the switch, assume we lost. */
- my_friendly_abort (45);
- /* NOTREACHED */
- return NULL_TREE;
-}
-
-/* Given the expression EXP of type `class *', return the head
- of the object pointed to by EXP. */
-tree
-build_headof (exp)
- tree exp;
-{
- tree type = TREE_TYPE (exp);
- tree vptr, offset;
-
- if (TREE_CODE (type) != POINTER_TYPE)
- {
- error ("`headof' applied to non-pointer type");
- return error_mark_node;
- }
- type = TREE_TYPE (type);
-
- if (!TYPE_VIRTUAL_P (type) || CLASSTYPE_VFIELD (type) == NULL_TREE)
- return exp;
-
- vptr = fold (size_binop (PLUS_EXPR,
- size_binop (FLOOR_DIV_EXPR,
- DECL_FIELD_BITPOS (CLASSTYPE_VFIELD (type)),
- size_int (BITS_PER_UNIT)),
- exp));
- vptr = build1 (INDIRECT_REF, build_pointer_type (vtable_entry_type), vptr);
-
- if (flag_vtable_thunks)
- offset = build_array_ref (vptr, integer_zero_node);
- else
- offset = build_component_ref (build_array_ref (vptr, integer_zero_node),
- delta_identifier,
- NULL_TREE, 0);
-
- type = build_type_variant (ptr_type_node, TREE_READONLY (exp),
- TREE_THIS_VOLATILE (exp));
- return build (PLUS_EXPR, type, exp,
- convert (ptrdiff_type_node, offset));
-}
-
-/* Return the type_info node associated with the expression EXP. If EXP is
- a reference to a polymorphic class, return the dynamic type; otherwise
- return the static type of the expression. */
-tree
-build_typeid (exp)
- tree exp;
-{
- tree type;
-
- if (!flag_rtti)
- cp_error ("cannot take typeid of object when -frtti is not specified");
-
- if (exp == error_mark_node)
- return error_mark_node;
-
- type = TREE_TYPE (exp);
-
- /* Strip top-level cv-qualifiers. */
- type = TYPE_MAIN_VARIANT (type);
-
- /* if b is an instance of B, typeid(b) == typeid(B). Do this before
- reference trickiness. */
- if (TREE_CODE (exp) == VAR_DECL && TREE_CODE (type) == RECORD_TYPE)
- return get_typeid (type);
-
- /* peel back references, so they match. */
- if (TREE_CODE (type) == REFERENCE_TYPE)
- type = TREE_TYPE (type);
-
- /* Peel off cv qualifiers. */
- type = TYPE_MAIN_VARIANT (type);
-
- /* Apply trivial conversion T -> T& for dereferenced ptrs. */
- if (TREE_CODE (type) == RECORD_TYPE)
- type = build_reference_type (type);
-
- /* If exp is a reference to polymorphic type, get the real type_info. */
- if (TREE_CODE (type) == REFERENCE_TYPE && TYPE_VIRTUAL_P (TREE_TYPE (type)))
- {
- /* build reference to type_info from vtable. */
- tree t;
-
- if (flag_vtable_thunks)
- t = build_vfn_ref ((tree *) NULL_TREE, exp, integer_one_node);
- else
- t = build_vfn_ref ((tree *) NULL_TREE, exp, integer_zero_node);
-
- TREE_TYPE (t) = build_pointer_type (__class_desc_type_node);
- t = build_indirect_ref (t, NULL);
- return t;
- }
-
- /* otherwise return the type_info for the static type of the expr. */
- return get_typeid (type);
-}
-
-/* Return the type_info object for TYPE, creating it if necessary. */
-tree
-get_typeid (type)
- tree type;
-{
- tree t, td;
-
- if (type == error_mark_node)
- return error_mark_node;
-
- /* Is it useful (and/or correct) to have different typeids for `T &'
- and `T'? */
- if (TREE_CODE (type) == REFERENCE_TYPE)
- type = TREE_TYPE (type);
-
- td = build_t_desc (type, 1);
- if (td == error_mark_node)
- return error_mark_node;
-
- t = TREE_OPERAND (td, 0);
- return t;
-}
-
-/* Get a bad_cast node for the program to throw...
-
- See libstdc++::exception{,.cc} for __bad_cast_object */
-tree
-get_bad_cast_node ()
-{
- static tree t;
- if (t == NULL_TREE
- && (t = lookup_name (get_identifier ("__bad_cast_object"), 0))
- == NULL_TREE)
- {
- error ("you must #include <typeinfo>");
- return error_mark_node;
- }
- return t;
-}
-
-/* Execute a dynamic cast, as described in section 5.2.6 of the 9/93 working
- paper. */
-tree
-build_dynamic_cast (type, expr)
- tree type, expr;
-{
- enum tree_code tc = TREE_CODE (type);
- tree exprtype = TREE_TYPE (expr);
- enum tree_code ec = TREE_CODE (exprtype);
- tree retval;
-
- if (type == error_mark_node || expr == error_mark_node)
- return error_mark_node;
-
- switch (tc)
- {
- case POINTER_TYPE:
- if (ec == REFERENCE_TYPE)
- {
- expr = convert_from_reference (expr);
- exprtype = TREE_TYPE (expr);
- ec = TREE_CODE (exprtype);
- }
- if (ec != POINTER_TYPE)
- goto fail;
- if (TREE_CODE (TREE_TYPE (exprtype)) != RECORD_TYPE)
- goto fail;
- if (TYPE_SIZE (TREE_TYPE (exprtype)) == 0)
- goto fail;
- if (TREE_READONLY (TREE_TYPE (exprtype)) &&
- ! TYPE_READONLY (TREE_TYPE (type)))
- goto fail;
- if (TYPE_MAIN_VARIANT (TREE_TYPE (type)) == void_type_node)
- break;
- /* else fall through */
- case REFERENCE_TYPE:
- if (TREE_CODE (TREE_TYPE (type)) == RECORD_TYPE
- && TYPE_SIZE (TREE_TYPE (type)) != NULL_TREE)
- break;
- /* else fall through */
- default:
- goto fail;
- }
-
- /* Apply trivial conversion T -> T& for dereferenced ptrs. */
- if (ec == RECORD_TYPE)
- {
- exprtype = build_type_variant (exprtype, TREE_READONLY (expr),
- TREE_THIS_VOLATILE (expr));
- exprtype = build_reference_type (exprtype);
- expr = convert_to_reference (exprtype, expr, CONV_IMPLICIT,
- LOOKUP_NORMAL, NULL_TREE);
- ec = REFERENCE_TYPE;
- }
-
- if (tc == REFERENCE_TYPE)
- {
- if (ec != REFERENCE_TYPE)
- goto fail;
- if (TREE_CODE (TREE_TYPE (exprtype)) != RECORD_TYPE)
- goto fail;
- if (TYPE_SIZE (TREE_TYPE (exprtype)) == 0)
- goto fail;
- }
-
- /* If *type is an unambiguous accessible base class of *exprtype,
- convert statically. */
- {
- int distance;
- tree path;
-
- distance = get_base_distance (TREE_TYPE (type), TREE_TYPE (exprtype), 1,
- &path);
- if (distance >= 0)
- return build_vbase_path (PLUS_EXPR, type, expr, path, 0);
- }
-
- /* Otherwise *exprtype must be a polymorphic class (have a vtbl). */
- if (TYPE_VIRTUAL_P (TREE_TYPE (exprtype)))
- {
- /* if TYPE is `void *', return pointer to complete object. */
- if (tc == POINTER_TYPE
- && TYPE_MAIN_VARIANT (TREE_TYPE (type)) == void_type_node)
- {
- /* if b is an object, dynamic_cast<void *>(&b) == (void *)&b. */
- if (TREE_CODE (expr) == ADDR_EXPR
- && TREE_CODE (TREE_OPERAND (expr, 0)) == VAR_DECL
- && TREE_CODE (TREE_TYPE (TREE_OPERAND (expr, 0))) == RECORD_TYPE)
- return build1 (NOP_EXPR, type, expr);
-
- return build_headof (expr);
- }
- else
- {
- tree retval;
- tree result, td1, td2, elems, tmp1, expr1;
-
- /* If we got here, we can't convert statically. Therefore,
- dynamic_cast<D&>(b) (b an object) cannot succeed. */
- if (ec == REFERENCE_TYPE)
- {
- if (TREE_CODE (expr) == VAR_DECL
- && TREE_CODE (TREE_TYPE (expr)) == RECORD_TYPE)
- {
- cp_warning ("dynamic_cast of `%#D' to `%#T' can never succeed",
- expr, type);
- return build_throw (get_bad_cast_node ());
- }
- }
- /* Ditto for dynamic_cast<D*>(&b). */
- else if (TREE_CODE (expr) == ADDR_EXPR)
- {
- tree op = TREE_OPERAND (expr, 0);
- if (TREE_CODE (op) == VAR_DECL
- && TREE_CODE (TREE_TYPE (op)) == RECORD_TYPE)
- {
- cp_warning ("dynamic_cast of `%#D' to `%#T' can never succeed",
- expr, type);
- retval = build_int_2 (0, 0);
- TREE_TYPE (retval) = type;
- return retval;
- }
- }
-
- expr1 = expr;
- if (tc == REFERENCE_TYPE)
- expr1 = build_unary_op (ADDR_EXPR, expr1, 0);
-
- /* Build run-time conversion. */
- expr1 = build_headof (expr1);
-
- if (ec == POINTER_TYPE)
- td1 = build_typeid (build_indirect_ref (expr, NULL_PTR));
- else
- td1 = build_typeid (expr);
-
- if (tc == POINTER_TYPE)
- td2 = get_typeid (TREE_TYPE (type));
- else
- td2 = get_typeid (type);
-
- elems = tree_cons (NULL_TREE, td2,
- tree_cons (NULL_TREE, build_int_2 (1, 0),
- tree_cons (NULL_TREE, expr1, NULL_TREE)));
- result = build_method_call (td1,
- get_identifier ("__rtti_match"), elems, NULL_TREE, LOOKUP_NORMAL);
-
- if (tc == REFERENCE_TYPE)
- {
- expr1 = build_throw (get_bad_cast_node ());
- expr1 = build_compound_expr (tree_cons (NULL_TREE, expr1,
- build_tree_list (NULL_TREE, convert (type, integer_zero_node))));
- TREE_TYPE (expr1) = type;
- return build (COND_EXPR, type, result, result, expr1);
- }
-
- /* Now back to the type we want from a void*. */
- result = convert (type, result);
- return result;
- }
- }
-
- fail:
- cp_error ("cannot dynamic_cast `%E' (of type `%#T') to type `%#T'",
- expr, exprtype, type);
- return error_mark_node;
-}
-
-/* Build and initialize various sorts of descriptors. Every descriptor
- node has a name associated with it (the name created by mangling).
- For this reason, we use the identifier as our access to the __*_desc
- nodes, instead of sticking them directly in the types. Otherwise we
- would burden all built-in types (and pointer types) with slots that
- we don't necessarily want to use.
-
- For each descriptor we build, we build a variable that contains
- the descriptor's information. When we need this info at runtime,
- all we need is access to these variables.
-
- Note: these constructors always return the address of the descriptor
- info, since that is simplest for their mutual interaction. */
-
-static tree
-build_generic_desc (tdecl, type, elems)
- tree tdecl;
- tree type;
- tree elems;
-{
- tree init = elems;
- int toplev = global_bindings_p ();
-
- TREE_CONSTANT (init) = 1;
- TREE_STATIC (init) = 1;
- TREE_READONLY (init) = 1;
-
- TREE_TYPE (tdecl) = type;
- DECL_INITIAL (tdecl) = init;
- TREE_STATIC (tdecl) = 1;
- DECL_SIZE (tdecl) = NULL_TREE;
- layout_decl (tdecl, 0);
- if (! toplev)
- push_to_top_level ();
- cp_finish_decl (tdecl, init, NULL_TREE, 0, 0);
- if (! toplev)
- pop_from_top_level ();
-
- if (! TREE_USED (tdecl))
- {
- assemble_external (tdecl);
- TREE_USED (tdecl) = 1;
- }
-
- return IDENTIFIER_AS_DESC (DECL_NAME (tdecl));
-}
-
-/* Build an initializer for a __bltn_desc node. */
-static tree
-build_bltn_desc (tdecl, type)
- tree tdecl;
- tree type;
-{
- tree elems, t;
-
- if (type == boolean_type_node)
- t = lookup_field (__bltn_desc_type_node, get_identifier("_RTTI_BI_BOOL"),
- 0, 0);
- else if (type == char_type_node)
- t = lookup_field (__bltn_desc_type_node, get_identifier("_RTTI_BI_CHAR"),
- 0, 0);
- else if (type == short_integer_type_node)
- t = lookup_field (__bltn_desc_type_node, get_identifier("_RTTI_BI_SHORT"),
- 0, 0);
- else if (type == integer_type_node)
- t = lookup_field (__bltn_desc_type_node, get_identifier("_RTTI_BI_INT"),
- 0, 0);
- else if (type == long_integer_type_node)
- t = lookup_field (__bltn_desc_type_node, get_identifier("_RTTI_BI_LONG"),
- 0, 0);
- else if (type == long_long_integer_type_node)
- t = lookup_field (__bltn_desc_type_node,
- get_identifier("_RTTI_BI_LONGLONG"), 0, 0);
- else if (type == float_type_node)
- t = lookup_field (__bltn_desc_type_node, get_identifier("_RTTI_BI_FLOAT"),
- 0, 0);
- else if (type == double_type_node)
- t = lookup_field (__bltn_desc_type_node,
- get_identifier("_RTTI_BI_DOUBLE"), 0, 0);
- else if (type == long_double_type_node)
- t = lookup_field (__bltn_desc_type_node,
- get_identifier("_RTTI_BI_LDOUBLE"), 0, 0);
- else if (type == unsigned_char_type_node)
- t = lookup_field (__bltn_desc_type_node, get_identifier("_RTTI_BI_UCHAR"),
- 0, 0);
- else if (type == short_unsigned_type_node)
- t = lookup_field (__bltn_desc_type_node, get_identifier("_RTTI_BI_USHORT"),
- 0, 0);
- else if (type == unsigned_type_node)
- t = lookup_field (__bltn_desc_type_node, get_identifier("_RTTI_BI_UINT"),
- 0, 0);
- else if (type == long_unsigned_type_node)
- t = lookup_field (__bltn_desc_type_node, get_identifier("_RTTI_BI_ULONG"),
- 0, 0);
- else if (type == long_long_unsigned_type_node)
- t = lookup_field (__bltn_desc_type_node,
- get_identifier("_RTTI_BI_ULONGLONG"), 0, 0);
- else if (type == signed_char_type_node)
- t = lookup_field (__bltn_desc_type_node, get_identifier("_RTTI_BI_SCHAR"),
- 0, 0);
- else if (type == wchar_type_node)
- t = lookup_field (__bltn_desc_type_node, get_identifier("_RTTI_BI_WCHAR"),
- 0, 0);
- else if (type == void_type_node)
- t = lookup_field (__bltn_desc_type_node, get_identifier("_RTTI_BI_VOID"),
- 0, 0);
- else
- {
- cp_compiler_error ("type `%T' not handled as a built-in type");
- }
-
- elems = tree_cons (NULL_TREE, t, NULL_TREE);
- return build_generic_desc (tdecl, __bltn_desc_type_node, elems);
-}
-
-/* Build an initializer for a __user_desc node. */
-static tree
-build_user_desc (tdecl)
- tree tdecl;
-{
- tree elems, name_string, t;
- tree tname = DECL_NAME (tdecl);
-
- name_string = combine_strings (build_string
- (IDENTIFIER_LENGTH (tname)+1, IDENTIFIER_POINTER (tname)));
- elems = name_string;
- return build_generic_desc (tdecl, __user_desc_type_node, elems);
-}
-
-/* Build an initializer for a __class_type_info node. */
-static tree
-build_class_desc (tdecl, type)
- tree tdecl;
- tree type;
-{
- tree tname = DECL_NAME (tdecl);
- tree name_string;
-
- int i = CLASSTYPE_N_BASECLASSES (type);
- int n_base = i;
- int base_cnt = 0;
- tree binfos = TYPE_BINFO_BASETYPES (type);
- tree vb = CLASSTYPE_VBASECLASSES (type);
- tree base, elems, access, offset, isvir;
- tree base_list, off_list, acc_list, isvir_list;
- tree t;
- static tree acc_pub = NULL_TREE;
- static tree acc_pro = NULL_TREE;
- static tree acc_pri = NULL_TREE;
-
- if (acc_pub == NULL_TREE)
- {
- acc_pub = lookup_field (__class_desc_type_node,
- get_identifier("_RTTI_ACCESS_PUBLIC"), 0, 0);
- acc_pro = lookup_field (__class_desc_type_node,
- get_identifier("_RTTI_ACCESS_PROTECTED"), 0, 0);
- acc_pri = lookup_field (__class_desc_type_node,
- get_identifier("_RTTI_ACCESS_PRIVATE"), 0, 0);
- }
-
- base_list = build_tree_list (NULL_TREE, integer_zero_node);
- off_list = build_tree_list (NULL_TREE, integer_zero_node);
- acc_list = build_tree_list (NULL_TREE, integer_zero_node);
- isvir_list = build_tree_list (NULL_TREE, integer_zero_node);
- while (--i >= 0)
- {
- tree binfo = TREE_VEC_ELT (binfos, i);
-
- base = build_t_desc (BINFO_TYPE (binfo), 1);
- if (TREE_VIA_VIRTUAL (binfo))
- {
- tree t = BINFO_TYPE (binfo);
- char *name;
- tree field;
- int off;
-
- name = (char *) alloca (TYPE_NAME_LENGTH (t)+sizeof (VBASE_NAME)+1);
- sprintf (name, VBASE_NAME_FORMAT, TYPE_NAME_STRING (t));
- field = lookup_field (type, get_identifier (name), 0, 0);
- offset = size_binop (FLOOR_DIV_EXPR,
- DECL_FIELD_BITPOS (field), size_int (BITS_PER_UNIT));
- }
- else
- offset = BINFO_OFFSET (binfo);
-
- if (TREE_VIA_PUBLIC (binfo))
- access = acc_pub;
- else if (TREE_VIA_PROTECTED (binfo))
- access = acc_pro;
- else
- access = acc_pri;
- if (TREE_VIA_VIRTUAL (binfo))
- isvir = build_int_2 (1, 0);
- else
- isvir = build_int_2 (0, 0);
-
- base_list = tree_cons (NULL_TREE, base, base_list);
- isvir_list = tree_cons (NULL_TREE, isvir, isvir_list);
- acc_list = tree_cons (NULL_TREE, access, acc_list);
- off_list = tree_cons (NULL_TREE, offset, off_list);
- base_cnt++;
- }
-#if 0
- i = n_base;
- while (vb)
- {
- tree b;
- access = acc_pub;
- while (--i >= 0)
- {
- b = TREE_VEC_ELT (binfos, i);
- if (BINFO_TYPE (vb) == BINFO_TYPE (b) && TREE_VIA_VIRTUAL (b))
- {
- if (TREE_VIA_PUBLIC (b))
- access = acc_pub;
- else if (TREE_VIA_PROTECTED (b))
- access = acc_pro;
- else
- access = acc_pri;
- break;
- }
- }
- base = build_t_desc (BINFO_TYPE (vb), 1);
- offset = BINFO_OFFSET (vb);
- isvir = build_int_2 (1, 0);
-
- base_list = tree_cons (NULL_TREE, base, base_list);
- isvir_list = tree_cons (NULL_TREE, isvir, isvir_list);
- acc_list = tree_cons (NULL_TREE, access, acc_list);
- off_list = tree_cons (NULL_TREE, offset, off_list);
-
- base_cnt++;
- vb = TREE_CHAIN (vb);
- }
-#endif
- base_list = finish_table (NULL_TREE, build_pointer_type (__t_desc_type_node),
- base_list, 0);
- off_list = finish_table (NULL_TREE, integer_type_node,
- off_list, 0);
- isvir_list = finish_table (NULL_TREE, integer_type_node,
- isvir_list, 0);
- acc_list = finish_table (NULL_TREE, __access_mode_type_node,
- acc_list, 0);
-
-
- name_string = combine_strings (build_string (IDENTIFIER_LENGTH (tname)+1, IDENTIFIER_POINTER (tname)));
-
- elems = tree_cons (NULL_TREE, name_string,
- tree_cons (NULL_TREE, default_conversion (base_list),
- tree_cons (NULL_TREE, default_conversion (off_list),
- tree_cons (NULL_TREE, default_conversion (isvir_list),
- tree_cons (NULL_TREE, default_conversion (acc_list),
- tree_cons (NULL_TREE, build_int_2 (base_cnt, 0), NULL_TREE))))));
-
- return build_generic_desc (tdecl, __class_desc_type_node, elems);
-}
-
-/* Build an initializer for a __pointer_type_info node. */
-static tree
-build_ptr_desc (tdecl, type)
- tree tdecl;
- tree type;
-{
- tree t, elems;
-
- t = TREE_TYPE (type);
- t = build_t_desc (t, 1);
- t = build_indirect_ref (t, NULL);
- elems = tree_cons (NULL_TREE, t, NULL_TREE);
- return build_generic_desc (tdecl, __ptr_desc_type_node, elems);
-}
-
-/* Build an initializer for a __attr_type_info node. */
-static tree
-build_attr_desc (tdecl, type)
- tree tdecl;
- tree type;
-{
- tree elems, t, attrval;
-
- if (TYPE_READONLY (type))
- {
- if (TYPE_VOLATILE (type))
- attrval = lookup_field (__attr_desc_type_node,
- get_identifier("_RTTI_ATTR_CONSTVOL"), 0, 0);
- else
- attrval = lookup_field (__attr_desc_type_node,
- get_identifier("_RTTI_ATTR_CONST"), 0, 0);
- }
- else
- {
- if (TYPE_VOLATILE (type))
- attrval = lookup_field (__attr_desc_type_node,
- get_identifier("_RTTI_ATTR_VOLATILE"), 0, 0);
- }
- t = build_t_desc (TYPE_MAIN_VARIANT (type), 1);
- t = build_indirect_ref (t , NULL);
- elems = tree_cons (NULL_TREE, attrval, tree_cons (NULL_TREE, t, NULL_TREE));
- return build_generic_desc (tdecl, __attr_desc_type_node, elems);
-}
-
-/* Build an initializer for a __func_type_info node. */
-static tree
-build_func_desc (tdecl)
- tree tdecl;
-{
- tree elems, name_string;
- tree tname = DECL_NAME (tdecl);
-
- name_string = combine_strings (build_string
- (IDENTIFIER_LENGTH (tname)+1, IDENTIFIER_POINTER (tname)));
- elems = name_string;
- return build_generic_desc (tdecl, __func_desc_type_node, elems);
-}
-
-/* Build an initializer for a __ptmf_type_info node. */
-static tree
-build_ptmf_desc (tdecl, type)
- tree tdecl;
- tree type;
-{
- tree elems, name_string;
- tree tname = DECL_NAME (tdecl);
-
- name_string = combine_strings (build_string
- (IDENTIFIER_LENGTH (tname)+1, IDENTIFIER_POINTER (tname)));
- elems = name_string;
- return build_generic_desc (tdecl, __ptmf_desc_type_node, elems);
-}
-
-/* Build an initializer for a __ptmd_type_info node. */
-static tree
-build_ptmd_desc (tdecl, type)
- tree tdecl;
- tree type;
-{
- tree tc, t, elems;
- tc = build_t_desc (TYPE_OFFSET_BASETYPE (type), 1);
- tc = build_indirect_ref (tc , NULL);
- t = build_t_desc (TREE_TYPE (type), 1);
- t = build_indirect_ref (t , NULL);
- elems = tree_cons (NULL_TREE, tc,
- tree_cons (NULL_TREE, t, NULL_TREE));
- return build_generic_desc (tdecl, __ptmd_desc_type_node, elems);
-}
-
-struct uninst_st {
- tree type;
- struct uninst_st *next;
-};
-typedef struct uninst_st uninst_node;
-static uninst_node * uninst_desc = (uninst_node *)NULL;
-
-static void
-add_uninstantiated_desc (type)
- tree type;
-{
- uninst_node *t;
-
- t = (uninst_node *) xmalloc (sizeof (struct uninst_st));
- t->type = type;
- t->next = uninst_desc;
- uninst_desc = t;
-}
-
-/* We may choose to link the emitting of certain high use TDs for certain
- objects, we do that here. Return the type to link against if such a
- link exists, otherwise just return TYPE. */
-
-tree
-get_def_to_follow (type)
- tree type;
-{
-#if 0
- /* For now we don't lay out T&, T* TDs with the main TD for the object. */
- /* Let T* and T& be written only when T is written (if T is an aggr).
- We do this for const, but not for volatile, since volatile
- is rare and const is not. */
- if (!TYPE_VOLATILE (taggr)
- && (TREE_CODE (taggr) == POINTER_TYPE
- || TREE_CODE (taggr) == REFERENCE_TYPE)
- && IS_AGGR_TYPE (TREE_TYPE (taggr)))
- taggr = TREE_TYPE (taggr);
-#endif
- return type;
-}
-
-/* build a general type_info node. */
-tree
-build_t_desc (type, definition)
- tree type;
- int definition;
-{
- tree tdecl;
- tree tname, name_string;
- tree elems;
- tree t, tt, taggr;
-
- if (__ptmd_desc_type_node == NULL_TREE)
- {
- init_type_desc();
- if (__ptmd_desc_type_node)
- {
- for ( ; uninst_desc; uninst_desc = uninst_desc->next )
- build_t_desc (uninst_desc->type, 1);
- }
- }
- if (__t_desc_type_node == NULL_TREE)
- {
- static int warned = 0;
- if (! warned)
- {
- cp_error ("failed to build type descriptor node of '%T', maybe typeinfo.h not included", type);
- }
- warned = 1;
- return error_mark_node;
- }
- if (__ptmd_desc_type_node == NULL_TREE)
- {
- add_uninstantiated_desc (type);
- definition = 0;
- }
-
- push_obstacks (&permanent_obstack, &permanent_obstack);
- tname = build_t_desc_overload (type);
-
- if (!IDENTIFIER_AS_DESC (tname))
- {
- tdecl = build_decl (VAR_DECL, tname, __t_desc_type_node);
- DECL_EXTERNAL (tdecl) = 1;
- TREE_PUBLIC (tdecl) = 1;
- tdecl = pushdecl_top_level (tdecl);
- SET_IDENTIFIER_AS_DESC (tname, build_unary_op (ADDR_EXPR, tdecl, 0));
- if (!definition)
- cp_finish_decl (tdecl, NULL_TREE, NULL_TREE, 0, 0);
- }
- else
- tdecl = TREE_OPERAND (IDENTIFIER_AS_DESC (tname), 0);
-
- /* If it's not a definition, don't do anything more. */
- if (!definition)
- return IDENTIFIER_AS_DESC (tname);
-
- /* If it has already been written, don't to anything more. */
- /* Should this be on tdecl? */
- if (TREE_ASM_WRITTEN (IDENTIFIER_AS_DESC (tname)))
- return IDENTIFIER_AS_DESC (tname);
-
- /* If we previously defined it, return the defined result. */
- if (DECL_INITIAL (tdecl))
- return IDENTIFIER_AS_DESC (tname);
-
- taggr = get_def_to_follow (type);
-
- /* If we know that we don't need to write out this type's
- vtable, then don't write out it's type_info. Somebody
- else will take care of that. */
- if (IS_AGGR_TYPE (taggr) && CLASSTYPE_VFIELD (taggr))
- {
- /* Let's play follow the vtable. */
- TREE_PUBLIC (tdecl) = CLASSTYPE_INTERFACE_KNOWN (taggr);
- DECL_EXTERNAL (tdecl) = CLASSTYPE_INTERFACE_ONLY (taggr);
- }
- else
- {
- DECL_EXTERNAL (tdecl) = 0;
- TREE_PUBLIC (tdecl) = (definition > 1);
- }
-
- if (DECL_EXTERNAL (tdecl))
- return IDENTIFIER_AS_DESC (tname);
-
- /* Show that we are defining the t_desc for this type. */
- DECL_INITIAL (tdecl) = error_mark_node;
- t = DECL_CONTEXT (tdecl);
- if ( t && TREE_CODE_CLASS (TREE_CODE (t)) == 't')
- pushclass (t, 2);
-
- if (TYPE_VOLATILE (type) || TYPE_READONLY (type))
- t = build_attr_desc (tdecl, type);
- else if (TREE_CODE (type) == ARRAY_TYPE)
- t = build_ptr_desc (tdecl, type);
- else if (TREE_CODE (type) == POINTER_TYPE)
- {
- if (TREE_CODE (TREE_TYPE (type)) == OFFSET_TYPE)
- {
- type = TREE_TYPE (type);
- t = build_ptmd_desc (tdecl, type);
- }
- else
- {
- t = build_ptr_desc (tdecl, type);
- }
- }
- else if (TYPE_BUILT_IN (type))
- t = build_bltn_desc (tdecl, type);
- else if (IS_AGGR_TYPE (type))
- {
- if (TYPE_PTRMEMFUNC_P (type))
- {
- t = build_ptmf_desc (tdecl, type);
- }
- else
- {
- t = build_class_desc (tdecl, type);
- }
- }
- else if (TREE_CODE (type) == FUNCTION_TYPE)
- t = build_func_desc (tdecl);
- else
- t = build_user_desc (tdecl);
-
- pop_obstacks ();
- return t;
-}
-
-#if 0
-/* This is the old dossier type descriptor generation code, it's much
- more extended than rtti. It's reserved for later use. */
-/* Build an initializer for a __t_desc node. So that we can take advantage
- of recursion, we accept NULL for TYPE.
- DEFINITION is greater than zero iff we must define the type descriptor
- (as opposed to merely referencing it). 1 means treat according to
- #pragma interface/#pragma implementation rules. 2 means define as
- global and public, no matter what. */
-tree
-build_t_desc (type, definition)
- tree type;
- int definition;
-{
- tree tdecl;
- tree tname, name_string;
- tree elems, fields;
- tree parents, vbases, offsets, ivars, methods, target_type;
- int method_count = 0, field_count = 0;
-
- if (type == NULL_TREE)
- return NULL_TREE;
-
- tname = build_t_desc_overload (type);
- if (IDENTIFIER_AS_DESC (tname)
- && (!definition || TREE_ASM_WRITTEN (IDENTIFIER_AS_DESC (tname))))
- return IDENTIFIER_AS_DESC (tname);
-
- tdecl = lookup_name (tname, 0);
- if (tdecl == NULL_TREE)
- {
- tdecl = build_decl (VAR_DECL, tname, __t_desc_type_node);
- DECL_EXTERNAL (tdecl) = 1;
- TREE_PUBLIC (tdecl) = 1;
- tdecl = pushdecl_top_level (tdecl);
- }
- /* If we previously defined it, return the defined result. */
- else if (definition && DECL_INITIAL (tdecl))
- return IDENTIFIER_AS_DESC (tname);
-
- if (definition)
- {
- tree taggr = type;
- /* Let T* and T& be written only when T is written (if T is an aggr).
- We do this for const, but not for volatile, since volatile
- is rare and const is not. */
- if (!TYPE_VOLATILE (taggr)
- && (TREE_CODE (taggr) == POINTER_TYPE
- || TREE_CODE (taggr) == REFERENCE_TYPE)
- && IS_AGGR_TYPE (TREE_TYPE (taggr)))
- taggr = TREE_TYPE (taggr);
-
- /* If we know that we don't need to write out this type's
- vtable, then don't write out it's dossier. Somebody
- else will take care of that. */
- if (IS_AGGR_TYPE (taggr) && CLASSTYPE_VFIELD (taggr))
- {
- if (CLASSTYPE_VTABLE_NEEDS_WRITING (taggr))
- {
- TREE_PUBLIC (tdecl) = ! CLASSTYPE_INTERFACE_ONLY (taggr)
- && CLASSTYPE_INTERFACE_KNOWN (taggr);
- DECL_EXTERNAL (tdecl) = 0;
- }
- else
- {
- if (write_virtuals != 0)
- TREE_PUBLIC (tdecl) = 1;
- }
- }
- else
- {
- DECL_EXTERNAL (tdecl) = 0;
- TREE_PUBLIC (tdecl) = (definition > 1);
- }
- }
- SET_IDENTIFIER_AS_DESC (tname, build_unary_op (ADDR_EXPR, tdecl, 0));
-
- if (!definition || DECL_EXTERNAL (tdecl))
- {
- /* That's it! */
- cp_finish_decl (tdecl, NULL_TREE, NULL_TREE, 0, 0);
- return IDENTIFIER_AS_DESC (tname);
- }
-
- /* Show that we are defining the t_desc for this type. */
- DECL_INITIAL (tdecl) = error_mark_node;
-
- parents = build_tree_list (NULL_TREE, integer_zero_node);
- vbases = build_tree_list (NULL_TREE, integer_zero_node);
- offsets = build_tree_list (NULL_TREE, integer_zero_node);
- methods = NULL_TREE;
- ivars = NULL_TREE;
-
- if (TYPE_LANG_SPECIFIC (type))
- {
- int i = CLASSTYPE_N_BASECLASSES (type);
- tree method_vec = CLASSTYPE_METHOD_VEC (type);
- tree *meth, *end;
- tree binfos = TYPE_BINFO_BASETYPES (type);
- tree vb = CLASSTYPE_VBASECLASSES (type);
-
- while (--i >= 0)
- parents = tree_cons (NULL_TREE, build_t_desc (BINFO_TYPE (TREE_VEC_ELT (binfos, i)), 0), parents);
-
- while (vb)
- {
- vbases = tree_cons (NULL_TREE, build_t_desc (BINFO_TYPE (vb), 0), vbases);
- offsets = tree_cons (NULL_TREE, BINFO_OFFSET (vb), offsets);
- vb = TREE_CHAIN (vb);
- }
-
- if (method_vec)
- for (meth = TREE_VEC_END (method_vec),
- end = &TREE_VEC_ELT (method_vec, 0); meth-- != end; )
- if (*meth)
- {
- methods = tree_cons (NULL_TREE, build_m_desc (*meth), methods);
- method_count++;
- }
- }
-
- if (IS_AGGR_TYPE (type))
- {
- for (fields = TYPE_FIELDS (type); fields; fields = TREE_CHAIN (fields))
- if (TREE_CODE (fields) == FIELD_DECL
- || TREE_CODE (fields) == VAR_DECL)
- {
- ivars = tree_cons (NULL_TREE, build_i_desc (fields), ivars);
- field_count++;
- }
- ivars = nreverse (ivars);
- }
-
- parents = finish_table (NULL_TREE, build_pointer_type (__t_desc_type_node), parents, 0);
- vbases = finish_table (NULL_TREE, build_pointer_type (__t_desc_type_node), vbases, 0);
- offsets = finish_table (NULL_TREE, integer_type_node, offsets, 0);
- if (methods == NULL_TREE)
- methods = null_pointer_node;
- else
- methods = build_unary_op (ADDR_EXPR,
- finish_table (NULL_TREE, __m_desc_type_node, methods, 0),
- 0);
- if (ivars == NULL_TREE)
- ivars = null_pointer_node;
- else
- ivars = build_unary_op (ADDR_EXPR,
- finish_table (NULL_TREE, __i_desc_type_node, ivars, 0),
- 0);
- if (TREE_TYPE (type))
- target_type = build_t_desc (TREE_TYPE (type), definition);
- else
- target_type = integer_zero_node;
-
- name_string = combine_strings (build_string (IDENTIFIER_LENGTH (tname)+1, IDENTIFIER_POINTER (tname)));
-
- elems = tree_cons (NULL_TREE, build_unary_op (ADDR_EXPR, name_string, 0),
- tree_cons (NULL_TREE,
- TYPE_SIZE(type)? size_in_bytes(type) : integer_zero_node,
- /* really should use bitfield initialization here. */
- tree_cons (NULL_TREE, integer_zero_node,
- tree_cons (NULL_TREE, target_type,
- tree_cons (NULL_TREE, build_int_2 (field_count, 2),
- tree_cons (NULL_TREE, build_int_2 (method_count, 2),
- tree_cons (NULL_TREE, ivars,
- tree_cons (NULL_TREE, methods,
- tree_cons (NULL_TREE, build_unary_op (ADDR_EXPR, parents, 0),
- tree_cons (NULL_TREE, build_unary_op (ADDR_EXPR, vbases, 0),
- build_tree_list (NULL_TREE, build_unary_op (ADDR_EXPR, offsets, 0))))))))))));
- return build_generic_desc (tdecl, elems);
-}
-
-/* Build an initializer for a __i_desc node. */
-tree
-build_i_desc (decl)
- tree decl;
-{
- tree elems, name_string;
- tree taggr;
-
- name_string = DECL_NAME (decl);
- name_string = combine_strings (build_string (IDENTIFIER_LENGTH (name_string)+1, IDENTIFIER_POINTER (name_string)));
-
- /* Now decide whether this ivar should cause it's type to get
- def'd or ref'd in this file. If the type we are looking at
- has a proxy definition, we look at the proxy (i.e., a
- `foo *' is equivalent to a `foo'). */
- taggr = TREE_TYPE (decl);
-
- if ((TREE_CODE (taggr) == POINTER_TYPE
- || TREE_CODE (taggr) == REFERENCE_TYPE)
- && TYPE_VOLATILE (taggr) == 0)
- taggr = TREE_TYPE (taggr);
-
- elems = tree_cons (NULL_TREE, build_unary_op (ADDR_EXPR, name_string, 0),
- tree_cons (NULL_TREE, DECL_FIELD_BITPOS (decl),
- build_tree_list (NULL_TREE, build_t_desc (TREE_TYPE (decl),
- ! IS_AGGR_TYPE (taggr)))));
- taggr = build (CONSTRUCTOR, __i_desc_type_node, NULL_TREE, elems);
- TREE_CONSTANT (taggr) = 1;
- TREE_STATIC (taggr) = 1;
- TREE_READONLY (taggr) = 1;
- return taggr;
-}
-
-/* Build an initializer for a __m_desc node. */
-tree
-build_m_desc (decl)
- tree decl;
-{
- tree taggr, elems, name_string;
- tree parm_count, req_count, vindex, vcontext;
- tree parms;
- int p_count, r_count;
- tree parm_types = NULL_TREE;
-
- for (parms = TYPE_ARG_TYPES (TREE_TYPE (decl)), p_count = 0, r_count = 0;
- parms != NULL_TREE; parms = TREE_CHAIN (parms), p_count++)
- {
- taggr = TREE_VALUE (parms);
- if ((TREE_CODE (taggr) == POINTER_TYPE
- || TREE_CODE (taggr) == REFERENCE_TYPE)
- && TYPE_VOLATILE (taggr) == 0)
- taggr = TREE_TYPE (taggr);
-
- parm_types = tree_cons (NULL_TREE, build_t_desc (TREE_VALUE (parms),
- ! IS_AGGR_TYPE (taggr)),
- parm_types);
- if (TREE_PURPOSE (parms) == NULL_TREE)
- r_count++;
- }
-
- parm_types = finish_table (NULL_TREE, build_pointer_type (__t_desc_type_node),
- nreverse (parm_types), 0);
- parm_count = build_int_2 (p_count, 0);
- req_count = build_int_2 (r_count, 0);
-
- if (DECL_VINDEX (decl))
- vindex = DECL_VINDEX (decl);
- else
- vindex = integer_zero_node;
- if (DECL_CONTEXT (decl)
- && TREE_CODE_CLASS (TREE_CODE (DECL_CONTEXT (decl))) == 't')
- vcontext = build_t_desc (DECL_CONTEXT (decl), 0);
- else
- vcontext = integer_zero_node;
- name_string = DECL_NAME (decl);
- if (name_string == NULL)
- name_string = DECL_ASSEMBLER_NAME (decl);
- name_string = combine_strings (build_string (IDENTIFIER_LENGTH (name_string)+1, IDENTIFIER_POINTER (name_string)));
-
- /* Now decide whether the return type of this mvar
- should cause it's type to get def'd or ref'd in this file.
- If the type we are looking at has a proxy definition,
- we look at the proxy (i.e., a `foo *' is equivalent to a `foo'). */
- taggr = TREE_TYPE (TREE_TYPE (decl));
-
- if ((TREE_CODE (taggr) == POINTER_TYPE
- || TREE_CODE (taggr) == REFERENCE_TYPE)
- && TYPE_VOLATILE (taggr) == 0)
- taggr = TREE_TYPE (taggr);
-
- elems = tree_cons (NULL_TREE, build_unary_op (ADDR_EXPR, name_string, 0),
- tree_cons (NULL_TREE, vindex,
- tree_cons (NULL_TREE, vcontext,
- tree_cons (NULL_TREE, build_t_desc (TREE_TYPE (TREE_TYPE (decl)),
- ! IS_AGGR_TYPE (taggr)),
- tree_cons (NULL_TREE, build_c_cast (build_pointer_type (default_function_type), build_unary_op (ADDR_EXPR, decl, 0), 0),
- tree_cons (NULL_TREE, parm_count,
- tree_cons (NULL_TREE, req_count,
- build_tree_list (NULL_TREE, build_unary_op (ADDR_EXPR, parm_types, 0)))))))));
-
- taggr = build (CONSTRUCTOR, __m_desc_type_node, NULL_TREE, elems);
- TREE_CONSTANT (taggr) = 1;
- TREE_STATIC (taggr) = 1;
- TREE_READONLY (taggr) = 1;
- return taggr;
-}
-#endif /* dossier */
-
-
-/* Conditionally emit code to set up an unwind-protect for the
- garbage collector. If this function doesn't do anything that involves
- the garbage collector, then do nothing. Otherwise, call __gc_push
- at the beginning and __gc_pop at the end.
-
- NOTE! The __gc_pop function must operate transparently, since
- it comes where the logical return label lies. This means that
- at runtime *it* must preserve any return value registers. */
-
-void
-expand_gc_prologue_and_epilogue ()
-{
- extern tree maybe_gc_cleanup;
- struct rtx_def *last_parm_insn, *mark;
- extern struct rtx_def *get_last_insn ();
- extern struct rtx_def *get_first_nonparm_insn ();
- extern struct rtx_def *previous_insn ();
- tree action;
-
- /* If we didn't need the obstack, don't cons any space. */
- if (current_function_obstack_index == 0
- || current_function_obstack_usage == 0)
- return;
-
- mark = get_last_insn ();
- last_parm_insn = get_first_nonparm_insn ();
- if (last_parm_insn == 0) last_parm_insn = mark;
- else last_parm_insn = previous_insn (last_parm_insn);
-
- action = build_function_call (gc_push_fndecl,
- build_tree_list (NULL_TREE, size_int (++current_function_obstack_index)));
- expand_expr_stmt (action);
-
- reorder_insns (next_insn (mark), get_last_insn (), last_parm_insn);
-
- /* This will be expanded as a cleanup. */
- TREE_VALUE (maybe_gc_cleanup)
- = build_function_call (gc_pop_fndecl, NULL_TREE);
-}
-
-/* Some day we'll use this function as a call-back and clean
- up all the unnecessary gc dribble that we otherwise create. */
-void
-lang_expand_end_bindings (first, last)
- struct rtx_def *first, *last;
-{
-}
-
-void
-init_gc_processing ()
-{
- tree parmtypes = hash_tree_chain (class_star_type_node,
- hash_tree_chain (integer_type_node, NULL_TREE));
- gc_protect_fndecl = define_function ("__gc_protect",
- build_function_type (class_star_type_node, parmtypes),
- NOT_BUILT_IN, 0, 0);
-
- parmtypes = hash_tree_chain (integer_type_node, NULL_TREE);
- gc_unprotect_fndecl = define_function ("__gc_unprotect",
- build_function_type (void_type_node, parmtypes),
- NOT_BUILT_IN, 0, 0);
-
- gc_push_fndecl = define_function ("__gc_push",
- TREE_TYPE (gc_unprotect_fndecl),
- NOT_BUILT_IN, 0, 0);
-
- gc_pop_fndecl = define_function ("__gc_pop",
- build_function_type (void_type_node,
- void_list_node),
- NOT_BUILT_IN, 0, 0);
- gc_nonobject = build_int_2 (0x80000000, 0);
- gc_visible = build_int_2 (0x40000000, 0);
- gc_white = integer_zero_node;
- gc_offwhite = build_int_2 (0x10000000, 0);
- gc_grey = build_int_2 (0x20000000, 0);
- gc_black = build_int_2 (0x30000000, 0);
-}