1 /* od-macho.c -- dump information about an Mach-O object file.
2 Copyright (C) 2011-2024 Free Software Foundation, Inc.
3 Written by Tristan Gingold, Adacore.
5 This file is part of GNU Binutils.
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 3, or (at your option)
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.
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, 51 Franklin Street - Fifth Floor, Boston,
20 MA 02110-1301, USA. */
25 #include "safe-ctype.h"
26 #include "libiberty.h"
34 #include "mach-o/external.h"
35 #include "mach-o/codesign.h"
36 #include "mach-o/unwind.h"
38 /* Index of the options in the options[] array. */
43 #define OPT_DYSYMTAB 4
44 #define OPT_CODESIGN 5
45 #define OPT_SEG_SPLIT_INFO 6
46 #define OPT_COMPACT_UNWIND 7
47 #define OPT_FUNCTION_STARTS 8
48 #define OPT_DATA_IN_CODE 9
49 #define OPT_TWOLEVEL_HINTS 10
50 #define OPT_DYLD_INFO 11
52 /* List of actions. */
53 static struct objdump_private_option options
[] =
61 { "seg_split_info", 0 },
62 { "compact_unwind", 0 },
63 { "function_starts", 0 },
64 { "data_in_code", 0 },
65 { "twolevel_hints", 0 },
73 mach_o_help (FILE *stream
)
77 header Display the file header\n\
78 section Display the segments and sections commands\n\
79 map Display the section map\n\
80 load Display the load commands\n\
81 dysymtab Display the dynamic symbol table\n\
82 codesign Display code signature\n\
83 seg_split_info Display segment split info\n\
84 compact_unwind Display compact unwinding info\n\
85 function_starts Display start address of functions\n\
86 data_in_code Display data in code entries\n\
87 twolevel_hints Display the two-level namespace lookup hints table\n\
88 dyld_info Display dyld information\n\
92 /* Return TRUE if ABFD is handled. */
95 mach_o_filter (bfd
*abfd
)
97 return bfd_get_flavour (abfd
) == bfd_target_mach_o_flavour
;
100 static const bfd_mach_o_xlat_name bfd_mach_o_cpu_name
[] =
102 { "vax", BFD_MACH_O_CPU_TYPE_VAX
},
103 { "mc680x0", BFD_MACH_O_CPU_TYPE_MC680x0
},
104 { "i386", BFD_MACH_O_CPU_TYPE_I386
},
105 { "mips", BFD_MACH_O_CPU_TYPE_MIPS
},
106 { "mc98000", BFD_MACH_O_CPU_TYPE_MC98000
},
107 { "hppa", BFD_MACH_O_CPU_TYPE_HPPA
},
108 { "arm", BFD_MACH_O_CPU_TYPE_ARM
},
109 { "mc88000", BFD_MACH_O_CPU_TYPE_MC88000
},
110 { "sparc", BFD_MACH_O_CPU_TYPE_SPARC
},
111 { "alpha", BFD_MACH_O_CPU_TYPE_ALPHA
},
112 { "powerpc", BFD_MACH_O_CPU_TYPE_POWERPC
},
113 { "powerpc_64", BFD_MACH_O_CPU_TYPE_POWERPC_64
},
114 { "x86_64", BFD_MACH_O_CPU_TYPE_X86_64
},
115 { "arm64", BFD_MACH_O_CPU_TYPE_ARM64
},
119 static const bfd_mach_o_xlat_name bfd_mach_o_filetype_name
[] =
121 { "object", BFD_MACH_O_MH_OBJECT
},
122 { "execute", BFD_MACH_O_MH_EXECUTE
},
123 { "fvmlib", BFD_MACH_O_MH_FVMLIB
},
124 { "core", BFD_MACH_O_MH_CORE
},
125 { "preload", BFD_MACH_O_MH_PRELOAD
},
126 { "dylib", BFD_MACH_O_MH_DYLIB
},
127 { "dylinker", BFD_MACH_O_MH_DYLINKER
},
128 { "bundle", BFD_MACH_O_MH_BUNDLE
},
129 { "dylib_stub", BFD_MACH_O_MH_DYLIB_STUB
},
130 { "dym", BFD_MACH_O_MH_DSYM
},
131 { "kext_bundle", BFD_MACH_O_MH_KEXT_BUNDLE
},
135 static const bfd_mach_o_xlat_name bfd_mach_o_header_flags_name
[] =
137 { "noundefs", BFD_MACH_O_MH_NOUNDEFS
},
138 { "incrlink", BFD_MACH_O_MH_INCRLINK
},
139 { "dyldlink", BFD_MACH_O_MH_DYLDLINK
},
140 { "bindatload", BFD_MACH_O_MH_BINDATLOAD
},
141 { "prebound", BFD_MACH_O_MH_PREBOUND
},
142 { "split_segs", BFD_MACH_O_MH_SPLIT_SEGS
},
143 { "lazy_init", BFD_MACH_O_MH_LAZY_INIT
},
144 { "twolevel", BFD_MACH_O_MH_TWOLEVEL
},
145 { "force_flat", BFD_MACH_O_MH_FORCE_FLAT
},
146 { "nomultidefs", BFD_MACH_O_MH_NOMULTIDEFS
},
147 { "nofixprebinding", BFD_MACH_O_MH_NOFIXPREBINDING
},
148 { "prebindable", BFD_MACH_O_MH_PREBINDABLE
},
149 { "allmodsbound", BFD_MACH_O_MH_ALLMODSBOUND
},
150 { "subsections_via_symbols", BFD_MACH_O_MH_SUBSECTIONS_VIA_SYMBOLS
},
151 { "canonical", BFD_MACH_O_MH_CANONICAL
},
152 { "weak_defines", BFD_MACH_O_MH_WEAK_DEFINES
},
153 { "binds_to_weak", BFD_MACH_O_MH_BINDS_TO_WEAK
},
154 { "allow_stack_execution", BFD_MACH_O_MH_ALLOW_STACK_EXECUTION
},
155 { "root_safe", BFD_MACH_O_MH_ROOT_SAFE
},
156 { "setuid_safe", BFD_MACH_O_MH_SETUID_SAFE
},
157 { "no_reexported_dylibs", BFD_MACH_O_MH_NO_REEXPORTED_DYLIBS
},
158 { "pie", BFD_MACH_O_MH_PIE
},
159 { "dead_strippable_dylib", BFD_MACH_O_MH_DEAD_STRIPPABLE_DYLIB
},
160 { "has_tlv", BFD_MACH_O_MH_HAS_TLV_DESCRIPTORS
},
161 { "no_heap_execution", BFD_MACH_O_MH_NO_HEAP_EXECUTION
},
162 { "app_extension_safe", BFD_MACH_O_MH_APP_EXTENSION_SAFE
},
166 static const bfd_mach_o_xlat_name bfd_mach_o_load_command_name
[] =
168 { "segment", BFD_MACH_O_LC_SEGMENT
},
169 { "symtab", BFD_MACH_O_LC_SYMTAB
},
170 { "symseg", BFD_MACH_O_LC_SYMSEG
},
171 { "thread", BFD_MACH_O_LC_THREAD
},
172 { "unixthread", BFD_MACH_O_LC_UNIXTHREAD
},
173 { "loadfvmlib", BFD_MACH_O_LC_LOADFVMLIB
},
174 { "idfvmlib", BFD_MACH_O_LC_IDFVMLIB
},
175 { "ident", BFD_MACH_O_LC_IDENT
},
176 { "fvmfile", BFD_MACH_O_LC_FVMFILE
},
177 { "prepage", BFD_MACH_O_LC_PREPAGE
},
178 { "dysymtab", BFD_MACH_O_LC_DYSYMTAB
},
179 { "load_dylib", BFD_MACH_O_LC_LOAD_DYLIB
},
180 { "id_dylib", BFD_MACH_O_LC_ID_DYLIB
},
181 { "load_dylinker", BFD_MACH_O_LC_LOAD_DYLINKER
},
182 { "id_dylinker", BFD_MACH_O_LC_ID_DYLINKER
},
183 { "prebound_dylib", BFD_MACH_O_LC_PREBOUND_DYLIB
},
184 { "routines", BFD_MACH_O_LC_ROUTINES
},
185 { "sub_framework", BFD_MACH_O_LC_SUB_FRAMEWORK
},
186 { "sub_umbrella", BFD_MACH_O_LC_SUB_UMBRELLA
},
187 { "sub_client", BFD_MACH_O_LC_SUB_CLIENT
},
188 { "sub_library", BFD_MACH_O_LC_SUB_LIBRARY
},
189 { "twolevel_hints", BFD_MACH_O_LC_TWOLEVEL_HINTS
},
190 { "prebind_cksum", BFD_MACH_O_LC_PREBIND_CKSUM
},
191 { "load_weak_dylib", BFD_MACH_O_LC_LOAD_WEAK_DYLIB
},
192 { "segment_64", BFD_MACH_O_LC_SEGMENT_64
},
193 { "routines_64", BFD_MACH_O_LC_ROUTINES_64
},
194 { "uuid", BFD_MACH_O_LC_UUID
},
195 { "rpath", BFD_MACH_O_LC_RPATH
},
196 { "code_signature", BFD_MACH_O_LC_CODE_SIGNATURE
},
197 { "segment_split_info", BFD_MACH_O_LC_SEGMENT_SPLIT_INFO
},
198 { "reexport_dylib", BFD_MACH_O_LC_REEXPORT_DYLIB
},
199 { "lazy_load_dylib", BFD_MACH_O_LC_LAZY_LOAD_DYLIB
},
200 { "encryption_info", BFD_MACH_O_LC_ENCRYPTION_INFO
},
201 { "dyld_info", BFD_MACH_O_LC_DYLD_INFO
},
202 { "load_upward_lib", BFD_MACH_O_LC_LOAD_UPWARD_DYLIB
},
203 { "version_min_macosx", BFD_MACH_O_LC_VERSION_MIN_MACOSX
},
204 { "version_min_iphoneos", BFD_MACH_O_LC_VERSION_MIN_IPHONEOS
},
205 { "function_starts", BFD_MACH_O_LC_FUNCTION_STARTS
},
206 { "dyld_environment", BFD_MACH_O_LC_DYLD_ENVIRONMENT
},
207 { "main", BFD_MACH_O_LC_MAIN
},
208 { "data_in_code", BFD_MACH_O_LC_DATA_IN_CODE
},
209 { "source_version", BFD_MACH_O_LC_SOURCE_VERSION
},
210 { "dylib_code_sign_drs", BFD_MACH_O_LC_DYLIB_CODE_SIGN_DRS
},
211 { "encryption_info_64", BFD_MACH_O_LC_ENCRYPTION_INFO_64
},
212 { "linker_options", BFD_MACH_O_LC_LINKER_OPTIONS
},
213 { "linker_optimization_hint", BFD_MACH_O_LC_LINKER_OPTIMIZATION_HINT
},
214 { "version_min_tvos", BFD_MACH_O_LC_VERSION_MIN_TVOS
},
215 { "version_min_watchos", BFD_MACH_O_LC_VERSION_MIN_WATCHOS
},
216 { "note", BFD_MACH_O_LC_NOTE
},
217 { "build_version", BFD_MACH_O_LC_BUILD_VERSION
},
218 { "exports_trie", BFD_MACH_O_LC_DYLD_EXPORTS_TRIE
},
219 { "chained_fixups", BFD_MACH_O_LC_DYLD_CHAINED_FIXUPS
},
223 static const bfd_mach_o_xlat_name bfd_mach_o_thread_x86_name
[] =
225 { "thread_state32", BFD_MACH_O_x86_THREAD_STATE32
},
226 { "float_state32", BFD_MACH_O_x86_FLOAT_STATE32
},
227 { "exception_state32", BFD_MACH_O_x86_EXCEPTION_STATE32
},
228 { "thread_state64", BFD_MACH_O_x86_THREAD_STATE64
},
229 { "float_state64", BFD_MACH_O_x86_FLOAT_STATE64
},
230 { "exception_state64", BFD_MACH_O_x86_EXCEPTION_STATE64
},
231 { "thread_state", BFD_MACH_O_x86_THREAD_STATE
},
232 { "float_state", BFD_MACH_O_x86_FLOAT_STATE
},
233 { "exception_state", BFD_MACH_O_x86_EXCEPTION_STATE
},
234 { "debug_state32", BFD_MACH_O_x86_DEBUG_STATE32
},
235 { "debug_state64", BFD_MACH_O_x86_DEBUG_STATE64
},
236 { "debug_state", BFD_MACH_O_x86_DEBUG_STATE
},
237 { "state_none", BFD_MACH_O_x86_THREAD_STATE_NONE
},
241 static const bfd_mach_o_xlat_name bfd_mach_o_platform_name
[] =
243 { "macos", BFD_MACH_O_PLATFORM_MACOS
},
244 { "ios", BFD_MACH_O_PLATFORM_IOS
},
245 { "tvos", BFD_MACH_O_PLATFORM_TVOS
},
246 { "watchos", BFD_MACH_O_PLATFORM_WATCHOS
},
247 { "bridgeos", BFD_MACH_O_PLATFORM_BRIDGEOS
},
251 static const bfd_mach_o_xlat_name bfd_mach_o_tool_name
[] =
253 { "clang", BFD_MACH_O_TOOL_CLANG
},
254 { "swift", BFD_MACH_O_TOOL_SWIFT
},
255 { "ld", BFD_MACH_O_TOOL_LD
},
260 bfd_mach_o_print_flags (const bfd_mach_o_xlat_name
*table
,
265 for (; table
->name
; table
++)
267 if (table
->val
& val
)
271 printf ("%s", table
->name
);
280 printf ("0x%lx", val
);
288 bfd_mach_o_get_name_or_null (const bfd_mach_o_xlat_name
*table
,
291 for (; table
->name
; table
++)
292 if (table
->val
== val
)
298 bfd_mach_o_get_name (const bfd_mach_o_xlat_name
*table
, unsigned long val
)
300 const char *res
= bfd_mach_o_get_name_or_null (table
, val
);
309 dump_header (bfd
*abfd
)
311 bfd_mach_o_data_struct
*mdata
= bfd_mach_o_get_data (abfd
);
312 bfd_mach_o_header
*h
= &mdata
->header
;
314 fputs (_("Mach-O header:\n"), stdout
);
315 printf (_(" magic : %08lx\n"), h
->magic
);
316 printf (_(" cputype : %08lx (%s)\n"), h
->cputype
,
317 bfd_mach_o_get_name (bfd_mach_o_cpu_name
, h
->cputype
));
318 printf (_(" cpusubtype: %08lx\n"), h
->cpusubtype
);
319 printf (_(" filetype : %08lx (%s)\n"),
321 bfd_mach_o_get_name (bfd_mach_o_filetype_name
, h
->filetype
));
322 printf (_(" ncmds : %08lx (%lu)\n"), h
->ncmds
, h
->ncmds
);
323 printf (_(" sizeofcmds: %08lx (%lu)\n"), h
->sizeofcmds
, h
->sizeofcmds
);
324 printf (_(" flags : %08lx ("), h
->flags
);
325 bfd_mach_o_print_flags (bfd_mach_o_header_flags_name
, h
->flags
);
326 fputs (_(")\n"), stdout
);
327 printf (_(" reserved : %08x\n"), h
->reserved
);
332 disp_segment_prot (unsigned int prot
)
334 putchar (prot
& BFD_MACH_O_PROT_READ
? 'r' : '-');
335 putchar (prot
& BFD_MACH_O_PROT_WRITE
? 'w' : '-');
336 putchar (prot
& BFD_MACH_O_PROT_EXECUTE
? 'x' : '-');
340 dump_section_map (bfd
*abfd
)
342 bfd_mach_o_data_struct
*mdata
= bfd_mach_o_get_data (abfd
);
343 bfd_mach_o_load_command
*cmd
;
344 unsigned int sec_nbr
= 0;
346 fputs (_("Segments and Sections:\n"), stdout
);
347 fputs (_(" #: Segment name Section name Address\n"), stdout
);
349 for (cmd
= mdata
->first_command
; cmd
!= NULL
; cmd
= cmd
->next
)
351 bfd_mach_o_segment_command
*seg
;
352 bfd_mach_o_section
*sec
;
354 if (cmd
->type
!= BFD_MACH_O_LC_SEGMENT
355 && cmd
->type
!= BFD_MACH_O_LC_SEGMENT_64
)
358 seg
= &cmd
->command
.segment
;
360 printf ("[Segment %-16s ", seg
->segname
);
361 bfd_printf_vma (abfd
, seg
->vmaddr
);
363 bfd_printf_vma (abfd
, seg
->vmaddr
+ seg
->vmsize
- 1);
365 disp_segment_prot (seg
->initprot
);
368 for (sec
= seg
->sect_head
; sec
!= NULL
; sec
= sec
->next
)
370 printf ("%02u: %-16s %-16s ", ++sec_nbr
,
371 sec
->segname
, sec
->sectname
);
372 bfd_printf_vma (abfd
, sec
->addr
);
374 bfd_printf_vma (abfd
, sec
->size
);
375 printf (" %08lx\n", sec
->flags
);
381 dump_section_header (bfd
*abfd
, bfd_mach_o_section
*sec
)
383 printf (" Section: %-16s %-16s (bfdname: %s)\n",
384 sec
->sectname
, sec
->segname
, sec
->bfdsection
->name
);
386 bfd_printf_vma (abfd
, sec
->addr
);
388 bfd_printf_vma (abfd
, sec
->size
);
389 printf (" offset: ");
390 bfd_printf_vma (abfd
, sec
->offset
);
392 printf (" align: %ld", sec
->align
);
393 printf (" nreloc: %lu reloff: ", sec
->nreloc
);
394 bfd_printf_vma (abfd
, sec
->reloff
);
396 printf (" flags: %08lx (type: %s", sec
->flags
,
397 bfd_mach_o_get_name (bfd_mach_o_section_type_name
,
398 sec
->flags
& BFD_MACH_O_SECTION_TYPE_MASK
));
400 bfd_mach_o_print_flags (bfd_mach_o_section_attribute_name
,
401 sec
->flags
& BFD_MACH_O_SECTION_ATTRIBUTES_MASK
);
403 switch (sec
->flags
& BFD_MACH_O_SECTION_TYPE_MASK
)
405 case BFD_MACH_O_S_NON_LAZY_SYMBOL_POINTERS
:
406 case BFD_MACH_O_S_LAZY_SYMBOL_POINTERS
:
407 case BFD_MACH_O_S_SYMBOL_STUBS
:
408 printf (" first indirect sym: %lu", sec
->reserved1
);
409 printf (" (%u entries)",
410 bfd_mach_o_section_get_nbr_indirect (abfd
, sec
));
413 printf (" reserved1: 0x%lx", sec
->reserved1
);
416 switch (sec
->flags
& BFD_MACH_O_SECTION_TYPE_MASK
)
418 case BFD_MACH_O_S_SYMBOL_STUBS
:
419 printf (" stub size: %lu", sec
->reserved2
);
422 printf (" reserved2: 0x%lx", sec
->reserved2
);
425 printf (" reserved3: 0x%lx\n", sec
->reserved3
);
429 dump_segment (bfd
*abfd
, bfd_mach_o_load_command
*cmd
)
431 bfd_mach_o_segment_command
*seg
= &cmd
->command
.segment
;
432 bfd_mach_o_section
*sec
;
434 printf (" name: %16s", *seg
->segname
? seg
->segname
: "*none*");
435 printf (" nsects: %lu", seg
->nsects
);
436 printf (" flags: %lx", seg
->flags
);
437 printf (" initprot: ");
438 disp_segment_prot (seg
->initprot
);
439 printf (" maxprot: ");
440 disp_segment_prot (seg
->maxprot
);
442 printf (" vmaddr: ");
443 bfd_printf_vma (abfd
, seg
->vmaddr
);
444 printf (" vmsize: ");
445 bfd_printf_vma (abfd
, seg
->vmsize
);
447 printf (" fileoff: ");
448 bfd_printf_vma (abfd
, seg
->fileoff
);
449 printf (" filesize: ");
450 bfd_printf_vma (abfd
, (bfd_vma
) seg
->filesize
);
451 printf (" endoff: ");
452 bfd_printf_vma (abfd
, (bfd_vma
) (seg
->fileoff
+ seg
->filesize
));
454 for (sec
= seg
->sect_head
; sec
!= NULL
; sec
= sec
->next
)
455 dump_section_header (abfd
, sec
);
459 dump_dysymtab (bfd
*abfd
, bfd_mach_o_load_command
*cmd
, bool verbose
)
461 bfd_mach_o_dysymtab_command
*dysymtab
= &cmd
->command
.dysymtab
;
462 bfd_mach_o_data_struct
*mdata
= bfd_mach_o_get_data (abfd
);
465 printf (" local symbols: idx: %10lu num: %-8lu",
466 dysymtab
->ilocalsym
, dysymtab
->nlocalsym
);
467 printf (" (nxtidx: %lu)\n",
468 dysymtab
->ilocalsym
+ dysymtab
->nlocalsym
);
469 printf (" external symbols: idx: %10lu num: %-8lu",
470 dysymtab
->iextdefsym
, dysymtab
->nextdefsym
);
471 printf (" (nxtidx: %lu)\n",
472 dysymtab
->iextdefsym
+ dysymtab
->nextdefsym
);
473 printf (" undefined symbols: idx: %10lu num: %-8lu",
474 dysymtab
->iundefsym
, dysymtab
->nundefsym
);
475 printf (" (nxtidx: %lu)\n",
476 dysymtab
->iundefsym
+ dysymtab
->nundefsym
);
477 printf (" table of content: off: 0x%08lx num: %-8lu",
478 dysymtab
->tocoff
, dysymtab
->ntoc
);
479 printf (" (endoff: 0x%08lx)\n",
480 dysymtab
->tocoff
+ dysymtab
->ntoc
* BFD_MACH_O_TABLE_OF_CONTENT_SIZE
);
481 printf (" module table: off: 0x%08lx num: %-8lu",
482 dysymtab
->modtaboff
, dysymtab
->nmodtab
);
483 printf (" (endoff: 0x%08lx)\n",
484 dysymtab
->modtaboff
+ dysymtab
->nmodtab
485 * (mdata
->header
.version
== 2 ?
486 BFD_MACH_O_DYLIB_MODULE_64_SIZE
: BFD_MACH_O_DYLIB_MODULE_SIZE
));
487 printf (" external reference table: off: 0x%08lx num: %-8lu",
488 dysymtab
->extrefsymoff
, dysymtab
->nextrefsyms
);
489 printf (" (endoff: 0x%08lx)\n",
490 dysymtab
->extrefsymoff
491 + dysymtab
->nextrefsyms
* BFD_MACH_O_REFERENCE_SIZE
);
492 printf (" indirect symbol table: off: 0x%08lx num: %-8lu",
493 dysymtab
->indirectsymoff
, dysymtab
->nindirectsyms
);
494 printf (" (endoff: 0x%08lx)\n",
495 dysymtab
->indirectsymoff
496 + dysymtab
->nindirectsyms
* BFD_MACH_O_INDIRECT_SYMBOL_SIZE
);
497 printf (" external relocation table: off: 0x%08lx num: %-8lu",
498 dysymtab
->extreloff
, dysymtab
->nextrel
);
499 printf (" (endoff: 0x%08lx)\n",
500 dysymtab
->extreloff
+ dysymtab
->nextrel
* BFD_MACH_O_RELENT_SIZE
);
501 printf (" local relocation table: off: 0x%08lx num: %-8lu",
502 dysymtab
->locreloff
, dysymtab
->nlocrel
);
503 printf (" (endoff: 0x%08lx)\n",
504 dysymtab
->locreloff
+ dysymtab
->nlocrel
* BFD_MACH_O_RELENT_SIZE
);
509 if (dysymtab
->ntoc
> 0
510 || dysymtab
->nindirectsyms
> 0
511 || dysymtab
->nextrefsyms
> 0)
513 /* Try to read the symbols to display the toc or indirect symbols. */
514 bfd_mach_o_read_symtab_symbols (abfd
);
516 else if (dysymtab
->nmodtab
> 0)
518 /* Try to read the strtab to display modules name. */
519 bfd_mach_o_read_symtab_strtab (abfd
);
522 for (i
= 0; i
< dysymtab
->nmodtab
; i
++)
524 bfd_mach_o_dylib_module
*module
= &dysymtab
->dylib_module
[i
];
525 printf (" module %u:\n", i
);
526 printf (" name: %lu", module
->module_name_idx
);
527 if (mdata
->symtab
&& mdata
->symtab
->strtab
)
529 mdata
->symtab
->strtab
+ module
->module_name_idx
);
531 printf (" extdefsym: idx: %8lu num: %lu\n",
532 module
->iextdefsym
, module
->nextdefsym
);
533 printf (" refsym: idx: %8lu num: %lu\n",
534 module
->irefsym
, module
->nrefsym
);
535 printf (" localsym: idx: %8lu num: %lu\n",
536 module
->ilocalsym
, module
->nlocalsym
);
537 printf (" extrel: idx: %8lu num: %lu\n",
538 module
->iextrel
, module
->nextrel
);
539 printf (" init: idx: %8u num: %u\n",
540 module
->iinit
, module
->ninit
);
541 printf (" term: idx: %8u num: %u\n",
542 module
->iterm
, module
->nterm
);
543 printf (" objc_module_info: addr: ");
544 bfd_printf_vma (abfd
, module
->objc_module_info_addr
);
545 printf (" size: %lu\n", module
->objc_module_info_size
);
548 if (dysymtab
->ntoc
> 0)
550 bfd_mach_o_symtab_command
*symtab
= mdata
->symtab
;
552 printf (" table of content: (symbol/module)\n");
553 for (i
= 0; i
< dysymtab
->ntoc
; i
++)
555 bfd_mach_o_dylib_table_of_content
*toc
= &dysymtab
->dylib_toc
[i
];
557 printf (" %4u: ", i
);
558 if (symtab
&& symtab
->symbols
&& toc
->symbol_index
< symtab
->nsyms
)
560 const char *name
= symtab
->symbols
[toc
->symbol_index
].symbol
.name
;
561 printf ("%s (%lu)", name
? name
: "*invalid*",
565 printf ("%lu", toc
->symbol_index
);
568 if (symtab
&& symtab
->strtab
569 && toc
->module_index
< dysymtab
->nmodtab
)
571 bfd_mach_o_dylib_module
*mod
;
572 mod
= &dysymtab
->dylib_module
[toc
->module_index
];
574 symtab
->strtab
+ mod
->module_name_idx
,
578 printf ("%lu", toc
->module_index
);
584 if (dysymtab
->nindirectsyms
!= 0)
586 printf (" indirect symbols:\n");
588 for (i
= 0; i
< mdata
->nsects
; i
++)
590 bfd_mach_o_section
*sec
= mdata
->sections
[i
];
591 unsigned int j
, first
, last
;
592 bfd_mach_o_symtab_command
*symtab
= mdata
->symtab
;
596 switch (sec
->flags
& BFD_MACH_O_SECTION_TYPE_MASK
)
598 case BFD_MACH_O_S_NON_LAZY_SYMBOL_POINTERS
:
599 case BFD_MACH_O_S_LAZY_SYMBOL_POINTERS
:
600 case BFD_MACH_O_S_SYMBOL_STUBS
:
601 first
= sec
->reserved1
;
602 last
= first
+ bfd_mach_o_section_get_nbr_indirect (abfd
, sec
);
604 entry_size
= bfd_mach_o_section_get_entry_size (abfd
, sec
);
605 printf (" for section %s.%s:\n",
606 sec
->segname
, sec
->sectname
);
607 for (j
= first
; j
< last
; j
++)
609 unsigned int isym
= dysymtab
->indirect_syms
[j
];
612 bfd_printf_vma (abfd
, addr
);
613 printf (" %5u: 0x%08x", j
, isym
);
614 if (isym
& BFD_MACH_O_INDIRECT_SYMBOL_LOCAL
)
616 if (isym
& BFD_MACH_O_INDIRECT_SYMBOL_ABS
)
617 printf (" ABSOLUTE");
618 if (symtab
&& symtab
->symbols
619 && isym
< symtab
->nsyms
620 && symtab
->symbols
[isym
].symbol
.name
)
621 printf (" %s", symtab
->symbols
[isym
].symbol
.name
);
631 if (dysymtab
->nextrefsyms
> 0)
633 bfd_mach_o_symtab_command
*symtab
= mdata
->symtab
;
635 printf (" external reference table: (symbol flags)\n");
636 for (i
= 0; i
< dysymtab
->nextrefsyms
; i
++)
638 bfd_mach_o_dylib_reference
*ref
= &dysymtab
->ext_refs
[i
];
640 printf (" %4u: %5lu 0x%02lx", i
, ref
->isym
, ref
->flags
);
641 if (symtab
&& symtab
->symbols
642 && ref
->isym
< symtab
->nsyms
643 && symtab
->symbols
[ref
->isym
].symbol
.name
)
644 printf (" %s", symtab
->symbols
[ref
->isym
].symbol
.name
);
652 load_and_dump (bfd
*abfd
, ufile_ptr off
, unsigned int len
,
653 void (*dump
)(bfd
*abfd
, unsigned char *buf
, unsigned int len
,
663 if (bfd_seek (abfd
, off
, SEEK_SET
) == 0
664 && bfd_read (buf
, len
, abfd
) == len
)
665 dump (abfd
, buf
, len
, off
);
673 static const bfd_mach_o_xlat_name bfd_mach_o_dyld_rebase_type_name
[] =
675 { "pointer", BFD_MACH_O_REBASE_TYPE_POINTER
},
676 { "text_abs32", BFD_MACH_O_REBASE_TYPE_TEXT_ABSOLUTE32
},
677 { "text_pcrel32", BFD_MACH_O_REBASE_TYPE_TEXT_PCREL32
},
682 dump_dyld_info_rebase (bfd
*abfd
, unsigned char *buf
, unsigned int len
,
683 ufile_ptr off ATTRIBUTE_UNUSED
)
686 bfd_mach_o_data_struct
*mdata
= bfd_mach_o_get_data (abfd
);
687 unsigned int ptrsize
= mdata
->header
.version
== 2 ? 8 : 4;
689 for (i
= 0; i
< len
; )
691 unsigned char b
= buf
[i
++];
692 unsigned char imm
= b
& BFD_MACH_O_REBASE_IMMEDIATE_MASK
;
696 printf (" [0x%04x] 0x%02x: ", i
, b
);
697 switch (b
& BFD_MACH_O_REBASE_OPCODE_MASK
)
699 case BFD_MACH_O_REBASE_OPCODE_DONE
:
702 case BFD_MACH_O_REBASE_OPCODE_SET_TYPE_IMM
:
703 printf ("set_type %s\n",
704 bfd_mach_o_get_name (bfd_mach_o_dyld_rebase_type_name
, imm
));
706 case BFD_MACH_O_REBASE_OPCODE_SET_SEGMENT_AND_OFFSET_ULEB
:
707 leb
= read_leb128 (buf
+ i
, buf
+ len
, 0, &leblen
, NULL
);
708 printf ("set segment: %u and offset: 0x%08x\n",
709 imm
, (unsigned) leb
);
712 case BFD_MACH_O_REBASE_OPCODE_ADD_ADDR_ULEB
:
713 leb
= read_leb128 (buf
+ i
, buf
+ len
, 0, &leblen
, NULL
);
714 printf ("add addr uleb: 0x%08x\n", (unsigned) leb
);
717 case BFD_MACH_O_REBASE_OPCODE_ADD_ADDR_IMM_SCALED
:
718 printf ("add addr imm scaled: %u\n", imm
* ptrsize
);
720 case BFD_MACH_O_REBASE_OPCODE_DO_REBASE_IMM_TIMES
:
721 printf ("rebase imm times: %u\n", imm
);
723 case BFD_MACH_O_REBASE_OPCODE_DO_REBASE_ULEB_TIMES
:
724 leb
= read_leb128 (buf
+ i
, buf
+ len
, 0, &leblen
, NULL
);
725 printf ("rebase uleb times: %u\n", (unsigned) leb
);
728 case BFD_MACH_O_REBASE_OPCODE_DO_REBASE_ADD_ADDR_ULEB
:
729 leb
= read_leb128 (buf
+ i
, buf
+ len
, 0, &leblen
, NULL
);
730 printf ("rebase add addr uleb: %u\n", (unsigned) leb
);
733 case BFD_MACH_O_REBASE_OPCODE_DO_REBASE_ULEB_TIMES_SKIPPING_ULEB
:
734 leb
= read_leb128 (buf
+ i
, buf
+ len
, 0, &leblen
, NULL
);
735 printf ("rebase uleb times (%u)", (unsigned) leb
);
737 leb
= read_leb128 (buf
+ i
, buf
+ len
, 0, &leblen
, NULL
);
738 printf (" skipping uleb (%u)\n", (unsigned) leb
);
742 printf ("unknown\n");
746 printf (" rebase commands without end!\n");
750 dump_dyld_info_bind (bfd
*abfd
, unsigned char *buf
, unsigned int len
,
751 ufile_ptr off ATTRIBUTE_UNUSED
)
754 bfd_mach_o_data_struct
*mdata
= bfd_mach_o_get_data (abfd
);
755 unsigned int ptrsize
= mdata
->header
.version
== 2 ? 8 : 4;
757 for (i
= 0; i
< len
; )
759 unsigned char b
= buf
[i
++];
760 unsigned char imm
= b
& BFD_MACH_O_BIND_IMMEDIATE_MASK
;
764 printf (" [0x%04x] 0x%02x: ", i
, b
);
765 switch (b
& BFD_MACH_O_BIND_OPCODE_MASK
)
767 case BFD_MACH_O_BIND_OPCODE_DONE
:
770 case BFD_MACH_O_BIND_OPCODE_SET_DYLIB_ORDINAL_IMM
:
771 printf ("set dylib ordinal imm: %u\n", imm
);
773 case BFD_MACH_O_BIND_OPCODE_SET_DYLIB_ORDINAL_ULEB
:
774 leb
= read_leb128 (buf
+ i
, buf
+ len
, 0, &leblen
, NULL
);
775 printf ("set dylib ordinal uleb: %u\n", imm
);
778 case BFD_MACH_O_BIND_OPCODE_SET_DYLIB_SPECIAL_IMM
:
779 imm
= (imm
!= 0) ? imm
| BFD_MACH_O_BIND_OPCODE_MASK
: imm
;
780 printf ("set dylib special imm: %d\n", imm
);
782 case BFD_MACH_O_BIND_OPCODE_SET_SYMBOL_TRAILING_FLAGS_IMM
:
783 printf ("set symbol trailing flags imm: 0x%02x, ", imm
);
784 for (; i
< len
&& buf
[i
] != 0; i
++)
785 putchar (buf
[i
] >= ' ' && buf
[i
] < 0x7f ? buf
[i
] : '?');
789 case BFD_MACH_O_BIND_OPCODE_SET_TYPE_IMM
:
790 /* Kludge: use the same table as rebase type. */
791 printf ("set_type %s\n",
792 bfd_mach_o_get_name (bfd_mach_o_dyld_rebase_type_name
, imm
));
794 case BFD_MACH_O_BIND_OPCODE_SET_ADDEND_SLEB
:
797 svma
= read_leb128 (buf
+ i
, buf
+ len
, 0, &leblen
, NULL
);
798 printf ("set addend sleb: 0x%08x\n", (unsigned) svma
);
802 case BFD_MACH_O_BIND_OPCODE_SET_SEGMENT_AND_OFFSET_ULEB
:
803 leb
= read_leb128 (buf
+ i
, buf
+ len
, 0, &leblen
, NULL
);
804 printf ("set segment: %u and offset: 0x%08x\n",
805 imm
, (unsigned) leb
);
808 case BFD_MACH_O_BIND_OPCODE_ADD_ADDR_ULEB
:
809 leb
= read_leb128 (buf
+ i
, buf
+ len
, 0, &leblen
, NULL
);
810 printf ("add addr uleb: 0x%08x\n", (unsigned) leb
);
813 case BFD_MACH_O_BIND_OPCODE_DO_BIND
:
814 printf ("do bind\n");
816 case BFD_MACH_O_BIND_OPCODE_DO_BIND_ADD_ADDR_ULEB
:
817 leb
= read_leb128 (buf
+ i
, buf
+ len
, 0, &leblen
, NULL
);
818 printf ("do bind add addr uleb: 0x%08x\n", (unsigned) leb
);
821 case BFD_MACH_O_BIND_OPCODE_DO_BIND_ADD_ADDR_IMM_SCALED
:
822 printf ("do bind add addr imm scaled: %u\n", imm
* ptrsize
);
824 case BFD_MACH_O_BIND_OPCODE_DO_BIND_ULEB_TIMES_SKIPPING_ULEB
:
825 leb
= read_leb128 (buf
+ i
, buf
+ len
, 0, &leblen
, NULL
);
826 printf ("do bind uleb times (%u)", (unsigned) leb
);
828 leb
= read_leb128 (buf
+ i
, buf
+ len
, 0, &leblen
, NULL
);
829 printf (" skipping uleb (%u)\n", (unsigned) leb
);
833 printf ("unknown\n");
837 printf (" bind commands without end!\n");
840 struct export_info_data
842 const unsigned char *name
;
843 struct export_info_data
*next
;
847 dump_dyld_info_export_1 (bfd
*abfd
, unsigned char *buf
, unsigned int len
,
848 unsigned int off
, struct export_info_data
*parent
,
849 struct export_info_data
*base
)
853 unsigned int child_count
;
856 size
= read_leb128 (buf
+ off
, buf
+ len
, 0, &leblen
, NULL
);
862 struct export_info_data
*d
;
864 flags
= read_leb128 (buf
+ off
, buf
+ len
, 0, &leblen
, NULL
);
868 switch (flags
& BFD_MACH_O_EXPORT_SYMBOL_FLAGS_KIND_MASK
)
870 case BFD_MACH_O_EXPORT_SYMBOL_FLAGS_KIND_REGULAR
:
873 case BFD_MACH_O_EXPORT_SYMBOL_FLAGS_KIND_THREAD_LOCAL
:
880 putchar ((flags
& BFD_MACH_O_EXPORT_SYMBOL_FLAGS_WEAK_DEFINITION
) ?
883 if (flags
& BFD_MACH_O_EXPORT_SYMBOL_FLAGS_REEXPORT
)
887 lib
= read_leb128 (buf
+ off
, buf
+ len
, 0, &leblen
, NULL
);
890 fputs (" [reexport] ", stdout
);
891 for (d
= base
; d
!= NULL
; d
= d
->next
)
892 printf ("%s", d
->name
);
894 fputs (" (", stdout
);
897 fputs ((const char *)buf
+ off
, stdout
);
899 off
+= strlen ((const char *)buf
+ off
);
901 printf ("from dylib %u)\n", (unsigned) lib
);
909 offset
= read_leb128 (buf
+ off
, buf
+ len
, 0, &leblen
, NULL
);
912 if (flags
& BFD_MACH_O_EXPORT_SYMBOL_FLAGS_STUB_AND_RESOLVER
)
914 resolv
= read_leb128 (buf
+ off
, buf
+ len
, 0, &leblen
, NULL
);
918 printf (" 0x%08x ", (unsigned) offset
);
919 for (d
= base
; d
!= NULL
; d
= d
->next
)
920 printf ("%s", d
->name
);
921 if (flags
& BFD_MACH_O_EXPORT_SYMBOL_FLAGS_STUB_AND_RESOLVER
)
922 printf (" [resolv: 0x%08x]", (unsigned) resolv
);
927 child_count
= read_leb128 (buf
+ off
, buf
+ len
, 0, &leblen
, NULL
);
930 for (i
= 0; i
< child_count
; i
++)
932 struct export_info_data sub_data
;
935 sub_data
.name
= buf
+ off
;
936 sub_data
.next
= NULL
;
937 parent
->next
= &sub_data
;
939 off
+= strlen ((const char *)buf
+ off
) + 1;
941 sub_off
= read_leb128 (buf
+ off
, buf
+ len
, 0, &leblen
, NULL
);
944 dump_dyld_info_export_1 (abfd
, buf
, len
, sub_off
, &sub_data
, base
);
949 dump_dyld_info_export (bfd
*abfd
, unsigned char *buf
, unsigned int len
,
950 ufile_ptr off ATTRIBUTE_UNUSED
)
952 struct export_info_data data
;
954 data
.name
= (const unsigned char *) "";
957 printf (" fl offset sym (Flags: Tls Weak)\n");
958 dump_dyld_info_export_1 (abfd
, buf
, len
, 0, &data
, &data
);
962 dump_dyld_info (bfd
*abfd
, bfd_mach_o_load_command
*cmd
,
965 bfd_mach_o_dyld_info_command
*dinfo
= &cmd
->command
.dyld_info
;
967 printf (" rebase: off: 0x%08x size: %-8u (endoff: 0x%08x)\n",
968 dinfo
->rebase_off
, dinfo
->rebase_size
,
969 dinfo
->rebase_off
+ dinfo
->rebase_size
);
970 printf (" bind: off: 0x%08x size: %-8u (endoff: 0x%08x)\n",
971 dinfo
->bind_off
, dinfo
->bind_size
,
972 dinfo
->bind_off
+ dinfo
->bind_size
);
973 printf (" weak bind: off: 0x%08x size: %-8u (endoff: 0x%08x)\n",
974 dinfo
->weak_bind_off
, dinfo
->weak_bind_size
,
975 dinfo
->weak_bind_off
+ dinfo
->weak_bind_size
);
976 printf (" lazy bind: off: 0x%08x size: %-8u (endoff: 0x%08x)\n",
977 dinfo
->lazy_bind_off
, dinfo
->lazy_bind_size
,
978 dinfo
->lazy_bind_off
+ dinfo
->lazy_bind_size
);
979 printf (" export: off: 0x%08x size: %-8u (endoff: 0x%08x)\n",
980 dinfo
->export_off
, dinfo
->export_size
,
981 dinfo
->export_off
+ dinfo
->export_size
);
986 printf (" rebase:\n");
987 if (!load_and_dump (abfd
, dinfo
->rebase_off
, dinfo
->rebase_size
,
988 dump_dyld_info_rebase
))
989 non_fatal (_("cannot read rebase dyld info"));
992 if (!load_and_dump (abfd
, dinfo
->bind_off
, dinfo
->bind_size
,
993 dump_dyld_info_bind
))
994 non_fatal (_("cannot read bind dyld info"));
996 printf (" weak bind:\n");
997 if (!load_and_dump (abfd
, dinfo
->weak_bind_off
, dinfo
->weak_bind_size
,
998 dump_dyld_info_bind
))
999 non_fatal (_("cannot read weak bind dyld info"));
1001 printf (" lazy bind:\n");
1002 if (!load_and_dump (abfd
, dinfo
->lazy_bind_off
, dinfo
->lazy_bind_size
,
1003 dump_dyld_info_bind
))
1004 non_fatal (_("cannot read lazy bind dyld info"));
1006 printf (" exported symbols:\n");
1007 if (!load_and_dump (abfd
, dinfo
->export_off
, dinfo
->export_size
,
1008 dump_dyld_info_export
))
1009 non_fatal (_("cannot read export symbols dyld info"));
1013 dump_thread (bfd
*abfd
, bfd_mach_o_load_command
*cmd
)
1015 bfd_mach_o_thread_command
*thread
= &cmd
->command
.thread
;
1017 bfd_mach_o_backend_data
*bed
= bfd_mach_o_get_backend_data (abfd
);
1018 bfd_mach_o_data_struct
*mdata
= bfd_mach_o_get_data (abfd
);
1020 printf (" nflavours: %lu\n", thread
->nflavours
);
1021 for (j
= 0; j
< thread
->nflavours
; j
++)
1023 bfd_mach_o_thread_flavour
*flavour
= &thread
->flavours
[j
];
1024 const bfd_mach_o_xlat_name
*name_table
;
1026 printf (" %2u: flavour: 0x%08lx", j
, flavour
->flavour
);
1027 switch (mdata
->header
.cputype
)
1029 case BFD_MACH_O_CPU_TYPE_I386
:
1030 case BFD_MACH_O_CPU_TYPE_X86_64
:
1031 name_table
= bfd_mach_o_thread_x86_name
;
1037 if (name_table
!= NULL
)
1038 printf (": %s", bfd_mach_o_get_name (name_table
, flavour
->flavour
));
1041 printf (" offset: 0x%08lx size: 0x%08lx\n",
1042 flavour
->offset
, flavour
->size
);
1043 if (bed
->_bfd_mach_o_print_thread
)
1045 char *buf
= xmalloc (flavour
->size
);
1047 if (bfd_seek (abfd
, flavour
->offset
, SEEK_SET
) == 0
1048 && bfd_read (buf
, flavour
->size
, abfd
) == flavour
->size
)
1049 (*bed
->_bfd_mach_o_print_thread
)(abfd
, flavour
, stdout
, buf
);
1056 static const bfd_mach_o_xlat_name bfd_mach_o_cs_magic
[] =
1058 { "embedded signature", BFD_MACH_O_CS_MAGIC_EMBEDDED_SIGNATURE
},
1059 { "requirement", BFD_MACH_O_CS_MAGIC_REQUIREMENT
},
1060 { "requirements", BFD_MACH_O_CS_MAGIC_REQUIREMENTS
},
1061 { "code directory", BFD_MACH_O_CS_MAGIC_CODEDIRECTORY
},
1062 { "embedded entitlements", BFD_MACH_O_CS_MAGIC_EMBEDDED_ENTITLEMENTS
},
1063 { "blob wrapper", BFD_MACH_O_CS_MAGIC_BLOB_WRAPPER
},
1067 static const bfd_mach_o_xlat_name bfd_mach_o_cs_hash_type
[] =
1069 { "no-hash", BFD_MACH_O_CS_NO_HASH
},
1070 { "sha1", BFD_MACH_O_CS_HASH_SHA1
},
1071 { "sha256", BFD_MACH_O_CS_HASH_SHA256
},
1072 { "skein 160", BFD_MACH_O_CS_HASH_PRESTANDARD_SKEIN_160x256
},
1073 { "skein 256", BFD_MACH_O_CS_HASH_PRESTANDARD_SKEIN_256x512
},
1078 dump_code_signature_blob (bfd
*abfd
, const unsigned char *buf
, unsigned int len
);
1081 dump_code_signature_superblob (bfd
*abfd ATTRIBUTE_UNUSED
,
1082 const unsigned char *buf
, unsigned int len
)
1089 printf (_(" [bad block length]\n"));
1092 count
= bfd_getb32 (buf
+ 8);
1093 printf (ngettext (" %u index entry:\n",
1094 " %u index entries:\n",
1097 if (len
< 12 + 8 * count
)
1099 printf (_(" [bad block length]\n"));
1102 for (i
= 0; i
< count
; i
++)
1107 type
= bfd_getb32 (buf
+ 12 + 8 * i
);
1108 off
= bfd_getb32 (buf
+ 12 + 8 * i
+ 4);
1109 printf (_(" index entry %u: type: %08x, offset: %08x\n"),
1112 dump_code_signature_blob (abfd
, buf
+ off
, len
- off
);
1117 swap_code_codedirectory_v1_in
1118 (const struct mach_o_codesign_codedirectory_external_v1
*src
,
1119 struct mach_o_codesign_codedirectory_v1
*dst
)
1121 dst
->version
= bfd_getb32 (src
->version
);
1122 dst
->flags
= bfd_getb32 (src
->flags
);
1123 dst
->hash_offset
= bfd_getb32 (src
->hash_offset
);
1124 dst
->ident_offset
= bfd_getb32 (src
->ident_offset
);
1125 dst
->nbr_special_slots
= bfd_getb32 (src
->nbr_special_slots
);
1126 dst
->nbr_code_slots
= bfd_getb32 (src
->nbr_code_slots
);
1127 dst
->code_limit
= bfd_getb32 (src
->code_limit
);
1128 dst
->hash_size
= src
->hash_size
[0];
1129 dst
->hash_type
= src
->hash_type
[0];
1130 dst
->spare1
= src
->spare1
[0];
1131 dst
->page_size
= src
->page_size
[0];
1132 dst
->spare2
= bfd_getb32 (src
->spare2
);
1136 hexdump (unsigned int start
, unsigned int len
,
1137 const unsigned char *buf
)
1141 for (i
= 0; i
< len
; i
+= 16)
1143 printf ("%08x:", start
+ i
);
1144 for (j
= 0; j
< 16; j
++)
1146 fputc (j
== 8 ? '-' : ' ', stdout
);
1148 printf ("%02x", buf
[i
+ j
]);
1150 fputs (" ", stdout
);
1152 fputc (' ', stdout
);
1153 for (j
= 0; j
< 16; j
++)
1156 fputc (ISPRINT (buf
[i
+ j
]) ? buf
[i
+ j
] : '.', stdout
);
1158 fputc (' ', stdout
);
1160 fputc ('\n', stdout
);
1165 dump_code_signature_codedirectory (bfd
*abfd ATTRIBUTE_UNUSED
,
1166 const unsigned char *buf
, unsigned int len
)
1168 struct mach_o_codesign_codedirectory_v1 cd
;
1171 if (len
< sizeof (struct mach_o_codesign_codedirectory_external_v1
))
1173 printf (_(" [bad block length]\n"));
1177 swap_code_codedirectory_v1_in
1178 ((const struct mach_o_codesign_codedirectory_external_v1
*) (buf
+ 8), &cd
);
1180 printf (_(" version: %08x\n"), cd
.version
);
1181 printf (_(" flags: %08x\n"), cd
.flags
);
1182 printf (_(" hash offset: %08x\n"), cd
.hash_offset
);
1183 id
= (const char *) buf
+ cd
.ident_offset
;
1184 printf (_(" ident offset: %08x (- %08x)\n"),
1185 cd
.ident_offset
, cd
.ident_offset
+ (unsigned) strlen (id
) + 1);
1186 printf (_(" identity: %s\n"), id
);
1187 printf (_(" nbr special slots: %08x (at offset %08x)\n"),
1188 cd
.nbr_special_slots
,
1189 cd
.hash_offset
- cd
.nbr_special_slots
* cd
.hash_size
);
1190 printf (_(" nbr code slots: %08x\n"), cd
.nbr_code_slots
);
1191 printf (_(" code limit: %08x\n"), cd
.code_limit
);
1192 printf (_(" hash size: %02x\n"), cd
.hash_size
);
1193 printf (_(" hash type: %02x (%s)\n"),
1195 bfd_mach_o_get_name (bfd_mach_o_cs_hash_type
, cd
.hash_type
));
1196 printf (_(" spare1: %02x\n"), cd
.spare1
);
1197 printf (_(" page size: %02x\n"), cd
.page_size
);
1198 printf (_(" spare2: %08x\n"), cd
.spare2
);
1199 if (cd
.version
>= 0x20100)
1200 printf (_(" scatter offset: %08x\n"),
1201 (unsigned) bfd_getb32 (buf
+ 44));
1205 dump_code_signature_blob (bfd
*abfd
, const unsigned char *buf
, unsigned int len
)
1208 unsigned int length
;
1212 printf (_(" [truncated block]\n"));
1215 magic
= bfd_getb32 (buf
);
1216 length
= bfd_getb32 (buf
+ 4);
1217 if (magic
== 0 || length
== 0)
1220 printf (_(" magic : %08x (%s)\n"), magic
,
1221 bfd_mach_o_get_name (bfd_mach_o_cs_magic
, magic
));
1222 printf (_(" length: %08x\n"), length
);
1225 printf (_(" [bad block length]\n"));
1231 case BFD_MACH_O_CS_MAGIC_EMBEDDED_SIGNATURE
:
1232 dump_code_signature_superblob (abfd
, buf
, length
);
1234 case BFD_MACH_O_CS_MAGIC_CODEDIRECTORY
:
1235 dump_code_signature_codedirectory (abfd
, buf
, length
);
1238 hexdump (0, length
- 8, buf
+ 8);
1245 dump_code_signature (bfd
*abfd
, bfd_mach_o_linkedit_command
*cmd
)
1247 unsigned char *buf
= xmalloc (cmd
->datasize
);
1250 if (bfd_seek (abfd
, cmd
->dataoff
, SEEK_SET
) != 0
1251 || bfd_read (buf
, cmd
->datasize
, abfd
) != cmd
->datasize
)
1253 non_fatal (_("cannot read code signature data"));
1257 for (off
= 0; off
< cmd
->datasize
;)
1261 len
= dump_code_signature_blob (abfd
, buf
+ off
, cmd
->datasize
- off
);
1271 dump_segment_split_info (bfd
*abfd
, bfd_mach_o_linkedit_command
*cmd
)
1273 unsigned char *buf
= xmalloc (cmd
->datasize
);
1278 if (bfd_seek (abfd
, cmd
->dataoff
, SEEK_SET
) != 0
1279 || bfd_read (buf
, cmd
->datasize
, abfd
) != cmd
->datasize
)
1281 non_fatal (_("cannot read segment split info"));
1285 if (buf
[cmd
->datasize
- 1] != 0)
1287 non_fatal (_("segment split info is not nul terminated"));
1295 printf (_(" 32 bit pointers:\n"));
1298 printf (_(" 64 bit pointers:\n"));
1301 printf (_(" PPC hi-16:\n"));
1304 printf (_(" Unhandled location type %u\n"), buf
[0]);
1307 for (p
= buf
+ 1; *p
!= 0; p
+= len
)
1309 addr
+= read_leb128 (p
, buf
+ cmd
->datasize
, 0, &len
, NULL
);
1310 fputs (" ", stdout
);
1311 bfd_printf_vma (abfd
, addr
);
1318 dump_function_starts (bfd
*abfd
, bfd_mach_o_linkedit_command
*cmd
)
1320 unsigned char *buf
= xmalloc (cmd
->datasize
);
1321 unsigned char *end_buf
= buf
+ cmd
->datasize
;
1325 if (bfd_seek (abfd
, cmd
->dataoff
, SEEK_SET
) != 0
1326 || bfd_read (buf
, cmd
->datasize
, abfd
) != cmd
->datasize
)
1328 non_fatal (_("cannot read function starts"));
1333 /* Function starts are delta encoded, starting from the base address. */
1334 addr
= bfd_mach_o_get_base_address (abfd
);
1339 unsigned int shift
= 0;
1341 if (*p
== 0 || p
== end_buf
)
1345 unsigned char b
= *p
++;
1347 delta
|= (b
& 0x7f) << shift
;
1348 if ((b
& 0x80) == 0)
1352 fputs (" [truncated]\n", stdout
);
1359 fputs (" ", stdout
);
1360 bfd_printf_vma (abfd
, addr
);
1366 static const bfd_mach_o_xlat_name data_in_code_kind_name
[] =
1368 { "data", BFD_MACH_O_DICE_KIND_DATA
},
1369 { "1 byte jump table", BFD_MACH_O_DICE_JUMP_TABLES8
},
1370 { "2 bytes jump table", BFD_MACH_O_DICE_JUMP_TABLES16
},
1371 { "4 bytes jump table", BFD_MACH_O_DICE_JUMP_TABLES32
},
1372 { "4 bytes abs jump table", BFD_MACH_O_DICE_ABS_JUMP_TABLES32
},
1377 dump_data_in_code (bfd
*abfd
, bfd_mach_o_linkedit_command
*cmd
)
1382 if (cmd
->datasize
== 0)
1384 printf (" no data_in_code entries\n");
1388 buf
= xmalloc (cmd
->datasize
);
1389 if (bfd_seek (abfd
, cmd
->dataoff
, SEEK_SET
) != 0
1390 || bfd_read (buf
, cmd
->datasize
, abfd
) != cmd
->datasize
)
1392 non_fatal (_("cannot read data_in_code"));
1397 printf (" offset length kind\n");
1398 for (p
= buf
; p
< buf
+ cmd
->datasize
; )
1400 struct mach_o_data_in_code_entry_external
*dice
;
1401 unsigned int offset
;
1402 unsigned int length
;
1405 dice
= (struct mach_o_data_in_code_entry_external
*) p
;
1407 offset
= bfd_get_32 (abfd
, dice
->offset
);
1408 length
= bfd_get_16 (abfd
, dice
->length
);
1409 kind
= bfd_get_16 (abfd
, dice
->kind
);
1411 printf (" 0x%08x 0x%04x 0x%04x %s\n", offset
, length
, kind
,
1412 bfd_mach_o_get_name (data_in_code_kind_name
, kind
));
1414 p
+= sizeof (*dice
);
1420 dump_twolevel_hints (bfd
*abfd
, bfd_mach_o_twolevel_hints_command
*cmd
)
1422 size_t sz
= 4 * cmd
->nhints
;
1427 if (bfd_seek (abfd
, cmd
->offset
, SEEK_SET
) != 0
1428 || bfd_read (buf
, sz
, abfd
) != sz
)
1430 non_fatal (_("cannot read twolevel hints"));
1435 for (p
= buf
; p
< buf
+ sz
; p
+= 4)
1438 unsigned int isub_image
;
1441 v
= bfd_get_32 (abfd
, p
);
1442 if (bfd_big_endian (abfd
))
1444 isub_image
= (v
>> 24) & 0xff;
1445 itoc
= v
& 0xffffff;
1449 isub_image
= v
& 0xff;
1450 itoc
= (v
>> 8) & 0xffffff;
1453 printf (" %3u %8u\n", isub_image
, itoc
);
1459 printf_version (uint32_t version
)
1461 uint32_t maj
, min
, upd
;
1463 maj
= (version
>> 16) & 0xffff;
1464 min
= (version
>> 8) & 0xff;
1465 upd
= version
& 0xff;
1467 printf ("%u.%u.%u", maj
, min
, upd
);
1471 dump_build_version (bfd
*abfd
, bfd_mach_o_load_command
*cmd
)
1473 const char *platform_name
;
1474 size_t tools_len
, tools_offset
;
1475 bfd_mach_o_build_version_tool
*tools
, *tool
;
1476 bfd_mach_o_build_version_command
*ver
= &cmd
->command
.build_version
;
1479 platform_name
= bfd_mach_o_get_name_or_null
1480 (bfd_mach_o_platform_name
, ver
->platform
);
1481 if (platform_name
== NULL
)
1482 printf (" platform: 0x%08x\n", ver
->platform
);
1484 printf (" platform: %s\n", platform_name
);
1486 printf_version (ver
->minos
);
1487 printf ("\n sdk: ");
1488 printf_version (ver
->sdk
);
1489 printf ("\n ntools: %u\n", ver
->ntools
);
1491 tools_len
= sizeof (bfd_mach_o_build_version_tool
) * ver
->ntools
;
1492 tools_offset
= cmd
->offset
+ cmd
->len
- tools_len
;
1494 tools
= xmalloc (tools_len
);
1495 if (bfd_seek (abfd
, tools_offset
, SEEK_SET
) != 0
1496 || bfd_read (tools
, tools_len
, abfd
) != tools_len
)
1498 non_fatal (_("cannot read build tools"));
1503 for (i
= 0, tool
= tools
; i
< ver
->ntools
; i
++, tool
++)
1505 const char * tool_name
;
1507 tool_name
= bfd_mach_o_get_name_or_null
1508 (bfd_mach_o_tool_name
, tool
->tool
);
1509 if (tool_name
== NULL
)
1510 printf (" tool: 0x%08x\n", tool
->tool
);
1512 printf (" tool: %s\n", tool_name
);
1513 printf (" version: ");
1514 printf_version (tool
->version
);
1521 dump_load_command (bfd
*abfd
, bfd_mach_o_load_command
*cmd
,
1522 unsigned int idx
, bool verbose
)
1524 bfd_mach_o_data_struct
*mdata
= bfd_mach_o_get_data (abfd
);
1525 const char *cmd_name
;
1527 cmd_name
= bfd_mach_o_get_name_or_null
1528 (bfd_mach_o_load_command_name
, cmd
->type
);
1529 printf ("Load command #%-2u (size: %3u, offset: %4u): ",
1530 idx
, cmd
->len
, cmd
->offset
);
1531 if (cmd_name
== NULL
)
1532 printf ("0x%02x\n", cmd
->type
);
1534 printf ("%s\n", cmd_name
);
1538 case BFD_MACH_O_LC_SEGMENT
:
1539 case BFD_MACH_O_LC_SEGMENT_64
:
1540 dump_segment (abfd
, cmd
);
1542 case BFD_MACH_O_LC_UUID
:
1544 bfd_mach_o_uuid_command
*uuid
= &cmd
->command
.uuid
;
1548 for (j
= 0; j
< sizeof (uuid
->uuid
); j
++)
1549 printf (" %02x", uuid
->uuid
[j
]);
1553 case BFD_MACH_O_LC_LOAD_DYLIB
:
1554 case BFD_MACH_O_LC_LAZY_LOAD_DYLIB
:
1555 case BFD_MACH_O_LC_LOAD_WEAK_DYLIB
:
1556 case BFD_MACH_O_LC_REEXPORT_DYLIB
:
1557 case BFD_MACH_O_LC_ID_DYLIB
:
1558 case BFD_MACH_O_LC_LOAD_UPWARD_DYLIB
:
1560 bfd_mach_o_dylib_command
*dylib
= &cmd
->command
.dylib
;
1561 printf (" name: %s\n", dylib
->name_str
);
1562 printf (" time stamp: 0x%08lx\n",
1564 printf (" current version: 0x%08lx\n",
1565 dylib
->current_version
);
1566 printf (" comptibility version: 0x%08lx\n",
1567 dylib
->compatibility_version
);
1570 case BFD_MACH_O_LC_LOAD_DYLINKER
:
1571 case BFD_MACH_O_LC_ID_DYLINKER
:
1572 printf (" %s\n", cmd
->command
.dylinker
.name_str
);
1574 case BFD_MACH_O_LC_DYLD_ENVIRONMENT
:
1575 printf (" %s\n", cmd
->command
.dylinker
.name_str
);
1577 case BFD_MACH_O_LC_SYMTAB
:
1579 bfd_mach_o_symtab_command
*symtab
= &cmd
->command
.symtab
;
1580 printf (" symoff: 0x%08x nsyms: %8u (endoff: 0x%08x)\n",
1581 symtab
->symoff
, symtab
->nsyms
,
1582 symtab
->symoff
+ symtab
->nsyms
1583 * (mdata
->header
.version
== 2
1584 ? BFD_MACH_O_NLIST_64_SIZE
: BFD_MACH_O_NLIST_SIZE
));
1585 printf (" stroff: 0x%08x strsize: %8u (endoff: 0x%08x)\n",
1586 symtab
->stroff
, symtab
->strsize
,
1587 symtab
->stroff
+ symtab
->strsize
);
1590 case BFD_MACH_O_LC_DYSYMTAB
:
1591 dump_dysymtab (abfd
, cmd
, verbose
);
1593 case BFD_MACH_O_LC_LOADFVMLIB
:
1594 case BFD_MACH_O_LC_IDFVMLIB
:
1596 bfd_mach_o_fvmlib_command
*fvmlib
= &cmd
->command
.fvmlib
;
1597 printf (" fvmlib: %s\n", fvmlib
->name_str
);
1598 printf (" minor version: 0x%08x\n", fvmlib
->minor_version
);
1599 printf (" header address: 0x%08x\n", fvmlib
->header_addr
);
1602 case BFD_MACH_O_LC_CODE_SIGNATURE
:
1603 case BFD_MACH_O_LC_SEGMENT_SPLIT_INFO
:
1604 case BFD_MACH_O_LC_FUNCTION_STARTS
:
1605 case BFD_MACH_O_LC_DATA_IN_CODE
:
1606 case BFD_MACH_O_LC_DYLIB_CODE_SIGN_DRS
:
1607 case BFD_MACH_O_LC_DYLD_EXPORTS_TRIE
:
1608 case BFD_MACH_O_LC_DYLD_CHAINED_FIXUPS
:
1610 bfd_mach_o_linkedit_command
*linkedit
= &cmd
->command
.linkedit
;
1612 (" dataoff: 0x%08lx datasize: 0x%08lx (endoff: 0x%08lx)\n",
1613 linkedit
->dataoff
, linkedit
->datasize
,
1614 linkedit
->dataoff
+ linkedit
->datasize
);
1619 case BFD_MACH_O_LC_CODE_SIGNATURE
:
1620 dump_code_signature (abfd
, linkedit
);
1622 case BFD_MACH_O_LC_SEGMENT_SPLIT_INFO
:
1623 dump_segment_split_info (abfd
, linkedit
);
1625 case BFD_MACH_O_LC_FUNCTION_STARTS
:
1626 dump_function_starts (abfd
, linkedit
);
1628 case BFD_MACH_O_LC_DATA_IN_CODE
:
1629 dump_data_in_code (abfd
, linkedit
);
1636 case BFD_MACH_O_LC_SUB_FRAMEWORK
:
1637 case BFD_MACH_O_LC_SUB_UMBRELLA
:
1638 case BFD_MACH_O_LC_SUB_LIBRARY
:
1639 case BFD_MACH_O_LC_SUB_CLIENT
:
1640 case BFD_MACH_O_LC_RPATH
:
1642 bfd_mach_o_str_command
*strc
= &cmd
->command
.str
;
1643 printf (" %s\n", strc
->str
);
1646 case BFD_MACH_O_LC_THREAD
:
1647 case BFD_MACH_O_LC_UNIXTHREAD
:
1648 dump_thread (abfd
, cmd
);
1650 case BFD_MACH_O_LC_ENCRYPTION_INFO
:
1652 bfd_mach_o_encryption_info_command
*cryp
=
1653 &cmd
->command
.encryption_info
;
1654 printf (" cryptoff: 0x%08x cryptsize: 0x%08x (endoff 0x%08x)"
1656 cryp
->cryptoff
, cryp
->cryptsize
,
1657 cryp
->cryptoff
+ cryp
->cryptsize
,
1661 case BFD_MACH_O_LC_DYLD_INFO
:
1662 dump_dyld_info (abfd
, cmd
, verbose
);
1664 case BFD_MACH_O_LC_VERSION_MIN_MACOSX
:
1665 case BFD_MACH_O_LC_VERSION_MIN_IPHONEOS
:
1666 case BFD_MACH_O_LC_VERSION_MIN_WATCHOS
:
1667 case BFD_MACH_O_LC_VERSION_MIN_TVOS
:
1669 bfd_mach_o_version_min_command
*ver
= &cmd
->command
.version_min
;
1672 printf_version (ver
->version
);
1673 printf ("\n sdk: ");
1674 printf_version (ver
->sdk
);
1678 case BFD_MACH_O_LC_SOURCE_VERSION
:
1680 bfd_mach_o_source_version_command
*version
=
1681 &cmd
->command
.source_version
;
1682 printf (" version a.b.c.d.e: %u.%u.%u.%u.%u\n",
1683 version
->a
, version
->b
, version
->c
, version
->d
, version
->e
);
1686 case BFD_MACH_O_LC_PREBOUND_DYLIB
:
1688 bfd_mach_o_prebound_dylib_command
*pbdy
= &cmd
->command
.prebound_dylib
;
1689 unsigned char *lm
= pbdy
->linked_modules
;
1693 printf (" dylib: %s\n", pbdy
->name_str
);
1694 printf (" nmodules: %u\n", pbdy
->nmodules
);
1695 printf (" linked modules (at %u): ",
1696 pbdy
->linked_modules_offset
- cmd
->offset
);
1697 last
= pbdy
->nmodules
> 32 ? 32 : pbdy
->nmodules
;
1698 for (j
= 0; j
< last
; j
++)
1699 printf ("%u", (lm
[j
>> 3] >> (j
& 7)) & 1);
1700 if (last
< pbdy
->nmodules
)
1705 case BFD_MACH_O_LC_PREBIND_CKSUM
:
1707 bfd_mach_o_prebind_cksum_command
*cksum
= &cmd
->command
.prebind_cksum
;
1708 printf (" 0x%08x\n", cksum
->cksum
);
1711 case BFD_MACH_O_LC_TWOLEVEL_HINTS
:
1713 bfd_mach_o_twolevel_hints_command
*hints
=
1714 &cmd
->command
.twolevel_hints
;
1716 printf (" table offset: 0x%08x nbr hints: %u\n",
1717 hints
->offset
, hints
->nhints
);
1719 dump_twolevel_hints (abfd
, hints
);
1722 case BFD_MACH_O_LC_MAIN
:
1724 bfd_mach_o_main_command
*entry
= &cmd
->command
.main
;
1725 printf (" entry offset: %#016" PRIx64
"\n"
1726 " stack size: %#016" PRIx64
"\n",
1727 entry
->entryoff
, entry
->stacksize
);
1730 case BFD_MACH_O_LC_NOTE
:
1732 bfd_mach_o_note_command
*note
= &cmd
->command
.note
;
1733 printf (" data owner: %.16s\n"
1734 " offset: %#016" PRIx64
"\n"
1735 " size: %#016" PRIx64
"\n",
1736 note
->data_owner
, note
->offset
, note
->size
);
1739 case BFD_MACH_O_LC_BUILD_VERSION
:
1740 dump_build_version (abfd
, cmd
);
1749 dump_load_commands (bfd
*abfd
, unsigned int cmd32
, unsigned int cmd64
)
1751 bfd_mach_o_data_struct
*mdata
= bfd_mach_o_get_data (abfd
);
1752 bfd_mach_o_load_command
*cmd
;
1755 for (cmd
= mdata
->first_command
, i
= 0; cmd
!= NULL
; cmd
= cmd
->next
, i
++)
1758 dump_load_command (abfd
, cmd
, i
, false);
1759 else if (cmd
->type
== cmd32
|| cmd
->type
== cmd64
)
1760 dump_load_command (abfd
, cmd
, i
, true);
1764 static const char * const unwind_x86_64_regs
[] =
1765 {"", "rbx", "r12", "r13", "r14", "r15", "rbp", "???" };
1767 static const char * const unwind_x86_regs
[] =
1768 {"", "ebx", "ecx", "edx", "edi", "edi", "ebp", "???" };
1770 /* Dump x86 or x86-64 compact unwind encoding. Works for both architecture,
1771 as the encoding is the same (but not register names). */
1774 dump_unwind_encoding_x86 (unsigned int encoding
, unsigned int sz
,
1775 const char * const regs_name
[])
1779 mode
= encoding
& MACH_O_UNWIND_X86_64_MODE_MASK
;
1782 case MACH_O_UNWIND_X86_64_MODE_RBP_FRAME
:
1785 char pfx
= sz
== 8 ? 'R' : 'E';
1787 regs
= encoding
& MACH_O_UNWIND_X86_64_RBP_FRAME_REGISTERS
;
1788 printf (" %cSP frame", pfx
);
1791 unsigned int offset
;
1794 offset
= (encoding
& MACH_O_UNWIND_X86_64_RBP_FRAME_OFFSET
) >> 16;
1795 printf (" at %cBP-%u:", pfx
, offset
* sz
);
1796 for (i
= 0; i
< 5; i
++)
1798 unsigned int reg
= (regs
>> (i
* 3)) & 0x7;
1799 if (reg
!= MACH_O_UNWIND_X86_64_REG_NONE
)
1800 printf (" %s", regs_name
[reg
]);
1805 case MACH_O_UNWIND_X86_64_MODE_STACK_IMMD
:
1806 case MACH_O_UNWIND_X86_64_MODE_STACK_IND
:
1808 unsigned int stack_size
;
1809 unsigned int reg_count
;
1810 unsigned int reg_perm
;
1811 unsigned int regs
[6];
1814 printf (" frameless");
1816 (encoding
& MACH_O_UNWIND_X86_64_FRAMELESS_STACK_SIZE
) >> 16;
1818 (encoding
& MACH_O_UNWIND_X86_64_FRAMELESS_REG_COUNT
) >> 10;
1819 reg_perm
= encoding
& MACH_O_UNWIND_X86_64_FRAMELESS_REG_PERMUTATION
;
1821 if (mode
== MACH_O_UNWIND_X86_64_MODE_STACK_IMMD
)
1822 printf (" size: 0x%03x", stack_size
* sz
);
1825 unsigned int stack_adj
;
1828 (encoding
& MACH_O_UNWIND_X86_64_FRAMELESS_STACK_ADJUST
) >> 13;
1829 printf (" size at 0x%03x + 0x%02x", stack_size
, stack_adj
* sz
);
1831 /* Registers are coded using arithmetic compression: the register
1832 is indexed in range 0-6, the second in range 0-5, the third in
1833 range 0-4, etc. Already used registers are removed in next
1835 #define DO_PERM(R, NUM) R = reg_perm / NUM; reg_perm -= R * NUM
1840 DO_PERM (regs
[0], 120);
1841 DO_PERM (regs
[1], 24);
1842 DO_PERM (regs
[2], 6);
1843 DO_PERM (regs
[3], 2);
1844 DO_PERM (regs
[4], 1);
1845 regs
[5] = 0; /* Not used if reg_count = 5. */
1848 DO_PERM (regs
[0], 60);
1849 DO_PERM (regs
[1], 12);
1850 DO_PERM (regs
[2], 3);
1851 DO_PERM (regs
[3], 1);
1854 DO_PERM (regs
[0], 20);
1855 DO_PERM (regs
[1], 4);
1856 DO_PERM (regs
[2], 1);
1859 DO_PERM (regs
[0], 5);
1860 DO_PERM (regs
[1], 1);
1863 DO_PERM (regs
[0], 1);
1868 printf (" [bad reg count]");
1873 for (i
= reg_count
- 1; i
>= 0; i
--)
1875 unsigned int inc
= 1;
1876 for (j
= 0; j
< i
; j
++)
1877 if (regs
[i
] >= regs
[j
])
1882 for (i
= 0; i
< (int) reg_count
; i
++)
1883 printf (" %s", regs_name
[regs
[i
]]);
1886 case MACH_O_UNWIND_X86_64_MODE_DWARF
:
1887 printf (" Dwarf offset: 0x%06x",
1888 encoding
& MACH_O_UNWIND_X86_64_DWARF_SECTION_OFFSET
);
1891 printf (" [unhandled mode]");
1896 /* Dump arm64 compact unwind entries. */
1899 dump_unwind_encoding_arm64 (unsigned int encoding
)
1901 switch (encoding
& MACH_O_UNWIND_ARM64_MODE_MASK
)
1903 case MACH_O_UNWIND_ARM64_MODE_FRAMELESS
:
1904 printf (" frameless");
1906 case MACH_O_UNWIND_ARM64_MODE_DWARF
:
1907 printf (" Dwarf offset: 0x%06x",
1908 encoding
& MACH_O_UNWIND_ARM64_DWARF_SECTION_OFFSET
);
1910 case MACH_O_UNWIND_ARM64_MODE_FRAME
:
1914 printf (" [unhandled mode]");
1917 switch (encoding
& MACH_O_UNWIND_ARM64_MODE_MASK
)
1919 case MACH_O_UNWIND_ARM64_MODE_FRAMELESS
:
1920 case MACH_O_UNWIND_ARM64_MODE_FRAME
:
1921 if (encoding
& MACH_O_UNWIND_ARM64_FRAME_X19_X20_PAIR
)
1922 printf (" x19-x20");
1923 if (encoding
& MACH_O_UNWIND_ARM64_FRAME_X21_X22_PAIR
)
1924 printf (" x21-x22");
1925 if (encoding
& MACH_O_UNWIND_ARM64_FRAME_X23_X24_PAIR
)
1926 printf (" x23-x24");
1927 if (encoding
& MACH_O_UNWIND_ARM64_FRAME_X25_X26_PAIR
)
1928 printf (" x25-x26");
1929 if (encoding
& MACH_O_UNWIND_ARM64_FRAME_X27_X28_PAIR
)
1930 printf (" x27-x28");
1933 switch (encoding
& MACH_O_UNWIND_ARM64_MODE_MASK
)
1935 case MACH_O_UNWIND_ARM64_MODE_FRAME
:
1936 if (encoding
& MACH_O_UNWIND_ARM64_FRAME_D8_D9_PAIR
)
1938 if (encoding
& MACH_O_UNWIND_ARM64_FRAME_D10_D11_PAIR
)
1939 printf (" d10-d11");
1940 if (encoding
& MACH_O_UNWIND_ARM64_FRAME_D12_D13_PAIR
)
1941 printf (" d12-d13");
1942 if (encoding
& MACH_O_UNWIND_ARM64_FRAME_D14_D15_PAIR
)
1943 printf (" d14-d15");
1945 case MACH_O_UNWIND_ARM64_MODE_FRAMELESS
:
1946 printf (" size: %u",
1947 (encoding
& MACH_O_UNWIND_ARM64_FRAMELESS_STACK_SIZE_MASK
) >> 8);
1953 dump_unwind_encoding (bfd_mach_o_data_struct
*mdata
, unsigned int encoding
)
1955 printf ("0x%08x", encoding
);
1959 switch (mdata
->header
.cputype
)
1961 case BFD_MACH_O_CPU_TYPE_X86_64
:
1962 dump_unwind_encoding_x86 (encoding
, 8, unwind_x86_64_regs
);
1964 case BFD_MACH_O_CPU_TYPE_I386
:
1965 dump_unwind_encoding_x86 (encoding
, 4, unwind_x86_regs
);
1967 case BFD_MACH_O_CPU_TYPE_ARM64
:
1968 dump_unwind_encoding_arm64 (encoding
);
1971 printf (" [unhandled cpu]");
1974 if (encoding
& MACH_O_UNWIND_HAS_LSDA
)
1976 if (encoding
& MACH_O_UNWIND_PERSONALITY_MASK
)
1977 printf (" PERS(%u)",
1978 ((encoding
& MACH_O_UNWIND_PERSONALITY_MASK
)
1979 >> MACH_O_UNWIND_PERSONALITY_SHIFT
));
1983 dump_obj_compact_unwind (bfd
*abfd
,
1984 const unsigned char *content
, bfd_size_type size
)
1986 bfd_mach_o_data_struct
*mdata
= bfd_mach_o_get_data (abfd
);
1987 int is_64
= mdata
->header
.version
== 2;
1988 const unsigned char *p
;
1990 printf ("Compact unwind info:\n");
1991 printf (" start length personality lsda\n");
1995 struct mach_o_compact_unwind_64
*e
=
1996 (struct mach_o_compact_unwind_64
*) content
;
1998 for (p
= content
; p
< content
+ size
; p
+= sizeof (*e
))
2000 e
= (struct mach_o_compact_unwind_64
*) p
;
2002 printf (" %#016" PRIx64
" %#08x %#016" PRIx64
" %#016" PRIx64
"\n",
2003 (uint64_t) bfd_get_64 (abfd
, e
->start
),
2004 (unsigned int) bfd_get_32 (abfd
, e
->length
),
2005 (uint64_t) bfd_get_64 (abfd
, e
->personality
),
2006 (uint64_t) bfd_get_64 (abfd
, e
->lsda
));
2008 printf (" encoding: ");
2009 dump_unwind_encoding (mdata
, bfd_get_32 (abfd
, e
->encoding
));
2015 printf ("unhandled\n");
2020 dump_exe_compact_unwind (bfd
*abfd
,
2021 const unsigned char *content
, bfd_size_type size
)
2023 bfd_mach_o_data_struct
*mdata
= bfd_mach_o_get_data (abfd
);
2024 struct mach_o_unwind_info_header
*hdr
;
2025 unsigned int version
;
2026 unsigned int encodings_offset
;
2027 unsigned int encodings_count
;
2028 unsigned int personality_offset
;
2029 unsigned int personality_count
;
2030 unsigned int index_offset
;
2031 unsigned int index_count
;
2032 struct mach_o_unwind_index_entry
*index_entry
;
2036 printf ("Compact unwind info:\n");
2038 hdr
= (struct mach_o_unwind_info_header
*) content
;
2039 if (size
< sizeof (*hdr
))
2041 printf (" truncated!\n");
2045 version
= bfd_get_32 (abfd
, hdr
->version
);
2046 if (version
!= MACH_O_UNWIND_SECTION_VERSION
)
2048 printf (" unknown version: %u\n", version
);
2051 encodings_offset
= bfd_get_32 (abfd
, hdr
->encodings_array_offset
);
2052 encodings_count
= bfd_get_32 (abfd
, hdr
->encodings_array_count
);
2053 personality_offset
= bfd_get_32 (abfd
, hdr
->personality_array_offset
);
2054 personality_count
= bfd_get_32 (abfd
, hdr
->personality_array_count
);
2055 index_offset
= bfd_get_32 (abfd
, hdr
->index_offset
);
2056 index_count
= bfd_get_32 (abfd
, hdr
->index_count
);
2057 printf (" %u encodings, %u personalities, %u level-1 indexes:\n",
2058 encodings_count
, personality_count
, index_count
);
2061 if (personality_count
> 0)
2063 const unsigned char *pers
= content
+ personality_offset
;
2065 printf (" personalities\n");
2066 for (i
= 0; i
< personality_count
; i
++)
2067 printf (" %u: 0x%08x\n", i
,
2068 (unsigned) bfd_get_32 (abfd
, pers
+ 4 * i
));
2071 /* Level-1 index. */
2072 printf (" idx function level2 off lsda off\n");
2074 index_entry
= (struct mach_o_unwind_index_entry
*) (content
+ index_offset
);
2075 for (i
= 0; i
< index_count
; i
++)
2077 unsigned int func_offset
;
2078 unsigned int level2_offset
;
2079 unsigned int lsda_offset
;
2081 func_offset
= bfd_get_32 (abfd
, index_entry
->function_offset
);
2082 level2_offset
= bfd_get_32 (abfd
, index_entry
->second_level_offset
);
2083 lsda_offset
= bfd_get_32 (abfd
, index_entry
->lsda_index_offset
);
2084 printf (" %3u 0x%08x 0x%08x 0x%08x\n",
2085 i
, func_offset
, level2_offset
, lsda_offset
);
2089 /* Level-1 index. */
2090 index_entry
= (struct mach_o_unwind_index_entry
*) (content
+ index_offset
);
2091 for (i
= 0; i
< index_count
; i
++)
2093 unsigned int func_offset
;
2094 unsigned int level2_offset
;
2095 const unsigned char *level2
;
2098 func_offset
= bfd_get_32 (abfd
, index_entry
->function_offset
);
2099 level2_offset
= bfd_get_32 (abfd
, index_entry
->second_level_offset
);
2101 /* No level-2 for this index (should be the last index). */
2102 if (level2_offset
== 0)
2105 level2
= content
+ level2_offset
;
2106 kind
= bfd_get_32 (abfd
, level2
);
2109 case MACH_O_UNWIND_SECOND_LEVEL_COMPRESSED
:
2111 struct mach_o_unwind_compressed_second_level_page_header
*l2
;
2112 unsigned int entry_offset
;
2113 unsigned int entry_count
;
2114 unsigned int l2_encodings_offset
;
2115 unsigned int l2_encodings_count
;
2116 const unsigned char *en
;
2119 l2
= (struct mach_o_unwind_compressed_second_level_page_header
*)
2121 entry_offset
= bfd_get_16 (abfd
, l2
->entry_page_offset
);
2122 entry_count
= bfd_get_16 (abfd
, l2
->entry_count
);
2123 l2_encodings_offset
= bfd_get_16 (abfd
, l2
->encodings_offset
);
2124 l2_encodings_count
= bfd_get_16 (abfd
, l2
->encodings_count
);
2126 printf (" index %2u: compressed second level: "
2127 "%u entries, %u encodings (at 0x%08x)\n",
2128 i
, entry_count
, l2_encodings_count
, l2_encodings_offset
);
2129 printf (" # function eidx encoding\n");
2131 en
= level2
+ entry_offset
;
2132 for (j
= 0; j
< entry_count
; j
++)
2135 unsigned int en_func
;
2136 unsigned int enc_idx
;
2137 unsigned int encoding
;
2138 const unsigned char *enc_addr
;
2140 entry
= bfd_get_32 (abfd
, en
);
2142 MACH_O_UNWIND_INFO_COMPRESSED_ENTRY_FUNC_OFFSET (entry
);
2144 MACH_O_UNWIND_INFO_COMPRESSED_ENTRY_ENCODING_INDEX (entry
);
2145 if (enc_idx
< encodings_count
)
2146 enc_addr
= content
+ encodings_offset
2149 enc_addr
= level2
+ l2_encodings_offset
2150 + 4 * (enc_idx
- encodings_count
);
2151 encoding
= bfd_get_32 (abfd
, enc_addr
);
2153 printf (" %4u 0x%08x [%3u] ", j
,
2154 func_offset
+ en_func
, enc_idx
);
2155 dump_unwind_encoding (mdata
, encoding
);
2163 case MACH_O_UNWIND_SECOND_LEVEL_REGULAR
:
2165 struct mach_o_unwind_regular_second_level_page_header
*l2
;
2166 struct mach_o_unwind_regular_second_level_entry
*en
;
2167 unsigned int entry_offset
;
2168 unsigned int entry_count
;
2171 l2
= (struct mach_o_unwind_regular_second_level_page_header
*)
2174 entry_offset
= bfd_get_16 (abfd
, l2
->entry_page_offset
);
2175 entry_count
= bfd_get_16 (abfd
, l2
->entry_count
);
2176 printf (" index %2u: regular level 2 at 0x%04x, %u entries\n",
2177 i
, entry_offset
, entry_count
);
2178 printf (" # function encoding\n");
2180 en
= (struct mach_o_unwind_regular_second_level_entry
*)
2181 (level2
+ entry_offset
);
2182 for (j
= 0; j
< entry_count
; j
++)
2184 unsigned int en_func
;
2185 unsigned int encoding
;
2187 en_func
= bfd_get_32 (abfd
, en
->function_offset
);
2188 encoding
= bfd_get_32 (abfd
, en
->encoding
);
2189 printf (" %-4u 0x%08x ", j
, en_func
);
2190 dump_unwind_encoding (mdata
, encoding
);
2198 printf (" index %2u: unhandled second level format (%u)\n",
2204 struct mach_o_unwind_lsda_index_entry
*lsda
;
2205 unsigned int lsda_offset
;
2206 unsigned int next_lsda_offset
;
2207 unsigned int nbr_lsda
;
2210 lsda_offset
= bfd_get_32 (abfd
, index_entry
->lsda_index_offset
);
2211 next_lsda_offset
= bfd_get_32 (abfd
, index_entry
[1].lsda_index_offset
);
2212 lsda
= (struct mach_o_unwind_lsda_index_entry
*)
2213 (content
+ lsda_offset
);
2214 nbr_lsda
= (next_lsda_offset
- lsda_offset
) / sizeof (*lsda
);
2215 for (j
= 0; j
< nbr_lsda
; j
++)
2217 printf (" lsda %3u: function 0x%08x lsda 0x%08x\n",
2218 j
, (unsigned int) bfd_get_32 (abfd
, lsda
->function_offset
),
2219 (unsigned int) bfd_get_32 (abfd
, lsda
->lsda_offset
));
2228 dump_section_content (bfd
*abfd
,
2229 const char *segname
, const char *sectname
,
2230 void (*dump
)(bfd
*, const unsigned char*, bfd_size_type
))
2232 bfd_mach_o_data_struct
*mdata
= bfd_mach_o_get_data (abfd
);
2233 bfd_mach_o_load_command
*cmd
;
2235 for (cmd
= mdata
->first_command
; cmd
!= NULL
; cmd
= cmd
->next
)
2237 if (cmd
->type
== BFD_MACH_O_LC_SEGMENT
2238 || cmd
->type
== BFD_MACH_O_LC_SEGMENT_64
)
2240 bfd_mach_o_segment_command
*seg
= &cmd
->command
.segment
;
2241 bfd_mach_o_section
*sec
;
2242 for (sec
= seg
->sect_head
; sec
!= NULL
; sec
= sec
->next
)
2243 if (strcmp (sec
->segname
, segname
) == 0
2244 && strcmp (sec
->sectname
, sectname
) == 0)
2247 asection
*bfdsec
= sec
->bfdsection
;
2248 unsigned char *content
;
2250 size
= bfd_section_size (bfdsec
);
2251 content
= (unsigned char *) xmalloc (size
);
2252 bfd_get_section_contents (abfd
, bfdsec
, content
, 0, size
);
2254 (*dump
)(abfd
, content
, size
);
2262 /* Dump ABFD (according to the options[] array). */
2265 mach_o_dump (bfd
*abfd
)
2267 if (options
[OPT_HEADER
].selected
)
2269 if (options
[OPT_SECTION
].selected
)
2270 dump_load_commands (abfd
, BFD_MACH_O_LC_SEGMENT
, BFD_MACH_O_LC_SEGMENT_64
);
2271 if (options
[OPT_MAP
].selected
)
2272 dump_section_map (abfd
);
2273 if (options
[OPT_LOAD
].selected
)
2274 dump_load_commands (abfd
, 0, 0);
2275 if (options
[OPT_DYSYMTAB
].selected
)
2276 dump_load_commands (abfd
, BFD_MACH_O_LC_DYSYMTAB
, 0);
2277 if (options
[OPT_CODESIGN
].selected
)
2278 dump_load_commands (abfd
, BFD_MACH_O_LC_CODE_SIGNATURE
, 0);
2279 if (options
[OPT_SEG_SPLIT_INFO
].selected
)
2280 dump_load_commands (abfd
, BFD_MACH_O_LC_SEGMENT_SPLIT_INFO
, 0);
2281 if (options
[OPT_FUNCTION_STARTS
].selected
)
2282 dump_load_commands (abfd
, BFD_MACH_O_LC_FUNCTION_STARTS
, 0);
2283 if (options
[OPT_DATA_IN_CODE
].selected
)
2284 dump_load_commands (abfd
, BFD_MACH_O_LC_DATA_IN_CODE
, 0);
2285 if (options
[OPT_TWOLEVEL_HINTS
].selected
)
2286 dump_load_commands (abfd
, BFD_MACH_O_LC_TWOLEVEL_HINTS
, 0);
2287 if (options
[OPT_COMPACT_UNWIND
].selected
)
2289 dump_section_content (abfd
, "__LD", "__compact_unwind",
2290 dump_obj_compact_unwind
);
2291 dump_section_content (abfd
, "__TEXT", "__unwind_info",
2292 dump_exe_compact_unwind
);
2294 if (options
[OPT_DYLD_INFO
].selected
)
2295 dump_load_commands (abfd
, BFD_MACH_O_LC_DYLD_INFO
, 0);
2298 /* Vector for Mach-O. */
2300 const struct objdump_private_desc objdump_private_desc_mach_o
=