PATCH: improve mach-o bfd backend

Tristan Gingold gingold@adacore.com
Tue Oct 28 16:10:00 GMT 2008


Hi,

this patch aims at improving binutils tools when they operate on mach- 
o files:
Various flags are set more correctly, print_private_bfd_data (objdump - 
p) is added,
print_symbols (objdump --syms) display much more details,
and fat files can be read without crashing.

Tristan.

bfd/
2008-10-28  Tristan Gingold  <gingold@adacore.com>

	* mach-o.h (BFD_MACH_O_NO_SECT): Add; reorders the macros.
	(BFD_MACH_O_SYM_NTYPE, BFD_MACH_O_SYM_NSECT,
	BFD_MACH_O_SYM_NDESC): New macros.
	(bfd_mach_o_i386_thread_flavour): Define according to the latest
	definition from system header.
	(bfd_mach_o_load_command_type): Add BFD_MACH_O_LC_RPATH,
	BFD_MACH_O_LC_CODE_SIGNATURE.
	(BFD_MACH_O_SECTION_TYPE_MASK, BFD_MACH_O_SECTION_ATTRIBUTES_MASK,
	BFD_MACH_O_SECTION_ATTRIBUTES_SYS, BFD_MACH_O_SECTION_ATTRIBUTES_USR,
	BFD_MACH_O_S_ATTR_LOC_RELOC, BFD_MACH_O_S_ATTR_EXT_RELOC,
	BFD_MACH_O_S_ATTR_SOME_INSTRUCTIONS, BFD_MACH_O_S_ATTR_DEBUG,
	BFD_MACH_O_S_ATTR_PURE_INSTRUCTIONS): Add.
	(bfd_mach_o_segment_command): Add room for a nul terminator in
	segname field.
	(BFD_MACH_O_PROT_READ, BFD_MACH_O_PROT_WRITE,
	BFD_MACH_O_PROT_EXECUTE): Add.
	(INDIRECT_SYMBOL_LOCAL): Renames to BFD_MACH_O_INDIRECT_SYMBOL_LOCAL.
	(INDIRECT_SYMBOL_ABS): Renames to BFD_MACH_O_INDIRECT_SYMBOL_ABS.
	(bfd_mach_o_uuid_command): Add the structure.
	(bfd_mach_o_load_command): Add uuid field.
	(bfd_get_mach_o_data): New macro.
	* mach-o.c (bfd_mach_o_bfd_print_private_bfd_data): New function which
	replaces the macro.
	(SECTION_TYPE, SECTION_ATTRIBUTES, SECTION_ATTRIBUTES_USR,
	S_ATTR_PURE_INSTRUCTIONS, SECTION_ATTRIBUTES_SYS,
	S_ATTR_SOME_INSTRUCTIONS, S_ATTR_EXT_RELOC, S_ATTR_LOC_RELOC): Renamed
	and moved to mach-o.h.
	(N_STAB, N_TYPE, N_EXT, N_UNDF, N_ABS, N_TEXT, N_DATA, N_BSS,
	N_SECT, N_INDR): Removed as they duplicated macros in mach-o.h.
	(bfd_mach_o_print_symbol): Print much more details.
	(bfd_mach_o_make_bfd_section): Add prot argument, use canonical
	dwarf name for dwarf sections.  Precisely set section flags.
	(bfd_mach_o_scan_read_section_32): Add prot argument.
	(bfd_mach_o_scan_read_section_64): Ditto.
	(bfd_mach_o_scan_read_section): Ditto.
	(bfd_mach_o_scan_read_symtab_symbol): Set section for debugging
	stabs, set BSF_GLOBAL and LOCAL flags correctly.  Fix section
	for N_SECT symbols.
	(bfd_mach_o_i386_flavour_string): Reindent and adjust for new
	names.
	(bfd_mach_o_scan_read_symtab): Set HAS_SYMS flags on bfd if there
	are symbols.
	(bfd_mach_o_scan_read_uuid): New function.
	(bfd_mach_o_scan_read_segment): Add a trailing nul.  Segments
	flags are now simply HAS_CONTENTS.  Pass protection to
	bfd_mach_o_scan_read_section.
	(bfd_mach_o_scan_read_command): Decode UUID command.
	(bfd_mach_o_flatten_sections): Add comments.  Fix flavour names.
	(bfd_mach_o_scan): Set flags according to file type.
	(mach_o_fat_archentry): Remove abfd field.
	(bfd_mach_o_archive_p): Remove initialization of abfd field.
	(bfd_mach_o_openr_next_archived_file): Find previous archive
	by position and not by bfd (as former bfds may have been freed).
	Give architecture name to archived file.
	* mach-o-target.c (TARGET_NAME): Use generic archive for non fat
	targets.

Index: bfd/mach-o-target.c
===================================================================
RCS file: /cvs/src/src/bfd/mach-o-target.c,v
retrieving revision 1.5
diff -c -p -r1.5 mach-o-target.c
*** bfd/mach-o-target.c	3 Jul 2007 14:26:42 -0000	1.5
--- bfd/mach-o-target.c	28 Oct 2008 15:41:25 -0000
*************** const bfd_target TARGET_NAME =
*** 84,110 ****
   #else
       _bfd_dummy_target,
       bfd_mach_o_object_p,
!     _bfd_dummy_target,
       bfd_mach_o_core_p
   #endif
     },
     {				/* bfd_set_format.  */
       bfd_false,
       bfd_mach_o_mkobject,
!     bfd_false,
       bfd_mach_o_mkobject,
     },
     {				/* bfd_write_contents.  */
       bfd_false,
       bfd_mach_o_write_contents,
!     bfd_false,
       bfd_mach_o_write_contents,
     },

     BFD_JUMP_TABLE_GENERIC (bfd_mach_o),
     BFD_JUMP_TABLE_COPY (bfd_mach_o),
     BFD_JUMP_TABLE_CORE (bfd_mach_o),
     BFD_JUMP_TABLE_ARCHIVE (bfd_mach_o),
     BFD_JUMP_TABLE_SYMBOLS (bfd_mach_o),
     BFD_JUMP_TABLE_RELOCS (_bfd_norelocs),
     BFD_JUMP_TABLE_WRITE (bfd_mach_o),
--- 84,114 ----
   #else
       _bfd_dummy_target,
       bfd_mach_o_object_p,
!     bfd_generic_archive_p,
       bfd_mach_o_core_p
   #endif
     },
     {				/* bfd_set_format.  */
       bfd_false,
       bfd_mach_o_mkobject,
!     _bfd_generic_mkarchive,
       bfd_mach_o_mkobject,
     },
     {				/* bfd_write_contents.  */
       bfd_false,
       bfd_mach_o_write_contents,
!     _bfd_write_archive_contents,
       bfd_mach_o_write_contents,
     },

     BFD_JUMP_TABLE_GENERIC (bfd_mach_o),
     BFD_JUMP_TABLE_COPY (bfd_mach_o),
     BFD_JUMP_TABLE_CORE (bfd_mach_o),
+ #if TARGET_ARCHIVE
     BFD_JUMP_TABLE_ARCHIVE (bfd_mach_o),
+ #else
+   BFD_JUMP_TABLE_ARCHIVE (_bfd_archive_bsd),
+ #endif
     BFD_JUMP_TABLE_SYMBOLS (bfd_mach_o),
     BFD_JUMP_TABLE_RELOCS (_bfd_norelocs),
     BFD_JUMP_TABLE_WRITE (bfd_mach_o),
Index: bfd/mach-o.c
===================================================================
RCS file: /cvs/src/src/bfd/mach-o.c,v
retrieving revision 1.29
diff -c -p -r1.29 mach-o.c
*** bfd/mach-o.c	5 Sep 2008 08:07:54 -0000	1.29
--- bfd/mach-o.c	28 Oct 2008 15:41:26 -0000
***************
*** 24,29 ****
--- 24,30 ----
   #include "bfd.h"
   #include "libbfd.h"
   #include "libiberty.h"
+ #include "aout/stab_gnu.h"
   #include <ctype.h>

   #ifndef BFD_IO_FUNCS
