]> git.ipfire.org Git - thirdparty/gcc.git/blame - gcc/tlink.c
Merge from pch-branch up to tag pch-commit-20020603.
[thirdparty/gcc.git] / gcc / tlink.c
CommitLineData
aa32d841
JL
1/* Scan linker error messages for missing template instantiations and provide
2 them.
3
d6edb99e 4 Copyright (C) 1995, 1998, 1999, 2000, 2001 Free Software Foundation, Inc.
aa32d841
JL
5 Contributed by Jason Merrill (jason@cygnus.com).
6
1322177d 7This file is part of GCC.
aa32d841 8
1322177d
LB
9GCC is free software; you can redistribute it and/or modify it under
10the terms of the GNU General Public License as published by the Free
11Software Foundation; either version 2, or (at your option) any later
12version.
aa32d841 13
1322177d
LB
14GCC is distributed in the hope that it will be useful, but WITHOUT ANY
15WARRANTY; without even the implied warranty of MERCHANTABILITY or
16FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
17for more details.
aa32d841
JL
18
19You should have received a copy of the GNU General Public License
1322177d
LB
20along with GCC; see the file COPYING. If not, write to the Free
21Software Foundation, 59 Temple Place - Suite 330, Boston, MA
2202111-1307, USA. */
aa32d841 23
aa32d841 24#include "config.h"
670ee920 25#include "system.h"
993c790e 26#include "intl.h"
e2500fed
GK
27#include "obstack.h"
28#include "hashtab.h"
aa32d841 29#include "demangle.h"
2edfd4ee 30#include "collect2.h"
aa32d841
JL
31
32#define MAX_ITERATIONS 17
33
34/* Obstack allocation and deallocation routines. */
35#define obstack_chunk_alloc xmalloc
36#define obstack_chunk_free free
37
aa32d841
JL
38/* Defined in the automatically-generated underscore.c. */
39extern int prepends_underscore;
40
41static int tlink_verbose;
42\f
e2500fed 43/* Hash table boilerplate for working with htab_t. We have hash tables
eb686064 44 for symbol names, file names, and demangled symbols. */
aa32d841
JL
45
46typedef struct symbol_hash_entry
47{
e2500fed 48 const char *key;
aa32d841
JL
49 struct file_hash_entry *file;
50 int chosen;
51 int tweaking;
52 int tweaked;
53} symbol;
54
55typedef struct file_hash_entry
56{
e2500fed 57 const char *key;
aa32d841
JL
58 const char *args;
59 const char *dir;
60 const char *main;
61 int tweaking;
62} file;
63
64typedef struct demangled_hash_entry
65{
e2500fed 66 const char *key;
aa32d841
JL
67 const char *mangled;
68} demangled;
69
e2500fed
GK
70/* Hash and comparison functions for these hash tables. */
71
72static int hash_string_eq PARAMS ((const void *, const void *));
73static hashval_t hash_string_hash PARAMS ((const void *));
74
75static int
76hash_string_eq (s1_p, s2_p)
77 const void *s1_p;
78 const void *s2_p;
79{
80 const char *const *s1 = (const char *const *)s1_p;
81 const char *s2 = (const char *)s2_p;
82 return strcmp (*s1, s2) == 0;
83}
84
85static hashval_t
86hash_string_hash (s_p)
87 const void *s_p;
88{
89 const char *const *s = (const char *const *)s_p;
90 return (*htab_hash_string) (*s);
91}
92
93static htab_t symbol_table;
aa32d841 94
54ea1de9 95static struct symbol_hash_entry * symbol_hash_lookup PARAMS ((const char *,
37a58036 96 int));
54ea1de9 97static struct file_hash_entry * file_hash_lookup PARAMS ((const char *));
54ea1de9 98static struct demangled_hash_entry *
37a58036 99 demangled_hash_lookup PARAMS ((const char *, int));
54ea1de9
KG
100static void symbol_push PARAMS ((symbol *));
101static symbol * symbol_pop PARAMS ((void));
102static void file_push PARAMS ((file *));
103static file * file_pop PARAMS ((void));
104static void tlink_init PARAMS ((void));
d4058195
KG
105static int tlink_execute PARAMS ((const char *, char **, const char *));
106static char * frob_extension PARAMS ((const char *, const char *));
54ea1de9
KG
107static char * obstack_fgets PARAMS ((FILE *, struct obstack *));
108static char * tfgets PARAMS ((FILE *));
109static char * pfgets PARAMS ((FILE *));
110static void freadsym PARAMS ((FILE *, file *, int));
111static void read_repo_file PARAMS ((file *));
112static void maybe_tweak PARAMS ((char *, file *));
113static int recompile_files PARAMS ((void));
114static int read_repo_files PARAMS ((char **));
115static void demangle_new_symbols PARAMS ((void));
116static int scan_linker_output PARAMS ((const char *));
117
eb686064
JM
118/* Look up an entry in the symbol hash table. */
119
aa32d841
JL
120static struct symbol_hash_entry *
121symbol_hash_lookup (string, create)
122 const char *string;
37a58036 123 int create;
aa32d841 124{
e2500fed
GK
125 PTR *e;
126 e = htab_find_slot_with_hash (symbol_table, string,
127 (*htab_hash_string)(string),
128 create ? INSERT : NO_INSERT);
129 if (e == NULL)
130 return NULL;
131 if (*e == NULL)
aa32d841 132 {
e2500fed
GK
133 struct symbol_hash_entry *v;
134 *e = v = xcalloc (1, sizeof (*v));
135 v->key = xstrdup (string);
aa32d841 136 }
e2500fed 137 return *e;
aa32d841
JL
138}
139
e2500fed
GK
140static htab_t file_table;
141
eb686064
JM
142/* Look up an entry in the file hash table. */
143
aa32d841
JL
144static struct file_hash_entry *
145file_hash_lookup (string)
146 const char *string;
147{
e2500fed
GK
148 PTR *e;
149 e = htab_find_slot_with_hash (file_table, string,
150 (*htab_hash_string)(string),
151 INSERT);
152 if (*e == NULL)
aa32d841 153 {
e2500fed
GK
154 struct file_hash_entry *v;
155 *e = v = xcalloc (1, sizeof (*v));
156 v->key = xstrdup (string);
aa32d841 157 }
e2500fed 158 return *e;
aa32d841
JL
159}
160
e2500fed
GK
161static htab_t demangled_table;
162
eb686064
JM
163/* Look up an entry in the demangled name hash table. */
164
aa32d841
JL
165static struct demangled_hash_entry *
166demangled_hash_lookup (string, create)
167 const char *string;
37a58036 168 int create;
aa32d841 169{
e2500fed
GK
170 PTR *e;
171 e = htab_find_slot_with_hash (demangled_table, string,
172 (*htab_hash_string)(string),
173 create ? INSERT : NO_INSERT);
174 if (e == NULL)
175 return NULL;
176 if (*e == NULL)
177 {
178 struct demangled_hash_entry *v;
179 *e = v = xcalloc (1, sizeof (*v));
180 v->key = xstrdup (string);
181 }
182 return *e;
aa32d841
JL
183}
184\f
185/* Stack code. */
186
187struct symbol_stack_entry
188{
189 symbol *value;
190 struct symbol_stack_entry *next;
191};
192struct obstack symbol_stack_obstack;
193struct symbol_stack_entry *symbol_stack;
194
195struct file_stack_entry
196{
197 file *value;
198 struct file_stack_entry *next;
199};
200struct obstack file_stack_obstack;
201struct file_stack_entry *file_stack;
202
203static void
204symbol_push (p)
205 symbol *p;
206{
207 struct symbol_stack_entry *ep = (struct symbol_stack_entry *) obstack_alloc
208 (&symbol_stack_obstack, sizeof (struct symbol_stack_entry));
209 ep->value = p;
210 ep->next = symbol_stack;
211 symbol_stack = ep;
212}
213
214static symbol *
215symbol_pop ()
216{
217 struct symbol_stack_entry *ep = symbol_stack;
218 symbol *p;
219 if (ep == NULL)
220 return NULL;
221 p = ep->value;
222 symbol_stack = ep->next;
223 obstack_free (&symbol_stack_obstack, ep);
224 return p;
225}
226
227static void
228file_push (p)
229 file *p;
230{
231 struct file_stack_entry *ep;
232
233 if (p->tweaking)
234 return;
235
236 ep = (struct file_stack_entry *) obstack_alloc
237 (&file_stack_obstack, sizeof (struct file_stack_entry));
238 ep->value = p;
239 ep->next = file_stack;
240 file_stack = ep;
241 p->tweaking = 1;
242}
243
244static file *
245file_pop ()
246{
247 struct file_stack_entry *ep = file_stack;
248 file *p;
249 if (ep == NULL)
250 return NULL;
251 p = ep->value;
252 file_stack = ep->next;
253 obstack_free (&file_stack_obstack, ep);
254 p->tweaking = 0;
255 return p;
256}
257\f
258/* Other machinery. */
259
eb686064
JM
260/* Initialize the tlink machinery. Called from do_tlink. */
261
aa32d841
JL
262static void
263tlink_init ()
264{
d4058195 265 const char *p;
aa32d841 266
e2500fed
GK
267 symbol_table = htab_create (500, hash_string_hash, hash_string_eq,
268 NULL);
269 file_table = htab_create (500, hash_string_hash, hash_string_eq,
270 NULL);
271 demangled_table = htab_create (500, hash_string_hash, hash_string_eq,
272 NULL);
273
aa32d841
JL
274 obstack_begin (&symbol_stack_obstack, 0);
275 obstack_begin (&file_stack_obstack, 0);
276
277 p = getenv ("TLINK_VERBOSE");
278 if (p)
279 tlink_verbose = atoi (p);
280 else
281 {
282 tlink_verbose = 1;
283 if (vflag)
284 tlink_verbose = 2;
285 if (debug)
286 tlink_verbose = 3;
287 }
288}
289
290static int
291tlink_execute (prog, argv, redir)
d4058195 292 const char *prog;
aa32d841 293 char **argv;
d4058195 294 const char *redir;
aa32d841
JL
295{
296 collect_execute (prog, argv, redir);
297 return collect_wait (prog);
d92b4486 298}
aa32d841
JL
299
300static char *
301frob_extension (s, ext)
d4058195 302 const char *s;
54ea1de9 303 const char *ext;
aa32d841 304{
9473c522 305 const char *p = strrchr (s, '/');
aa32d841
JL
306 if (! p)
307 p = s;
9473c522 308 p = strrchr (p, '.');
aa32d841
JL
309 if (! p)
310 p = s + strlen (s);
311
312 obstack_grow (&temporary_obstack, s, p - s);
313 return obstack_copy0 (&temporary_obstack, ext, strlen (ext));
314}
315
316static char *
317obstack_fgets (stream, ob)
318 FILE *stream;
319 struct obstack *ob;
320{
321 int c;
322 while ((c = getc (stream)) != EOF && c != '\n')
323 obstack_1grow (ob, c);
324 if (obstack_object_size (ob) == 0)
325 return NULL;
326 obstack_1grow (ob, '\0');
327 return obstack_finish (ob);
328}
329
330static char *
331tfgets (stream)
332 FILE *stream;
333{
334 return obstack_fgets (stream, &temporary_obstack);
335}
336
337static char *
338pfgets (stream)
339 FILE *stream;
340{
341 return obstack_fgets (stream, &permanent_obstack);
342}
343\f
344/* Real tlink code. */
345
eb686064
JM
346/* Subroutine of read_repo_file. We are reading the repo file for file F,
347 which is coming in on STREAM, and the symbol that comes next in STREAM
348 is offerred, chosen or provided if CHOSEN is 0, 1 or 2, respectively.
349
350 XXX "provided" is unimplemented, both here and in the compiler. */
351
aa32d841
JL
352static void
353freadsym (stream, f, chosen)
354 FILE *stream;
355 file *f;
356 int chosen;
357{
358 symbol *sym;
359
360 {
d4058195 361 const char *name = tfgets (stream);
aa32d841
JL
362 sym = symbol_hash_lookup (name, true);
363 }
364
365 if (sym->file == NULL)
366 {
eb686064
JM
367 /* We didn't have this symbol already, so we choose this file. */
368
aa32d841
JL
369 symbol_push (sym);
370 sym->file = f;
371 sym->chosen = chosen;
372 }
373 else if (chosen)
374 {
eb686064
JM
375 /* We want this file; cast aside any pretender. */
376
aa32d841
JL
377 if (sym->chosen && sym->file != f)
378 {
379 if (sym->chosen == 1)
380 file_push (sym->file);
381 else
382 {
383 file_push (f);
384 f = sym->file;
385 chosen = sym->chosen;
386 }
387 }
388 sym->file = f;
389 sym->chosen = chosen;
390 }
391}
392
eb686064
JM
393/* Read in the repo file denoted by F, and record all its information. */
394
aa32d841
JL
395static void
396read_repo_file (f)
397 file *f;
398{
399 char c;
e2500fed 400 FILE *stream = fopen (f->key, "r");
aa32d841
JL
401
402 if (tlink_verbose >= 2)
e2500fed 403 fprintf (stderr, _("collect: reading %s\n"), f->key);
aa32d841
JL
404
405 while (fscanf (stream, "%c ", &c) == 1)
406 {
407 switch (c)
408 {
409 case 'A':
410 f->args = pfgets (stream);
411 break;
412 case 'D':
413 f->dir = pfgets (stream);
414 break;
415 case 'M':
416 f->main = pfgets (stream);
417 break;
418 case 'P':
419 freadsym (stream, f, 2);
420 break;
421 case 'C':
422 freadsym (stream, f, 1);
423 break;
424 case 'O':
425 freadsym (stream, f, 0);
426 break;
427 }
428 obstack_free (&temporary_obstack, temporary_firstobj);
429 }
430 fclose (stream);
431 if (f->args == NULL)
432 f->args = getenv ("COLLECT_GCC_OPTIONS");
433 if (f->dir == NULL)
434 f->dir = ".";
435}
436
eb686064
JM
437/* We might want to modify LINE, which is a symbol line from file F. We do
438 this if either we saw an error message referring to the symbol in
439 question, or we have already allocated the symbol to another file and
440 this one wants to emit it as well. */
441
aa32d841
JL
442static void
443maybe_tweak (line, f)
444 char *line;
445 file *f;
446{
447 symbol *sym = symbol_hash_lookup (line + 2, false);
448
449 if ((sym->file == f && sym->tweaking)
450 || (sym->file != f && line[0] == 'C'))
451 {
452 sym->tweaking = 0;
453 sym->tweaked = 1;
454
455 if (line[0] == 'O')
456 line[0] = 'C';
457 else
458 line[0] = 'O';
459 }
460}
461
eb686064
JM
462/* Update the repo files for each of the object files we have adjusted and
463 recompile.
464
465 XXX Should this use collect_execute instead of system? */
466
aa32d841
JL
467static int
468recompile_files ()
469{
470 file *f;
471
137bb46a
KG
472 putenv (xstrdup ("COMPILER_PATH"));
473 putenv (xstrdup ("LIBRARY_PATH"));
d92b4486 474
aa32d841
JL
475 while ((f = file_pop ()) != NULL)
476 {
477 char *line, *command;
e2500fed
GK
478 FILE *stream = fopen (f->key, "r");
479 const char *const outname = frob_extension (f->key, ".rnw");
aa32d841
JL
480 FILE *output = fopen (outname, "w");
481
482 while ((line = tfgets (stream)) != NULL)
483 {
484 switch (line[0])
485 {
486 case 'C':
487 case 'O':
488 maybe_tweak (line, f);
489 }
490 fprintf (output, "%s\n", line);
491 }
492 fclose (stream);
493 fclose (output);
e2500fed 494 rename (outname, f->key);
aa32d841
JL
495
496 obstack_grow (&temporary_obstack, "cd ", 3);
497 obstack_grow (&temporary_obstack, f->dir, strlen (f->dir));
498 obstack_grow (&temporary_obstack, "; ", 2);
499 obstack_grow (&temporary_obstack, c_file_name, strlen (c_file_name));
500 obstack_1grow (&temporary_obstack, ' ');
501 obstack_grow (&temporary_obstack, f->args, strlen (f->args));
502 obstack_1grow (&temporary_obstack, ' ');
503 command = obstack_copy0 (&temporary_obstack, f->main, strlen (f->main));
504
505 if (tlink_verbose)
5e4adfba 506 fprintf (stderr, _("collect: recompiling %s\n"), f->main);
aa32d841
JL
507 if (tlink_verbose >= 3)
508 fprintf (stderr, "%s\n", command);
509
510 if (system (command) != 0)
511 return 0;
512
513 read_repo_file (f);
514
515 obstack_free (&temporary_obstack, temporary_firstobj);
516 }
517 return 1;
518}
519
eb686064
JM
520/* The first phase of processing: determine which object files have
521 .rpo files associated with them, and read in the information. */
522
aa32d841
JL
523static int
524read_repo_files (object_lst)
525 char **object_lst;
526{
527 char **object = object_lst;
528
529 for (; *object; object++)
530 {
2c561874 531 const char *p;
aa32d841
JL
532 file *f;
533
2c561874
JM
534 /* Don't bother trying for ld flags. */
535 if (*object[0] == '-')
536 continue;
537
538 p = frob_extension (*object, ".rpo");
539
aa32d841
JL
540 if (! file_exists (p))
541 continue;
542
543 f = file_hash_lookup (p);
544
545 read_repo_file (f);
546 }
547
548 if (file_stack != NULL && ! recompile_files ())
549 return 0;
550
551 return (symbol_stack != NULL);
552}
553
eb686064
JM
554/* Add the demangled forms of any new symbols to the hash table. */
555
aa32d841
JL
556static void
557demangle_new_symbols ()
558{
559 symbol *sym;
560
561 while ((sym = symbol_pop ()) != NULL)
562 {
563 demangled *dem;
e2500fed 564 const char *p = cplus_demangle (sym->key, DMGL_PARAMS | DMGL_ANSI);
aa32d841
JL
565
566 if (! p)
567 continue;
568
569 dem = demangled_hash_lookup (p, true);
e2500fed 570 dem->mangled = sym->key;
aa32d841
JL
571 }
572}
573
eb686064
JM
574/* Step through the output of the linker, in the file named FNAME, and
575 adjust the settings for each symbol encountered. */
576
aa32d841
JL
577static int
578scan_linker_output (fname)
54ea1de9 579 const char *fname;
aa32d841
JL
580{
581 FILE *stream = fopen (fname, "r");
582 char *line;
583
584 while ((line = tfgets (stream)) != NULL)
585 {
586 char *p = line, *q;
587 symbol *sym;
588 int end;
d92b4486 589
79c9824e 590 while (*p && ISSPACE ((unsigned char)*p))
aa32d841
JL
591 ++p;
592
593 if (! *p)
594 continue;
595
79c9824e 596 for (q = p; *q && ! ISSPACE ((unsigned char)*q); ++q)
aa32d841
JL
597 ;
598
599 /* Try the first word on the line. */
600 if (*p == '.')
601 ++p;
602 if (*p == '_' && prepends_underscore)
603 ++p;
604
605 end = ! *q;
606 *q = 0;
607 sym = symbol_hash_lookup (p, false);
608
644c7c4f
GK
609 /* Some SVR4 linkers produce messages like
610 ld: 0711-317 ERROR: Undefined symbol: .g__t3foo1Zi
611 */
612 if (! sym && ! end && strstr (q+1, "Undefined symbol: "))
613 {
614 char *p = strrchr (q+1, ' ');
615 p++;
616 if (*p == '.')
617 p++;
618 if (*p == '_' && prepends_underscore)
619 p++;
620 sym = symbol_hash_lookup (p, false);
621 }
622
aa32d841 623 if (! sym && ! end)
b4558b57 624 /* Try a mangled name in quotes. */
aa32d841 625 {
d4058195 626 const char *oldq = q+1;
aa32d841 627 demangled *dem = 0;
aa32d841
JL
628 q = 0;
629
b4558b57 630 /* First try `GNU style'. */
9473c522 631 p = strchr (oldq, '`');
b4558b57 632 if (p)
9473c522 633 p++, q = strchr (p, '\'');
b4558b57 634 /* Then try "double quotes". */
9473c522
JM
635 else if (p = strchr (oldq, '"'), p)
636 p++, q = strchr (p, '"');
aa32d841 637
6ff7fb95
JM
638 /* Don't let the strstr's below see the demangled name; we
639 might get spurious matches. */
640 if (p)
641 p[-1] = '\0';
642
57be4e89
JM
643 /* We need to check for certain error keywords here, or we would
644 mistakenly use GNU ld's "In function `foo':" message. */
645 if (q && (strstr (oldq, "ndefined")
3f94eee6 646 || strstr (oldq, "nresolved")
eb20f668 647 || strstr (oldq, "nsatisfied")
57be4e89 648 || strstr (oldq, "ultiple")))
aa32d841 649 {
b4558b57
JM
650 *q = 0;
651 dem = demangled_hash_lookup (p, false);
652 if (dem)
653 sym = symbol_hash_lookup (dem->mangled, false);
654 else
d92b4486
KH
655 {
656 if (*p == '_' && prepends_underscore)
9c5b50b3
JM
657 ++p;
658 sym = symbol_hash_lookup (p, false);
659 }
aa32d841 660 }
aa32d841
JL
661 }
662
663 if (sym && sym->tweaked)
7b6ffd11
KI
664 {
665 fclose (stream);
666 return 0;
667 }
aa32d841
JL
668 if (sym && !sym->tweaking)
669 {
670 if (tlink_verbose >= 2)
5e4adfba 671 fprintf (stderr, _("collect: tweaking %s in %s\n"),
e2500fed 672 sym->key, sym->file->key);
aa32d841
JL
673 sym->tweaking = 1;
674 file_push (sym->file);
675 }
d92b4486 676
aa32d841
JL
677 obstack_free (&temporary_obstack, temporary_firstobj);
678 }
679
7b6ffd11 680 fclose (stream);
aa32d841
JL
681 return (file_stack != NULL);
682}
683
eb686064
JM
684/* Entry point for tlink. Called from main in collect2.c.
685
686 Iteratively try to provide definitions for all the unresolved symbols
687 mentioned in the linker error messages.
688
689 LD_ARGV is an array of arguments for the linker.
690 OBJECT_LST is an array of object files that we may be able to recompile
691 to provide missing definitions. Currently ignored. */
692
aa32d841
JL
693void
694do_tlink (ld_argv, object_lst)
d4058195 695 char **ld_argv, **object_lst ATTRIBUTE_UNUSED;
aa32d841
JL
696{
697 int exit = tlink_execute ("ld", ld_argv, ldout);
698
699 tlink_init ();
700
701 if (exit)
702 {
703 int i = 0;
704
705 /* Until collect does a better job of figuring out which are object
706 files, assume that everything on the command line could be. */
707 if (read_repo_files (ld_argv))
708 while (exit && i++ < MAX_ITERATIONS)
709 {
710 if (tlink_verbose >= 3)
711 dump_file (ldout);
712 demangle_new_symbols ();
713 if (! scan_linker_output (ldout))
714 break;
715 if (! recompile_files ())
716 break;
717 if (tlink_verbose)
5e4adfba 718 fprintf (stderr, _("collect: relinking\n"));
aa32d841
JL
719 exit = tlink_execute ("ld", ld_argv, ldout);
720 }
721 }
722
723 dump_file (ldout);
724 unlink (ldout);
725 if (exit)
726 {
727 error ("ld returned %d exit status", exit);
728 collect_exit (exit);
729 }
730}