/src/binutils-gdb/bfd/syms.c
Line | Count | Source |
1 | | /* Generic symbol-table support for the BFD library. |
2 | | Copyright (C) 1990-2026 Free Software Foundation, Inc. |
3 | | Written by Cygnus Support. |
4 | | |
5 | | This file is part of BFD, the Binary File Descriptor library. |
6 | | |
7 | | This program is free software; you can redistribute it and/or modify |
8 | | it under the terms of the GNU General Public License as published by |
9 | | the Free Software Foundation; either version 3 of the License, or |
10 | | (at your option) any later version. |
11 | | |
12 | | This program is distributed in the hope that it will be useful, |
13 | | but WITHOUT ANY WARRANTY; without even the implied warranty of |
14 | | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
15 | | GNU General Public License for more details. |
16 | | |
17 | | You should have received a copy of the GNU General Public License |
18 | | along with this program; if not, write to the Free Software |
19 | | Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, |
20 | | MA 02110-1301, USA. */ |
21 | | |
22 | | /* |
23 | | SECTION |
24 | | Symbols |
25 | | |
26 | | BFD tries to maintain as much symbol information as it can when |
27 | | it moves information from file to file. BFD passes information |
28 | | to applications though the <<asymbol>> structure. When the |
29 | | application requests the symbol table, BFD reads the table in |
30 | | the native form and translates parts of it into the internal |
31 | | format. To maintain more than the information passed to |
32 | | applications, some targets keep some information ``behind the |
33 | | scenes'' in a structure only the particular back end knows |
34 | | about. For example, the coff back end keeps the original |
35 | | symbol table structure as well as the canonical structure when |
36 | | a BFD is read in. On output, the coff back end can reconstruct |
37 | | the output symbol table so that no information is lost, even |
38 | | information unique to coff which BFD doesn't know or |
39 | | understand. If a coff symbol table were read, but were written |
40 | | through an a.out back end, all the coff specific information |
41 | | would be lost. The symbol table of a BFD |
42 | | is not necessarily read in until a canonicalize request is |
43 | | made. Then the BFD back end fills in a table provided by the |
44 | | application with pointers to the canonical information. To |
45 | | output symbols, the application provides BFD with a table of |
46 | | pointers to pointers to <<asymbol>>s. This allows applications |
47 | | like the linker to output a symbol as it was read, since the ``behind |
48 | | the scenes'' information will be still available. |
49 | | @menu |
50 | | @* Reading Symbols:: |
51 | | @* Writing Symbols:: |
52 | | @* Mini Symbols:: |
53 | | @* typedef asymbol:: |
54 | | @* symbol handling functions:: |
55 | | @end menu |
56 | | |
57 | | INODE |
58 | | Reading Symbols, Writing Symbols, Symbols, Symbols |
59 | | SUBSECTION |
60 | | Reading symbols |
61 | | |
62 | | There are two stages to reading a symbol table from a BFD: |
63 | | allocating storage, and the actual reading process. This is an |
64 | | excerpt from an application which reads the symbol table: |
65 | | |
66 | | | long storage_needed; |
67 | | | asymbol **symbol_table; |
68 | | | long number_of_symbols; |
69 | | | long i; |
70 | | | |
71 | | | storage_needed = bfd_get_symtab_upper_bound (abfd); |
72 | | | |
73 | | | if (storage_needed < 0) |
74 | | | FAIL |
75 | | | |
76 | | | if (storage_needed == 0) |
77 | | | return; |
78 | | | |
79 | | | symbol_table = xmalloc (storage_needed); |
80 | | | ... |
81 | | | number_of_symbols = |
82 | | | bfd_canonicalize_symtab (abfd, symbol_table); |
83 | | | |
84 | | | if (number_of_symbols < 0) |
85 | | | FAIL |
86 | | | |
87 | | | for (i = 0; i < number_of_symbols; i++) |
88 | | | process_symbol (symbol_table[i]); |
89 | | |
90 | | All storage for the symbols themselves is in an objalloc |
91 | | connected to the BFD; it is freed when the BFD is closed. |
92 | | |
93 | | INODE |
94 | | Writing Symbols, Mini Symbols, Reading Symbols, Symbols |
95 | | SUBSECTION |
96 | | Writing symbols |
97 | | |
98 | | Writing of a symbol table is automatic when a BFD open for |
99 | | writing is closed. The application attaches a vector of |
100 | | pointers to pointers to symbols to the BFD being written, and |
101 | | fills in the symbol count. The close and cleanup code reads |
102 | | through the table provided and performs all the necessary |
103 | | operations. The BFD output code must always be provided with an |
104 | | ``owned'' symbol: one which has come from another BFD, or one |
105 | | which has been created using <<bfd_make_empty_symbol>>. Here is an |
106 | | example showing the creation of a symbol table with only one element: |
107 | | |
108 | | | #include "sysdep.h" |
109 | | | #include "bfd.h" |
110 | | | int main (void) |
111 | | | { |
112 | | | bfd *abfd; |
113 | | | asymbol *ptrs[2]; |
114 | | | asymbol *new; |
115 | | | |
116 | | | abfd = bfd_openw ("foo","a.out-sunos-big"); |
117 | | | bfd_set_format (abfd, bfd_object); |
118 | | | new = bfd_make_empty_symbol (abfd); |
119 | | | new->name = "dummy_symbol"; |
120 | | | new->section = bfd_make_section_old_way (abfd, ".text"); |
121 | | | new->flags = BSF_GLOBAL; |
122 | | | new->value = 0x12345; |
123 | | | |
124 | | | ptrs[0] = new; |
125 | | | ptrs[1] = 0; |
126 | | | |
127 | | | bfd_set_symtab (abfd, ptrs, 1); |
128 | | | bfd_close (abfd); |
129 | | | return 0; |
130 | | | } |
131 | | | |
132 | | | ./makesym |
133 | | | nm foo |
134 | | | 00012345 A dummy_symbol |
135 | | |
136 | | Many formats cannot represent arbitrary symbol information; for |
137 | | instance, the <<a.out>> object format does not allow an |
138 | | arbitrary number of sections. A symbol pointing to a section |
139 | | which is not one of <<.text>>, <<.data>> or <<.bss>> cannot |
140 | | be described. |
141 | | |
142 | | INODE |
143 | | Mini Symbols, typedef asymbol, Writing Symbols, Symbols |
144 | | SUBSECTION |
145 | | Mini Symbols |
146 | | |
147 | | Mini symbols provide read-only access to the symbol table. |
148 | | They use less memory space, but require more time to access. |
149 | | They can be useful for tools like nm or objdump, which may |
150 | | have to handle symbol tables of extremely large executables. |
151 | | |
152 | | The <<bfd_read_minisymbols>> function will read the symbols |
153 | | into memory in an internal form. It will return a <<void *>> |
154 | | pointer to a block of memory, a symbol count, and the size of |
155 | | each symbol. The pointer is allocated using <<malloc>>, and |
156 | | should be freed by the caller when it is no longer needed. |
157 | | |
158 | | The function <<bfd_minisymbol_to_symbol>> will take a pointer |
159 | | to a minisymbol, and a pointer to a structure returned by |
160 | | <<bfd_make_empty_symbol>>, and return a <<asymbol>> structure. |
161 | | The return value may or may not be the same as the value from |
162 | | <<bfd_make_empty_symbol>> which was passed in. |
163 | | |
164 | | */ |
165 | | |
166 | | /* |
167 | | DOCDD |
168 | | INODE |
169 | | typedef asymbol, symbol handling functions, Mini Symbols, Symbols |
170 | | |
171 | | SUBSECTION |
172 | | typedef asymbol |
173 | | |
174 | | An <<asymbol>> has the form: |
175 | | |
176 | | CODE_FRAGMENT |
177 | | .typedef struct bfd_symbol |
178 | | .{ |
179 | | . {* A pointer to the BFD which owns the symbol. This information |
180 | | . is necessary so that a back end can work out what additional |
181 | | . information (invisible to the application writer) is carried |
182 | | . with the symbol. |
183 | | . |
184 | | . This field is *almost* redundant, since you can use section->owner |
185 | | . instead, except that some symbols point to the global sections |
186 | | . bfd_{abs,com,und}_section. This could be fixed by making |
187 | | . these globals be per-bfd (or per-target-flavor). FIXME. *} |
188 | | . struct bfd *the_bfd; {* Use bfd_asymbol_bfd(sym) to access this field. *} |
189 | | . |
190 | | . {* The text of the symbol. The name is left alone, and not copied; the |
191 | | . application may not alter it. *} |
192 | | . const char *name; |
193 | | . |
194 | | . {* The value of the symbol. This really should be a union of a |
195 | | . numeric value with a pointer, since some flags indicate that |
196 | | . a pointer to another symbol is stored here. *} |
197 | | . symvalue value; |
198 | | . |
199 | | . {* Attributes of a symbol. *} |
200 | | .#define BSF_NO_FLAGS 0 |
201 | | . |
202 | | . {* The symbol has local scope; <<static>> in <<C>>. The value |
203 | | . is the offset into the section of the data. *} |
204 | | .#define BSF_LOCAL (1 << 0) |
205 | | . |
206 | | . {* The symbol has global scope; initialized data in <<C>>. The |
207 | | . value is the offset into the section of the data. *} |
208 | | .#define BSF_GLOBAL (1 << 1) |
209 | | . |
210 | | . {* The symbol has global scope and is exported. The value is |
211 | | . the offset into the section of the data. *} |
212 | | .#define BSF_EXPORT BSF_GLOBAL {* No real difference. *} |
213 | | . |
214 | | . {* A normal C symbol would be one of: |
215 | | . <<BSF_LOCAL>>, <<BSF_UNDEFINED>> or <<BSF_GLOBAL>>. *} |
216 | | . |
217 | | . {* The symbol is a debugging record. The value has an arbitrary |
218 | | . meaning, unless BSF_DEBUGGING_RELOC is also set. *} |
219 | | .#define BSF_DEBUGGING (1 << 2) |
220 | | . |
221 | | . {* The symbol denotes a function entry point. Used in ELF, |
222 | | . perhaps others someday. *} |
223 | | .#define BSF_FUNCTION (1 << 3) |
224 | | . |
225 | | . {* Used by the linker. *} |
226 | | .#define BSF_KEEP (1 << 5) |
227 | | . |
228 | | . {* An ELF common symbol. *} |
229 | | .#define BSF_ELF_COMMON (1 << 6) |
230 | | . |
231 | | . {* A weak global symbol, overridable without warnings by |
232 | | . a regular global symbol of the same name. *} |
233 | | .#define BSF_WEAK (1 << 7) |
234 | | . |
235 | | . {* This symbol was created to point to a section, e.g. ELF's |
236 | | . STT_SECTION symbols. *} |
237 | | .#define BSF_SECTION_SYM (1 << 8) |
238 | | . |
239 | | . {* The symbol used to be a common symbol, but now it is |
240 | | . allocated. *} |
241 | | .#define BSF_OLD_COMMON (1 << 9) |
242 | | . |
243 | | . {* In some files the type of a symbol sometimes alters its |
244 | | . location in an output file - ie in coff a <<ISFCN>> symbol |
245 | | . which is also <<C_EXT>> symbol appears where it was |
246 | | . declared and not at the end of a section. This bit is set |
247 | | . by the target BFD part to convey this information. *} |
248 | | .#define BSF_NOT_AT_END (1 << 10) |
249 | | . |
250 | | . {* Signal that the symbol is the label of constructor section. *} |
251 | | .#define BSF_CONSTRUCTOR (1 << 11) |
252 | | . |
253 | | . {* Signal that the symbol is a warning symbol. The name is a |
254 | | . warning. The name of the next symbol is the one to warn about; |
255 | | . if a reference is made to a symbol with the same name as the next |
256 | | . symbol, a warning is issued by the linker. *} |
257 | | .#define BSF_WARNING (1 << 12) |
258 | | . |
259 | | . {* Signal that the symbol is indirect. This symbol is an indirect |
260 | | . pointer to the symbol with the same name as the next symbol. *} |
261 | | .#define BSF_INDIRECT (1 << 13) |
262 | | . |
263 | | . {* BSF_FILE marks symbols that contain a file name. This is used |
264 | | . for ELF STT_FILE symbols. *} |
265 | | .#define BSF_FILE (1 << 14) |
266 | | . |
267 | | . {* Symbol is from dynamic linking information. *} |
268 | | .#define BSF_DYNAMIC (1 << 15) |
269 | | . |
270 | | . {* The symbol denotes a data object. Used in ELF, and perhaps |
271 | | . others someday. *} |
272 | | .#define BSF_OBJECT (1 << 16) |
273 | | . |
274 | | . {* This symbol is a debugging symbol. The value is the offset |
275 | | . into the section of the data. BSF_DEBUGGING should be set |
276 | | . as well. *} |
277 | | .#define BSF_DEBUGGING_RELOC (1 << 17) |
278 | | . |
279 | | . {* This symbol is thread local. Used in ELF. *} |
280 | | .#define BSF_THREAD_LOCAL (1 << 18) |
281 | | . |
282 | | . {* This symbol represents a complex relocation expression, |
283 | | . with the expression tree serialized in the symbol name. *} |
284 | | .#define BSF_RELC (1 << 19) |
285 | | . |
286 | | . {* This symbol represents a signed complex relocation expression, |
287 | | . with the expression tree serialized in the symbol name. *} |
288 | | .#define BSF_SRELC (1 << 20) |
289 | | . |
290 | | . {* This symbol was created by bfd_get_synthetic_symtab. *} |
291 | | .#define BSF_SYNTHETIC (1 << 21) |
292 | | . |
293 | | . {* This symbol is an indirect code object. Unrelated to BSF_INDIRECT. |
294 | | . The dynamic linker will compute the value of this symbol by |
295 | | . calling the function that it points to. BSF_FUNCTION must |
296 | | . also be also set. *} |
297 | | .#define BSF_GNU_INDIRECT_FUNCTION (1 << 22) |
298 | | . {* This symbol is a globally unique data object. The dynamic linker |
299 | | . will make sure that in the entire process there is just one symbol |
300 | | . with this name and type in use. BSF_OBJECT must also be set. *} |
301 | | .#define BSF_GNU_UNIQUE (1 << 23) |
302 | | . |
303 | | . {* This section symbol should be included in the symbol table. *} |
304 | | .#define BSF_SECTION_SYM_USED (1 << 24) |
305 | | . |
306 | | . {* This symbol underwent section merge resolution. *} |
307 | | .#define BSF_MERGE_RESOLVED (1 << 25) |
308 | | . |
309 | | . flagword flags; |
310 | | . |
311 | | . {* A pointer to the section to which this symbol is |
312 | | . relative. This will always be non NULL, there are special |
313 | | . sections for undefined and absolute symbols. *} |
314 | | . struct bfd_section *section; |
315 | | . |
316 | | . {* Back end special data. *} |
317 | | . union |
318 | | . { |
319 | | . void *p; |
320 | | . bfd_vma i; |
321 | | . } |
322 | | . udata; |
323 | | .} |
324 | | .asymbol; |
325 | | . |
326 | | |
327 | | EXTERNAL |
328 | | .typedef enum bfd_print_symbol |
329 | | .{ |
330 | | . bfd_print_symbol_name, |
331 | | . bfd_print_symbol_more, |
332 | | . bfd_print_symbol_all |
333 | | .} bfd_print_symbol_type; |
334 | | . |
335 | | .{* Information about a symbol that nm needs. *} |
336 | | . |
337 | | .typedef struct _symbol_info |
338 | | .{ |
339 | | . symvalue value; |
340 | | . char type; |
341 | | . const char *name; {* Symbol name. *} |
342 | | . unsigned char stab_type; {* Stab type. *} |
343 | | . char stab_other; {* Stab other. *} |
344 | | . short stab_desc; {* Stab desc. *} |
345 | | . const char *stab_name; {* String for stab type. *} |
346 | | .} symbol_info; |
347 | | . |
348 | | .{* An empty string that will not match the address of any other |
349 | | . symbol name, even unnamed local symbols which will also have empty |
350 | | . string names. This can be used to flag a symbol as corrupt if its |
351 | | . name uses an out of range string table index. *} |
352 | | .extern const char bfd_symbol_error_name[]; |
353 | | */ |
354 | | |
355 | | #include "sysdep.h" |
356 | | #include "bfd.h" |
357 | | #include "libbfd.h" |
358 | | #include "safe-ctype.h" |
359 | | #include "bfdlink.h" |
360 | | #include "aout/stab_gnu.h" |
361 | | |
362 | | const char bfd_symbol_error_name[] = { 0 }; |
363 | | |
364 | | /* |
365 | | DOCDD |
366 | | INODE |
367 | | symbol handling functions, , typedef asymbol, Symbols |
368 | | SUBSECTION |
369 | | Symbol handling functions |
370 | | */ |
371 | | |
372 | | /* |
373 | | FUNCTION |
374 | | bfd_get_symtab_upper_bound |
375 | | |
376 | | DESCRIPTION |
377 | | Return the number of bytes required to store a vector of pointers |
378 | | to <<asymbols>> for all the symbols in the BFD @var{abfd}, |
379 | | including a terminal NULL pointer. If there are no symbols in |
380 | | the BFD, then return 0. If an error occurs, return -1. |
381 | | |
382 | | .#define bfd_get_symtab_upper_bound(abfd) \ |
383 | | . BFD_SEND (abfd, _bfd_get_symtab_upper_bound, (abfd)) |
384 | | . |
385 | | */ |
386 | | |
387 | | /* |
388 | | FUNCTION |
389 | | bfd_is_local_label |
390 | | |
391 | | SYNOPSIS |
392 | | bool bfd_is_local_label (bfd *abfd, asymbol *sym); |
393 | | |
394 | | DESCRIPTION |
395 | | Return TRUE if the given symbol @var{sym} in the BFD @var{abfd} is |
396 | | a compiler generated local label, else return FALSE. |
397 | | */ |
398 | | |
399 | | bool |
400 | | bfd_is_local_label (bfd *abfd, asymbol *sym) |
401 | 1 | { |
402 | | /* The BSF_SECTION_SYM check is needed for IA-64, where every label that |
403 | | starts with '.' is local. This would accidentally catch section names |
404 | | if we didn't reject them here. */ |
405 | 1 | if ((sym->flags & (BSF_GLOBAL | BSF_WEAK | BSF_FILE | BSF_SECTION_SYM)) != 0) |
406 | 0 | return false; |
407 | 1 | if (sym->name == NULL || sym->name == bfd_symbol_error_name) |
408 | 0 | return false; |
409 | 1 | return bfd_is_local_label_name (abfd, sym->name); |
410 | 1 | } |
411 | | |
412 | | /* |
413 | | FUNCTION |
414 | | bfd_is_local_label_name |
415 | | |
416 | | SYNOPSIS |
417 | | bool bfd_is_local_label_name (bfd *abfd, const char *name); |
418 | | |
419 | | DESCRIPTION |
420 | | Return TRUE if a symbol with the name @var{name} in the BFD |
421 | | @var{abfd} is a compiler generated local label, else return |
422 | | FALSE. This just checks whether the name has the form of a |
423 | | local label. |
424 | | |
425 | | .#define bfd_is_local_label_name(abfd, name) \ |
426 | | . BFD_SEND (abfd, _bfd_is_local_label_name, (abfd, name)) |
427 | | . |
428 | | */ |
429 | | |
430 | | /* |
431 | | FUNCTION |
432 | | bfd_is_target_special_symbol |
433 | | |
434 | | SYNOPSIS |
435 | | bool bfd_is_target_special_symbol (bfd *abfd, asymbol *sym); |
436 | | |
437 | | DESCRIPTION |
438 | | Return TRUE iff a symbol @var{sym} in the BFD @var{abfd} is something |
439 | | special to the particular target represented by the BFD. Such symbols |
440 | | should normally not be mentioned to the user. |
441 | | |
442 | | .#define bfd_is_target_special_symbol(abfd, sym) \ |
443 | | . BFD_SEND (abfd, _bfd_is_target_special_symbol, (abfd, sym)) |
444 | | . |
445 | | */ |
446 | | |
447 | | /* |
448 | | FUNCTION |
449 | | bfd_canonicalize_symtab |
450 | | |
451 | | DESCRIPTION |
452 | | Read the symbols from the BFD @var{abfd}, and fills in |
453 | | the vector @var{location} with pointers to the symbols and |
454 | | a trailing NULL. |
455 | | Return the actual number of symbol pointers, not |
456 | | including the NULL. |
457 | | |
458 | | .#define bfd_canonicalize_symtab(abfd, location) \ |
459 | | . BFD_SEND (abfd, _bfd_canonicalize_symtab, (abfd, location)) |
460 | | . |
461 | | */ |
462 | | |
463 | | /* |
464 | | FUNCTION |
465 | | bfd_set_symtab |
466 | | |
467 | | SYNOPSIS |
468 | | bool bfd_set_symtab |
469 | | (bfd *abfd, asymbol **location, unsigned int count); |
470 | | |
471 | | DESCRIPTION |
472 | | Arrange that when the output BFD @var{abfd} is closed, |
473 | | the table @var{location} of @var{count} pointers to symbols |
474 | | will be written. |
475 | | */ |
476 | | |
477 | | bool |
478 | | bfd_set_symtab (bfd *abfd, asymbol **location, unsigned int symcount) |
479 | 4.30k | { |
480 | 4.30k | if (abfd->format != bfd_object || bfd_read_p (abfd)) |
481 | 196 | { |
482 | 196 | bfd_set_error (bfd_error_invalid_operation); |
483 | 196 | return false; |
484 | 196 | } |
485 | | |
486 | 4.11k | abfd->outsymbols = location; |
487 | 4.11k | abfd->symcount = symcount; |
488 | 4.11k | return true; |
489 | 4.30k | } |
490 | | |
491 | | /* |
492 | | FUNCTION |
493 | | bfd_print_symbol_vandf |
494 | | |
495 | | SYNOPSIS |
496 | | void bfd_print_symbol_vandf (bfd *abfd, void *file, asymbol *symbol); |
497 | | |
498 | | DESCRIPTION |
499 | | Print the value and flags of the @var{symbol} supplied to the |
500 | | stream @var{file}. |
501 | | */ |
502 | | void |
503 | | bfd_print_symbol_vandf (bfd *abfd, void *arg, asymbol *symbol) |
504 | 0 | { |
505 | 0 | FILE *file = (FILE *) arg; |
506 | |
|
507 | 0 | flagword type = symbol->flags; |
508 | |
|
509 | 0 | if (symbol->section != NULL) |
510 | 0 | bfd_fprintf_vma (abfd, file, symbol->value + symbol->section->vma); |
511 | 0 | else |
512 | 0 | bfd_fprintf_vma (abfd, file, symbol->value); |
513 | | |
514 | | /* This presumes that a symbol can not be both BSF_DEBUGGING and |
515 | | BSF_DYNAMIC, nor more than one of BSF_FUNCTION, BSF_FILE, and |
516 | | BSF_OBJECT. */ |
517 | 0 | fprintf (file, " %c%c%c%c%c%c%c", |
518 | 0 | ((type & BSF_LOCAL) |
519 | 0 | ? (type & BSF_GLOBAL) ? '!' : 'l' |
520 | 0 | : (type & BSF_GLOBAL) ? 'g' |
521 | 0 | : (type & BSF_GNU_UNIQUE) ? 'u' : ' '), |
522 | 0 | (type & BSF_WEAK) ? 'w' : ' ', |
523 | 0 | (type & BSF_CONSTRUCTOR) ? 'C' : ' ', |
524 | 0 | (type & BSF_WARNING) ? 'W' : ' ', |
525 | 0 | (type & BSF_INDIRECT) ? 'I' : (type & BSF_GNU_INDIRECT_FUNCTION) ? 'i' : ' ', |
526 | 0 | (type & BSF_DEBUGGING) ? 'd' : (type & BSF_DYNAMIC) ? 'D' : ' ', |
527 | 0 | ((type & BSF_FUNCTION) |
528 | 0 | ? 'F' |
529 | 0 | : ((type & BSF_FILE) |
530 | 0 | ? 'f' |
531 | 0 | : ((type & BSF_OBJECT) ? 'O' : ' ')))); |
532 | 0 | } |
533 | | |
534 | | /* |
535 | | FUNCTION |
536 | | bfd_make_empty_symbol |
537 | | |
538 | | DESCRIPTION |
539 | | Create a new <<asymbol>> structure for the BFD @var{abfd} |
540 | | and return a pointer to it. |
541 | | |
542 | | This routine is necessary because each back end has private |
543 | | information surrounding the <<asymbol>>. Building your own |
544 | | <<asymbol>> and pointing to it will not create the private |
545 | | information, and will cause problems later on. |
546 | | |
547 | | .#define bfd_make_empty_symbol(abfd) \ |
548 | | . BFD_SEND (abfd, _bfd_make_empty_symbol, (abfd)) |
549 | | . |
550 | | */ |
551 | | |
552 | | /* |
553 | | FUNCTION |
554 | | _bfd_generic_make_empty_symbol |
555 | | |
556 | | SYNOPSIS |
557 | | asymbol *_bfd_generic_make_empty_symbol (bfd *); |
558 | | |
559 | | DESCRIPTION |
560 | | Create a new <<asymbol>> structure for the BFD @var{abfd} |
561 | | and return a pointer to it. Used by core file routines, |
562 | | binary back-end and anywhere else where no private info |
563 | | is needed. |
564 | | */ |
565 | | |
566 | | asymbol * |
567 | | _bfd_generic_make_empty_symbol (bfd *abfd) |
568 | 50.4k | { |
569 | 50.4k | size_t amt = sizeof (asymbol); |
570 | 50.4k | asymbol *new_symbol = (asymbol *) bfd_zalloc (abfd, amt); |
571 | 50.4k | if (new_symbol) |
572 | 50.4k | new_symbol->the_bfd = abfd; |
573 | 50.4k | return new_symbol; |
574 | 50.4k | } |
575 | | |
576 | | /* |
577 | | FUNCTION |
578 | | bfd_make_debug_symbol |
579 | | |
580 | | DESCRIPTION |
581 | | Create a new <<asymbol>> structure for the BFD @var{abfd}, |
582 | | to be used as a debugging symbol. |
583 | | |
584 | | .#define bfd_make_debug_symbol(abfd) \ |
585 | | . BFD_SEND (abfd, _bfd_make_debug_symbol, (abfd)) |
586 | | . |
587 | | */ |
588 | | |
589 | | struct section_to_type |
590 | | { |
591 | | const char *section; |
592 | | char type; |
593 | | }; |
594 | | |
595 | | /* Map special section names to POSIX/BSD single-character symbol types. |
596 | | This table is probably incomplete. It is sorted for convenience of |
597 | | adding entries. Since it is so short, a linear search is used. */ |
598 | | static const struct section_to_type stt[] = |
599 | | { |
600 | | {".didat", 'i'}, /* MSVC's .didat (delay import) section */ |
601 | | {".drectve", 'i'}, /* MSVC's .drective section */ |
602 | | {".edata", 'e'}, /* MSVC's .edata (export) section */ |
603 | | {".idata", 'i'}, /* MSVC's .idata (import) section */ |
604 | | {".pdata", 'p'}, /* MSVC's .pdata (stack unwind) section */ |
605 | | {0, 0} |
606 | | }; |
607 | | |
608 | | /* Return the single-character symbol type corresponding to |
609 | | section S, or '?' for an unknown COFF section. |
610 | | |
611 | | Check for leading strings which match, followed by a number, '.', |
612 | | or '$' so .idata5 matches the .idata entry. */ |
613 | | |
614 | | static char |
615 | | coff_section_type (const char *s) |
616 | 14.4k | { |
617 | 14.4k | const struct section_to_type *t; |
618 | | |
619 | 86.0k | for (t = &stt[0]; t->section; t++) |
620 | 71.7k | { |
621 | 71.7k | size_t len = strlen (t->section); |
622 | 71.7k | if (strncmp (s, t->section, len) == 0 |
623 | 505 | && memchr (".$0123456789", s[len], 13) != 0) |
624 | 174 | return t->type; |
625 | 71.7k | } |
626 | | |
627 | 14.2k | return '?'; |
628 | 14.4k | } |
629 | | |
630 | | /* Return the single-character symbol type corresponding to section |
631 | | SECTION, or '?' for an unknown section. This uses section flags to |
632 | | identify sections. |
633 | | |
634 | | FIXME These types are unhandled: e, i, p. If we handled these also, |
635 | | we could perhaps obsolete coff_section_type. */ |
636 | | |
637 | | static char |
638 | | decode_section_type (const struct bfd_section *section) |
639 | 14.2k | { |
640 | 14.2k | if (section->flags & SEC_CODE) |
641 | 6.41k | return 't'; |
642 | 7.84k | if (section->flags & SEC_DATA) |
643 | 6.26k | { |
644 | 6.26k | if (section->flags & SEC_READONLY) |
645 | 1.73k | return 'r'; |
646 | 4.53k | else if (section->flags & SEC_SMALL_DATA) |
647 | 5 | return 'g'; |
648 | 4.52k | else |
649 | 4.52k | return 'd'; |
650 | 6.26k | } |
651 | 1.57k | if ((section->flags & SEC_HAS_CONTENTS) == 0) |
652 | 935 | { |
653 | 935 | if (section->flags & SEC_SMALL_DATA) |
654 | 1 | return 's'; |
655 | 934 | else |
656 | 934 | return 'b'; |
657 | 935 | } |
658 | 644 | if (section->flags & SEC_DEBUGGING) |
659 | 45 | return 'N'; |
660 | 599 | if ((section->flags & SEC_HAS_CONTENTS) && (section->flags & SEC_READONLY)) |
661 | 335 | return 'n'; |
662 | | |
663 | 264 | return '?'; |
664 | 599 | } |
665 | | |
666 | | /* |
667 | | FUNCTION |
668 | | bfd_decode_symclass |
669 | | |
670 | | SYNOPSIS |
671 | | int bfd_decode_symclass (asymbol *symbol); |
672 | | |
673 | | DESCRIPTION |
674 | | Return a character corresponding to the symbol |
675 | | class of @var{symbol}, or '?' for an unknown class. |
676 | | */ |
677 | | int |
678 | | bfd_decode_symclass (asymbol *symbol) |
679 | 52.5k | { |
680 | 52.5k | char c; |
681 | | |
682 | | /* Paranoia... */ |
683 | 52.5k | if (symbol == NULL || symbol->section == NULL) |
684 | 0 | return '?'; |
685 | | |
686 | 52.5k | if (symbol->section && bfd_is_com_section (symbol->section)) |
687 | 521 | { |
688 | 521 | if (symbol->section->flags & SEC_SMALL_DATA) |
689 | 4 | return 'c'; |
690 | 517 | else |
691 | 517 | return 'C'; |
692 | 521 | } |
693 | 52.0k | if (bfd_is_und_section (symbol->section)) |
694 | 24.7k | { |
695 | 24.7k | if (symbol->flags & BSF_WEAK) |
696 | 1.75k | { |
697 | | /* If weak, determine if it's specifically an object |
698 | | or non-object weak. */ |
699 | 1.75k | if (symbol->flags & BSF_OBJECT) |
700 | 22 | return 'v'; |
701 | 1.73k | else |
702 | 1.73k | return 'w'; |
703 | 1.75k | } |
704 | 22.9k | else |
705 | 22.9k | return 'U'; |
706 | 24.7k | } |
707 | 27.3k | if (bfd_is_ind_section (symbol->section)) |
708 | 497 | return 'I'; |
709 | 26.8k | if (symbol->flags & BSF_GNU_INDIRECT_FUNCTION) |
710 | 73 | return 'i'; |
711 | 26.7k | if (symbol->flags & BSF_WEAK) |
712 | 221 | { |
713 | | /* If weak, determine if it's specifically an object |
714 | | or non-object weak. */ |
715 | 221 | if (symbol->flags & BSF_OBJECT) |
716 | 20 | return 'V'; |
717 | 201 | else |
718 | 201 | return 'W'; |
719 | 221 | } |
720 | 26.5k | if (symbol->flags & BSF_GNU_UNIQUE) |
721 | 47 | return 'u'; |
722 | 26.4k | if (!(symbol->flags & (BSF_GLOBAL | BSF_LOCAL))) |
723 | 1.39k | return '?'; |
724 | | |
725 | 25.0k | if (bfd_is_abs_section (symbol->section)) |
726 | 10.6k | c = 'a'; |
727 | 14.4k | else if (symbol->section) |
728 | 14.4k | { |
729 | 14.4k | c = coff_section_type (symbol->section->name); |
730 | 14.4k | if (c == '?') |
731 | 14.2k | c = decode_section_type (symbol->section); |
732 | 14.4k | } |
733 | 0 | else |
734 | 0 | return '?'; |
735 | 25.0k | if (symbol->flags & BSF_GLOBAL) |
736 | 7.59k | c = TOUPPER (c); |
737 | 25.0k | return c; |
738 | | |
739 | | /* We don't have to handle these cases just yet, but we will soon: |
740 | | N_SETV: 'v'; |
741 | | N_SETA: 'l'; |
742 | | N_SETT: 'x'; |
743 | | N_SETD: 'z'; |
744 | | N_SETB: 's'; |
745 | | N_INDR: 'i'; |
746 | | */ |
747 | 25.0k | } |
748 | | |
749 | | /* |
750 | | FUNCTION |
751 | | bfd_is_undefined_symclass |
752 | | |
753 | | SYNOPSIS |
754 | | bool bfd_is_undefined_symclass (int symclass); |
755 | | |
756 | | DESCRIPTION |
757 | | Returns non-zero if the class symbol returned by |
758 | | bfd_decode_symclass represents an undefined symbol. |
759 | | Returns zero otherwise. |
760 | | */ |
761 | | |
762 | | bool |
763 | | bfd_is_undefined_symclass (int symclass) |
764 | 75.9k | { |
765 | 75.9k | return symclass == 'U' || symclass == 'w' || symclass == 'v'; |
766 | 75.9k | } |
767 | | |
768 | | /* |
769 | | FUNCTION |
770 | | bfd_symbol_info |
771 | | |
772 | | SYNOPSIS |
773 | | void bfd_symbol_info (asymbol *symbol, symbol_info *ret); |
774 | | |
775 | | DESCRIPTION |
776 | | Fill in the basic info about symbol that nm needs. |
777 | | Additional info may be added by the back-ends after |
778 | | calling this function. |
779 | | */ |
780 | | |
781 | | void |
782 | | bfd_symbol_info (asymbol *symbol, symbol_info *ret) |
783 | 39.8k | { |
784 | 39.8k | ret->type = bfd_decode_symclass (symbol); |
785 | | |
786 | 39.8k | if (bfd_is_undefined_symclass (ret->type)) |
787 | 20.2k | ret->value = 0; |
788 | 19.5k | else |
789 | 19.5k | ret->value = symbol->value + symbol->section->vma; |
790 | | |
791 | 39.8k | ret->name = (symbol->name != bfd_symbol_error_name |
792 | 39.8k | ? symbol->name : _("<corrupt>")); |
793 | 39.8k | } |
794 | | |
795 | | /* |
796 | | FUNCTION |
797 | | bfd_copy_private_symbol_data |
798 | | |
799 | | DESCRIPTION |
800 | | Copy private symbol information from @var{isym} in the BFD |
801 | | @var{ibfd} to the symbol @var{osym} in the BFD @var{obfd}. |
802 | | Return <<TRUE>> on success, <<FALSE>> on error. Possible error |
803 | | returns are: |
804 | | |
805 | | o <<bfd_error_no_memory>> - |
806 | | Not enough memory exists to create private data for @var{osec}. |
807 | | |
808 | | .#define bfd_copy_private_symbol_data(ibfd, isymbol, obfd, osymbol) \ |
809 | | . BFD_SEND (obfd, _bfd_copy_private_symbol_data, \ |
810 | | . (ibfd, isymbol, obfd, osymbol)) |
811 | | . |
812 | | */ |
813 | | |
814 | | /* The generic version of the function which returns mini symbols. |
815 | | This is used when the backend does not provide a more efficient |
816 | | version. It just uses BFD asymbol structures as mini symbols. */ |
817 | | |
818 | | long |
819 | | _bfd_generic_read_minisymbols (bfd *abfd, |
820 | | bool dynamic, |
821 | | void **minisymsp, |
822 | | unsigned int *sizep) |
823 | 6.23k | { |
824 | 6.23k | long storage; |
825 | 6.23k | asymbol **syms = NULL; |
826 | 6.23k | long symcount; |
827 | | |
828 | 6.23k | if (dynamic) |
829 | 0 | storage = bfd_get_dynamic_symtab_upper_bound (abfd); |
830 | 6.23k | else |
831 | 6.23k | storage = bfd_get_symtab_upper_bound (abfd); |
832 | 6.23k | if (storage < 0) |
833 | 3.76k | goto error_return; |
834 | 2.47k | if (storage == 0) |
835 | 8 | return 0; |
836 | | |
837 | 2.46k | syms = (asymbol **) bfd_malloc (storage); |
838 | 2.46k | if (syms == NULL) |
839 | 0 | goto error_return; |
840 | | |
841 | 2.46k | if (dynamic) |
842 | 0 | symcount = bfd_canonicalize_dynamic_symtab (abfd, syms); |
843 | 2.46k | else |
844 | 2.46k | symcount = bfd_canonicalize_symtab (abfd, syms); |
845 | 2.46k | if (symcount < 0) |
846 | 212 | goto error_return; |
847 | | |
848 | 2.25k | if (symcount == 0) |
849 | | /* We return 0 above when storage is 0. Exit in the same state |
850 | | here, so as to not complicate callers with having to deal with |
851 | | freeing memory for zero symcount. */ |
852 | 32 | free (syms); |
853 | 2.22k | else |
854 | 2.22k | { |
855 | 2.22k | *minisymsp = syms; |
856 | 2.22k | *sizep = sizeof (asymbol *); |
857 | 2.22k | } |
858 | 2.25k | return symcount; |
859 | | |
860 | 3.97k | error_return: |
861 | 3.97k | free (syms); |
862 | 3.97k | return -1; |
863 | 2.46k | } |
864 | | |
865 | | /* The generic version of the function which converts a minisymbol to |
866 | | an asymbol. We don't worry about the sym argument we are passed; |
867 | | we just return the asymbol the minisymbol points to. */ |
868 | | |
869 | | asymbol * |
870 | | _bfd_generic_minisymbol_to_symbol (bfd *abfd ATTRIBUTE_UNUSED, |
871 | | bool dynamic ATTRIBUTE_UNUSED, |
872 | | const void *minisym, |
873 | | asymbol *sym ATTRIBUTE_UNUSED) |
874 | 507k | { |
875 | 507k | return *(asymbol **) minisym; |
876 | 507k | } |
877 | | |
878 | | /* Look through stabs debugging information in .stab and .stabstr |
879 | | sections to find the source file and line closest to a desired |
880 | | location. This is used by COFF and ELF targets. It sets *pfound |
881 | | to TRUE if it finds some information. The *pinfo field is used to |
882 | | pass cached information in and out of this routine; this first time |
883 | | the routine is called for a BFD, *pinfo should be NULL. The value |
884 | | placed in *pinfo should be saved with the BFD, and passed back each |
885 | | time this function is called. */ |
886 | | |
887 | | /* We use a cache by default. */ |
888 | | |
889 | | #define ENABLE_CACHING |
890 | | |
891 | | /* We keep an array of indexentry structures to record where in the |
892 | | stabs section we should look to find line number information for a |
893 | | particular address. */ |
894 | | |
895 | | struct indexentry |
896 | | { |
897 | | bfd_vma val; |
898 | | bfd_byte *stab; |
899 | | bfd_byte *str; |
900 | | char *directory_name; |
901 | | char *file_name; |
902 | | char *function_name; |
903 | | int idx; |
904 | | }; |
905 | | |
906 | | /* Compare two indexentry structures. This is called via qsort. */ |
907 | | |
908 | | static int |
909 | | cmpindexentry (const void *a, const void *b) |
910 | 9.81k | { |
911 | 9.81k | const struct indexentry *contestantA = (const struct indexentry *) a; |
912 | 9.81k | const struct indexentry *contestantB = (const struct indexentry *) b; |
913 | | |
914 | 9.81k | if (contestantA->val < contestantB->val) |
915 | 2.04k | return -1; |
916 | 7.77k | if (contestantA->val > contestantB->val) |
917 | 3.76k | return 1; |
918 | 4.01k | return contestantA->idx - contestantB->idx; |
919 | 7.77k | } |
920 | | |
921 | | /* A pointer to this structure is stored in *pinfo. */ |
922 | | |
923 | | struct stab_find_info |
924 | | { |
925 | | /* The .stab section. */ |
926 | | asection *stabsec; |
927 | | /* The .stabstr section. */ |
928 | | asection *strsec; |
929 | | /* The contents of the .stab section. */ |
930 | | bfd_byte *stabs; |
931 | | /* The contents of the .stabstr section. */ |
932 | | bfd_byte *strs; |
933 | | |
934 | | /* A table that indexes stabs by memory address. */ |
935 | | struct indexentry *indextable; |
936 | | /* The number of entries in indextable. */ |
937 | | int indextablesize; |
938 | | |
939 | | #ifdef ENABLE_CACHING |
940 | | /* Cached values to restart quickly. */ |
941 | | struct indexentry *cached_indexentry; |
942 | | bfd_vma cached_offset; |
943 | | bfd_byte *cached_stab; |
944 | | char *cached_file_name; |
945 | | #endif |
946 | | |
947 | | /* Saved ptr to malloc'ed filename. */ |
948 | | char *filename; |
949 | | }; |
950 | | |
951 | | bool |
952 | | _bfd_stab_section_find_nearest_line (bfd *abfd, |
953 | | asymbol **symbols, |
954 | | asection *section, |
955 | | bfd_vma offset, |
956 | | bool *pfound, |
957 | | const char **pfilename, |
958 | | const char **pfnname, |
959 | | unsigned int *pline, |
960 | | void **pinfo) |
961 | 54.7k | { |
962 | 54.7k | struct stab_find_info *info; |
963 | 54.7k | bfd_size_type stabsize, strsize; |
964 | 54.7k | bfd_byte *stab, *str; |
965 | 54.7k | bfd_byte *nul_fun, *nul_str; |
966 | 54.7k | bfd_size_type stroff; |
967 | 54.7k | struct indexentry *indexentry; |
968 | 54.7k | char *file_name; |
969 | 54.7k | char *directory_name; |
970 | 54.7k | bool saw_line, saw_func; |
971 | | |
972 | 54.7k | *pfound = false; |
973 | 54.7k | *pfilename = bfd_get_filename (abfd); |
974 | 54.7k | *pfnname = NULL; |
975 | 54.7k | *pline = 0; |
976 | | |
977 | | /* Stabs entries use a 12 byte format: |
978 | | 4 byte string table index |
979 | | 1 byte stab type |
980 | | 1 byte stab other field |
981 | | 2 byte stab desc field |
982 | | 4 byte stab value |
983 | | FIXME: This will have to change for a 64 bit object format. |
984 | | |
985 | | The stabs symbols are divided into compilation units. For the |
986 | | first entry in each unit, the type of 0, the value is the length |
987 | | of the string table for this unit, and the desc field is the |
988 | | number of stabs symbols for this unit. */ |
989 | | |
990 | 54.7k | #define STRDXOFF (0) |
991 | 102k | #define TYPEOFF (4) |
992 | 54.7k | #define OTHEROFF (5) |
993 | 54.7k | #define DESCOFF (6) |
994 | 54.7k | #define VALOFF (8) |
995 | 81.4k | #define STABSIZE (12) |
996 | | |
997 | 54.7k | info = (struct stab_find_info *) *pinfo; |
998 | 54.7k | if (info != NULL) |
999 | 49.6k | { |
1000 | 49.6k | if (info->stabsec == NULL || info->strsec == NULL) |
1001 | 48.5k | { |
1002 | | /* No usable stabs debugging information. */ |
1003 | 48.5k | return true; |
1004 | 48.5k | } |
1005 | | |
1006 | 1.13k | stabsize = (info->stabsec->rawsize |
1007 | 1.13k | ? info->stabsec->rawsize |
1008 | 1.13k | : info->stabsec->size); |
1009 | 1.13k | strsize = (info->strsec->rawsize |
1010 | 1.13k | ? info->strsec->rawsize |
1011 | 1.13k | : info->strsec->size); |
1012 | 1.13k | } |
1013 | 5.06k | else |
1014 | 5.06k | { |
1015 | 5.06k | long reloc_size, reloc_count; |
1016 | 5.06k | arelent **reloc_vector; |
1017 | 5.06k | int i; |
1018 | 5.06k | char *function_name; |
1019 | 5.06k | bfd_size_type amt = sizeof *info; |
1020 | | |
1021 | 5.06k | info = (struct stab_find_info *) bfd_zalloc (abfd, amt); |
1022 | 5.06k | if (info == NULL) |
1023 | 0 | return false; |
1024 | 5.06k | *pinfo = info; |
1025 | | |
1026 | | /* FIXME: When using the linker --split-by-file or |
1027 | | --split-by-reloc options, it is possible for the .stab and |
1028 | | .stabstr sections to be split. We should handle that. */ |
1029 | | |
1030 | 5.06k | info->stabsec = bfd_get_section_by_name (abfd, ".stab"); |
1031 | 5.06k | info->strsec = bfd_get_section_by_name (abfd, ".stabstr"); |
1032 | | |
1033 | 5.06k | if (info->stabsec == NULL || info->strsec == NULL) |
1034 | 4.64k | { |
1035 | | /* Try SOM section names. */ |
1036 | 4.64k | info->stabsec = bfd_get_section_by_name (abfd, "$GDB_SYMBOLS$"); |
1037 | 4.64k | info->strsec = bfd_get_section_by_name (abfd, "$GDB_STRINGS$"); |
1038 | | |
1039 | 4.64k | if (info->stabsec == NULL || info->strsec == NULL) |
1040 | 4.64k | return true; |
1041 | 4.64k | } |
1042 | | |
1043 | 422 | if ((info->stabsec->flags & SEC_HAS_CONTENTS) == 0 |
1044 | 420 | || (info->strsec->flags & SEC_HAS_CONTENTS) == 0) |
1045 | 3 | goto out; |
1046 | | |
1047 | 419 | stabsize = (info->stabsec->rawsize |
1048 | 419 | ? info->stabsec->rawsize |
1049 | 419 | : info->stabsec->size); |
1050 | 419 | stabsize = (stabsize / STABSIZE) * STABSIZE; |
1051 | 419 | strsize = (info->strsec->rawsize |
1052 | 419 | ? info->strsec->rawsize |
1053 | 419 | : info->strsec->size); |
1054 | | |
1055 | 419 | if (stabsize == 0 || strsize == 0) |
1056 | 3 | goto out; |
1057 | | |
1058 | 416 | if (!bfd_malloc_and_get_section (abfd, info->stabsec, &info->stabs)) |
1059 | 16 | goto out; |
1060 | 400 | if (!bfd_malloc_and_get_section (abfd, info->strsec, &info->strs)) |
1061 | 2 | goto out1; |
1062 | | |
1063 | | /* Stab strings ought to be nul terminated. Ensure the last one |
1064 | | is, to prevent running off the end of the buffer. */ |
1065 | 398 | info->strs[strsize - 1] = 0; |
1066 | | |
1067 | | /* If this is a relocatable object file, we have to relocate |
1068 | | the entries in .stab. This should always be simple 32 bit |
1069 | | relocations against symbols defined in this object file, so |
1070 | | this should be no big deal. */ |
1071 | 398 | reloc_size = bfd_get_reloc_upper_bound (abfd, info->stabsec); |
1072 | 398 | if (reloc_size < 0) |
1073 | 0 | goto out2; |
1074 | 398 | reloc_vector = (arelent **) bfd_malloc (reloc_size); |
1075 | 398 | if (reloc_vector == NULL && reloc_size != 0) |
1076 | 0 | goto out2; |
1077 | 398 | reloc_count = bfd_canonicalize_reloc (abfd, info->stabsec, reloc_vector, |
1078 | 398 | symbols); |
1079 | 398 | if (reloc_count < 0) |
1080 | 175 | { |
1081 | 196 | out3: |
1082 | 196 | free (reloc_vector); |
1083 | 196 | out2: |
1084 | 196 | free (info->strs); |
1085 | 196 | info->strs = NULL; |
1086 | 198 | out1: |
1087 | 198 | free (info->stabs); |
1088 | 198 | info->stabs = NULL; |
1089 | 220 | out: |
1090 | 220 | info->stabsec = NULL; |
1091 | 220 | return false; |
1092 | 198 | } |
1093 | 223 | if (reloc_count > 0) |
1094 | 23 | { |
1095 | 23 | arelent **pr; |
1096 | | |
1097 | 26 | for (pr = reloc_vector; *pr != NULL; pr++) |
1098 | 24 | { |
1099 | 24 | arelent *r; |
1100 | 24 | unsigned long val; |
1101 | 24 | asymbol *sym; |
1102 | 24 | bfd_size_type octets; |
1103 | | |
1104 | 24 | r = *pr; |
1105 | | /* Ignore R_*_NONE relocs. */ |
1106 | 24 | if (r->howto->dst_mask == 0) |
1107 | 0 | continue; |
1108 | | |
1109 | 24 | octets = r->address * bfd_octets_per_byte (abfd, NULL); |
1110 | 24 | if (r->howto->rightshift != 0 |
1111 | 13 | || bfd_get_reloc_size (r->howto) != 4 |
1112 | 7 | || r->howto->bitsize != 32 |
1113 | 6 | || r->howto->pc_relative |
1114 | 6 | || r->howto->bitpos != 0 |
1115 | 6 | || r->howto->dst_mask != 0xffffffff |
1116 | 6 | || octets > stabsize - 4) |
1117 | 21 | { |
1118 | 21 | _bfd_error_handler |
1119 | 21 | (_("unsupported .stab relocation")); |
1120 | 21 | bfd_set_error (bfd_error_invalid_operation); |
1121 | 21 | goto out3; |
1122 | 21 | } |
1123 | | |
1124 | 3 | val = bfd_get_32 (abfd, info->stabs + octets); |
1125 | 3 | val &= r->howto->src_mask; |
1126 | 3 | sym = *r->sym_ptr_ptr; |
1127 | 3 | val += sym->value + sym->section->vma + r->addend; |
1128 | 3 | bfd_put_32 (abfd, (bfd_vma) val, info->stabs + octets); |
1129 | 3 | } |
1130 | 23 | } |
1131 | | |
1132 | 202 | free (reloc_vector); |
1133 | | |
1134 | | /* First time through this function, build a table matching |
1135 | | function VM addresses to stabs, then sort based on starting |
1136 | | VM address. Do this in two passes: once to count how many |
1137 | | table entries we'll need, and a second to actually build the |
1138 | | table. */ |
1139 | | |
1140 | 202 | info->indextablesize = 0; |
1141 | 202 | nul_fun = NULL; |
1142 | 27.1k | for (stab = info->stabs; stab < info->stabs + stabsize; stab += STABSIZE) |
1143 | 26.9k | { |
1144 | 26.9k | if (stab[TYPEOFF] == (bfd_byte) N_SO) |
1145 | 2.01k | { |
1146 | | /* if we did not see a function def, leave space for one. */ |
1147 | 2.01k | if (nul_fun != NULL) |
1148 | 1.70k | ++info->indextablesize; |
1149 | | |
1150 | | /* N_SO with null name indicates EOF */ |
1151 | 2.01k | if (bfd_get_32 (abfd, stab + STRDXOFF) == 0) |
1152 | 60 | nul_fun = NULL; |
1153 | 1.95k | else |
1154 | 1.95k | { |
1155 | 1.95k | nul_fun = stab; |
1156 | | |
1157 | | /* two N_SO's in a row is a filename and directory. Skip */ |
1158 | 1.95k | if (stab + STABSIZE + TYPEOFF < info->stabs + stabsize |
1159 | 1.94k | && *(stab + STABSIZE + TYPEOFF) == (bfd_byte) N_SO) |
1160 | 1.32k | stab += STABSIZE; |
1161 | 1.95k | } |
1162 | 2.01k | } |
1163 | 24.9k | else if (stab[TYPEOFF] == (bfd_byte) N_FUN |
1164 | 765 | && bfd_get_32 (abfd, stab + STRDXOFF) != 0) |
1165 | 708 | { |
1166 | 708 | nul_fun = NULL; |
1167 | 708 | ++info->indextablesize; |
1168 | 708 | } |
1169 | 26.9k | } |
1170 | | |
1171 | 202 | if (nul_fun != NULL) |
1172 | 105 | ++info->indextablesize; |
1173 | | |
1174 | 202 | if (info->indextablesize == 0) |
1175 | 9 | { |
1176 | 9 | free (info->strs); |
1177 | 9 | info->strs = NULL; |
1178 | 9 | free (info->stabs); |
1179 | 9 | info->stabs = NULL; |
1180 | 9 | info->stabsec = NULL; |
1181 | 9 | return true; |
1182 | 9 | } |
1183 | 193 | ++info->indextablesize; |
1184 | | |
1185 | 193 | amt = info->indextablesize; |
1186 | 193 | amt *= sizeof (struct indexentry); |
1187 | 193 | info->indextable = (struct indexentry *) bfd_malloc (amt); |
1188 | 193 | if (info->indextable == NULL) |
1189 | 0 | goto out3; |
1190 | | |
1191 | 193 | file_name = NULL; |
1192 | 193 | directory_name = NULL; |
1193 | 193 | nul_fun = NULL; |
1194 | 193 | stroff = 0; |
1195 | | |
1196 | 193 | for (i = 0, stab = info->stabs, nul_str = str = info->strs; |
1197 | 26.7k | i < info->indextablesize && stab < info->stabs + stabsize; |
1198 | 26.5k | stab += STABSIZE) |
1199 | 26.5k | { |
1200 | 26.5k | switch (stab[TYPEOFF]) |
1201 | 26.5k | { |
1202 | 10.7k | case 0: |
1203 | | /* This is the first entry in a compilation unit. */ |
1204 | 10.7k | if ((bfd_size_type) ((info->strs + strsize) - str) < stroff) |
1205 | 10.3k | break; |
1206 | 415 | str += stroff; |
1207 | 415 | stroff = bfd_get_32 (abfd, stab + VALOFF); |
1208 | 415 | break; |
1209 | | |
1210 | 2.01k | case N_SO: |
1211 | | /* The main file name. */ |
1212 | | |
1213 | | /* The following code creates a new indextable entry with |
1214 | | a NULL function name if there were no N_FUNs in a file. |
1215 | | Note that a N_SO without a file name is an EOF and |
1216 | | there could be 2 N_SO following it with the new filename |
1217 | | and directory. */ |
1218 | 2.01k | if (nul_fun != NULL) |
1219 | 1.70k | { |
1220 | 1.70k | info->indextable[i].val = bfd_get_32 (abfd, nul_fun + VALOFF); |
1221 | 1.70k | info->indextable[i].stab = nul_fun; |
1222 | 1.70k | info->indextable[i].str = nul_str; |
1223 | 1.70k | info->indextable[i].directory_name = directory_name; |
1224 | 1.70k | info->indextable[i].file_name = file_name; |
1225 | 1.70k | info->indextable[i].function_name = NULL; |
1226 | 1.70k | info->indextable[i].idx = i; |
1227 | 1.70k | ++i; |
1228 | 1.70k | } |
1229 | | |
1230 | 2.01k | directory_name = NULL; |
1231 | 2.01k | file_name = (char *) str + bfd_get_32 (abfd, stab + STRDXOFF); |
1232 | 2.01k | if (file_name == (char *) str) |
1233 | 58 | { |
1234 | 58 | file_name = NULL; |
1235 | 58 | nul_fun = NULL; |
1236 | 58 | } |
1237 | 1.95k | else |
1238 | 1.95k | { |
1239 | 1.95k | nul_fun = stab; |
1240 | 1.95k | nul_str = str; |
1241 | 1.95k | if (file_name >= (char *) info->strs + strsize |
1242 | 66 | || file_name < (char *) str) |
1243 | 1.89k | file_name = NULL; |
1244 | 1.95k | if (stab + STABSIZE + TYPEOFF < info->stabs + stabsize |
1245 | 1.94k | && *(stab + STABSIZE + TYPEOFF) == (bfd_byte) N_SO) |
1246 | 1.32k | { |
1247 | | /* Two consecutive N_SOs are a directory and a |
1248 | | file name. */ |
1249 | 1.32k | stab += STABSIZE; |
1250 | 1.32k | directory_name = file_name; |
1251 | 1.32k | file_name = ((char *) str |
1252 | 1.32k | + bfd_get_32 (abfd, stab + STRDXOFF)); |
1253 | 1.32k | if (file_name >= (char *) info->strs + strsize |
1254 | 27 | || file_name < (char *) str) |
1255 | 1.30k | file_name = NULL; |
1256 | 1.32k | } |
1257 | 1.95k | } |
1258 | 2.01k | break; |
1259 | | |
1260 | 312 | case N_SOL: |
1261 | | /* The name of an include file. */ |
1262 | 312 | file_name = (char *) str + bfd_get_32 (abfd, stab + STRDXOFF); |
1263 | | /* PR 17512: file: 0c680a1f. */ |
1264 | | /* PR 17512: file: 5da8aec4. */ |
1265 | 312 | if (file_name >= (char *) info->strs + strsize |
1266 | 92 | || file_name < (char *) str) |
1267 | 220 | file_name = NULL; |
1268 | 312 | break; |
1269 | | |
1270 | 764 | case N_FUN: |
1271 | | /* A function name. */ |
1272 | 764 | function_name = (char *) str + bfd_get_32 (abfd, stab + STRDXOFF); |
1273 | 764 | if (function_name == (char *) str) |
1274 | 56 | continue; |
1275 | 708 | if (function_name >= (char *) info->strs + strsize |
1276 | 331 | || function_name < (char *) str) |
1277 | 377 | function_name = NULL; |
1278 | | |
1279 | 708 | nul_fun = NULL; |
1280 | 708 | info->indextable[i].val = bfd_get_32 (abfd, stab + VALOFF); |
1281 | 708 | info->indextable[i].stab = stab; |
1282 | 708 | info->indextable[i].str = str; |
1283 | 708 | info->indextable[i].directory_name = directory_name; |
1284 | 708 | info->indextable[i].file_name = file_name; |
1285 | 708 | info->indextable[i].function_name = function_name; |
1286 | 708 | info->indextable[i].idx = i; |
1287 | 708 | ++i; |
1288 | 708 | break; |
1289 | 26.5k | } |
1290 | 26.5k | } |
1291 | | |
1292 | 193 | if (nul_fun != NULL) |
1293 | 105 | { |
1294 | 105 | info->indextable[i].val = bfd_get_32 (abfd, nul_fun + VALOFF); |
1295 | 105 | info->indextable[i].stab = nul_fun; |
1296 | 105 | info->indextable[i].str = nul_str; |
1297 | 105 | info->indextable[i].directory_name = directory_name; |
1298 | 105 | info->indextable[i].file_name = file_name; |
1299 | 105 | info->indextable[i].function_name = NULL; |
1300 | 105 | info->indextable[i].idx = i; |
1301 | 105 | ++i; |
1302 | 105 | } |
1303 | | |
1304 | 193 | info->indextable[i].val = (bfd_vma) -1; |
1305 | 193 | info->indextable[i].stab = info->stabs + stabsize; |
1306 | 193 | info->indextable[i].str = str; |
1307 | 193 | info->indextable[i].directory_name = NULL; |
1308 | 193 | info->indextable[i].file_name = NULL; |
1309 | 193 | info->indextable[i].function_name = NULL; |
1310 | 193 | info->indextable[i].idx = i; |
1311 | 193 | ++i; |
1312 | | |
1313 | 193 | info->indextablesize = i; |
1314 | 193 | qsort (info->indextable, (size_t) i, sizeof (struct indexentry), |
1315 | 193 | cmpindexentry); |
1316 | 193 | } |
1317 | | |
1318 | | /* We are passed a section relative offset. The offsets in the |
1319 | | stabs information are absolute. */ |
1320 | 1.32k | offset += bfd_section_vma (section); |
1321 | | |
1322 | 1.32k | #ifdef ENABLE_CACHING |
1323 | 1.32k | if (info->cached_indexentry != NULL |
1324 | 397 | && offset >= info->cached_offset |
1325 | 113 | && offset < (info->cached_indexentry + 1)->val) |
1326 | 87 | { |
1327 | 87 | stab = info->cached_stab; |
1328 | 87 | indexentry = info->cached_indexentry; |
1329 | 87 | file_name = info->cached_file_name; |
1330 | 87 | } |
1331 | 1.23k | else |
1332 | 1.23k | #endif |
1333 | 1.23k | { |
1334 | 1.23k | long low, high; |
1335 | 1.23k | long mid = -1; |
1336 | | |
1337 | | /* Cache non-existent or invalid. Do binary search on |
1338 | | indextable. */ |
1339 | 1.23k | indexentry = NULL; |
1340 | | |
1341 | 1.23k | low = 0; |
1342 | 1.23k | high = info->indextablesize - 1; |
1343 | 3.56k | while (low != high) |
1344 | 2.88k | { |
1345 | 2.88k | mid = (high + low) / 2; |
1346 | 2.88k | if (offset >= info->indextable[mid].val |
1347 | 1.00k | && offset < info->indextable[mid + 1].val) |
1348 | 557 | { |
1349 | 557 | indexentry = &info->indextable[mid]; |
1350 | 557 | break; |
1351 | 557 | } |
1352 | | |
1353 | 2.32k | if (info->indextable[mid].val > offset) |
1354 | 1.88k | high = mid; |
1355 | 444 | else |
1356 | 444 | low = mid + 1; |
1357 | 2.32k | } |
1358 | | |
1359 | 1.23k | if (indexentry == NULL) |
1360 | 682 | return true; |
1361 | | |
1362 | 557 | stab = indexentry->stab + STABSIZE; |
1363 | 557 | file_name = indexentry->file_name; |
1364 | 557 | } |
1365 | | |
1366 | 644 | directory_name = indexentry->directory_name; |
1367 | 644 | str = indexentry->str; |
1368 | | |
1369 | 644 | saw_line = false; |
1370 | 644 | saw_func = false; |
1371 | 16.7k | for (; stab < (indexentry+1)->stab; stab += STABSIZE) |
1372 | 16.3k | { |
1373 | 16.3k | bool done; |
1374 | 16.3k | bfd_vma val; |
1375 | | |
1376 | 16.3k | done = false; |
1377 | | |
1378 | 16.3k | switch (stab[TYPEOFF]) |
1379 | 16.3k | { |
1380 | 642 | case N_SOL: |
1381 | | /* The name of an include file. */ |
1382 | 642 | val = bfd_get_32 (abfd, stab + VALOFF); |
1383 | 642 | if (val <= offset) |
1384 | 396 | { |
1385 | 396 | file_name = (char *) str + bfd_get_32 (abfd, stab + STRDXOFF); |
1386 | 396 | if (file_name >= (char *) info->strs + strsize |
1387 | 108 | || file_name < (char *) str) |
1388 | 288 | file_name = NULL; |
1389 | 396 | *pline = 0; |
1390 | 396 | } |
1391 | 642 | break; |
1392 | | |
1393 | 153 | case N_SLINE: |
1394 | 306 | case N_DSLINE: |
1395 | 499 | case N_BSLINE: |
1396 | | /* A line number. If the function was specified, then the value |
1397 | | is relative to the start of the function. Otherwise, the |
1398 | | value is an absolute address. */ |
1399 | 499 | val = ((indexentry->function_name ? indexentry->val : 0) |
1400 | 499 | + bfd_get_32 (abfd, stab + VALOFF)); |
1401 | | /* If this line starts before our desired offset, or if it's |
1402 | | the first line we've been able to find, use it. The |
1403 | | !saw_line check works around a bug in GCC 2.95.3, which emits |
1404 | | the first N_SLINE late. */ |
1405 | 499 | if (!saw_line || val <= offset) |
1406 | 466 | { |
1407 | 466 | *pline = bfd_get_16 (abfd, stab + DESCOFF); |
1408 | | |
1409 | 466 | #ifdef ENABLE_CACHING |
1410 | 466 | info->cached_stab = stab; |
1411 | 466 | info->cached_offset = val; |
1412 | 466 | info->cached_file_name = file_name; |
1413 | 466 | info->cached_indexentry = indexentry; |
1414 | 466 | #endif |
1415 | 466 | } |
1416 | 499 | if (val > offset) |
1417 | 90 | done = true; |
1418 | 499 | saw_line = true; |
1419 | 499 | break; |
1420 | | |
1421 | 118 | case N_FUN: |
1422 | 368 | case N_SO: |
1423 | 368 | if (saw_func || saw_line) |
1424 | 173 | done = true; |
1425 | 368 | saw_func = true; |
1426 | 368 | break; |
1427 | 16.3k | } |
1428 | | |
1429 | 16.3k | if (done) |
1430 | 263 | break; |
1431 | 16.3k | } |
1432 | | |
1433 | 644 | *pfound = true; |
1434 | | |
1435 | 644 | if (file_name == NULL || IS_ABSOLUTE_PATH (file_name) |
1436 | 97 | || directory_name == NULL) |
1437 | 608 | *pfilename = file_name; |
1438 | 36 | else |
1439 | 36 | { |
1440 | 36 | size_t dirlen; |
1441 | | |
1442 | 36 | dirlen = strlen (directory_name); |
1443 | 36 | if (info->filename == NULL |
1444 | 26 | || filename_ncmp (info->filename, directory_name, dirlen) != 0 |
1445 | 26 | || filename_cmp (info->filename + dirlen, file_name) != 0) |
1446 | 16 | { |
1447 | 16 | size_t len; |
1448 | | |
1449 | | /* Don't free info->filename here. objdump and other |
1450 | | apps keep a copy of a previously returned file name |
1451 | | pointer. */ |
1452 | 16 | len = strlen (file_name) + 1; |
1453 | 16 | info->filename = (char *) bfd_alloc (abfd, dirlen + len); |
1454 | 16 | if (info->filename == NULL) |
1455 | 0 | return false; |
1456 | 16 | memcpy (info->filename, directory_name, dirlen); |
1457 | 16 | memcpy (info->filename + dirlen, file_name, len); |
1458 | 16 | } |
1459 | | |
1460 | 36 | *pfilename = info->filename; |
1461 | 36 | } |
1462 | | |
1463 | 644 | if (indexentry->function_name != NULL) |
1464 | 115 | { |
1465 | 115 | char *s; |
1466 | | |
1467 | | /* This will typically be something like main:F(0,1), so we want |
1468 | | to clobber the colon. It's OK to change the name, since the |
1469 | | string is in our own local storage anyhow. */ |
1470 | 115 | s = strchr (indexentry->function_name, ':'); |
1471 | 115 | if (s != NULL) |
1472 | 1 | *s = '\0'; |
1473 | | |
1474 | 115 | *pfnname = indexentry->function_name; |
1475 | 115 | } |
1476 | | |
1477 | 644 | return true; |
1478 | 644 | } |
1479 | | |
1480 | | void |
1481 | | _bfd_stab_cleanup (bfd *abfd ATTRIBUTE_UNUSED, void **pinfo) |
1482 | 104k | { |
1483 | 104k | struct stab_find_info *info = (struct stab_find_info *) *pinfo; |
1484 | 104k | if (info == NULL) |
1485 | 99.3k | return; |
1486 | | |
1487 | 5.01k | free (info->indextable); |
1488 | 5.01k | free (info->strs); |
1489 | 5.01k | free (info->stabs); |
1490 | 5.01k | } |
1491 | | |
1492 | | long |
1493 | | _bfd_nosymbols_canonicalize_symtab (bfd *abfd ATTRIBUTE_UNUSED, |
1494 | | asymbol **location ATTRIBUTE_UNUSED) |
1495 | 782 | { |
1496 | 782 | return 0; |
1497 | 782 | } |
1498 | | |
1499 | | void |
1500 | | _bfd_nosymbols_print_symbol (bfd *abfd ATTRIBUTE_UNUSED, |
1501 | | void *afile ATTRIBUTE_UNUSED, |
1502 | | asymbol *symbol ATTRIBUTE_UNUSED, |
1503 | | bfd_print_symbol_type how ATTRIBUTE_UNUSED) |
1504 | 0 | { |
1505 | 0 | } |
1506 | | |
1507 | | void |
1508 | | _bfd_nosymbols_get_symbol_info (bfd *abfd ATTRIBUTE_UNUSED, |
1509 | | asymbol *sym ATTRIBUTE_UNUSED, |
1510 | | symbol_info *ret ATTRIBUTE_UNUSED) |
1511 | 0 | { |
1512 | 0 | } |
1513 | | |
1514 | | const char * |
1515 | | _bfd_nosymbols_get_symbol_version_string (bfd *abfd, |
1516 | | asymbol *symbol ATTRIBUTE_UNUSED, |
1517 | | bool base_p ATTRIBUTE_UNUSED, |
1518 | | bool *hidden ATTRIBUTE_UNUSED) |
1519 | 4.07k | { |
1520 | 4.07k | return (const char *) _bfd_ptr_bfd_null_error (abfd); |
1521 | 4.07k | } |
1522 | | |
1523 | | bool |
1524 | | _bfd_nosymbols_bfd_is_local_label_name (bfd *abfd ATTRIBUTE_UNUSED, |
1525 | | const char *name ATTRIBUTE_UNUSED) |
1526 | 0 | { |
1527 | 0 | return false; |
1528 | 0 | } |
1529 | | |
1530 | | alent * |
1531 | | _bfd_nosymbols_get_lineno (bfd *abfd, asymbol *sym ATTRIBUTE_UNUSED) |
1532 | 0 | { |
1533 | 0 | return (alent *) _bfd_ptr_bfd_null_error (abfd); |
1534 | 0 | } |
1535 | | |
1536 | | bool |
1537 | | _bfd_nosymbols_find_nearest_line |
1538 | | (bfd *abfd, |
1539 | | asymbol **symbols ATTRIBUTE_UNUSED, |
1540 | | asection *section ATTRIBUTE_UNUSED, |
1541 | | bfd_vma offset ATTRIBUTE_UNUSED, |
1542 | | const char **filename_ptr ATTRIBUTE_UNUSED, |
1543 | | const char **functionname_ptr ATTRIBUTE_UNUSED, |
1544 | | unsigned int *line_ptr ATTRIBUTE_UNUSED, |
1545 | | unsigned int *discriminator_ptr ATTRIBUTE_UNUSED) |
1546 | 3.83k | { |
1547 | 3.83k | return _bfd_bool_bfd_false_error (abfd); |
1548 | 3.83k | } |
1549 | | |
1550 | | bool |
1551 | | _bfd_nosymbols_find_nearest_line_with_alt |
1552 | | (bfd *abfd, |
1553 | | const char *alt_filename ATTRIBUTE_UNUSED, |
1554 | | asymbol **symbols ATTRIBUTE_UNUSED, |
1555 | | asection *section ATTRIBUTE_UNUSED, |
1556 | | bfd_vma offset ATTRIBUTE_UNUSED, |
1557 | | const char **filename_ptr ATTRIBUTE_UNUSED, |
1558 | | const char **functionname_ptr ATTRIBUTE_UNUSED, |
1559 | | unsigned int *line_ptr ATTRIBUTE_UNUSED, |
1560 | | unsigned int *discriminator_ptr ATTRIBUTE_UNUSED) |
1561 | 0 | { |
1562 | 0 | return _bfd_bool_bfd_false_error (abfd); |
1563 | 0 | } |
1564 | | |
1565 | | bool |
1566 | | _bfd_nosymbols_find_line (bfd *abfd, |
1567 | | asymbol **symbols ATTRIBUTE_UNUSED, |
1568 | | asymbol *symbol ATTRIBUTE_UNUSED, |
1569 | | const char **filename_ptr ATTRIBUTE_UNUSED, |
1570 | | unsigned int *line_ptr ATTRIBUTE_UNUSED) |
1571 | 3.57k | { |
1572 | 3.57k | return _bfd_bool_bfd_false_error (abfd); |
1573 | 3.57k | } |
1574 | | |
1575 | | bool |
1576 | | _bfd_nosymbols_find_inliner_info |
1577 | | (bfd *abfd, |
1578 | | const char **filename_ptr ATTRIBUTE_UNUSED, |
1579 | | const char **functionname_ptr ATTRIBUTE_UNUSED, |
1580 | | unsigned int *line_ptr ATTRIBUTE_UNUSED) |
1581 | 0 | { |
1582 | 0 | return _bfd_bool_bfd_false_error (abfd); |
1583 | 0 | } |
1584 | | |
1585 | | asymbol * |
1586 | | _bfd_nosymbols_bfd_make_debug_symbol (bfd *abfd) |
1587 | 0 | { |
1588 | 0 | return (asymbol *) _bfd_ptr_bfd_null_error (abfd); |
1589 | 0 | } |
1590 | | |
1591 | | long |
1592 | | _bfd_nosymbols_read_minisymbols (bfd *abfd, |
1593 | | bool dynamic ATTRIBUTE_UNUSED, |
1594 | | void **minisymsp ATTRIBUTE_UNUSED, |
1595 | | unsigned int *sizep ATTRIBUTE_UNUSED) |
1596 | 0 | { |
1597 | 0 | return _bfd_long_bfd_n1_error (abfd); |
1598 | 0 | } |
1599 | | |
1600 | | asymbol * |
1601 | | _bfd_nosymbols_minisymbol_to_symbol (bfd *abfd, |
1602 | | bool dynamic ATTRIBUTE_UNUSED, |
1603 | | const void *minisym ATTRIBUTE_UNUSED, |
1604 | | asymbol *sym ATTRIBUTE_UNUSED) |
1605 | 0 | { |
1606 | 0 | return (asymbol *) _bfd_ptr_bfd_null_error (abfd); |
1607 | 0 | } |
1608 | | |
1609 | | long |
1610 | | _bfd_nodynamic_get_synthetic_symtab (bfd *abfd, |
1611 | | long symcount ATTRIBUTE_UNUSED, |
1612 | | asymbol **syms ATTRIBUTE_UNUSED, |
1613 | | long dynsymcount ATTRIBUTE_UNUSED, |
1614 | | asymbol **dynsyms ATTRIBUTE_UNUSED, |
1615 | | asymbol **ret ATTRIBUTE_UNUSED) |
1616 | 4.25k | { |
1617 | 4.25k | return _bfd_long_bfd_n1_error (abfd); |
1618 | 4.25k | } |