Renamed hppaosf.mh to hppaelf.mh
[deliverable/binutils-gdb.git] / ld / ldmisc.c
1 /* ldmisc.c
2 Copyright (C) 1991, 1993 Free Software Foundation, Inc.
3
4 Written by Steve Chamberlain of Cygnus Support.
5
6 This file is part of GLD, the Gnu Linker.
7
8 GLD is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2, or (at your option)
11 any later version.
12
13 GLD is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with GLD; see the file COPYING. If not, write to
20 the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
21
22 #include "bfd.h"
23 #include "sysdep.h"
24 #include <varargs.h>
25 #include <demangle.h>
26
27 #include "ld.h"
28 #include "ldmisc.h"
29 #include "ldexp.h"
30 #include "ldlang.h"
31 #include "ldlex.h"
32 #include "ldmain.h"
33 #include "ldfile.h"
34
35 /* VARARGS*/
36 static void finfo ();
37 static const char *demangle PARAMS ((const char *string,
38 int remove_underscore));
39
40 /*
41 %% literal %
42 %F error is fatal
43 %P print program name
44 %S print script file and linenumber
45 %E current bfd error or errno
46 %I filename from a lang_input_statement_type
47 %B filename from a bfd
48 %T symbol name
49 %X no object output, fail return
50 %V hex bfd_vma
51 %v hex bfd_vma, no leading zeros
52 %C Clever filename:linenumber
53 %R info about a relent
54 %s arbitrary string, like printf
55 %d integer, like printf
56 */
57
58 static const char *
59 demangle (string, remove_underscore)
60 const char *string;
61 int remove_underscore;
62 {
63 const char *res;
64 if (remove_underscore && output_bfd)
65 {
66 if (bfd_get_symbol_leading_char (output_bfd) == string[0])
67 string++;
68 }
69 /* Note that there's a memory leak here, we keep buying memory
70 for demangled names, and never free. But if you have so many
71 errors that you run out of VM with the error messages, then
72 there's something up */
73 res = cplus_demangle (string, DMGL_ANSI|DMGL_PARAMS);
74 return res ? res : string;
75 }
76
77 static void
78 vfinfo(fp, fmt, arg)
79 FILE *fp;
80 char *fmt;
81 va_list arg;
82 {
83 boolean fatal = false;
84
85 while (*fmt)
86 {
87 while (*fmt != '%' && *fmt != '\0')
88 {
89 putc(*fmt, fp);
90 fmt++;
91 }
92
93 if (*fmt == '%')
94 {
95 fmt ++;
96 switch (*fmt++)
97 {
98 default:
99 fprintf(fp,"%%%c", fmt[-1]);
100 break;
101
102 case '%':
103 /* literal % */
104 putc('%', fp);
105 break;
106
107 case 'X':
108 /* no object output, fail return */
109 config.make_executable = false;
110 break;
111
112 case 'V':
113 /* hex bfd_vma */
114 {
115 bfd_vma value = va_arg(arg, bfd_vma);
116 fprintf_vma(fp, value);
117 }
118 break;
119
120 case 'v':
121 /* hex bfd_vma, no leading zeros */
122 {
123 char buf[100];
124 char *p = buf;
125 bfd_vma value = va_arg (arg, bfd_vma);
126 sprintf_vma (p, value);
127 while (*p == '0')
128 p++;
129 if (!*p)
130 p--;
131 fputs (p, fp);
132 }
133 break;
134
135 case 'T':
136 /* Symbol name. */
137 {
138 const char *name = va_arg (arg, const char *);
139
140 if (name != (const char *) NULL)
141 fprintf (fp, "%s", demangle (name, 1));
142 else
143 fprintf (fp, "no symbol");
144 }
145 break;
146
147 case 'B':
148 /* filename from a bfd */
149 {
150 bfd *abfd = va_arg(arg, bfd *);
151 if (abfd->my_archive) {
152 fprintf(fp,"%s(%s)", abfd->my_archive->filename,
153 abfd->filename);
154 }
155 else {
156 fprintf(fp,"%s", abfd->filename);
157 }
158 }
159 break;
160
161 case 'F':
162 /* error is fatal */
163 fatal = true;
164 break;
165
166 case 'P':
167 /* print program name */
168 fprintf(fp,"%s", program_name);
169 break;
170
171 case 'E':
172 /* current bfd error or errno */
173 fprintf(fp, bfd_errmsg(bfd_error));
174 break;
175
176 case 'I':
177 /* filename from a lang_input_statement_type */
178 {
179 lang_input_statement_type *i =
180 va_arg(arg,lang_input_statement_type *);
181
182 if (i->the_bfd->my_archive)
183 fprintf(fp, "(%s)", i->the_bfd->my_archive->filename);
184 fprintf(fp,"%s", i->local_sym_name);
185 }
186 break;
187
188 case 'S':
189 /* print script file and linenumber */
190 {
191 if (ldfile_input_filename == (char *)NULL) {
192 fprintf(fp,"command line");
193 }
194 else {
195 fprintf(fp,"%s:%u", ldfile_input_filename, lineno );
196 }
197 }
198 break;
199
200 case 'R':
201 /* Print all that's interesting about a relent */
202 {
203 arelent *relent = va_arg(arg, arelent *);
204
205 finfo (fp, "%s+0x%v (type %s)",
206 (*(relent->sym_ptr_ptr))->name,
207 relent->addend,
208 relent->howto->name);
209 }
210 break;
211
212 case 'C':
213 /* Clever filename:linenumber with function name if possible,
214 or section name as a last resort. The arguments are a BFD,
215 a section, and an offset. */
216 {
217 bfd *abfd;
218 asection *section;
219 bfd_vma offset;
220 lang_input_statement_type *entry;
221 asymbol **asymbols;
222 const char *filename;
223 const char *functionname;
224 unsigned int linenumber;
225
226 abfd = va_arg (arg, bfd *);
227 section = va_arg (arg, asection *);
228 offset = va_arg (arg, bfd_vma);
229
230 entry = (lang_input_statement_type *) abfd->usrdata;
231 if (entry != (lang_input_statement_type *) NULL
232 && entry->asymbols != (asymbol **) NULL)
233 asymbols = entry->asymbols;
234 else
235 {
236 unsigned int symsize;
237 unsigned int symbol_count;
238
239 symsize = get_symtab_upper_bound (abfd);
240 asymbols = (asymbol **) ldmalloc (symsize);
241 symbol_count = bfd_canonicalize_symtab (abfd, asymbols);
242 if (entry != (lang_input_statement_type *) NULL)
243 {
244 entry->asymbols = asymbols;
245 entry->symbol_count = symbol_count;
246 }
247 }
248
249 if (bfd_find_nearest_line (abfd, section, asymbols, offset,
250 &filename, &functionname, &linenumber))
251 {
252 if (filename == (char *) NULL)
253 filename = abfd->filename;
254
255 if (functionname != (char *)NULL)
256 fprintf (fp, "%s:%u: %s", filename, linenumber,
257 demangle (functionname, 1));
258 else if (linenumber != 0)
259 fprintf (fp, "%s:%u", filename, linenumber);
260 else
261 finfo (fp, "%s(%s+0x%v)", filename, section->name, offset);
262
263 }
264 else
265 finfo (fp, "%s(%s+0x%v)", abfd->filename, section->name, offset);
266 }
267 break;
268
269 case 's':
270 /* arbitrary string, like printf */
271 fprintf(fp,"%s", va_arg(arg, char *));
272 break;
273
274 case 'd':
275 /* integer, like printf */
276 fprintf(fp,"%d", va_arg(arg, int));
277 break;
278 }
279 }
280 }
281
282 if (fatal == true)
283 {
284 if (output_filename)
285 {
286 if (output_bfd && output_bfd->iostream)
287 fclose((FILE *)(output_bfd->iostream));
288 if (delete_output_file_on_failure)
289 unlink (output_filename);
290 }
291 exit(1);
292 }
293 }
294
295 /* Format info message and print on stdout. */
296
297 /* (You would think this should be called just "info", but then you would
298 hosed by LynxOS, which defines that name in its libc.) */
299
300 void info_msg(va_alist)
301 va_dcl
302 {
303 char *fmt;
304 va_list arg;
305 va_start(arg);
306 fmt = va_arg(arg, char *);
307 vfinfo(stdout, fmt, arg);
308 va_end(arg);
309 }
310
311 /* ('e' for error.) Format info message and print on stderr. */
312
313 void einfo(va_alist)
314 va_dcl
315 {
316 char *fmt;
317 va_list arg;
318 va_start(arg);
319 fmt = va_arg(arg, char *);
320 vfinfo(stderr, fmt, arg);
321 va_end(arg);
322 }
323
324 /* Warn about a symbol NEWSYM being multiply defined with another symbol OLDSYM.
325 MESSAGE1 and MESSAGE2 should look something like:
326 "%C: warning: multiple commons of `%s'\n"
327 "%C: warning: previous common here\n" */
328
329 void
330 multiple_warn (message1, newsym, message2, oldsym)
331 char *message1;
332 asymbol *newsym;
333 char *message2;
334 asymbol *oldsym;
335 {
336 lang_input_statement_type *inp_stat;
337 asymbol **stat_symbols;
338
339 inp_stat = (lang_input_statement_type *) bfd_asymbol_bfd (newsym)->usrdata;
340 stat_symbols = inp_stat ? inp_stat->asymbols : 0;
341
342 einfo (message1,
343 bfd_asymbol_bfd (newsym), newsym->section, stat_symbols, newsym->value,
344 demangle (newsym->name, 1));
345
346 inp_stat = (lang_input_statement_type *) bfd_asymbol_bfd (oldsym)->usrdata;
347 stat_symbols = inp_stat ? inp_stat->asymbols : 0;
348
349 einfo (message2,
350 bfd_asymbol_bfd (oldsym), oldsym->section, stat_symbols, oldsym->value);
351 }
352
353 void
354 info_assert(file, line)
355 char *file;
356 unsigned int line;
357 {
358 einfo("%F%P: internal error %s %d\n", file,line);
359 }
360
361 /* Return a newly-allocated string
362 whose contents concatenate those of S1, S2, S3. */
363
364 char *
365 concat (s1, s2, s3)
366 CONST char *s1;
367 CONST char *s2;
368 CONST char *s3;
369 {
370 size_t len1 = strlen (s1);
371 size_t len2 = strlen (s2);
372 size_t len3 = strlen (s3);
373 char *result = ldmalloc (len1 + len2 + len3 + 1);
374
375 if (len1 != 0)
376 memcpy(result, s1, len1);
377 if (len2 != 0)
378 memcpy(result+len1, s2, len2);
379 if (len3 != 0)
380 memcpy(result+len1+len2, s2, len3);
381 *(result + len1 + len2 + len3) = 0;
382
383 return result;
384 }
385
386
387 PTR
388 ldmalloc (size)
389 size_t size;
390 {
391 PTR result = malloc ((int)size);
392
393 if (result == (char *)NULL && size != 0)
394 einfo("%F%P: virtual memory exhausted\n");
395
396 return result;
397 }
398
399 PTR
400 xmalloc (size)
401 int size;
402 {
403 return ldmalloc ((size_t) size);
404 }
405
406
407 PTR
408 ldrealloc (ptr, size)
409 PTR ptr;
410 size_t size;
411 {
412 PTR result = realloc (ptr, (int)size);
413
414 if (result == (char *)NULL && size != 0)
415 einfo("%F%P: virtual memory exhausted\n");
416
417 return result;
418 }
419
420 PTR
421 xrealloc (ptr, size)
422 PTR ptr;
423 int size;
424 {
425 return ldrealloc (ptr, (size_t) size);
426 }
427
428
429 char *
430 buystring (x)
431 CONST char *CONST x;
432 {
433 size_t l = strlen(x)+1;
434 char *r = ldmalloc(l);
435 memcpy(r, x,l);
436 return r;
437 }
438
439
440 /* ('m' for map) Format info message and print on map. */
441
442 void minfo(va_alist)
443 va_dcl
444 {
445 char *fmt;
446 va_list arg;
447 va_start(arg);
448 fmt = va_arg(arg, char *);
449 vfinfo(config.map_file, fmt, arg);
450 va_end(arg);
451 }
452
453
454 static void
455 finfo (va_alist)
456 va_dcl
457 {
458 char *fmt;
459 FILE *file;
460 va_list arg;
461 va_start (arg);
462 file = va_arg (arg, FILE *);
463 fmt = va_arg (arg, char *);
464 vfinfo (file, fmt, arg);
465 va_end (arg);
466 }
467
468
469
470 /*----------------------------------------------------------------------
471 Functions to print the link map
472 */
473
474 void
475 print_space ()
476 {
477 fprintf(config.map_file, " ");
478 }
479 void
480 print_nl ()
481 {
482 fprintf(config.map_file, "\n");
483 }
484 void
485 print_address (value)
486 bfd_vma value;
487 {
488 fprintf_vma(config.map_file, value);
489 }
This page took 0.037863 seconds and 4 git commands to generate.