OSDN Git Service

2011-01-05 Michael Snyder <msnyder@vmware.com>
[pf3gnuchains/sourceware.git] / gdb / machoread.c
1 /* Darwin support for GDB, the GNU debugger.
2    Copyright (C) 2008, 2009, 2010, 2011 Free Software Foundation, Inc.
3
4    Contributed by AdaCore.
5
6    This file is part of GDB.
7
8    This program is free software; you can redistribute it and/or modify
9    it under the terms of the GNU General Public License as published by
10    the Free Software Foundation; either version 3 of the License, or
11    (at your option) any later version.
12
13    This program is distributed in the hope that it will be useful,
14    but WITHOUT ANY WARRANTY; without even the implied warranty of
15    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16    GNU General Public License for more details.
17
18    You should have received a copy of the GNU General Public License
19    along with this program.  If not, see <http://www.gnu.org/licenses/>.
20  */
21
22 #include "defs.h"
23 #include "symtab.h"
24 #include "gdbtypes.h"
25 #include "bfd.h"
26 #include "symfile.h"
27 #include "objfiles.h"
28 #include "buildsym.h"
29 #include "gdbcmd.h"
30 #include "gdbcore.h"
31 #include "mach-o.h"
32 #include "gdb_assert.h"
33 #include "aout/stab_gnu.h"
34 #include "vec.h"
35 #include "psympriv.h"
36
37 #include <string.h>
38
39 /* If non-zero displays debugging message.  */
40 static int mach_o_debug_level = 0;
41
42 /* Dwarf debugging information are never in the final executable.  They stay
43    in object files and the executable contains the list of object files read
44    during the link.
45    Each time an oso (other source) is found in the executable, the reader
46    creates such a structure.  They are read after the processing of the
47    executable.
48 */
49 typedef struct oso_el
50 {
51   /* Object file name.  */
52   const char *name;
53
54   /* Associated time stamp.  */
55   unsigned long mtime;
56
57   /* Number of sections.  This is the length of SYMBOLS and OFFSETS array.  */
58   int num_sections;
59
60   /* Each seaction of the object file is represented by a symbol and its
61      offset.  If the offset is 0, we assume that the symbol is at offset 0
62      in the OSO object file and a symbol lookup in the main file is
63      required to get the offset.  */
64   asymbol **symbols;
65   bfd_vma *offsets;
66 }
67 oso_el;
68
69 /* Vector of object files to be read after the executable.  This is one
70    global variable but it's life-time is the one of macho_symfile_read.  */
71 DEF_VEC_O (oso_el);
72 static VEC (oso_el) *oso_vector;
73
74 struct macho_oso_data
75 {
76   /* Per objfile symbol table.  This is used to apply relocation to sections
77      It is loaded only once, then relocated, and free after sections are
78      relocated.  */
79   asymbol **symbol_table;
80
81   /* The offsets for this objfile.  Used to relocate the symbol_table.  */
82   struct oso_el *oso;
83
84   struct objfile *main_objfile;
85 };
86
87 /* Data for OSO being processed.  */
88
89 static struct macho_oso_data current_oso;
90
91 static void
92 macho_new_init (struct objfile *objfile)
93 {
94 }
95
96 static void
97 macho_symfile_init (struct objfile *objfile)
98 {
99   objfile->flags |= OBJF_REORDERED;
100   init_entry_point_info (objfile);
101 }
102
103 /*  Add a new OSO to the vector of OSO to load.  */
104
105 static void
106 macho_register_oso (const asymbol *oso_sym, int nbr_sections,
107                     asymbol **symbols, bfd_vma *offsets)
108 {
109   oso_el el;
110
111   el.name = oso_sym->name;
112   el.mtime = oso_sym->value;
113   el.num_sections = nbr_sections;
114   el.symbols = symbols;
115   el.offsets = offsets;
116   VEC_safe_push (oso_el, oso_vector, &el);
117 }
118
119 /* Build the minimal symbol table from SYMBOL_TABLE of length
120    NUMBER_OF_SYMBOLS for OBJFILE.
121    Read OSO files at the end.  */
122
123 static void
124 macho_symtab_read (struct objfile *objfile,
125                    long number_of_symbols, asymbol **symbol_table)
126 {
127   struct gdbarch *gdbarch = get_objfile_arch (objfile);
128   long storage_needed;
129   long i, j;
130   CORE_ADDR offset;
131   enum minimal_symbol_type ms_type;
132   unsigned int nbr_sections = bfd_count_sections (objfile->obfd);
133   asymbol **first_symbol = NULL;
134   bfd_vma *first_offset = NULL;
135   const asymbol *oso_file = NULL;
136
137   for (i = 0; i < number_of_symbols; i++)
138     {
139       asymbol *sym = symbol_table[i];
140       bfd_mach_o_asymbol *mach_o_sym = (bfd_mach_o_asymbol *)sym;
141
142       offset = ANOFFSET (objfile->section_offsets, sym->section->index);
143
144       if (sym->flags & BSF_DEBUGGING)
145         {
146           bfd_vma addr;
147
148           /* Debugging symbols are used to collect OSO file names as well
149              as section offsets.  */
150
151           switch (mach_o_sym->n_type)
152             {
153             case N_SO:
154               /* An empty SO entry terminates a chunk for an OSO file.  */
155               if ((sym->name == NULL || sym->name[0] == 0) && oso_file != NULL)
156                 {
157                   macho_register_oso (oso_file, nbr_sections,
158                                       first_symbol, first_offset);
159                   first_symbol = NULL;
160                   first_offset = NULL;
161                   oso_file = NULL;
162                 }
163               break;
164             case N_FUN:
165             case N_STSYM:
166               if (sym->name == NULL || sym->name[0] == '\0')
167                 break;
168               /* Fall through.  */
169             case N_BNSYM:
170               gdb_assert (oso_file != NULL);
171               addr = sym->value 
172                 + bfd_get_section_vma (sym->section->bfd, sym->section);
173               if (addr != 0
174                   && first_symbol[sym->section->index] == NULL)
175                 {
176                   /* These STAB entries can directly relocate a section.  */
177                   first_symbol[sym->section->index] = sym;
178                   first_offset[sym->section->index] = addr + offset;
179                 }
180               break;
181             case N_GSYM:
182               gdb_assert (oso_file != NULL);
183               if (first_symbol[sym->section->index] == NULL)
184                 {
185                   /* This STAB entry needs a symbol look-up to relocate
186                      the section.  */
187                   first_symbol[sym->section->index] = sym;
188                   first_offset[sym->section->index] = 0;
189                 }
190               break;
191             case N_OSO:
192               /* New OSO file.  */
193               gdb_assert (oso_file == NULL);
194               first_symbol = (asymbol **)xmalloc (nbr_sections
195                                                   * sizeof (asymbol *));
196               first_offset = (bfd_vma *)xmalloc (nbr_sections
197                                                  * sizeof (bfd_vma));
198               for (j = 0; j < nbr_sections; j++)
199                 first_symbol[j] = NULL;
200               oso_file = sym;
201               break;
202             }
203           continue;
204         }
205
206       if (sym->name == NULL || *sym->name == '\0')
207         {
208           /* Skip names that don't exist (shouldn't happen), or names
209              that are null strings (may happen). */
210           continue;
211         }
212
213       if (sym->flags & (BSF_GLOBAL | BSF_LOCAL | BSF_WEAK))
214         {
215           struct minimal_symbol *msym;
216           CORE_ADDR symaddr;
217
218           /* Bfd symbols are section relative. */
219           symaddr = sym->value + sym->section->vma;
220
221           /* Select global/local/weak symbols.  Note that bfd puts abs
222              symbols in their own section, so all symbols we are
223              interested in will have a section. */
224           /* Relocate all non-absolute and non-TLS symbols by the
225              section offset.  */
226           if (sym->section != &bfd_abs_section
227               && !(sym->section->flags & SEC_THREAD_LOCAL))
228             symaddr += offset;
229
230           if (sym->section == &bfd_abs_section)
231             ms_type = mst_abs;
232           else if (sym->section->flags & SEC_CODE)
233             {
234               if (sym->flags & (BSF_GLOBAL | BSF_WEAK))
235                 ms_type = mst_text;
236               else
237                 ms_type = mst_file_text;
238             }
239           else if (sym->section->flags & SEC_ALLOC)
240             {
241               if (sym->flags & (BSF_GLOBAL | BSF_WEAK))
242                 {
243                   if (sym->section->flags & SEC_LOAD)
244                     ms_type = mst_data;
245                   else
246                     ms_type = mst_bss;
247                 }
248               else if (sym->flags & BSF_LOCAL)
249                 {
250                   /* Not a special stabs-in-elf symbol, do regular
251                      symbol processing.  */
252                   if (sym->section->flags & SEC_LOAD)
253                     ms_type = mst_file_data;
254                   else
255                     ms_type = mst_file_bss;
256                 }
257               else
258                 ms_type = mst_unknown;
259             }
260           else
261             continue;   /* Skip this symbol. */
262
263           gdb_assert (sym->section->index < nbr_sections);
264           if (oso_file != NULL
265               && first_symbol[sym->section->index] == NULL)
266             {
267               /* Standard symbols can directly relocate sections.  */
268               first_symbol[sym->section->index] = sym;
269               first_offset[sym->section->index] = symaddr;
270             }
271
272           msym = prim_record_minimal_symbol_and_info
273             (sym->name, symaddr, ms_type, sym->section->index,
274              sym->section, objfile);
275         }
276     }
277
278   /* Just in case there is no trailing SO entry.  */
279   if (oso_file != NULL)
280     macho_register_oso (oso_file, nbr_sections, first_symbol, first_offset);
281 }
282
283 /* If NAME describes an archive member (ie: ARCHIVE '(' MEMBER ')'),
284    returns the length of the archive name.
285    Returns -1 otherwise.  */
286
287 static int
288 get_archive_prefix_len (const char *name)
289 {
290   char *lparen;
291   int name_len = strlen (name);
292
293   if (name_len == 0 || name[name_len - 1] != ')')
294     return -1;
295   
296   lparen = strrchr (name, '(');
297   if (lparen == NULL || lparen == name)
298     return -1;
299   return lparen - name;
300 }
301
302 static int
303 oso_el_compare_name (const void *vl, const void *vr)
304 {
305   const oso_el *l = (const oso_el *)vl;
306   const oso_el *r = (const oso_el *)vr;
307
308   return strcmp (l->name, r->name);
309 }
310
311 /* Add an oso file as a symbol file.  */
312
313 static void
314 macho_add_oso_symfile (oso_el *oso, bfd *abfd,
315                        struct objfile *main_objfile, int symfile_flags)
316 {
317   struct objfile *objfile;
318   int i;
319   char leading_char;
320
321   if (mach_o_debug_level > 0)
322     printf_unfiltered (_("Loading symbols from oso: %s\n"), oso->name);
323
324   if (!bfd_check_format (abfd, bfd_object))
325     {
326       warning (_("`%s': can't read symbols: %s."), oso->name,
327                bfd_errmsg (bfd_get_error ()));
328       bfd_close (abfd);
329       return;
330     }
331
332   bfd_set_cacheable (abfd, 1);
333
334   /* Relocate sections.  */
335
336   leading_char = bfd_get_symbol_leading_char (main_objfile->obfd);
337
338   for (i = 0; i < oso->num_sections; i++)
339     {
340       asection *sect;
341       const char *sectname;
342       bfd_vma vma;
343
344       /* Empty slot.  */
345       if (oso->symbols[i] == NULL)
346         continue;
347
348       if (oso->offsets[i])
349         vma = oso->offsets[i];
350       else
351         {
352           struct minimal_symbol *msym;
353           const char *name = oso->symbols[i]->name;
354
355           if (name[0] == leading_char)
356             ++name;
357
358           if (mach_o_debug_level > 3)
359             printf_unfiltered (_("resolve sect %s with %s\n"),
360                                oso->symbols[i]->section->name,
361                                oso->symbols[i]->name);
362           msym = lookup_minimal_symbol (name, NULL, main_objfile);
363           if (msym == NULL)
364             {
365               warning (_("can't find symbol '%s' in minsymtab"), name);
366               continue;
367             }
368           else
369             vma = SYMBOL_VALUE_ADDRESS (msym);
370         }
371       sectname = (char *)oso->symbols[i]->section->name;
372
373       sect = bfd_get_section_by_name (abfd, sectname);
374       if (sect == NULL)
375         {
376           warning (_("can't find section '%s' in OSO file %s"),
377                    sectname, oso->name);
378           continue;
379         }
380       bfd_set_section_vma (abfd, sect, vma);
381
382       if (mach_o_debug_level > 1)
383         printf_unfiltered (_("  %s: %s\n"),
384                            core_addr_to_string (vma), sectname);
385     }
386
387   /* Make sure that the filename was malloc'ed.  The current filename comes
388      either from an OSO symbol name or from an archive name.  Memory for both
389      is not managed by gdb.  */
390   abfd->filename = xstrdup (abfd->filename);
391
392   gdb_assert (current_oso.symbol_table == NULL);
393   current_oso.main_objfile = main_objfile;
394
395   /* We need to clear SYMFILE_MAINLINE to avoid interractive question
396      from symfile.c:symbol_file_add_with_addrs_or_offsets.  */
397   objfile = symbol_file_add_from_bfd
398     (abfd, symfile_flags & ~(SYMFILE_MAINLINE | SYMFILE_VERBOSE), NULL,
399      main_objfile->flags & (OBJF_REORDERED | OBJF_SHARED
400                             | OBJF_READNOW | OBJF_USERLOADED));
401   add_separate_debug_objfile (objfile, main_objfile);
402
403   current_oso.main_objfile = NULL;
404   if (current_oso.symbol_table)
405     {
406       xfree (current_oso.symbol_table);
407       current_oso.symbol_table = NULL;
408     }
409 }
410
411 /* Read symbols from the vector of oso files.  */
412
413 static void
414 macho_symfile_read_all_oso (struct objfile *main_objfile, int symfile_flags)
415 {
416   int ix;
417   VEC (oso_el) *vec;
418   oso_el *oso;
419
420   vec = oso_vector;
421   oso_vector = NULL;
422   
423   /* Sort oso by name so that files from libraries are gathered.  */
424   qsort (VEC_address (oso_el, vec), VEC_length (oso_el, vec),
425          sizeof (oso_el), oso_el_compare_name);
426
427   for (ix = 0; VEC_iterate (oso_el, vec, ix, oso);)
428     {
429       int pfx_len;
430       
431       /* Check if this is a library name.  */
432       pfx_len = get_archive_prefix_len (oso->name);
433       if (pfx_len > 0)
434         {
435           bfd *archive_bfd;
436           bfd *member_bfd;
437           char *archive_name = XNEWVEC (char, pfx_len + 1);
438           int last_ix;
439           oso_el *oso2;
440           int ix2;
441
442           memcpy (archive_name, oso->name, pfx_len);
443           archive_name[pfx_len] = '\0';
444
445           /* Compute number of oso for this archive.  */
446           for (last_ix = ix;
447                VEC_iterate (oso_el, vec, last_ix, oso2); last_ix++)
448             {
449               if (strncmp (oso2->name, archive_name, pfx_len) != 0)
450                 break;
451             }
452           
453           /* Open the archive and check the format.  */
454           archive_bfd = bfd_openr (archive_name, gnutarget);
455           if (archive_bfd == NULL)
456             {
457               warning (_("Could not open OSO archive file \"%s\""),
458                        archive_name);
459               ix = last_ix;
460               continue;
461             }
462           if (!bfd_check_format (archive_bfd, bfd_archive))
463             {
464               warning (_("OSO archive file \"%s\" not an archive."),
465                        archive_name);
466               bfd_close (archive_bfd);
467               ix = last_ix;
468               continue;
469             }
470           member_bfd = bfd_openr_next_archived_file (archive_bfd, NULL);
471           
472           if (member_bfd == NULL)
473             {
474               warning (_("Could not read archive members out of "
475                          "OSO archive \"%s\""), archive_name);
476               bfd_close (archive_bfd);
477               ix = last_ix;
478               continue;
479             }
480
481           /* Load all oso in this library.  */
482           while (member_bfd != NULL)
483             {
484               bfd *prev;
485               const char *member_name = member_bfd->filename;
486               int member_len = strlen (member_name);
487
488               /* If this member is referenced, add it as a symfile.  */
489               for (ix2 = ix; ix2 < last_ix; ix2++)
490                 {
491                   oso2 = VEC_index (oso_el, vec, ix2);
492
493                   if (oso2->name
494                       && strlen (oso2->name) == pfx_len + member_len + 2
495                       && !memcmp (member_name, oso2->name + pfx_len + 1,
496                                   member_len))
497                     {
498                       macho_add_oso_symfile (oso2, member_bfd,
499                                              main_objfile, symfile_flags);
500                       oso2->name = NULL;
501                       break;
502                     }
503                 }
504
505               prev = member_bfd;
506               member_bfd = bfd_openr_next_archived_file
507                 (archive_bfd, member_bfd);
508
509               /* Free previous member if not referenced by an oso.  */
510               if (ix2 >= last_ix)
511                 bfd_close (prev);
512             }
513           for (ix2 = ix; ix2 < last_ix; ix2++)
514             {
515               oso_el *oso2 = VEC_index (oso_el, vec, ix2);
516
517               if (oso2->name != NULL)
518                 warning (_("Could not find specified archive member "
519                            "for OSO name \"%s\""), oso->name);
520             }
521           ix = last_ix;
522         }
523       else
524         {
525           bfd *abfd;
526
527           abfd = bfd_openr (oso->name, gnutarget);
528           if (!abfd)
529             warning (_("`%s': can't open to read symbols: %s."), oso->name,
530                      bfd_errmsg (bfd_get_error ()));
531           else
532             macho_add_oso_symfile (oso, abfd, main_objfile, symfile_flags);
533
534           ix++;
535         }
536     }
537
538   for (ix = 0; VEC_iterate (oso_el, vec, ix, oso); ix++)
539     {
540       xfree (oso->symbols);
541       xfree (oso->offsets);
542     }
543   VEC_free (oso_el, vec);
544 }
545
546 /* DSYM (debug symbols) files contain the debug info of an executable.
547    This is a separate file created by dsymutil(1) and is similar to debug
548    link feature on ELF.
549    DSYM files are located in a subdirectory.  Append DSYM_SUFFIX to the
550    executable name and the executable base name to get the DSYM file name.  */
551 #define DSYM_SUFFIX ".dSYM/Contents/Resources/DWARF/"
552
553 /* Check if a dsym file exists for OBJFILE.  If so, returns a bfd for it.
554    Return NULL if no valid dsym file is found.  */
555
556 static bfd *
557 macho_check_dsym (struct objfile *objfile)
558 {
559   size_t name_len = strlen (objfile->name);
560   size_t dsym_len = strlen (DSYM_SUFFIX);
561   const char *base_name = lbasename (objfile->name);
562   size_t base_len = strlen (base_name);
563   char *dsym_filename = alloca (name_len + dsym_len + base_len + 1);
564   bfd *dsym_bfd;
565   bfd_mach_o_load_command *main_uuid;
566   bfd_mach_o_load_command *dsym_uuid;
567
568   strcpy (dsym_filename, objfile->name);
569   strcpy (dsym_filename + name_len, DSYM_SUFFIX);
570   strcpy (dsym_filename + name_len + dsym_len, base_name);
571
572   if (access (dsym_filename, R_OK) != 0)
573     return NULL;
574
575   if (bfd_mach_o_lookup_command (objfile->obfd,
576                                  BFD_MACH_O_LC_UUID, &main_uuid) == 0)
577     {
578       warning (_("can't find UUID in %s"), objfile->name);
579       return NULL;
580     }
581   dsym_filename = xstrdup (dsym_filename);
582   dsym_bfd = bfd_openr (dsym_filename, gnutarget);
583   if (dsym_bfd == NULL)
584     {
585       warning (_("can't open dsym file %s"), dsym_filename);
586       xfree (dsym_filename);
587       return NULL;
588     }
589
590   if (!bfd_check_format (dsym_bfd, bfd_object))
591     {
592       bfd_close (dsym_bfd);
593       warning (_("bad dsym file format: %s"), bfd_errmsg (bfd_get_error ()));
594       xfree (dsym_filename);
595       return NULL;
596     }
597
598   if (bfd_mach_o_lookup_command (dsym_bfd,
599                                  BFD_MACH_O_LC_UUID, &dsym_uuid) == 0)
600     {
601       warning (_("can't find UUID in %s"), dsym_filename);
602       bfd_close (dsym_bfd);
603       xfree (dsym_filename);
604       return NULL;
605     }
606   if (memcmp (dsym_uuid->command.uuid.uuid, main_uuid->command.uuid.uuid,
607               sizeof (main_uuid->command.uuid.uuid)))
608     {
609       warning (_("dsym file UUID doesn't match the one in %s"), objfile->name);
610       bfd_close (dsym_bfd);
611       xfree (dsym_filename);
612       return NULL;
613     }
614   return dsym_bfd;
615 }
616
617 static void
618 macho_symfile_read (struct objfile *objfile, int symfile_flags)
619 {
620   bfd *abfd = objfile->obfd;
621   struct cleanup *back_to;
622   CORE_ADDR offset;
623   long storage_needed;
624   bfd *dsym_bfd;
625
626   init_minimal_symbol_collection ();
627   back_to = make_cleanup_discard_minimal_symbols ();
628
629   /* Get symbols from the symbol table only if the file is an executable.
630      The symbol table of object files is not relocated and is expected to
631      be in the executable.  */
632   if (bfd_get_file_flags (abfd) & (EXEC_P | DYNAMIC))
633     {
634       /* Process the normal symbol table first.  */
635       storage_needed = bfd_get_symtab_upper_bound (objfile->obfd);
636       if (storage_needed < 0)
637         error (_("Can't read symbols from %s: %s"),
638                bfd_get_filename (objfile->obfd),
639                bfd_errmsg (bfd_get_error ()));
640
641       if (storage_needed > 0)
642         {
643           asymbol **symbol_table;
644           long symcount;
645
646           symbol_table = (asymbol **) xmalloc (storage_needed);
647           make_cleanup (xfree, symbol_table);
648           symcount = bfd_canonicalize_symtab (objfile->obfd, symbol_table);
649           
650           if (symcount < 0)
651             error (_("Can't read symbols from %s: %s"),
652                    bfd_get_filename (objfile->obfd),
653                    bfd_errmsg (bfd_get_error ()));
654           
655           macho_symtab_read (objfile, symcount, symbol_table);
656         }
657       
658       install_minimal_symbols (objfile);
659
660       /* Try to read .eh_frame / .debug_frame.  */
661       /* First, locate these sections.  We ignore the result status
662          as it only checks for debug info.  */
663       dwarf2_has_info (objfile);
664       dwarf2_build_frame_info (objfile);
665       
666       /* Check for DSYM file.  */
667       dsym_bfd = macho_check_dsym (objfile);
668       if (dsym_bfd != NULL)
669         {
670           int ix;
671           oso_el *oso;
672           struct bfd_section *asect, *dsect;
673
674           if (mach_o_debug_level > 0)
675             printf_unfiltered (_("dsym file found\n"));
676
677           /* Remove oso.  They won't be used.  */
678           for (ix = 0; VEC_iterate (oso_el, oso_vector, ix, oso); ix++)
679             {
680               xfree (oso->symbols);
681               xfree (oso->offsets);
682             }
683           VEC_free (oso_el, oso_vector);
684           oso_vector = NULL;
685
686           /* Set dsym section size.  */
687           for (asect = objfile->obfd->sections, dsect = dsym_bfd->sections;
688                asect && dsect;
689                asect = asect->next, dsect = dsect->next)
690             {
691               if (strcmp (asect->name, dsect->name) != 0)
692                 break;
693               bfd_set_section_size (dsym_bfd, dsect,
694                                     bfd_get_section_size (asect));
695             }
696
697           /* Add the dsym file as a separate file.  */
698           symbol_file_add_separate (dsym_bfd, symfile_flags, objfile);
699       
700           /* Don't try to read dwarf2 from main file or shared libraries.  */
701           return;
702         }
703     }
704
705   if (dwarf2_has_info (objfile))
706     {
707       /* DWARF 2 sections */
708       dwarf2_build_psymtabs (objfile);
709     }
710
711   /* Do not try to read .eh_frame/.debug_frame as they are not relocated
712      and dwarf2_build_frame_info cannot deal with unrelocated sections.  */
713
714   /* Then the oso.  */
715   if (oso_vector != NULL)
716     macho_symfile_read_all_oso (objfile, symfile_flags);
717 }
718
719 static bfd_byte *
720 macho_symfile_relocate (struct objfile *objfile, asection *sectp,
721                         bfd_byte *buf)
722 {
723   bfd *abfd = objfile->obfd;
724
725   /* We're only interested in sections with relocation
726      information.  */
727   if ((sectp->flags & SEC_RELOC) == 0)
728     return NULL;
729
730   if (mach_o_debug_level > 0)
731     printf_unfiltered (_("Relocate section '%s' of %s\n"),
732                        sectp->name, objfile->name);
733
734   if (current_oso.symbol_table == NULL)
735     {
736       int storage;
737       int i;
738       char leading_char;
739
740       storage = bfd_get_symtab_upper_bound (abfd);
741       current_oso.symbol_table = (asymbol **) xmalloc (storage);
742       bfd_canonicalize_symtab (abfd, current_oso.symbol_table);
743
744       leading_char = bfd_get_symbol_leading_char (abfd);
745
746       for (i = 0; current_oso.symbol_table[i]; i++)
747         {
748           asymbol *sym = current_oso.symbol_table[i];
749
750           if (bfd_is_com_section (sym->section))
751             {
752               /* This one must be solved.  */
753               struct minimal_symbol *msym;
754               const char *name = sym->name;
755
756               if (name[0] == leading_char)
757                 name++;
758
759               msym = lookup_minimal_symbol
760                 (name, NULL, current_oso.main_objfile);
761               if (msym == NULL)
762                 {
763                   warning (_("can't find symbol '%s' in minsymtab"), name);
764                   continue;
765                 }
766               else
767                 {
768                   sym->section = &bfd_abs_section;
769                   sym->value = SYMBOL_VALUE_ADDRESS (msym);
770                 }
771             }
772         }
773     }
774
775   return bfd_simple_get_relocated_section_contents (abfd, sectp, buf, NULL);
776 }
777
778 static void
779 macho_symfile_finish (struct objfile *objfile)
780 {
781 }
782
783 static void
784 macho_symfile_offsets (struct objfile *objfile,
785                        struct section_addr_info *addrs)
786 {
787   unsigned int i;
788   unsigned int num_sections;
789   struct obj_section *osect;
790
791   /* Allocate section_offsets.  */
792   objfile->num_sections = bfd_count_sections (objfile->obfd);
793   objfile->section_offsets = (struct section_offsets *)
794     obstack_alloc (&objfile->objfile_obstack,
795                    SIZEOF_N_SECTION_OFFSETS (objfile->num_sections));
796   memset (objfile->section_offsets, 0,
797           SIZEOF_N_SECTION_OFFSETS (objfile->num_sections));
798
799   /* This code is run when we first add the objfile with
800      symfile_add_with_addrs_or_offsets, when "addrs" not "offsets" are
801      passed in.  The place in symfile.c where the addrs are applied
802      depends on the addrs having section names.  But in the dyld code
803      we build an anonymous array of addrs, so that code is a no-op.
804      Because of that, we have to apply the addrs to the sections here.
805      N.B. if an objfile slides after we've already created it, then it
806      goes through objfile_relocate.  */
807
808   for (i = 0; i < addrs->num_sections; i++)
809     {
810       if (addrs->other[i].name == NULL)
811         continue;
812
813       ALL_OBJFILE_OSECTIONS (objfile, osect)
814         {
815           const char *bfd_sect_name = osect->the_bfd_section->name;
816
817           if (strcmp (bfd_sect_name, addrs->other[i].name) == 0)
818             {
819               obj_section_offset (osect) = addrs->other[i].addr;
820               break;
821             }
822         }
823     }
824
825   objfile->sect_index_text = 0;
826
827   ALL_OBJFILE_OSECTIONS (objfile, osect)
828     {
829       const char *bfd_sect_name = osect->the_bfd_section->name;
830       int sect_index = osect->the_bfd_section->index;
831       
832       if (strncmp (bfd_sect_name, "LC_SEGMENT.", 11) == 0)
833         bfd_sect_name += 11;
834       if (strcmp (bfd_sect_name, "__TEXT") == 0
835           || strcmp (bfd_sect_name, "__TEXT.__text") == 0)
836         objfile->sect_index_text = sect_index;
837     }
838 }
839
840 static const struct sym_fns macho_sym_fns = {
841   bfd_target_mach_o_flavour,
842
843   macho_new_init,               /* init anything gbl to entire symtab */
844   macho_symfile_init,           /* read initial info, setup for sym_read() */
845   macho_symfile_read,           /* read a symbol file into symtab */
846   macho_symfile_finish,         /* finished with file, cleanup */
847   macho_symfile_offsets,        /* xlate external to internal form */
848   default_symfile_segments,     /* Get segment information from a file.  */
849   NULL,
850   macho_symfile_relocate,       /* Relocate a debug section.  */
851   &psym_functions
852 };
853
854 void
855 _initialize_machoread ()
856 {
857   add_symtab_fns (&macho_sym_fns);
858
859   add_setshow_zinteger_cmd ("mach-o", class_obscure,
860                             &mach_o_debug_level,
861                             _("Set if printing Mach-O symbols processing."),
862                             _("Show if printing Mach-O symbols processing."),
863                             NULL, NULL, NULL,
864                             &setdebuglist, &showdebuglist);
865 }