a4431cc2c86c5b755e44c193535becb5676a4e08
[deliverable/binutils-gdb.git] / bfd / archive.c
1
2 /*** archive.c -- an attempt at combining the machine-independent parts of
3 archives */
4
5 /* Copyright (C) 1990, 1991 Free Software Foundation, Inc.
6
7 This file is part of BFD, the Binary File Diddler.
8
9 BFD 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 1, or (at your option)
12 any later version.
13
14 BFD 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 BFD; see the file COPYING. If not, write to
21 the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
22
23
24 /* Assumes:
25 o - all archive elements start on an even boundary, newline padded;
26 o - all arch headers are char *;
27 o - all arch headers are the same size (across architectures).
28 */
29
30 /* $Id$ */
31
32 #include <sysdep.h>
33 #include "bfd.h"
34 #include "libbfd.h"
35 #include "ar.h"
36 #include "ranlib.h"
37
38 #ifdef GNU960
39 #define BFD_GNU960_ARMAG(abfd) (BFD_COFF_FILE_P((abfd)) ? ARMAG : ARMAGB)
40 #endif
41
42 /* We keep a cache of archive filepointers to archive elements to
43 speed up searching the archive by filepos. We only add an entry to
44 the cache when we actually read one. We also don't sort the cache;
45 it's short enough to search linearly.
46 Note that the pointers here point to the front of the ar_hdr, not
47 to the front of the contents!
48 */
49 struct ar_cache {
50 file_ptr ptr;
51 bfd* arelt;
52 struct ar_cache *next;
53 };
54
55 #define ar_padchar(abfd) ((abfd)->xvec->ar_pad_char)
56 #define ar_maxnamelen(abfd) ((abfd)->xvec->ar_max_namelen)
57
58 #define arch_hdr(bfd) ((struct ar_hdr *) \
59 (((struct areltdata *)((bfd)->arelt_data))->arch_header))
60 \f
61 boolean
62 _bfd_generic_mkarchive (abfd)
63 bfd *abfd;
64 {
65 set_tdata (abfd, bfd_zalloc(abfd, sizeof (struct artdata)));
66
67 if (bfd_ardata (abfd) == NULL) {
68 bfd_error = no_memory;
69 return false;
70 }
71 bfd_ardata(abfd)->cache = 0;
72 return true;
73 }
74
75 symindex
76 bfd_get_next_mapent (abfd, prev, entry)
77 bfd *abfd;
78 symindex prev;
79 carsym **entry;
80 {
81 if (!bfd_has_map (abfd)) {
82 bfd_error = invalid_operation;
83 return BFD_NO_MORE_SYMBOLS;
84 }
85
86 if (prev == BFD_NO_MORE_SYMBOLS) prev = 0;
87 else if (++prev >= bfd_ardata (abfd)->symdef_count)
88 return BFD_NO_MORE_SYMBOLS;
89
90 *entry = (bfd_ardata (abfd)->symdefs + prev);
91 return prev;
92 }
93
94
95 /* To be called by backends only */
96 bfd *
97 _bfd_create_empty_archive_element_shell (obfd)
98 bfd *obfd;
99 {
100 bfd *nbfd;
101
102 nbfd = new_bfd_contained_in(obfd);
103 if (nbfd == NULL) {
104 bfd_error = no_memory;
105 return NULL;
106 }
107 return nbfd;
108 }
109
110 boolean
111 bfd_set_archive_head (output_archive, new_head)
112 bfd *output_archive, *new_head;
113 {
114
115 output_archive->archive_head = new_head;
116 return true;
117 }
118
119 bfd *
120 look_for_bfd_in_cache (arch_bfd, filepos)
121 bfd *arch_bfd;
122 file_ptr filepos;
123 {
124 struct ar_cache *current;
125
126 for (current = bfd_ardata (arch_bfd)->cache; current != NULL;
127 current = current->next)
128 if (current->ptr == filepos) return current->arelt;
129
130 return NULL;
131 }
132
133 /* Kind of stupid to call cons for each one, but we don't do too many */
134 boolean
135 add_bfd_to_cache (arch_bfd, filepos, new_elt)
136 bfd *arch_bfd, *new_elt;
137 file_ptr filepos;
138 {
139 struct ar_cache *new_cache = (struct ar_cache *)
140 bfd_zalloc(arch_bfd, sizeof (struct ar_cache));
141
142 if (new_cache == NULL) {
143 bfd_error = no_memory;
144 return false;
145 }
146
147 new_cache->ptr = filepos;
148 new_cache->arelt = new_elt;
149 new_cache->next = (struct ar_cache *)NULL;
150 if (bfd_ardata (arch_bfd)->cache == NULL)
151 bfd_ardata (arch_bfd)->cache = new_cache;
152 else {
153 struct ar_cache *current = bfd_ardata (arch_bfd)->cache;
154
155 for (; current->next != NULL; current = current->next);
156 current->next = new_cache;
157 }
158
159 return true;
160 }
161
162 \f
163
164 /* The name begins with space. Hence the rest of the name is an index into
165 the string table. */
166
167 char *
168 get_extended_arelt_filename (arch, name)
169 bfd *arch;
170 char *name;
171 {
172 #ifndef errno
173 extern int errno;
174 #endif
175 unsigned long index = 0;
176
177 /* Should extract string so that I can guarantee not to overflow into
178 the next region, but I"m too lazy. */
179 errno = 0;
180 index = strtol (name, NULL, 10);
181 if (errno != 0) {
182 bfd_error = malformed_archive;
183 return NULL;
184 }
185
186 return bfd_ardata (arch)->extended_names + index;
187 }
188
189 /* This functions reads an arch header and returns an areltdata pointer, or
190 NULL on error.
191
192 Presumes the file pointer is already in the right place (ie pointing
193 to the ar_hdr in the file). Moves the file pointer; on success it
194 should be pointing to the front of the file contents; on failure it
195 could have been moved arbitrarily.
196 */
197
198 struct areltdata *
199 snarf_ar_hdr (abfd)
200 bfd *abfd;
201 {
202 #ifndef errno
203 extern int errno;
204 #endif
205
206 struct ar_hdr hdr;
207 char *hdrp = (char *) &hdr;
208 unsigned int parsed_size;
209 struct areltdata *ared;
210 char *filename = NULL;
211 unsigned int namelen = 0;
212 unsigned int allocsize = sizeof (struct areltdata) + sizeof (struct ar_hdr);
213 char *allocptr;
214
215 if (bfd_read ((PTR)hdrp, 1, sizeof (struct ar_hdr), abfd)
216 != sizeof (struct ar_hdr)) {
217 bfd_error = no_more_archived_files;
218 return NULL;
219 }
220 if (strncmp ((hdr.ar_fmag), ARFMAG, 2)) {
221 bfd_error = malformed_archive;
222 return NULL;
223 }
224
225 errno = 0;
226 parsed_size = strtol (hdr.ar_size, NULL, 10);
227 if (errno != 0) {
228 bfd_error = malformed_archive;
229 return NULL;
230 }
231
232 /* extract the filename from the archive */
233 if (hdr.ar_name[0] == ' ' && bfd_ardata (abfd)->extended_names != NULL) {
234 filename = get_extended_arelt_filename (abfd, hdr.ar_name);
235 if (filename == NULL) {
236 bfd_error = malformed_archive;
237 return NULL;
238 }
239 }
240 else
241 {
242 /* We judge the end of the name by looking for a space or a
243 padchar */
244
245 namelen = 0;
246
247 while (namelen < (unsigned)ar_maxnamelen(abfd) &&
248 ( hdr.ar_name[namelen] != 0 &&
249 hdr.ar_name[namelen] != ' ' &&
250 hdr.ar_name[namelen] != ar_padchar(abfd))) {
251 namelen++;
252 }
253
254 allocsize += namelen + 1;
255 }
256
257 allocptr = bfd_zalloc(abfd, allocsize);
258 if (allocptr == NULL) {
259 bfd_error = no_memory;
260 return NULL;
261 }
262
263 ared = (struct areltdata *) allocptr;
264
265 ared->arch_header = allocptr + sizeof (struct areltdata);
266 memcpy ((char *) ared->arch_header, &hdr, sizeof (struct ar_hdr));
267 ared->parsed_size = parsed_size;
268
269 if (filename != NULL) ared->filename = filename;
270 else {
271 ared->filename = allocptr + (sizeof (struct areltdata) +
272 sizeof (struct ar_hdr));
273 if (namelen)
274 memcpy (ared->filename, hdr.ar_name, namelen);
275 ared->filename[namelen] = '\0';
276 }
277
278 return ared;
279 }
280 \f
281 bfd *
282 get_elt_at_filepos (archive, filepos)
283 bfd *archive;
284 file_ptr filepos;
285 {
286 struct areltdata *new_areldata;
287 bfd *n_nfd;
288
289 n_nfd = look_for_bfd_in_cache (archive, filepos);
290 if (n_nfd) return n_nfd;
291
292 if (0 > bfd_seek (archive, filepos, SEEK_SET)) {
293 bfd_error = system_call_error;
294 return NULL;
295 }
296
297 if ((new_areldata = snarf_ar_hdr (archive)) == NULL) return NULL;
298
299 n_nfd = _bfd_create_empty_archive_element_shell (archive);
300 if (n_nfd == NULL) {
301 bfd_release (archive, (PTR)new_areldata);
302 return NULL;
303 }
304 n_nfd->origin = bfd_tell (archive);
305 n_nfd->arelt_data = (PTR) new_areldata;
306 n_nfd->filename = new_areldata->filename;
307
308 if (add_bfd_to_cache (archive, filepos, n_nfd))
309 return n_nfd;
310
311 /* huh? */
312 bfd_release (archive, (PTR)n_nfd);
313 bfd_release (archive, (PTR)new_areldata);
314 return NULL;
315 }
316
317 bfd *
318 bfd_get_elt_at_index (abfd, index)
319 bfd *abfd;
320 int index;
321 {
322 bfd *result =
323 get_elt_at_filepos
324 (abfd, (bfd_ardata (abfd)->symdefs + index)->file_offset);
325 return result;
326 }
327
328 /* If you've got an archive, call this to read each subfile. */
329 bfd *
330 bfd_openr_next_archived_file (archive, last_file)
331 bfd *archive, *last_file;
332 {
333
334 if ((bfd_get_format (archive) != bfd_archive) ||
335 (archive->direction == write_direction)) {
336 bfd_error = invalid_operation;
337 return NULL;
338 }
339
340
341 return BFD_SEND (archive,
342 openr_next_archived_file,
343 (archive,
344 last_file));
345
346 }
347
348 bfd *bfd_generic_openr_next_archived_file(archive, last_file)
349 bfd *archive;
350 bfd *last_file;
351 {
352 file_ptr filestart;
353
354 if (!last_file)
355 filestart = bfd_ardata (archive)->first_file_filepos;
356 else {
357 unsigned int size = arelt_size(last_file);
358 /* Pad to an even boundary... */
359 filestart = last_file->origin + size + size%2;
360 }
361
362 return get_elt_at_filepos (archive, filestart);
363 }
364 \f
365
366 bfd_target *
367 bfd_generic_archive_p (abfd)
368 bfd *abfd;
369 {
370 char armag[SARMAG+1];
371
372 if (bfd_read ((PTR)armag, 1, SARMAG, abfd) != SARMAG) {
373 bfd_error = wrong_format;
374 return 0;
375 }
376
377 #ifdef GNU960
378 if (strncmp (armag, BFD_GNU960_ARMAG(abfd), SARMAG)) return 0;
379 #else
380 if (strncmp (armag, ARMAG, SARMAG)) return 0;
381 #endif
382
383 /* We are setting bfd_ardata(abfd) here, but since bfd_ardata
384 involves a cast, we can't do it as the left operand of assignment. */
385 set_tdata (abfd, bfd_zalloc(abfd,sizeof (struct artdata)));
386
387 if (bfd_ardata (abfd) == NULL) {
388 bfd_error = no_memory;
389 return 0;
390 }
391
392 bfd_ardata (abfd)->first_file_filepos = SARMAG;
393
394 if (!BFD_SEND (abfd, _bfd_slurp_armap, (abfd))) {
395 bfd_release(abfd, bfd_ardata (abfd));
396 abfd->tdata = NULL;
397 return 0;
398 }
399
400 if (!BFD_SEND (abfd, _bfd_slurp_extended_name_table, (abfd))) {
401 bfd_release(abfd, bfd_ardata (abfd));
402 abfd->tdata = NULL;
403 return 0;
404 }
405
406 return abfd->xvec;
407 }
408
409 /* Returns false on error, true otherwise */
410 boolean
411 bfd_slurp_bsd_armap (abfd)
412 bfd *abfd;
413 {
414 int i;
415 struct areltdata *mapdata;
416 char nextname[17];
417 unsigned int counter = 0;
418 int *raw_armap, *rbase;
419 struct artdata *ardata = bfd_ardata (abfd);
420 char *stringbase;
421
422 /* FIXME, if the read fails, this routine quietly returns "true"!!
423 It should probably do that if the read gives 0 bytes (empty archive),
424 but fail for any other size... */
425 if (bfd_read ((PTR)nextname, 1, 16, abfd) == 16) {
426 /* The archive has at least 16 bytes in it */
427 bfd_seek (abfd, -16L, SEEK_CUR);
428
429 /* This should be using RANLIBMAG, but at least it can be grepped for
430 in this comment. */
431 if (strncmp (nextname, "__.SYMDEF ", 16)) {
432 bfd_has_map (abfd) = false;
433 return true;
434 }
435
436 mapdata = snarf_ar_hdr (abfd);
437 if (mapdata == NULL) return false;
438
439 raw_armap = (int *) bfd_zalloc(abfd,mapdata->parsed_size);
440 if (raw_armap == NULL) {
441 bfd_error = no_memory;
442 byebye:
443 bfd_release (abfd, (PTR)mapdata);
444 return false;
445 }
446
447 if (bfd_read ((PTR)raw_armap, 1, mapdata->parsed_size, abfd) !=
448 mapdata->parsed_size) {
449 bfd_error = malformed_archive;
450 bfd_release (abfd, (PTR)raw_armap);
451 goto byebye;
452 }
453
454 ardata->symdef_count = bfd_h_get_32(abfd, raw_armap) / sizeof (struct symdef);
455 ardata->cache = 0;
456 rbase = raw_armap+1;
457 ardata->symdefs = (carsym *) rbase;
458 stringbase = ((char *) (ardata->symdefs + ardata->symdef_count)) + 4;
459
460 for (;counter < ardata->symdef_count; counter++) {
461 struct symdef *sym = ((struct symdef *) rbase) + counter;
462 sym->s.name = bfd_h_get_32(abfd, &(sym->s.string_offset)) + stringbase;
463 sym->file_offset = bfd_h_get_32(abfd, &(sym->file_offset));
464 }
465
466 ardata->first_file_filepos = bfd_tell (abfd);
467 /* Pad to an even boundary if you have to */
468 ardata->first_file_filepos += (ardata-> first_file_filepos) %2;
469 /* FIXME, we should provide some way to free raw_ardata when
470 we are done using the strings from it. For now, it seems
471 to be allocated on an obstack anyway... */
472 bfd_has_map (abfd) = true;
473 }
474 return true;
475 }
476
477 /* Returns false on error, true otherwise */
478 boolean
479 bfd_slurp_coff_armap (abfd)
480 bfd *abfd;
481 {
482 struct areltdata *mapdata;
483 char nextname;
484 int *raw_armap, *rawptr;
485 struct artdata *ardata = bfd_ardata (abfd);
486 char *stringbase;
487 unsigned int stringsize;
488 carsym *carsyms;
489 int result;
490
491 result = bfd_read ((PTR)&nextname, 1, 1, abfd);
492 bfd_seek (abfd, -1L, SEEK_CUR);
493
494 if (result != 1 || nextname != '/') {
495 /* Actually I think this is an error for a COFF archive */
496 bfd_has_map (abfd) = false;
497 return true;
498 }
499
500 mapdata = snarf_ar_hdr (abfd);
501 if (mapdata == NULL) return false;
502
503 raw_armap = (int *) bfd_alloc(abfd,mapdata->parsed_size);
504 if (raw_armap == NULL) {
505 bfd_error = no_memory;
506 byebye:
507 bfd_release (abfd, (PTR)mapdata);
508 return false;
509 }
510
511 if (bfd_read ((PTR)raw_armap, 1, mapdata->parsed_size, abfd) !=
512 mapdata->parsed_size) {
513 bfd_error = malformed_archive;
514 oops:
515 bfd_release (abfd, (PTR)raw_armap);
516 goto byebye;
517 }
518
519 /* The coff armap must be read sequentially. So we construct a bsd-style
520 one in core all at once, for simplicity. */
521
522 stringsize = mapdata->parsed_size - (4 * (*raw_armap)) - 4;
523
524 {
525 unsigned int nsymz = *raw_armap;
526 unsigned int carsym_size = (nsymz * sizeof (carsym));
527 unsigned int ptrsize = (4 * nsymz);
528 unsigned int i;
529 ardata->symdefs = (carsym *) bfd_zalloc(abfd,carsym_size + stringsize + 1);
530 if (ardata->symdefs == NULL) {
531 bfd_error = no_memory;
532 goto oops;
533 }
534 carsyms = ardata->symdefs;
535
536 stringbase = ((char *) ardata->symdefs) + carsym_size;
537 memcpy (stringbase, (char*)raw_armap + ptrsize + 4, stringsize);
538
539
540 /* OK, build the carsyms */
541 for (i = 0; i < nsymz; i++)
542 {
543 rawptr = raw_armap + i + 1;
544 carsyms->file_offset = *rawptr;
545 carsyms->name = stringbase;
546 for (; *(stringbase++););
547 carsyms++;
548 }
549 *stringbase = 0;
550 }
551 ardata->symdef_count = *raw_armap;
552 ardata->first_file_filepos = bfd_tell (abfd);
553 /* Pad to an even boundary if you have to */
554 ardata->first_file_filepos += (ardata->first_file_filepos) %2;
555 bfd_release (abfd, (PTR)raw_armap);
556 bfd_release (abfd, (PTR)mapdata);
557 bfd_has_map (abfd) = true;
558 return true;
559 }
560 \f
561 /** Extended name table.
562
563 Normally archives support only 14-character filenames. Intel has extended
564 the format: longer names are stored in a special element (the first in the
565 archive, or second if there is an armap); the name in the ar_hdr is replaced
566 by <space><index into filename element>. Index is the P.R. of an int (radix:
567 8). */
568
569 /* Returns false on error, true otherwise */
570 boolean
571 _bfd_slurp_extended_name_table (abfd)
572 bfd *abfd;
573 {
574 char nextname[17];
575 struct areltdata *namedata;
576
577 /* FIXME: Formatting sucks here, and in case of failure of BFD_READ,
578 we probably don't want to return true. */
579 if (bfd_read ((PTR)nextname, 1, 16, abfd) == 16) {
580
581 bfd_seek (abfd, -16L, SEEK_CUR);
582
583 if (strncmp (nextname, "ARFILENAMES/ ", 16)) {
584 bfd_ardata (abfd)->extended_names = NULL;
585 return true;
586 }
587
588 namedata = snarf_ar_hdr (abfd);
589 if (namedata == NULL) return false;
590
591 bfd_ardata (abfd)->extended_names = bfd_zalloc(abfd,namedata->parsed_size);
592 if (bfd_ardata (abfd)->extended_names == NULL) {
593 bfd_error = no_memory;
594 byebye:
595 bfd_release (abfd, (PTR)namedata);
596 return false;
597 }
598
599 if (bfd_read ((PTR)bfd_ardata (abfd)->extended_names, 1,
600 namedata->parsed_size, abfd) != namedata->parsed_size) {
601 bfd_error = malformed_archive;
602 bfd_release (abfd, (PTR)(bfd_ardata (abfd)->extended_names));
603 bfd_ardata (abfd)->extended_names = NULL;
604 goto byebye;
605 }
606
607 /* It appears that the extended names are newline-padded, not null padded.
608 */
609 {
610 char *temp = bfd_ardata (abfd)->extended_names;
611 for (; *temp != '\0'; ++temp)
612 if (*temp == '\n') *temp = '\0';
613 }
614
615 /* Pad to an even boundary if you have to */
616 bfd_ardata (abfd)->first_file_filepos = bfd_tell (abfd);
617 bfd_ardata (abfd)->first_file_filepos +=
618 (bfd_ardata (abfd)->first_file_filepos) %2;
619
620 /* FIXME, we can't release namedata here because it was allocated
621 below extended_names on the obstack... */
622 /* bfd_release (abfd, namedata); */
623 }
624 return true;
625 }
626
627 static
628 char *normalize(file)
629 char *file;
630 {
631 char * filename = strrchr(file, '/');
632 if (filename != (char *)NULL) {
633 filename ++;
634 }
635 else {
636 filename = file;
637 }
638 return filename;
639 }
640
641 /* Follows archive_head and produces an extended name table if necessary.
642 Returns (in tabloc) a pointer to an extended name table, and in tablen
643 the length of the table. If it makes an entry it clobbers the filename
644 so that the element may be written without further massage.
645 Returns true if it ran successfully, false if something went wrong.
646 A successful return may still involve a zero-length tablen!
647 */
648 boolean
649 bfd_construct_extended_name_table (abfd, tabloc, tablen)
650 bfd *abfd;
651 char **tabloc;
652 unsigned int *tablen;
653 {
654 unsigned int maxname = abfd->xvec->ar_max_namelen;
655 unsigned int total_namelen = 0;
656 bfd *current;
657 char *strptr;
658
659 *tablen = 0;
660
661 /* Figure out how long the table should be */
662 for (current = abfd->archive_head; current != NULL; current = current->next){
663 unsigned int thislen = strlen (normalize(current->filename));
664 if (thislen > maxname) total_namelen += thislen + 1; /* leave room for \n */
665 }
666
667 if (total_namelen == 0) return true;
668
669 *tabloc = bfd_zalloc (abfd,total_namelen);
670 if (*tabloc == NULL) {
671 bfd_error = no_memory;
672 return false;
673 }
674
675 *tablen = total_namelen;
676 strptr = *tabloc;
677
678 for (current = abfd->archive_head; current != NULL; current =
679 current->next) {
680 char *normal =normalize( current->filename);
681 unsigned int thislen = strlen (normal);
682 if (thislen > maxname) {
683 /* Works for now; may need to be re-engineered if we encounter an oddball
684 archive format and want to generalise this hack. */
685 struct ar_hdr *hdr = arch_hdr(current);
686 strcpy (strptr, normal);
687 strptr[thislen] = '\n';
688 hdr->ar_name[0] = ' ';
689 /* We know there will always be enough room (one of the few cases
690 where you may safely use sprintf). */
691 sprintf ((hdr->ar_name) + 1, "%-o", (unsigned) (strptr - *tabloc));
692 /* Kinda Kludgy. We should just use the returned value of sprintf
693 but not all implementations get this right */
694 {
695 char *temp = hdr->ar_name +2;
696 for (; temp < hdr->ar_name + maxname; temp++)
697 if (*temp == '\0') *temp = ' ';
698 }
699 strptr += thislen + 1;
700 }
701 }
702
703 return true;
704 }
705 \f
706 /** A couple of functions for creating ar_hdrs */
707
708 /* Takes a filename, returns an arelt_data for it, or NULL if it can't make one.
709 The filename must refer to a filename in the filesystem.
710 The filename field of the ar_hdr will NOT be initialized
711 */
712
713 struct areltdata *
714 DEFUN(bfd_ar_hdr_from_filesystem, (abfd,filename),
715 bfd* abfd AND
716 CONST char *filename)
717 {
718 struct stat status;
719 struct areltdata *ared;
720 struct ar_hdr *hdr;
721 char *temp, *temp1;
722
723
724 if (stat (filename, &status) != 0) {
725 bfd_error = system_call_error;
726 return NULL;
727 }
728
729 ared = (struct areltdata *) bfd_zalloc(abfd, sizeof (struct ar_hdr) +
730 sizeof (struct areltdata));
731 if (ared == NULL) {
732 bfd_error = no_memory;
733 return NULL;
734 }
735 hdr = (struct ar_hdr *) (((char *) ared) + sizeof (struct areltdata));
736
737 /* ar headers are space padded, not null padded! */
738 temp = (char *) hdr;
739 temp1 = temp + sizeof (struct ar_hdr) - 2;
740 for (; temp < temp1; *(temp++) = ' ');
741 strncpy (hdr->ar_fmag, ARFMAG, 2);
742
743 /* Goddamned sprintf doesn't permit MAXIMUM field lengths */
744 sprintf ((hdr->ar_date), "%-12ld", status.st_mtime);
745 sprintf ((hdr->ar_uid), "%d", status.st_uid);
746 sprintf ((hdr->ar_gid), "%d", status.st_gid);
747 sprintf ((hdr->ar_mode), "%-8o", (unsigned) status.st_mode);
748 sprintf ((hdr->ar_size), "%-10ld", status.st_size);
749 /* Correct for a lossage in sprintf whereby it null-terminates. I cannot
750 understand how these C losers could design such a ramshackle bunch of
751 IO operations */
752 temp = (char *) hdr;
753 temp1 = temp + sizeof (struct ar_hdr) - 2;
754 for (; temp < temp1; temp++) {
755 if (*temp == '\0') *temp = ' ';
756 }
757 strncpy (hdr->ar_fmag, ARFMAG, 2);
758 ared->parsed_size = status.st_size;
759 ared->arch_header = (char *) hdr;
760
761 return ared;
762 }
763
764 struct ar_hdr *
765 DEFUN(bfd_special_undocumented_glue, (abfd, filename),
766 bfd *abfd AND
767 char *filename)
768 {
769
770 return (struct ar_hdr *) bfd_ar_hdr_from_filesystem (abfd, filename) -> arch_header;
771 }
772
773
774 /* Analogous to stat call */
775 int
776 bfd_generic_stat_arch_elt (abfd, buf)
777 bfd *abfd;
778 struct stat *buf;
779 {
780 struct ar_hdr *hdr;
781 char *aloser;
782
783 if (abfd->arelt_data == NULL) {
784 bfd_error = invalid_operation;
785 return -1;
786 }
787
788 hdr = arch_hdr (abfd);
789
790 #define foo(arelt, stelt, size) \
791 buf->stelt = strtol (hdr->arelt, &aloser, size); \
792 if (aloser == hdr->arelt) return -1;
793
794 foo (ar_date, st_mtime, 10);
795 foo (ar_uid, st_uid, 10);
796 foo (ar_gid, st_gid, 10);
797 foo (ar_mode, st_mode, 8);
798 foo (ar_size, st_size, 10);
799
800 return 0;
801 }
802
803 void
804 bfd_dont_truncate_arname (abfd, pathname, arhdr)
805 bfd *abfd;
806 CONST char *pathname;
807 char *arhdr;
808 {
809 /* FIXME: This interacts unpleasantly with ar's quick-append option.
810 Fortunately ic960 users will never use that option. Fixing this
811 is very hard; fortunately I know how to do it and will do so once
812 intel's release is out the door. */
813
814 struct ar_hdr *hdr = (struct ar_hdr *) arhdr;
815 int length;
816 CONST char *filename = strrchr (pathname, '/');
817 int maxlen = ar_maxnamelen (abfd);
818
819 if (filename == NULL)
820 filename = pathname;
821 else
822 ++filename;
823
824 length = strlen (filename);
825
826 if (length <= maxlen)
827 memcpy (hdr->ar_name, filename, length);
828
829 if (length < maxlen) (hdr->ar_name)[length] = ar_padchar (abfd);
830 return;
831
832 }
833
834 void
835 bfd_bsd_truncate_arname (abfd, pathname, arhdr)
836 bfd *abfd;
837 CONST char *pathname;
838 char *arhdr;
839 {
840 struct ar_hdr *hdr = (struct ar_hdr *) arhdr;
841 int length;
842 CONST char *filename = strrchr (pathname, '/');
843 int maxlen = ar_maxnamelen (abfd);
844
845
846 if (filename == NULL)
847 filename = pathname;
848 else
849 ++filename;
850
851 length = strlen (filename);
852
853 if (length <= maxlen)
854 memcpy (hdr->ar_name, filename, length);
855 else {
856 /* pathname: meet procrustes */
857 memcpy (hdr->ar_name, filename, maxlen);
858 length = maxlen;
859 }
860
861 if (length < maxlen) (hdr->ar_name)[length] = ar_padchar (abfd);
862 }
863
864 /* Store name into ar header. Truncates the name to fit.
865 1> strip pathname to be just the basename.
866 2> if it's short enuf to fit, stuff it in.
867 3> If it doesn't end with .o, truncate it to fit
868 4> truncate it before the .o, append .o, stuff THAT in.
869 */
870
871 /* This is what gnu ar does. It's better but incompatible with the bsd ar. */
872 void
873 bfd_gnu_truncate_arname (abfd, pathname, arhdr)
874 bfd *abfd;
875 CONST char *pathname;
876 char *arhdr;
877 {
878 struct ar_hdr *hdr = (struct ar_hdr *) arhdr;
879 int length;
880 CONST char *filename = strrchr (pathname, '/');
881 int maxlen = ar_maxnamelen (abfd);
882
883 if (filename == NULL)
884 filename = pathname;
885 else
886 ++filename;
887
888 length = strlen (filename);
889
890 if (length <= maxlen)
891 memcpy (hdr->ar_name, filename, length);
892 else { /* pathname: meet procrustes */
893 memcpy (hdr->ar_name, filename, maxlen);
894 if ((filename[length - 2] == '.') && (filename[length - 1] == 'o')) {
895 hdr->ar_name[maxlen - 2] = '.';
896 hdr->ar_name[maxlen - 1] = 'o';
897 }
898 length = maxlen;
899 }
900
901 if (length < 16) (hdr->ar_name)[length] = ar_padchar (abfd);
902 }
903 \f
904
905 PROTO (boolean, compute_and_write_armap, (bfd *arch, unsigned int elength));
906
907 /* The bfd is open for write and has its format set to bfd_archive */
908 boolean
909 _bfd_write_archive_contents (arch)
910 bfd *arch;
911 {
912 bfd *current;
913 char *etable = NULL;
914 unsigned int elength = 0;
915 boolean makemap = bfd_has_map (arch);
916 boolean hasobjects = false; /* if no .o's, don't bother to make a map */
917 unsigned int i;
918
919 /* Verify the viability of all entries; if any of them live in the
920 filesystem (as opposed to living in an archive open for input)
921 then construct a fresh ar_hdr for them.
922 */
923 for (current = arch->archive_head; current; current = current->next) {
924 if (bfd_write_p (current)) {
925 bfd_error = invalid_operation;
926 return false;
927 }
928 if (!current->arelt_data) {
929 current->arelt_data =
930 (PTR) bfd_ar_hdr_from_filesystem (arch, current->filename);
931 if (!current->arelt_data) return false;
932
933 /* Put in the file name */
934
935 BFD_SEND (arch, _bfd_truncate_arname,(arch,
936 current->filename,
937 (char *) arch_hdr(current)));
938
939
940 }
941
942 if (makemap) { /* don't bother if we won't make a map! */
943 if ((bfd_check_format (current, bfd_object))
944 #if 0 /* FIXME -- these are not set correctly */
945 && ((bfd_get_file_flags (current) & HAS_SYMS))
946 #endif
947 )
948 hasobjects = true;
949 }
950 }
951
952 if (!bfd_construct_extended_name_table (arch, &etable, &elength))
953 return false;
954
955 bfd_seek (arch, 0, SEEK_SET);
956 #ifdef GNU960
957 bfd_write (BFD_GNU960_ARMAG(arch), 1, SARMAG, arch);
958 #else
959 bfd_write (ARMAG, 1, SARMAG, arch);
960 #endif
961
962 if (makemap && hasobjects) {
963
964 if (compute_and_write_armap (arch, elength) != true) {
965 return false;
966 }
967 }
968
969 if (elength != 0) {
970 struct ar_hdr hdr;
971
972 memset ((char *)(&hdr), 0, sizeof (struct ar_hdr));
973 sprintf (&(hdr.ar_name[0]), "ARFILENAMES/");
974 sprintf (&(hdr.ar_size[0]), "%-10d", (int) elength);
975 hdr.ar_fmag[0] = '`'; hdr.ar_fmag[1] = '\n';
976 for (i = 0; i < sizeof (struct ar_hdr); i++)
977 if (((char *)(&hdr))[i] == '\0') (((char *)(&hdr))[i]) = ' ';
978 bfd_write ((char *)&hdr, 1, sizeof (struct ar_hdr), arch);
979 bfd_write (etable, 1, elength, arch);
980 if ((elength % 2) == 1) bfd_write ("\n", 1, 1, arch);
981
982 }
983
984 for (current = arch->archive_head; current; current = current->next) {
985 char buffer[DEFAULT_BUFFERSIZE];
986 unsigned int remaining = arelt_size (current);
987 struct ar_hdr *hdr = arch_hdr(current);
988 /* write ar header */
989
990 if (bfd_write ((char *)hdr, 1, sizeof(*hdr), arch) != sizeof(*hdr)) {
991 syserr:
992 bfd_error = system_call_error;
993 return false;
994 }
995 if (bfd_seek (current, 0L, SEEK_SET) != 0L) goto syserr;
996 while (remaining)
997 {
998 unsigned int amt = DEFAULT_BUFFERSIZE;
999 if (amt > remaining) {
1000 amt = remaining;
1001 }
1002 if (bfd_read (buffer, amt, 1, current) != amt) goto syserr;
1003 if (bfd_write (buffer, amt, 1, arch) != amt) goto syserr;
1004 remaining -= amt;
1005 }
1006 if ((arelt_size (current) % 2) == 1) bfd_write ("\n", 1, 1, arch);
1007 }
1008 return true;
1009 }
1010 \f
1011 /* Note that the namidx for the first symbol is 0 */
1012
1013 boolean
1014 compute_and_write_armap (arch, elength)
1015 bfd *arch;
1016 unsigned int elength;
1017 {
1018 bfd *current;
1019 file_ptr elt_no = 0;
1020 struct orl *map;
1021 int orl_max = 15000; /* fine initial default */
1022 int orl_count = 0;
1023 int stridx = 0; /* string index */
1024
1025 /* Dunno if this is the best place for this info... */
1026 if (elength != 0) elength += sizeof (struct ar_hdr);
1027 elength += elength %2 ;
1028
1029 map = (struct orl *) bfd_zalloc (arch,orl_max * sizeof (struct orl));
1030 if (map == NULL) {
1031 bfd_error = no_memory;
1032 return false;
1033 }
1034
1035 /* Map over each element */
1036 for (current = arch->archive_head;
1037 current != (bfd *)NULL;
1038 current = current->next, elt_no++)
1039 {
1040 if ((bfd_check_format (current, bfd_object) == true)
1041 && ((bfd_get_file_flags (current) & HAS_SYMS))) {
1042 asymbol **syms;
1043 unsigned int storage;
1044 unsigned int symcount;
1045 unsigned int src_count;
1046
1047 storage = get_symtab_upper_bound (current);
1048 if (storage != 0) {
1049
1050 syms = (asymbol **) bfd_zalloc (arch,storage);
1051 if (syms == NULL) {
1052 bfd_error = no_memory; /* FIXME -- memory leak */
1053 return false;
1054 }
1055 symcount = bfd_canonicalize_symtab (current, syms);
1056
1057
1058 /* Now map over all the symbols, picking out the ones we want */
1059 for (src_count = 0; src_count <symcount; src_count++) {
1060 flagword flags = (syms[src_count])->flags;
1061 if ((flags & BSF_GLOBAL) ||
1062 (flags & BSF_FORT_COMM)) {
1063
1064 /* This symbol will go into the archive header */
1065 if (orl_count == orl_max)
1066 {
1067 orl_max *= 2;
1068 map = (struct orl *) bfd_realloc (arch, (char *) map,
1069 orl_max * sizeof (struct orl));
1070 }
1071
1072 (map[orl_count]).name = (char **) &((syms[src_count])->name);
1073 (map[orl_count]).pos = (file_ptr) current;
1074 (map[orl_count]).namidx = stridx;
1075
1076 stridx += strlen ((syms[src_count])->name) + 1;
1077 ++orl_count;
1078 }
1079 }
1080 }
1081 }
1082 }
1083 /* OK, now we have collected all the data, let's write them out */
1084 if (!BFD_SEND (arch, write_armap,
1085 (arch, elength, map, orl_count, stridx))) {
1086
1087 return false;
1088 }
1089
1090
1091 return true;
1092 }
1093
1094 boolean
1095 bsd_write_armap (arch, elength, map, orl_count, stridx)
1096 bfd *arch;
1097 unsigned int elength;
1098 struct orl *map;
1099 int orl_count;
1100 int stridx;
1101 {
1102 unsigned int ranlibsize = (orl_count * sizeof (struct ranlib)) + 4;
1103 unsigned int stringsize = stridx + 4;
1104 unsigned int mapsize = stringsize + ranlibsize;
1105 file_ptr firstreal;
1106 bfd *current = arch->archive_head;
1107 bfd *last_elt = current; /* last element arch seen */
1108 int temp;
1109 int count;
1110 struct ar_hdr hdr;
1111 struct stat statbuf;
1112 unsigned int i;
1113 int padit = mapsize & 1;
1114
1115 if (padit) mapsize ++;
1116
1117 firstreal = mapsize + elength + sizeof (struct ar_hdr) + SARMAG;
1118
1119 stat (arch->filename, &statbuf);
1120 memset ((char *)(&hdr), 0, sizeof (struct ar_hdr));
1121 sprintf (hdr.ar_name, RANLIBMAG);
1122 sprintf (hdr.ar_date, "%ld", statbuf.st_mtime);
1123 sprintf (hdr.ar_uid, "%d", getuid());
1124 sprintf (hdr.ar_gid, "%d", getgid());
1125 sprintf (hdr.ar_size, "%-10d", (int) mapsize);
1126 hdr.ar_fmag[0] = '`'; hdr.ar_fmag[1] = '\n';
1127 for (i = 0; i < sizeof (struct ar_hdr); i++)
1128 if (((char *)(&hdr))[i] == '\0') (((char *)(&hdr))[i]) = ' ';
1129 bfd_write ((char *)&hdr, 1, sizeof (struct ar_hdr), arch);
1130 bfd_h_put_32(arch, ranlibsize, &temp);
1131 bfd_write (&temp, 1, sizeof (temp), arch);
1132
1133 for (count = 0; count < orl_count; count++) {
1134 struct symdef outs;
1135 struct symdef *outp = &outs;
1136
1137 if (((bfd *)(map[count]).pos) != last_elt) {
1138 do {
1139 firstreal += arelt_size (current) + sizeof (struct ar_hdr);
1140 firstreal += firstreal % 2;
1141 current = current->next;
1142 } while (current != (bfd *)(map[count]).pos);
1143 } /* if new archive element */
1144
1145 last_elt = current;
1146 bfd_h_put_32(arch, ((map[count]).namidx), &outs.s.string_offset);
1147 bfd_h_put_32(arch, firstreal, &outs.file_offset);
1148 bfd_write ((char *)outp, 1, sizeof (outs), arch);
1149 }
1150
1151 /* now write the strings themselves */
1152 bfd_h_put_32(arch, stridx, &temp);
1153 bfd_write ((PTR)&temp, 1, sizeof (temp), arch);
1154 for (count = 0; count < orl_count; count++)
1155 bfd_write (*((map[count]).name), 1, strlen (*((map[count]).name))+1, arch);
1156
1157 /* The spec sez this should be a newline. But in order to be
1158 bug-compatible for sun's ar we use a null. */
1159 if (padit)
1160 bfd_write("\0",1,1,arch);
1161
1162 return true;
1163 }
1164 \f
1165
1166 /* A coff armap looks like :
1167 ARMAG
1168 struct ar_hdr with name = '/'
1169 number of symbols
1170 offset of file for symbol 0
1171 offset of file for symbol 1
1172 ..
1173 offset of file for symbol n-1
1174 symbol name 0
1175 symbol name 1
1176 ..
1177 symbol name n-1
1178
1179 */
1180
1181 boolean
1182 coff_write_armap (arch, elength, map, orl_count, stridx)
1183 bfd *arch;
1184 unsigned int elength;
1185 struct orl *map;
1186 int orl_count;
1187 int stridx;
1188 {
1189 unsigned int ranlibsize = (orl_count * 4) + 4;
1190 unsigned int stringsize = stridx;
1191 unsigned int mapsize = stringsize + ranlibsize;
1192 file_ptr archive_member_file_ptr;
1193 bfd *current = arch->archive_head;
1194 int last_eltno = 0; /* last element arch seen */
1195 int count;
1196 struct ar_hdr hdr;
1197 unsigned int i;
1198 int padit = mapsize & 1;
1199
1200 if (padit) mapsize ++;
1201
1202 archive_member_file_ptr =
1203 mapsize + elength + sizeof (struct ar_hdr) + SARMAG;
1204
1205 memset ((char *)(&hdr), 0, sizeof (struct ar_hdr));
1206 hdr.ar_name[0] = '/';
1207 sprintf (hdr.ar_size, "%-10d", (int) mapsize);
1208 sprintf (hdr.ar_date, "%ld", (long)time (NULL));
1209 /* This, at least, is what Intel coff sets the values to.: */
1210 sprintf ((hdr.ar_uid), "%d", 0);
1211 sprintf ((hdr.ar_gid), "%d", 0);
1212 sprintf ((hdr.ar_mode), "%-7o",(unsigned ) 0);
1213 hdr.ar_fmag[0] = '`'; hdr.ar_fmag[1] = '\n';
1214
1215 for (i = 0; i < sizeof (struct ar_hdr); i++)
1216 if (((char *)(&hdr))[i] == '\0') (((char *)(&hdr))[i]) = ' ';
1217
1218 /* Write the ar header for this item and the number of symbols */
1219
1220 bfd_write ((PTR)&hdr, 1, sizeof (struct ar_hdr), arch);
1221 /* FIXME, this needs to be byte-swapped */
1222 bfd_write ((PTR)&orl_count, 1, sizeof (orl_count), arch);
1223
1224 /* Two passes, first write the file offsets for each symbol -
1225 remembering that each offset is on a two byte boundary
1226 */
1227
1228 for (count = 0; count < orl_count; count++) {
1229 while ((map[count]).pos != last_eltno) {
1230 /* If this is the first time we've seen a ref to this archive
1231 then remember it's size */
1232 archive_member_file_ptr +=
1233 arelt_size (current) + sizeof (struct ar_hdr);
1234 archive_member_file_ptr += archive_member_file_ptr % 2;
1235 current = current->next;
1236 last_eltno++;
1237 }
1238 /* FIXME, this needs to be byte-swapped */
1239 bfd_write ((PTR)&archive_member_file_ptr,
1240 1,
1241 sizeof (archive_member_file_ptr),
1242 arch);
1243 }
1244
1245 /* now write the strings themselves */
1246 for (count = 0; count < orl_count; count++) {
1247 bfd_write ((PTR)*((map[count]).name),
1248 1,
1249 strlen (*((map[count]).name))+1, arch);
1250
1251 }
1252 /* The spec sez this should be a newline. But in order to be
1253 bug-compatible for arc960 we use a null. */
1254 if (padit)
1255 bfd_write("\0",1,1,arch);
1256
1257 return true;
1258 }
This page took 0.057705 seconds and 4 git commands to generate.