* libnlm.h (nlm_obj_tdata): Rename hidden struct members to avoid
[deliverable/binutils-gdb.git] / bfd / nlmcode.h
1 /* NLM (NetWare Loadable Module) executable support for BFD.
2 Copyright (C) 1993 Free Software Foundation, Inc.
3
4 Written by Fred Fish @ Cygnus Support, using ELF support as the
5 template.
6
7 This file is part of BFD, the Binary File Descriptor library.
8
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 2 of the License, or
12 (at your option) any later version.
13
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
18
19 You should have received a copy of the GNU General Public License
20 along with this program; if not, write to the Free Software
21 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
22
23 #include <string.h> /* For strrchr and friends */
24 #include "bfd.h"
25 #include "sysdep.h"
26 #include "libbfd.h"
27 #include "libnlm.h"
28
29 #define Nlm_External_Fixed_Header NAME(Nlm,External_Fixed_Header)
30 #define Nlm_External_Version_Header NAME(Nlm,External_Version_Header)
31 #define Nlm_External_Copyright_Header NAME(Nlm,External_Copyright_Header)
32 #define Nlm_External_Extended_Header NAME(Nlm,External_Extended_Header)
33 #define Nlm_External_Custom_Header NAME(Nlm,External_Custom_Header)
34
35 #define nlm_symbol_type NAME(nlm,symbol_type)
36
37 #define nlm_get_symtab_upper_bound NAME(bfd_nlm,get_symtab_upper_bound)
38 #define nlm_get_symtab NAME(bfd_nlm,get_symtab)
39 #define nlm_make_empty_symbol NAME(bfd_nlm,make_empty_symbol)
40 #define nlm_print_symbol NAME(bfd_nlm,print_symbol)
41 #define nlm_get_symbol_info NAME(bfd_nlm,get_symbol_info)
42 #define nlm_set_arch_mach NAME(bfd_nlm,set_arch_mach)
43 #define nlm_object_p NAME(bfd_nlm,object_p)
44
45 #define MSB (~(~(unsigned long)0 >> 1))
46
47 /* Forward declarations of static functions */
48
49 static boolean add_bfd_section
50 PARAMS ((bfd *, char *, file_ptr, bfd_size_type, flagword));
51
52 static void nlm_swap_fixed_header_in
53 PARAMS ((bfd *, Nlm_External_Fixed_Header *, Nlm_Internal_Fixed_Header *));
54
55 static boolean nlm_swap_variable_header_in PARAMS ((bfd *));
56
57 static boolean nlm_swap_auxiliary_headers_in PARAMS ((bfd *));
58
59 static struct sec *section_from_nlm_index PARAMS ((bfd *, int));
60
61 static int nlm_section_from_bfd_section PARAMS ((bfd *, struct sec *));
62
63 static boolean nlm_slurp_symbol_table PARAMS ((bfd *, asymbol **));
64
65 static int nlm_symbol_from_bfd_symbol
66 PARAMS ((bfd *, struct symbol_cache_entry **));
67
68 static void nlm_map_symbols PARAMS ((bfd *));
69
70 /* Should perhaps use put_offset, put_word, etc. For now, the two versions
71 can be handled by explicitly specifying 32 bits or "the long type". */
72 #if ARCH_SIZE == 64
73 #define put_word bfd_h_put_64
74 #define get_word bfd_h_get_64
75 #endif
76 #if ARCH_SIZE == 32
77 #define put_word bfd_h_put_32
78 #define get_word bfd_h_get_32
79 #endif
80
81 bfd_target *
82 DEFUN (nlm_object_p, (abfd), bfd * abfd)
83 {
84 Nlm_External_Fixed_Header x_fxdhdr; /* Nlm file header, external form */
85 Nlm_Internal_Fixed_Header *i_fxdhdrp; /* Nlm file header, internal form */
86 int shindex;
87
88 /* Read in the fixed length portion of the NLM header in external format. */
89
90 if (bfd_read ((PTR) &x_fxdhdr, sizeof (x_fxdhdr), 1, abfd) !=
91 sizeof (x_fxdhdr))
92 {
93 bfd_error = system_call_error;
94 return (NULL);
95 }
96
97 /* Check to see if we have an NLM file by matching the NLM signature. */
98
99 if (strncmp (x_fxdhdr.signature, NLM_SIGNATURE, NLM_SIGNATURE_SIZE) != 0)
100 {
101 wrong:
102 bfd_error = wrong_format;
103 return (NULL);
104 }
105
106 /* There's no supported way to discover the endianess of an NLM, so test for
107 a sane version number after doing byte swapping appropriate for this
108 XVEC. (Hack alert!) */
109
110 if (get_word (abfd, (bfd_byte *) x_fxdhdr.version) > 0xFFFF)
111 {
112 goto wrong;
113 }
114
115 /* There's no supported way to check for 32 bit versus 64 bit addresses,
116 so ignore this distinction for now. (FIXME) */
117
118 /* Allocate an instance of the nlm_obj_tdata structure and hook it up to
119 the tdata pointer in the bfd. */
120
121 nlm_tdata (abfd) = (struct nlm_obj_tdata *)
122 bfd_zalloc (abfd, sizeof (struct nlm_obj_tdata));
123 if (nlm_tdata (abfd) == NULL)
124 {
125 bfd_error = no_memory;
126 return (NULL);
127 }
128
129 /* FIXME: Any `wrong' exits below here will leak memory (tdata). */
130
131 /* Swap in the rest of the fixed length header. */
132
133 i_fxdhdrp = nlm_fixed_header (abfd);
134 nlm_swap_fixed_header_in (abfd, &x_fxdhdr, i_fxdhdrp);
135
136 if (!nlm_swap_variable_header_in (abfd)
137 || !nlm_swap_auxiliary_headers_in (abfd)
138 || !add_bfd_section (abfd, NLM_CODE_NAME,
139 i_fxdhdrp -> codeImageOffset,
140 i_fxdhdrp -> codeImageSize,
141 SEC_CODE | SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS)
142 || !add_bfd_section (abfd, NLM_INITIALIZED_DATA_NAME,
143 i_fxdhdrp -> dataImageOffset,
144 i_fxdhdrp -> dataImageSize,
145 SEC_DATA | SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS)
146 || !add_bfd_section (abfd, NLM_UNINITIALIZED_DATA_NAME,
147 (file_ptr) 0,
148 i_fxdhdrp -> uninitializedDataSize,
149 SEC_DATA | SEC_ALLOC))
150 {
151 return (NULL);
152 }
153
154 return (abfd -> xvec);
155 }
156
157 /* Add a section to the bfd. */
158
159 static boolean
160 DEFUN (add_bfd_section, (abfd, name, offset, size, flags),
161 bfd *abfd AND
162 char *name AND
163 file_ptr offset AND
164 bfd_size_type size AND
165 flagword flags)
166 {
167 asection *newsect;
168
169 newsect = bfd_make_section (abfd, name);
170 if (newsect == NULL)
171 {
172 return (false);
173 }
174 newsect -> vma = 0; /* NLM's are relocatable. */
175 newsect -> _raw_size = size;
176 newsect -> filepos = offset;
177 newsect -> flags = flags;
178 newsect -> alignment_power = bfd_log2 (0); /* FIXME */
179 return (true);
180 }
181
182
183 /* Translate an NLM fixed length file header in external format into an NLM
184 file header in internal format. */
185
186 static void
187 DEFUN (nlm_swap_fixed_header_in, (abfd, src, dst),
188 bfd * abfd AND
189 Nlm_External_Fixed_Header * src AND
190 Nlm_Internal_Fixed_Header * dst)
191 {
192 memcpy (dst -> signature, src -> signature, NLM_SIGNATURE_SIZE);
193 memcpy (dst -> moduleName, src -> moduleName, NLM_MODULE_NAME_SIZE);
194 dst -> version =
195 get_word (abfd, (bfd_byte *) src -> version);
196 dst -> codeImageOffset =
197 get_word (abfd, (bfd_byte *) src -> codeImageOffset);
198 dst -> codeImageSize =
199 get_word (abfd, (bfd_byte *) src -> codeImageSize);
200 dst -> dataImageOffset =
201 get_word (abfd, (bfd_byte *) src -> dataImageOffset);
202 dst -> dataImageSize =
203 get_word (abfd, (bfd_byte *) src -> dataImageSize);
204 dst -> uninitializedDataSize =
205 get_word (abfd, (bfd_byte *) src -> uninitializedDataSize);
206 dst -> customDataOffset =
207 get_word (abfd, (bfd_byte *) src -> customDataOffset);
208 dst -> customDataSize =
209 get_word (abfd, (bfd_byte *) src -> customDataSize);
210 dst -> moduleDependencyOffset =
211 get_word (abfd, (bfd_byte *) src -> moduleDependencyOffset);
212 dst -> numberOfModuleDependencies =
213 get_word (abfd, (bfd_byte *) src -> numberOfModuleDependencies);
214 dst -> relocationFixupOffset =
215 get_word (abfd, (bfd_byte *) src -> relocationFixupOffset);
216 dst -> numberOfRelocationFixups =
217 get_word (abfd, (bfd_byte *) src -> numberOfRelocationFixups);
218 dst -> externalReferencesOffset =
219 get_word (abfd, (bfd_byte *) src -> externalReferencesOffset);
220 dst -> numberOfExternalReferences =
221 get_word (abfd, (bfd_byte *) src -> numberOfExternalReferences);
222 dst -> publicsOffset =
223 get_word (abfd, (bfd_byte *) src -> publicsOffset);
224 dst -> numberOfPublics =
225 get_word (abfd, (bfd_byte *) src -> numberOfPublics);
226 dst -> debugInfoOffset =
227 get_word (abfd, (bfd_byte *) src -> debugInfoOffset);
228 dst -> numberOfDebugRecords =
229 get_word (abfd, (bfd_byte *) src -> numberOfDebugRecords);
230 dst -> codeStartOffset =
231 get_word (abfd, (bfd_byte *) src -> codeStartOffset);
232 dst -> exitProcedureOffset =
233 get_word (abfd, (bfd_byte *) src -> exitProcedureOffset);
234 dst -> checkUnloadProcedureOffset =
235 get_word (abfd, (bfd_byte *) src -> checkUnloadProcedureOffset);
236 dst -> moduleType =
237 get_word (abfd, (bfd_byte *) src -> moduleType);
238 dst -> flags =
239 get_word (abfd, (bfd_byte *) src -> flags);
240 }
241
242 /* Read and swap in the variable length header. All the fields must
243 exist in the NLM, and must exist in the order they are read here. */
244
245 static boolean
246 DEFUN (nlm_swap_variable_header_in, (abfd),
247 bfd * abfd)
248 {
249 unsigned char temp [TARGET_LONG_SIZE];
250
251 /* Read the description length and text members. */
252
253 if (bfd_read ((PTR) &nlm_variable_header (abfd) -> descriptionLength,
254 sizeof (nlm_variable_header (abfd) -> descriptionLength),
255 1, abfd) !=
256 sizeof (nlm_variable_header (abfd) -> descriptionLength))
257 {
258 bfd_error = system_call_error;
259 return (false);
260 }
261 if (bfd_read ((PTR) nlm_variable_header (abfd) -> descriptionText,
262 nlm_variable_header (abfd) -> descriptionLength + 1,
263 1, abfd) !=
264 nlm_variable_header (abfd) -> descriptionLength + 1)
265 {
266 bfd_error = system_call_error;
267 return (false);
268 }
269
270 /* Read and convert the stackSize field. */
271
272 if (bfd_read ((PTR) temp, sizeof (temp), 1, abfd) != sizeof (temp))
273 {
274 bfd_error = system_call_error;
275 return (false);
276 }
277 nlm_variable_header (abfd) -> stackSize = get_word (abfd, (bfd_byte *) temp);
278
279 /* Read and convert the reserved field. */
280
281 if (bfd_read ((PTR) temp, sizeof (temp), 1, abfd) != sizeof (temp))
282 {
283 bfd_error = system_call_error;
284 return (false);
285 }
286 nlm_variable_header (abfd) -> reserved = get_word (abfd, (bfd_byte *) temp);
287
288 /* Read the oldThreadName field. This field is a fixed length string. */
289
290 if (bfd_read ((PTR) nlm_variable_header (abfd) -> oldThreadName,
291 sizeof (nlm_variable_header (abfd) -> oldThreadName),
292 1, abfd) !=
293 sizeof (nlm_variable_header (abfd) -> oldThreadName))
294 {
295 bfd_error = system_call_error;
296 return (false);
297 }
298
299 /* Read the screen name length and text members. */
300
301 if (bfd_read ((PTR) &nlm_variable_header (abfd) -> screenNameLength,
302 sizeof (nlm_variable_header (abfd) -> screenNameLength),
303 1, abfd) !=
304 sizeof (nlm_variable_header (abfd) -> screenNameLength))
305 {
306 bfd_error = system_call_error;
307 return (false);
308 }
309 if (bfd_read ((PTR) nlm_variable_header (abfd) -> screenName,
310 nlm_variable_header (abfd) -> screenNameLength + 1,
311 1, abfd) !=
312 nlm_variable_header (abfd) -> screenNameLength + 1)
313 {
314 bfd_error = system_call_error;
315 return (false);
316 }
317
318 /* Read the thread name length and text members. */
319
320 if (bfd_read ((PTR) &nlm_variable_header (abfd) -> threadNameLength,
321 sizeof (nlm_variable_header (abfd) -> threadNameLength),
322 1, abfd) !=
323 sizeof (nlm_variable_header (abfd) -> threadNameLength))
324 {
325 bfd_error = system_call_error;
326 return (false);
327 }
328 if (bfd_read ((PTR) nlm_variable_header (abfd) -> threadName,
329 nlm_variable_header (abfd) -> threadNameLength + 1,
330 1, abfd) !=
331 nlm_variable_header (abfd) -> threadNameLength + 1)
332 {
333 bfd_error = system_call_error;
334 return (false);
335 }
336 return (true);
337 }
338
339 /* Read and swap in the contents of all the auxiliary headers. Because of
340 the braindead design, we have to do strcmps on strings of indeterminate
341 length to figure out what each auxiliary header is. Even worse, we have
342 no way of knowing how many auxiliary headers there are or where the end
343 of the auxiliary headers are, except by finding something that doesn't
344 look like a known auxiliary header. This means that the first new type
345 of auxiliary header added will break all existing tools that don't
346 recognize it. */
347
348 static boolean
349 DEFUN (nlm_swap_auxiliary_headers_in, (abfd),
350 bfd * abfd)
351 {
352 unsigned char temp [TARGET_LONG_SIZE];
353 unsigned char tempstr [16];
354 long position;
355
356 for (;;)
357 {
358 position = bfd_tell (abfd);
359 if (bfd_read ((PTR) tempstr, sizeof (tempstr), 1, abfd) !=
360 sizeof (tempstr))
361 {
362 bfd_error = system_call_error;
363 return (false);
364 }
365 if (bfd_seek (abfd, position, SEEK_SET) == -1)
366 {
367 bfd_error = system_call_error;
368 return (false);
369 }
370 if (strncmp (tempstr, "VeRsIoN#", 8) == 0)
371 {
372 Nlm_External_Version_Header thdr;
373 if (bfd_read ((PTR) &thdr, sizeof (thdr), 1, abfd) != sizeof (thdr))
374 {
375 bfd_error = system_call_error;
376 return (false);
377 }
378 memcpy (nlm_version_header (abfd) -> stamp, thdr.stamp,
379 sizeof (thdr.stamp));
380 nlm_version_header (abfd) -> majorVersion =
381 get_word (abfd, (bfd_byte *) thdr.majorVersion);
382 nlm_version_header (abfd) -> minorVersion =
383 get_word (abfd, (bfd_byte *) thdr.minorVersion);
384 nlm_version_header (abfd) -> revision =
385 get_word (abfd, (bfd_byte *) thdr.revision);
386 nlm_version_header (abfd) -> year =
387 get_word (abfd, (bfd_byte *) thdr.year);
388 nlm_version_header (abfd) -> month =
389 get_word (abfd, (bfd_byte *) thdr.month);
390 nlm_version_header (abfd) -> day =
391 get_word (abfd, (bfd_byte *) thdr.day);
392 }
393 else if (strncmp (tempstr, "MeSsAgEs", 8) == 0)
394 {
395 Nlm_External_Extended_Header thdr;
396 if (bfd_read ((PTR) &thdr, sizeof (thdr), 1, abfd) != sizeof (thdr))
397 {
398 bfd_error = system_call_error;
399 return (false);
400 }
401 memcpy (nlm_extended_header (abfd) -> stamp, thdr.stamp,
402 sizeof (thdr.stamp));
403 nlm_extended_header (abfd) -> languageID =
404 get_word (abfd, (bfd_byte *) thdr.languageID);
405 nlm_extended_header (abfd) -> messageFileOffset =
406 get_word (abfd, (bfd_byte *) thdr.messageFileOffset);
407 nlm_extended_header (abfd) -> messageFileLength =
408 get_word (abfd, (bfd_byte *) thdr.messageFileLength);
409 nlm_extended_header (abfd) -> messageCount =
410 get_word (abfd, (bfd_byte *) thdr.messageCount);
411 nlm_extended_header (abfd) -> helpFileOffset =
412 get_word (abfd, (bfd_byte *) thdr.helpFileOffset);
413 nlm_extended_header (abfd) -> helpFileLength =
414 get_word (abfd, (bfd_byte *) thdr.helpFileLength);
415 nlm_extended_header (abfd) -> RPCDataOffset =
416 get_word (abfd, (bfd_byte *) thdr.RPCDataOffset);
417 nlm_extended_header (abfd) -> RPCDataLength =
418 get_word (abfd, (bfd_byte *) thdr.RPCDataLength);
419 nlm_extended_header (abfd) -> sharedCodeOffset =
420 get_word (abfd, (bfd_byte *) thdr.sharedCodeOffset);
421 nlm_extended_header (abfd) -> sharedCodeLength =
422 get_word (abfd, (bfd_byte *) thdr.sharedCodeLength);
423 nlm_extended_header (abfd) -> sharedDataOffset =
424 get_word (abfd, (bfd_byte *) thdr.sharedDataOffset);
425 nlm_extended_header (abfd) -> sharedDataLength =
426 get_word (abfd, (bfd_byte *) thdr.sharedDataLength);
427 nlm_extended_header (abfd) -> sharedRelocationFixupOffset =
428 get_word (abfd, (bfd_byte *) thdr.sharedRelocationFixupOffset);
429 nlm_extended_header (abfd) -> sharedRelocationFixupCount =
430 get_word (abfd, (bfd_byte *) thdr.sharedRelocationFixupCount);
431 nlm_extended_header (abfd) -> sharedExternalReferenceOffset =
432 get_word (abfd, (bfd_byte *) thdr.sharedExternalReferenceOffset);
433 nlm_extended_header (abfd) -> sharedExternalReferenceCount =
434 get_word (abfd, (bfd_byte *) thdr.sharedExternalReferenceCount);
435 nlm_extended_header (abfd) -> sharedPublicsOffset =
436 get_word (abfd, (bfd_byte *) thdr.sharedPublicsOffset);
437 nlm_extended_header (abfd) -> sharedPublicsCount =
438 get_word (abfd, (bfd_byte *) thdr.sharedPublicsCount);
439 nlm_extended_header (abfd) -> SharedInitializationOffset =
440 get_word (abfd, (bfd_byte *) thdr.sharedInitializationOffset);
441 nlm_extended_header (abfd) -> SharedExitProcedureOffset =
442 get_word (abfd, (bfd_byte *) thdr.SharedExitProcedureOffset);
443 nlm_extended_header (abfd) -> productID =
444 get_word (abfd, (bfd_byte *) thdr.productID);
445 nlm_extended_header (abfd) -> reserved0 =
446 get_word (abfd, (bfd_byte *) thdr.reserved0);
447 nlm_extended_header (abfd) -> reserved1 =
448 get_word (abfd, (bfd_byte *) thdr.reserved1);
449 nlm_extended_header (abfd) -> reserved2 =
450 get_word (abfd, (bfd_byte *) thdr.reserved2);
451 nlm_extended_header (abfd) -> reserved3 =
452 get_word (abfd, (bfd_byte *) thdr.reserved3);
453 nlm_extended_header (abfd) -> reserved4 =
454 get_word (abfd, (bfd_byte *) thdr.reserved4);
455 nlm_extended_header (abfd) -> reserved5 =
456 get_word (abfd, (bfd_byte *) thdr.reserved5);
457 }
458 else if (strncmp (tempstr, "CuStHeAd", 8) == 0)
459 {
460 Nlm_External_Custom_Header thdr;
461 if (bfd_read ((PTR) &thdr, sizeof (thdr), 1, abfd) != sizeof (thdr))
462 {
463 bfd_error = system_call_error;
464 return (false);
465 }
466 memcpy (nlm_custom_header (abfd) -> stamp, thdr.stamp,
467 sizeof (thdr.stamp));
468 nlm_custom_header (abfd) -> dataLength =
469 get_word (abfd, (bfd_byte *) thdr.dataLength);
470 nlm_custom_header (abfd) -> debugRecOffset =
471 get_word (abfd, (bfd_byte *) thdr.debugRecOffset);
472 nlm_custom_header (abfd) -> debugRecLength =
473 get_word (abfd, (bfd_byte *) thdr.debugRecLength);
474 }
475 else if (strncmp (tempstr, "CoPyRiGhT=", 10) == 0)
476 {
477 Nlm_External_Copyright_Header thdr;
478 if (bfd_read ((PTR) &thdr, sizeof (thdr), 1, abfd) != sizeof (thdr))
479 {
480 bfd_error = system_call_error;
481 return (false);
482 }
483 memcpy (nlm_copyright_header (abfd) -> stamp, thdr.stamp,
484 sizeof (thdr.stamp));
485 nlm_copyright_header (abfd) -> copyrightMessageLength =
486 get_word (abfd, (bfd_byte *) thdr.copyrightMessageLength);
487 /* The copyright message is a variable length string. */
488 if (bfd_read ((PTR) nlm_copyright_header (abfd) -> copyrightMessage,
489 nlm_copyright_header (abfd) -> copyrightMessageLength + 1,
490 1, abfd) !=
491 nlm_copyright_header (abfd) -> copyrightMessageLength + 1)
492 {
493 bfd_error = system_call_error;
494 return (false);
495 }
496 }
497 else
498 {
499 break;
500 }
501 }
502 }
503
504 /* We read the NLM's public symbols and use it to generate a bfd symbol
505 table (hey, it's better than nothing) on a one-for-one basis. Thus
506 use the number of public symbols as the number of bfd symbols we will
507 have once we actually get around to reading them in.
508
509 Return the number of bytes required to hold the symtab vector, based on
510 the count plus 1, since we will NULL terminate the vector allocated based
511 on this size. */
512
513 unsigned int
514 DEFUN (nlm_get_symtab_upper_bound, (abfd), bfd * abfd)
515 {
516 Nlm_Internal_Fixed_Header *i_fxdhdrp; /* Nlm file header, internal form */
517 unsigned int symcount;
518 unsigned int symtab_size = 0;
519
520 i_fxdhdrp = nlm_fixed_header (abfd);
521 symcount = i_fxdhdrp -> numberOfPublics;
522 symtab_size = (symcount + 1) * (sizeof (asymbol));
523 return (symtab_size);
524 }
525
526 /* Note that bfd_get_symcount is guaranteed to be zero if slurping the
527 symbol table fails. */
528
529 unsigned int
530 DEFUN (nlm_get_symtab, (abfd, alocation),
531 bfd *abfd AND
532 asymbol **alocation)
533 {
534 nlm_slurp_symbol_table (abfd, alocation);
535 return (bfd_get_symcount (abfd));
536 }
537
538 asymbol *
539 DEFUN (nlm_make_empty_symbol, (abfd), /* FIXME! */
540 bfd * abfd)
541 {
542 asymbol *new = (asymbol *) bfd_zalloc (abfd, sizeof (asymbol));
543 new -> the_bfd = abfd;
544 return new;
545 }
546
547 void
548 DEFUN (nlm_get_symbol_info, (ignore_abfd, symbol, ret),
549 bfd * ignore_abfd AND
550 asymbol * symbol AND
551 symbol_info * ret)
552 {
553 bfd_symbol_info (symbol, ret);
554 }
555
556 boolean
557 DEFUN (nlm_set_arch_mach, (abfd, arch, machine),
558 bfd * abfd AND
559 enum bfd_architecture arch AND
560 unsigned long machine)
561 {
562 return false;
563 }
564
565 /* Slurp in nlm symbol table.
566
567 In the external (in-file) form, NLM export records are variable length,
568 with the following form:
569
570 1 byte length of the symbol name (N)
571 N bytes the symbol name
572 4 bytes the symbol offset from start of it's section
573
574 Note that we currently ignore the internal debug records. There is
575 a lot of duplication between the export records and the internal debug
576 records. We may in the future, want to merge the information from the
577 debug records with the information from the export records to produce
578 a more complete symbol table, treating additional information from the
579 debug records as static symbols. (FIXME)
580
581 If SYMPTRS is non-NULL, the bfd symbols are copied to where it points.
582
583 When we return, the bfd symcount is either zero or contains the correct
584 number of symbols.
585 */
586
587 static boolean
588 DEFUN (nlm_slurp_symbol_table, (abfd, symptrs),
589 bfd *abfd AND
590 asymbol **symptrs) /* Buffer for generated bfd symbols */
591 {
592 Nlm_Internal_Fixed_Header *i_fxdhdrp; /* Nlm file header, internal form */
593 int symcount; /* Number of external NLM symbols */
594 int idx;
595 nlm_symbol_type *sym; /* Pointer to current bfd symbol */
596 nlm_symbol_type *symbase; /* Buffer for generated bfd symbols */
597 char symlength; /* Symbol length read into here */
598 long symoffset; /* Symbol offset read into here */
599
600 if (bfd_get_outsymbols (abfd) != NULL)
601 {
602 return (true);
603 }
604
605 /* Read each raw NLM symbol, using the information to create a canonical bfd
606 symbol table entry.
607
608 Note that we allocate the initial bfd canonical symbol buffer based on a
609 one-to-one mapping of the NLM symbols to canonical symbols. We actually
610 use all the NLM symbols, so there will be no space left over at the end.
611 When we have all the symbols, we build the caller's pointer vector. */
612
613 abfd -> symcount = 0;
614 i_fxdhdrp = nlm_fixed_header (abfd);
615 symcount = i_fxdhdrp -> numberOfPublics;
616 if (symcount == 0)
617 {
618 return (true);
619 }
620 if (bfd_seek (abfd, i_fxdhdrp -> publicsOffset, SEEK_SET) == -1)
621 {
622 bfd_error = system_call_error;
623 return (false);
624 }
625 symbase = (nlm_symbol_type *)
626 bfd_zalloc (abfd, symcount * sizeof (nlm_symbol_type));
627 sym = symbase;
628
629 /* We use the bfd's symcount directly as the control count, so that early
630 termination of the loop leaves the symcount correct for the symbols that
631 were read. */
632
633 while (abfd -> symcount < symcount)
634 {
635 if (bfd_read ((PTR) &symlength, sizeof (symlength), 1, abfd)
636 != sizeof (symlength))
637 {
638 bfd_error = system_call_error;
639 return (false);
640 }
641 sym -> symbol.the_bfd = abfd;
642 sym -> symbol.name = bfd_alloc (abfd, symlength + 1);
643 if (bfd_read ((PTR) sym -> symbol.name, symlength, 1, abfd)
644 != symlength)
645 {
646 bfd_error = system_call_error;
647 return (false);
648 }
649 if (bfd_read ((PTR) &symoffset, sizeof (symoffset), 1, abfd)
650 != sizeof (symoffset))
651 {
652 bfd_error = system_call_error;
653 return (false);
654 }
655 sym -> symbol.flags = BSF_GLOBAL | BSF_EXPORT;
656 sym -> symbol.value = get_word (abfd, (bfd_byte *) &symoffset);
657 if (sym -> symbol.value & MSB)
658 {
659 sym -> symbol.value &= ~MSB;
660 sym -> symbol.flags |= BSF_FUNCTION;
661 sym -> symbol.section =
662 bfd_get_section_by_name (abfd, NLM_CODE_NAME);
663 }
664 else
665 {
666 sym -> symbol.section =
667 bfd_get_section_by_name (abfd, NLM_INITIALIZED_DATA_NAME);
668 }
669 abfd -> symcount++;
670 sym++;
671 }
672
673 /* Fill in the user's symbol pointer vector if needed. */
674
675 if (symptrs != NULL)
676 {
677 sym = symbase;
678 symcount = abfd -> symcount;
679 while (symcount-- > 0)
680 {
681 *symptrs++ = &sym -> symbol;
682 sym++;
683 }
684 *symptrs = NULL; /* Final NULL pointer */
685 }
686
687 return (true);
688 }
689
This page took 0.062831 seconds and 5 git commands to generate.