OSDN Git Service

194898c171e62051c4c9c04700e6e3ef922a8ab3
[pf3gnuchains/pf3gnuchains4x.git] / bfd / mach-o.c
1 /* Mach-O support for BFD.
2    Copyright 1999, 2000, 2001, 2002, 2003, 2004
3    Free Software Foundation, Inc.
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 2 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
20
21 #include "mach-o.h"
22 #include "bfd.h"
23 #include "sysdep.h"
24 #include "libbfd.h"
25 #include "libiberty.h"
26 #include <ctype.h>
27
28 #ifndef BFD_IO_FUNCS
29 #define BFD_IO_FUNCS 0
30 #endif
31
32 #define bfd_mach_o_mkarchive _bfd_noarchive_mkarchive
33 #define bfd_mach_o_read_ar_hdr _bfd_noarchive_read_ar_hdr
34 #define bfd_mach_o_slurp_armap _bfd_noarchive_slurp_armap
35 #define bfd_mach_o_slurp_extended_name_table _bfd_noarchive_slurp_extended_name_table
36 #define bfd_mach_o_construct_extended_name_table _bfd_noarchive_construct_extended_name_table
37 #define bfd_mach_o_truncate_arname _bfd_noarchive_truncate_arname
38 #define bfd_mach_o_write_armap _bfd_noarchive_write_armap
39 #define bfd_mach_o_get_elt_at_index _bfd_noarchive_get_elt_at_index
40 #define bfd_mach_o_generic_stat_arch_elt _bfd_noarchive_generic_stat_arch_elt
41 #define bfd_mach_o_update_armap_timestamp _bfd_noarchive_update_armap_timestamp
42 #define bfd_mach_o_close_and_cleanup _bfd_generic_close_and_cleanup
43 #define bfd_mach_o_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
44 #define bfd_mach_o_new_section_hook _bfd_generic_new_section_hook
45 #define bfd_mach_o_get_section_contents_in_window _bfd_generic_get_section_contents_in_window
46 #define bfd_mach_o_bfd_is_local_label_name _bfd_nosymbols_bfd_is_local_label_name
47 #define bfd_mach_o_get_lineno _bfd_nosymbols_get_lineno
48 #define bfd_mach_o_find_nearest_line _bfd_nosymbols_find_nearest_line
49 #define bfd_mach_o_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
50 #define bfd_mach_o_read_minisymbols _bfd_generic_read_minisymbols
51 #define bfd_mach_o_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
52 #define bfd_mach_o_get_reloc_upper_bound _bfd_norelocs_get_reloc_upper_bound
53 #define bfd_mach_o_canonicalize_reloc _bfd_norelocs_canonicalize_reloc
54 #define bfd_mach_o_bfd_reloc_type_lookup _bfd_norelocs_bfd_reloc_type_lookup
55 #define bfd_mach_o_bfd_get_relocated_section_contents bfd_generic_get_relocated_section_contents
56 #define bfd_mach_o_bfd_relax_section bfd_generic_relax_section
57 #define bfd_mach_o_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
58 #define bfd_mach_o_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
59 #define bfd_mach_o_bfd_link_add_symbols _bfd_generic_link_add_symbols
60 #define bfd_mach_o_bfd_link_just_syms _bfd_generic_link_just_syms
61 #define bfd_mach_o_bfd_final_link _bfd_generic_final_link
62 #define bfd_mach_o_bfd_link_split_section _bfd_generic_link_split_section
63 #define bfd_mach_o_set_arch_mach bfd_default_set_arch_mach
64 #define bfd_mach_o_bfd_merge_private_bfd_data _bfd_generic_bfd_merge_private_bfd_data
65 #define bfd_mach_o_bfd_set_private_flags _bfd_generic_bfd_set_private_flags
66 #define bfd_mach_o_bfd_print_private_bfd_data _bfd_generic_bfd_print_private_bfd_data
67 #define bfd_mach_o_get_section_contents _bfd_generic_get_section_contents
68 #define bfd_mach_o_set_section_contents _bfd_generic_set_section_contents
69 #define bfd_mach_o_bfd_gc_sections bfd_generic_gc_sections
70 #define bfd_mach_o_bfd_merge_sections bfd_generic_merge_sections
71 #define bfd_mach_o_bfd_is_group_section bfd_generic_is_group_section
72 #define bfd_mach_o_bfd_discard_group bfd_generic_discard_group
73 #define bfd_mach_o_bfd_copy_private_header_data _bfd_generic_bfd_copy_private_header_data
74
75 static bfd_boolean bfd_mach_o_bfd_copy_private_symbol_data
76   PARAMS ((bfd *, asymbol *, bfd *, asymbol *));
77 static bfd_boolean bfd_mach_o_bfd_copy_private_section_data
78   PARAMS ((bfd *, asection *, bfd *, asection *));
79 static bfd_boolean bfd_mach_o_bfd_copy_private_bfd_data
80   PARAMS ((bfd *, bfd *));
81 static long bfd_mach_o_count_symbols
82   PARAMS ((bfd *));
83 static long bfd_mach_o_get_symtab_upper_bound
84   PARAMS ((bfd *));
85 static long bfd_mach_o_canonicalize_symtab
86   PARAMS ((bfd *, asymbol **));
87 static void bfd_mach_o_get_symbol_info
88   PARAMS ((bfd *, asymbol *, symbol_info *));
89 static void bfd_mach_o_print_symbol
90   PARAMS ((bfd *, PTR, asymbol *, bfd_print_symbol_type));
91 static void bfd_mach_o_convert_architecture
92   PARAMS ((bfd_mach_o_cpu_type, bfd_mach_o_cpu_subtype,
93            enum bfd_architecture *, unsigned long *));
94 static bfd_boolean bfd_mach_o_write_contents
95   PARAMS ((bfd *));
96 static int bfd_mach_o_sizeof_headers
97   PARAMS ((bfd *, bfd_boolean));
98 static asymbol * bfd_mach_o_make_empty_symbol
99   PARAMS ((bfd *));
100 static int bfd_mach_o_write_header
101   PARAMS ((bfd *, bfd_mach_o_header *));
102 static int bfd_mach_o_read_header
103   PARAMS ((bfd *, bfd_mach_o_header *));
104 static asection * bfd_mach_o_make_bfd_section
105   PARAMS ((bfd *, bfd_mach_o_section *));
106 static int bfd_mach_o_scan_read_section
107   PARAMS ((bfd *, bfd_mach_o_section *, bfd_vma));
108 static int bfd_mach_o_scan_write_section
109   PARAMS ((bfd *, bfd_mach_o_section *, bfd_vma));
110 static int bfd_mach_o_scan_write_symtab_symbols
111   PARAMS ((bfd *, bfd_mach_o_load_command *));
112 static int bfd_mach_o_scan_write_thread
113   PARAMS ((bfd *, bfd_mach_o_load_command *));
114 static int bfd_mach_o_scan_read_dylinker
115   PARAMS ((bfd *, bfd_mach_o_load_command *));
116 static int bfd_mach_o_scan_read_dylib
117   PARAMS ((bfd *, bfd_mach_o_load_command *));
118 static int bfd_mach_o_scan_read_prebound_dylib
119   PARAMS ((bfd *, bfd_mach_o_load_command *));
120 static int bfd_mach_o_scan_read_thread
121   PARAMS ((bfd *, bfd_mach_o_load_command *));
122 static int bfd_mach_o_scan_write_symtab
123   PARAMS ((bfd *, bfd_mach_o_load_command *));
124 static int bfd_mach_o_scan_read_dysymtab
125   PARAMS ((bfd *, bfd_mach_o_load_command *));
126 static int bfd_mach_o_scan_read_symtab
127   PARAMS ((bfd *, bfd_mach_o_load_command *));
128 static int bfd_mach_o_scan_read_segment
129   PARAMS ((bfd *, bfd_mach_o_load_command *));
130 static int bfd_mach_o_scan_write_segment
131   PARAMS ((bfd *, bfd_mach_o_load_command *));
132 static int bfd_mach_o_scan_read_command
133   PARAMS ((bfd *, bfd_mach_o_load_command *));
134 static void bfd_mach_o_flatten_sections
135   PARAMS ((bfd *));
136 static const char * bfd_mach_o_i386_flavour_string
137   PARAMS ((unsigned int));
138 static const char * bfd_mach_o_ppc_flavour_string
139   PARAMS ((unsigned int));
140
141 /* The flags field of a section structure is separated into two parts a section
142    type and section attributes.  The section types are mutually exclusive (it
143    can only have one type) but the section attributes are not (it may have more
144    than one attribute).  */
145
146 #define SECTION_TYPE             0x000000ff     /* 256 section types.  */
147 #define SECTION_ATTRIBUTES       0xffffff00     /*  24 section attributes.  */
148
149 /* Constants for the section attributes part of the flags field of a section
150    structure.  */
151
152 #define SECTION_ATTRIBUTES_USR   0xff000000     /* User-settable attributes.  */
153 #define S_ATTR_PURE_INSTRUCTIONS 0x80000000     /* Section contains only true machine instructions.  */
154 #define SECTION_ATTRIBUTES_SYS   0x00ffff00     /* System setable attributes.  */
155 #define S_ATTR_SOME_INSTRUCTIONS 0x00000400     /* Section contains some machine instructions.  */
156 #define S_ATTR_EXT_RELOC         0x00000200     /* Section has external relocation entries.  */
157 #define S_ATTR_LOC_RELOC         0x00000100     /* Section has local relocation entries.  */
158
159 #define N_STAB 0xe0
160 #define N_TYPE 0x1e
161 #define N_EXT  0x01
162 #define N_UNDF 0x0
163 #define N_ABS  0x2
164 #define N_SECT 0xe
165 #define N_INDR 0xa
166
167 bfd_boolean
168 bfd_mach_o_valid (abfd)
169      bfd *abfd;
170 {
171   if (abfd == NULL || abfd->xvec == NULL)
172     return 0;
173
174   if (! ((abfd->xvec == &mach_o_be_vec)
175          || (abfd->xvec == &mach_o_le_vec)
176          || (abfd->xvec == &mach_o_fat_vec)))
177     return 0;
178
179   if (abfd->tdata.mach_o_data == NULL)
180     return 0;
181   return 1;
182 }
183
184 /* Copy any private info we understand from the input symbol
185    to the output symbol.  */
186
187 static bfd_boolean
188 bfd_mach_o_bfd_copy_private_symbol_data (ibfd, isymbol, obfd, osymbol)
189      bfd *ibfd ATTRIBUTE_UNUSED;
190      asymbol *isymbol ATTRIBUTE_UNUSED;
191      bfd *obfd ATTRIBUTE_UNUSED;
192      asymbol *osymbol ATTRIBUTE_UNUSED;
193 {
194   return TRUE;
195 }
196
197 /* Copy any private info we understand from the input section
198    to the output section.  */
199
200 static bfd_boolean
201 bfd_mach_o_bfd_copy_private_section_data (ibfd, isection, obfd, osection)
202      bfd *ibfd ATTRIBUTE_UNUSED;
203      asection *isection ATTRIBUTE_UNUSED;
204      bfd *obfd ATTRIBUTE_UNUSED;
205      asection *osection ATTRIBUTE_UNUSED;
206 {
207   return TRUE;
208 }
209
210 /* Copy any private info we understand from the input bfd
211    to the output bfd.  */
212
213 static bfd_boolean
214 bfd_mach_o_bfd_copy_private_bfd_data (ibfd, obfd)
215      bfd *ibfd;
216      bfd *obfd;
217 {
218   BFD_ASSERT (bfd_mach_o_valid (ibfd));
219   BFD_ASSERT (bfd_mach_o_valid (obfd));
220
221   obfd->tdata.mach_o_data = ibfd->tdata.mach_o_data;
222   obfd->tdata.mach_o_data->ibfd = ibfd;
223   return TRUE;
224 }
225
226 static long
227 bfd_mach_o_count_symbols (abfd)
228      bfd *abfd;
229 {
230   bfd_mach_o_data_struct *mdata = NULL;
231   long nsyms = 0;
232   unsigned long i;
233
234   BFD_ASSERT (bfd_mach_o_valid (abfd));
235   mdata = abfd->tdata.mach_o_data;
236
237   for (i = 0; i < mdata->header.ncmds; i++)
238     if (mdata->commands[i].type == BFD_MACH_O_LC_SYMTAB)
239       {
240         bfd_mach_o_symtab_command *sym = &mdata->commands[i].command.symtab;
241         nsyms += sym->nsyms;
242       }
243
244   return nsyms;
245 }
246
247 static long
248 bfd_mach_o_get_symtab_upper_bound (abfd)
249      bfd *abfd;
250 {
251   long nsyms = bfd_mach_o_count_symbols (abfd);
252
253   if (nsyms < 0)
254     return nsyms;
255
256   return ((nsyms + 1) * sizeof (asymbol *));
257 }
258
259 static long
260 bfd_mach_o_canonicalize_symtab (abfd, alocation)
261      bfd *abfd;
262      asymbol **alocation;
263 {
264   bfd_mach_o_data_struct *mdata = abfd->tdata.mach_o_data;
265   long nsyms = bfd_mach_o_count_symbols (abfd);
266   asymbol **csym = alocation;
267   unsigned long i, j;
268
269   if (nsyms < 0)
270     return nsyms;
271
272   for (i = 0; i < mdata->header.ncmds; i++)
273     {
274       if (mdata->commands[i].type == BFD_MACH_O_LC_SYMTAB)
275         {
276           bfd_mach_o_symtab_command *sym = &mdata->commands[i].command.symtab;
277
278           if (bfd_mach_o_scan_read_symtab_symbols (abfd, &mdata->commands[i].command.symtab) != 0)
279             {
280               fprintf (stderr, "bfd_mach_o_canonicalize_symtab: unable to load symbols for section %lu\n", i);
281               return 0;
282             }
283
284           BFD_ASSERT (sym->symbols != NULL);
285
286           for (j = 0; j < sym->nsyms; j++)
287             {
288               BFD_ASSERT (csym < (alocation + nsyms));
289               *csym++ = &sym->symbols[j];
290             }
291         }
292     }
293
294   *csym++ = NULL;
295
296   return nsyms;
297 }
298
299 static void
300 bfd_mach_o_get_symbol_info (abfd, symbol, ret)
301      bfd *abfd ATTRIBUTE_UNUSED;
302      asymbol *symbol;
303      symbol_info *ret;
304 {
305   bfd_symbol_info (symbol, ret);
306 }
307
308 static void
309 bfd_mach_o_print_symbol (abfd, afile, symbol, how)
310      bfd *abfd;
311      PTR afile;
312      asymbol *symbol;
313      bfd_print_symbol_type how;
314 {
315   FILE *file = (FILE *) afile;
316
317   switch (how)
318     {
319     case bfd_print_symbol_name:
320       fprintf (file, "%s", symbol->name);
321       break;
322     default:
323       bfd_print_symbol_vandf (abfd, (PTR) file, symbol);
324       fprintf (file, " %-5s %s", symbol->section->name, symbol->name);
325     }
326 }
327
328 static void
329 bfd_mach_o_convert_architecture (mtype, msubtype, type, subtype)
330      bfd_mach_o_cpu_type mtype;
331      bfd_mach_o_cpu_subtype msubtype ATTRIBUTE_UNUSED;
332      enum bfd_architecture *type;
333      unsigned long *subtype;
334 {
335   *subtype = bfd_arch_unknown;
336
337   switch (mtype)
338     {
339     case BFD_MACH_O_CPU_TYPE_VAX: *type = bfd_arch_vax; break;
340     case BFD_MACH_O_CPU_TYPE_MC680x0: *type = bfd_arch_m68k; break;
341     case BFD_MACH_O_CPU_TYPE_I386: *type = bfd_arch_i386; break;
342     case BFD_MACH_O_CPU_TYPE_MIPS: *type = bfd_arch_mips; break;
343     case BFD_MACH_O_CPU_TYPE_MC98000: *type = bfd_arch_m98k; break;
344     case BFD_MACH_O_CPU_TYPE_HPPA: *type = bfd_arch_hppa; break;
345     case BFD_MACH_O_CPU_TYPE_ARM: *type = bfd_arch_arm; break;
346     case BFD_MACH_O_CPU_TYPE_MC88000: *type = bfd_arch_m88k; break;
347     case BFD_MACH_O_CPU_TYPE_SPARC: *type = bfd_arch_sparc; break;
348     case BFD_MACH_O_CPU_TYPE_I860: *type = bfd_arch_i860; break;
349     case BFD_MACH_O_CPU_TYPE_ALPHA: *type = bfd_arch_alpha; break;
350     case BFD_MACH_O_CPU_TYPE_POWERPC: *type = bfd_arch_powerpc; break;
351     default: *type = bfd_arch_unknown; break;
352     }
353
354   switch (*type)
355     {
356     case bfd_arch_i386: *subtype = bfd_mach_i386_i386; break;
357     case bfd_arch_sparc: *subtype = bfd_mach_sparc; break;
358     default:
359       *subtype = bfd_arch_unknown;
360     }
361 }
362
363 static bfd_boolean
364 bfd_mach_o_write_contents (abfd)
365      bfd *abfd;
366 {
367   unsigned int i;
368   asection *s;
369
370   bfd_mach_o_data_struct *mdata = abfd->tdata.mach_o_data;
371
372   /* Write data sections first in case they overlap header data to be
373      written later.  */
374
375   for (s = abfd->sections; s != (asection *) NULL; s = s->next)
376     ;
377
378 #if 0
379   for (i = 0; i < mdata->header.ncmds; i++)
380     {
381       bfd_mach_o_load_command *cur = &mdata->commands[i];
382       if (cur->type != BFD_MACH_O_LC_SEGMENT)
383         break;
384
385       {
386         bfd_mach_o_segment_command *seg = &cur->command.segment;
387         char buf[1024];
388         bfd_vma nbytes = seg->filesize;
389         bfd_vma curoff = seg->fileoff;
390
391         while (nbytes > 0)
392           {
393             bfd_vma thisread = nbytes;
394
395             if (thisread > 1024)
396               thisread = 1024;
397
398             bfd_seek (abfd, curoff, SEEK_SET);
399             if (bfd_bread ((PTR) buf, thisread, abfd) != thisread)
400               return FALSE;
401
402             bfd_seek (abfd, curoff, SEEK_SET);
403             if (bfd_bwrite ((PTR) buf, thisread, abfd) != thisread)
404               return FALSE;
405
406             nbytes -= thisread;
407             curoff += thisread;
408           }
409       }
410   }
411 #endif
412
413   /* Now write header information.  */
414   if (bfd_mach_o_write_header (abfd, &mdata->header) != 0)
415     return FALSE;
416
417   for (i = 0; i < mdata->header.ncmds; i++)
418     {
419       unsigned char buf[8];
420       bfd_mach_o_load_command *cur = &mdata->commands[i];
421       unsigned long typeflag;
422
423       typeflag = cur->type_required ? cur->type & BFD_MACH_O_LC_REQ_DYLD : cur->type;
424
425       bfd_h_put_32 (abfd, typeflag, buf);
426       bfd_h_put_32 (abfd, cur->len, buf + 4);
427
428       bfd_seek (abfd, cur->offset, SEEK_SET);
429       if (bfd_bwrite ((PTR) buf, 8, abfd) != 8)
430         return FALSE;
431
432       switch (cur->type)
433         {
434         case BFD_MACH_O_LC_SEGMENT:
435           if (bfd_mach_o_scan_write_segment (abfd, cur) != 0)
436             return FALSE;
437           break;
438         case BFD_MACH_O_LC_SYMTAB:
439           if (bfd_mach_o_scan_write_symtab (abfd, cur) != 0)
440             return FALSE;
441           break;
442         case BFD_MACH_O_LC_SYMSEG:
443           break;
444         case BFD_MACH_O_LC_THREAD:
445         case BFD_MACH_O_LC_UNIXTHREAD:
446           if (bfd_mach_o_scan_write_thread (abfd, cur) != 0)
447             return FALSE;
448           break;
449         case BFD_MACH_O_LC_LOADFVMLIB:
450         case BFD_MACH_O_LC_IDFVMLIB:
451         case BFD_MACH_O_LC_IDENT:
452         case BFD_MACH_O_LC_FVMFILE:
453         case BFD_MACH_O_LC_PREPAGE:
454         case BFD_MACH_O_LC_DYSYMTAB:
455         case BFD_MACH_O_LC_LOAD_DYLIB:
456         case BFD_MACH_O_LC_LOAD_WEAK_DYLIB:
457         case BFD_MACH_O_LC_ID_DYLIB:
458         case BFD_MACH_O_LC_LOAD_DYLINKER:
459         case BFD_MACH_O_LC_ID_DYLINKER:
460         case BFD_MACH_O_LC_PREBOUND_DYLIB:
461         case BFD_MACH_O_LC_ROUTINES:
462         case BFD_MACH_O_LC_SUB_FRAMEWORK:
463           break;
464         default:
465           fprintf (stderr,
466                    "unable to write unknown load command 0x%lx\n",
467                    (long) cur->type);
468           return FALSE;
469         }
470     }
471
472   return TRUE;
473 }
474
475 static int
476 bfd_mach_o_sizeof_headers (a, b)
477      bfd *a ATTRIBUTE_UNUSED;
478      bfd_boolean b ATTRIBUTE_UNUSED;
479 {
480   return 0;
481 }
482
483 /* Make an empty symbol.  This is required only because
484    bfd_make_section_anyway wants to create a symbol for the section.  */
485
486 static asymbol *
487 bfd_mach_o_make_empty_symbol (abfd)
488      bfd *abfd;
489 {
490   asymbol *new;
491
492   new = (asymbol *) bfd_zalloc (abfd, sizeof (asymbol));
493   if (new == NULL)
494     return new;
495   new->the_bfd = abfd;
496   return new;
497 }
498
499 static int
500 bfd_mach_o_write_header (abfd, header)
501      bfd *abfd;
502      bfd_mach_o_header *header;
503 {
504   unsigned char buf[28];
505
506   bfd_h_put_32 (abfd, header->magic, buf + 0);
507   bfd_h_put_32 (abfd, header->cputype, buf + 4);
508   bfd_h_put_32 (abfd, header->cpusubtype, buf + 8);
509   bfd_h_put_32 (abfd, header->filetype, buf + 12);
510   bfd_h_put_32 (abfd, header->ncmds, buf + 16);
511   bfd_h_put_32 (abfd, header->sizeofcmds, buf + 20);
512   bfd_h_put_32 (abfd, header->flags, buf + 24);
513
514   bfd_seek (abfd, 0, SEEK_SET);
515   if (bfd_bwrite ((PTR) buf, 28, abfd) != 28)
516     return -1;
517
518   return 0;
519 }
520
521 static int
522 bfd_mach_o_read_header (abfd, header)
523      bfd *abfd;
524      bfd_mach_o_header *header;
525 {
526   unsigned char buf[28];
527   bfd_vma (*get32) (const void *) = NULL;
528
529   bfd_seek (abfd, 0, SEEK_SET);
530
531   if (bfd_bread ((PTR) buf, 28, abfd) != 28)
532     return -1;
533
534   if (bfd_getb32 (buf) == 0xfeedface)
535     {
536       header->byteorder = BFD_ENDIAN_BIG;
537       header->magic = 0xfeedface;
538       get32 = bfd_getb32;
539     }
540   else if (bfd_getl32 (buf) == 0xfeedface)
541     {
542       header->byteorder = BFD_ENDIAN_LITTLE;
543       header->magic = 0xfeedface;
544       get32 = bfd_getl32;
545     }
546   else
547     {
548       header->byteorder = BFD_ENDIAN_UNKNOWN;
549       return -1;
550     }
551
552   header->cputype = (*get32) (buf + 4);
553   header->cpusubtype = (*get32) (buf + 8);
554   header->filetype = (*get32) (buf + 12);
555   header->ncmds = (*get32) (buf + 16);
556   header->sizeofcmds = (*get32) (buf + 20);
557   header->flags = (*get32) (buf + 24);
558
559   return 0;
560 }
561
562 static asection *
563 bfd_mach_o_make_bfd_section (abfd, section)
564      bfd *abfd;
565      bfd_mach_o_section *section;
566 {
567   asection *bfdsec;
568   char *sname;
569   const char *prefix = "LC_SEGMENT";
570   unsigned int snamelen;
571
572   snamelen = strlen (prefix) + 1
573     + strlen (section->segname) + 1
574     + strlen (section->sectname) + 1;
575
576   sname = (char *) bfd_alloc (abfd, snamelen);
577   if (sname == NULL)
578     return NULL;
579   sprintf (sname, "%s.%s.%s", prefix, section->segname, section->sectname);
580
581   bfdsec = bfd_make_section_anyway (abfd, sname);
582   if (bfdsec == NULL)
583     return NULL;
584
585   bfdsec->vma = section->addr;
586   bfdsec->lma = section->addr;
587   bfdsec->size = section->size;
588   bfdsec->filepos = section->offset;
589   bfdsec->alignment_power = section->align;
590
591   if (section->flags & BFD_MACH_O_S_ZEROFILL)
592     bfdsec->flags = SEC_ALLOC;
593   else
594     bfdsec->flags = SEC_HAS_CONTENTS | SEC_LOAD | SEC_ALLOC | SEC_CODE;
595
596   return bfdsec;
597 }
598
599 static int
600 bfd_mach_o_scan_read_section (abfd, section, offset)
601      bfd *abfd;
602      bfd_mach_o_section *section;
603      bfd_vma offset;
604 {
605   unsigned char buf[68];
606
607   bfd_seek (abfd, offset, SEEK_SET);
608   if (bfd_bread ((PTR) buf, 68, abfd) != 68)
609     return -1;
610
611   memcpy (section->sectname, buf, 16);
612   section->sectname[16] = '\0';
613   memcpy (section->segname, buf + 16, 16);
614   section->segname[16] = '\0';
615   section->addr = bfd_h_get_32 (abfd, buf + 32);
616   section->size = bfd_h_get_32 (abfd, buf + 36);
617   section->offset = bfd_h_get_32 (abfd, buf + 40);
618   section->align = bfd_h_get_32 (abfd, buf + 44);
619   section->reloff = bfd_h_get_32 (abfd, buf + 48);
620   section->nreloc = bfd_h_get_32 (abfd, buf + 52);
621   section->flags = bfd_h_get_32 (abfd, buf + 56);
622   section->reserved1 = bfd_h_get_32 (abfd, buf + 60);
623   section->reserved2 = bfd_h_get_32 (abfd, buf + 64);
624   section->bfdsection = bfd_mach_o_make_bfd_section (abfd, section);
625
626   if (section->bfdsection == NULL)
627     return -1;
628
629   return 0;
630 }
631
632 static int
633 bfd_mach_o_scan_write_section (abfd, section, offset)
634      bfd *abfd;
635      bfd_mach_o_section *section;
636      bfd_vma offset;
637 {
638   unsigned char buf[68];
639
640   memcpy (buf, section->sectname, 16);
641   memcpy (buf + 16, section->segname, 16);
642   bfd_h_put_32 (abfd, section->addr, buf + 32);
643   bfd_h_put_32 (abfd, section->size, buf + 36);
644   bfd_h_put_32 (abfd, section->offset, buf + 40);
645   bfd_h_put_32 (abfd, section->align, buf + 44);
646   bfd_h_put_32 (abfd, section->reloff, buf + 48);
647   bfd_h_put_32 (abfd, section->nreloc, buf + 52);
648   bfd_h_put_32 (abfd, section->flags, buf + 56);
649   /* bfd_h_put_32 (abfd, section->reserved1, buf + 60); */
650   /* bfd_h_put_32 (abfd, section->reserved2, buf + 64); */
651
652   bfd_seek (abfd, offset, SEEK_SET);
653   if (bfd_bwrite ((PTR) buf, 68, abfd) != 68)
654     return -1;
655
656   return 0;
657 }
658
659 static int
660 bfd_mach_o_scan_write_symtab_symbols (abfd, command)
661      bfd *abfd;
662      bfd_mach_o_load_command *command;
663 {
664   bfd_mach_o_symtab_command *sym = &command->command.symtab;
665   asymbol *s = NULL;
666   unsigned long i;
667
668   for (i = 0; i < sym->nsyms; i++)
669     {
670       unsigned char buf[12];
671       bfd_vma symoff = sym->symoff + (i * 12);
672       unsigned char ntype = 0;
673       unsigned char nsect = 0;
674       short ndesc = 0;
675
676       s = &sym->symbols[i];
677
678       /* Don't set this from the symbol information; use stored values.  */
679 #if 0
680       if (s->flags & BSF_GLOBAL)
681         ntype |= N_EXT;
682       if (s->flags & BSF_DEBUGGING)
683         ntype |= N_STAB;
684
685       if (s->section == bfd_und_section_ptr)
686         ntype |= N_UNDF;
687       else if (s->section == bfd_abs_section_ptr)
688         ntype |= N_ABS;
689       else
690         ntype |= N_SECT;
691 #endif
692
693       /* Instead just set from the stored values.  */
694       ntype = (s->udata.i >> 24) & 0xff;
695       nsect = (s->udata.i >> 16) & 0xff;
696       ndesc = s->udata.i & 0xffff;
697
698       bfd_h_put_32 (abfd, s->name - sym->strtab, buf);
699       bfd_h_put_8 (abfd, ntype, buf + 4);
700       bfd_h_put_8 (abfd, nsect, buf + 5);
701       bfd_h_put_16 (abfd, ndesc, buf + 6);
702       bfd_h_put_32 (abfd, s->section->vma + s->value, buf + 8);
703
704       bfd_seek (abfd, symoff, SEEK_SET);
705       if (bfd_bwrite ((PTR) buf, 12, abfd) != 12)
706         {
707           fprintf (stderr, "bfd_mach_o_scan_write_symtab_symbols: unable to write %d bytes at %lu\n",
708                    12, (unsigned long) symoff);
709           return -1;
710         }
711     }
712
713   return 0;
714 }
715
716 int
717 bfd_mach_o_scan_read_symtab_symbol (abfd, sym, s, i)
718      bfd *abfd;
719      bfd_mach_o_symtab_command *sym;
720      asymbol *s;
721      unsigned long i;
722 {
723   bfd_mach_o_data_struct *mdata = abfd->tdata.mach_o_data;
724   bfd_vma symoff = sym->symoff + (i * 12);
725   unsigned char buf[12];
726   unsigned char type = -1;
727   unsigned char section = -1;
728   short desc = -1;
729   unsigned long value = -1;
730   unsigned long stroff = -1;
731   unsigned int symtype = -1;
732
733   BFD_ASSERT (sym->strtab != NULL);
734
735   bfd_seek (abfd, symoff, SEEK_SET);
736   if (bfd_bread ((PTR) buf, 12, abfd) != 12)
737     {
738       fprintf (stderr, "bfd_mach_o_scan_read_symtab_symbol: unable to read %d bytes at %lu\n",
739                12, (unsigned long) symoff);
740       return -1;
741     }
742
743   stroff = bfd_h_get_32 (abfd, buf);
744   type = bfd_h_get_8 (abfd, buf + 4);
745   symtype = (type & 0x0e);
746   section = bfd_h_get_8 (abfd, buf + 5) - 1;
747   desc = bfd_h_get_16 (abfd, buf + 6);
748   value = bfd_h_get_32 (abfd, buf + 8);
749
750   if (stroff >= sym->strsize)
751     {
752       fprintf (stderr, "bfd_mach_o_scan_read_symtab_symbol: symbol name out of range (%lu >= %lu)\n",
753                (unsigned long) stroff, (unsigned long) sym->strsize);
754       return -1;
755     }
756
757   s->the_bfd = abfd;
758   s->name = sym->strtab + stroff;
759   s->value = value;
760   s->udata.i = (type << 24) | (section << 16) | desc;
761   s->flags = 0x0;
762
763   if (type & BFD_MACH_O_N_STAB)
764     {
765       s->flags |= BSF_DEBUGGING;
766       s->section = bfd_und_section_ptr;
767     }
768   else
769     {
770       if (type & BFD_MACH_O_N_PEXT)
771         {
772           type &= ~BFD_MACH_O_N_PEXT;
773           s->flags |= BSF_GLOBAL;
774         }
775
776       if (type & BFD_MACH_O_N_EXT)
777         {
778           type &= ~BFD_MACH_O_N_EXT;
779           s->flags |= BSF_GLOBAL;
780         }
781
782       switch (symtype)
783         {
784         case BFD_MACH_O_N_UNDF:
785           s->section = bfd_und_section_ptr;
786           break;
787         case BFD_MACH_O_N_PBUD:
788           s->section = bfd_und_section_ptr;
789           break;
790         case BFD_MACH_O_N_ABS:
791           s->section = bfd_abs_section_ptr;
792           break;
793         case BFD_MACH_O_N_SECT:
794           if ((section > 0) && (section <= mdata->nsects))
795             {
796               s->section = mdata->sections[section - 1]->bfdsection;
797               s->value = s->value - mdata->sections[section - 1]->addr;
798             }
799           else
800             {
801               /* Mach-O uses 0 to mean "no section"; not an error.  */
802               if (section != 0)
803                 {
804                   fprintf (stderr, "bfd_mach_o_scan_read_symtab_symbol: "
805                            "symbol \"%s\" specified invalid section %d (max %lu): setting to undefined\n",
806                            s->name, section, mdata->nsects);
807                 }
808               s->section = bfd_und_section_ptr;
809             }
810           break;
811         case BFD_MACH_O_N_INDR:
812           fprintf (stderr, "bfd_mach_o_scan_read_symtab_symbol: "
813                    "symbol \"%s\" is unsupported 'indirect' reference: setting to undefined\n",
814                    s->name);
815           s->section = bfd_und_section_ptr;
816           break;
817         default:
818           fprintf (stderr, "bfd_mach_o_scan_read_symtab_symbol: "
819                    "symbol \"%s\" specified invalid type field 0x%x: setting to undefined\n",
820                    s->name, symtype);
821           s->section = bfd_und_section_ptr;
822           break;
823         }
824     }
825
826   return 0;
827 }
828
829 int
830 bfd_mach_o_scan_read_symtab_strtab (abfd, sym)
831      bfd *abfd;
832      bfd_mach_o_symtab_command *sym;
833 {
834   BFD_ASSERT (sym->strtab == NULL);
835
836   if (abfd->flags & BFD_IN_MEMORY)
837     {
838       struct bfd_in_memory *b;
839
840       b = (struct bfd_in_memory *) abfd->iostream;
841
842       if ((sym->stroff + sym->strsize) > b->size)
843         {
844           bfd_set_error (bfd_error_file_truncated);
845           return -1;
846         }
847       sym->strtab = b->buffer + sym->stroff;
848       return 0;
849     }
850
851   sym->strtab = bfd_alloc (abfd, sym->strsize);
852   if (sym->strtab == NULL)
853     return -1;
854
855   bfd_seek (abfd, sym->stroff, SEEK_SET);
856   if (bfd_bread ((PTR) sym->strtab, sym->strsize, abfd) != sym->strsize)
857     {
858       fprintf (stderr, "bfd_mach_o_scan_read_symtab_strtab: unable to read %lu bytes at %lu\n",
859                sym->strsize, sym->stroff);
860       return -1;
861     }
862
863   return 0;
864 }
865
866 int
867 bfd_mach_o_scan_read_symtab_symbols (abfd, sym)
868      bfd *abfd;
869      bfd_mach_o_symtab_command *sym;
870 {
871   unsigned long i;
872   int ret;
873
874   BFD_ASSERT (sym->symbols == NULL);
875   sym->symbols = bfd_alloc (abfd, sym->nsyms * sizeof (asymbol));
876
877   if (sym->symbols == NULL)
878     {
879       fprintf (stderr, "bfd_mach_o_scan_read_symtab_symbols: unable to allocate memory for symbols\n");
880       return -1;
881     }
882
883   ret = bfd_mach_o_scan_read_symtab_strtab (abfd, sym);
884   if (ret != 0)
885     return ret;
886
887   for (i = 0; i < sym->nsyms; i++)
888     {
889       ret = bfd_mach_o_scan_read_symtab_symbol (abfd, sym, &sym->symbols[i], i);
890       if (ret != 0)
891         return ret;
892     }
893
894   return 0;
895 }
896
897 int
898 bfd_mach_o_scan_read_dysymtab_symbol (abfd, dysym, sym, s, i)
899      bfd *abfd;
900      bfd_mach_o_dysymtab_command *dysym;
901      bfd_mach_o_symtab_command *sym;
902      asymbol *s;
903      unsigned long i;
904 {
905   unsigned long isymoff = dysym->indirectsymoff + (i * 4);
906   unsigned long symindex;
907   unsigned char buf[4];
908
909   BFD_ASSERT (i < dysym->nindirectsyms);
910
911   bfd_seek (abfd, isymoff, SEEK_SET);
912   if (bfd_bread ((PTR) buf, 4, abfd) != 4)
913     {
914       fprintf (stderr, "bfd_mach_o_scan_read_dysymtab_symbol: unable to read %lu bytes at %lu\n",
915                (unsigned long) 4, isymoff);
916       return -1;
917     }
918   symindex = bfd_h_get_32 (abfd, buf);
919
920   return bfd_mach_o_scan_read_symtab_symbol (abfd, sym, s, symindex);
921 }
922
923 static const char *
924 bfd_mach_o_i386_flavour_string (flavour)
925      unsigned int flavour;
926 {
927   switch ((int) flavour)
928     {
929     case BFD_MACH_O_i386_NEW_THREAD_STATE: return "i386_NEW_THREAD_STATE";
930     case BFD_MACH_O_i386_FLOAT_STATE: return "i386_FLOAT_STATE";
931     case BFD_MACH_O_i386_ISA_PORT_MAP_STATE: return "i386_ISA_PORT_MAP_STATE";
932     case BFD_MACH_O_i386_V86_ASSIST_STATE: return "i386_V86_ASSIST_STATE";
933     case BFD_MACH_O_i386_REGS_SEGS_STATE: return "i386_REGS_SEGS_STATE";
934     case BFD_MACH_O_i386_THREAD_SYSCALL_STATE: return "i386_THREAD_SYSCALL_STATE";
935     case BFD_MACH_O_i386_THREAD_STATE_NONE: return "i386_THREAD_STATE_NONE";
936     case BFD_MACH_O_i386_SAVED_STATE: return "i386_SAVED_STATE";
937     case BFD_MACH_O_i386_THREAD_STATE: return "i386_THREAD_STATE";
938     case BFD_MACH_O_i386_THREAD_FPSTATE: return "i386_THREAD_FPSTATE";
939     case BFD_MACH_O_i386_THREAD_EXCEPTSTATE: return "i386_THREAD_EXCEPTSTATE";
940     case BFD_MACH_O_i386_THREAD_CTHREADSTATE: return "i386_THREAD_CTHREADSTATE";
941     default: return "UNKNOWN";
942     }
943 }
944
945 static const char *
946 bfd_mach_o_ppc_flavour_string (flavour)
947      unsigned int flavour;
948 {
949   switch ((int) flavour)
950     {
951     case BFD_MACH_O_PPC_THREAD_STATE: return "PPC_THREAD_STATE";
952     case BFD_MACH_O_PPC_FLOAT_STATE: return "PPC_FLOAT_STATE";
953     case BFD_MACH_O_PPC_EXCEPTION_STATE: return "PPC_EXCEPTION_STATE";
954     case BFD_MACH_O_PPC_VECTOR_STATE: return "PPC_VECTOR_STATE";
955     default: return "UNKNOWN";
956     }
957 }
958
959 static int
960 bfd_mach_o_scan_write_thread (abfd, command)
961      bfd *abfd;
962      bfd_mach_o_load_command *command;
963 {
964   bfd_mach_o_thread_command *cmd = &command->command.thread;
965   unsigned int i;
966   unsigned char buf[8];
967   bfd_vma offset;
968   unsigned int nflavours;
969
970   BFD_ASSERT ((command->type == BFD_MACH_O_LC_THREAD)
971               || (command->type == BFD_MACH_O_LC_UNIXTHREAD));
972
973   offset = 8;
974   nflavours = 0;
975   for (i = 0; i < cmd->nflavours; i++)
976     {
977       BFD_ASSERT ((cmd->flavours[i].size % 4) == 0);
978       BFD_ASSERT (cmd->flavours[i].offset == (command->offset + offset + 8));
979
980       bfd_h_put_32 (abfd, cmd->flavours[i].flavour, buf);
981       bfd_h_put_32 (abfd, (cmd->flavours[i].size / 4), buf + 4);
982
983       bfd_seek (abfd, command->offset + offset, SEEK_SET);
984       if (bfd_bwrite ((PTR) buf, 8, abfd) != 8)
985         return -1;
986
987       offset += cmd->flavours[i].size + 8;
988     }
989
990   return 0;
991 }
992
993 static int
994 bfd_mach_o_scan_read_dylinker (abfd, command)
995      bfd *abfd;
996      bfd_mach_o_load_command *command;
997 {
998   bfd_mach_o_dylinker_command *cmd = &command->command.dylinker;
999   unsigned char buf[4];
1000   unsigned int nameoff;
1001   asection *bfdsec;
1002   char *sname;
1003   const char *prefix;
1004
1005   BFD_ASSERT ((command->type == BFD_MACH_O_LC_ID_DYLINKER)
1006               || (command->type == BFD_MACH_O_LC_LOAD_DYLINKER));
1007
1008   bfd_seek (abfd, command->offset + 8, SEEK_SET);
1009   if (bfd_bread ((PTR) buf, 4, abfd) != 4)
1010     return -1;
1011
1012   nameoff = bfd_h_get_32 (abfd, buf + 0);
1013
1014   cmd->name_offset = command->offset + nameoff;
1015   cmd->name_len = command->len - nameoff;
1016
1017   if (command->type == BFD_MACH_O_LC_LOAD_DYLINKER)
1018     prefix = "LC_LOAD_DYLINKER";
1019   else if (command->type == BFD_MACH_O_LC_ID_DYLINKER)
1020     prefix = "LC_ID_DYLINKER";
1021   else
1022     abort ();
1023
1024   sname = (char *) bfd_alloc (abfd, strlen (prefix) + 1);
1025   if (sname == NULL)
1026     return -1;
1027   strcpy (sname, prefix);
1028
1029   bfdsec = bfd_make_section_anyway (abfd, sname);
1030   if (bfdsec == NULL)
1031     return -1;
1032
1033   bfdsec->vma = 0;
1034   bfdsec->lma = 0;
1035   bfdsec->size = command->len - 8;
1036   bfdsec->filepos = command->offset + 8;
1037   bfdsec->alignment_power = 0;
1038   bfdsec->flags = SEC_HAS_CONTENTS;
1039
1040   cmd->section = bfdsec;
1041
1042   return 0;
1043 }
1044
1045 static int
1046 bfd_mach_o_scan_read_dylib (abfd, command)
1047      bfd *abfd;
1048      bfd_mach_o_load_command *command;
1049 {
1050   bfd_mach_o_dylib_command *cmd = &command->command.dylib;
1051   unsigned char buf[16];
1052   unsigned int nameoff;
1053   asection *bfdsec;
1054   char *sname;
1055   const char *prefix;
1056
1057   BFD_ASSERT ((command->type == BFD_MACH_O_LC_ID_DYLIB)
1058               || (command->type == BFD_MACH_O_LC_LOAD_DYLIB)
1059               || (command->type == BFD_MACH_O_LC_LOAD_WEAK_DYLIB));
1060
1061   bfd_seek (abfd, command->offset + 8, SEEK_SET);
1062   if (bfd_bread ((PTR) buf, 16, abfd) != 16)
1063     return -1;
1064
1065   nameoff = bfd_h_get_32 (abfd, buf + 0);
1066   cmd->timestamp = bfd_h_get_32 (abfd, buf + 4);
1067   cmd->current_version = bfd_h_get_32 (abfd, buf + 8);
1068   cmd->compatibility_version = bfd_h_get_32 (abfd, buf + 12);
1069
1070   cmd->name_offset = command->offset + nameoff;
1071   cmd->name_len = command->len - nameoff;
1072
1073   if (command->type == BFD_MACH_O_LC_LOAD_DYLIB)
1074     prefix = "LC_LOAD_DYLIB";
1075   else if (command->type == BFD_MACH_O_LC_LOAD_WEAK_DYLIB)
1076     prefix = "LC_LOAD_WEAK_DYLIB";
1077   else if (command->type == BFD_MACH_O_LC_ID_DYLIB)
1078     prefix = "LC_ID_DYLIB";
1079   else
1080     abort ();
1081
1082   sname = (char *) bfd_alloc (abfd, strlen (prefix) + 1);
1083   if (sname == NULL)
1084     return -1;
1085   strcpy (sname, prefix);
1086
1087   bfdsec = bfd_make_section_anyway (abfd, sname);
1088   if (bfdsec == NULL)
1089     return -1;
1090
1091   bfdsec->vma = 0;
1092   bfdsec->lma = 0;
1093   bfdsec->size = command->len - 8;
1094   bfdsec->filepos = command->offset + 8;
1095   bfdsec->alignment_power = 0;
1096   bfdsec->flags = SEC_HAS_CONTENTS;
1097
1098   cmd->section = bfdsec;
1099
1100   return 0;
1101 }
1102
1103 static int
1104 bfd_mach_o_scan_read_prebound_dylib (abfd, command)
1105      bfd *abfd ATTRIBUTE_UNUSED;
1106      bfd_mach_o_load_command *command ATTRIBUTE_UNUSED;
1107 {
1108   /* bfd_mach_o_prebound_dylib_command *cmd = &command->command.prebound_dylib; */
1109
1110   BFD_ASSERT (command->type == BFD_MACH_O_LC_PREBOUND_DYLIB);
1111   return 0;
1112 }
1113
1114 static int
1115 bfd_mach_o_scan_read_thread (abfd, command)
1116      bfd *abfd;
1117      bfd_mach_o_load_command *command;
1118 {
1119   bfd_mach_o_data_struct *mdata = NULL;
1120   bfd_mach_o_thread_command *cmd = &command->command.thread;
1121   unsigned char buf[8];
1122   bfd_vma offset;
1123   unsigned int nflavours;
1124   unsigned int i;
1125
1126   BFD_ASSERT ((command->type == BFD_MACH_O_LC_THREAD)
1127               || (command->type == BFD_MACH_O_LC_UNIXTHREAD));
1128
1129   BFD_ASSERT (bfd_mach_o_valid (abfd));
1130   mdata = abfd->tdata.mach_o_data;
1131
1132   offset = 8;
1133   nflavours = 0;
1134   while (offset != command->len)
1135     {
1136       if (offset >= command->len)
1137         return -1;
1138
1139       bfd_seek (abfd, command->offset + offset, SEEK_SET);
1140
1141       if (bfd_bread ((PTR) buf, 8, abfd) != 8)
1142         return -1;
1143
1144       offset += 8 + bfd_h_get_32 (abfd, buf + 4) * 4;
1145       nflavours++;
1146     }
1147
1148   cmd->flavours =
1149     ((bfd_mach_o_thread_flavour *)
1150      bfd_alloc (abfd, nflavours * sizeof (bfd_mach_o_thread_flavour)));
1151   if (cmd->flavours == NULL)
1152     return -1;
1153   cmd->nflavours = nflavours;
1154
1155   offset = 8;
1156   nflavours = 0;
1157   while (offset != command->len)
1158     {
1159       if (offset >= command->len)
1160         return -1;
1161
1162       if (nflavours >= cmd->nflavours)
1163         return -1;
1164
1165       bfd_seek (abfd, command->offset + offset, SEEK_SET);
1166
1167       if (bfd_bread ((PTR) buf, 8, abfd) != 8)
1168         return -1;
1169
1170       cmd->flavours[nflavours].flavour = bfd_h_get_32 (abfd, buf);
1171       cmd->flavours[nflavours].offset = command->offset + offset + 8;
1172       cmd->flavours[nflavours].size = bfd_h_get_32 (abfd, buf + 4) * 4;
1173       offset += cmd->flavours[nflavours].size + 8;
1174       nflavours++;
1175     }
1176
1177   for (i = 0; i < nflavours; i++)
1178     {
1179       asection *bfdsec;
1180       unsigned int snamelen;
1181       char *sname;
1182       const char *flavourstr;
1183       const char *prefix = "LC_THREAD";
1184       unsigned int j = 0;
1185
1186       switch (mdata->header.cputype)
1187         {
1188         case BFD_MACH_O_CPU_TYPE_POWERPC:
1189           flavourstr = bfd_mach_o_ppc_flavour_string (cmd->flavours[i].flavour);
1190           break;
1191         case BFD_MACH_O_CPU_TYPE_I386:
1192           flavourstr = bfd_mach_o_i386_flavour_string (cmd->flavours[i].flavour);
1193           break;
1194         default:
1195           flavourstr = "UNKNOWN_ARCHITECTURE";
1196           break;
1197         }
1198
1199       snamelen = strlen (prefix) + 1 + 20 + 1 + strlen (flavourstr) + 1;
1200       sname = (char *) bfd_alloc (abfd, snamelen);
1201       if (sname == NULL)
1202         return -1;
1203
1204       for (;;)
1205         {
1206           sprintf (sname, "%s.%s.%u", prefix, flavourstr, j);
1207           if (bfd_get_section_by_name (abfd, sname) == NULL)
1208             break;
1209           j++;
1210         }
1211
1212       bfdsec = bfd_make_section (abfd, sname);
1213
1214       bfdsec->vma = 0;
1215       bfdsec->lma = 0;
1216       bfdsec->size = cmd->flavours[i].size;
1217       bfdsec->filepos = cmd->flavours[i].offset;
1218       bfdsec->alignment_power = 0x0;
1219       bfdsec->flags = SEC_HAS_CONTENTS;
1220
1221       cmd->section = bfdsec;
1222     }
1223
1224   return 0;
1225 }
1226
1227 static int
1228 bfd_mach_o_scan_write_symtab (abfd, command)
1229      bfd *abfd;
1230      bfd_mach_o_load_command *command;
1231 {
1232   bfd_mach_o_symtab_command *seg = &command->command.symtab;
1233   unsigned char buf[16];
1234
1235   BFD_ASSERT (command->type == BFD_MACH_O_LC_SYMTAB);
1236
1237   bfd_h_put_32 (abfd, seg->symoff, buf);
1238   bfd_h_put_32 (abfd, seg->nsyms, buf + 4);
1239   bfd_h_put_32 (abfd, seg->stroff, buf + 8);
1240   bfd_h_put_32 (abfd, seg->strsize, buf + 12);
1241
1242   bfd_seek (abfd, command->offset + 8, SEEK_SET);
1243   if (bfd_bwrite ((PTR) buf, 16, abfd) != 16)
1244     return -1;
1245
1246   if (bfd_mach_o_scan_write_symtab_symbols (abfd, command) != 0)
1247     return -1;
1248
1249   return 0;
1250 }
1251
1252 static int
1253 bfd_mach_o_scan_read_dysymtab (abfd, command)
1254      bfd *abfd;
1255      bfd_mach_o_load_command *command;
1256 {
1257   bfd_mach_o_dysymtab_command *seg = &command->command.dysymtab;
1258   unsigned char buf[72];
1259
1260   BFD_ASSERT (command->type == BFD_MACH_O_LC_DYSYMTAB);
1261
1262   bfd_seek (abfd, command->offset + 8, SEEK_SET);
1263   if (bfd_bread ((PTR) buf, 72, abfd) != 72)
1264     return -1;
1265
1266   seg->ilocalsym = bfd_h_get_32 (abfd, buf + 0);
1267   seg->nlocalsym = bfd_h_get_32 (abfd, buf + 4);
1268   seg->iextdefsym = bfd_h_get_32 (abfd, buf + 8);
1269   seg->nextdefsym = bfd_h_get_32 (abfd, buf + 12);
1270   seg->iundefsym = bfd_h_get_32 (abfd, buf + 16);
1271   seg->nundefsym = bfd_h_get_32 (abfd, buf + 20);
1272   seg->tocoff = bfd_h_get_32 (abfd, buf + 24);
1273   seg->ntoc = bfd_h_get_32 (abfd, buf + 28);
1274   seg->modtaboff = bfd_h_get_32 (abfd, buf + 32);
1275   seg->nmodtab = bfd_h_get_32 (abfd, buf + 36);
1276   seg->extrefsymoff = bfd_h_get_32 (abfd, buf + 40);
1277   seg->nextrefsyms = bfd_h_get_32 (abfd, buf + 44);
1278   seg->indirectsymoff = bfd_h_get_32 (abfd, buf + 48);
1279   seg->nindirectsyms = bfd_h_get_32 (abfd, buf + 52);
1280   seg->extreloff = bfd_h_get_32 (abfd, buf + 56);
1281   seg->nextrel = bfd_h_get_32 (abfd, buf + 60);
1282   seg->locreloff = bfd_h_get_32 (abfd, buf + 64);
1283   seg->nlocrel = bfd_h_get_32 (abfd, buf + 68);
1284
1285   return 0;
1286 }
1287
1288 static int
1289 bfd_mach_o_scan_read_symtab (abfd, command)
1290      bfd *abfd;
1291      bfd_mach_o_load_command *command;
1292 {
1293   bfd_mach_o_symtab_command *seg = &command->command.symtab;
1294   unsigned char buf[16];
1295   asection *bfdsec;
1296   char *sname;
1297   const char *prefix = "LC_SYMTAB.stabs";
1298
1299   BFD_ASSERT (command->type == BFD_MACH_O_LC_SYMTAB);
1300
1301   bfd_seek (abfd, command->offset + 8, SEEK_SET);
1302   if (bfd_bread ((PTR) buf, 16, abfd) != 16)
1303     return -1;
1304
1305   seg->symoff = bfd_h_get_32 (abfd, buf);
1306   seg->nsyms = bfd_h_get_32 (abfd, buf + 4);
1307   seg->stroff = bfd_h_get_32 (abfd, buf + 8);
1308   seg->strsize = bfd_h_get_32 (abfd, buf + 12);
1309   seg->symbols = NULL;
1310   seg->strtab = NULL;
1311
1312   sname = (char *) bfd_alloc (abfd, strlen (prefix) + 1);
1313   if (sname == NULL)
1314     return -1;
1315   strcpy (sname, prefix);
1316
1317   bfdsec = bfd_make_section_anyway (abfd, sname);
1318   if (bfdsec == NULL)
1319     return -1;
1320
1321   bfdsec->vma = 0;
1322   bfdsec->lma = 0;
1323   bfdsec->size = seg->nsyms * 12;
1324   bfdsec->filepos = seg->symoff;
1325   bfdsec->alignment_power = 0;
1326   bfdsec->flags = SEC_HAS_CONTENTS;
1327
1328   seg->stabs_segment = bfdsec;
1329
1330   prefix = "LC_SYMTAB.stabstr";
1331   sname = (char *) bfd_alloc (abfd, strlen (prefix) + 1);
1332   if (sname == NULL)
1333     return -1;
1334   strcpy (sname, prefix);
1335
1336   bfdsec = bfd_make_section_anyway (abfd, sname);
1337   if (bfdsec == NULL)
1338     return -1;
1339
1340   bfdsec->vma = 0;
1341   bfdsec->lma = 0;
1342   bfdsec->size = seg->strsize;
1343   bfdsec->filepos = seg->stroff;
1344   bfdsec->alignment_power = 0;
1345   bfdsec->flags = SEC_HAS_CONTENTS;
1346
1347   seg->stabstr_segment = bfdsec;
1348
1349   return 0;
1350 }
1351
1352 static int
1353 bfd_mach_o_scan_read_segment (abfd, command)
1354      bfd *abfd;
1355      bfd_mach_o_load_command *command;
1356 {
1357   unsigned char buf[48];
1358   bfd_mach_o_segment_command *seg = &command->command.segment;
1359   unsigned long i;
1360   asection *bfdsec;
1361   char *sname;
1362   const char *prefix = "LC_SEGMENT";
1363   unsigned int snamelen;
1364
1365   BFD_ASSERT (command->type == BFD_MACH_O_LC_SEGMENT);
1366
1367   bfd_seek (abfd, command->offset + 8, SEEK_SET);
1368   if (bfd_bread ((PTR) buf, 48, abfd) != 48)
1369     return -1;
1370
1371   memcpy (seg->segname, buf, 16);
1372   seg->vmaddr = bfd_h_get_32 (abfd, buf + 16);
1373   seg->vmsize = bfd_h_get_32 (abfd, buf + 20);
1374   seg->fileoff = bfd_h_get_32 (abfd, buf + 24);
1375   seg->filesize = bfd_h_get_32 (abfd, buf +  28);
1376   /* seg->maxprot = bfd_h_get_32 (abfd, buf + 32); */
1377   /* seg->initprot = bfd_h_get_32 (abfd, buf + 36); */
1378   seg->nsects = bfd_h_get_32 (abfd, buf + 40);
1379   seg->flags = bfd_h_get_32 (abfd, buf + 44);
1380
1381   snamelen = strlen (prefix) + 1 + strlen (seg->segname) + 1;
1382   sname = (char *) bfd_alloc (abfd, snamelen);
1383   if (sname == NULL)
1384     return -1;
1385   sprintf (sname, "%s.%s", prefix, seg->segname);
1386
1387   bfdsec = bfd_make_section_anyway (abfd, sname);
1388   if (bfdsec == NULL)
1389     return -1;
1390
1391   bfdsec->vma = seg->vmaddr;
1392   bfdsec->lma = seg->vmaddr;
1393   bfdsec->size = seg->filesize;
1394   bfdsec->filepos = seg->fileoff;
1395   bfdsec->alignment_power = 0x0;
1396   bfdsec->flags = SEC_HAS_CONTENTS | SEC_LOAD | SEC_ALLOC | SEC_CODE;
1397
1398   seg->segment = bfdsec;
1399
1400   if (seg->nsects != 0)
1401     {
1402       seg->sections =
1403         ((bfd_mach_o_section *)
1404          bfd_alloc (abfd, seg->nsects * sizeof (bfd_mach_o_section)));
1405       if (seg->sections == NULL)
1406         return -1;
1407
1408       for (i = 0; i < seg->nsects; i++)
1409         {
1410           bfd_vma segoff = command->offset + 48 + 8 + (i * 68);
1411
1412           if (bfd_mach_o_scan_read_section (abfd, &seg->sections[i],
1413                                             segoff) != 0)
1414             return -1;
1415         }
1416     }
1417
1418   return 0;
1419 }
1420
1421 static int
1422 bfd_mach_o_scan_write_segment (abfd, command)
1423      bfd *abfd;
1424      bfd_mach_o_load_command *command;
1425 {
1426   unsigned char buf[48];
1427   bfd_mach_o_segment_command *seg = &command->command.segment;
1428   unsigned long i;
1429
1430   BFD_ASSERT (command->type == BFD_MACH_O_LC_SEGMENT);
1431
1432   memcpy (buf, seg->segname, 16);
1433   bfd_h_put_32 (abfd, seg->vmaddr, buf + 16);
1434   bfd_h_put_32 (abfd, seg->vmsize, buf + 20);
1435   bfd_h_put_32 (abfd, seg->fileoff, buf + 24);
1436   bfd_h_put_32 (abfd, seg->filesize, buf + 28);
1437   bfd_h_put_32 (abfd, 0 /* seg->maxprot */, buf + 32);
1438   bfd_h_put_32 (abfd, 0 /* seg->initprot */, buf + 36);
1439   bfd_h_put_32 (abfd, seg->nsects, buf + 40);
1440   bfd_h_put_32 (abfd, seg->flags, buf + 44);
1441
1442   bfd_seek (abfd, command->offset + 8, SEEK_SET);
1443   if (bfd_bwrite ((PTR) buf, 48, abfd) != 48)
1444     return -1;
1445
1446   {
1447     char buf[1024];
1448     bfd_vma nbytes = seg->filesize;
1449     bfd_vma curoff = seg->fileoff;
1450
1451     while (nbytes > 0)
1452       {
1453         bfd_vma thisread = nbytes;
1454
1455         if (thisread > 1024)
1456           thisread = 1024;
1457
1458         bfd_seek (abfd, curoff, SEEK_SET);
1459         if (bfd_bread ((PTR) buf, thisread, abfd) != thisread)
1460           return -1;
1461
1462         bfd_seek (abfd, curoff, SEEK_SET);
1463         if (bfd_bwrite ((PTR) buf, thisread, abfd) != thisread)
1464           return -1;
1465
1466         nbytes -= thisread;
1467         curoff += thisread;
1468       }
1469   }
1470
1471   for (i = 0; i < seg->nsects; i++)
1472     {
1473       bfd_vma segoff = command->offset + 48 + 8 + (i * 68);
1474
1475       if (bfd_mach_o_scan_write_section (abfd, &seg->sections[i], segoff) != 0)
1476         return -1;
1477     }
1478
1479   return 0;
1480 }
1481
1482 static int
1483 bfd_mach_o_scan_read_command (abfd, command)
1484      bfd *abfd;
1485      bfd_mach_o_load_command *command;
1486 {
1487   unsigned char buf[8];
1488
1489   bfd_seek (abfd, command->offset, SEEK_SET);
1490   if (bfd_bread ((PTR) buf, 8, abfd) != 8)
1491     return -1;
1492
1493   command->type = (bfd_h_get_32 (abfd, buf) & ~BFD_MACH_O_LC_REQ_DYLD);
1494   command->type_required = (bfd_h_get_32 (abfd, buf) & BFD_MACH_O_LC_REQ_DYLD
1495                             ? 1 : 0);
1496   command->len = bfd_h_get_32 (abfd, buf + 4);
1497
1498   switch (command->type)
1499     {
1500     case BFD_MACH_O_LC_SEGMENT:
1501       if (bfd_mach_o_scan_read_segment (abfd, command) != 0)
1502         return -1;
1503       break;
1504     case BFD_MACH_O_LC_SYMTAB:
1505       if (bfd_mach_o_scan_read_symtab (abfd, command) != 0)
1506         return -1;
1507       break;
1508     case BFD_MACH_O_LC_SYMSEG:
1509       break;
1510     case BFD_MACH_O_LC_THREAD:
1511     case BFD_MACH_O_LC_UNIXTHREAD:
1512       if (bfd_mach_o_scan_read_thread (abfd, command) != 0)
1513         return -1;
1514       break;
1515     case BFD_MACH_O_LC_LOAD_DYLINKER:
1516     case BFD_MACH_O_LC_ID_DYLINKER:
1517       if (bfd_mach_o_scan_read_dylinker (abfd, command) != 0)
1518         return -1;
1519       break;
1520     case BFD_MACH_O_LC_LOAD_DYLIB:
1521     case BFD_MACH_O_LC_ID_DYLIB:
1522     case BFD_MACH_O_LC_LOAD_WEAK_DYLIB:
1523       if (bfd_mach_o_scan_read_dylib (abfd, command) != 0)
1524         return -1;
1525       break;
1526     case BFD_MACH_O_LC_PREBOUND_DYLIB:
1527       if (bfd_mach_o_scan_read_prebound_dylib (abfd, command) != 0)
1528         return -1;
1529       break;
1530     case BFD_MACH_O_LC_LOADFVMLIB:
1531     case BFD_MACH_O_LC_IDFVMLIB:
1532     case BFD_MACH_O_LC_IDENT:
1533     case BFD_MACH_O_LC_FVMFILE:
1534     case BFD_MACH_O_LC_PREPAGE:
1535     case BFD_MACH_O_LC_ROUTINES:
1536     case BFD_MACH_O_LC_SUB_FRAMEWORK:
1537       break;
1538     case BFD_MACH_O_LC_DYSYMTAB:
1539       if (bfd_mach_o_scan_read_dysymtab (abfd, command) != 0)
1540         return -1;
1541       break;
1542     case BFD_MACH_O_LC_SUB_UMBRELLA:
1543     case BFD_MACH_O_LC_SUB_CLIENT:
1544     case BFD_MACH_O_LC_SUB_LIBRARY:
1545     case BFD_MACH_O_LC_TWOLEVEL_HINTS:
1546     case BFD_MACH_O_LC_PREBIND_CKSUM:
1547       break;
1548     default:
1549       fprintf (stderr, "unable to read unknown load command 0x%lx\n",
1550                (unsigned long) command->type);
1551       break;
1552     }
1553
1554   return 0;
1555 }
1556
1557 static void
1558 bfd_mach_o_flatten_sections (abfd)
1559      bfd *abfd;
1560 {
1561   bfd_mach_o_data_struct *mdata = abfd->tdata.mach_o_data;
1562   long csect = 0;
1563   unsigned long i, j;
1564
1565   mdata->nsects = 0;
1566
1567   for (i = 0; i < mdata->header.ncmds; i++)
1568     {
1569       if (mdata->commands[i].type == BFD_MACH_O_LC_SEGMENT)
1570         {
1571           bfd_mach_o_segment_command *seg;
1572
1573           seg = &mdata->commands[i].command.segment;
1574           mdata->nsects += seg->nsects;
1575         }
1576     }
1577
1578   mdata->sections = bfd_alloc (abfd,
1579                                mdata->nsects * sizeof (bfd_mach_o_section *));
1580   csect = 0;
1581
1582   for (i = 0; i < mdata->header.ncmds; i++)
1583     {
1584       if (mdata->commands[i].type == BFD_MACH_O_LC_SEGMENT)
1585         {
1586           bfd_mach_o_segment_command *seg;
1587
1588           seg = &mdata->commands[i].command.segment;
1589           BFD_ASSERT (csect + seg->nsects <= mdata->nsects);
1590
1591           for (j = 0; j < seg->nsects; j++)
1592             mdata->sections[csect++] = &seg->sections[j];
1593         }
1594     }
1595 }
1596
1597 int
1598 bfd_mach_o_scan_start_address (abfd)
1599      bfd *abfd;
1600 {
1601   bfd_mach_o_data_struct *mdata = abfd->tdata.mach_o_data;
1602   bfd_mach_o_thread_command *cmd = NULL;
1603   unsigned long i;
1604
1605   for (i = 0; i < mdata->header.ncmds; i++)
1606     {
1607       if ((mdata->commands[i].type == BFD_MACH_O_LC_THREAD) ||
1608           (mdata->commands[i].type == BFD_MACH_O_LC_UNIXTHREAD))
1609         {
1610           if (cmd == NULL)
1611             cmd = &mdata->commands[i].command.thread;
1612           else
1613             return 0;
1614         }
1615     }
1616
1617   if (cmd == NULL)
1618     return 0;
1619
1620   for (i = 0; i < cmd->nflavours; i++)
1621     {
1622       if ((mdata->header.cputype == BFD_MACH_O_CPU_TYPE_I386)
1623           && (cmd->flavours[i].flavour
1624               == (unsigned long) BFD_MACH_O_i386_THREAD_STATE))
1625         {
1626           unsigned char buf[4];
1627
1628           bfd_seek (abfd, cmd->flavours[i].offset + 40, SEEK_SET);
1629
1630           if (bfd_bread (buf, 4, abfd) != 4)
1631             return -1;
1632
1633           abfd->start_address = bfd_h_get_32 (abfd, buf);
1634         }
1635       else if ((mdata->header.cputype == BFD_MACH_O_CPU_TYPE_POWERPC)
1636                && (cmd->flavours[i].flavour == BFD_MACH_O_PPC_THREAD_STATE))
1637         {
1638           unsigned char buf[4];
1639
1640           bfd_seek (abfd, cmd->flavours[i].offset + 0, SEEK_SET);
1641
1642           if (bfd_bread (buf, 4, abfd) != 4)
1643             return -1;
1644
1645           abfd->start_address = bfd_h_get_32 (abfd, buf);
1646         }
1647     }
1648
1649   return 0;
1650 }
1651
1652 int
1653 bfd_mach_o_scan (abfd, header, mdata)
1654      bfd *abfd;
1655      bfd_mach_o_header *header;
1656      bfd_mach_o_data_struct *mdata;
1657 {
1658   unsigned int i;
1659   enum bfd_architecture cputype;
1660   unsigned long cpusubtype;
1661
1662   mdata->header = *header;
1663   mdata->symbols = NULL;
1664
1665   abfd->flags = (abfd->xvec->object_flags
1666                  | (abfd->flags & (BFD_IN_MEMORY | BFD_IO_FUNCS)));
1667   abfd->tdata.mach_o_data = mdata;
1668
1669   bfd_mach_o_convert_architecture (header->cputype, header->cpusubtype,
1670                                    &cputype, &cpusubtype);
1671   if (cputype == bfd_arch_unknown)
1672     {
1673       fprintf (stderr, "bfd_mach_o_scan: unknown architecture 0x%lx/0x%lx\n",
1674                header->cputype, header->cpusubtype);
1675       return -1;
1676     }
1677
1678   bfd_set_arch_mach (abfd, cputype, cpusubtype);
1679
1680   if (header->ncmds != 0)
1681     {
1682       mdata->commands =
1683         ((bfd_mach_o_load_command *)
1684          bfd_alloc (abfd, header->ncmds * sizeof (bfd_mach_o_load_command)));
1685       if (mdata->commands == NULL)
1686         return -1;
1687
1688       for (i = 0; i < header->ncmds; i++)
1689         {
1690           bfd_mach_o_load_command *cur = &mdata->commands[i];
1691
1692           if (i == 0)
1693             cur->offset = 28;
1694           else
1695             {
1696               bfd_mach_o_load_command *prev = &mdata->commands[i - 1];
1697               cur->offset = prev->offset + prev->len;
1698             }
1699
1700           if (bfd_mach_o_scan_read_command (abfd, cur) < 0)
1701             return -1;
1702         }
1703     }
1704
1705   if (bfd_mach_o_scan_start_address (abfd) < 0)
1706     {
1707 #if 0
1708       fprintf (stderr, "bfd_mach_o_scan: unable to scan start address: %s\n",
1709                bfd_errmsg (bfd_get_error ()));
1710       abfd->tdata.mach_o_data = NULL;
1711       return -1;
1712 #endif
1713     }
1714
1715   bfd_mach_o_flatten_sections (abfd);
1716
1717   return 0;
1718 }
1719
1720 bfd_boolean
1721 bfd_mach_o_mkobject (abfd)
1722      bfd *abfd;
1723 {
1724   bfd_mach_o_data_struct *mdata = NULL;
1725
1726   mdata = ((bfd_mach_o_data_struct *)
1727            bfd_alloc (abfd, sizeof (bfd_mach_o_data_struct)));
1728   if (mdata == NULL)
1729     return FALSE;
1730   abfd->tdata.mach_o_data = mdata;
1731
1732   mdata->header.magic = 0;
1733   mdata->header.cputype = 0;
1734   mdata->header.cpusubtype = 0;
1735   mdata->header.filetype = 0;
1736   mdata->header.ncmds = 0;
1737   mdata->header.sizeofcmds = 0;
1738   mdata->header.flags = 0;
1739   mdata->header.byteorder = BFD_ENDIAN_UNKNOWN;
1740   mdata->commands = NULL;
1741   mdata->nsymbols = 0;
1742   mdata->symbols = NULL;
1743   mdata->nsects = 0;
1744   mdata->sections = NULL;
1745   mdata->ibfd = NULL;
1746
1747   return TRUE;
1748 }
1749
1750 const bfd_target *
1751 bfd_mach_o_object_p (abfd)
1752      bfd *abfd;
1753 {
1754   struct bfd_preserve preserve;
1755   bfd_mach_o_header header;
1756
1757   preserve.marker = NULL;
1758   if (bfd_mach_o_read_header (abfd, &header) != 0)
1759     goto wrong;
1760
1761   if (! (header.byteorder == BFD_ENDIAN_BIG
1762          || header.byteorder == BFD_ENDIAN_LITTLE))
1763     {
1764       fprintf (stderr, "unknown header byte-order value 0x%lx\n",
1765                (long) header.byteorder);
1766       goto wrong;
1767     }
1768
1769   if (! ((header.byteorder == BFD_ENDIAN_BIG
1770           && abfd->xvec->byteorder == BFD_ENDIAN_BIG
1771           && abfd->xvec->header_byteorder == BFD_ENDIAN_BIG)
1772          || (header.byteorder == BFD_ENDIAN_LITTLE
1773              && abfd->xvec->byteorder == BFD_ENDIAN_LITTLE
1774              && abfd->xvec->header_byteorder == BFD_ENDIAN_LITTLE)))
1775     goto wrong;
1776
1777   preserve.marker = bfd_zalloc (abfd, sizeof (bfd_mach_o_data_struct));
1778   if (preserve.marker == NULL
1779       || !bfd_preserve_save (abfd, &preserve))
1780     goto fail;
1781
1782   if (bfd_mach_o_scan (abfd, &header,
1783                        (bfd_mach_o_data_struct *) preserve.marker) != 0)
1784     goto wrong;
1785
1786   bfd_preserve_finish (abfd, &preserve);
1787   return abfd->xvec;
1788
1789  wrong:
1790   bfd_set_error (bfd_error_wrong_format);
1791
1792  fail:
1793   if (preserve.marker != NULL)
1794     bfd_preserve_restore (abfd, &preserve);
1795   return NULL;
1796 }
1797
1798 const bfd_target *
1799 bfd_mach_o_core_p (abfd)
1800      bfd *abfd;
1801 {
1802   struct bfd_preserve preserve;
1803   bfd_mach_o_header header;
1804
1805   preserve.marker = NULL;
1806   if (bfd_mach_o_read_header (abfd, &header) != 0)
1807     goto wrong;
1808
1809   if (! (header.byteorder == BFD_ENDIAN_BIG
1810          || header.byteorder == BFD_ENDIAN_LITTLE))
1811     {
1812       fprintf (stderr, "unknown header byte-order value 0x%lx\n",
1813                (long) header.byteorder);
1814       abort ();
1815     }
1816
1817   if (! ((header.byteorder == BFD_ENDIAN_BIG
1818           && abfd->xvec->byteorder == BFD_ENDIAN_BIG
1819           && abfd->xvec->header_byteorder == BFD_ENDIAN_BIG)
1820          || (header.byteorder == BFD_ENDIAN_LITTLE
1821              && abfd->xvec->byteorder == BFD_ENDIAN_LITTLE
1822              && abfd->xvec->header_byteorder == BFD_ENDIAN_LITTLE)))
1823     goto wrong;
1824
1825   if (header.filetype != BFD_MACH_O_MH_CORE)
1826     goto wrong;
1827
1828   preserve.marker = bfd_zalloc (abfd, sizeof (bfd_mach_o_data_struct));
1829   if (preserve.marker == NULL
1830       || !bfd_preserve_save (abfd, &preserve))
1831     goto fail;
1832
1833   if (bfd_mach_o_scan (abfd, &header,
1834                        (bfd_mach_o_data_struct *) preserve.marker) != 0)
1835     goto wrong;
1836
1837   bfd_preserve_finish (abfd, &preserve);
1838   return abfd->xvec;
1839
1840  wrong:
1841   bfd_set_error (bfd_error_wrong_format);
1842
1843  fail:
1844   if (preserve.marker != NULL)
1845     bfd_preserve_restore (abfd, &preserve);
1846   return NULL;
1847 }
1848
1849 typedef struct mach_o_fat_archentry
1850 {
1851   unsigned long cputype;
1852   unsigned long cpusubtype;
1853   unsigned long offset;
1854   unsigned long size;
1855   unsigned long align;
1856   bfd *abfd;
1857 } mach_o_fat_archentry;
1858
1859 typedef struct mach_o_fat_data_struct
1860 {
1861   unsigned long magic;
1862   unsigned long nfat_arch;
1863   mach_o_fat_archentry *archentries;
1864 } mach_o_fat_data_struct;
1865
1866 const bfd_target *
1867 bfd_mach_o_archive_p (abfd)
1868      bfd *abfd;
1869 {
1870   mach_o_fat_data_struct *adata = NULL;
1871   unsigned char buf[20];
1872   unsigned long i;
1873
1874   bfd_seek (abfd, 0, SEEK_SET);
1875   if (bfd_bread ((PTR) buf, 8, abfd) != 8)
1876     goto error;
1877
1878   adata = (mach_o_fat_data_struct *)
1879     bfd_alloc (abfd, sizeof (mach_o_fat_data_struct));
1880   if (adata == NULL)
1881     goto error;
1882
1883   adata->magic = bfd_getb32 (buf);
1884   adata->nfat_arch = bfd_getb32 (buf + 4);
1885   if (adata->magic != 0xcafebabe)
1886     goto error;
1887
1888   adata->archentries = (mach_o_fat_archentry *)
1889     bfd_alloc (abfd, adata->nfat_arch * sizeof (mach_o_fat_archentry));
1890   if (adata->archentries == NULL)
1891     goto error;
1892
1893   for (i = 0; i < adata->nfat_arch; i++)
1894     {
1895       bfd_seek (abfd, 8 + 20 * i, SEEK_SET);
1896
1897       if (bfd_bread ((PTR) buf, 20, abfd) != 20)
1898         goto error;
1899       adata->archentries[i].cputype = bfd_getb32 (buf);
1900       adata->archentries[i].cpusubtype = bfd_getb32 (buf + 4);
1901       adata->archentries[i].offset = bfd_getb32 (buf + 8);
1902       adata->archentries[i].size = bfd_getb32 (buf + 12);
1903       adata->archentries[i].align = bfd_getb32 (buf + 16);
1904       adata->archentries[i].abfd = NULL;
1905     }
1906
1907   abfd->tdata.mach_o_fat_data = adata;
1908   return abfd->xvec;
1909
1910  error:
1911   if (adata != NULL)
1912     bfd_release (abfd, adata);
1913   bfd_set_error (bfd_error_wrong_format);
1914   return NULL;
1915 }
1916
1917 bfd *
1918 bfd_mach_o_openr_next_archived_file (archive, prev)
1919   bfd *archive;
1920   bfd *prev;
1921 {
1922   mach_o_fat_data_struct *adata;
1923   mach_o_fat_archentry *entry = NULL;
1924   unsigned long i;
1925
1926   adata = (mach_o_fat_data_struct *) archive->tdata.mach_o_fat_data;
1927   BFD_ASSERT (adata != NULL);
1928
1929   /* Find index of previous entry.  */
1930   if (prev == NULL)
1931     i = 0;      /* Start at first one.  */
1932   else
1933     {
1934       for (i = 0; i < adata->nfat_arch; i++)
1935         {
1936           if (adata->archentries[i].abfd == prev)
1937             break;
1938         }
1939
1940       if (i == adata->nfat_arch)
1941         {
1942           /* Not found.  */
1943           bfd_set_error (bfd_error_bad_value);
1944           return NULL;
1945         }
1946     i++;        /* Get next entry.  */
1947   }
1948
1949   if (i >= adata->nfat_arch)
1950     {
1951       bfd_set_error (bfd_error_no_more_archived_files);
1952       return NULL;
1953     }
1954
1955   entry = &adata->archentries[i];
1956   if (entry->abfd == NULL)
1957     {
1958       bfd *nbfd = _bfd_new_bfd_contained_in (archive);
1959       char *s = NULL;
1960
1961       if (nbfd == NULL)
1962         return NULL;
1963
1964       nbfd->origin = entry->offset;
1965       s = bfd_malloc (strlen (archive->filename) + 1);
1966       if (s == NULL)
1967         return NULL;
1968       strcpy (s, archive->filename);
1969       nbfd->filename = s;
1970       nbfd->iostream = NULL;
1971       entry->abfd = nbfd;
1972     }
1973
1974   return entry->abfd;
1975 }
1976
1977 int
1978 bfd_mach_o_lookup_section (abfd, section, mcommand, msection)
1979      bfd *abfd;
1980      asection *section;
1981      bfd_mach_o_load_command **mcommand;
1982      bfd_mach_o_section **msection;
1983 {
1984   struct mach_o_data_struct *md = abfd->tdata.mach_o_data;
1985   unsigned int i, j, num;
1986
1987   bfd_mach_o_load_command *ncmd = NULL;
1988   bfd_mach_o_section *nsect = NULL;
1989
1990   BFD_ASSERT (mcommand != NULL);
1991   BFD_ASSERT (msection != NULL);
1992
1993   num = 0;
1994   for (i = 0; i < md->header.ncmds; i++)
1995     {
1996       struct bfd_mach_o_load_command *cmd = &md->commands[i];
1997       struct bfd_mach_o_segment_command *seg = NULL;
1998
1999       if (cmd->type != BFD_MACH_O_LC_SEGMENT)
2000         continue;
2001       seg = &cmd->command.segment;
2002
2003       if (seg->segment == section)
2004         {
2005           if (num == 0)
2006             ncmd = cmd;
2007           num++;
2008         }
2009
2010       for (j = 0; j < seg->nsects; j++)
2011         {
2012           struct bfd_mach_o_section *sect = &seg->sections[j];
2013
2014           if (sect->bfdsection == section)
2015             {
2016               if (num == 0)
2017                 nsect = sect;
2018               num++;
2019             }
2020         }
2021     }
2022
2023   *mcommand = ncmd;
2024   *msection = nsect;
2025   return num;
2026 }
2027
2028 int
2029 bfd_mach_o_lookup_command (abfd, type, mcommand)
2030      bfd *abfd;
2031      bfd_mach_o_load_command_type type;
2032      bfd_mach_o_load_command **mcommand;
2033 {
2034   struct mach_o_data_struct *md = NULL;
2035   bfd_mach_o_load_command *ncmd = NULL;
2036   unsigned int i, num;
2037
2038   md = abfd->tdata.mach_o_data;
2039
2040   BFD_ASSERT (md != NULL);
2041   BFD_ASSERT (mcommand != NULL);
2042
2043   num = 0;
2044   for (i = 0; i < md->header.ncmds; i++)
2045     {
2046       struct bfd_mach_o_load_command *cmd = &md->commands[i];
2047
2048       if (cmd->type != type)
2049         continue;
2050
2051       if (num == 0)
2052         ncmd = cmd;
2053       num++;
2054     }
2055
2056   *mcommand = ncmd;
2057   return num;
2058 }
2059
2060 unsigned long
2061 bfd_mach_o_stack_addr (type)
2062      enum bfd_mach_o_cpu_type type;
2063 {
2064   switch (type)
2065     {
2066     case BFD_MACH_O_CPU_TYPE_MC680x0:
2067       return 0x04000000;
2068     case BFD_MACH_O_CPU_TYPE_MC88000:
2069       return 0xffffe000;
2070     case BFD_MACH_O_CPU_TYPE_POWERPC:
2071       return 0xc0000000;
2072     case BFD_MACH_O_CPU_TYPE_I386:
2073       return 0xc0000000;
2074     case BFD_MACH_O_CPU_TYPE_SPARC:
2075       return 0xf0000000;
2076     case BFD_MACH_O_CPU_TYPE_I860:
2077       return 0;
2078     case BFD_MACH_O_CPU_TYPE_HPPA:
2079       return 0xc0000000 - 0x04000000;
2080     default:
2081       return 0;
2082     }
2083 }
2084
2085 int
2086 bfd_mach_o_core_fetch_environment (abfd, rbuf, rlen)
2087      bfd *abfd;
2088      unsigned char **rbuf;
2089      unsigned int *rlen;
2090 {
2091   bfd_mach_o_data_struct *mdata = abfd->tdata.mach_o_data;
2092   unsigned long stackaddr = bfd_mach_o_stack_addr (mdata->header.cputype);
2093   unsigned int i = 0;
2094
2095   for (i = 0; i < mdata->header.ncmds; i++)
2096     {
2097       bfd_mach_o_load_command *cur = &mdata->commands[i];
2098       bfd_mach_o_segment_command *seg = NULL;
2099
2100       if (cur->type != BFD_MACH_O_LC_SEGMENT)
2101         continue;
2102
2103       seg = &cur->command.segment;
2104
2105       if ((seg->vmaddr + seg->vmsize) == stackaddr)
2106         {
2107           unsigned long start = seg->fileoff;
2108           unsigned long end = seg->fileoff + seg->filesize;
2109           unsigned char *buf = bfd_malloc (1024);
2110           unsigned long size = 1024;
2111
2112           for (;;)
2113             {
2114               bfd_size_type nread = 0;
2115               unsigned long offset;
2116               int found_nonnull = 0;
2117
2118               if (size > (end - start))
2119                 size = (end - start);
2120
2121               buf = bfd_realloc (buf, size);
2122
2123               bfd_seek (abfd, end - size, SEEK_SET);
2124               nread = bfd_bread (buf, size, abfd);
2125
2126               if (nread != size)
2127                 return -1;
2128
2129               for (offset = 4; offset <= size; offset += 4)
2130                 {
2131                   unsigned long val;
2132
2133                   val = *((unsigned long *) (buf + size - offset));
2134                   if (! found_nonnull)
2135                     {
2136                       if (val != 0)
2137                         found_nonnull = 1;
2138                     }
2139                   else if (val == 0x0)
2140                     {
2141                       unsigned long bottom;
2142                       unsigned long top;
2143
2144                       bottom = seg->fileoff + seg->filesize - offset;
2145                       top = seg->fileoff + seg->filesize - 4;
2146                       *rbuf = bfd_malloc (top - bottom);
2147                       *rlen = top - bottom;
2148
2149                       memcpy (*rbuf, buf + size - *rlen, *rlen);
2150                       return 0;
2151                     }
2152                 }
2153
2154               if (size == (end - start))
2155                 break;
2156
2157               size *= 2;
2158             }
2159         }
2160     }
2161
2162   return -1;
2163 }
2164
2165 char *
2166 bfd_mach_o_core_file_failing_command (abfd)
2167      bfd *abfd;
2168 {
2169   unsigned char *buf = NULL;
2170   unsigned int len = 0;
2171   int ret = -1;
2172
2173   ret = bfd_mach_o_core_fetch_environment (abfd, &buf, &len);
2174   if (ret < 0)
2175     return NULL;
2176
2177   return buf;
2178 }
2179
2180 int
2181 bfd_mach_o_core_file_failing_signal (abfd)
2182      bfd *abfd ATTRIBUTE_UNUSED;
2183 {
2184   return 0;
2185 }
2186
2187 bfd_boolean
2188 bfd_mach_o_core_file_matches_executable_p (core_bfd, exec_bfd)
2189      bfd *core_bfd ATTRIBUTE_UNUSED;
2190      bfd *exec_bfd ATTRIBUTE_UNUSED;
2191 {
2192   return TRUE;
2193 }
2194
2195 #define TARGET_NAME mach_o_be_vec
2196 #define TARGET_STRING "mach-o-be"
2197 #define TARGET_BIG_ENDIAN 1
2198 #define TARGET_ARCHIVE 0
2199
2200 #include "mach-o-target.c"
2201
2202 #undef TARGET_NAME
2203 #undef TARGET_STRING
2204 #undef TARGET_BIG_ENDIAN
2205 #undef TARGET_ARCHIVE
2206
2207 #define TARGET_NAME mach_o_le_vec
2208 #define TARGET_STRING "mach-o-le"
2209 #define TARGET_BIG_ENDIAN 0
2210 #define TARGET_ARCHIVE 0
2211
2212 #include "mach-o-target.c"
2213
2214 #undef TARGET_NAME
2215 #undef TARGET_STRING
2216 #undef TARGET_BIG_ENDIAN
2217 #undef TARGET_ARCHIVE
2218
2219 #define TARGET_NAME mach_o_fat_vec
2220 #define TARGET_STRING "mach-o-fat"
2221 #define TARGET_BIG_ENDIAN 1
2222 #define TARGET_ARCHIVE 1
2223
2224 #include "mach-o-target.c"
2225
2226 #undef TARGET_NAME
2227 #undef TARGET_STRING
2228 #undef TARGET_BIG_ENDIAN
2229 #undef TARGET_ARCHIVE