* configure.in: Fix sed invocation for GFORTRAN_FOR_TARGET.
[official-gcc.git] / gcc / collect2.c
blobb9c7cae8a5e46db565a39a7c9599311d3a02d6f7
1 /* Collect static initialization info into data structures that can be
2 traversed by C++ initialization and finalization routines.
3 Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998,
4 1999, 2000, 2001, 2002, 2003, 2004 Free Software Foundation, Inc.
5 Contributed by Chris Smith (csmith@convex.com).
6 Heavily modified by Michael Meissner (meissner@cygnus.com),
7 Per Bothner (bothner@cygnus.com), and John Gilmore (gnu@cygnus.com).
9 This file is part of GCC.
11 GCC is free software; you can redistribute it and/or modify it under
12 the terms of the GNU General Public License as published by the Free
13 Software Foundation; either version 2, or (at your option) any later
14 version.
16 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
17 WARRANTY; without even the implied warranty of MERCHANTABILITY or
18 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
19 for more details.
21 You should have received a copy of the GNU General Public License
22 along with GCC; see the file COPYING. If not, write to the Free
23 Software Foundation, 59 Temple Place - Suite 330, Boston, MA
24 02111-1307, USA. */
27 /* Build tables of static constructors and destructors and run ld. */
29 #include "config.h"
30 #include "system.h"
31 #include "coretypes.h"
32 #include "tm.h"
33 #include <signal.h>
34 #if ! defined( SIGCHLD ) && defined( SIGCLD )
35 # define SIGCHLD SIGCLD
36 #endif
38 #ifdef vfork /* Autoconf may define this to fork for us. */
39 # define VFORK_STRING "fork"
40 #else
41 # define VFORK_STRING "vfork"
42 #endif
43 #ifdef HAVE_VFORK_H
44 #include <vfork.h>
45 #endif
46 #ifdef VMS
47 #define vfork() (decc$$alloc_vfork_blocks() >= 0 ? \
48 lib$get_current_invo_context(decc$$get_vfork_jmpbuf()) : -1)
49 #endif /* VMS */
51 #ifndef LIBRARY_PATH_ENV
52 #define LIBRARY_PATH_ENV "LIBRARY_PATH"
53 #endif
55 #define COLLECT
57 #include "collect2.h"
58 #include "demangle.h"
59 #include "obstack.h"
60 #include "intl.h"
61 #include "version.h"
63 /* On certain systems, we have code that works by scanning the object file
64 directly. But this code uses system-specific header files and library
65 functions, so turn it off in a cross-compiler. Likewise, the names of
66 the utilities are not correct for a cross-compiler; we have to hope that
67 cross-versions are in the proper directories. */
69 #ifdef CROSS_COMPILE
70 #undef OBJECT_FORMAT_COFF
71 #undef MD_EXEC_PREFIX
72 #undef REAL_LD_FILE_NAME
73 #undef REAL_NM_FILE_NAME
74 #undef REAL_STRIP_FILE_NAME
75 #endif
77 /* If we cannot use a special method, use the ordinary one:
78 run nm to find what symbols are present.
79 In a cross-compiler, this means you need a cross nm,
80 but that is not quite as unpleasant as special headers. */
82 #if !defined (OBJECT_FORMAT_COFF)
83 #define OBJECT_FORMAT_NONE
84 #endif
86 #ifdef OBJECT_FORMAT_COFF
88 #include <a.out.h>
89 #include <ar.h>
91 #ifdef UMAX
92 #include <sgs.h>
93 #endif
95 /* Many versions of ldfcn.h define these. */
96 #ifdef FREAD
97 #undef FREAD
98 #undef FWRITE
99 #endif
101 #include <ldfcn.h>
103 /* Some systems have an ISCOFF macro, but others do not. In some cases
104 the macro may be wrong. MY_ISCOFF is defined in tm.h files for machines
105 that either do not have an ISCOFF macro in /usr/include or for those
106 where it is wrong. */
108 #ifndef MY_ISCOFF
109 #define MY_ISCOFF(X) ISCOFF (X)
110 #endif
112 #endif /* OBJECT_FORMAT_COFF */
114 #ifdef OBJECT_FORMAT_NONE
116 /* Default flags to pass to nm. */
117 #ifndef NM_FLAGS
118 #define NM_FLAGS "-n"
119 #endif
121 #endif /* OBJECT_FORMAT_NONE */
123 /* Some systems use __main in a way incompatible with its use in gcc, in these
124 cases use the macros NAME__MAIN to give a quoted symbol and SYMBOL__MAIN to
125 give the same symbol without quotes for an alternative entry point. */
126 #ifndef NAME__MAIN
127 #define NAME__MAIN "__main"
128 #endif
130 /* This must match tree.h. */
131 #define DEFAULT_INIT_PRIORITY 65535
133 #ifndef COLLECT_SHARED_INIT_FUNC
134 #define COLLECT_SHARED_INIT_FUNC(STREAM, FUNC) \
135 fprintf ((STREAM), "void _GLOBAL__DI() {\n\t%s();\n}\n", (FUNC))
136 #endif
137 #ifndef COLLECT_SHARED_FINI_FUNC
138 #define COLLECT_SHARED_FINI_FUNC(STREAM, FUNC) \
139 fprintf ((STREAM), "void _GLOBAL__DD() {\n\t%s();\n}\n", (FUNC))
140 #endif
142 #ifdef LDD_SUFFIX
143 #define SCAN_LIBRARIES
144 #endif
146 #ifdef USE_COLLECT2
147 int do_collecting = 1;
148 #else
149 int do_collecting = 0;
150 #endif
152 #ifndef COLLECT_PARSE_FLAG
153 #define COLLECT_PARSE_FLAG(FLAG)
154 #endif
156 /* Nonzero if we should suppress the automatic demangling of identifiers
157 in linker error messages. Set from COLLECT_NO_DEMANGLE. */
158 int no_demangle;
160 /* Linked lists of constructor and destructor names. */
162 struct id
164 struct id *next;
165 int sequence;
166 char name[1];
169 struct head
171 struct id *first;
172 struct id *last;
173 int number;
176 /* Enumeration giving which pass this is for scanning the program file. */
178 enum pass {
179 PASS_FIRST, /* without constructors */
180 PASS_OBJ, /* individual objects */
181 PASS_LIB, /* looking for shared libraries */
182 PASS_SECOND /* with constructors linked in */
185 int vflag; /* true if -v */
186 static int rflag; /* true if -r */
187 static int strip_flag; /* true if -s */
188 #ifdef COLLECT_EXPORT_LIST
189 static int export_flag; /* true if -bE */
190 static int aix64_flag; /* true if -b64 */
191 #endif
193 int debug; /* true if -debug */
195 static int shared_obj; /* true if -shared */
197 static const char *c_file; /* <xxx>.c for constructor/destructor list. */
198 static const char *o_file; /* <xxx>.o for constructor/destructor list. */
199 #ifdef COLLECT_EXPORT_LIST
200 static const char *export_file; /* <xxx>.x for AIX export list. */
201 #endif
202 const char *ldout; /* File for ld errors. */
203 static const char *output_file; /* Output file for ld. */
204 static const char *nm_file_name; /* pathname of nm */
205 #ifdef LDD_SUFFIX
206 static const char *ldd_file_name; /* pathname of ldd (or equivalent) */
207 #endif
208 static const char *strip_file_name; /* pathname of strip */
209 const char *c_file_name; /* pathname of gcc */
210 static char *initname, *fininame; /* names of init and fini funcs */
212 static struct head constructors; /* list of constructors found */
213 static struct head destructors; /* list of destructors found */
214 #ifdef COLLECT_EXPORT_LIST
215 static struct head exports; /* list of exported symbols */
216 #endif
217 static struct head frame_tables; /* list of frame unwind info tables */
219 struct obstack temporary_obstack;
220 char * temporary_firstobj;
222 /* Holds the return value of pexecute and fork. */
223 int pid;
225 /* Structure to hold all the directories in which to search for files to
226 execute. */
228 struct prefix_list
230 const char *prefix; /* String to prepend to the path. */
231 struct prefix_list *next; /* Next in linked list. */
234 struct path_prefix
236 struct prefix_list *plist; /* List of prefixes to try */
237 int max_len; /* Max length of a prefix in PLIST */
238 const char *name; /* Name of this list (used in config stuff) */
241 #ifdef COLLECT_EXPORT_LIST
242 /* Lists to keep libraries to be scanned for global constructors/destructors. */
243 static struct head libs; /* list of libraries */
244 static struct path_prefix cmdline_lib_dirs; /* directories specified with -L */
245 static struct path_prefix libpath_lib_dirs; /* directories in LIBPATH */
246 static struct path_prefix *libpaths[3] = {&cmdline_lib_dirs,
247 &libpath_lib_dirs, NULL};
248 static const char *const libexts[3] = {"a", "so", NULL}; /* possible library extensions */
249 #endif
251 static void handler (int);
252 static int is_ctor_dtor (const char *);
253 static char *find_a_file (struct path_prefix *, const char *);
254 static void add_prefix (struct path_prefix *, const char *);
255 static void prefix_from_env (const char *, struct path_prefix *);
256 static void prefix_from_string (const char *, struct path_prefix *);
257 static void do_wait (const char *);
258 static void fork_execute (const char *, char **);
259 static void maybe_unlink (const char *);
260 static void add_to_list (struct head *, const char *);
261 static int extract_init_priority (const char *);
262 static void sort_ids (struct head *);
263 static void write_list (FILE *, const char *, struct id *);
264 #ifdef COLLECT_EXPORT_LIST
265 static void dump_list (FILE *, const char *, struct id *);
266 #endif
267 #if 0
268 static void dump_prefix_list (FILE *, const char *, struct prefix_list *);
269 #endif
270 static void write_list_with_asm (FILE *, const char *, struct id *);
271 static void write_c_file (FILE *, const char *);
272 static void write_c_file_stat (FILE *, const char *);
273 #ifndef LD_INIT_SWITCH
274 static void write_c_file_glob (FILE *, const char *);
275 #endif
276 static void scan_prog_file (const char *, enum pass);
277 #ifdef SCAN_LIBRARIES
278 static void scan_libraries (const char *);
279 #endif
280 #if LINK_ELIMINATE_DUPLICATE_LDIRECTORIES
281 static int is_in_args (const char *, const char **, const char **);
282 #endif
283 #ifdef COLLECT_EXPORT_LIST
284 #if 0
285 static int is_in_list (const char *, struct id *);
286 #endif
287 static void write_aix_file (FILE *, struct id *);
288 static char *resolve_lib_name (const char *);
289 #endif
290 static char *extract_string (const char **);
292 #ifndef HAVE_DUP2
293 static int
294 dup2 (int oldfd, int newfd)
296 int fdtmp[256];
297 int fdx = 0;
298 int fd;
300 if (oldfd == newfd)
301 return oldfd;
302 close (newfd);
303 while ((fd = dup (oldfd)) != newfd && fd >= 0) /* good enough for low fd's */
304 fdtmp[fdx++] = fd;
305 while (fdx > 0)
306 close (fdtmp[--fdx]);
308 return fd;
310 #endif /* ! HAVE_DUP2 */
312 /* Delete tempfiles and exit function. */
314 void
315 collect_exit (int status)
317 if (c_file != 0 && c_file[0])
318 maybe_unlink (c_file);
320 if (o_file != 0 && o_file[0])
321 maybe_unlink (o_file);
323 #ifdef COLLECT_EXPORT_LIST
324 if (export_file != 0 && export_file[0])
325 maybe_unlink (export_file);
326 #endif
328 if (ldout != 0 && ldout[0])
330 dump_file (ldout);
331 maybe_unlink (ldout);
334 if (status != 0 && output_file != 0 && output_file[0])
335 maybe_unlink (output_file);
337 exit (status);
341 /* Notify user of a non-error. */
342 void
343 notice (const char *msgid, ...)
345 va_list ap;
347 va_start (ap, msgid);
348 vfprintf (stderr, _(msgid), ap);
349 va_end (ap);
352 /* Die when sys call fails. */
354 void
355 fatal_perror (const char * msgid, ...)
357 int e = errno;
358 va_list ap;
360 va_start (ap, msgid);
361 fprintf (stderr, "collect2: ");
362 vfprintf (stderr, _(msgid), ap);
363 fprintf (stderr, ": %s\n", xstrerror (e));
364 va_end (ap);
366 collect_exit (FATAL_EXIT_CODE);
369 /* Just die. */
371 void
372 fatal (const char * msgid, ...)
374 va_list ap;
376 va_start (ap, msgid);
377 fprintf (stderr, "collect2: ");
378 vfprintf (stderr, _(msgid), ap);
379 fprintf (stderr, "\n");
380 va_end (ap);
382 collect_exit (FATAL_EXIT_CODE);
385 /* Write error message. */
387 void
388 error (const char * msgid, ...)
390 va_list ap;
392 va_start (ap, msgid);
393 fprintf (stderr, "collect2: ");
394 vfprintf (stderr, _(msgid), ap);
395 fprintf (stderr, "\n");
396 va_end(ap);
399 /* In case obstack is linked in, and abort is defined to fancy_abort,
400 provide a default entry. */
402 void
403 fancy_abort (void)
405 fatal ("internal error");
408 static void
409 handler (int signo)
411 if (c_file != 0 && c_file[0])
412 maybe_unlink (c_file);
414 if (o_file != 0 && o_file[0])
415 maybe_unlink (o_file);
417 if (ldout != 0 && ldout[0])
418 maybe_unlink (ldout);
420 #ifdef COLLECT_EXPORT_LIST
421 if (export_file != 0 && export_file[0])
422 maybe_unlink (export_file);
423 #endif
425 signal (signo, SIG_DFL);
426 kill (getpid (), signo);
431 file_exists (const char *name)
433 return access (name, R_OK) == 0;
436 /* Parse a reasonable subset of shell quoting syntax. */
438 static char *
439 extract_string (const char **pp)
441 const char *p = *pp;
442 int backquote = 0;
443 int inside = 0;
445 for (;;)
447 char c = *p;
448 if (c == '\0')
449 break;
450 ++p;
451 if (backquote)
452 obstack_1grow (&temporary_obstack, c);
453 else if (! inside && c == ' ')
454 break;
455 else if (! inside && c == '\\')
456 backquote = 1;
457 else if (c == '\'')
458 inside = !inside;
459 else
460 obstack_1grow (&temporary_obstack, c);
463 obstack_1grow (&temporary_obstack, '\0');
464 *pp = p;
465 return obstack_finish (&temporary_obstack);
468 void
469 dump_file (const char *name)
471 FILE *stream = fopen (name, "r");
473 if (stream == 0)
474 return;
475 while (1)
477 int c;
478 while (c = getc (stream),
479 c != EOF && (ISIDNUM (c) || c == '$' || c == '.'))
480 obstack_1grow (&temporary_obstack, c);
481 if (obstack_object_size (&temporary_obstack) > 0)
483 const char *word, *p;
484 char *result;
485 obstack_1grow (&temporary_obstack, '\0');
486 word = obstack_finish (&temporary_obstack);
488 if (*word == '.')
489 ++word, putc ('.', stderr);
490 p = word;
491 if (!strncmp (p, USER_LABEL_PREFIX, strlen (USER_LABEL_PREFIX)))
492 p += strlen (USER_LABEL_PREFIX);
494 if (no_demangle)
495 result = 0;
496 else
497 result = cplus_demangle (p, DMGL_PARAMS | DMGL_ANSI | DMGL_VERBOSE);
499 if (result)
501 int diff;
502 fputs (result, stderr);
504 diff = strlen (word) - strlen (result);
505 while (diff > 0 && c == ' ')
506 --diff, putc (' ', stderr);
507 while (diff < 0 && c == ' ')
508 ++diff, c = getc (stream);
510 free (result);
512 else
513 fputs (word, stderr);
515 fflush (stderr);
516 obstack_free (&temporary_obstack, temporary_firstobj);
518 if (c == EOF)
519 break;
520 putc (c, stderr);
522 fclose (stream);
525 /* Decide whether the given symbol is: a constructor (1), a destructor
526 (2), a routine in a shared object that calls all the constructors
527 (3) or destructors (4), a DWARF exception-handling table (5), or
528 nothing special (0). */
530 static int
531 is_ctor_dtor (const char *s)
533 struct names { const char *const name; const int len; const int ret;
534 const int two_underscores; };
536 const struct names *p;
537 int ch;
538 const char *orig_s = s;
540 static const struct names special[] = {
541 #ifndef NO_DOLLAR_IN_LABEL
542 { "GLOBAL__I$", sizeof ("GLOBAL__I$")-1, 1, 0 },
543 { "GLOBAL__D$", sizeof ("GLOBAL__D$")-1, 2, 0 },
544 #else
545 #ifndef NO_DOT_IN_LABEL
546 { "GLOBAL__I.", sizeof ("GLOBAL__I.")-1, 1, 0 },
547 { "GLOBAL__D.", sizeof ("GLOBAL__D.")-1, 2, 0 },
548 #endif /* NO_DOT_IN_LABEL */
549 #endif /* NO_DOLLAR_IN_LABEL */
550 { "GLOBAL__I_", sizeof ("GLOBAL__I_")-1, 1, 0 },
551 { "GLOBAL__D_", sizeof ("GLOBAL__D_")-1, 2, 0 },
552 { "GLOBAL__F_", sizeof ("GLOBAL__F_")-1, 5, 0 },
553 { "GLOBAL__FI_", sizeof ("GLOBAL__FI_")-1, 3, 0 },
554 { "GLOBAL__FD_", sizeof ("GLOBAL__FD_")-1, 4, 0 },
555 { NULL, 0, 0, 0 }
558 while ((ch = *s) == '_')
559 ++s;
561 if (s == orig_s)
562 return 0;
564 for (p = &special[0]; p->len > 0; p++)
566 if (ch == p->name[0]
567 && (!p->two_underscores || ((s - orig_s) >= 2))
568 && strncmp(s, p->name, p->len) == 0)
570 return p->ret;
573 return 0;
576 /* We maintain two prefix lists: one from COMPILER_PATH environment variable
577 and one from the PATH variable. */
579 static struct path_prefix cpath, path;
581 #ifdef CROSS_COMPILE
582 /* This is the name of the target machine. We use it to form the name
583 of the files to execute. */
585 static const char *const target_machine = TARGET_MACHINE;
586 #endif
588 /* Search for NAME using prefix list PPREFIX. We only look for executable
589 files.
591 Return 0 if not found, otherwise return its name, allocated with malloc. */
593 static char *
594 find_a_file (struct path_prefix *pprefix, const char *name)
596 char *temp;
597 struct prefix_list *pl;
598 int len = pprefix->max_len + strlen (name) + 1;
600 if (debug)
601 fprintf (stderr, "Looking for '%s'\n", name);
603 #ifdef HOST_EXECUTABLE_SUFFIX
604 len += strlen (HOST_EXECUTABLE_SUFFIX);
605 #endif
607 temp = xmalloc (len);
609 /* Determine the filename to execute (special case for absolute paths). */
611 if (*name == '/'
612 #ifdef HAVE_DOS_BASED_FILE_SYSTEM
613 || (*name && name[1] == ':')
614 #endif
617 if (access (name, X_OK) == 0)
619 strcpy (temp, name);
621 if (debug)
622 fprintf (stderr, " - found: absolute path\n");
624 return temp;
627 #ifdef HOST_EXECUTABLE_SUFFIX
628 /* Some systems have a suffix for executable files.
629 So try appending that. */
630 strcpy (temp, name);
631 strcat (temp, HOST_EXECUTABLE_SUFFIX);
633 if (access (temp, X_OK) == 0)
634 return temp;
635 #endif
637 if (debug)
638 fprintf (stderr, " - failed to locate using absolute path\n");
640 else
641 for (pl = pprefix->plist; pl; pl = pl->next)
643 struct stat st;
645 strcpy (temp, pl->prefix);
646 strcat (temp, name);
648 if (stat (temp, &st) >= 0
649 && ! S_ISDIR (st.st_mode)
650 && access (temp, X_OK) == 0)
651 return temp;
653 #ifdef HOST_EXECUTABLE_SUFFIX
654 /* Some systems have a suffix for executable files.
655 So try appending that. */
656 strcat (temp, HOST_EXECUTABLE_SUFFIX);
658 if (stat (temp, &st) >= 0
659 && ! S_ISDIR (st.st_mode)
660 && access (temp, X_OK) == 0)
661 return temp;
662 #endif
665 if (debug && pprefix->plist == NULL)
666 fprintf (stderr, " - failed: no entries in prefix list\n");
668 free (temp);
669 return 0;
672 /* Add an entry for PREFIX to prefix list PPREFIX. */
674 static void
675 add_prefix (struct path_prefix *pprefix, const char *prefix)
677 struct prefix_list *pl, **prev;
678 int len;
680 if (pprefix->plist)
682 for (pl = pprefix->plist; pl->next; pl = pl->next)
684 prev = &pl->next;
686 else
687 prev = &pprefix->plist;
689 /* Keep track of the longest prefix. */
691 len = strlen (prefix);
692 if (len > pprefix->max_len)
693 pprefix->max_len = len;
695 pl = xmalloc (sizeof (struct prefix_list));
696 pl->prefix = xstrdup (prefix);
698 if (*prev)
699 pl->next = *prev;
700 else
701 pl->next = (struct prefix_list *) 0;
702 *prev = pl;
705 /* Take the value of the environment variable ENV, break it into a path, and
706 add of the entries to PPREFIX. */
708 static void
709 prefix_from_env (const char *env, struct path_prefix *pprefix)
711 const char *p;
712 GET_ENVIRONMENT (p, env);
714 if (p)
715 prefix_from_string (p, pprefix);
718 static void
719 prefix_from_string (const char *p, struct path_prefix *pprefix)
721 const char *startp, *endp;
722 char *nstore = xmalloc (strlen (p) + 3);
724 if (debug)
725 fprintf (stderr, "Convert string '%s' into prefixes, separator = '%c'\n", p, PATH_SEPARATOR);
727 startp = endp = p;
728 while (1)
730 if (*endp == PATH_SEPARATOR || *endp == 0)
732 strncpy (nstore, startp, endp-startp);
733 if (endp == startp)
735 strcpy (nstore, "./");
737 else if (! IS_DIR_SEPARATOR (endp[-1]))
739 nstore[endp-startp] = DIR_SEPARATOR;
740 nstore[endp-startp+1] = 0;
742 else
743 nstore[endp-startp] = 0;
745 if (debug)
746 fprintf (stderr, " - add prefix: %s\n", nstore);
748 add_prefix (pprefix, nstore);
749 if (*endp == 0)
750 break;
751 endp = startp = endp + 1;
753 else
754 endp++;
758 /* Main program. */
761 main (int argc, char **argv)
763 static const char *const ld_suffix = "ld";
764 static const char *const real_ld_suffix = "real-ld";
765 static const char *const collect_ld_suffix = "collect-ld";
766 static const char *const nm_suffix = "nm";
767 static const char *const gnm_suffix = "gnm";
768 #ifdef LDD_SUFFIX
769 static const char *const ldd_suffix = LDD_SUFFIX;
770 #endif
771 static const char *const strip_suffix = "strip";
772 static const char *const gstrip_suffix = "gstrip";
774 #ifdef CROSS_COMPILE
775 /* If we look for a program in the compiler directories, we just use
776 the short name, since these directories are already system-specific.
777 But it we look for a program in the system directories, we need to
778 qualify the program name with the target machine. */
780 const char *const full_ld_suffix =
781 concat(target_machine, "-", ld_suffix, NULL);
782 const char *const full_nm_suffix =
783 concat (target_machine, "-", nm_suffix, NULL);
784 const char *const full_gnm_suffix =
785 concat (target_machine, "-", gnm_suffix, NULL);
786 #ifdef LDD_SUFFIX
787 const char *const full_ldd_suffix =
788 concat (target_machine, "-", ldd_suffix, NULL);
789 #endif
790 const char *const full_strip_suffix =
791 concat (target_machine, "-", strip_suffix, NULL);
792 const char *const full_gstrip_suffix =
793 concat (target_machine, "-", gstrip_suffix, NULL);
794 #else
795 const char *const full_ld_suffix = ld_suffix;
796 const char *const full_nm_suffix = nm_suffix;
797 const char *const full_gnm_suffix = gnm_suffix;
798 #ifdef LDD_SUFFIX
799 const char *const full_ldd_suffix = ldd_suffix;
800 #endif
801 const char *const full_strip_suffix = strip_suffix;
802 const char *const full_gstrip_suffix = gstrip_suffix;
803 #endif /* CROSS_COMPILE */
805 const char *arg;
806 FILE *outf;
807 #ifdef COLLECT_EXPORT_LIST
808 FILE *exportf;
809 #endif
810 const char *ld_file_name;
811 const char *p;
812 char **c_argv;
813 const char **c_ptr;
814 char **ld1_argv;
815 const char **ld1;
816 char **ld2_argv;
817 const char **ld2;
818 char **object_lst;
819 const char **object;
820 int first_file;
821 int num_c_args = argc+9;
823 no_demangle = !! getenv ("COLLECT_NO_DEMANGLE");
825 /* Suppress demangling by the real linker, which may be broken. */
826 putenv (xstrdup ("COLLECT_NO_DEMANGLE="));
828 #if defined (COLLECT2_HOST_INITIALIZATION)
829 /* Perform system dependent initialization, if necessary. */
830 COLLECT2_HOST_INITIALIZATION;
831 #endif
833 #ifdef SIGCHLD
834 /* We *MUST* set SIGCHLD to SIG_DFL so that the wait4() call will
835 receive the signal. A different setting is inheritable */
836 signal (SIGCHLD, SIG_DFL);
837 #endif
839 gcc_init_libintl ();
841 /* Do not invoke xcalloc before this point, since locale needs to be
842 set first, in case a diagnostic is issued. */
844 ld1 = (const char **)(ld1_argv = xcalloc(sizeof (char *), argc+3));
845 ld2 = (const char **)(ld2_argv = xcalloc(sizeof (char *), argc+10));
846 object = (const char **)(object_lst = xcalloc(sizeof (char *), argc));
848 #ifdef DEBUG
849 debug = 1;
850 #endif
852 /* Parse command line early for instances of -debug. This allows
853 the debug flag to be set before functions like find_a_file()
854 are called. */
856 int i;
858 for (i = 1; argv[i] != NULL; i ++)
860 if (! strcmp (argv[i], "-debug"))
861 debug = 1;
862 COLLECT_PARSE_FLAG (argv[i]);
864 vflag = debug;
867 #ifndef DEFAULT_A_OUT_NAME
868 output_file = "a.out";
869 #else
870 output_file = DEFAULT_A_OUT_NAME;
871 #endif
873 obstack_begin (&temporary_obstack, 0);
874 temporary_firstobj = obstack_alloc (&temporary_obstack, 0);
876 current_demangling_style = auto_demangling;
877 p = getenv ("COLLECT_GCC_OPTIONS");
878 while (p && *p)
880 const char *q = extract_string (&p);
881 if (*q == '-' && (q[1] == 'm' || q[1] == 'f'))
882 num_c_args++;
884 obstack_free (&temporary_obstack, temporary_firstobj);
886 /* -fno-profile-arcs -fno-test-coverage -fno-branch-probabilities
887 -fno-exceptions -w */
888 num_c_args += 5;
890 c_ptr = (const char **) (c_argv = xcalloc (sizeof (char *), num_c_args));
892 if (argc < 2)
893 fatal ("no arguments");
895 #ifdef SIGQUIT
896 if (signal (SIGQUIT, SIG_IGN) != SIG_IGN)
897 signal (SIGQUIT, handler);
898 #endif
899 if (signal (SIGINT, SIG_IGN) != SIG_IGN)
900 signal (SIGINT, handler);
901 #ifdef SIGALRM
902 if (signal (SIGALRM, SIG_IGN) != SIG_IGN)
903 signal (SIGALRM, handler);
904 #endif
905 #ifdef SIGHUP
906 if (signal (SIGHUP, SIG_IGN) != SIG_IGN)
907 signal (SIGHUP, handler);
908 #endif
909 if (signal (SIGSEGV, SIG_IGN) != SIG_IGN)
910 signal (SIGSEGV, handler);
911 #ifdef SIGBUS
912 if (signal (SIGBUS, SIG_IGN) != SIG_IGN)
913 signal (SIGBUS, handler);
914 #endif
916 /* Extract COMPILER_PATH and PATH into our prefix list. */
917 prefix_from_env ("COMPILER_PATH", &cpath);
918 prefix_from_env ("PATH", &path);
920 /* Try to discover a valid linker/nm/strip to use. */
922 /* Maybe we know the right file to use (if not cross). */
923 ld_file_name = 0;
924 #ifdef DEFAULT_LINKER
925 if (access (DEFAULT_LINKER, X_OK) == 0)
926 ld_file_name = DEFAULT_LINKER;
927 if (ld_file_name == 0)
928 #endif
929 #ifdef REAL_LD_FILE_NAME
930 ld_file_name = find_a_file (&path, REAL_LD_FILE_NAME);
931 if (ld_file_name == 0)
932 #endif
933 /* Search the (target-specific) compiler dirs for ld'. */
934 ld_file_name = find_a_file (&cpath, real_ld_suffix);
935 /* Likewise for `collect-ld'. */
936 if (ld_file_name == 0)
937 ld_file_name = find_a_file (&cpath, collect_ld_suffix);
938 /* Search the compiler directories for `ld'. We have protection against
939 recursive calls in find_a_file. */
940 if (ld_file_name == 0)
941 ld_file_name = find_a_file (&cpath, ld_suffix);
942 /* Search the ordinary system bin directories
943 for `ld' (if native linking) or `TARGET-ld' (if cross). */
944 if (ld_file_name == 0)
945 ld_file_name = find_a_file (&path, full_ld_suffix);
947 #ifdef REAL_NM_FILE_NAME
948 nm_file_name = find_a_file (&path, REAL_NM_FILE_NAME);
949 if (nm_file_name == 0)
950 #endif
951 nm_file_name = find_a_file (&cpath, gnm_suffix);
952 if (nm_file_name == 0)
953 nm_file_name = find_a_file (&path, full_gnm_suffix);
954 if (nm_file_name == 0)
955 nm_file_name = find_a_file (&cpath, nm_suffix);
956 if (nm_file_name == 0)
957 nm_file_name = find_a_file (&path, full_nm_suffix);
959 #ifdef LDD_SUFFIX
960 ldd_file_name = find_a_file (&cpath, ldd_suffix);
961 if (ldd_file_name == 0)
962 ldd_file_name = find_a_file (&path, full_ldd_suffix);
963 #endif
965 #ifdef REAL_STRIP_FILE_NAME
966 strip_file_name = find_a_file (&path, REAL_STRIP_FILE_NAME);
967 if (strip_file_name == 0)
968 #endif
969 strip_file_name = find_a_file (&cpath, gstrip_suffix);
970 if (strip_file_name == 0)
971 strip_file_name = find_a_file (&path, full_gstrip_suffix);
972 if (strip_file_name == 0)
973 strip_file_name = find_a_file (&cpath, strip_suffix);
974 if (strip_file_name == 0)
975 strip_file_name = find_a_file (&path, full_strip_suffix);
977 /* Determine the full path name of the C compiler to use. */
978 c_file_name = getenv ("COLLECT_GCC");
979 if (c_file_name == 0)
981 #ifdef CROSS_COMPILE
982 c_file_name = concat (target_machine, "-gcc", NULL);
983 #else
984 c_file_name = "gcc";
985 #endif
988 p = find_a_file (&cpath, c_file_name);
990 /* Here it should be safe to use the system search path since we should have
991 already qualified the name of the compiler when it is needed. */
992 if (p == 0)
993 p = find_a_file (&path, c_file_name);
995 if (p)
996 c_file_name = p;
998 *ld1++ = *ld2++ = ld_file_name;
1000 /* Make temp file names. */
1001 c_file = make_temp_file (".c");
1002 o_file = make_temp_file (".o");
1003 #ifdef COLLECT_EXPORT_LIST
1004 export_file = make_temp_file (".x");
1005 #endif
1006 ldout = make_temp_file (".ld");
1007 *c_ptr++ = c_file_name;
1008 *c_ptr++ = "-x";
1009 *c_ptr++ = "c";
1010 *c_ptr++ = "-c";
1011 *c_ptr++ = "-o";
1012 *c_ptr++ = o_file;
1014 #ifdef COLLECT_EXPORT_LIST
1015 /* Generate a list of directories from LIBPATH. */
1016 prefix_from_env ("LIBPATH", &libpath_lib_dirs);
1017 /* Add to this list also two standard directories where
1018 AIX loader always searches for libraries. */
1019 add_prefix (&libpath_lib_dirs, "/lib");
1020 add_prefix (&libpath_lib_dirs, "/usr/lib");
1021 #endif
1023 /* Get any options that the upper GCC wants to pass to the sub-GCC.
1025 AIX support needs to know if -shared has been specified before
1026 parsing commandline arguments. */
1028 p = getenv ("COLLECT_GCC_OPTIONS");
1029 while (p && *p)
1031 const char *q = extract_string (&p);
1032 if (*q == '-' && (q[1] == 'm' || q[1] == 'f'))
1033 *c_ptr++ = xstrdup (q);
1034 if (strcmp (q, "-EL") == 0 || strcmp (q, "-EB") == 0)
1035 *c_ptr++ = xstrdup (q);
1036 if (strcmp (q, "-shared") == 0)
1037 shared_obj = 1;
1038 if (*q == '-' && q[1] == 'B')
1040 *c_ptr++ = xstrdup (q);
1041 if (q[2] == 0)
1043 q = extract_string (&p);
1044 *c_ptr++ = xstrdup (q);
1048 obstack_free (&temporary_obstack, temporary_firstobj);
1049 *c_ptr++ = "-fno-profile-arcs";
1050 *c_ptr++ = "-fno-test-coverage";
1051 *c_ptr++ = "-fno-branch-probabilities";
1052 *c_ptr++ = "-fno-exceptions";
1053 *c_ptr++ = "-w";
1055 /* !!! When GCC calls collect2,
1056 it does not know whether it is calling collect2 or ld.
1057 So collect2 cannot meaningfully understand any options
1058 except those ld understands.
1059 If you propose to make GCC pass some other option,
1060 just imagine what will happen if ld is really ld!!! */
1062 /* Parse arguments. Remember output file spec, pass the rest to ld. */
1063 /* After the first file, put in the c++ rt0. */
1065 first_file = 1;
1066 while ((arg = *++argv) != (char *) 0)
1068 *ld1++ = *ld2++ = arg;
1070 if (arg[0] == '-')
1072 switch (arg[1])
1074 #ifdef COLLECT_EXPORT_LIST
1075 /* We want to disable automatic exports on AIX when user
1076 explicitly puts an export list in command line */
1077 case 'b':
1078 if (arg[2] == 'E' || strncmp (&arg[2], "export", 6) == 0)
1079 export_flag = 1;
1080 else if (arg[2] == '6' && arg[3] == '4')
1081 aix64_flag = 1;
1082 break;
1083 #endif
1085 case 'd':
1086 if (!strcmp (arg, "-debug"))
1088 /* Already parsed. */
1089 ld1--;
1090 ld2--;
1092 break;
1094 case 'l':
1095 if (first_file)
1097 /* place o_file BEFORE this argument! */
1098 first_file = 0;
1099 ld2--;
1100 *ld2++ = o_file;
1101 *ld2++ = arg;
1103 #ifdef COLLECT_EXPORT_LIST
1105 /* Resolving full library name. */
1106 const char *s = resolve_lib_name (arg+2);
1108 /* Saving a full library name. */
1109 add_to_list (&libs, s);
1111 #endif
1112 break;
1114 #ifdef COLLECT_EXPORT_LIST
1115 /* Saving directories where to search for libraries. */
1116 case 'L':
1117 add_prefix (&cmdline_lib_dirs, arg+2);
1118 break;
1119 #else
1120 #if LINK_ELIMINATE_DUPLICATE_LDIRECTORIES
1121 case 'L':
1122 if (is_in_args (arg, (const char **) ld1_argv, ld1-1))
1123 --ld1;
1124 break;
1125 #endif /* LINK_ELIMINATE_DUPLICATE_LDIRECTORIES */
1126 #endif
1128 case 'o':
1129 if (arg[2] == '\0')
1130 output_file = *ld1++ = *ld2++ = *++argv;
1131 else if (1
1132 #ifdef SWITCHES_NEED_SPACES
1133 && ! strchr (SWITCHES_NEED_SPACES, arg[1])
1134 #endif
1137 output_file = &arg[2];
1138 break;
1140 case 'r':
1141 if (arg[2] == '\0')
1142 rflag = 1;
1143 break;
1145 case 's':
1146 if (arg[2] == '\0' && do_collecting)
1148 /* We must strip after the nm run, otherwise C++ linking
1149 will not work. Thus we strip in the second ld run, or
1150 else with strip if there is no second ld run. */
1151 strip_flag = 1;
1152 ld1--;
1154 break;
1156 case 'v':
1157 if (arg[2] == '\0')
1158 vflag = 1;
1159 break;
1162 else if ((p = strrchr (arg, '.')) != (char *) 0
1163 && (strcmp (p, ".o") == 0 || strcmp (p, ".a") == 0
1164 || strcmp (p, ".so") == 0 || strcmp (p, ".lo") == 0
1165 || strcmp (p, ".obj") == 0))
1167 if (first_file)
1169 first_file = 0;
1170 if (p[1] == 'o')
1171 *ld2++ = o_file;
1172 else
1174 /* place o_file BEFORE this argument! */
1175 ld2--;
1176 *ld2++ = o_file;
1177 *ld2++ = arg;
1180 if (p[1] == 'o' || p[1] == 'l')
1181 *object++ = arg;
1182 #ifdef COLLECT_EXPORT_LIST
1183 /* libraries can be specified directly, i.e. without -l flag. */
1184 else
1186 /* Saving a full library name. */
1187 add_to_list (&libs, arg);
1189 #endif
1193 #ifdef COLLECT_EXPORT_LIST
1194 /* This is added only for debugging purposes. */
1195 if (debug)
1197 fprintf (stderr, "List of libraries:\n");
1198 dump_list (stderr, "\t", libs.first);
1201 /* The AIX linker will discard static constructors in object files if
1202 nothing else in the file is referenced, so look at them first. */
1204 const char **export_object_lst = (const char **)object_lst;
1206 while (export_object_lst < object)
1207 scan_prog_file (*export_object_lst++, PASS_OBJ);
1210 struct id *list = libs.first;
1212 for (; list; list = list->next)
1213 scan_prog_file (list->name, PASS_FIRST);
1216 if (exports.first)
1218 char *buf = concat ("-bE:", export_file, NULL);
1220 *ld1++ = buf;
1221 *ld2++ = buf;
1223 exportf = fopen (export_file, "w");
1224 if (exportf == (FILE *) 0)
1225 fatal_perror ("fopen %s", export_file);
1226 write_aix_file (exportf, exports.first);
1227 if (fclose (exportf))
1228 fatal_perror ("fclose %s", export_file);
1230 #endif
1232 *c_ptr++ = c_file;
1233 *c_ptr = *ld1 = *object = (char *) 0;
1235 if (vflag)
1237 notice ("collect2 version %s", version_string);
1238 #ifdef TARGET_VERSION
1239 TARGET_VERSION;
1240 #endif
1241 fprintf (stderr, "\n");
1244 if (debug)
1246 const char *ptr;
1247 fprintf (stderr, "ld_file_name = %s\n",
1248 (ld_file_name ? ld_file_name : "not found"));
1249 fprintf (stderr, "c_file_name = %s\n",
1250 (c_file_name ? c_file_name : "not found"));
1251 fprintf (stderr, "nm_file_name = %s\n",
1252 (nm_file_name ? nm_file_name : "not found"));
1253 #ifdef LDD_SUFFIX
1254 fprintf (stderr, "ldd_file_name = %s\n",
1255 (ldd_file_name ? ldd_file_name : "not found"));
1256 #endif
1257 fprintf (stderr, "strip_file_name = %s\n",
1258 (strip_file_name ? strip_file_name : "not found"));
1259 fprintf (stderr, "c_file = %s\n",
1260 (c_file ? c_file : "not found"));
1261 fprintf (stderr, "o_file = %s\n",
1262 (o_file ? o_file : "not found"));
1264 ptr = getenv ("COLLECT_GCC_OPTIONS");
1265 if (ptr)
1266 fprintf (stderr, "COLLECT_GCC_OPTIONS = %s\n", ptr);
1268 ptr = getenv ("COLLECT_GCC");
1269 if (ptr)
1270 fprintf (stderr, "COLLECT_GCC = %s\n", ptr);
1272 ptr = getenv ("COMPILER_PATH");
1273 if (ptr)
1274 fprintf (stderr, "COMPILER_PATH = %s\n", ptr);
1276 ptr = getenv (LIBRARY_PATH_ENV);
1277 if (ptr)
1278 fprintf (stderr, "%-20s= %s\n", LIBRARY_PATH_ENV, ptr);
1280 fprintf (stderr, "\n");
1283 /* Load the program, searching all libraries and attempting to provide
1284 undefined symbols from repository information. */
1286 /* On AIX we do this later. */
1287 #ifndef COLLECT_EXPORT_LIST
1288 do_tlink (ld1_argv, object_lst);
1289 #endif
1291 /* If -r or they will be run via some other method, do not build the
1292 constructor or destructor list, just return now. */
1293 if (rflag
1294 #ifndef COLLECT_EXPORT_LIST
1295 || ! do_collecting
1296 #endif
1299 #ifdef COLLECT_EXPORT_LIST
1300 /* Do the link we avoided above if we are exiting. */
1301 do_tlink (ld1_argv, object_lst);
1303 /* But make sure we delete the export file we may have created. */
1304 if (export_file != 0 && export_file[0])
1305 maybe_unlink (export_file);
1306 #endif
1307 maybe_unlink (c_file);
1308 maybe_unlink (o_file);
1309 return 0;
1312 /* Examine the namelist with nm and search it for static constructors
1313 and destructors to call.
1314 Write the constructor and destructor tables to a .s file and reload. */
1316 /* On AIX we already scanned for global constructors/destructors. */
1317 #ifndef COLLECT_EXPORT_LIST
1318 scan_prog_file (output_file, PASS_FIRST);
1319 #endif
1321 #ifdef SCAN_LIBRARIES
1322 scan_libraries (output_file);
1323 #endif
1325 if (debug)
1327 notice ("%d constructor(s) found\n", constructors.number);
1328 notice ("%d destructor(s) found\n", destructors.number);
1329 notice ("%d frame table(s) found\n", frame_tables.number);
1332 if (constructors.number == 0 && destructors.number == 0
1333 && frame_tables.number == 0
1334 #if defined (SCAN_LIBRARIES) || defined (COLLECT_EXPORT_LIST)
1335 /* If we will be running these functions ourselves, we want to emit
1336 stubs into the shared library so that we do not have to relink
1337 dependent programs when we add static objects. */
1338 && ! shared_obj
1339 #endif
1342 #ifdef COLLECT_EXPORT_LIST
1343 /* Do tlink without additional code generation. */
1344 do_tlink (ld1_argv, object_lst);
1345 #endif
1346 /* Strip now if it was requested on the command line. */
1347 if (strip_flag)
1349 char **real_strip_argv = xcalloc (sizeof (char *), 3);
1350 const char ** strip_argv = (const char **) real_strip_argv;
1352 strip_argv[0] = strip_file_name;
1353 strip_argv[1] = output_file;
1354 strip_argv[2] = (char *) 0;
1355 fork_execute ("strip", real_strip_argv);
1358 #ifdef COLLECT_EXPORT_LIST
1359 maybe_unlink (export_file);
1360 #endif
1361 maybe_unlink (c_file);
1362 maybe_unlink (o_file);
1363 return 0;
1366 /* Sort ctor and dtor lists by priority. */
1367 sort_ids (&constructors);
1368 sort_ids (&destructors);
1370 maybe_unlink(output_file);
1371 outf = fopen (c_file, "w");
1372 if (outf == (FILE *) 0)
1373 fatal_perror ("fopen %s", c_file);
1375 write_c_file (outf, c_file);
1377 if (fclose (outf))
1378 fatal_perror ("fclose %s", c_file);
1380 /* Tell the linker that we have initializer and finalizer functions. */
1381 #ifdef LD_INIT_SWITCH
1382 #ifdef COLLECT_EXPORT_LIST
1383 *ld2++ = concat (LD_INIT_SWITCH, ":", initname, ":", fininame, NULL);
1384 #else
1385 *ld2++ = LD_INIT_SWITCH;
1386 *ld2++ = initname;
1387 *ld2++ = LD_FINI_SWITCH;
1388 *ld2++ = fininame;
1389 #endif
1390 #endif
1392 #ifdef COLLECT_EXPORT_LIST
1393 if (shared_obj)
1395 /* If we did not add export flag to link arguments before, add it to
1396 second link phase now. No new exports should have been added. */
1397 if (! exports.first)
1398 *ld2++ = concat ("-bE:", export_file, NULL);
1400 #ifndef LD_INIT_SWITCH
1401 add_to_list (&exports, initname);
1402 add_to_list (&exports, fininame);
1403 add_to_list (&exports, "_GLOBAL__DI");
1404 add_to_list (&exports, "_GLOBAL__DD");
1405 #endif
1406 exportf = fopen (export_file, "w");
1407 if (exportf == (FILE *) 0)
1408 fatal_perror ("fopen %s", export_file);
1409 write_aix_file (exportf, exports.first);
1410 if (fclose (exportf))
1411 fatal_perror ("fclose %s", export_file);
1413 #endif
1415 /* End of arguments to second link phase. */
1416 *ld2 = (char*) 0;
1418 if (debug)
1420 fprintf (stderr, "\n========== output_file = %s, c_file = %s\n",
1421 output_file, c_file);
1422 write_c_file (stderr, "stderr");
1423 fprintf (stderr, "========== end of c_file\n\n");
1424 #ifdef COLLECT_EXPORT_LIST
1425 fprintf (stderr, "\n========== export_file = %s\n", export_file);
1426 write_aix_file (stderr, exports.first);
1427 fprintf (stderr, "========== end of export_file\n\n");
1428 #endif
1431 /* Assemble the constructor and destructor tables.
1432 Link the tables in with the rest of the program. */
1434 fork_execute ("gcc", c_argv);
1435 #ifdef COLLECT_EXPORT_LIST
1436 /* On AIX we must call tlink because of possible templates resolution. */
1437 do_tlink (ld2_argv, object_lst);
1438 #else
1439 /* Otherwise, simply call ld because tlink is already done. */
1440 fork_execute ("ld", ld2_argv);
1442 /* Let scan_prog_file do any final mods (OSF/rose needs this for
1443 constructors/destructors in shared libraries. */
1444 scan_prog_file (output_file, PASS_SECOND);
1445 #endif
1447 maybe_unlink (c_file);
1448 maybe_unlink (o_file);
1450 #ifdef COLLECT_EXPORT_LIST
1451 maybe_unlink (export_file);
1452 #endif
1454 return 0;
1458 /* Wait for a process to finish, and exit if a nonzero status is found. */
1461 collect_wait (const char *prog)
1463 int status;
1465 pwait (pid, &status, 0);
1466 if (status)
1468 if (WIFSIGNALED (status))
1470 int sig = WTERMSIG (status);
1471 error ("%s terminated with signal %d [%s]%s",
1472 prog, sig, strsignal(sig),
1473 WCOREDUMP(status) ? ", core dumped" : "");
1474 collect_exit (FATAL_EXIT_CODE);
1477 if (WIFEXITED (status))
1478 return WEXITSTATUS (status);
1480 return 0;
1483 static void
1484 do_wait (const char *prog)
1486 int ret = collect_wait (prog);
1487 if (ret != 0)
1489 error ("%s returned %d exit status", prog, ret);
1490 collect_exit (ret);
1495 /* Execute a program, and wait for the reply. */
1497 void
1498 collect_execute (const char *prog, char **argv, const char *redir)
1500 char *errmsg_fmt;
1501 char *errmsg_arg;
1502 int redir_handle = -1;
1503 int stdout_save = -1;
1504 int stderr_save = -1;
1506 if (vflag || debug)
1508 char **p_argv;
1509 const char *str;
1511 if (argv[0])
1512 fprintf (stderr, "%s", argv[0]);
1513 else
1514 notice ("[cannot find %s]", prog);
1516 for (p_argv = &argv[1]; (str = *p_argv) != (char *) 0; p_argv++)
1517 fprintf (stderr, " %s", str);
1519 fprintf (stderr, "\n");
1522 fflush (stdout);
1523 fflush (stderr);
1525 /* If we cannot find a program we need, complain error. Do this here
1526 since we might not end up needing something that we could not find. */
1528 if (argv[0] == 0)
1529 fatal ("cannot find `%s'", prog);
1531 if (redir)
1533 /* Open response file. */
1534 redir_handle = open (redir, O_WRONLY | O_TRUNC | O_CREAT);
1536 /* Duplicate the stdout and stderr file handles
1537 so they can be restored later. */
1538 stdout_save = dup (STDOUT_FILENO);
1539 if (stdout_save == -1)
1540 fatal_perror ("redirecting stdout: %s", redir);
1541 stderr_save = dup (STDERR_FILENO);
1542 if (stderr_save == -1)
1543 fatal_perror ("redirecting stdout: %s", redir);
1545 /* Redirect stdout & stderr to our response file. */
1546 dup2 (redir_handle, STDOUT_FILENO);
1547 dup2 (redir_handle, STDERR_FILENO);
1550 pid = pexecute (argv[0], argv, argv[0], NULL, &errmsg_fmt, &errmsg_arg,
1551 (PEXECUTE_FIRST | PEXECUTE_LAST | PEXECUTE_SEARCH));
1553 if (redir)
1555 /* Restore stdout and stderr to their previous settings. */
1556 dup2 (stdout_save, STDOUT_FILENO);
1557 dup2 (stderr_save, STDERR_FILENO);
1559 /* Close response file. */
1560 close (redir_handle);
1563 if (pid == -1)
1564 fatal_perror (errmsg_fmt, errmsg_arg);
1567 static void
1568 fork_execute (const char *prog, char **argv)
1570 collect_execute (prog, argv, NULL);
1571 do_wait (prog);
1574 /* Unlink a file unless we are debugging. */
1576 static void
1577 maybe_unlink (const char *file)
1579 if (!debug)
1580 unlink (file);
1581 else
1582 notice ("[Leaving %s]\n", file);
1586 static long sequence_number = 0;
1588 /* Add a name to a linked list. */
1590 static void
1591 add_to_list (struct head *head_ptr, const char *name)
1593 struct id *newid = xcalloc (sizeof (struct id) + strlen (name), 1);
1594 struct id *p;
1595 strcpy (newid->name, name);
1597 if (head_ptr->first)
1598 head_ptr->last->next = newid;
1599 else
1600 head_ptr->first = newid;
1602 /* Check for duplicate symbols. */
1603 for (p = head_ptr->first;
1604 strcmp (name, p->name) != 0;
1605 p = p->next)
1607 if (p != newid)
1609 head_ptr->last->next = 0;
1610 free (newid);
1611 return;
1614 newid->sequence = ++sequence_number;
1615 head_ptr->last = newid;
1616 head_ptr->number++;
1619 /* Grab the init priority number from an init function name that
1620 looks like "_GLOBAL_.I.12345.foo". */
1622 static int
1623 extract_init_priority (const char *name)
1625 int pos = 0, pri;
1627 while (name[pos] == '_')
1628 ++pos;
1629 pos += 10; /* strlen ("GLOBAL__X_") */
1631 /* Extract init_p number from ctor/dtor name. */
1632 pri = atoi (name + pos);
1633 return pri ? pri : DEFAULT_INIT_PRIORITY;
1636 /* Insertion sort the ids from ctor/dtor list HEAD_PTR in descending order.
1637 ctors will be run from right to left, dtors from left to right. */
1639 static void
1640 sort_ids (struct head *head_ptr)
1642 /* id holds the current element to insert. id_next holds the next
1643 element to insert. id_ptr iterates through the already sorted elements
1644 looking for the place to insert id. */
1645 struct id *id, *id_next, **id_ptr;
1647 id = head_ptr->first;
1649 /* We don't have any sorted elements yet. */
1650 head_ptr->first = NULL;
1652 for (; id; id = id_next)
1654 id_next = id->next;
1655 id->sequence = extract_init_priority (id->name);
1657 for (id_ptr = &(head_ptr->first); ; id_ptr = &((*id_ptr)->next))
1658 if (*id_ptr == NULL
1659 /* If the sequence numbers are the same, we put the id from the
1660 file later on the command line later in the list. */
1661 || id->sequence > (*id_ptr)->sequence
1662 /* Hack: do lexical compare, too.
1663 || (id->sequence == (*id_ptr)->sequence
1664 && strcmp (id->name, (*id_ptr)->name) > 0) */
1667 id->next = *id_ptr;
1668 *id_ptr = id;
1669 break;
1673 /* Now set the sequence numbers properly so write_c_file works. */
1674 for (id = head_ptr->first; id; id = id->next)
1675 id->sequence = ++sequence_number;
1678 /* Write: `prefix', the names on list LIST, `suffix'. */
1680 static void
1681 write_list (FILE *stream, const char *prefix, struct id *list)
1683 while (list)
1685 fprintf (stream, "%sx%d,\n", prefix, list->sequence);
1686 list = list->next;
1690 #if LINK_ELIMINATE_DUPLICATE_LDIRECTORIES
1691 /* Given a STRING, return nonzero if it occurs in the list in range
1692 [ARGS_BEGIN,ARGS_END). */
1694 static int
1695 is_in_args (const char *string, const char **args_begin,
1696 const char **args_end)
1698 const char **args_pointer;
1699 for (args_pointer = args_begin; args_pointer != args_end; ++args_pointer)
1700 if (strcmp (string, *args_pointer) == 0)
1701 return 1;
1702 return 0;
1704 #endif /* LINK_ELIMINATE_DUPLICATE_LDIRECTORIES */
1706 #ifdef COLLECT_EXPORT_LIST
1707 /* This function is really used only on AIX, but may be useful. */
1708 #if 0
1709 static int
1710 is_in_list (const char *prefix, struct id *list)
1712 while (list)
1714 if (!strcmp (prefix, list->name)) return 1;
1715 list = list->next;
1717 return 0;
1719 #endif
1720 #endif /* COLLECT_EXPORT_LIST */
1722 /* Added for debugging purpose. */
1723 #ifdef COLLECT_EXPORT_LIST
1724 static void
1725 dump_list (FILE *stream, const char *prefix, struct id *list)
1727 while (list)
1729 fprintf (stream, "%s%s,\n", prefix, list->name);
1730 list = list->next;
1733 #endif
1735 #if 0
1736 static void
1737 dump_prefix_list (FILE *stream, const char *prefix, struct prefix_list *list)
1739 while (list)
1741 fprintf (stream, "%s%s,\n", prefix, list->prefix);
1742 list = list->next;
1745 #endif
1747 static void
1748 write_list_with_asm (FILE *stream, const char *prefix, struct id *list)
1750 while (list)
1752 fprintf (stream, "%sx%d __asm__ (\"%s\");\n",
1753 prefix, list->sequence, list->name);
1754 list = list->next;
1758 /* Write out the constructor and destructor tables statically (for a shared
1759 object), along with the functions to execute them. */
1761 static void
1762 write_c_file_stat (FILE *stream, const char *name ATTRIBUTE_UNUSED)
1764 const char *p, *q;
1765 char *prefix, *r;
1766 int frames = (frame_tables.number > 0);
1768 /* Figure out name of output_file, stripping off .so version. */
1769 p = strrchr (output_file, '/');
1770 if (p == 0)
1771 p = output_file;
1772 else
1773 p++;
1774 q = p;
1775 while (q)
1777 q = strchr (q,'.');
1778 if (q == 0)
1780 q = p + strlen (p);
1781 break;
1783 else
1785 if (strncmp (q, ".so", 3) == 0)
1787 q += 3;
1788 break;
1790 else
1791 q++;
1794 /* q points to null at end of the string (or . of the .so version) */
1795 prefix = xmalloc (q - p + 1);
1796 strncpy (prefix, p, q - p);
1797 prefix[q - p] = 0;
1798 for (r = prefix; *r; r++)
1799 if (!ISALNUM ((unsigned char)*r))
1800 *r = '_';
1801 if (debug)
1802 notice ("\nwrite_c_file - output name is %s, prefix is %s\n",
1803 output_file, prefix);
1805 initname = concat ("_GLOBAL__FI_", prefix, NULL);
1806 fininame = concat ("_GLOBAL__FD_", prefix, NULL);
1808 free (prefix);
1810 /* Write the tables as C code. */
1812 fprintf (stream, "static int count;\n");
1813 fprintf (stream, "typedef void entry_pt();\n");
1814 write_list_with_asm (stream, "extern entry_pt ", constructors.first);
1816 if (frames)
1818 write_list_with_asm (stream, "extern void *", frame_tables.first);
1820 fprintf (stream, "\tstatic void *frame_table[] = {\n");
1821 write_list (stream, "\t\t&", frame_tables.first);
1822 fprintf (stream, "\t0\n};\n");
1824 /* This must match what's in frame.h. */
1825 fprintf (stream, "struct object {\n");
1826 fprintf (stream, " void *pc_begin;\n");
1827 fprintf (stream, " void *pc_end;\n");
1828 fprintf (stream, " void *fde_begin;\n");
1829 fprintf (stream, " void *fde_array;\n");
1830 fprintf (stream, " __SIZE_TYPE__ count;\n");
1831 fprintf (stream, " struct object *next;\n");
1832 fprintf (stream, "};\n");
1834 fprintf (stream, "extern void __register_frame_info_table (void *, struct object *);\n");
1835 fprintf (stream, "extern void *__deregister_frame_info (void *);\n");
1837 fprintf (stream, "static void reg_frame () {\n");
1838 fprintf (stream, "\tstatic struct object ob;\n");
1839 fprintf (stream, "\t__register_frame_info_table (frame_table, &ob);\n");
1840 fprintf (stream, "\t}\n");
1842 fprintf (stream, "static void dereg_frame () {\n");
1843 fprintf (stream, "\t__deregister_frame_info (frame_table);\n");
1844 fprintf (stream, "\t}\n");
1847 fprintf (stream, "void %s() {\n", initname);
1848 if (constructors.number > 0 || frames)
1850 fprintf (stream, "\tstatic entry_pt *ctors[] = {\n");
1851 write_list (stream, "\t\t", constructors.first);
1852 if (frames)
1853 fprintf (stream, "\treg_frame,\n");
1854 fprintf (stream, "\t};\n");
1855 fprintf (stream, "\tentry_pt **p;\n");
1856 fprintf (stream, "\tif (count++ != 0) return;\n");
1857 fprintf (stream, "\tp = ctors + %d;\n", constructors.number + frames);
1858 fprintf (stream, "\twhile (p > ctors) (*--p)();\n");
1860 else
1861 fprintf (stream, "\t++count;\n");
1862 fprintf (stream, "}\n");
1863 write_list_with_asm (stream, "extern entry_pt ", destructors.first);
1864 fprintf (stream, "void %s() {\n", fininame);
1865 if (destructors.number > 0 || frames)
1867 fprintf (stream, "\tstatic entry_pt *dtors[] = {\n");
1868 write_list (stream, "\t\t", destructors.first);
1869 if (frames)
1870 fprintf (stream, "\tdereg_frame,\n");
1871 fprintf (stream, "\t};\n");
1872 fprintf (stream, "\tentry_pt **p;\n");
1873 fprintf (stream, "\tif (--count != 0) return;\n");
1874 fprintf (stream, "\tp = dtors;\n");
1875 fprintf (stream, "\twhile (p < dtors + %d) (*p++)();\n",
1876 destructors.number + frames);
1878 fprintf (stream, "}\n");
1880 if (shared_obj)
1882 COLLECT_SHARED_INIT_FUNC(stream, initname);
1883 COLLECT_SHARED_FINI_FUNC(stream, fininame);
1887 /* Write the constructor/destructor tables. */
1889 #ifndef LD_INIT_SWITCH
1890 static void
1891 write_c_file_glob (FILE *stream, const char *name ATTRIBUTE_UNUSED)
1893 /* Write the tables as C code. */
1895 int frames = (frame_tables.number > 0);
1897 fprintf (stream, "typedef void entry_pt();\n\n");
1899 write_list_with_asm (stream, "extern entry_pt ", constructors.first);
1901 if (frames)
1903 write_list_with_asm (stream, "extern void *", frame_tables.first);
1905 fprintf (stream, "\tstatic void *frame_table[] = {\n");
1906 write_list (stream, "\t\t&", frame_tables.first);
1907 fprintf (stream, "\t0\n};\n");
1909 /* This must match what's in frame.h. */
1910 fprintf (stream, "struct object {\n");
1911 fprintf (stream, " void *pc_begin;\n");
1912 fprintf (stream, " void *pc_end;\n");
1913 fprintf (stream, " void *fde_begin;\n");
1914 fprintf (stream, " void *fde_array;\n");
1915 fprintf (stream, " __SIZE_TYPE__ count;\n");
1916 fprintf (stream, " struct object *next;\n");
1917 fprintf (stream, "};\n");
1919 fprintf (stream, "extern void __register_frame_info_table (void *, struct object *);\n");
1920 fprintf (stream, "extern void *__deregister_frame_info (void *);\n");
1922 fprintf (stream, "static void reg_frame () {\n");
1923 fprintf (stream, "\tstatic struct object ob;\n");
1924 fprintf (stream, "\t__register_frame_info_table (frame_table, &ob);\n");
1925 fprintf (stream, "\t}\n");
1927 fprintf (stream, "static void dereg_frame () {\n");
1928 fprintf (stream, "\t__deregister_frame_info (frame_table);\n");
1929 fprintf (stream, "\t}\n");
1932 fprintf (stream, "\nentry_pt * __CTOR_LIST__[] = {\n");
1933 fprintf (stream, "\t(entry_pt *) %d,\n", constructors.number + frames);
1934 write_list (stream, "\t", constructors.first);
1935 if (frames)
1936 fprintf (stream, "\treg_frame,\n");
1937 fprintf (stream, "\t0\n};\n\n");
1939 write_list_with_asm (stream, "extern entry_pt ", destructors.first);
1941 fprintf (stream, "\nentry_pt * __DTOR_LIST__[] = {\n");
1942 fprintf (stream, "\t(entry_pt *) %d,\n", destructors.number + frames);
1943 write_list (stream, "\t", destructors.first);
1944 if (frames)
1945 fprintf (stream, "\tdereg_frame,\n");
1946 fprintf (stream, "\t0\n};\n\n");
1948 fprintf (stream, "extern entry_pt %s;\n", NAME__MAIN);
1949 fprintf (stream, "entry_pt *__main_reference = %s;\n\n", NAME__MAIN);
1951 #endif /* ! LD_INIT_SWITCH */
1953 static void
1954 write_c_file (FILE *stream, const char *name)
1956 fprintf (stream, "#ifdef __cplusplus\nextern \"C\" {\n#endif\n");
1957 #ifndef LD_INIT_SWITCH
1958 if (! shared_obj)
1959 write_c_file_glob (stream, name);
1960 else
1961 #endif
1962 write_c_file_stat (stream, name);
1963 fprintf (stream, "#ifdef __cplusplus\n}\n#endif\n");
1966 #ifdef COLLECT_EXPORT_LIST
1967 static void
1968 write_aix_file (FILE *stream, struct id *list)
1970 for (; list; list = list->next)
1972 fputs (list->name, stream);
1973 putc ('\n', stream);
1976 #endif
1978 #ifdef OBJECT_FORMAT_NONE
1980 /* Generic version to scan the name list of the loaded program for
1981 the symbols g++ uses for static constructors and destructors.
1983 The constructor table begins at __CTOR_LIST__ and contains a count
1984 of the number of pointers (or -1 if the constructors are built in a
1985 separate section by the linker), followed by the pointers to the
1986 constructor functions, terminated with a null pointer. The
1987 destructor table has the same format, and begins at __DTOR_LIST__. */
1989 static void
1990 scan_prog_file (const char *prog_name, enum pass which_pass)
1992 void (*int_handler) (int);
1993 void (*quit_handler) (int);
1994 char *real_nm_argv[4];
1995 const char **nm_argv = (const char **) real_nm_argv;
1996 int argc = 0;
1997 int pipe_fd[2];
1998 char *p, buf[1024];
1999 FILE *inf;
2001 if (which_pass == PASS_SECOND)
2002 return;
2004 /* If we do not have an `nm', complain. */
2005 if (nm_file_name == 0)
2006 fatal ("cannot find `nm'");
2008 nm_argv[argc++] = nm_file_name;
2009 if (NM_FLAGS[0] != '\0')
2010 nm_argv[argc++] = NM_FLAGS;
2012 nm_argv[argc++] = prog_name;
2013 nm_argv[argc++] = (char *) 0;
2015 if (pipe (pipe_fd) < 0)
2016 fatal_perror ("pipe");
2018 inf = fdopen (pipe_fd[0], "r");
2019 if (inf == (FILE *) 0)
2020 fatal_perror ("fdopen");
2022 /* Trace if needed. */
2023 if (vflag)
2025 const char **p_argv;
2026 const char *str;
2028 for (p_argv = &nm_argv[0]; (str = *p_argv) != (char *) 0; p_argv++)
2029 fprintf (stderr, " %s", str);
2031 fprintf (stderr, "\n");
2034 fflush (stdout);
2035 fflush (stderr);
2037 /* Spawn child nm on pipe. */
2038 pid = vfork ();
2039 if (pid == -1)
2040 fatal_perror (VFORK_STRING);
2042 if (pid == 0) /* child context */
2044 /* setup stdout */
2045 if (dup2 (pipe_fd[1], 1) < 0)
2046 fatal_perror ("dup2 %d 1", pipe_fd[1]);
2048 if (close (pipe_fd[0]) < 0)
2049 fatal_perror ("close %d", pipe_fd[0]);
2051 if (close (pipe_fd[1]) < 0)
2052 fatal_perror ("close %d", pipe_fd[1]);
2054 execv (nm_file_name, real_nm_argv);
2055 fatal_perror ("execv %s", nm_file_name);
2058 /* Parent context from here on. */
2059 int_handler = (void (*) (int)) signal (SIGINT, SIG_IGN);
2060 #ifdef SIGQUIT
2061 quit_handler = (void (*) (int)) signal (SIGQUIT, SIG_IGN);
2062 #endif
2064 if (close (pipe_fd[1]) < 0)
2065 fatal_perror ("close %d", pipe_fd[1]);
2067 if (debug)
2068 fprintf (stderr, "\nnm output with constructors/destructors.\n");
2070 /* Read each line of nm output. */
2071 while (fgets (buf, sizeof buf, inf) != (char *) 0)
2073 int ch, ch2;
2074 char *name, *end;
2076 /* If it contains a constructor or destructor name, add the name
2077 to the appropriate list. */
2079 for (p = buf; (ch = *p) != '\0' && ch != '\n' && ch != '_'; p++)
2080 if (ch == ' ' && p[1] == 'U' && p[2] == ' ')
2081 break;
2083 if (ch != '_')
2084 continue;
2086 name = p;
2087 /* Find the end of the symbol name.
2088 Do not include `|', because Encore nm can tack that on the end. */
2089 for (end = p; (ch2 = *end) != '\0' && !ISSPACE (ch2) && ch2 != '|';
2090 end++)
2091 continue;
2094 *end = '\0';
2095 switch (is_ctor_dtor (name))
2097 case 1:
2098 if (which_pass != PASS_LIB)
2099 add_to_list (&constructors, name);
2100 break;
2102 case 2:
2103 if (which_pass != PASS_LIB)
2104 add_to_list (&destructors, name);
2105 break;
2107 case 3:
2108 if (which_pass != PASS_LIB)
2109 fatal ("init function found in object %s", prog_name);
2110 #ifndef LD_INIT_SWITCH
2111 add_to_list (&constructors, name);
2112 #endif
2113 break;
2115 case 4:
2116 if (which_pass != PASS_LIB)
2117 fatal ("fini function found in object %s", prog_name);
2118 #ifndef LD_FINI_SWITCH
2119 add_to_list (&destructors, name);
2120 #endif
2121 break;
2123 case 5:
2124 if (which_pass != PASS_LIB)
2125 add_to_list (&frame_tables, name);
2126 break;
2128 default: /* not a constructor or destructor */
2129 continue;
2132 if (debug)
2133 fprintf (stderr, "\t%s\n", buf);
2136 if (debug)
2137 fprintf (stderr, "\n");
2139 if (fclose (inf) != 0)
2140 fatal_perror ("fclose");
2142 do_wait (nm_file_name);
2144 signal (SIGINT, int_handler);
2145 #ifdef SIGQUIT
2146 signal (SIGQUIT, quit_handler);
2147 #endif
2150 #ifdef LDD_SUFFIX
2152 /* Use the List Dynamic Dependencies program to find shared libraries that
2153 the output file depends upon and their initialization/finalization
2154 routines, if any. */
2156 static void
2157 scan_libraries (const char *prog_name)
2159 static struct head libraries; /* list of shared libraries found */
2160 struct id *list;
2161 void (*int_handler) (int);
2162 void (*quit_handler) (int);
2163 char *real_ldd_argv[4];
2164 const char **ldd_argv = (const char **) real_ldd_argv;
2165 int argc = 0;
2166 int pipe_fd[2];
2167 char buf[1024];
2168 FILE *inf;
2170 /* If we do not have an `ldd', complain. */
2171 if (ldd_file_name == 0)
2173 error ("cannot find `ldd'");
2174 return;
2177 ldd_argv[argc++] = ldd_file_name;
2178 ldd_argv[argc++] = prog_name;
2179 ldd_argv[argc++] = (char *) 0;
2181 if (pipe (pipe_fd) < 0)
2182 fatal_perror ("pipe");
2184 inf = fdopen (pipe_fd[0], "r");
2185 if (inf == (FILE *) 0)
2186 fatal_perror ("fdopen");
2188 /* Trace if needed. */
2189 if (vflag)
2191 const char **p_argv;
2192 const char *str;
2194 for (p_argv = &ldd_argv[0]; (str = *p_argv) != (char *) 0; p_argv++)
2195 fprintf (stderr, " %s", str);
2197 fprintf (stderr, "\n");
2200 fflush (stdout);
2201 fflush (stderr);
2203 /* Spawn child ldd on pipe. */
2204 pid = vfork ();
2205 if (pid == -1)
2206 fatal_perror (VFORK_STRING);
2208 if (pid == 0) /* child context */
2210 /* setup stdout */
2211 if (dup2 (pipe_fd[1], 1) < 0)
2212 fatal_perror ("dup2 %d 1", pipe_fd[1]);
2214 if (close (pipe_fd[0]) < 0)
2215 fatal_perror ("close %d", pipe_fd[0]);
2217 if (close (pipe_fd[1]) < 0)
2218 fatal_perror ("close %d", pipe_fd[1]);
2220 execv (ldd_file_name, real_ldd_argv);
2221 fatal_perror ("execv %s", ldd_file_name);
2224 /* Parent context from here on. */
2225 int_handler = (void (*) (int)) signal (SIGINT, SIG_IGN);
2226 #ifdef SIGQUIT
2227 quit_handler = (void (*) (int)) signal (SIGQUIT, SIG_IGN);
2228 #endif
2230 if (close (pipe_fd[1]) < 0)
2231 fatal_perror ("close %d", pipe_fd[1]);
2233 if (debug)
2234 notice ("\nldd output with constructors/destructors.\n");
2236 /* Read each line of ldd output. */
2237 while (fgets (buf, sizeof buf, inf) != (char *) 0)
2239 int ch2;
2240 char *name, *end, *p = buf;
2242 /* Extract names of libraries and add to list. */
2243 PARSE_LDD_OUTPUT (p);
2244 if (p == 0)
2245 continue;
2247 name = p;
2248 if (strncmp (name, "not found", sizeof ("not found") - 1) == 0)
2249 fatal ("dynamic dependency %s not found", buf);
2251 /* Find the end of the symbol name. */
2252 for (end = p;
2253 (ch2 = *end) != '\0' && ch2 != '\n' && !ISSPACE (ch2) && ch2 != '|';
2254 end++)
2255 continue;
2256 *end = '\0';
2258 if (access (name, R_OK) == 0)
2259 add_to_list (&libraries, name);
2260 else
2261 fatal ("unable to open dynamic dependency '%s'", buf);
2263 if (debug)
2264 fprintf (stderr, "\t%s\n", buf);
2266 if (debug)
2267 fprintf (stderr, "\n");
2269 if (fclose (inf) != 0)
2270 fatal_perror ("fclose");
2272 do_wait (ldd_file_name);
2274 signal (SIGINT, int_handler);
2275 #ifdef SIGQUIT
2276 signal (SIGQUIT, quit_handler);
2277 #endif
2279 /* Now iterate through the library list adding their symbols to
2280 the list. */
2281 for (list = libraries.first; list; list = list->next)
2282 scan_prog_file (list->name, PASS_LIB);
2285 #endif /* LDD_SUFFIX */
2287 #endif /* OBJECT_FORMAT_NONE */
2291 * COFF specific stuff.
2294 #ifdef OBJECT_FORMAT_COFF
2296 #if defined (EXTENDED_COFF)
2298 # define GCC_SYMBOLS(X) (SYMHEADER(X).isymMax + SYMHEADER(X).iextMax)
2299 # define GCC_SYMENT SYMR
2300 # define GCC_OK_SYMBOL(X) ((X).st == stProc || (X).st == stGlobal)
2301 # define GCC_SYMINC(X) (1)
2302 # define GCC_SYMZERO(X) (SYMHEADER(X).isymMax)
2303 # define GCC_CHECK_HDR(X) (PSYMTAB(X) != 0)
2305 #else
2307 # define GCC_SYMBOLS(X) (HEADER(ldptr).f_nsyms)
2308 # define GCC_SYMENT SYMENT
2309 # if defined (C_WEAKEXT)
2310 # define GCC_OK_SYMBOL(X) \
2311 (((X).n_sclass == C_EXT || (X).n_sclass == C_WEAKEXT) && \
2312 ((X).n_scnum > N_UNDEF) && \
2313 (aix64_flag \
2314 || (((X).n_type & N_TMASK) == (DT_NON << N_BTSHFT) \
2315 || ((X).n_type & N_TMASK) == (DT_FCN << N_BTSHFT))))
2316 # define GCC_UNDEF_SYMBOL(X) \
2317 (((X).n_sclass == C_EXT || (X).n_sclass == C_WEAKEXT) && \
2318 ((X).n_scnum == N_UNDEF))
2319 # else
2320 # define GCC_OK_SYMBOL(X) \
2321 (((X).n_sclass == C_EXT) && \
2322 ((X).n_scnum > N_UNDEF) && \
2323 (aix64_flag \
2324 || (((X).n_type & N_TMASK) == (DT_NON << N_BTSHFT) \
2325 || ((X).n_type & N_TMASK) == (DT_FCN << N_BTSHFT))))
2326 # define GCC_UNDEF_SYMBOL(X) \
2327 (((X).n_sclass == C_EXT) && ((X).n_scnum == N_UNDEF))
2328 # endif
2329 # define GCC_SYMINC(X) ((X).n_numaux+1)
2330 # define GCC_SYMZERO(X) 0
2332 /* 0757 = U803XTOCMAGIC (AIX 4.3) and 0767 = U64_TOCMAGIC (AIX V5) */
2333 #ifdef _AIX51
2334 # define GCC_CHECK_HDR(X) \
2335 ((HEADER (X).f_magic == U802TOCMAGIC && ! aix64_flag) \
2336 || (HEADER (X).f_magic == 0767 && aix64_flag))
2337 #else
2338 # define GCC_CHECK_HDR(X) \
2339 ((HEADER (X).f_magic == U802TOCMAGIC && ! aix64_flag) \
2340 || (HEADER (X).f_magic == 0757 && aix64_flag))
2341 #endif
2343 #endif
2345 #ifdef COLLECT_EXPORT_LIST
2346 /* Array of standard AIX libraries which should not
2347 be scanned for ctors/dtors. */
2348 static const char *const aix_std_libs[] = {
2349 "/unix",
2350 "/lib/libc.a",
2351 "/lib/libm.a",
2352 "/lib/libc_r.a",
2353 "/lib/libm_r.a",
2354 "/usr/lib/libc.a",
2355 "/usr/lib/libm.a",
2356 "/usr/lib/libc_r.a",
2357 "/usr/lib/libm_r.a",
2358 "/usr/lib/threads/libc.a",
2359 "/usr/ccs/lib/libc.a",
2360 "/usr/ccs/lib/libm.a",
2361 "/usr/ccs/lib/libc_r.a",
2362 "/usr/ccs/lib/libm_r.a",
2363 NULL
2366 /* This function checks the filename and returns 1
2367 if this name matches the location of a standard AIX library. */
2368 static int ignore_library (const char *);
2369 static int
2370 ignore_library (const char *name)
2372 const char *const *p = &aix_std_libs[0];
2373 while (*p++ != NULL)
2374 if (! strcmp (name, *p)) return 1;
2375 return 0;
2377 #endif /* COLLECT_EXPORT_LIST */
2379 #if defined (HAVE_DECL_LDGETNAME) && !HAVE_DECL_LDGETNAME
2380 extern char *ldgetname (LDFILE *, GCC_SYMENT *);
2381 #endif
2383 /* COFF version to scan the name list of the loaded program for
2384 the symbols g++ uses for static constructors and destructors.
2386 The constructor table begins at __CTOR_LIST__ and contains a count
2387 of the number of pointers (or -1 if the constructors are built in a
2388 separate section by the linker), followed by the pointers to the
2389 constructor functions, terminated with a null pointer. The
2390 destructor table has the same format, and begins at __DTOR_LIST__. */
2392 static void
2393 scan_prog_file (const char *prog_name, enum pass which_pass)
2395 LDFILE *ldptr = NULL;
2396 int sym_index, sym_count;
2397 int is_shared = 0;
2399 if (which_pass != PASS_FIRST && which_pass != PASS_OBJ)
2400 return;
2402 #ifdef COLLECT_EXPORT_LIST
2403 /* We do not need scanning for some standard C libraries. */
2404 if (which_pass == PASS_FIRST && ignore_library (prog_name))
2405 return;
2407 /* On AIX we have a loop, because there is not much difference
2408 between an object and an archive. This trick allows us to
2409 eliminate scan_libraries() function. */
2412 #endif
2413 /* Some platforms (e.g. OSF4) declare ldopen as taking a
2414 non-const char * filename parameter, even though it will not
2415 modify that string. So we must cast away const-ness here,
2416 which will cause -Wcast-qual to burp. */
2417 if ((ldptr = ldopen ((char *)prog_name, ldptr)) != NULL)
2419 if (! MY_ISCOFF (HEADER (ldptr).f_magic))
2420 fatal ("%s: not a COFF file", prog_name);
2422 if (GCC_CHECK_HDR (ldptr))
2424 sym_count = GCC_SYMBOLS (ldptr);
2425 sym_index = GCC_SYMZERO (ldptr);
2427 #ifdef COLLECT_EXPORT_LIST
2428 /* Is current archive member a shared object? */
2429 is_shared = HEADER (ldptr).f_flags & F_SHROBJ;
2430 #endif
2432 while (sym_index < sym_count)
2434 GCC_SYMENT symbol;
2436 if (ldtbread (ldptr, sym_index, &symbol) <= 0)
2437 break;
2438 sym_index += GCC_SYMINC (symbol);
2440 if (GCC_OK_SYMBOL (symbol))
2442 char *name;
2444 if ((name = ldgetname (ldptr, &symbol)) == NULL)
2445 continue; /* Should never happen. */
2447 #ifdef XCOFF_DEBUGGING_INFO
2448 /* All AIX function names have a duplicate entry
2449 beginning with a dot. */
2450 if (*name == '.')
2451 ++name;
2452 #endif
2454 switch (is_ctor_dtor (name))
2456 case 1:
2457 if (! is_shared)
2458 add_to_list (&constructors, name);
2459 #if defined (COLLECT_EXPORT_LIST) && !defined (LD_INIT_SWITCH)
2460 if (which_pass == PASS_OBJ)
2461 add_to_list (&exports, name);
2462 #endif
2463 break;
2465 case 2:
2466 if (! is_shared)
2467 add_to_list (&destructors, name);
2468 #if defined (COLLECT_EXPORT_LIST) && !defined (LD_INIT_SWITCH)
2469 if (which_pass == PASS_OBJ)
2470 add_to_list (&exports, name);
2471 #endif
2472 break;
2474 #ifdef COLLECT_EXPORT_LIST
2475 case 3:
2476 #ifndef LD_INIT_SWITCH
2477 if (is_shared)
2478 add_to_list (&constructors, name);
2479 #endif
2480 break;
2482 case 4:
2483 #ifndef LD_INIT_SWITCH
2484 if (is_shared)
2485 add_to_list (&destructors, name);
2486 #endif
2487 break;
2488 #endif
2490 case 5:
2491 if (! is_shared)
2492 add_to_list (&frame_tables, name);
2493 #if defined (COLLECT_EXPORT_LIST) && !defined (LD_INIT_SWITCH)
2494 if (which_pass == PASS_OBJ)
2495 add_to_list (&exports, name);
2496 #endif
2497 break;
2499 default: /* not a constructor or destructor */
2500 #ifdef COLLECT_EXPORT_LIST
2501 /* Explicitly export all global symbols when
2502 building a shared object on AIX, but do not
2503 re-export symbols from another shared object
2504 and do not export symbols if the user
2505 provides an explicit export list. */
2506 if (shared_obj && !is_shared
2507 && which_pass == PASS_OBJ && !export_flag)
2508 add_to_list (&exports, name);
2509 #endif
2510 continue;
2513 if (debug)
2514 #if !defined(EXTENDED_COFF)
2515 fprintf (stderr, "\tsec=%d class=%d type=%s%o %s\n",
2516 symbol.n_scnum, symbol.n_sclass,
2517 (symbol.n_type ? "0" : ""), symbol.n_type,
2518 name);
2519 #else
2520 fprintf (stderr,
2521 "\tiss = %5d, value = %5ld, index = %5d, name = %s\n",
2522 symbol.iss, (long) symbol.value, symbol.index, name);
2523 #endif
2527 #ifdef COLLECT_EXPORT_LIST
2528 else
2530 /* If archive contains both 32-bit and 64-bit objects,
2531 we want to skip objects in other mode so mismatch normal. */
2532 if (debug)
2533 fprintf (stderr, "%s : magic=%o aix64=%d mismatch\n",
2534 prog_name, HEADER (ldptr).f_magic, aix64_flag);
2536 #endif
2538 else
2540 fatal ("%s: cannot open as COFF file", prog_name);
2542 #ifdef COLLECT_EXPORT_LIST
2543 /* On AIX loop continues while there are more members in archive. */
2545 while (ldclose (ldptr) == FAILURE);
2546 #else
2547 /* Otherwise we simply close ldptr. */
2548 (void) ldclose(ldptr);
2549 #endif
2551 #endif /* OBJECT_FORMAT_COFF */
2553 #ifdef COLLECT_EXPORT_LIST
2554 /* Given a library name without "lib" prefix, this function
2555 returns a full library name including a path. */
2556 static char *
2557 resolve_lib_name (const char *name)
2559 char *lib_buf;
2560 int i, j, l = 0;
2562 for (i = 0; libpaths[i]; i++)
2563 if (libpaths[i]->max_len > l)
2564 l = libpaths[i]->max_len;
2566 lib_buf = xmalloc (l + strlen(name) + 10);
2568 for (i = 0; libpaths[i]; i++)
2570 struct prefix_list *list = libpaths[i]->plist;
2571 for (; list; list = list->next)
2573 /* The following lines are needed because path_prefix list
2574 may contain directories both with trailing '/' and
2575 without it. */
2576 const char *p = "";
2577 if (list->prefix[strlen(list->prefix)-1] != '/')
2578 p = "/";
2579 for (j = 0; libexts[j]; j++)
2581 sprintf (lib_buf, "%s%slib%s.%s",
2582 list->prefix, p, name, libexts[j]);
2583 if (debug) fprintf (stderr, "searching for: %s\n", lib_buf);
2584 if (file_exists (lib_buf))
2586 if (debug) fprintf (stderr, "found: %s\n", lib_buf);
2587 return (lib_buf);
2592 if (debug)
2593 fprintf (stderr, "not found\n");
2594 else
2595 fatal ("library lib%s not found", name);
2596 return (NULL);
2598 #endif /* COLLECT_EXPORT_LIST */