***************
*** 64,70 ****
   #define bfd_mach_o_set_arch_mach                       
bfd_default_set_arch_mach
   #define bfd_mach_o_bfd_merge_private_bfd_data          
_bfd_generic_bfd_merge_private_bfd_data
   #define bfd_mach_o_bfd_set_private_flags               
_bfd_generic_bfd_set_private_flags
- #define bfd_mach_o_bfd_print_private_bfd_data          
_bfd_generic_bfd_print_private_bfd_data
   #define bfd_mach_o_get_section_contents                
_bfd_generic_get_section_contents
   #define bfd_mach_o_set_section_contents                
_bfd_generic_set_section_contents
   #define bfd_mach_o_bfd_gc_sections                     
bfd_generic_gc_sections
--- 65,70 ----
***************
*** 75,111 ****
   #define bfd_mach_o_bfd_copy_private_header_data        
_bfd_generic_bfd_copy_private_header_data
   #define bfd_mach_o_core_file_matches_executable_p      
generic_core_file_matches_executable_p

-
- /* The flags field of a section structure is separated into two  
parts a section
-    type and section attributes.  The section types are mutually  
exclusive (it
-    can only have one type) but the section attributes are not (it  
may have more
-    than one attribute).  */
-
- #define SECTION_TYPE             0x000000ff     /* 256 section  
types.  */
- #define SECTION_ATTRIBUTES       0xffffff00     /*  24 section  
attributes.  */
-
- /* Constants for the section attributes part of the flags field of a  
section
-    structure.  */
-
- #define SECTION_ATTRIBUTES_USR   0xff000000     /* User-settable  
attributes.  */
- #define S_ATTR_PURE_INSTRUCTIONS 0x80000000     /* Section contains  
only true machine instructions.  */
- #define SECTION_ATTRIBUTES_SYS   0x00ffff00     /* System setable  
attributes.  */
- #define S_ATTR_SOME_INSTRUCTIONS 0x00000400     /* Section contains  
some machine instructions.  */
- #define S_ATTR_EXT_RELOC         0x00000200     /* Section has  
external relocation entries.  */
- #define S_ATTR_LOC_RELOC         0x00000100     /* Section has local  
relocation entries.  */
-
- #define N_STAB 0xe0
- #define N_TYPE 0x1e
- #define N_EXT  0x01
-
- #define N_UNDF 0x0
- #define N_ABS  0x2
- #define N_TEXT 0x4
- #define N_DATA 0x6
- #define N_BSS  0x8
- #define N_SECT 0xe
- #define N_INDR 0xa
-
   static unsigned int
   bfd_mach_o_version (bfd *abfd)
   {
--- 75,80 ----
*************** bfd_mach_o_print_symbol (bfd *abfd,
*** 255,260 ****
--- 224,233 ----
   			 bfd_print_symbol_type how)
   {
     FILE *file = (FILE *) afile;
+   unsigned char ntype;
+   unsigned char nsect;
+   unsigned int ndesc;
+   const char *name;

     switch (how)
       {
*************** bfd_mach_o_print_symbol (bfd *abfd,
*** 263,269 ****
         break;
       default:
         bfd_print_symbol_vandf (abfd, (PTR) file, symbol);
!       fprintf (file, " %-5s %s", symbol->section->name, symbol->name);
       }
   }

--- 236,275 ----
         break;
       default:
         bfd_print_symbol_vandf (abfd, (PTR) file, symbol);
!       ntype = BFD_MACH_O_SYM_NTYPE (symbol);
!       nsect = BFD_MACH_O_SYM_NSECT (symbol);
!       ndesc = BFD_MACH_O_SYM_NDESC (symbol);
!       if (ntype & BFD_MACH_O_N_STAB)
! 	name = bfd_get_stab_name (ntype);
!       else
! 	switch (ntype & BFD_MACH_O_N_TYPE)
! 	  {
! 	  case BFD_MACH_O_N_UNDF:
! 	    name = "UND";
! 	    break;
! 	  case BFD_MACH_O_N_ABS:
! 	    name = "ABS";
! 	    break;
! 	  case BFD_MACH_O_N_INDR:
! 	    name = "INDR";
! 	    break;
! 	  case BFD_MACH_O_N_PBUD:
! 	    name = "PBUD";
! 	    break;
! 	  case BFD_MACH_O_N_SECT:
! 	    name = "SECT";
! 	    break;
! 	  default:
! 	    name = "???";
! 	    break;
! 	  }
!       if (name == NULL)
! 	name = "";
!       fprintf (file, " %02x %-6s %02x %04x", ntype, name, nsect,  
ndesc);
!       if ((ntype & BFD_MACH_O_N_STAB) == 0
! 	  && (ntype & BFD_MACH_O_N_TYPE) == BFD_MACH_O_N_SECT)
! 	fprintf (file, " %-5s", symbol->section->name);
!       fprintf (file, " %s", symbol->name);
       }
   }

*************** bfd_mach_o_scan_write_symtab_symbols (bf
*** 554,562 ****
         s = &sym->symbols[i];

         /* Instead just set from the stored values.  */
!       ntype = (s->udata.i >> 24) & 0xff;
!       nsect = (s->udata.i >> 16) & 0xff;
!       ndesc = s->udata.i & 0xffff;

         bfd_h_put_32 (abfd, s->name - sym->strtab, buf);
         bfd_h_put_8 (abfd, ntype, buf + 4);
--- 560,568 ----
         s = &sym->symbols[i];

         /* Instead just set from the stored values.  */
!       ntype = BFD_MACH_O_SYM_NTYPE (s);
!       nsect = BFD_MACH_O_SYM_NSECT (s);
!       ndesc = BFD_MACH_O_SYM_NDESC (s);

         bfd_h_put_32 (abfd, s->name - sym->strtab, buf);
         bfd_h_put_8 (abfd, ntype, buf + 4);
*************** bfd_mach_o_read_header (bfd *abfd, bfd_m
*** 769,775 ****
   }

   static asection *
! bfd_mach_o_make_bfd_section (bfd *abfd, bfd_mach_o_section *section)
   {
     asection *bfdsec;
     char *sname;
--- 775,782 ----
   }

   static asection *
! bfd_mach_o_make_bfd_section (bfd *abfd, bfd_mach_o_section *section,
! 			     unsigned long prot)
   {
     asection *bfdsec;
     char *sname;
*************** bfd_mach_o_make_bfd_section (bfd *abfd,
*** 784,794 ****
     sname = bfd_alloc (abfd, snamelen);
     if (sname == NULL)
       return NULL;
-   sprintf (sname, "%s.%s.%s", prefix, section->segname, section- 
 >sectname);

!   flags = SEC_ALLOC;
!   if ((section->flags & SECTION_TYPE) != BFD_MACH_O_S_ZEROFILL)
!     flags = SEC_HAS_CONTENTS | SEC_LOAD | SEC_ALLOC | SEC_CODE;
     bfdsec = bfd_make_section_anyway_with_flags (abfd, sname, flags);
     if (bfdsec == NULL)
       return NULL;
--- 791,821 ----
     sname = bfd_alloc (abfd, snamelen);
     if (sname == NULL)
       return NULL;

!   /* Use canonical dwarf section names for dwarf sections.  */
!   if (strcmp (section->segname, "__DWARF") == 0
!       && strncmp (section->sectname, "__", 2) == 0)
!     sprintf (sname, ".%s", section->sectname + 2);
!   else
!     sprintf (sname, "%s.%s.%s", prefix, section->segname, section- 
 >sectname);
!
!   if (section->flags & BFD_MACH_O_S_ATTR_DEBUG)
!     flags = SEC_HAS_CONTENTS | SEC_DEBUGGING;
!   else
!     {
!       flags = SEC_ALLOC;
!       if ((section->flags & BFD_MACH_O_SECTION_TYPE_MASK)
! 	  != BFD_MACH_O_S_ZEROFILL)
! 	{
! 	  flags |= SEC_HAS_CONTENTS | SEC_LOAD;
! 	  if (prot & BFD_MACH_O_PROT_EXECUTE)
! 	    flags |= SEC_CODE;
! 	  if (prot & BFD_MACH_O_PROT_WRITE)
! 	    flags |= SEC_DATA;
! 	  else if (prot & BFD_MACH_O_PROT_READ)
! 	    flags |= SEC_READONLY;
! 	}
!     }
     bfdsec = bfd_make_section_anyway_with_flags (abfd, sname, flags);
     if (bfdsec == NULL)
       return NULL;
*************** bfd_mach_o_make_bfd_section (bfd *abfd,
*** 806,812 ****
   static int
   bfd_mach_o_scan_read_section_32 (bfd *abfd,
   				 bfd_mach_o_section *section,
! 				 bfd_vma offset)
   {
     unsigned char buf[68];

--- 833,840 ----
   static int
   bfd_mach_o_scan_read_section_32 (bfd *abfd,
   				 bfd_mach_o_section *section,
! 				 bfd_vma offset,
! 				 unsigned long prot)
   {
     unsigned char buf[68];

*************** bfd_mach_o_scan_read_section_32 (bfd *ab
*** 828,834 ****
     section->reserved1 = bfd_h_get_32 (abfd, buf + 60);
     section->reserved2 = bfd_h_get_32 (abfd, buf + 64);
     section->reserved3 = 0;
!   section->bfdsection = bfd_mach_o_make_bfd_section (abfd, section);

     if (section->bfdsection == NULL)
       return -1;
--- 856,862 ----
     section->reserved1 = bfd_h_get_32 (abfd, buf + 60);
     section->reserved2 = bfd_h_get_32 (abfd, buf + 64);
     section->reserved3 = 0;
!   section->bfdsection = bfd_mach_o_make_bfd_section (abfd, section,  
prot);

     if (section->bfdsection == NULL)
       return -1;
*************** bfd_mach_o_scan_read_section_32 (bfd *ab
*** 839,845 ****
   static int
   bfd_mach_o_scan_read_section_64 (bfd *abfd,
   				 bfd_mach_o_section *section,
! 				 bfd_vma offset)
   {
     unsigned char buf[80];

--- 867,874 ----
   static int
   bfd_mach_o_scan_read_section_64 (bfd *abfd,
   				 bfd_mach_o_section *section,
! 				 bfd_vma offset,
! 				 unsigned long prot)
   {
     unsigned char buf[80];

*************** bfd_mach_o_scan_read_section_64 (bfd *ab
*** 861,867 ****
     section->reserved1 = bfd_h_get_32 (abfd, buf + 68);
     section->reserved2 = bfd_h_get_32 (abfd, buf + 72);
     section->reserved3 = bfd_h_get_32 (abfd, buf + 76);
!   section->bfdsection = bfd_mach_o_make_bfd_section (abfd, section);

     if (section->bfdsection == NULL)
       return -1;
--- 890,896 ----
     section->reserved1 = bfd_h_get_32 (abfd, buf + 68);
     section->reserved2 = bfd_h_get_32 (abfd, buf + 72);
     section->reserved3 = bfd_h_get_32 (abfd, buf + 76);
!   section->bfdsection = bfd_mach_o_make_bfd_section (abfd, section,  
prot);

     if (section->bfdsection == NULL)
       return -1;
*************** static int
*** 873,884 ****
   bfd_mach_o_scan_read_section (bfd *abfd,
   			      bfd_mach_o_section *section,
   			      bfd_vma offset,
   			      unsigned int wide)
   {
     if (wide)
!     return bfd_mach_o_scan_read_section_64 (abfd, section, offset);
     else
!     return bfd_mach_o_scan_read_section_32 (abfd, section, offset);
   }

   int
--- 902,914 ----
   bfd_mach_o_scan_read_section (bfd *abfd,
   			      bfd_mach_o_section *section,
   			      bfd_vma offset,
+ 			      unsigned long prot,
   			      unsigned int wide)
   {
     if (wide)
!     return bfd_mach_o_scan_read_section_64 (abfd, section, offset,  
prot);
     else
!     return bfd_mach_o_scan_read_section_32 (abfd, section, offset,  
prot);
   }

   int
*************** bfd_mach_o_scan_read_symtab_symbol (bfd
*** 912,918 ****
     stroff = bfd_h_get_32 (abfd, buf);
     type = bfd_h_get_8 (abfd, buf + 4);
     symtype = (type & 0x0e);
!   section = bfd_h_get_8 (abfd, buf + 5) - 1;
     desc = bfd_h_get_16 (abfd, buf + 6);
     if (wide)
       value = bfd_h_get_64 (abfd, buf + 8);
--- 942,948 ----
     stroff = bfd_h_get_32 (abfd, buf);
     type = bfd_h_get_8 (abfd, buf + 4);
     symtype = (type & 0x0e);
!   section = bfd_h_get_8 (abfd, buf + 5);
     desc = bfd_h_get_16 (abfd, buf + 6);
     if (wide)
       value = bfd_h_get_64 (abfd, buf + 8);
*************** bfd_mach_o_scan_read_symtab_symbol (bfd
*** 936,955 ****
       {
         s->flags |= BSF_DEBUGGING;
         s->section = bfd_und_section_ptr;
       }
     else
       {
         if (type & BFD_MACH_O_N_PEXT)
! 	{
! 	  type &= ~BFD_MACH_O_N_PEXT;
! 	  s->flags |= BSF_GLOBAL;
! 	}
!
         if (type & BFD_MACH_O_N_EXT)
! 	{
! 	  type &= ~BFD_MACH_O_N_EXT;
! 	  s->flags |= BSF_GLOBAL;
! 	}

         switch (symtype)
   	{
--- 966,1000 ----
       {
         s->flags |= BSF_DEBUGGING;
         s->section = bfd_und_section_ptr;
+       switch (type)
+ 	{
+ 	case N_FUN:
+ 	case N_STSYM:
+ 	case N_LCSYM:
+ 	case N_BNSYM:
+ 	case N_SLINE:
+ 	case N_ENSYM:
+ 	case N_ECOMM:
+ 	case N_ECOML:
+ 	case N_GSYM:
+ 	  if ((section > 0) && (section <= mdata->nsects))
+ 	    {
+ 	      s->section = mdata->sections[section - 1]->bfdsection;
+ 	      s->value = s->value - mdata->sections[section - 1]->addr;
+ 	    }
+ 	  break;
+ 	}
       }
     else
       {
         if (type & BFD_MACH_O_N_PEXT)
! 	s->flags |= BSF_GLOBAL;
!
         if (type & BFD_MACH_O_N_EXT)
! 	s->flags |= BSF_GLOBAL;
!
!       if (!(type & (BFD_MACH_O_N_PEXT | BFD_MACH_O_N_EXT)))
! 	s->flags |= BSF_LOCAL;

         switch (symtype)
   	{
*************** bfd_mach_o_scan_read_symtab_symbol (bfd
*** 965,972 ****
   	case BFD_MACH_O_N_SECT:
   	  if ((section > 0) && (section <= mdata->nsects))
   	    {
! 	      s->section = mdata->sections[section]->bfdsection;
! 	      s->value = s->value - mdata->sections[section]->addr;
   	    }
   	  else
   	    {
--- 1010,1017 ----
   	case BFD_MACH_O_N_SECT:
   	  if ((section > 0) && (section <= mdata->nsects))
   	    {
! 	      s->section = mdata->sections[section - 1]->bfdsection;
! 	      s->value = s->value - mdata->sections[section - 1]->addr;
   	    }
   	  else
   	    {
*************** bfd_mach_o_i386_flavour_string (unsigned
*** 1094,1111 ****
   {
     switch ((int) flavour)
       {
!     case BFD_MACH_O_i386_NEW_THREAD_STATE: return  
"i386_NEW_THREAD_STATE";
!     case BFD_MACH_O_i386_FLOAT_STATE: return "i386_FLOAT_STATE";
!     case BFD_MACH_O_i386_ISA_PORT_MAP_STATE: return  
"i386_ISA_PORT_MAP_STATE";
!     case BFD_MACH_O_i386_V86_ASSIST_STATE: return  
"i386_V86_ASSIST_STATE";
!     case BFD_MACH_O_i386_REGS_SEGS_STATE: return  
"i386_REGS_SEGS_STATE";
!     case BFD_MACH_O_i386_THREAD_SYSCALL_STATE: return  
"i386_THREAD_SYSCALL_STATE";
!     case BFD_MACH_O_i386_THREAD_STATE_NONE: return  
"i386_THREAD_STATE_NONE";
!     case BFD_MACH_O_i386_SAVED_STATE: return "i386_SAVED_STATE";
!     case BFD_MACH_O_i386_THREAD_STATE: return "i386_THREAD_STATE";
!     case BFD_MACH_O_i386_THREAD_FPSTATE: return "i386_THREAD_FPSTATE";
!     case BFD_MACH_O_i386_THREAD_EXCEPTSTATE: return  
"i386_THREAD_EXCEPTSTATE";
!     case BFD_MACH_O_i386_THREAD_CTHREADSTATE: return  
"i386_THREAD_CTHREADSTATE";
       default: return "UNKNOWN";
       }
   }
--- 1139,1157 ----
   {
     switch ((int) flavour)
       {
!     case BFD_MACH_O_x86_THREAD_STATE32:    return  
"x86_THREAD_STATE32";
!     case BFD_MACH_O_x86_FLOAT_STATE32:     return "x86_FLOAT_STATE32";
!     case BFD_MACH_O_x86_EXCEPTION_STATE32: return  
"x86_EXCEPTION_STATE32";
!     case BFD_MACH_O_x86_THREAD_STATE64:    return  
"x86_THREAD_STATE64";
!     case BFD_MACH_O_x86_FLOAT_STATE64:     return "x86_FLOAT_STATE64";
!     case BFD_MACH_O_x86_EXCEPTION_STATE64: return  
"x86_EXCEPTION_STATE64";
!     case BFD_MACH_O_x86_THREAD_STATE:      return "x86_THREAD_STATE";
!     case BFD_MACH_O_x86_FLOAT_STATE:       return "x86_FLOAT_STATE";
!     case BFD_MACH_O_x86_EXCEPTION_STATE:   return  
"x86_EXCEPTION_STATE";
!     case BFD_MACH_O_x86_DEBUG_STATE32:     return "x86_DEBUG_STATE32";
!     case BFD_MACH_O_x86_DEBUG_STATE64:     return "x86_DEBUG_STATE64";
!     case BFD_MACH_O_x86_DEBUG_STATE:       return "x86_DEBUG_STATE";
!     case BFD_MACH_O_THREAD_STATE_NONE:     return "THREAD_STATE_NONE";
       default: return "UNKNOWN";
       }
   }
*************** bfd_mach_o_scan_read_symtab (bfd *abfd,
*** 1422,1427 ****
--- 1468,1476 ----

     seg->stabs_segment = bfdsec;

+   if (seg->nsyms != 0)
+     abfd->flags |= HAS_SYMS;
+
     prefix = "LC_SYMTAB.stabstr";
     sname = bfd_alloc (abfd, strlen (prefix) + 1);
     if (sname == NULL)
*************** bfd_mach_o_scan_read_symtab (bfd *abfd,
*** 1444,1449 ****
--- 1493,1532 ----
   }

   static int
+ bfd_mach_o_scan_read_uuid (bfd *abfd, bfd_mach_o_load_command  
*command)
+ {
+   bfd_mach_o_uuid_command *cmd = &command->command.uuid;
+   asection *bfdsec;
+   char *sname;
+   static const char prefix[] = "LC_UUID";
+
+   BFD_ASSERT (command->type == BFD_MACH_O_LC_UUID);
+
+   bfd_seek (abfd, command->offset + 8, SEEK_SET);
+   if (bfd_bread ((PTR) cmd->uuid, 16, abfd) != 16)
+     return -1;
+
+   sname = bfd_alloc (abfd, strlen (prefix) + 1);
+   if (sname == NULL)
+     return -1;
+   strcpy (sname, prefix);
+
+   bfdsec = bfd_make_section_anyway_with_flags (abfd, sname,  
SEC_HAS_CONTENTS);
+   if (bfdsec == NULL)
+     return -1;
+
+   bfdsec->vma = 0;
+   bfdsec->lma = 0;
+   bfdsec->size = command->len - 8;
+   bfdsec->filepos = command->offset + 8;
+   bfdsec->alignment_power = 0;
+
+   cmd->section = bfdsec;
+
+   return 0;
+ }
+
+ static int
   bfd_mach_o_scan_read_segment (bfd *abfd,
   			      bfd_mach_o_load_command *command,
   			      unsigned int wide)
*************** bfd_mach_o_scan_read_segment (bfd *abfd,
*** 1465,1470 ****
--- 1548,1554 ----
   	return -1;

         memcpy (seg->segname, buf, 16);
+       seg->segname[16] = '\0';

         seg->vmaddr = bfd_h_get_64 (abfd, buf + 16);
         seg->vmsize = bfd_h_get_64 (abfd, buf + 24);
*************** bfd_mach_o_scan_read_segment (bfd *abfd,
*** 1484,1489 ****
--- 1568,1574 ----
   	return -1;

         memcpy (seg->segname, buf, 16);
+       seg->segname[16] = '\0';

         seg->vmaddr = bfd_h_get_32 (abfd, buf + 16);
         seg->vmsize = bfd_h_get_32 (abfd, buf + 20);
*************** bfd_mach_o_scan_read_segment (bfd *abfd,
*** 1510,1516 ****
     bfdsec->size = seg->filesize;
     bfdsec->filepos = seg->fileoff;
     bfdsec->alignment_power = 0x0;
!   bfdsec->flags = SEC_HAS_CONTENTS | SEC_LOAD | SEC_ALLOC | SEC_CODE;
     bfdsec->segment_mark = 1;

     seg->segment = bfdsec;
--- 1595,1601 ----
     bfdsec->size = seg->filesize;
     bfdsec->filepos = seg->fileoff;
     bfdsec->alignment_power = 0x0;
!   bfdsec->flags = SEC_HAS_CONTENTS;
     bfdsec->segment_mark = 1;

     seg->segment = bfdsec;
*************** bfd_mach_o_scan_read_segment (bfd *abfd,
*** 1530,1536 ****
   	    segoff = command->offset + 48 + 8 + (i * 68);

   	  if (bfd_mach_o_scan_read_section
! 	      (abfd, &seg->sections[i], segoff, wide) != 0)
   	    return -1;
   	}
       }
--- 1615,1621 ----
   	    segoff = command->offset + 48 + 8 + (i * 68);

   	  if (bfd_mach_o_scan_read_section
! 	      (abfd, &seg->sections[i], segoff, seg->initprot, wide) != 0)
   	    return -1;
   	}
       }
*************** bfd_mach_o_scan_read_command (bfd *abfd,
*** 1618,1623 ****
--- 1703,1714 ----
       case BFD_MACH_O_LC_TWOLEVEL_HINTS:
       case BFD_MACH_O_LC_PREBIND_CKSUM:
         break;
+     case BFD_MACH_O_LC_UUID:
+       if (bfd_mach_o_scan_read_uuid (abfd, command) != 0)
+ 	return -1;
+       break;
+     case BFD_MACH_O_LC_CODE_SIGNATURE:
+       break;
       default:
         fprintf (stderr, "unable to read unknown load command 0x%lx\n",
   	       (unsigned long) command->type);
*************** bfd_mach_o_flatten_sections (bfd *abfd)
*** 1634,1639 ****
--- 1725,1731 ----
     long csect = 0;
     unsigned long i, j;

+   /* Count total number of sections.  */
     mdata->nsects = 0;

     for (i = 0; i < mdata->header.ncmds; i++)
*************** bfd_mach_o_flatten_sections (bfd *abfd)
*** 1648,1655 ****
--- 1740,1750 ----
   	}
       }

+   /* Allocate sections array.  */
     mdata->sections = bfd_alloc (abfd,
   			       mdata->nsects * sizeof (bfd_mach_o_section *));
+
+   /* Fill the array.  */
     csect = 0;

     for (i = 0; i < mdata->header.ncmds; i++)
*************** bfd_mach_o_scan_start_address (bfd *abfd
*** 1694,1700 ****
       {
         if ((mdata->header.cputype == BFD_MACH_O_CPU_TYPE_I386)
   	  && (cmd->flavours[i].flavour
! 	      == (unsigned long) BFD_MACH_O_i386_THREAD_STATE))
   	{
   	  unsigned char buf[4];

--- 1789,1795 ----
       {
         if ((mdata->header.cputype == BFD_MACH_O_CPU_TYPE_I386)
   	  && (cmd->flavours[i].flavour
! 	      == (unsigned long) BFD_MACH_O_x86_THREAD_STATE32))
   	{
   	  unsigned char buf[4];

*************** bfd_mach_o_scan (bfd *abfd,
*** 1761,1768 ****
     mdata->header = *header;
     mdata->symbols = NULL;

!   abfd->flags = (abfd->xvec->object_flags
! 		 | (abfd->flags & (BFD_IN_MEMORY | BFD_IO_FUNCS)));
     abfd->tdata.mach_o_data = mdata;

     bfd_mach_o_convert_architecture (header->cputype, header- 
 >cpusubtype,
--- 1856,1876 ----
     mdata->header = *header;
     mdata->symbols = NULL;

!   abfd->flags = abfd->flags & (BFD_IN_MEMORY | BFD_IO_FUNCS);
!   switch (header->filetype)
!     {
!     case BFD_MACH_O_MH_OBJECT:
!       abfd->flags |= HAS_RELOC;
!       break;
!     case BFD_MACH_O_MH_EXECUTE:
!       abfd->flags |= EXEC_P;
!       break;
!     case BFD_MACH_O_MH_DYLIB:
!     case BFD_MACH_O_MH_BUNDLE:
!       abfd->flags |= DYNAMIC;
!       break;
!     }
!
     abfd->tdata.mach_o_data = mdata;

     bfd_mach_o_convert_architecture (header->cputype, header- 
 >cpusubtype,
*************** typedef struct mach_o_fat_archentry
*** 1938,1944 ****
     unsigned long offset;
     unsigned long size;
     unsigned long align;
-   bfd *abfd;
   } mach_o_fat_archentry;

   typedef struct mach_o_fat_data_struct
--- 2046,2051 ----
*************** bfd_mach_o_archive_p (bfd *abfd)
*** 1984,1990 ****
         adata->archentries[i].offset = bfd_getb32 (buf + 8);
         adata->archentries[i].size = bfd_getb32 (buf + 12);
         adata->archentries[i].align = bfd_getb32 (buf + 16);
-       adata->archentries[i].abfd = NULL;
       }

     abfd->tdata.mach_o_fat_data = adata;
--- 2091,2096 ----
*************** bfd_mach_o_openr_next_archived_file (bfd
*** 2003,2008 ****
--- 2109,2119 ----
     mach_o_fat_data_struct *adata;
     mach_o_fat_archentry *entry = NULL;
     unsigned long i;
+   bfd *nbfd;
+   const char *arch_name;
+   enum bfd_architecture arch_type;
+   unsigned long arch_subtype;
+   char *s = NULL;

     adata = (mach_o_fat_data_struct *) archive->tdata.mach_o_fat_data;
     BFD_ASSERT (adata != NULL);
*************** bfd_mach_o_openr_next_archived_file (bfd
*** 2014,2020 ****
       {
         for (i = 0; i < adata->nfat_arch; i++)
   	{
! 	  if (adata->archentries[i].abfd == prev)
   	    break;
   	}

--- 2125,2131 ----
       {
         for (i = 0; i < adata->nfat_arch; i++)
   	{
! 	  if (adata->archentries[i].offset == prev->origin)
   	    break;
   	}

*************** bfd_mach_o_openr_next_archived_file (bfd
*** 2034,2058 ****
       }

     entry = &adata->archentries[i];
!   if (entry->abfd == NULL)
!     {
!       bfd *nbfd = _bfd_new_bfd_contained_in (archive);
!       char *s = NULL;

!       if (nbfd == NULL)
! 	return NULL;

!       nbfd->origin = entry->offset;
!       s = bfd_malloc (strlen (archive->filename) + 1);
!       if (s == NULL)
! 	return NULL;
!       strcpy (s, archive->filename);
!       nbfd->filename = s;
!       nbfd->iostream = NULL;
!       entry->abfd = nbfd;
!     }

!   return entry->abfd;
   }

   int
--- 2145,2167 ----
       }

     entry = &adata->archentries[i];
!   nbfd = _bfd_new_bfd_contained_in (archive);
!   if (nbfd == NULL)
!     return NULL;

!   nbfd->origin = entry->offset;

!   bfd_mach_o_convert_architecture (entry->cputype, entry->cpusubtype,
! 				   &arch_type, &arch_subtype);
!   arch_name = bfd_printable_arch_mach (arch_type, arch_subtype);
!   s = bfd_malloc (strlen (arch_name) + 1);
!   if (s == NULL)
!     return NULL;
!   strcpy (s, arch_name);
!   nbfd->filename = s;
!   nbfd->iostream = NULL;

!   return nbfd;
   }

   int
*************** bfd_mach_o_stack_addr (enum bfd_mach_o_c
*** 2161,2166 ****
--- 2270,2416 ----
       }
   }

+ static bfd_boolean
+ bfd_mach_o_bfd_print_private_bfd_data (bfd *abfd, PTR ptr)
+ {
+   bfd_mach_o_data_struct *mdata = abfd->tdata.mach_o_data;
+   FILE *file = (FILE *) ptr;
+   unsigned int i, j;
+   unsigned int sec_nbr = 0;
+
+   fprintf (file, _("Segments and Sections:\n"));
+   fprintf (file, _(" #: Segment name     Section name     Address 
\n"));
+
+   for (i = 0; i < mdata->header.ncmds; i++)
+     {
+       bfd_mach_o_segment_command *seg;
+
+       if (mdata->commands[i].type != BFD_MACH_O_LC_SEGMENT
+ 	  && mdata->commands[i].type != BFD_MACH_O_LC_SEGMENT_64)
+ 	continue;
+
+       seg = &mdata->commands[i].command.segment;
+
+       fprintf (file, "[Segment %-16s ", seg->segname);
+       fprintf_vma (file, seg->vmaddr);
+       fprintf (file, "-");
+       fprintf_vma  (file, seg->vmaddr + seg->vmsize - 1);
+       fputc (' ', file);
+       fputc (seg->initprot & BFD_MACH_O_PROT_READ ? 'r' : '-', file);
+       fputc (seg->initprot & BFD_MACH_O_PROT_WRITE ? 'w' : '-', file);
+       fputc (seg->initprot & BFD_MACH_O_PROT_EXECUTE ? 'x' : '-',  
file);
+       fprintf (file, "]\n");
+       for (j = 0; j < seg->nsects; j++)
+ 	{
+ 	  bfd_mach_o_section *sec = &seg->sections[j];
+ 	  fprintf (file, "%02u: %-16s %-16s ", ++sec_nbr,
+ 		   sec->segname, sec->sectname);
+ 	  fprintf_vma (file, sec->addr);
+ 	  fprintf (file, " ");
+ 	  fprintf_vma  (file, sec->size);
+ 	  fprintf (file, " %08lx\n", sec->flags);
+ 	}
+     }
+
+   for (i = 0; i < mdata->header.ncmds; i++)
+     {
+       bfd_mach_o_load_command *cmd = &mdata->commands[i];
+
+       switch (cmd->type)
+ 	{
+ 	case BFD_MACH_O_LC_SEGMENT:
+ 	case BFD_MACH_O_LC_SEGMENT_64:
+ 	  break;
+ 	case BFD_MACH_O_LC_UUID:
+ 	  {
+ 	    bfd_mach_o_uuid_command *uuid = &cmd->command.uuid;
+ 	    unsigned int i;
+
+ 	    fprintf (file, "\n"
+ 		     "UUID:");
+ 	    for (i = 0; i < sizeof (uuid->uuid); i++)
+ 	      fprintf (file, " %02x", uuid->uuid[i]);
+ 	    fputc ('\n', file);
+ 	  }
+ 	  break;
+ 	case BFD_MACH_O_LC_LOAD_DYLIB:
+ 	  {
+ 	    bfd_mach_o_dylib_command *dylib = &cmd->command.dylib;
+ 	    bfd_byte *data = NULL;
+
+ 	    if (! bfd_malloc_and_get_section (abfd, dylib->section, &data))
+ 	      {
+ 		if (data != NULL)
+ 		  free (data);
+ 		break;
+ 	      }
+ 	    fprintf (file, "\n"
+ 		     "LOAD_DYLIB: %s\n",
+ 		     data + dylib->name_offset - cmd->offset - 8);
+ 	    fprintf (file, "            time stamp: 0x%08lx\n",
+ 		     dylib->timestamp);
+ 	    fprintf (file, "       current version: 0x%08lx\n",
+ 		     dylib->current_version);
+ 	    fprintf (file, "  comptibility version: 0x%08lx\n",
+ 		     dylib->compatibility_version);
+ 	    free (data);
+ 	    break;
+ 	  }
+ 	case BFD_MACH_O_LC_LOAD_DYLINKER:
+ 	  {
+ 	    bfd_mach_o_dylinker_command *linker = &cmd->command.dylinker;
+ 	    bfd_byte *data = NULL;
+
+ 	    if (! bfd_malloc_and_get_section (abfd, linker->section, &data))
+ 	      {
+ 		if (data != NULL)
+ 		  free (data);
+ 		break;
+ 	      }
+ 	    fprintf (file, "\n"
+ 		     "LOAD_DYLINKER: %s\n",
+ 		     data + linker->name_offset - cmd->offset - 8);
+ 	    free (data);
+ 	    break;
+ 	  }
+ 	case BFD_MACH_O_LC_SYMTAB:
+ 	  {
+ 	    bfd_mach_o_symtab_command *symtab = &cmd->command.symtab;
+ 	    fprintf (file, "\n"
+ 		     "LC_SYMTAB: nsyms: %lu, strsize: %lu\n",
+ 		     symtab->nsyms, symtab->strsize);
+ 	    break;
+ 	  }
+ 	case BFD_MACH_O_LC_DYSYMTAB:
+ 	  {
+ 	    bfd_mach_o_dysymtab_command *dysymtab = &cmd->command.dysymtab;
+ 	    fprintf (file, "\n"
+ 		     "LC_DYSYMTAB:\n"
+ 		     "      local symbols: index: %lu  number: %lu\n",
+ 		     dysymtab->ilocalsym, dysymtab->nlocalsym);
+ 	    fprintf (file,
+ 		     "   external symbols: index: %lu  number: %lu\n",
+ 		     dysymtab->iextdefsym, dysymtab->nextdefsym);
+ 	    fprintf (file,
+ 		     "  undefined symbols: index: %lu  number: %lu\n",
+ 		     dysymtab->iundefsym, dysymtab->nundefsym);
+ 	    fprintf (file,
+ 		     "               ntoc: offset: %lu  number: %lu\n",
+ 		     dysymtab->tocoff, dysymtab->ntoc);
+ 	    fprintf (file,
+ 		     "       module table: offset: %lu  number: %lu\n",
+ 		     dysymtab->modtaboff, dysymtab->nmodtab);
+ 	    break;
+ 	  }
+ 	default:
+ 	  fprintf (file, "LC_%d\n", cmd->type);
+ 	  break;
+ 	}
+     }
+
+   return TRUE;
+ }
+
   int
   bfd_mach_o_core_fetch_environment (bfd *abfd,
   				   unsigned char **rbuf,
Index: bfd/mach-o.h
===================================================================
RCS file: /cvs/src/src/bfd/mach-o.h,v
retrieving revision 1.10
diff -c -p -r1.10 mach-o.h
*** bfd/mach-o.h	5 Sep 2008 08:07:54 -0000	1.10
--- bfd/mach-o.h	28 Oct 2008 15:41:26 -0000
***************
*** 30,38 ****
   #define BFD_MACH_O_N_EXT   0x01	/* External symbol bit, set for  
external symbols.  */
   #define BFD_MACH_O_N_UNDF  0x00	/* Undefined, n_sect == NO_SECT.  */
   #define BFD_MACH_O_N_ABS   0x02	/* Absolute, n_sect == NO_SECT.  */
- #define BFD_MACH_O_N_SECT  0x0e	/* Defined in section number  
n_sect.  */
- #define BFD_MACH_O_N_PBUD  0x0c /* Prebound undefined (defined in a  
dylib).  */
   #define BFD_MACH_O_N_INDR  0x0a	/* Indirect.  */

   typedef enum bfd_mach_o_ppc_thread_flavour
   {
--- 30,44 ----
   #define BFD_MACH_O_N_EXT   0x01	/* External symbol bit, set for  
external symbols.  */
   #define BFD_MACH_O_N_UNDF  0x00	/* Undefined, n_sect == NO_SECT.  */
   #define BFD_MACH_O_N_ABS   0x02	/* Absolute, n_sect == NO_SECT.  */
   #define BFD_MACH_O_N_INDR  0x0a	/* Indirect.  */
+ #define BFD_MACH_O_N_PBUD  0x0c /* Prebound undefined (defined in a  
dylib).  */
+ #define BFD_MACH_O_N_SECT  0x0e	/* Defined in section number  
n_sect.  */
+
+ #define BFD_MACH_O_NO_SECT 0
+
+ #define BFD_MACH_O_SYM_NTYPE(SYM) (((SYM)->udata.i >> 24) & 0xff)
+ #define BFD_MACH_O_SYM_NSECT(SYM) (((SYM)->udata.i >> 16) & 0xff)
+ #define BFD_MACH_O_SYM_NDESC(SYM) ((SYM)->udata.i & 0xffff)

   typedef enum bfd_mach_o_ppc_thread_flavour
   {
*************** typedef enum bfd_mach_o_ppc_thread_flavo
*** 44,69 ****
   }
   bfd_mach_o_ppc_thread_flavour;

   typedef enum bfd_mach_o_i386_thread_flavour
   {
!   BFD_MACH_O_i386_NEW_THREAD_STATE = 1,
!   BFD_MACH_O_i386_FLOAT_STATE = 2,
!   BFD_MACH_O_i386_ISA_PORT_MAP_STATE = 3,
!   BFD_MACH_O_i386_V86_ASSIST_STATE = 4,
!   BFD_MACH_O_i386_REGS_SEGS_STATE = 5,
!   BFD_MACH_O_i386_THREAD_SYSCALL_STATE = 6,
!   BFD_MACH_O_i386_SAVED_STATE = 8,
!   BFD_MACH_O_i386_THREAD_STATE = -1,
!   BFD_MACH_O_i386_THREAD_FPSTATE = -2,
!   BFD_MACH_O_i386_THREAD_EXCEPTSTATE = -3,
!   BFD_MACH_O_i386_THREAD_CTHREADSTATE = -4,
     BFD_MACH_O_x86_THREAD_STATE64 = 4,
     BFD_MACH_O_x86_FLOAT_STATE64 = 5,
     BFD_MACH_O_x86_EXCEPTION_STATE64 = 6,
     BFD_MACH_O_x86_THREAD_STATE = 7,
     BFD_MACH_O_x86_FLOAT_STATE = 8,
     BFD_MACH_O_x86_EXCEPTION_STATE = 9,
!   BFD_MACH_O_i386_THREAD_STATE_NONE = 10,
   }
   bfd_mach_o_i386_thread_flavour;

--- 50,71 ----
   }
   bfd_mach_o_ppc_thread_flavour;

+ /* Defined in <mach/i386/thread_status.h> */
   typedef enum bfd_mach_o_i386_thread_flavour
   {
!   BFD_MACH_O_x86_THREAD_STATE32 = 1,
!   BFD_MACH_O_x86_FLOAT_STATE32 = 2,
!   BFD_MACH_O_x86_EXCEPTION_STATE32 = 3,
     BFD_MACH_O_x86_THREAD_STATE64 = 4,
     BFD_MACH_O_x86_FLOAT_STATE64 = 5,
     BFD_MACH_O_x86_EXCEPTION_STATE64 = 6,
     BFD_MACH_O_x86_THREAD_STATE = 7,
     BFD_MACH_O_x86_FLOAT_STATE = 8,
     BFD_MACH_O_x86_EXCEPTION_STATE = 9,
!   BFD_MACH_O_x86_DEBUG_STATE32 = 10,
!   BFD_MACH_O_x86_DEBUG_STATE64 = 11,
!   BFD_MACH_O_x86_DEBUG_STATE = 12,
!   BFD_MACH_O_THREAD_STATE_NONE = 13
   }
   bfd_mach_o_i386_thread_flavour;

*************** typedef enum bfd_mach_o_load_command_typ
*** 99,107 ****
     BFD_MACH_O_LC_LOAD_WEAK_DYLIB = 0x18,
     BFD_MACH_O_LC_SEGMENT_64 = 0x19,	/* 64-bit segment of this file  
to be
                                              mapped.  */
!   BFD_MACH_O_LC_ROUTINES_64 = 0x1a,      /* Address of the dyld init  
routine
!                                             in a dylib.  */
!   BFD_MACH_O_LC_UUID = 0x1b              /* 128-bit UUID of the  
executable.  */
   }
   bfd_mach_o_load_command_type;

--- 101,111 ----
     BFD_MACH_O_LC_LOAD_WEAK_DYLIB = 0x18,
     BFD_MACH_O_LC_SEGMENT_64 = 0x19,	/* 64-bit segment of this file  
to be
                                              mapped.  */
!   BFD_MACH_O_LC_ROUTINES_64 = 0x1a,     /* Address of the dyld init  
routine
!                                            in a dylib.  */
!   BFD_MACH_O_LC_UUID = 0x1b,            /* 128-bit UUID of the  
executable.  */
!   BFD_MACH_O_LC_RPATH = 0x1c,		/* Run path addiions.  */
!   BFD_MACH_O_LC_CODE_SIGNATURE = 0x1d	/* Local of code signature.  */
   }
   bfd_mach_o_load_command_type;

*************** typedef enum bfd_mach_o_section_type
*** 188,193 ****
--- 192,226 ----
   }
   bfd_mach_o_section_type;

+ /* The flags field of a section structure is separated into two  
parts a section
+    type and section attributes.  The section types are mutually  
exclusive (it
+    can only have one type) but the section attributes are not (it  
may have more
+    than one attribute).  */
+
+ #define BFD_MACH_O_SECTION_TYPE_MASK        0x000000ff
+
+ /* Constants for the section attributes part of the flags field of a  
section
+    structure.  */
+ #define BFD_MACH_O_SECTION_ATTRIBUTES_MASK  0xffffff00
+ /* System setable attributes.  */
+ #define BFD_MACH_O_SECTION_ATTRIBUTES_SYS   0x00ffff00
+ /* User attributes.  */
+ #define BFD_MACH_O_SECTION_ATTRIBUTES_USR   0xff000000
+
+ /* Section has local relocation entries.  */
+ #define BFD_MACH_O_S_ATTR_LOC_RELOC         0x00000100
+
+ /* Section has external relocation entries.  */
+ #define BFD_MACH_O_S_ATTR_EXT_RELOC         0x00000200
+
+ /* Section contains some machine instructions.  */
+ #define BFD_MACH_O_S_ATTR_SOME_INSTRUCTIONS 0x00004000
+
+ #define BFD_MACH_O_S_ATTR_DEBUG             0x02000000
+
+ /* Section contains only true machine instructions.  */
+ #define BFD_MACH_O_S_ATTR_PURE_INSTRUCTIONS 0x80000000
+
   typedef unsigned long bfd_mach_o_cpu_subtype;

   typedef struct bfd_mach_o_header
*************** bfd_mach_o_section;
*** 226,238 ****

   typedef struct bfd_mach_o_segment_command
   {
!   char segname[16];
     bfd_vma vmaddr;
     bfd_vma vmsize;
     bfd_vma fileoff;
     unsigned long filesize;
!   unsigned long maxprot;
!   unsigned long initprot;
     unsigned long nsects;
     unsigned long flags;
     bfd_mach_o_section *sections;
--- 259,271 ----

   typedef struct bfd_mach_o_segment_command
   {
!   char segname[16 + 1];
     bfd_vma vmaddr;
     bfd_vma vmsize;
     bfd_vma fileoff;
     unsigned long filesize;
!   unsigned long maxprot;	/* Maximum permitted protection.  */
!   unsigned long initprot;	/* Initial protection.  */
     unsigned long nsects;
     unsigned long flags;
     bfd_mach_o_section *sections;
*************** typedef struct bfd_mach_o_segment_comman
*** 240,245 ****
--- 273,283 ----
   }
   bfd_mach_o_segment_command;

+ /* Protection flags.  */
+ #define BFD_MACH_O_PROT_READ    0x01
+ #define BFD_MACH_O_PROT_WRITE   0x02
+ #define BFD_MACH_O_PROT_EXECUTE 0x04
+
   typedef struct bfd_mach_o_symtab_command
   {
     unsigned long symoff;
*************** bfd_mach_o_dysymtab_command;
*** 399,406 ****
      removed.  In which case it has the value INDIRECT_SYMBOL_LOCAL.   
If the
      symbol was also absolute INDIRECT_SYMBOL_ABS is or'ed with  
that.  */

! #define INDIRECT_SYMBOL_LOCAL 0x80000000
! #define INDIRECT_SYMBOL_ABS   0x40000000

   typedef struct bfd_mach_o_thread_flavour
   {
--- 437,444 ----
      removed.  In which case it has the value INDIRECT_SYMBOL_LOCAL.   
If the
      symbol was also absolute INDIRECT_SYMBOL_ABS is or'ed with  
that.  */

! #define BFD_MACH_O_INDIRECT_SYMBOL_LOCAL 0x80000000
! #define BFD_MACH_O_INDIRECT_SYMBOL_ABS   0x40000000

   typedef struct bfd_mach_o_thread_flavour
   {
*************** typedef struct bfd_mach_o_prebound_dylib
*** 452,457 ****
--- 490,504 ----
   }
   bfd_mach_o_prebound_dylib_command;

+ typedef struct bfd_mach_o_uuid_command
+ {
+   unsigned long cmd;                 /* LC_PREBOUND_DYLIB.  */
+   unsigned long cmdsize;             /* Includes uuid.  */
+   unsigned char uuid[16];	     /* Uuid.  */
+   asection *section;
+ }
+ bfd_mach_o_uuid_command;
+
   typedef struct bfd_mach_o_load_command
   {
     bfd_mach_o_load_command_type type;
*************** typedef struct bfd_mach_o_load_command
*** 467,472 ****
--- 514,520 ----
       bfd_mach_o_dylib_command dylib;
       bfd_mach_o_dylinker_command dylinker;
       bfd_mach_o_prebound_dylib_command prebound_dylib;
+     bfd_mach_o_uuid_command uuid;
     }
     command;
   }
*************** typedef struct mach_o_data_struct
*** 484,489 ****
--- 532,539 ----
   }
   mach_o_data_struct;

+ #define bfd_get_mach_o_data(abfd) ((abfd)->tdata.mach_o_data)
+
   typedef struct mach_o_data_struct bfd_mach_o_data_struct;

   bfd_boolean        bfd_mach_o_valid  (bfd *);
Index: binutils/objdump.c
===================================================================
RCS file: /cvs/src/src/binutils/objdump.c,v
retrieving revision 1.146
diff -c -p -r1.146 objdump.c
*** binutils/objdump.c	28 Aug 2008 16:05:03 -0000	1.146
--- binutils/objdump.c	28 Oct 2008 15:41:26 -0000
*************** load_debug_section (enum dwarf_section_d
*** 2083,2101 ****
       return 0;
     section_is_compressed = section->name == section->compressed_name;

!   /* Compute a bias to be added to offsets found within the DWARF  
debug
!      information.  These offsets are meant to be relative to the  
start of
!      the dwarf section, and hence the bias should be 0.  For MACH-O  
however
!      a dwarf section is really just a region of a much larger  
section and so
!      the bias is the address of the start of that area within the  
larger
!      section.  This test is important for PE and COFF based targets  
which
!      use DWARF debug information, since unlike ELF, they do not  
allow the
!      dwarf sections to be placed at address 0.  */
!   if (bfd_get_flavour (abfd) == bfd_target_mach_o_flavour)
!     section->address = bfd_get_section_vma (abfd, sec);
!   else
!     section->address = 0;
!
     section->size = bfd_get_section_size (sec);
     section->start = xmalloc (section->size);

--- 2083,2089 ----
       return 0;
     section_is_compressed = section->name == section->compressed_name;

!   section->address = 0;
     section->size = bfd_get_section_size (sec);
     section->start = xmalloc (section->size);

*************** dump_dwarf_section (bfd *abfd, asection
*** 2178,2263 ****
         }
   }

- static const char *mach_o_uncompressed_dwarf_sections [] = {
-   "LC_SEGMENT.__DWARFA.__debug_abbrev",		/* .debug_abbrev */
-   "LC_SEGMENT.__DWARFA.__debug_aranges",	/* .debug_aranges */
-   "LC_SEGMENT.__DWARFA.__debug_frame",		/* .debug_frame */
-   "LC_SEGMENT.__DWARFA.__debug_info",		/* .debug_info */
-   "LC_SEGMENT.__DWARFA.__debug_line",		/* .debug_line */
-   "LC_SEGMENT.__DWARFA.__debug_pubnames",	/* .debug_pubnames */
-   ".eh_frame",					/* .eh_frame */
-   "LC_SEGMENT.__DWARFA.__debug_macinfo",	/* .debug_macinfo */
-   "LC_SEGMENT.__DWARFA.__debug_str",		/* .debug_str */
-   "LC_SEGMENT.__DWARFA.__debug_loc",		/* .debug_loc */
-   "LC_SEGMENT.__DWARFA.__debug_pubtypes",	/* .debug_pubtypes */
-   "LC_SEGMENT.__DWARFA.__debug_ranges",		/* .debug_ranges */
-   "LC_SEGMENT.__DWARFA.__debug_static_func",	/* .debug_static_func */
-   "LC_SEGMENT.__DWARFA.__debug_static_vars",	/* .debug_static_vars */
-   "LC_SEGMENT.__DWARFA.__debug_types",		/* .debug_types */
-   "LC_SEGMENT.__DWARFA.__debug_weaknames"	/* .debug_weaknames */
- };
-
- static const char *mach_o_compressed_dwarf_sections [] = {
-   "LC_SEGMENT.__DWARFA.__zdebug_abbrev",	/* .zdebug_abbrev */
-   "LC_SEGMENT.__DWARFA.__zdebug_aranges",	/* .zdebug_aranges */
-   "LC_SEGMENT.__DWARFA.__zdebug_frame",		/* .zdebug_frame */
-   "LC_SEGMENT.__DWARFA.__zdebug_info",		/* .zdebug_info */
-   "LC_SEGMENT.__DWARFA.__zdebug_line",		/* .zdebug_line */
-   "LC_SEGMENT.__DWARFA.__zdebug_pubnames",	/* .zdebug_pubnames */
-   ".eh_frame",					/* .eh_frame */
-   "LC_SEGMENT.__DWARFA.__zdebug_macinfo",	/* .zdebug_macinfo */
-   "LC_SEGMENT.__DWARFA.__zdebug_str",		/* .zdebug_str */
-   "LC_SEGMENT.__DWARFA.__zdebug_loc",		/* .zdebug_loc */
-   "LC_SEGMENT.__DWARFA.__zdebug_pubtypes",	/* .zdebug_pubtypes */
-   "LC_SEGMENT.__DWARFA.__zdebug_ranges",	/* .zdebug_ranges */
-   "LC_SEGMENT.__DWARFA.__zdebug_static_func",	/* .zdebug_static_func  
*/
-   "LC_SEGMENT.__DWARFA.__zdebug_static_vars",	/* .zdebug_static_vars  
*/
-   "LC_SEGMENT.__DWARFA.__zdebug_types",		/* .zdebug_types */
-   "LC_SEGMENT.__DWARFA.__zdebug_weaknames"	/* .zdebug_weaknames */
- };
-
- static const char *generic_uncompressed_dwarf_sections [max];
- static const char *generic_compressed_dwarf_sections [max];
-
- static void
- check_mach_o_dwarf (bfd *abfd)
- {
-   static enum bfd_flavour old_flavour = bfd_target_unknown_flavour;
-   enum bfd_flavour current_flavour = bfd_get_flavour (abfd);
-   enum dwarf_section_display_enum i;
-
-   if (generic_uncompressed_dwarf_sections [0] == NULL)
-     for (i = 0; i < max; i++)
-       {
-         generic_uncompressed_dwarf_sections [i]
-             = debug_displays[i].section.uncompressed_name;
-         generic_compressed_dwarf_sections [i]
-             = debug_displays[i].section.compressed_name;
-       }
-
-   if (old_flavour != current_flavour)
-     {
-       if (current_flavour == bfd_target_mach_o_flavour)
- 	for (i = 0; i < max; i++)
-           {
-             debug_displays[i].section.uncompressed_name
-                 = mach_o_uncompressed_dwarf_sections [i];
-             debug_displays[i].section.compressed_name
-                 = mach_o_compressed_dwarf_sections [i];
-           }
-       else if (old_flavour == bfd_target_mach_o_flavour)
- 	for (i = 0; i < max; i++)
-           {
-             debug_displays[i].section.uncompressed_name
-                 = generic_uncompressed_dwarf_sections [i];
-             debug_displays[i].section.compressed_name
-                 = generic_compressed_dwarf_sections [i];
-           }
-
-       old_flavour = current_flavour;
-     }
- }
-
   /* Dump the dwarf debugging information.  */

   static void
--- 2166,2171 ----
*************** dump_dwarf (bfd *abfd)
*** 2276,2283 ****
     else
       abort ();

-   check_mach_o_dwarf (abfd);
-
     if (bfd_get_flavour (abfd) == bfd_target_elf_flavour)
       {
         const struct elf_backend_data *bed = get_elf_backend_data  
(abfd);
--- 2184,2189 ----
*************** print_section_stabs (bfd *abfd,
*** 2377,2391 ****
         value = bfd_h_get_32 (abfd, stabp + VALOFF);

         printf ("\n%-6d ", i);
!       /* Either print the stab name, or, if unnamed, print its number
! 	 again (makes consistent formatting for tools like awk).  */
!       name = bfd_get_stab_name (type);
!       if (name != NULL)
! 	printf ("%-6s", name);
!       else if (type == N_UNDF)
! 	printf ("HdrSym");
         else
! 	printf ("%-6d", type);
         printf (" %-6d %-6d ", other, desc);
         bfd_printf_vma (abfd, value);
         printf (" %-6lu", strx);
--- 2283,2302 ----
         value = bfd_h_get_32 (abfd, stabp + VALOFF);

         printf ("\n%-6d ", i);
!       if ((type & 0xe0) == 0)
! 	printf ("%02x    ", type);
         else
! 	{
! 	  /* Either print the stab name, or, if unnamed, print its number
! 	     again (makes consistent formatting for tools like awk).  */
! 	  name = bfd_get_stab_name (type);
! 	  if (name != NULL)
! 	    printf ("%-6s", name);
! 	  else if (type == N_UNDF)
! 	    printf ("HdrSym");
! 	  else
! 	    printf ("%-6d", type);
! 	}
         printf (" %-6d %-6d ", other, desc);
         bfd_printf_vma (abfd, value);
         printf (" %-6lu", strx);



More information about the Binutils mailing list