1/* 2 * Copyright (c) 1999-2003 Apple Computer, Inc. All Rights Reserved. 3 * 4 * @APPLE_LICENSE_HEADER_START@ 5 * 6 * This file contains Original Code and/or Modifications of Original Code 7 * as defined in and that are subject to the Apple Public Source License 8 * Version 2.0 (the 'License'). You may not use this file except in 9 * compliance with the License. Please obtain a copy of the License at 10 * http://www.opensource.apple.com/apsl/ and read it before using this 11 * file. 12 * 13 * The Original Code and all software distributed under the License are 14 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER 15 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, 16 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, 17 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT. 18 * Please see the License for the specific language governing rights and 19 * limitations under the License. 20 * 21 * @APPLE_LICENSE_HEADER_END@ 22 */ 23#ifdef SHLIB 24#include "shlib.h" 25#endif /* SHLIB */ 26/* 27 * The Apple, Inc. Mach-O (Mach object file format) link-editor. This file 28 * contains the main() routine and the global error handling routines and other 29 * miscellaneous small global routines. It also defines the global varaibles 30 * that are set or changed by command line arguments. 31 */ 32#include <stdlib.h> 33#include <string.h> 34#include <stdarg.h> 35#include <sys/types.h> 36#include <sys/stat.h> 37#include <mach-o/loader.h> 38#include <mach-o/nlist.h> 39#include "stuff/arch.h" 40#include "stuff/version_number.h" 41#include "stuff/guess_short_name.h" 42#include "stuff/macosx_deployment_target.h" 43#include "stuff/execute.h" 44#if !(defined(KLD)) 45#include <stdio.h> 46#endif 47#if !(defined(KLD) && defined(__STATIC__)) 48#include <signal.h> 49#include <errno.h> 50#include <libc.h> 51#include <ar.h> 52#include <mach/mach.h> 53#include <mach/mach_error.h> 54#include "stuff/seg_addr_table.h" 55#ifndef RLD 56#include "stuff/symbol_list.h" 57#endif 58#include <mach/mach_init.h> 59#if defined(__OPENSTEP__) || defined(__GONZO_BUNSEN_BEAKER__) 60#include <servers/netname.h> 61#else 62#include <servers/bootstrap.h> 63#endif 64#else /* defined(KLD) && defined(__STATIC__) */ 65#include <mach/mach.h> 66#include <mach/kern_return.h> 67#endif /* !(defined(KLD) && defined(__STATIC__)) */ 68 69#include "ld.h" 70#ifndef RLD 71static char *mkstr( 72 const char *args, 73 ...); 74#endif /* !defined(RLD) */ 75#include "specs.h" 76#include "pass1.h" 77#include "live_refs.h" 78#include "objects.h" 79#include "sections.h" 80#include "fvmlibs.h" 81#include "symbols.h" 82#include "layout.h" 83#include "pass2.h" 84 85/* name of this program as executed (argv[0]) */ 86__private_extern__ char *progname = NULL; 87/* indication of an error set in error(), for processing a number of errors 88 and then exiting */ 89__private_extern__ unsigned long errors = 0; 90/* the pagesize of the machine this program is running on, getpagesize() value*/ 91__private_extern__ unsigned long host_pagesize = 0; 92/* the byte sex of the machine this program is running on */ 93__private_extern__ enum byte_sex host_byte_sex = UNKNOWN_BYTE_SEX; 94 95/* name of output file */ 96__private_extern__ char *outputfile = NULL; 97/* type of output file */ 98__private_extern__ unsigned long filetype = MH_EXECUTE; 99/* multi or single module dylib output */ 100__private_extern__ enum bool multi_module_dylib = TRUE; 101#ifndef RLD 102static enum bool filetype_specified = FALSE; 103static enum bool moduletype_specified = FALSE; 104/* if the -A flag is specified use to set the object file type */ 105static enum bool Aflag_specified = FALSE; 106#endif /* !defined(RLD) */ 107/* 108 * The architecture of the output file as specified by -arch and the cputype 109 * and cpusubtype of the object files being loaded which will be the output 110 * cputype and cpusubtype. specific_arch_flag is true if an -arch flag is 111 * specified and the flag for a specific implementation of an architecture. 112 */ 113__private_extern__ struct arch_flag arch_flag = 114#if defined(KLD) && defined(__STATIC__) 115 116#ifdef __ppc__ 117 { "ppc", CPU_TYPE_POWERPC, CPU_SUBTYPE_POWERPC_ALL }; 118#elif __i386__ 119 { "i386", CPU_TYPE_I386, CPU_SUBTYPE_I386_ALL }; 120#elif __arm__ 121 { "arm", CPU_TYPE_ARM, CPU_SUBTYPE_ARM_ALL }; 122#else 123#error "unsupported architecture for static KLD" 124#endif 125 126#else /* !(defined(KLD) && defined(__STATIC__)) */ 127 { 0 }; 128#endif /* defined(KLD) && defined(__STATIC__) */ 129__private_extern__ enum bool specific_arch_flag = FALSE; 130 131/* 132 * The -force_cpusubtype_ALL flag. 133 */ 134__private_extern__ enum bool force_cpusubtype_ALL = FALSE; 135 136/* the byte sex of the output file */ 137__private_extern__ enum byte_sex target_byte_sex = UNKNOWN_BYTE_SEX; 138static enum bool arch_multiple = FALSE; /* print one arch message before error*/ 139 140__private_extern__ 141enum bool trace = FALSE; /* print stages of link-editing */ 142__private_extern__ 143enum bool save_reloc = FALSE; /* save relocation information */ 144__private_extern__ 145enum bool output_for_dyld = FALSE; /* produce output for use with dyld */ 146__private_extern__ 147enum bool bind_at_load = FALSE; /* mark the output for dyld to be bound 148 when loaded */ 149__private_extern__ 150enum bool no_fix_prebinding = FALSE; /* mark the output for dyld to never 151 run fix_prebinding */ 152__private_extern__ 153enum bool load_map = FALSE; /* print a load map */ 154__private_extern__ 155enum bool define_comldsyms = TRUE; /* define common and link-editor defined 156 symbol reguardless of file type */ 157#ifndef RLD 158static enum bool 159 dflag_specified = FALSE; /* the -d flag has been specified */ 160#endif /* !defined(RLD) */ 161__private_extern__ 162enum bool seglinkedit = FALSE; /* create the link edit segment */ 163#ifndef RLD 164static enum bool 165 seglinkedit_specified = FALSE; /* if either -seglinkedit or */ 166 /* -noseglinkedit was specified */ 167#endif /* !defined(RLD) */ 168__private_extern__ 169enum bool whyload = FALSE; /* print why archive members are 170 loaded */ 171#ifndef RLD 172static enum bool whatsloaded = FALSE; /* print which object files are loaded*/ 173#endif /* !defined(RLD) */ 174__private_extern__ 175enum bool flush = TRUE; /* Use the output_flush routine to flush 176 output file by pages */ 177__private_extern__ 178enum bool sectorder_detail = FALSE; /* print sectorder warnings in detail */ 179__private_extern__ 180enum bool nowarnings = FALSE; /* suppress warnings */ 181__private_extern__ 182enum bool no_arch_warnings = FALSE; /* suppress wrong arch warnings */ 183__private_extern__ 184enum bool arch_errors_fatal = FALSE; /* cause wrong arch errors to be fatal*/ 185__private_extern__ 186enum bool archive_ObjC = FALSE; /* objective-C archive semantics */ 187__private_extern__ 188enum bool archive_all = FALSE; /* always load everything in archives */ 189__private_extern__ 190enum bool keep_private_externs = FALSE; /* don't turn private externs into 191 non-external symbols */ 192/* TRUE if -dynamic is specified, FALSE if -static is specified */ 193__private_extern__ 194enum bool dynamic = TRUE; 195#ifndef RLD 196static enum bool dynamic_specified = FALSE; 197static enum bool static_specified = FALSE; 198#endif 199 200/* The level of symbol table stripping */ 201__private_extern__ enum strip_levels strip_level = STRIP_DUP_INCLS; 202/* Strip the base file symbols (the -A argument's symbols) */ 203__private_extern__ enum bool strip_base_symbols = FALSE; 204 205/* strip dead blocks */ 206__private_extern__ enum bool dead_strip = FALSE; 207/* don't strip module init and term sections */ 208__private_extern__ enum bool no_dead_strip_inits_and_terms = FALSE; 209/* print timings for dead striping code */ 210__private_extern__ enum bool dead_strip_times = FALSE; 211 212#ifndef RLD 213/* 214 * Data structures to perform selective exporting of global symbols. 215 * save_symbols is the names of the symbols from -exported_symbols_list 216 * remove_symbols is the names of the symbols from -unexported_symbols_list 217 */ 218__private_extern__ struct symbol_list *save_symbols = NULL; 219__private_extern__ uint32_t nsave_symbols = 0; 220__private_extern__ struct symbol_list *remove_symbols = NULL; 221__private_extern__ uint32_t nremove_symbols = 0; 222 223/* 224 * -executable_path option's argument, executable_path is used to replace 225 * @executable_path for dependent libraries. 226 */ 227__private_extern__ char *executable_path = NULL; 228#endif /* RLD */ 229 230 231/* The list of symbols to be traced */ 232__private_extern__ char **trace_syms = NULL; 233__private_extern__ unsigned long ntrace_syms = 0; 234 235/* The number of references of undefined symbols to print */ 236__private_extern__ unsigned long Yflag = 0; 237 238/* The list of allowed undefined symbols */ 239__private_extern__ char **undef_syms = NULL; 240__private_extern__ unsigned long nundef_syms = 0; 241 242/* The list of -dylib_file arguments */ 243__private_extern__ char **dylib_files = NULL; 244__private_extern__ unsigned long ndylib_files = 0; 245 246/* The checking for undefined symbols */ 247__private_extern__ enum undefined_check_level undefined_flag = UNDEFINED_ERROR; 248#ifndef RLD 249static enum bool undefined_flag_specified = FALSE; 250#endif 251 252/* The checking for (twolevel namespace) multiply defined symbols */ 253__private_extern__ enum multiply_defined_check_level 254 multiply_defined_flag = MULTIPLY_DEFINED_WARNING; 255__private_extern__ enum multiply_defined_check_level 256 multiply_defined_unused_flag = MULTIPLY_DEFINED_SUPPRESS; 257/* the -nomultidefs option */ 258__private_extern__ enum bool nomultidefs = FALSE; 259#ifndef RLD 260static enum bool multiply_defined_flag_specified = FALSE; 261static enum bool multiply_defined_unused_flag_specified = FALSE; 262#endif 263 264/* The checking for read only relocs */ 265__private_extern__ enum read_only_reloc_check_level 266 read_only_reloc_flag = READ_ONLY_RELOC_ERROR; 267 268/* The checking for section difference relocs */ 269__private_extern__ enum sect_diff_reloc_check_level 270 sect_diff_reloc_flag = SECT_DIFF_RELOC_SUPPRESS; 271 272/* The handling for weak reference mismatches */ 273__private_extern__ enum weak_reference_mismatches_handling 274 weak_reference_mismatches = WEAK_REFS_MISMATCH_ERROR; 275 276/* The Mac OS X deployment target */ 277__private_extern__ struct macosx_deployment_target 278 macosx_deployment_target = { 0 }; 279 280/* The prebinding optimization */ 281#ifndef RLD 282static enum bool prebinding_flag_specified = FALSE; 283#endif 284__private_extern__ enum bool prebinding = FALSE; 285__private_extern__ enum bool prebind_allow_overlap = FALSE; 286__private_extern__ enum bool prebind_all_twolevel_modules = FALSE; 287#ifndef RLD 288static enum bool read_only_reloc_flag_specified = FALSE; 289static enum bool sect_diff_reloc_flag_specified = FALSE; 290static enum bool weak_reference_mismatches_specified = FALSE; 291static enum bool prebind_all_twolevel_modules_specified = FALSE; 292static enum bool unprebound_library( 293 char *dylib_install_name, 294 char *seg_addr_table_filename); 295#endif 296 297/* True if -m is specified to allow multiply symbols, as a warning */ 298__private_extern__ enum bool allow_multiply_defined_symbols = FALSE; 299 300/* The segment alignment and pagezero_size, note the segalign is reset in 301 * layout() by get_segalign_from_flag() based on the target architecture. 302 */ 303__private_extern__ unsigned long segalign = 0x2000; 304#ifndef RLD 305__private_extern__ enum bool segalign_specified = FALSE; 306#endif /* !defined(RLD) */ 307__private_extern__ unsigned long pagezero_size = 0; 308 309/* The default section alignment */ 310__private_extern__ unsigned long defaultsectalign = DEFAULTSECTALIGN; 311 312/* The first segment address */ 313__private_extern__ unsigned long seg1addr = 0; 314__private_extern__ enum bool seg1addr_specified = FALSE; 315 316/* read-only and read-write segment addresses */ 317__private_extern__ unsigned long segs_read_only_addr = 0; 318__private_extern__ enum bool segs_read_only_addr_specified = FALSE; 319__private_extern__ unsigned long segs_read_write_addr = 0; 320__private_extern__ enum bool segs_read_write_addr_specified = FALSE; 321 322#ifndef RLD 323/* file name of the segment address table */ 324static char *seg_addr_table_name = NULL; 325/* the file system path name to use instead of the install name */ 326static char *seg_addr_table_filename = NULL; 327#endif /* !defined(RLD) */ 328 329/* The stack address and size */ 330__private_extern__ unsigned long stack_addr = 0; 331__private_extern__ enum bool stack_addr_specified = FALSE; 332__private_extern__ unsigned long stack_size = 0; 333__private_extern__ enum bool stack_size_specified = FALSE; 334 335/* TRUE if -allow_stack_execute is specified */ 336__private_extern__ enum bool allow_stack_execute = FALSE; 337 338#ifndef RLD 339/* A -segaddr option was specified */ 340static enum bool segaddr_specified = FALSE; 341#endif /* !defined(RLD) */ 342 343/* 344 * The header pad, the default is set to the size of a section strcuture so 345 * that if /bin/objcunique is run on the result and up to two sections can be 346 * added. 347 */ 348__private_extern__ unsigned long headerpad = sizeof(struct section) * 2; 349#ifndef RLD 350static enum bool headerpad_specified = FALSE; 351#endif /* !defined(RLD) */ 352/* 353 * If specified makes sure the header pad is big enough to change all the 354 * install name of the dylibs in the output to MAXPATHLEN. 355 */ 356__private_extern__ enum bool headerpad_max_install_names = FALSE; 357 358/* The name of the specified entry point */ 359__private_extern__ char *entry_point_name = NULL; 360 361/* The name of the specified library initialization routine */ 362__private_extern__ char *init_name = NULL; 363 364/* The dylib information */ 365__private_extern__ char *dylib_install_name = NULL; 366__private_extern__ uint32_t dylib_current_version = 0; 367__private_extern__ uint32_t dylib_compatibility_version = 0; 368 369/* the umbrella/sub/client framework information */ 370__private_extern__ enum bool sub_framework = FALSE; 371__private_extern__ enum bool umbrella_framework = FALSE; 372__private_extern__ char *sub_framework_name = NULL; 373__private_extern__ char *umbrella_framework_name = NULL; 374__private_extern__ char *client_name = NULL; 375__private_extern__ char **allowable_clients = NULL; 376__private_extern__ unsigned long nallowable_clients = 0; 377 378/* The list of sub_umbrella frameworks */ 379__private_extern__ char **sub_umbrellas = NULL; 380__private_extern__ unsigned long nsub_umbrellas = 0; 381 382/* The list of sub_library dynamic libraries */ 383__private_extern__ char **sub_librarys = NULL; 384__private_extern__ unsigned long nsub_librarys = 0; 385 386/* The dylinker information */ 387__private_extern__ char *dylinker_install_name = NULL; 388 389#ifndef RLD 390/* set to the -bundle_loader argument if specified */ 391static char *bundle_loader = NULL; 392#endif 393 394/* set to TRUE if -private_bundle is specified */ 395__private_extern__ enum bool private_bundle = FALSE; 396 397/* The value of the environment variable NEXT_ROOT or the -syslibroot argument*/ 398__private_extern__ char *next_root = NULL; 399#ifndef RLD 400static enum bool syslibroot_specified = FALSE; 401#endif 402 403/* TRUE if the environment variable LD_TRACE_ARCHIVES 404 (or temporarily RC_TRACE_ARCHIVES) is set */ 405__private_extern__ enum bool ld_trace_archives = FALSE; 406 407/* TRUE if the environment variable LD_TRACE_DYLIBS 408 (or temporarily RC_TRACE_DYLIBS) is set */ 409__private_extern__ enum bool ld_trace_dylibs = FALSE; 410 411/* TRUE if the environment variable LD_TRACE_PREBINDING_DISABLED 412 (or temporarily LD_TRACE_PREBINDING_DISABLED) is set */ 413__private_extern__ enum bool ld_trace_prebinding_disabled = FALSE; 414 415#ifndef KLD 416/* The file LD_TRACE_FILE references, or NULL if none is set */ 417static const char *trace_file_path = NULL; 418#endif 419 420/* the argument to -final_output if any */ 421__private_extern__ char *final_output = NULL; 422 423/* The variables to support namespace options */ 424__private_extern__ enum bool namespace_specified = FALSE; 425__private_extern__ enum bool twolevel_namespace = TRUE; 426__private_extern__ enum bool force_flat_namespace = FALSE; 427 428#ifndef RLD 429/* Variable to support options logging. */ 430static enum bool ld_print_options = FALSE; 431#endif 432 433/* 434 * Because the MacOS X 10.0 code in libSystem for the NSObjectFileImage*() APIs 435 * does not ignore unknown load commands if MH_BUNDLE files are built with 436 * two-level namespace hints the LC_TWOLEVEL_HINTS load command will produce a 437 * "malformed object" errors. So to make the MacOS X 10.1 ld(1) produce 438 * MH_BUNDLE files that will work on MacOS X 10.0 the hints table is not 439 * produced by default for MH_BUNDLE files. 440 */ 441#ifndef RLD 442static enum bool twolevel_namespace_hints_specified = FALSE; 443#endif 444__private_extern__ enum bool twolevel_namespace_hints = TRUE; 445 446#ifdef DEBUG 447__private_extern__ unsigned long debug = 0; /* link-editor debugging */ 448#endif /* DEBUG */ 449 450#ifdef RLD 451/* the cleanup routine for fatal errors to remove the output file */ 452__private_extern__ void cleanup(void); 453#else /* !defined(RLD) */ 454static void cleanup(void); 455static void ld_exit(int exit_value); 456 457/* The signal hander routine for SIGINT, SIGTERM, SIGBUS & SIGSEGV */ 458static void handler(int sig); 459 460/* Static routines to help parse arguments */ 461static enum bool ispoweroftwo(unsigned long x); 462static vm_prot_t getprot(char *prot, char **endp); 463static enum bool check_max_init_prot(vm_prot_t maxprot, vm_prot_t initprot); 464 465/* apple_version is created by the libstuff/Makefile */ 466extern char apple_version[]; 467 468/* 469 * main() parses the command line arguments and drives the link-edit process. 470 */ 471int 472main( 473int argc, 474char *argv[], 475char *envp[]) 476{ 477 int i; 478 unsigned long j, symbols_created, objects_specified, sections_created; 479 uint32_t table_size; 480 int fd; 481 char *p, *symbol_name, *indr_symbol_name, *endp, *file_name; 482 char *filelist, *dirname, *addr, *env_seg_addr_table_name; 483 struct seg_addr_table *seg_addr_table, *seg_addr_table_entry; 484 struct segment_spec *seg_spec; 485 struct section_spec *sect_spec; 486 unsigned long align, tmp; 487 struct stat stat_buf; 488 kern_return_t r; 489 const struct arch_flag *family_arch_flag; 490 enum undefined_check_level new_undefined_flag; 491 enum multiply_defined_check_level new_multiply_defined_flag, 492 new_multiply_defined_unused_flag; 493 enum read_only_reloc_check_level new_read_only_reloc_flag; 494 enum sect_diff_reloc_check_level new_sect_diff_reloc_flag; 495 enum weak_reference_mismatches_handling new_weak_reference_mismatches; 496 enum bool is_framework; 497 char *has_suffix; 498 struct symbol_list *sp; 499 char *exported_symbols_list, *unexported_symbols_list; 500 enum bool missing_syms; 501 enum bool vflag; 502 enum bool prebinding_via_LD_PREBIND; 503 enum bool hash_instrument_specified; 504 char *ld_library_path; 505 506#ifdef __MWERKS__ 507 char **dummy; 508 dummy = envp; 509#endif 510 511 vflag = FALSE; 512 exported_symbols_list = NULL; 513 unexported_symbols_list = NULL; 514 seg_addr_table_entry = NULL; 515 hash_instrument_specified = FALSE; 516 517 progname = argv[0]; 518#ifndef BINARY_COMPARE 519 host_pagesize = 0x2000; 520#else 521 host_pagesize = getpagesize(); 522#endif 523 host_byte_sex = get_host_byte_sex(); 524 525 if(argc == 1) 526 fatal("Usage: %s [options] file [...]", progname); 527 528 /* 529 * If interrupt and termination signal are not being ignored catch 530 * them so things can be cleaned up. 531 */ 532 if(signal(SIGINT, SIG_IGN) != SIG_IGN) 533 signal(SIGINT, handler); 534 if(signal(SIGTERM, SIG_IGN) != SIG_IGN) 535 signal(SIGTERM, handler); 536 if(signal(SIGBUS, SIG_IGN) != SIG_IGN) 537 signal(SIGBUS, handler); 538 if(signal(SIGSEGV, SIG_IGN) != SIG_IGN) 539 signal(SIGSEGV, handler); 540 541 /* This needs to be here so that we test the environment variable before 542 the rest of options parsing. */ 543 if (getenv("LD_PRINT_OPTIONS") != NULL) 544 ld_print_options = TRUE; 545 546 /* 547 * Parse the command line options in this pass and skip the object files 548 * and symbol creation flags in this pass. This will make sure optionsd 549 * like -Ldir are not position dependent relative to -lx options (the 550 * same for -ysymbol relative to object files, etc). 551 */ 552 for(i = 1 ; i < argc ; i++){ 553 if(*argv[i] != '-'){ 554 /* object file argv[i] processed in the next pass of 555 parsing arguments */ 556 continue; 557 } 558 else{ 559 if (ld_print_options == TRUE) 560 print("[Logging ld options]\t%s\n", argv[i]); 561 562 p = &(argv[i][1]); 563 switch(*p){ 564 case 'l': 565 if(p[1] == '\0') 566 fatal("-l: argument missing"); 567 /* path searched abbrevated file name, processed in the 568 next pass of parsing arguments */ 569 break; 570 571 /* Flags effecting search path of -lx arguments */ 572 case 'L': 573 if(p[1] == '\0') 574 fatal("-L: directory name missing"); 575 /* add a pathname to the list of search paths */ 576 search_dirs = reallocate(search_dirs, 577 (nsearch_dirs + 1) * sizeof(char *)); 578 search_dirs[nsearch_dirs++] = &(p[1]); 579 if(stat(&(p[1]), &stat_buf) == -1) 580 warning("-L: directory name (%s) does not exist", 581 &(p[1])); 582 break; 583 case 'Z': 584 if(p[1] != '\0') 585 goto unknown_flag; 586 /* do not use the standard search path */ 587 standard_dirs[0] = NULL; 588 standard_framework_dirs[0] = NULL; 589 break; 590 591 /* File format flags */ 592 case 'M': 593 if(strcmp(p, "Mach") == 0){ 594 if(filetype_specified == TRUE && filetype != MH_EXECUTE) 595 fatal("more than one output filetype specified"); 596 filetype_specified = TRUE; 597 filetype = MH_EXECUTE; 598 } 599 else if(strcmp(p, "M") == 0){ 600 /* produce load map */ 601 load_map = TRUE; 602 } 603 else 604 goto unknown_flag; 605 break; 606 case 'p': 607 if(strcmp(p, "preload") == 0 || p[1] == '\0'){ 608 if(filetype_specified == TRUE && filetype != MH_PRELOAD) 609 fatal("more than one output filetype specified"); 610 filetype_specified = TRUE; 611 filetype = MH_PRELOAD; 612 } 613 else if(strcmp(p, "pagezero_size") == 0){ 614 if(i + 1 >= argc) 615 fatal("-pagezero_size: argument missing"); 616 if(pagezero_size != 0) 617 fatal("-pagezero_size: multiply specified"); 618 pagezero_size = strtoul(argv[i+1], &endp, 16); 619 if(*endp != '\0') 620 fatal("size for -pagezero_size %s not a proper " 621 "hexadecimal number", argv[i+1]); 622 if(pagezero_size == 0) 623 fatal("size for -pagezero_size %s must not be zero", 624 argv[i+1]); 625 i += 1; 626 } 627 else if(strcmp(p, "prebind") == 0){ 628 if(prebinding_flag_specified == TRUE && 629 prebinding == FALSE) 630 fatal("both -prebind and -noprebind can't " 631 "be specified"); 632 prebinding_flag_specified = TRUE; 633 prebinding = TRUE; 634 } 635 else if(strcmp(p, "prebind_allow_overlap") == 0){ 636 prebind_allow_overlap = TRUE; 637 } 638 else if(strcmp(p, "prebind_all_twolevel_modules") == 0){ 639 if(prebind_all_twolevel_modules_specified == TRUE && 640 prebind_all_twolevel_modules == FALSE) 641 fatal("both -prebind_all_twolevel_modules and " 642 "-noprebind_all_twolevel_modules can't be " 643 "specified"); 644 prebind_all_twolevel_modules = TRUE; 645 prebind_all_twolevel_modules_specified = TRUE; 646 } 647 else if(strcmp(p, "private_bundle") == 0){ 648 private_bundle = TRUE; 649 } 650 else 651 goto unknown_flag; 652 break; 653 case 'f': 654 if(p[1] == '\0') 655 fatal("use of old flag -f (old version of mkshlib(1) " 656 "will not work with this version of ld(1))"); 657 else if(strcmp(p, "fvmlib") == 0){ 658 if(filetype_specified == TRUE && filetype != MH_FVMLIB) 659 fatal("more than one output filetype specified"); 660 filetype_specified = TRUE; 661 filetype = MH_FVMLIB; 662 } 663 else if(strcmp(p, "force_cpusubtype_ALL") == 0){ 664 force_cpusubtype_ALL = TRUE; 665 } 666 else if(strcmp(p, "framework") == 0){ 667 if(i + 1 >= argc) 668 fatal("-framework: argument missing"); 669 /* path searched abbrevated framework name, processed 670 in the next pass of parsing arguments */ 671 i += 1; 672 } 673 else if(strcmp(p, "filelist") == 0){ 674 if(i + 1 >= argc) 675 fatal("-filelist: argument missing"); 676 /* filelist of object names, processed 677 in the next pass of parsing arguments */ 678 i += 1; 679 } 680 else if(strcmp(p, "flat_namespace") == 0){ 681 if(namespace_specified == TRUE && 682 twolevel_namespace == TRUE) 683 fatal("can't specify both -flat_namespace and " 684 "-twolevel_namespace"); 685 namespace_specified = TRUE; 686 twolevel_namespace = FALSE; 687 } 688 else if(strcmp(p, "force_flat_namespace") == 0){ 689 if(namespace_specified == TRUE && 690 twolevel_namespace == TRUE) 691 fatal("can't specify both -force_flat_namespace " 692 "and -twolevel_namespace"); 693 force_flat_namespace = TRUE; 694 twolevel_namespace = FALSE; 695 } 696 else if(strcmp(p, "final_output") == 0){ 697 if(i + 1 >= argc) 698 fatal("-final_output: argument missing"); 699 if(final_output != NULL) 700 fatal("-final_output multiply specified"); 701 final_output = argv[i+1]; 702 i += 1; 703 } 704 else 705 goto unknown_flag; 706 break; 707 708 case 'F': 709 if(p[1] == '\0') 710 fatal("-F: directory name missing"); 711 /* add a pathname to the list of framework search paths */ 712 framework_dirs = reallocate(framework_dirs, 713 (nframework_dirs + 1) * sizeof(char *)); 714 framework_dirs[nframework_dirs++] = &(p[1]); 715 if(stat(&(p[1]), &stat_buf) == -1) 716 warning("-F: directory name (%s) does not exist", 717 &(p[1])); 718 break; 719 720 case 'r': 721 if(strcmp(p, "read_only_relocs") == 0){ 722 if(++i >= argc) 723 fatal("-read_only_relocs: argument missing"); 724 if(strcmp(argv[i], "error") == 0) 725 new_read_only_reloc_flag = READ_ONLY_RELOC_ERROR; 726 else if(strcmp(argv[i], "warning") == 0) 727 new_read_only_reloc_flag = READ_ONLY_RELOC_WARNING; 728 else if(strcmp(argv[i], "suppress") == 0) 729 new_read_only_reloc_flag = READ_ONLY_RELOC_SUPPRESS; 730 else{ 731 fatal("-read_only_relocs: unknown argument: %s", 732 argv[i]); 733 new_read_only_reloc_flag = READ_ONLY_RELOC_ERROR; 734 } 735 if(read_only_reloc_flag_specified == TRUE && 736 new_read_only_reloc_flag != read_only_reloc_flag) 737 fatal("more than one value specified for " 738 "-read_only_relocs"); 739 read_only_reloc_flag_specified = TRUE; 740 read_only_reloc_flag = new_read_only_reloc_flag; 741 break; 742 } 743 else if(strcmp(p, "run_init_lazily") == 0){ 744 warning("-run_init_lazily is obsolete"); 745 break; 746 } 747 if(p[1] != '\0') 748 goto unknown_flag; 749 /* save relocation information, and produce a relocatable 750 object */ 751 save_reloc = TRUE; 752 if(filetype_specified == FALSE) 753 filetype = MH_OBJECT; 754 if(dflag_specified == FALSE) 755 define_comldsyms = FALSE; 756 break; 757 case 'A': 758 if(p[1] != '\0') 759 goto unknown_flag; 760 if(++i >= argc) 761 fatal("-A: argument missing"); 762 /* object file argv[i] processed in the next pass of 763 parsing arguments */ 764 Aflag_specified = TRUE; 765 break; 766 case 'd': 767 if(strcmp(p, "d") == 0){ 768 /* define common symbols and loader defined symbols 769 reguardless of file format */ 770 dflag_specified = TRUE; 771 define_comldsyms = TRUE; 772 } 773 else if(strcmp(p, "dynamic") == 0){ 774 if(static_specified) 775 fatal("only one of -dynamic or -static can be " 776 "specified"); 777 778 dynamic = TRUE; 779 dynamic_specified = TRUE; 780 } 781 else if(strcmp(p, "dylib") == 0){ 782 if(filetype_specified == TRUE && filetype != MH_DYLIB) 783 fatal("more than one output filetype specified"); 784 filetype_specified = TRUE; 785 filetype = MH_DYLIB; 786 output_for_dyld = TRUE; 787 } 788 else if(strcmp(p, "dylib_install_name") == 0){ 789 if(i + 1 >= argc) 790 fatal("-dylib_install_name: argument missing"); 791 dylib_install_name = argv[i + 1]; 792 i += 1; 793 } 794 else if(strcmp(p, "dylib_current_version") == 0){ 795 if(i + 1 >= argc) 796 fatal("-dylib_current_version: argument missing"); 797 if(get_version_number("-dylib_current_version", 798 argv[i+1], &dylib_current_version) == FALSE) 799 cleanup(); 800 if(dylib_current_version == 0) 801 fatal("-dylib_current_version must be greater than " 802 "zero"); 803 i += 1; 804 } 805 else if(strcmp(p, "dylib_compatibility_version") == 0){ 806 if(i + 1 >= argc) 807 fatal("-dylib_compatibility_version: argument " 808 "missing"); 809 if(get_version_number("-dylib_compatibility_version", 810 argv[i+1], &dylib_compatibility_version) == FALSE) 811 cleanup(); 812 if(dylib_compatibility_version == 0) 813 fatal("-dylib_compatibility_version must be " 814 "greater than zero"); 815 i += 1; 816 } 817 else if(strcmp(p, "dylib_file") == 0){ 818 if(++i >= argc) 819 fatal("-dylib_file: argument missing"); 820 file_name = strchr(argv[i], ':'); 821 if(file_name == NULL || 822 file_name[1] == '\0' || argv[i][0] == ':') 823 fatal("-dylib_file argument: %s must have a ':' " 824 "between its file names", argv[i]); 825 dylib_files = reallocate(dylib_files, 826 (ndylib_files + 1) * sizeof(char *)); 827 dylib_files[ndylib_files++] = argv[i]; 828 } 829 else if(strcmp(p, "dylinker") == 0){ 830 if(filetype_specified == TRUE && 831 filetype != MH_DYLINKER) 832 fatal("more than one output filetype specified"); 833 filetype_specified = TRUE; 834 filetype = MH_DYLINKER; 835 output_for_dyld = TRUE; 836 } 837 else if(strcmp(p, "dylinker_install_name") == 0){ 838 if(i + 1 >= argc) 839 fatal("-dylinker_install_name: argument missing"); 840 if(dylinker_install_name != NULL) 841 fatal("-dylinker_install_name multiply specified"); 842 dylinker_install_name = argv[i + 1]; 843 i += 1; 844 } 845 else if(strcmp(p, "dead_strip") == 0){ 846 dead_strip = TRUE; 847 } 848 else if(strcmp(p, "dead_strip_times") == 0){ 849 dead_strip_times = TRUE; 850 } 851#ifdef DEBUG 852 else if(strcmp(p, "debug") == 0){ 853 if(++i >= argc) 854 fatal("-debug: argument missing"); 855 debug |= 1 << strtoul(argv[i], &endp, 10); 856 if(*endp != '\0' || strtoul(argv[i], &endp, 10) > 32) 857 fatal("argument for -debug %s not a proper " 858 "decimal number less than 32", argv[i]); 859 } 860#endif /* DEBUG */ 861 else 862 goto unknown_flag; 863 break; 864 865 case 'n': 866 if(strcmp(p, "noflush") == 0){ 867 flush = FALSE; 868 } 869 else if(strcmp(p, "nofixprebinding") == 0){ 870 no_fix_prebinding = TRUE; 871 } 872 else if(strcmp(p, "no_arch_warnings") == 0){ 873 no_arch_warnings = TRUE; 874 } 875 else if(strcmp(p, "noseglinkedit") == 0){ 876 if(seglinkedit_specified && seglinkedit == TRUE) 877 fatal("both -seglinkedit and -noseglinkedit can't " 878 "be specified"); 879 seglinkedit = FALSE; 880 seglinkedit_specified = TRUE; 881 } 882 else if(strcmp(p, "noprebind") == 0){ 883 if(prebinding_flag_specified == TRUE && 884 prebinding == TRUE) 885 fatal("both -prebind and -noprebind can't " 886 "be specified"); 887 prebinding_flag_specified = TRUE; 888 prebinding = FALSE; 889 } 890 else if(strcmp(p, "nomultidefs") == 0){ 891 nomultidefs = TRUE; 892 } 893 else if(strcmp(p, "noprebind_all_twolevel_modules") == 0){ 894 if(prebind_all_twolevel_modules_specified == TRUE && 895 prebind_all_twolevel_modules == TRUE) 896 fatal("both -prebind_all_twolevel_modules and " 897 "-noprebind_all_twolevel_modules can't be " 898 "specified"); 899 prebind_all_twolevel_modules = FALSE; 900 prebind_all_twolevel_modules_specified = TRUE; 901 } 902 else if(strcmp(p, "no_dead_strip_inits_and_terms") == 0){ 903 no_dead_strip_inits_and_terms = TRUE; 904 } 905 else if(strcmp(p, "no_uuid") == 0){ 906 output_uuid_info.suppress = TRUE; 907 } 908 else if(strcmp(p, "noall_load") == 0){ 909 /* Ignore the flag. */ 910 ; 911 } 912 else 913 goto unknown_flag; 914 break; 915 916 case 'b': 917 if(strcmp(p, "bundle") == 0){ 918 if(filetype_specified == TRUE && filetype != MH_BUNDLE) 919 fatal("more than one output filetype specified"); 920 filetype_specified = TRUE; 921 filetype = MH_BUNDLE; 922 output_for_dyld = TRUE; 923 } 924 else if(strcmp(p, "bind_at_load") == 0){ 925 bind_at_load = TRUE; 926 } 927 else if(strcmp(p, "bundle_loader") == 0){ 928 if(i + 1 >= argc) 929 fatal("-bundle_loader: argument missing"); 930 if(bundle_loader != NULL) 931 fatal("-bundle_loader multiply specified"); 932 bundle_loader = argv[i + 1]; 933 i += 1; 934 } 935 /* Strip the base file symbols (the -A argument's symbols)*/ 936 else if(p[1] == '\0') 937 strip_base_symbols = TRUE; 938 else 939 goto unknown_flag; 940 break; 941 942 /* 943 * Stripping level flags, in increasing level of stripping. The 944 * level of stripping is set to the maximum level specified. 945 */ 946 case 'X': 947 if(p[1] != '\0') 948 goto unknown_flag; 949 if(strip_level < STRIP_L_SYMBOLS) 950 strip_level = STRIP_L_SYMBOLS; 951 break; 952 case 'S': 953 if(strcmp(p, "Sn") == 0){ 954 strip_level = STRIP_NONE; 955 } 956 else if(strcmp(p, "Si") == 0){ 957 if(strip_level < STRIP_DUP_INCLS) 958 strip_level = STRIP_DUP_INCLS; 959 } 960 else if(strcmp(p, "Sp") == 0){ 961 if(strip_level < STRIP_MIN_DEBUG) 962 strip_level = STRIP_MIN_DEBUG; 963 } 964 else if(p[1] == '\0'){ 965 if(strip_level < STRIP_DEBUG) 966 strip_level = STRIP_DEBUG; 967 } 968 else{ 969 goto unknown_flag; 970 } 971 break; 972 case 'x': 973 if(p[1] != '\0') 974 goto unknown_flag; 975 if(strip_level < STRIP_NONGLOBALS) 976 strip_level = STRIP_NONGLOBALS; 977 break; 978 case 's': 979 if(strcmp(p, "s") == 0){ 980 strip_level = STRIP_ALL; 981 } 982 else if(strcmp(p, "static") == 0){ 983 if(dynamic_specified) 984 fatal("only one of -static or -dynamic can be " 985 "specified"); 986 dynamic = FALSE; 987 static_specified = TRUE; 988 twolevel_namespace = FALSE; 989 } 990 else if(strcmp(p, "search_paths_first") == 0){ 991 search_paths_first = TRUE; 992 } 993 /* 994 * Flags for specifing information about sections. 995 */ 996 /* create a section from the contents of a file 997 -sectcreate <segname> <sectname> <filename> */ 998 else if(strcmp(p, "sectcreate") == 0 || 999 strcmp(p, "segcreate") == 0){ /* the old name */ 1000 if(i + 3 >= argc) 1001 fatal("%s: arguments missing", argv[i]); 1002 seg_spec = create_segment_spec(argv[i+1]); 1003 sect_spec = create_section_spec(seg_spec, argv[i+2]); 1004 if(sect_spec->contents_filename != NULL) 1005 fatal("section (%s,%s) multiply specified with a " 1006 "%s option", argv[i+1], argv[i+2], argv[i]); 1007 if((fd = open(argv[i+3], O_RDONLY, 0)) == -1) 1008 system_fatal("Can't open: %s for %s %s %s", 1009 argv[i+3], argv[i], argv[i+1], argv[i+2]); 1010 if(fstat(fd, &stat_buf) == -1) 1011 system_fatal("Can't stat file: %s for %s %s %s", 1012 argv[i+3], argv[i], argv[i+1], argv[i+2]); 1013 /* 1014 * For some reason mapping files with zero size fails 1015 * so it has to be handled specially. 1016 */ 1017 if(stat_buf.st_size != 0){ 1018 if((r = map_fd((int)fd, (vm_offset_t)0, 1019 (vm_offset_t *)&(sect_spec->file_addr), 1020 (boolean_t)TRUE, (vm_size_t)stat_buf.st_size) 1021 ) != KERN_SUCCESS) 1022 mach_fatal(r, "can't map file: %s for %s %s %s", 1023 argv[i+3], argv[i], argv[i+1], argv[i+2]); 1024 } 1025 else{ 1026 sect_spec->file_addr = NULL; 1027 } 1028 close(fd); 1029 sect_spec->file_size = stat_buf.st_size; 1030 sect_spec->contents_filename = argv[i+3]; 1031 i += 3; 1032 } 1033 /* specify the alignment of a section as a hexadecimal 1034 power of 2 1035 -sectalign <segname> <sectname> <number> */ 1036 else if(strcmp(p, "sectalign") == 0){ 1037 if(i + 3 >= argc) 1038 fatal("-sectalign arguments missing"); 1039 seg_spec = create_segment_spec(argv[i+1]); 1040 sect_spec = create_section_spec(seg_spec, argv[i+2]); 1041 if(sect_spec->align_specified) 1042 fatal("alignment for section (%s,%s) multiply " 1043 "specified", argv[i+1], argv[i+2]); 1044 sect_spec->align_specified = TRUE; 1045 align = strtoul(argv[i+3], &endp, 16); 1046 if(*endp != '\0') 1047 fatal("argument for -sectalign %s %s: %s not a " 1048 "proper hexadecimal number", argv[i+1], 1049 argv[i+2], argv[i+3]); 1050 if(!ispoweroftwo(align)) 1051 fatal("argument to -sectalign %s %s: %lx (hex) must" 1052 " be a power of two", argv[i+1], argv[i+2], 1053 align); 1054 if(align != 0) 1055 for(tmp = align; (tmp & 1) == 0; tmp >>= 1) 1056 sect_spec->align++; 1057 if(sect_spec->align > MAXSECTALIGN) 1058 fatal("argument to -sectalign %s %s: %lx (hex) must" 1059 " equal to or less than %x (hex)", argv[i+1], 1060 argv[i+2], align, 1061 (unsigned int)(1 << MAXSECTALIGN)); 1062 i += 3; 1063 } 1064 /* specify that section object symbols are to be created 1065 for the specified section 1066 -sectobjectsymbols <segname> <sectname> */ 1067 else if(strcmp(p, "sectobjectsymbols") == 0){ 1068 if(i + 2 >= argc) 1069 fatal("-sectobjectsymbols arguments missing"); 1070 if(sect_object_symbols.specified && 1071 (strcmp(sect_object_symbols.segname, 1072 argv[i+1]) != 0 || 1073 strcmp(sect_object_symbols.sectname, 1074 argv[i+2]) != 0) ) 1075 fatal("-sectobjectsymbols multiply specified (it " 1076 "can only be specified for one section)"); 1077 sect_object_symbols.specified = TRUE; 1078 sect_object_symbols.segname = argv[i+1]; 1079 sect_object_symbols.sectname = argv[i+2]; 1080 i += 2; 1081 } 1082 /* layout a section in the order the symbols appear in file 1083 -sectorder <segname> <sectname> <filename> */ 1084 else if(strcmp(p, "sectorder") == 0){ 1085 if(i + 3 >= argc) 1086 fatal("%s: arguments missing", argv[i]); 1087 seg_spec = create_segment_spec(argv[i+1]); 1088 sect_spec = create_section_spec(seg_spec, argv[i+2]); 1089 if(sect_spec->order_filename != NULL) 1090 fatal("section (%s,%s) multiply specified with a " 1091 "%s option", argv[i+1], argv[i+2], argv[i]); 1092 if((fd = open(argv[i+3], O_RDONLY, 0)) == -1) 1093 system_fatal("Can't open: %s for %s %s %s", 1094 argv[i+3], argv[i], argv[i+1], argv[i+2]); 1095 if(fstat(fd, &stat_buf) == -1) 1096 system_fatal("Can't stat file: %s for %s %s %s", 1097 argv[i+3], argv[i], argv[i+1], argv[i+2]); 1098 /* 1099 * For some reason mapping files with zero size fails 1100 * so it has to be handled specially. 1101 */ 1102 if(stat_buf.st_size != 0){ 1103 if((r = map_fd((int)fd, (vm_offset_t)0, 1104 (vm_offset_t *)&(sect_spec->order_addr), 1105 (boolean_t)TRUE, (vm_size_t)stat_buf.st_size) 1106 ) != KERN_SUCCESS) 1107 mach_fatal(r, "can't map file: %s for %s %s %s", 1108 argv[i+3], argv[i], argv[i+1], argv[i+2]); 1109 } 1110 else{ 1111 sect_spec->order_addr = NULL; 1112 } 1113 close(fd); 1114 sect_spec->order_size = stat_buf.st_size; 1115 sect_spec->order_filename = argv[i+3]; 1116 i += 3; 1117 } 1118 else if(strcmp(p, "sectorder_detail") == 0){ 1119 sectorder_detail = TRUE; 1120 } 1121 else if(strcmp(p, "sect_diff_relocs") == 0){ 1122 if(++i >= argc) 1123 fatal("-sect_diff_relocs: argument missing"); 1124 if(strcmp(argv[i], "error") == 0) 1125 new_sect_diff_reloc_flag = SECT_DIFF_RELOC_ERROR; 1126 else if(strcmp(argv[i], "warning") == 0) 1127 new_sect_diff_reloc_flag = SECT_DIFF_RELOC_WARNING; 1128 else if(strcmp(argv[i], "suppress") == 0) 1129 new_sect_diff_reloc_flag = SECT_DIFF_RELOC_SUPPRESS; 1130 else{ 1131 fatal("-sect_diff_relocs: unknown argument: %s", 1132 argv[i]); 1133 new_sect_diff_reloc_flag = SECT_DIFF_RELOC_SUPPRESS; 1134 } 1135 if(sect_diff_reloc_flag_specified == TRUE && 1136 new_sect_diff_reloc_flag != sect_diff_reloc_flag) 1137 fatal("more than one value specified for " 1138 "-sect_diff_relocs"); 1139 sect_diff_reloc_flag_specified = TRUE; 1140 sect_diff_reloc_flag = new_sect_diff_reloc_flag; 1141 break; 1142 } 1143 /* 1144 * Flags for specifing information about segments. 1145 */ 1146 /* specify the address (in hex) of a segment 1147 -segaddr <segname> <address> */ 1148 else if(strcmp(p, "segaddr") == 0){ 1149 if(i + 2 >= argc) 1150 fatal("-segaddr: arguments missing"); 1151 seg_spec = create_segment_spec(argv[i+1]); 1152 if(seg_spec->addr_specified == TRUE) 1153 fatal("address of segment %s multiply specified", 1154 argv[i+1]); 1155 segaddr_specified = TRUE; 1156 seg_spec->addr_specified = TRUE; 1157 seg_spec->addr = strtoul(argv[i+2], &endp, 16); 1158 if(*endp != '\0') 1159 fatal("address for -segaddr %s %s not a proper " 1160 "hexadecimal number", argv[i+1], argv[i+2]); 1161 i += 2; 1162 } 1163 /* specify the protection for a segment 1164 -segprot <segname> <maxprot> <initprot> 1165 where the protections are specified with "rwx" with a 1166 "-" for no protection. */ 1167 else if(strcmp(p, "segprot") == 0){ 1168 if(i + 3 >= argc) 1169 fatal("-segprot: arguments missing"); 1170 seg_spec = create_segment_spec(argv[i+1]); 1171 if(seg_spec->prot_specified == TRUE) 1172 fatal("protection of segment %s multiply " 1173 "specified", argv[i]); 1174 seg_spec->maxprot = getprot(argv[i+2], &endp); 1175 if(*endp != '\0') 1176 fatal("bad character: '%c' in maximum protection: " 1177 "%s for segment %s", *endp, argv[i+2], 1178 argv[i+1]); 1179 seg_spec->initprot = getprot(argv[i+3], &endp); 1180 if(*endp != '\0') 1181 fatal("bad character: '%c' in initial protection: " 1182 "%s for segment %s", *endp, argv[i+3], 1183 argv[i+1]); 1184 if(check_max_init_prot(seg_spec->maxprot, 1185 seg_spec->initprot) == FALSE) 1186 fatal("maximum protection: %s for segment: %s " 1187 "doesn't include all initial protections: %s", 1188 argv[i+2], argv[i+1], argv[i+3]); 1189 seg_spec->prot_specified = TRUE; 1190 i += 3; 1191 } 1192 /* specify the address (in hex) of the first segment 1193 -seg1addr <address> */ 1194 else if(strcmp(p, "seg1addr") == 0){ 1195 if(i + 1 >= argc) 1196 fatal("%s: argument missing", argv[i]); 1197 if(seg1addr_specified == TRUE) 1198 fatal("%s: multiply specified", argv[i]); 1199 seg1addr = strtoul(argv[i+1], &endp, 16); 1200 if(*endp != '\0') 1201 fatal("address for %s %s not a proper " 1202 "hexadecimal number", argv[i], argv[i+1]); 1203 seg1addr_specified = TRUE; 1204 i += 1; 1205 } 1206 /* specify the address (in hex) of the read-only segments 1207 -segs_read_only_addr <address> */ 1208 else if(strcmp(p, "segs_read_only_addr") == 0){ 1209 if(i + 1 >= argc) 1210 fatal("%s: argument missing", argv[i]); 1211 if(segs_read_only_addr_specified == TRUE) 1212 fatal("%s: multiply specified", argv[i]); 1213 segs_read_only_addr = strtoul(argv[i+1], &endp, 16); 1214 if(*endp != '\0') 1215 fatal("address for %s %s not a proper " 1216 "hexadecimal number", argv[i], argv[i+1]); 1217 segs_read_only_addr_specified = TRUE; 1218 i += 1; 1219 } 1220 /* specify the address (in hex) of the read-write segments 1221 -segs_read_write_addr <address> */ 1222 else if(strcmp(p, "segs_read_write_addr") == 0){ 1223 if(i + 1 >= argc) 1224 fatal("%s: argument missing", argv[i]); 1225 if(segs_read_write_addr_specified == TRUE) 1226 fatal("%s: multiply specified", argv[i]); 1227 segs_read_write_addr = strtoul(argv[i+1], &endp, 16); 1228 if(*endp != '\0') 1229 fatal("address for %s %s not a proper " 1230 "hexadecimal number", argv[i], argv[i+1]); 1231 segs_read_write_addr_specified = TRUE; 1232 i += 1; 1233 } 1234 /* specify the name of the segment address table */ 1235 else if(strcmp(p, "seg_addr_table") == 0){ 1236 if(i + 1 >= argc) 1237 fatal("%s: argument missing", argv[i]); 1238 if(seg_addr_table_name != NULL) 1239 fatal("%s: multiply specified", argv[i]); 1240 seg_addr_table_name = argv[i+1]; 1241 i += 1; 1242 } 1243 /* specify the file system path name to be used instead of 1244 the install name in the segment address table */ 1245 else if(strcmp(p, "seg_addr_table_filename") == 0){ 1246 if(i + 1 >= argc) 1247 fatal("%s: argument missing", argv[i]); 1248 if(seg_addr_table_filename != NULL) 1249 fatal("%s: multiply specified", argv[i]); 1250 seg_addr_table_filename = argv[i+1]; 1251 i += 1; 1252 } 1253 /* specify the segment alignment as a hexadecimal power of 2 1254 -segalign <number> */ 1255 else if(strcmp(p, "segalign") == 0){ 1256 if(segalign_specified) 1257 fatal("-segalign: multiply specified"); 1258 if(++i >= argc) 1259 fatal("-segalign: argument missing"); 1260 segalign = strtoul(argv[i], &endp, 16); 1261 if(*endp != '\0') 1262 fatal("argument for -segalign %s not a proper " 1263 "hexadecimal number", argv[i]); 1264 if(!ispoweroftwo(segalign) || segalign == 0) 1265 fatal("argument to -segalign: %lx (hex) must be a " 1266 "non-zero power of two", segalign); 1267 if(segalign > MAXSEGALIGN) 1268 fatal("argument to -segalign: %lx (hex) must equal " 1269 "to or less than %x (hex)", segalign, 1270 (unsigned int)MAXSEGALIGN); 1271 segalign_specified = TRUE; 1272 if(segalign < (1 << DEFAULTSECTALIGN)){ 1273 defaultsectalign = 0; 1274 align = segalign; 1275 while((align & 0x1) != 1){ 1276 defaultsectalign++; 1277 align >>= 1; 1278 } 1279 } 1280 } 1281 else if(strcmp(p, "seglinkedit") == 0){ 1282 if(seglinkedit_specified && seglinkedit == FALSE) 1283 fatal("both -seglinkedit and -noseglinkedit can't " 1284 "be specified"); 1285 seglinkedit = TRUE; 1286 seglinkedit_specified = TRUE; 1287 } 1288 /* specify the stack address as a hexadecimal number 1289 -stack_addr <address> */ 1290 else if(strcmp(p, "stack_addr") == 0){ 1291 if(i + 1 >= argc) 1292 fatal("%s: argument missing", argv[i]); 1293 if(stack_addr_specified == TRUE) 1294 fatal("%s: multiply specified", argv[i]); 1295 stack_addr = strtoul(argv[i+1], &endp, 16); 1296 if(*endp != '\0') 1297 fatal("address for %s %s not a proper " 1298 "hexadecimal number", argv[i], argv[i+1]); 1299 stack_addr_specified = TRUE; 1300 i += 1; 1301 } 1302 /* specify the stack size as a hexadecimal number 1303 -stack_size <address> */ 1304 else if(strcmp(p, "stack_size") == 0){ 1305 if(i + 1 >= argc) 1306 fatal("%s: argument missing", argv[i]); 1307 if(stack_size_specified == TRUE) 1308 fatal("%s: multiply specified", argv[i]); 1309 stack_size = strtoul(argv[i+1], &endp, 16); 1310 if(*endp != '\0') 1311 fatal("address for %s %s not a proper " 1312 "hexadecimal number", argv[i], argv[i+1]); 1313 stack_size_specified = TRUE; 1314 i += 1; 1315 } 1316 /* specify a sub_umbrella 1317 -sub_umbrella <name> */ 1318 else if(strcmp(p, "sub_umbrella") == 0){ 1319 if(i + 1 >= argc) 1320 fatal("%s: argument missing", argv[i]); 1321 sub_umbrellas = reallocate(sub_umbrellas, 1322 (nsub_umbrellas + 1) * sizeof(char *)); 1323 sub_umbrellas[nsub_umbrellas++] = argv[i+1]; 1324 i += 1; 1325 } 1326 /* specify a sub_library 1327 -sub_library <name> */ 1328 else if(strcmp(p, "sub_library") == 0){ 1329 if(i + 1 >= argc) 1330 fatal("%s: argument missing", argv[i]); 1331 sub_librarys = reallocate(sub_librarys, 1332 (nsub_librarys + 1) * sizeof(char *)); 1333 sub_librarys[nsub_librarys++] = argv[i+1]; 1334 i += 1; 1335 } 1336 /* -single_module for MH_DYLIB output */ 1337 else if(strcmp(p, "single_module") == 0){ 1338 if(moduletype_specified == TRUE && 1339 multi_module_dylib == TRUE) 1340 fatal("can't specify both -single_module and " 1341 "-multi_module"); 1342 moduletype_specified = TRUE; 1343 multi_module_dylib = FALSE; 1344 } 1345 else if(strcmp(p, "syslibroot") == 0){ 1346 if(i + 1 >= argc) 1347 fatal("%s: argument missing", argv[i]); 1348 if(syslibroot_specified == TRUE && strcmp(next_root, argv[i+1]) != 0) 1349 fatal("%s: multiply specified", argv[i]); 1350 next_root = argv[i+1]; 1351 syslibroot_specified = TRUE; 1352 i += 1; 1353 } 1354 else 1355 goto unknown_flag; 1356 break; 1357 1358 case 't': 1359 /* trace flag */ 1360 if(strcmp(p, "twolevel_namespace") == 0){ 1361 if(namespace_specified == TRUE && 1362 twolevel_namespace == FALSE) 1363 fatal("can't specify both -twolevel_namespace and " 1364 "-flat_namespace"); 1365 namespace_specified = TRUE; 1366 twolevel_namespace = TRUE; 1367 } 1368 else if(strcmp(p, "twolevel_namespace_hints") == 0){ 1369 if(namespace_specified == TRUE && 1370 twolevel_namespace == FALSE) 1371 fatal("can't specify both -twolevel_namespace_hints" 1372 " and -flat_namespace"); 1373 twolevel_namespace_hints_specified = TRUE; 1374 } 1375 else if(p[1] == '\0') 1376 trace = TRUE; 1377 else 1378 goto unknown_flag; 1379 break; 1380 1381 case 'o': 1382 if(strcmp(p, "object") == 0){ 1383 if(filetype_specified == TRUE && filetype != MH_OBJECT) 1384 fatal("more than one output filetype specified"); 1385 filetype_specified = TRUE; 1386 filetype = MH_OBJECT; 1387 break; 1388 } 1389 /* specify the output file name */ 1390 if(p[1] != '\0') 1391 goto unknown_flag; 1392 if(outputfile != NULL) 1393 fatal("-o: multiply specified"); 1394 if(++i >= argc) 1395 fatal("-o: argument missing"); 1396 outputfile = argv[i]; 1397 break; 1398 1399 case 'a': 1400 if(strcmp(p, "all_load") == 0) 1401 archive_all = TRUE; 1402 else if(strcmp(p, "arch_multiple") == 0) 1403 arch_multiple = TRUE; 1404 else if(strcmp(p, "arch_errors_fatal") == 0) 1405 arch_errors_fatal = TRUE; 1406 else if(strcmp(p, "allow_stack_execute") == 0) 1407 allow_stack_execute = TRUE; 1408 else if(strcmp(p, "arch") == 0){ 1409 if(++i >= argc) 1410 fatal("-arch: argument missing"); 1411 if(arch_flag.name != NULL && 1412 strcmp(arch_flag.name, argv[i]) != 0) 1413 fatal("-arch: multiply specified"); 1414 if(get_arch_from_flag(argv[i], &arch_flag) == 0){ 1415 error("unknown architecture specification flag: " 1416 "-arch %s", argv[i]); 1417 fatal("Usage: %s [options] file [...]", progname); 1418 } 1419 /* Default to -single_module on ARM. */ 1420 if(arch_flag.cputype == CPU_TYPE_ARM){ 1421 multi_module_dylib = FALSE; 1422 } 1423 target_byte_sex = get_byte_sex_from_flag(&arch_flag); 1424 } 1425 /* specify an allowable client of this subframework 1426 -allowable_client client_name */ 1427 else if(strcmp(p, "allowable_client") == 0){ 1428 if(i + 1 >= argc) 1429 fatal("%s: argument missing", argv[i]); 1430 allowable_clients = reallocate(allowable_clients, 1431 (nallowable_clients + 1) * sizeof(char *)); 1432 allowable_clients[nallowable_clients++] = argv[i+1]; 1433 i += 1; 1434 break; 1435 } 1436 else 1437 goto unknown_flag; 1438 break; 1439 1440 case 'c': 1441 /* specify this client's name which is using a subframework 1442 -client_name client_name */ 1443 if(strcmp(p, "client_name") == 0){ 1444 if(i + 1 >= argc) 1445 fatal("%s: argument missing", argv[i]); 1446 if(client_name != NULL) 1447 fatal("%s: multiply specified", argv[i]); 1448 client_name = argv[i+1]; 1449 i += 1; 1450 break; 1451 } 1452 else if(strcmp(p, "compatibility_version") == 0){ 1453 if(i + 1 >= argc) 1454 fatal("-compatibility_version: argument " 1455 "missing"); 1456 if(get_version_number("-compatibility_version", 1457 argv[i+1], &dylib_compatibility_version) == FALSE) 1458 cleanup(); 1459 if(dylib_compatibility_version == 0) 1460 fatal("-compatibility_version must be " 1461 "greater than zero"); 1462 i += 1; 1463 break; 1464 } 1465 else if(strcmp(p, "current_version") == 0){ 1466 if(i + 1 >= argc) 1467 fatal("-current_version: argument missing"); 1468 if(get_version_number("-current_version", 1469 argv[i+1], &dylib_current_version) == FALSE) 1470 cleanup(); 1471 if(dylib_current_version == 0) 1472 fatal("-current_version must be greater than " 1473 "zero"); 1474 i += 1; 1475 break; 1476 } 1477 if(p[1] != '\0') 1478 goto unknown_flag; 1479 break; 1480 1481 1482 /* Flags dealing with symbols */ 1483 case 'i': 1484 if(strcmp(p, "image_base") == 0){ 1485 if(i + 1 >= argc) 1486 fatal("%s: argument missing", argv[i]); 1487 if(seg1addr_specified == TRUE) 1488 fatal("%s: argument missing", argv[i]); 1489 seg1addr = strtoul(argv[i+1], &endp, 16); 1490 if(*endp != '\0') 1491 fatal("address for %s %s not a proper " 1492 "hexadecimal number", argv[i], argv[i+1]); 1493 seg1addr_specified = TRUE; 1494 i += 1; 1495 } 1496 else if(strcmp(p, "init") == 0){ 1497 /* check to see if the pointer is not already set */ 1498 if(init_name != NULL) 1499 fatal("-init: multiply specified"); 1500 if(++i >= argc) 1501 fatal("-init: argument missing"); 1502 init_name = argv[i]; 1503 } 1504 else if(strcmp(p, "install_name") == 0){ 1505 if(i + 1 >= argc) 1506 fatal("-install_name: argument missing"); 1507 dylib_install_name = argv[i + 1]; 1508 i += 1; 1509 } 1510 else{ 1511 /* create an indirect symbol, symbol_name, to be an 1512 indirect symbol for indr_symbol_name */ 1513 symbol_name = p + 1; 1514 indr_symbol_name = strchr(p + 1, ':'); 1515 if(indr_symbol_name == NULL || 1516 indr_symbol_name[1] == '\0' || *symbol_name == ':') 1517 fatal("-i argument: %s must have a ':' between " 1518 "its symbol names", p + 1); 1519 /* the creating of the symbol is done in the next pass 1520 of parsing arguments */ 1521 } 1522 break; 1523 1524 case 'm': 1525 if(strcmp(p, "multiply_defined") == 0){ 1526 if(++i >= argc) 1527 fatal("-multiply_defined: argument missing"); 1528 if(strcmp(argv[i], "error") == 0) 1529 new_multiply_defined_flag = MULTIPLY_DEFINED_ERROR; 1530 else if(strcmp(argv[i], "warning") == 0) 1531 new_multiply_defined_flag =MULTIPLY_DEFINED_WARNING; 1532 else if(strcmp(argv[i], "suppress") == 0) 1533 new_multiply_defined_flag=MULTIPLY_DEFINED_SUPPRESS; 1534 else{ 1535 fatal("-multiply_defined: unknown argument: %s", 1536 argv[i]); 1537 new_multiply_defined_flag =MULTIPLY_DEFINED_WARNING; 1538 } 1539 if(multiply_defined_flag_specified == TRUE && 1540 new_multiply_defined_flag != multiply_defined_flag) 1541 fatal("more than one value specified for " 1542 "-multiply_defined"); 1543 multiply_defined_flag_specified = TRUE; 1544 multiply_defined_flag = new_multiply_defined_flag; 1545 break; 1546 } 1547 else if(strcmp(p, "multiply_defined_unused") == 0){ 1548 if(++i >= argc) 1549 fatal("-multiply_defined_unused: argument missing"); 1550 if(strcmp(argv[i], "error") == 0) 1551 new_multiply_defined_unused_flag = 1552 MULTIPLY_DEFINED_ERROR; 1553 else if(strcmp(argv[i], "warning") == 0) 1554 new_multiply_defined_unused_flag = 1555 MULTIPLY_DEFINED_WARNING; 1556 else if(strcmp(argv[i], "suppress") == 0) 1557 new_multiply_defined_unused_flag = 1558 MULTIPLY_DEFINED_SUPPRESS; 1559 else{ 1560 fatal("-multiply_defined_unused: unknown argument: " 1561 "%s", argv[i]); 1562 new_multiply_defined_unused_flag = 1563 MULTIPLY_DEFINED_SUPPRESS; 1564 } 1565 if(multiply_defined_unused_flag_specified == TRUE && 1566 new_multiply_defined_unused_flag != 1567 multiply_defined_unused_flag) 1568 fatal("more than one value specified for " 1569 "-multiply_defined_unused"); 1570 multiply_defined_unused_flag_specified = TRUE; 1571 multiply_defined_unused_flag = 1572 new_multiply_defined_unused_flag; 1573 break; 1574 } 1575 /* -multi_module for MH_DYLIB output */ 1576 else if(strcmp(p, "multi_module") == 0){ 1577 if(moduletype_specified == TRUE && 1578 multi_module_dylib == FALSE) 1579 fatal("can't specify both -single_module and " 1580 "-multi_module"); 1581 moduletype_specified = TRUE; 1582 multi_module_dylib = TRUE; 1583 break; 1584 } 1585 /* -macosx_version_min for overriding 1586 MACOSX_DEPLOYMENT_TARGET on command line */ 1587 else if(strcmp (p, "macosx_version_min") == 0){ 1588 if(++i >= argc) 1589 fatal("-macosx_version_min: argument missing"); 1590 put_macosx_deployment_target (argv[i]); 1591 break; 1592 } 1593 /* treat multiply defined symbols as a warning not a 1594 hard error */ 1595 if(p[1] != '\0') 1596 goto unknown_flag; 1597 allow_multiply_defined_symbols = TRUE; 1598 break; 1599 1600 case 'u': 1601 if(strcmp(p, "undefined") == 0){ 1602 if(++i >= argc) 1603 fatal("-undefined: argument missing"); 1604 if(strcmp(argv[i], "error") == 0) 1605 new_undefined_flag = UNDEFINED_ERROR; 1606 else if(strcmp(argv[i], "warning") == 0) 1607 new_undefined_flag = UNDEFINED_WARNING; 1608 else if(strcmp(argv[i], "suppress") == 0) 1609 new_undefined_flag = UNDEFINED_SUPPRESS; 1610 else if(strcmp(argv[i], "dynamic_lookup") == 0) 1611 new_undefined_flag = UNDEFINED_DYNAMIC_LOOKUP; 1612 else if(strcmp(argv[i], "define_a_way") == 0){ 1613 new_undefined_flag = UNDEFINED_DEFINE_A_WAY; 1614 warning("suggest the use of -dead_strip instead of " 1615 "-undefined define_a_way"); 1616 } 1617 else{ 1618 fatal("-undefined: unknown argument: %s", argv[i]); 1619 new_undefined_flag = UNDEFINED_ERROR; 1620 } 1621 if(undefined_flag_specified == TRUE && 1622 new_undefined_flag != undefined_flag) 1623 fatal("more than one value specified for " 1624 "-undefined"); 1625 undefined_flag_specified = TRUE; 1626 undefined_flag = new_undefined_flag; 1627 break; 1628 } 1629 /* specify this dynamic library as a subframework 1630 -umbrella umbrella_framework_name */ 1631 else if(strcmp(p, "umbrella") == 0){ 1632 if(i + 1 >= argc) 1633 fatal("%s: argument missing", argv[i]); 1634 if(sub_framework == TRUE) 1635 fatal("%s: multiply specified", argv[i]); 1636 umbrella_framework_name = argv[i+1]; 1637 sub_framework = TRUE; 1638 i += 1; 1639 break; 1640 } 1641 else if(strcmp(p, "unexported_symbols_list") == 0){ 1642 if(i + 1 >= argc) 1643 fatal("%s: argument missing", argv[i]); 1644 if(remove_symbols != NULL) 1645 fatal("%s: multiply specified", argv[i]); 1646 setup_symbol_list(argv[i+1], &remove_symbols, 1647 &nremove_symbols); 1648 unexported_symbols_list = argv[i+1]; 1649 i += 1; 1650 break; 1651 } 1652 if(p[1] != '\0') 1653 goto unknown_flag; 1654 /* cause the specified symbol name to be undefined */ 1655 if(++i >= argc) 1656 fatal("-u: argument missing"); 1657 /* the creating of the symbol is done in the next pass of 1658 parsing arguments */ 1659 break; 1660 1661 case 'e': 1662 if(strcmp(p, "execute") == 0){ 1663 if(filetype_specified == TRUE && filetype != MH_EXECUTE) 1664 fatal("more than one output filetype specified"); 1665 filetype_specified = TRUE; 1666 filetype = MH_EXECUTE; 1667 break; 1668 } 1669 else if(strcmp(p, "exported_symbols_list") == 0){ 1670 if(i + 1 >= argc) 1671 fatal("%s: argument missing", argv[i]); 1672 if(save_symbols != NULL) 1673 fatal("%s: multiply specified", argv[i]); 1674 setup_symbol_list(argv[i+1], &save_symbols, 1675 &nsave_symbols); 1676 exported_symbols_list = argv[i+1]; 1677 i += 1; 1678 break; 1679 } 1680 else if(strcmp(p, "executable_path") == 0){ 1681 if(i + 1 >= argc) 1682 fatal("%s: argument missing", argv[i]); 1683 if(executable_path != NULL) 1684 fatal("%s: multiply specified", argv[i]); 1685 executable_path = argv[i+1]; 1686 i += 1; 1687 break; 1688 } 1689 /* specify the entry point, the symbol who's value to be 1690 used as the program counter in the unix thread */ 1691 if(p[1] != '\0') 1692 goto unknown_flag; 1693 /* check to see if the pointer is not already set */ 1694 if(entry_point_name != NULL) 1695 fatal("-e: multiply specified"); 1696 if(++i >= argc) 1697 fatal("-e: argument missing"); 1698 entry_point_name = argv[i]; 1699 break; 1700 1701 case 'U': 1702 if(p[1] != '\0') 1703 goto unknown_flag; 1704 /* allow the specified symbol name to be undefined */ 1705 if(++i >= argc) 1706 fatal("-U: argument missing"); 1707 undef_syms = reallocate(undef_syms, 1708 (nundef_syms + 1) * sizeof(char *)); 1709 undef_syms[nundef_syms++] = argv[i]; 1710 break; 1711 1712 case 'w': 1713 if(strcmp(p, "w") == 0) 1714 nowarnings = TRUE; 1715 else if(strcmp(p, "whyload") == 0) 1716 whyload = TRUE; 1717 else if(strcmp(p, "whatsloaded") == 0) 1718 whatsloaded = TRUE; 1719 else if(strcmp(p, "weak_reference_mismatches") == 0){ 1720 if(++i >= argc) 1721 fatal("-weak_reference_mismatches: " 1722 "argument missing"); 1723 if(strcmp(argv[i], "error") == 0) 1724 new_weak_reference_mismatches = 1725 WEAK_REFS_MISMATCH_ERROR; 1726 else if(strcmp(argv[i], "weak") == 0) 1727 new_weak_reference_mismatches = 1728 WEAK_REFS_MISMATCH_WEAK; 1729 else if(strcmp(argv[i], "non-weak") == 0) 1730 new_weak_reference_mismatches = 1731 WEAK_REFS_MISMATCH_NON_WEAK; 1732 else{ 1733 fatal("-weak_reference_mismatches: unknown " 1734 "argument: %s", argv[i]); 1735 new_weak_reference_mismatches = 1736 WEAK_REFS_MISMATCH_ERROR; 1737 } 1738 if(weak_reference_mismatches_specified == TRUE && 1739 new_weak_reference_mismatches != 1740 weak_reference_mismatches) 1741 fatal("more than one value specified for " 1742 "-weak_reference_mismatches"); 1743 weak_reference_mismatches_specified = TRUE; 1744 weak_reference_mismatches = 1745 new_weak_reference_mismatches; 1746 break; 1747 } 1748 else if(strcmp(p, "weak_library") == 0){ 1749 if(i + 1 >= argc) 1750 fatal("-weak_library: argument missing"); 1751 /* object file argv[i] processed in the next pass of 1752 parsing arguments */ 1753 i += 1; 1754 } 1755 else if(strncmp(p, "weak-l", sizeof("weak-l") - 1) == 0){ 1756 if(p[sizeof("weak-l") - 1] == '\0') 1757 fatal("-weak-l: argument missing"); 1758 /* path searched abbrevated file name, processed in the 1759 next pass of parsing arguments */ 1760 } 1761 else if(strcmp(p, "weak_framework") == 0){ 1762 if(i + 1 >= argc) 1763 fatal("-weak_framework: argument missing"); 1764 /* path searched abbrevated framework name, processed 1765 in the next pass of parsing arguments */ 1766 i += 1; 1767 } 1768 else 1769 goto unknown_flag; 1770 break; 1771 1772 case 'O': 1773 if(strcmp(p, "ObjC") == 0) 1774 archive_ObjC = TRUE; 1775 else 1776 goto unknown_flag; 1777 break; 1778 1779 case 'y': 1780 /* symbol tracing */ 1781 if(p[1] == '\0') 1782 fatal("-y: symbol name missing"); 1783 trace_syms = reallocate(trace_syms, 1784 (ntrace_syms + 1) * sizeof(char *)); 1785 trace_syms[ntrace_syms++] = &(p[1]); 1786 break; 1787 1788 case 'Y': 1789 /* undefined reference symbol tracing */ 1790 if(strcmp(p, "Y") == 0){ 1791 if(i + 1 >= argc) 1792 fatal("-Y: argument missing"); 1793 Yflag = strtoul(argv[i+1], &endp, 10); 1794 if(*endp != '\0') 1795 fatal("reference count for -Y %s not a proper " 1796 "decimal number", argv[i+1]); 1797 } 1798 else 1799 goto unknown_flag; 1800 break; 1801 1802 case 'h': 1803 /* specify the header pad (in hex) 1804 -headerpad <value> */ 1805 if(strcmp(p, "headerpad") == 0){ 1806 if(i + 1 >= argc) 1807 fatal("-headerpad: argument missing"); 1808 if(headerpad_specified == TRUE) 1809 fatal("-headerpad: multiply specified"); 1810 headerpad = strtoul(argv[i+1], &endp, 16); 1811 if(*endp != '\0') 1812 fatal("address for -headerpad %s not a proper " 1813 "hexadecimal number", argv[i+1]); 1814 headerpad_specified = TRUE; 1815 i += 1; 1816 } 1817 else if(strcmp(p, "headerpad_max_install_names") == 0){ 1818 headerpad_max_install_names = TRUE; 1819 } 1820 else if(strcmp(p, "hash_instrument") == 0){ 1821 hash_instrument_specified = TRUE; 1822 } 1823 else 1824 goto unknown_flag; 1825 break; 1826 1827 case 'k': 1828 if(strcmp(p, "keep_private_externs") == 0) 1829 keep_private_externs = TRUE; 1830 else if(strcmp(p, "k") == 0) 1831 dynamic = TRUE; 1832 else 1833 goto unknown_flag; 1834 break; 1835 1836 case 'N': 1837 if(strcmp(p, "NEXTSTEP-deployment-target") == 0){ 1838 if(i + 1 >= argc) 1839 fatal("-NEXTSTEP-deployment-target: argument " 1840 "missing"); 1841 if(dynamic_specified == TRUE || 1842 static_specified == TRUE) 1843 fatal("-NEXTSTEP-deployment-target, -dynamic or " 1844 "-static : multiply specified"); 1845 if(strcmp(argv[i+1], "3.3") == 0){ 1846 if(static_specified) 1847 fatal("only one of -NEXTSTEP-deployment-target " 1848 "3.3 or -static can be specified"); 1849 dynamic = TRUE; 1850 dynamic_specified = TRUE; 1851 } 1852 else if(strcmp(argv[i+1], "3.2") == 0){ 1853 if(dynamic_specified) 1854 fatal("only one of -NEXTSTEP-deployment-target " 1855 "3.2 or -dynamic can be specified"); 1856 dynamic = FALSE; 1857 static_specified = TRUE; 1858 } 1859 else 1860 fatal("unknown deployment release flag: " 1861 "-NEXTSTEP-deployment-target %s", argv[i+1]); 1862 i += 1; 1863 } 1864 else 1865 goto unknown_flag; 1866 break; 1867 1868 case 'v': 1869 if(strcmp(p, "v") == 0){ 1870 vflag = TRUE; 1871 printf("Apple Inc. version %s\n", apple_version); 1872 } 1873 else 1874 goto unknown_flag; 1875 break; 1876 1877 default: 1878unknown_flag: 1879 fatal("unknown flag: %s", argv[i]); 1880 } 1881 } 1882 } 1883 1884 /* 1885 * -sub_umbrella and -sub_library are not supported on ARM. 1886 * See <rdar://problem/4771657>. 1887 */ 1888 if(arch_flag.cputype == CPU_TYPE_ARM){ 1889 if(sub_umbrellas != NULL){ 1890 fatal("-sub_umbrella is not supported on ARM"); 1891 } 1892 if(sub_librarys != NULL){ 1893 fatal("-sub_library is not supported on ARM"); 1894 } 1895 } 1896 1897 /* 1898 * If either -syslibroot or the environment variable NEXT_ROOT is set 1899 * prepend it to the standard paths for library searches. This was 1900 * added to ease cross build environments. 1901 */ 1902 p = getenv("NEXT_ROOT"); 1903 if(syslibroot_specified == TRUE){ 1904 if(p != NULL && strcmp(p, next_root) != 0) 1905 warning("NEXT_ROOT environment variable ignored because " 1906 "-syslibroot specified"); 1907 } 1908 else{ 1909 next_root = p; 1910 } 1911 if(next_root != NULL){ 1912 for(i = 0; standard_dirs[i] != NULL; i++){ 1913 p = allocate(strlen(next_root) + 1914 strlen(standard_dirs[i]) + 1); 1915 strcpy(p, next_root); 1916 strcat(p, standard_dirs[i]); 1917 standard_dirs[i] = p; 1918 } 1919 for(i = 0; standard_framework_dirs[i] != NULL; i++){ 1920 p = allocate(strlen(next_root) + 1921 strlen(standard_framework_dirs[i]) + 1); 1922 strcpy(p, next_root); 1923 strcat(p, standard_framework_dirs[i]); 1924 standard_framework_dirs[i] = p; 1925 } 1926 } 1927 /* 1928 * If -syslibroot is specified, prepend it to the user-specified 1929 * paths *if* the prepended version exists. 1930 */ 1931 if(syslibroot_specified == TRUE){ 1932 for(i = 0; i < nsearch_dirs; i++){ 1933 if(search_dirs[i][0] == '/'){ 1934 p = mkstr(next_root, search_dirs[i], NULL); 1935 if(stat(p, &stat_buf) == 0) 1936 search_dirs[i] = p; 1937 else 1938 free(p); 1939 } 1940 } 1941 for(i = 0; i < nframework_dirs; i++){ 1942 if(framework_dirs[i][0] == '/'){ 1943 p = mkstr(next_root, framework_dirs[i], NULL); 1944 if(stat(p, &stat_buf) == 0) 1945 framework_dirs[i] = p; 1946 else 1947 free(p); 1948 } 1949 } 1950 } 1951 1952 /* 1953 * Test to see if the various RC_* or XBS_* environment variables 1954 * are set. 1955 */ 1956 if((getenv("LD_TRACE_ARCHIVES") != NULL) || 1957 getenv("RC_TRACE_ARCHIVES") != NULL) 1958 ld_trace_archives = TRUE; 1959 if((getenv("LD_TRACE_DYLIBS") != NULL) || 1960 (getenv("RC_TRACE_DYLIBS") != NULL)) 1961 ld_trace_dylibs = TRUE; 1962 if((getenv("LD_TRACE_PREBINDING_DISABLED") != NULL) || 1963 getenv("RC_TRACE_PREBINDING_DISABLED") != NULL) 1964 ld_trace_prebinding_disabled = TRUE; 1965 if(ld_trace_archives || ld_trace_dylibs) 1966 trace_file_path = getenv("LD_TRACE_FILE"); 1967 if(getenv("LD_TRACE_BUNDLE_LOADER") != NULL && 1968 bundle_loader != NULL) 1969 print("[Logging for XBS] Referenced bundle loader: %s\n", 1970 bundle_loader); 1971 1972 if(save_reloc == FALSE){ 1973 if(getenv("LD_DEAD_STRIP") != NULL) 1974 dead_strip = TRUE; 1975 if(getenv("LD_NO_DEAD_STRIP_INITS_AND_TERMS") != NULL) 1976 no_dead_strip_inits_and_terms = TRUE; 1977 } 1978 if(getenv("LD_DEAD_STRIP_DYLIB") != NULL && filetype == MH_DYLIB) 1979 dead_strip = TRUE; 1980 1981 prebinding_via_LD_PREBIND = FALSE; 1982 /* 1983 * The LD_FORCE_NO_PREBIND environment variable overrides the command 1984 * line and the LD_PREBIND environment variable. 1985 */ 1986 if(getenv("LD_FORCE_NO_PREBIND") != NULL){ 1987 if(prebinding_flag_specified == TRUE && 1988 prebinding == TRUE){ 1989 warning("-prebind ignored because LD_FORCE_NO_PREBIND " 1990 "environment variable specified"); 1991 prebinding_flag_specified = TRUE; 1992 prebinding = FALSE; 1993 } 1994 } 1995 /* 1996 * The -prebind flag can also be specified with the LD_PREBIND 1997 * environment variable. We quitely ignore this when -r is on or 1998 * if this is a fixed shared library output. 1999 */ 2000 else if(getenv("LD_PREBIND") != NULL && 2001 save_reloc == FALSE && 2002 filetype != MH_FVMLIB){ 2003 if(prebinding_flag_specified == TRUE && 2004 prebinding == FALSE){ 2005 warning("LD_PREBIND environment variable ignored because " 2006 "-noprebind specified"); 2007 } 2008 else{ 2009 if(prebinding_flag_specified == FALSE) 2010 prebinding_via_LD_PREBIND = TRUE; 2011 prebinding_flag_specified = TRUE; 2012 prebinding = TRUE; 2013 } 2014 } 2015 if(getenv("LD_PREBIND_ALLOW_OVERLAP") != NULL) 2016 prebind_allow_overlap = TRUE; 2017 if(prebind_all_twolevel_modules_specified == FALSE && 2018 getenv("LD_PREBIND_ALL_TWOLEVEL_MODULES") != NULL) 2019 prebind_all_twolevel_modules = TRUE; 2020 2021 /* 2022 * The -twolevel_namespace flag can also be specified with the 2023 * LD_TWOLEVEL_NAMESPACE environment variable. We quitely ignore this 2024 * when -flat_namespace or -static is specified. 2025 */ 2026 if(getenv("LD_TWOLEVEL_NAMESPACE") != NULL && 2027 namespace_specified == FALSE && 2028 static_specified == FALSE){ 2029 namespace_specified = TRUE; 2030 twolevel_namespace = TRUE; 2031 } 2032 2033 /* 2034 * See if LD_LIBRARY_PATH is set. And if so parse out the colon 2035 * separated set of paths. 2036 */ 2037 ld_library_path = getenv("LD_LIBRARY_PATH"); 2038 if(ld_library_path != NULL){ 2039 nld_library_paths = 1; 2040 for(i = 0; ld_library_path[i] != '\0'; i++){ 2041 if(ld_library_path[i] == ':') 2042 nld_library_paths++; 2043 } 2044 ld_library_paths = allocate(sizeof(char *) * nld_library_paths); 2045 j = 0; 2046 ld_library_paths[j] = ld_library_path; 2047 j++; 2048 for(i = 0; ld_library_path[i] != '\0'; i++){ 2049 if(ld_library_path[i] == ':'){ 2050 ld_library_path[i] = '\0'; 2051 ld_library_paths[j] = ld_library_path + i + 1; 2052 j++; 2053 } 2054 } 2055 } 2056 2057 /* 2058 * If there was a -arch flag two things needed to be done in reguard to 2059 * the handling of the cpusubtypes. 2060 */ 2061 if(arch_flag.name != NULL){ 2062 2063 /* 2064 * 64-bit architectures are an error. 2065 */ 2066 if(arch_flag.cputype & CPU_ARCH_ABI64) 2067 fatal("does not support 64-bit architectures"); 2068 2069 family_arch_flag = get_arch_family_from_cputype(arch_flag.cputype); 2070 if(family_arch_flag == NULL) 2071 fatal("internal error: unknown cputype (%d) for -arch %s (this " 2072 "program out of sync with get_arch_family_from_cputype())" 2073 ,arch_flag.cputype, arch_flag.name); 2074 /* 2075 * Pick up the Mac OS X deployment target. 2076 */ 2077 get_macosx_deployment_target(&macosx_deployment_target); 2078 /* 2079 * If for this cputype we are to always output the ALL cpusubtype 2080 * then set force_cpusubtype_ALL. 2081 */ 2082 if(force_cpusubtype_ALL_for_cputype(arch_flag.cputype) == TRUE) 2083 force_cpusubtype_ALL = TRUE; 2084 /* 2085 * First, if -force_cpusubtype_ALL is set and an -arch flag was 2086 * specified set the cpusubtype to the _ALL type for that cputype 2087 * since the specified flag may not have the _ALL type and the 2088 * -force_cpusubtype_ALL has precedence over an -arch flags for a 2089 * specific implementation of an architecture. 2090 */ 2091 if(force_cpusubtype_ALL == TRUE){ 2092 arch_flag.cpusubtype = family_arch_flag->cpusubtype; 2093 } 2094 else{ 2095 /* 2096 * Second, if no -force_cpusubtype_ALL is specified and an -arch 2097 * flag for a specific implementation of an architecture was 2098 * specified then the resulting cpusubtype will be for that 2099 * specific implementation of that architecture and all 2100 * cpusubtypes must combine with the cpusubtype for the -arch 2101 * flag to the cpusubtype for the -arch flag else an error must 2102 * be flaged. This is done check_cur_obj() where cpusubtypes 2103 * are combined. What needs to be done here is to determine if 2104 * the -arch flag is for a specific implementation of an 2105 * architecture. 2106 */ 2107 if(arch_flag.cpusubtype != family_arch_flag->cpusubtype) 2108 specific_arch_flag = TRUE; 2109 } 2110 } 2111 else{ 2112 /* 2113 * We need to pick up the Mac OS X deployment target even if the 2114 * target architecture is not yet known so we can check to see if 2115 * the flags specified are valid. 2116 */ 2117 if(macosx_deployment_target.major == 0) 2118 get_macosx_deployment_target(&macosx_deployment_target); 2119 } 2120 2121 /* 2122 * If the -sect_diff_relocs is specified check to see it can be used 2123 * else pick up the LD_SECT_DIFF_RELOC if that can be used. 2124 */ 2125 if(sect_diff_reloc_flag_specified == TRUE){ 2126 if(filetype != MH_EXECUTE || dynamic == FALSE) 2127 fatal("can't use -sect_diff_relocs unless both -execute and " 2128 "-dynamic are in effect"); 2129 } 2130 else{ 2131 /* 2132 * The -sect_diff_relocs flag was not specified on the command 2133 * line, so if both -execute and -dynamic are in effect see if 2134 * LD_SECT_DIFF_RELOCS is specified as an environment variable and 2135 * use that value. 2136 */ 2137 if(filetype == MH_EXECUTE && dynamic == TRUE){ 2138 p = getenv("LD_SECT_DIFF_RELOCS"); 2139 if(p != NULL){ 2140 if(strcmp(p, "error") == 0) 2141 sect_diff_reloc_flag = SECT_DIFF_RELOC_ERROR; 2142 else if(strcmp(p, "warning") == 0) 2143 sect_diff_reloc_flag = SECT_DIFF_RELOC_WARNING; 2144 else if(strcmp(p, "suppress") == 0) 2145 sect_diff_reloc_flag = SECT_DIFF_RELOC_SUPPRESS; 2146 else{ 2147 fatal("Unknown LD_SECT_DIFF_RELOCS environment variable" 2148 " %s value", p); 2149 } 2150 } 2151 } 2152 } 2153 2154 /* 2155 * Check for flag combinations that would result in a bad output file. 2156 */ 2157 if(save_reloc && strip_level == STRIP_ALL) 2158 fatal("can't use -s with -r (resulting file would not be " 2159 "relocatable)"); 2160 if(save_reloc && strip_level == STRIP_MIN_DEBUG) 2161 fatal("can't use -Sp with -r (only allowed for fully linked " 2162 "images)"); 2163 if(save_reloc && strip_base_symbols == TRUE) 2164 fatal("can't use -b with -r (resulting file would not be " 2165 "relocatable)"); 2166 if(save_reloc && dead_strip == TRUE) 2167 fatal("can't use -dead_strip with -r (only allowed for fully " 2168 "linked images)"); 2169 if(keep_private_externs == TRUE){ 2170 if(save_symbols != NULL) 2171 fatal("can't use both -keep_private_externs and " 2172 "-exported_symbols_list"); 2173 if(remove_symbols != NULL) 2174 fatal("can't use both -keep_private_externs and " 2175 "-unexported_symbols_list"); 2176 } 2177 if(save_symbols != NULL && remove_symbols != NULL){ 2178 for(j = 0; j < nremove_symbols ; j++){ 2179 sp = bsearch(remove_symbols[j].name, 2180 save_symbols, nsave_symbols, 2181 sizeof(struct symbol_list), 2182 (int (*)(const void *, const void *)) 2183 symbol_list_bsearch); 2184 if(sp != NULL){ 2185 error("symbol name: %s is listed in both " 2186 "-exported_symbols_list and -unexported_symbols_list " 2187 "(can't be both exported and unexported)", 2188 remove_symbols[j].name); 2189 } 2190 } 2191 if(errors != 0) 2192 ld_exit(1); 2193 } 2194 if(filetype_specified == TRUE && filetype == MH_OBJECT){ 2195 if(dynamic == TRUE) 2196 fatal("incompatible to specifiy -object when -dynamic is used " 2197 "(use -execute (the default) with -dynamic or -static " 2198 "with -object)"); 2199 } 2200 if(filetype == MH_DYLINKER){ 2201 if(dynamic == FALSE) 2202 fatal("incompatible flag -dylinker used (must specify " 2203 "\"-dynamic\" to be used)"); 2204 } 2205 if(filetype == MH_DYLIB){ 2206 if(dynamic == FALSE) 2207 fatal("incompatible flag -dylib used (must specify " 2208 "\"-dynamic\" to be used)"); 2209 if(save_reloc) 2210 fatal("can't use -r and -dylib (file format produced with " 2211 "-dylib is not a relocatable format)"); 2212 if(strip_level == STRIP_ALL) 2213 fatal("can't use -s with -dylib (file must contain at least " 2214 "global symbols, for maximum stripping use -x)"); 2215 if(Aflag_specified) 2216 fatal("can't use -A and -dylib"); 2217 if(keep_private_externs == TRUE) 2218 fatal("can't use -keep_private_externs and -dylib"); 2219 if(segaddr_specified) 2220 fatal("can't use -segaddr options with -dylib (use seg1addr to " 2221 "specify the starting address)"); 2222 if(seg1addr_specified && segs_read_only_addr_specified) 2223 fatal("can't use both the -seg1addr option and " 2224 "-segs_read_only_addr option"); 2225 if(seg1addr_specified && segs_read_write_addr_specified) 2226 fatal("can't use both the -seg1addr option and " 2227 "-segs_read_write_addr option"); 2228 if(seg1addr_specified && seg_addr_table_name != NULL) 2229 fatal("can't use both the -seg1addr option and " 2230 "-seg_addr_table option"); 2231 if(seg_addr_table_name != NULL && segs_read_only_addr_specified) 2232 fatal("can't use both the -seg_addr_table option and " 2233 "-segs_read_only_addr option"); 2234 if(seg_addr_table_name != NULL && segs_read_write_addr_specified) 2235 fatal("can't use both the -seg_addr_table option and " 2236 "-segs_read_only_addr option"); 2237 if(seg_addr_table_name != NULL && dylib_install_name == NULL) 2238 fatal("must also specify -dylib_install_name when using " 2239 "-seg_addr_table"); 2240 if(segs_read_only_addr_specified && 2241 read_only_reloc_flag != READ_ONLY_RELOC_ERROR) 2242 fatal("can't used -read_only_relocs %s with format produced " 2243 "with the -segs_read_only_addr option\n", 2244 read_only_reloc_flag == READ_ONLY_RELOC_WARNING ? 2245 "warning" : "suppress"); 2246 if(segs_read_write_addr_specified && 2247 !segs_read_only_addr_specified) 2248 fatal("must also specify -segs_read_only_addr when using " 2249 "-segs_read_write_addr"); 2250 if(seglinkedit_specified && seglinkedit == FALSE) 2251 fatal("can't use -noseglinkedit with -dylib (resulting file " 2252 "must have a link edit segment to access symbols)"); 2253 if(bind_at_load == TRUE){ 2254 warning("-bind_at_load is meaningless with -dylib"); 2255 bind_at_load = FALSE; 2256 } 2257 /* use a segment address table if specified */ 2258 env_seg_addr_table_name = getenv("LD_SEG_ADDR_TABLE"); 2259 if(seg_addr_table_name != NULL || 2260 (env_seg_addr_table_name != NULL && dylib_install_name != NULL)){ 2261 if(seg_addr_table_name != NULL && 2262 env_seg_addr_table_name != NULL && 2263 strcmp(seg_addr_table_name, env_seg_addr_table_name) != 0){ 2264 warning("-seg_addr_table %s ignored, LD_SEG_ADDR_TABLE " 2265 "environment variable: %s used instead", 2266 seg_addr_table_name, env_seg_addr_table_name); 2267 } 2268 if(env_seg_addr_table_name != NULL){ 2269 seg_addr_table_name = env_seg_addr_table_name; 2270 seg_addr_table = parse_seg_addr_table(seg_addr_table_name, 2271 "LD_SEG_ADDR_TABLE", "environment variable", 2272 &table_size); 2273 } 2274 else 2275 seg_addr_table = parse_seg_addr_table(seg_addr_table_name, 2276 "-seg_addr_table", seg_addr_table_name, &table_size); 2277 if(seg_addr_table_filename != NULL) 2278 seg_addr_table_entry = search_seg_addr_table(seg_addr_table, 2279 seg_addr_table_filename); 2280 else 2281 seg_addr_table_entry = search_seg_addr_table(seg_addr_table, 2282 dylib_install_name); 2283 if(seg_addr_table_entry != NULL){ 2284 if(seg_addr_table_entry->split == TRUE){ 2285 if(read_only_reloc_flag != READ_ONLY_RELOC_ERROR){ 2286 warning("-read_only_relocs %s ignored, when using " 2287 "with format produced with the " 2288 "-segs_read_only_addr option (via the " 2289 "segment address table: %s %s line %u)", 2290 read_only_reloc_flag == 2291 READ_ONLY_RELOC_WARNING ? 2292 "warning" : "suppress", 2293 env_seg_addr_table_name != NULL ? 2294 "LD_SEG_ADDR_TABLE" : "-seg_addr_table", 2295 seg_addr_table_name, 2296 seg_addr_table_entry->line); 2297 read_only_reloc_flag = READ_ONLY_RELOC_ERROR; 2298 } 2299 if(seg1addr_specified){ 2300 warning("-seg1addr 0x%x ignored, using " 2301 "-segs_read_only_addr 0x%x and " 2302 "-segs_read_write_addr 0x%x from segment " 2303 "address table: %s %s line %u", 2304 (unsigned int)seg1addr, 2305 (unsigned int)seg_addr_table_entry-> 2306 segs_read_only_addr, 2307 (unsigned int)seg_addr_table_entry-> 2308 segs_read_write_addr, 2309 env_seg_addr_table_name != NULL ? 2310 "LD_SEG_ADDR_TABLE" : "-seg_addr_table", 2311 seg_addr_table_name, 2312 seg_addr_table_entry->line); 2313 } 2314 if(segs_read_only_addr_specified && 2315 segs_read_only_addr != 2316 seg_addr_table_entry->segs_read_only_addr){ 2317 warning("-segs_read_only_addr 0x%x ignored, using " 2318 "-segs_read_only_addr 0x%x from segment " 2319 "address table: %s %s line %u", 2320 (unsigned int)segs_read_only_addr, 2321 (unsigned int)seg_addr_table_entry-> 2322 segs_read_only_addr, 2323 env_seg_addr_table_name != NULL ? 2324 "LD_SEG_ADDR_TABLE" : "-seg_addr_table", 2325 seg_addr_table_name, 2326 seg_addr_table_entry->line); 2327 } 2328 if(segs_read_write_addr_specified && 2329 segs_read_write_addr != 2330 seg_addr_table_entry->segs_read_write_addr){ 2331 warning("-segs_read_write_addr 0x%x ignored, using " 2332 "-segs_read_write_addr 0x%x from segment " 2333 "address table: %s %s line %u", 2334 (unsigned int)segs_read_write_addr, 2335 (unsigned int)seg_addr_table_entry-> 2336 segs_read_write_addr, 2337 env_seg_addr_table_name != NULL ? 2338 "LD_SEG_ADDR_TABLE" : "-seg_addr_table", 2339 seg_addr_table_name, 2340 seg_addr_table_entry->line); 2341 } 2342 seg1addr_specified = FALSE; 2343 seg1addr = 0; 2344 segs_read_only_addr_specified = TRUE; 2345 segs_read_only_addr = 2346 seg_addr_table_entry->segs_read_only_addr; 2347 segs_read_write_addr_specified = TRUE; 2348 segs_read_write_addr = 2349 seg_addr_table_entry->segs_read_write_addr; 2350 if(segs_read_only_addr == 0 && 2351 segs_read_write_addr == 0){ 2352 segs_read_write_addr = get_shared_region_size_from_flag(&arch_flag); 2353 warning("-segs_read_write_addr 0x0 ignored from " 2354 "segment address table: %s %s line %u " 2355 "using -segs_read_write_addr 0x%x", 2356 env_seg_addr_table_name != NULL ? 2357 "LD_SEG_ADDR_TABLE" : "-seg_addr_table", 2358 seg_addr_table_name, 2359 seg_addr_table_entry->line, 2360 (unsigned int)segs_read_write_addr); 2361 } 2362 } 2363 else{ 2364 if(seg1addr_specified && 2365 seg1addr != seg_addr_table_entry->seg1addr){ 2366 warning("-seg1addr 0x%x ignored, using " 2367 "-seg1addr 0x%x from segment address " 2368 "table: %s %s line %u", 2369 (unsigned int)seg1addr, 2370 (unsigned int)seg_addr_table_entry-> 2371 seg1addr, 2372 env_seg_addr_table_name != NULL ? 2373 "LD_SEG_ADDR_TABLE" : "-seg_addr_table", 2374 seg_addr_table_name, 2375 seg_addr_table_entry->line); 2376 } 2377 if(segs_read_only_addr_specified){ 2378 warning("-segs_read_only_addr 0x%x ignored, using " 2379 "-seg1addr 0x%x from segment address " 2380 "table: %s %s line %u", 2381 (unsigned int)segs_read_only_addr, 2382 (unsigned int)seg_addr_table_entry-> 2383 seg1addr, 2384 env_seg_addr_table_name != NULL ? 2385 "LD_SEG_ADDR_TABLE" : "-seg_addr_table", 2386 seg_addr_table_name, 2387 seg_addr_table_entry->line); 2388 } 2389 if(segs_read_write_addr_specified){ 2390 warning("-segs_read_write_addr 0x%x ignored, using " 2391 "-seg1addr 0x%x from segment address " 2392 "table: %s %s line %u", 2393 (unsigned int)segs_read_write_addr, 2394 (unsigned int)seg_addr_table_entry-> 2395 seg1addr, 2396 env_seg_addr_table_name != NULL ? 2397 "LD_SEG_ADDR_TABLE" : "-seg_addr_table", 2398 seg_addr_table_name, 2399 seg_addr_table_entry->line); 2400 } 2401 seg1addr_specified = TRUE; 2402 seg1addr = seg_addr_table_entry->seg1addr; 2403 segs_read_only_addr_specified = FALSE; 2404 segs_read_only_addr = 0; 2405 segs_read_write_addr_specified = FALSE; 2406 segs_read_write_addr = 0; 2407 } 2408 } 2409 else{ 2410 warning("%s %s not found in segment address table %s %s", 2411 seg_addr_table_filename != NULL ? 2412 "-seg_addr_table_filename" : "-dylib_install_name", 2413 seg_addr_table_filename != NULL ? 2414 seg_addr_table_filename : dylib_install_name, 2415 env_seg_addr_table_name != NULL ? 2416 "LD_SEG_ADDR_TABLE" : "-seg_addr_table", 2417 seg_addr_table_name); 2418 } 2419 } 2420 /* 2421 * If this is not a subframework then if it has an install name 2422 * then guess its implied umbrella framework name from the 2423 * install name. Then if its install name is a framework name use 2424 * that as the umbrella framework name. Otherwise it is not 2425 * considered an umbrella framework. 2426 */ 2427 if(sub_framework == FALSE && dylib_install_name != NULL){ 2428 umbrella_framework_name = guess_short_name(dylib_install_name, 2429 &is_framework, &has_suffix); 2430 if(umbrella_framework_name != NULL && is_framework == TRUE) 2431 umbrella_framework = TRUE; 2432 else 2433 umbrella_framework_name = NULL; 2434 } 2435 if(nallowable_clients != 0 && sub_framework == FALSE) 2436 fatal("-allowable_client flags can only be used when -umbrella " 2437 "is also specified"); 2438 } 2439 else{ 2440 if(segs_read_only_addr_specified) 2441 fatal("-segs_read_only_addr can only be used when -dylib " 2442 "is also specified"); 2443 if(segs_read_write_addr_specified) 2444 fatal("-segs_read_write_addr can only be used when -dylib " 2445 "is also specified"); 2446 if(seg_addr_table_name != NULL) 2447 fatal("-seg_addr_table can only be used when -dylib " 2448 "is also specified"); 2449 if(sub_framework == TRUE) 2450 fatal("-umbrella %s can only be used when -dylib " 2451 "is also specified", umbrella_framework_name); 2452 if(nsub_umbrellas != 0) 2453 fatal("-sub_umbrella flags can only be used when -dylib " 2454 "is also specified"); 2455 if(nsub_librarys != 0) 2456 fatal("-sub_library flags can only be used when -dylib " 2457 "is also specified"); 2458 if(nallowable_clients != 0) 2459 fatal("-allowable_client flags can only be used when -dylib " 2460 "is also specified"); 2461 if(moduletype_specified == TRUE) 2462 fatal("-single_module or -multi_module flags can only be used " 2463 "when -dylib is also specified"); 2464 } 2465 2466 /* 2467 * For Mac OS X 10.4 and later, prebinding will be limited to split 2468 * shared libraries. So if this is not a split library then turn off 2469 * prebinding. 2470 */ 2471 if(macosx_deployment_target.major >= 4){ 2472 if(filetype != MH_DYLIB){ 2473 /* 2474 * If this is arm* or xscale, we want to prebind executables 2475 * too, not just dylibs and frameworks. 2476 */ 2477 if (!((arch_flag.name != NULL) && 2478 ((strncmp(arch_flag.name, "arm", 3) == 0) || 2479 (strcmp(arch_flag.name, "xscale") == 0)))) 2480 { 2481 if(prebinding_via_LD_PREBIND == FALSE && 2482 prebinding_flag_specified == TRUE && 2483 prebinding == TRUE){ 2484 warning("-prebind ignored because MACOSX_DEPLOYMENT_TARGET " 2485 "environment variable greater or equal to 10.4"); 2486 } 2487 prebinding = FALSE; 2488 } 2489 } 2490 /* 2491 * This is an MH_DYLIB. First see if it is on the list of libraries 2492 * not to be prebound. Then see if was specified to be built as a 2493 * split, if not check LD_SPLITSEGS_NEW_LIBRARIES to see if we are 2494 * forcing it to be a split library. 2495 */ 2496 else{ 2497 /* 2498 * If this library was not in the seg_addr_table see if it is 2499 * on the list of libraries not to be prebound. And if so turn 2500 * off prebinding. Note this list is only ever used when 2501 * macosx_deployment_target.major >= 4 . 2502 */ 2503 if(seg_addr_table_entry == NULL && 2504 unprebound_library(dylib_install_name, 2505 seg_addr_table_filename) == TRUE){ 2506 if(prebinding_flag_specified == TRUE && 2507 prebinding == TRUE){ 2508 warning("-prebind ignored because -install_name %s " 2509 "listed in LD_UNPREBOUND_LIBRARIES environment " 2510 "variable file: %s", dylib_install_name, 2511 getenv("LD_UNPREBOUND_LIBRARIES")); 2512 } 2513 prebinding = FALSE; 2514 } 2515 else{ 2516 /* 2517 * This is not on the list of libraries not to be prebound, 2518 * and if there was no seg_addr_table entry for this then 2519 * force this to be a split library. Note even if 2520 * prebinding was not specified we will still force this to 2521 * be a split library. 2522 */ 2523 if(seg_addr_table_entry == NULL && 2524 getenv("LD_SPLITSEGS_NEW_LIBRARIES") != NULL){ 2525 unsigned long arch_rw_addr = 2526 get_shared_region_size_from_flag(&arch_flag); 2527 2528 if(seg1addr_specified){ 2529 warning("-seg1addr 0x%x ignored, using " 2530 "-segs_read_only_addr 0x%x and " 2531 "-segs_read_write_addr 0x%x because " 2532 "LD_SPLITSEGS_NEW_LIBRARIES environment is " 2533 "set",(unsigned int)seg1addr, 0, 2534 (unsigned int)arch_rw_addr); 2535 } 2536 seg1addr_specified = FALSE; 2537 seg1addr = 0; 2538 segs_read_only_addr_specified = TRUE; 2539 segs_read_only_addr = 0; 2540 segs_read_write_addr = arch_rw_addr; 2541 } 2542 /* 2543 * Finally if this is not a split library then turn off 2544 * prebinding. 2545 */ 2546 if(segs_read_only_addr_specified == FALSE){ 2547 if(prebinding_via_LD_PREBIND == FALSE && 2548 prebinding_flag_specified == TRUE && 2549 prebinding == TRUE){ 2550 warning("-prebind ignored because " 2551 "MACOSX_DEPLOYMENT_TARGET environment " 2552 "variable greater or equal to 10.4"); 2553 } 2554 prebinding = FALSE; 2555 } 2556 } 2557 } 2558 } 2559 2560 if(filetype == MH_BUNDLE){ 2561 if(dynamic == FALSE) 2562 fatal("incompatible flag -bundle used (must specify " 2563 "\"-dynamic\" to be used)"); 2564 if(save_reloc) 2565 fatal("can't use -r and -bundle (flags are mutually " 2566 "exclusive, only one or the other can be used)"); 2567 if(strip_level == STRIP_ALL) 2568 fatal("can't use -s with -bundle (file must contain " 2569 "at least global symbols, for maximum stripping use -x)"); 2570 if(Aflag_specified) 2571 fatal("can't use -A and -bundle"); 2572 if(keep_private_externs == TRUE) 2573 fatal("can't use -keep_private_externs and -bundle"); 2574 if(segaddr_specified) 2575 fatal("can't use -segaddr options with -bundle (use " 2576 "seg1addr to specify the starting address)"); 2577 if(seglinkedit_specified && seglinkedit == FALSE) 2578 fatal("can't use -noseglinkedit with -bundle " 2579 "(resulting file must have a link edit segment to access " 2580 "symbols)"); 2581 if(prebinding == TRUE){ 2582 if(prebinding_flag_specified == TRUE) 2583 warning("-prebind has no effect with -bundle"); 2584 prebinding = FALSE; 2585 } 2586 if(private_bundle == TRUE && twolevel_namespace == TRUE) 2587 warning("-private_bundle has no effect when " 2588 "-twolevel_namespace is in effect"); 2589 if(twolevel_namespace_hints_specified != TRUE) 2590 twolevel_namespace_hints = FALSE; 2591 } 2592 else{ 2593 if(client_name != NULL) 2594 fatal("-client_name %s flag can only be used with -bundle", 2595 client_name); 2596 if(bundle_loader != NULL) 2597 fatal("-bundle_loader %s flag can only be used with -bundle", 2598 bundle_loader); 2599 if(private_bundle == TRUE) 2600 fatal("-private_bundle flag can only be used with -bundle"); 2601 } 2602 if(filetype != MH_DYLINKER){ 2603 if(dylinker_install_name != NULL) 2604 warning("flag: -dylinker_install_name %s ignored (-dylinker " 2605 "was not specified", dylinker_install_name); 2606 } 2607 if(filetype != MH_DYLIB){ 2608 if(dylib_install_name != NULL) 2609 warning("flag: -dylib_install_name %s ignored (-dylib " 2610 "was not specified", dylib_install_name); 2611 if(dylib_current_version != 0) 2612 warning("flag: -dylib_current_version %u ignored (-dylib " 2613 "was not specified", dylib_current_version); 2614 if(dylib_compatibility_version != 0) 2615 warning("flag: -dylib_compatibility_version %u ignored (-dylib" 2616 " was not specified", dylib_compatibility_version); 2617 if(init_name != NULL) 2618 warning("flag: -init %s ignored (-dylib was not specified", 2619 init_name); 2620 } 2621 if(twolevel_namespace == TRUE && 2622 undefined_flag != UNDEFINED_ERROR && 2623 undefined_flag != UNDEFINED_DYNAMIC_LOOKUP && 2624 undefined_flag != UNDEFINED_DEFINE_A_WAY){ 2625 if(macosx_deployment_target.major >= 3) 2626 fatal("-undefined error, -undefined dynamic_lookup or " 2627 "-undefined define_a_way must be used when " 2628 "-twolevel_namespace is in effect"); 2629 else 2630 fatal("-undefined error or -undefined define_a_way must be " 2631 "used when -twolevel_namespace is in effect"); 2632 } 2633 if(undefined_flag == UNDEFINED_DYNAMIC_LOOKUP){ 2634 if(dynamic == FALSE) 2635 fatal("incompatible flag -undefined dynamic_lookup used (must " 2636 "specify \"-dynamic\" to be used)"); 2637 if(macosx_deployment_target.major < 3) 2638 fatal("flag: -undefined dynamic_lookup can't be used with " 2639 "MACOSX_DEPLOYMENT_TARGET environment variable set to: " 2640 "%s", macosx_deployment_target.name); 2641 } 2642 if(twolevel_namespace == TRUE && nundef_syms != 0){ 2643 fatal("can't use -U flags when -twolevel_namespace is in effect"); 2644 } 2645 if(nomultidefs == TRUE){ 2646 if(multiply_defined_flag_specified == TRUE && 2647 multiply_defined_flag != MULTIPLY_DEFINED_ERROR) 2648 fatal("-multiply_defined error must be used when -nomultidefs " 2649 "is specified"); 2650 multiply_defined_flag = MULTIPLY_DEFINED_ERROR; 2651 } 2652 if(prebinding == TRUE && undefined_flag == UNDEFINED_SUPPRESS){ 2653 if(prebinding_flag_specified == TRUE) 2654 warning("-undefined suppress disables -prebind"); 2655 prebinding = FALSE; 2656 } 2657 if(prebinding == TRUE && save_reloc){ 2658 if(prebinding_flag_specified == TRUE) 2659 warning("-r disables -prebind"); 2660 prebinding = FALSE; 2661 } 2662 if(prebinding == TRUE && dynamic == FALSE){ 2663 prebinding = FALSE; 2664 } 2665 2666 /* 2667 * If the output file name as not specified set it to the default name 2668 * "a.out". This needs to be done before any segments are merged 2669 * because this is used when merging them (the 'filename' field in a 2670 * merged_segment is set to it). 2671 */ 2672 if(outputfile == NULL) 2673 outputfile = "a.out"; 2674 /* 2675 * If the -A flag is specified and the file type has not been specified 2676 * then make the output file type MH_OBJECT. 2677 */ 2678 if(Aflag_specified == TRUE && filetype_specified == FALSE) 2679 filetype = MH_OBJECT; 2680 2681 /* 2682 * If neither the -seglinkedit or -noseglinkedit has been specified then 2683 * set creation of this segment if the output file type can have one. 2684 * If -seglinkedit has been specified make sure the output file type 2685 * can have one. 2686 */ 2687 if(seglinkedit_specified == FALSE){ 2688 if(filetype == MH_EXECUTE || filetype == MH_BUNDLE || 2689 filetype == MH_FVMLIB || 2690 filetype == MH_DYLIB || filetype == MH_DYLINKER) 2691 seglinkedit = TRUE; 2692 else 2693 seglinkedit = FALSE; 2694 } 2695 else{ 2696 if(seglinkedit && 2697 (filetype != MH_EXECUTE && filetype != MH_BUNDLE && 2698 filetype != MH_FVMLIB && 2699 filetype != MH_DYLIB && filetype != MH_DYLINKER)) 2700 fatal("link edit segment can't be created (wrong output file " 2701 "type, file type must be MH_EXECUTE, MH_BUNDLE, " 2702 "MH_DYLIB, MH_DYLINKER or MH_FVMLIB)"); 2703 } 2704 if(allow_stack_execute == TRUE && filetype != MH_EXECUTE) 2705 fatal("-allow_stack_execute can only be used when output file type " 2706 "is MH_EXECUTE"); 2707 2708 if(trace) 2709 print("%s: Pass 1\n", progname); 2710 /* 2711 * This pass of parsing arguments only processes object files 2712 * and creation of symbols now that all the options are set. 2713 * This are order dependent and must be processed as they appear 2714 * on the command line. 2715 */ 2716 symbols_created = 0; 2717 objects_specified = 0; 2718 sections_created = 0; 2719 /* 2720 * If a -bundle_loader is specified and this is a flat_namespace 2721 * output force the bundle_loader to be loaded first. 2722 */ 2723 if(bundle_loader != NULL && twolevel_namespace == FALSE){ 2724 pass1(bundle_loader, FALSE, FALSE, FALSE, TRUE, FALSE); 2725 } 2726 for(i = 1 ; i < argc ; i++){ 2727 if(*argv[i] != '-'){ 2728 /* just a normal object file name */ 2729 pass1(argv[i], FALSE, FALSE, FALSE, FALSE, FALSE); 2730 objects_specified++; 2731 } 2732 else{ 2733 p = &(argv[i][1]); 2734 switch(*p){ 2735 case 'b': 2736 if(strcmp(p, "bundle_loader") == 0){ 2737 /* 2738 * If a -bundle_loader was specified and this is a 2739 * flat_namespace output force the bundle_loader was 2740 * loaded first above. 2741 */ 2742 if(twolevel_namespace == TRUE) 2743 pass1(argv[i+1], FALSE, FALSE, FALSE, TRUE, FALSE); 2744 i++; 2745 break; 2746 } 2747 break; 2748 case 'l': 2749 /* path searched abbrevated file name */ 2750 pass1(argv[i], TRUE, FALSE, FALSE, FALSE, FALSE); 2751 objects_specified++; 2752 break; 2753 case 'A': 2754 if(base_obj != NULL) 2755 fatal("only one -A argument can be specified"); 2756 pass1(argv[++i], FALSE, TRUE, FALSE, FALSE, FALSE); 2757 objects_specified++; 2758 break; 2759 case 'f': 2760 if(strcmp(p, "framework") == 0){ 2761 if(dynamic == FALSE) 2762 fatal("incompatible flag -framework used (must " 2763 "specify \"-dynamic\" to be used)"); 2764 pass1(argv[++i], FALSE, FALSE, TRUE, FALSE, FALSE); 2765 objects_specified++; 2766 } 2767 if(strcmp(p, "filelist") == 0){ 2768 filelist = argv[++i]; 2769 dirname = strrchr(filelist, ','); 2770 if(dirname != NULL){ 2771 *dirname = '\0'; 2772 dirname++; 2773 } 2774 else 2775 dirname = ""; 2776 if((fd = open(filelist, O_RDONLY, 0)) == -1) 2777 system_fatal("can't open file list file: %s", 2778 filelist); 2779 if(fstat(fd, &stat_buf) == -1) 2780 system_fatal("can't stat file list file: %s", 2781 filelist); 2782 /* 2783 * For some reason mapping files with zero size fails 2784 * so it has to be handled specially. 2785 */ 2786 if(stat_buf.st_size != 0){ 2787 if((r = map_fd((int)fd, (vm_offset_t)0, 2788 (vm_offset_t *)&(addr), (boolean_t)TRUE, 2789 (vm_size_t)stat_buf.st_size)) != KERN_SUCCESS) 2790 mach_fatal(r, "can't map file list file: %s", 2791 filelist); 2792 } 2793 else{ 2794 fatal("file list file: %s is empty", filelist); 2795 } 2796 close(fd); 2797 file_name = addr; 2798 for(j = 0; j < stat_buf.st_size; j++){ 2799 if(addr[j] == '\n'){ 2800 addr[j] = '\0'; 2801 if(*dirname != '\0'){ 2802 file_name = mkstr(dirname, "/", 2803 file_name, NULL); 2804 } 2805 pass1(file_name, FALSE, FALSE, FALSE, FALSE, 2806 FALSE); 2807 objects_specified++; 2808 file_name = addr + j + 1; 2809 } 2810 } 2811 } 2812 if(strcmp(p, "final_output") == 0) 2813 i++; 2814 break; 2815 case 'm': 2816 if(strcmp(p, "multiply_defined") == 0 || 2817 strcmp(p, "multiply_defined_unused") == 0 || 2818 strcmp(p, "macosx_version_min") == 0){ 2819 i++; 2820 break; 2821 } 2822 break; 2823 case 'u': 2824 if(strcmp(p, "undefined") == 0 || 2825 strcmp(p, "umbrella") == 0 || 2826 strcmp(p, "unexported_symbols_list") == 0){ 2827 i++; 2828 break; 2829 } 2830 /* cause the specified symbol name to be undefined */ 2831 (void)command_line_symbol(argv[++i]); 2832 symbols_created++; 2833 break; 2834 case 'i': 2835 if(strcmp(p, "image_base") == 0){ 2836 i++; 2837 break; 2838 } 2839 else if(strcmp(p, "init") == 0){ 2840 i++; 2841 break; 2842 } 2843 else if(strcmp(p, "install_name") == 0){ 2844 i++; 2845 break; 2846 } 2847 /* create an indirect symbol, symbol_name, to be an indirect 2848 symbol for indr_symbol_name */ 2849 symbol_name = p + 1; 2850 indr_symbol_name = strchr(p + 1, ':'); 2851 *indr_symbol_name = '\0'; 2852 indr_symbol_name++; 2853 command_line_indr_symbol(symbol_name, indr_symbol_name); 2854 symbols_created++; 2855 break; 2856 2857 /* multi argument flags */ 2858 case 'a': 2859 if(strcmp(p, "all_load") == 0 || 2860 strcmp(p, "arch_multiple") == 0 || 2861 strcmp(p, "arch_errors_fatal") == 0 || 2862 strcmp(p, "allow_stack_execute") == 0) 2863 break; 2864 i++; 2865 break; 2866 case 'c': 2867 i++; 2868 break; 2869 case 'p': 2870 if(strcmp(p, "pagezero_size") == 0){ 2871 i++; 2872 break; 2873 } 2874 break; 2875 case 's': 2876 if(strcmp(p, "sectcreate") == 0 || 2877 strcmp(p, "segcreate") == 0){ 2878 sections_created++; 2879 i += 3; 2880 } 2881 else if(strcmp(p, "sectalign") == 0 || 2882 strcmp(p, "segprot") == 0 || 2883 strcmp(p, "sectorder") == 0) 2884 i += 3; 2885 else if(strcmp(p, "segaddr") == 0 || 2886 strcmp(p, "sect_diff_relocs") == 0 || 2887 strcmp(p, "sectobjectsymbols") == 0) 2888 i += 2; 2889 else if(strcmp(p, "seg1addr") == 0 || 2890 strcmp(p, "stack_addr") == 0 || 2891 strcmp(p, "stack_size") == 0 || 2892 strcmp(p, "segalign") == 0 || 2893 strcmp(p, "segs_read_only_addr") == 0 || 2894 strcmp(p, "segs_read_write_addr") == 0 || 2895 strcmp(p, "seg_addr_table") == 0 || 2896 strcmp(p, "seg_addr_table_filename") == 0 || 2897 strcmp(p, "sub_umbrella") == 0 || 2898 strcmp(p, "sub_library") == 0 || 2899 strcmp(p, "syslibroot") == 0) 2900 i++; 2901 break; 2902 case 'r': 2903 if(strcmp(p, "r") == 0 || 2904 strcmp(p, "run_init_lazily") == 0) 2905 break; 2906 i++; 2907 break; 2908 case 'o': 2909 if(strcmp(p, "object") == 0) 2910 break; 2911 i++; 2912 break; 2913 case 'e': 2914 if(strcmp(p, "execute") == 0) 2915 break; 2916 i++; 2917 break; 2918 case 'd': 2919 if(strcmp(p, "d") == 0 || 2920 strcmp(p, "dylib") == 0 || 2921 strcmp(p, "dylinker") == 0 || 2922 strcmp(p, "dynamic") == 0 || 2923 strcmp(p, "dead_strip") == 0) 2924 break; 2925 i++; 2926 break; 2927 case 'h': 2928 if(strcmp(p, "headerpad_max_install_names") == 0) 2929 break; 2930 i++; 2931 break; 2932 case 'U': 2933 case 'N': 2934 case 'Y': 2935 i++; 2936 break; 2937 case 'w': 2938 if(strcmp(p, "weak_reference_mismatches") == 0) 2939 i++; 2940 else if(strcmp(p, "weak_library") == 0){ 2941 pass1(argv[++i], FALSE, FALSE, FALSE, FALSE, TRUE); 2942 objects_specified++; 2943 } 2944 else if(strncmp(p, "weak-l", sizeof("weak-l") - 1) == 0){ 2945 /* path searched abbrevated file name */ 2946 pass1(argv[i] + sizeof("weak"), TRUE, FALSE, FALSE, 2947 FALSE, TRUE); 2948 objects_specified++; 2949 } 2950 else if(strcmp(p, "weak_framework") == 0){ 2951 if(dynamic == FALSE) 2952 fatal("incompatible flag -weak_framework used (must" 2953 " specify \"-dynamic\" to be used)"); 2954 pass1(argv[++i], FALSE, FALSE, TRUE, FALSE, TRUE); 2955 objects_specified++; 2956 } 2957 break; 2958 } 2959 } 2960 } 2961 2962 /* 2963 * If the architecture was not specified, and was inferred 2964 * from the object files, if it is a 64-bit architecture it is an error. 2965 */ 2966 if(arch_flag.cputype != 0 && 2967 arch_flag.cputype & CPU_ARCH_ABI64){ 2968 fatal("does not support 64-bit architectures"); 2969 } 2970 2971 /* 2972 * Now search the libraries on the dynamic shared libraries search list 2973 */ 2974 search_dynamic_libs(); 2975 2976 /* 2977 * Check to see that the output file will have something in it. 2978 */ 2979 if(objects_specified == 0){ 2980 if(symbols_created != 0 || sections_created != 0){ 2981 warning("no object files specified, only command line created " 2982 "symbols and/or sections created from files will " 2983 "appear in the output file"); 2984 if(arch_flag.name == NULL) 2985 target_byte_sex = host_byte_sex; 2986 segalign = host_pagesize; 2987 } 2988 else{ 2989 if(vflag == TRUE) 2990 ld_exit(0); 2991 fatal("no object files specified"); 2992 } 2993 } 2994 else if(base_obj != NULL && nobjects == 1){ 2995 if(symbols_created != 0 || sections_created != 0) 2996 warning("no object files loaded other than base file, only " 2997 "additional command line created symbols and/or " 2998 "sections created from files will appear in the output " 2999 "file"); 3000 else{ 3001 if(vflag == TRUE) 3002 ld_exit(0); 3003 fatal("no object files loaded other than base file"); 3004 } 3005 } 3006 else if(nobjects == 0){ 3007 if(symbols_created != 0 || sections_created != 0) 3008 warning("no object files loaded, only command line created " 3009 "symbols and/or sections created from files will " 3010 "appear in the output file"); 3011 else{ 3012 if(vflag == TRUE) 3013 ld_exit(0); 3014 fatal("no object files loaded"); 3015 } 3016 } 3017 3018#ifdef DEBUG 3019 if(debug & (1 < 0)) 3020 print_object_list(); 3021 if(debug & (1 << 1)) 3022 print_merged_sections("after pass1"); 3023 if(debug & (1 << 2)) 3024 print_symbol_list("after pass1", TRUE); 3025 if(debug & (1 << 3)) 3026 print_undefined_list(); 3027 if(debug & (1 << 4)) 3028 print_segment_specs(); 3029 if(debug & (1 << 5)) 3030 print_load_fvmlibs_list(); 3031 if(debug & (1 << 6)) 3032 print_fvmlib_segments(); 3033 if(debug & (1 << 9)){ 3034 print("Number of objects loaded = %lu\n", nobjects); 3035 print("Number of merged symbols = %lu\n", nmerged_symbols); 3036 } 3037#endif /* DEBUG */ 3038 3039 /* 3040 * If there were any errors from pass1() then don't continue. 3041 */ 3042 if(errors != 0) 3043 ld_exit(1); 3044 3045 /* 3046 * Print which files are loaded if requested. 3047 */ 3048 if(whatsloaded == TRUE) 3049 print_whatsloaded(); 3050 3051 /* 3052 * Clean up any data structures not need for layout() or pass2(). 3053 */ 3054 if(nsearch_dirs != 0){ 3055 free(search_dirs); 3056 nsearch_dirs = 0; 3057 } 3058 3059 /* 3060 * Layout the output object file. 3061 */ 3062 layout(); 3063 3064 /* 3065 * Check to that the exported or unexported symbols listed were seen. 3066 */ 3067 if(save_symbols != NULL){ 3068 missing_syms = FALSE; 3069 for(j = 0; j < nsave_symbols ; j++){ 3070 if(save_symbols[j].seen == FALSE){ 3071 if(missing_syms == FALSE){ 3072 error("symbols names listed in " 3073 "-exported_symbols_list: %s not in linked " 3074 "objects", exported_symbols_list); 3075 missing_syms = TRUE; 3076 } 3077 printf("%s\n", save_symbols[j].name); 3078 } 3079 } 3080 } 3081 3082 /* 3083 * If there were any errors from layout() then don't continue. 3084 */ 3085 if(errors != 0) 3086 ld_exit(1); 3087 3088 /* 3089 * Clean up any data structures not need for pass2(). 3090 */ 3091 free_pass1_symbol_data(); 3092 if(ntrace_syms != 0){ 3093 free(trace_syms); 3094 ntrace_syms = 0; 3095 } 3096 if(nundef_syms != 0){ 3097 free(undef_syms); 3098 nundef_syms = 0; 3099 } 3100 3101 /* 3102 * Write the output object file doing relocation on the sections. 3103 */ 3104 if(trace) 3105 print("%s: Pass 2\n", progname); 3106 pass2(); 3107 /* 3108 * If there were any errors from pass2() make sure the output file is 3109 * removed and exit non-zero. 3110 */ 3111 if(errors != 0) 3112 cleanup(); 3113 3114 if(hash_instrument_specified == TRUE) 3115 hash_instrument(); 3116 3117 ld_exit(0); 3118 3119 /* this is to remove the compiler warning, it never gets here */ 3120 return(0); 3121} 3122 3123/* 3124 * unprebound_library() checks the file for the environment variable 3125 * LD_UNPREBOUND_LIBRARIES to see if the dynamic library is one listed as to 3126 * not be prebound. The dynamic library is specified with the 3127 * dylib_install_name unless seg_addr_table_filename is not NULL then 3128 * seg_addr_table_filename is used. If it is found on the list then TRUE is 3129 * returned. If not FALSE is returned. 3130 */ 3131static 3132enum bool 3133unprebound_library( 3134char *dylib_install_name, 3135char *seg_addr_table_filename) 3136{ 3137 int fd; 3138 kern_return_t r; 3139 struct stat stat_buf; 3140 unsigned long j, file_size, line; 3141 char *file_name, *library_name, *file_addr, *name, *end; 3142 3143 /* 3144 * If there is no file name then it is not on the list and return FALSE. 3145 */ 3146 file_name = getenv("LD_UNPREBOUND_LIBRARIES"); 3147 if(file_name == NULL) 3148 return(FALSE); 3149 3150 /* 3151 * If there is no library name then it is not on the list and return 3152 * FALSE. 3153 */ 3154 if(seg_addr_table_filename != NULL) 3155 library_name = dylib_install_name; 3156 else if(dylib_install_name != NULL) 3157 library_name = dylib_install_name; 3158 else 3159 return(FALSE); 3160 3161 3162 if((fd = open(file_name, O_RDONLY, 0)) == -1) 3163 system_fatal("Can't open: %s for LD_UNPREBOUND_LIBRARIES " 3164 "environment variable", file_name); 3165 if(fstat(fd, &stat_buf) == -1) 3166 system_fatal("Can't stat file: %s for LD_UNPREBOUND_LIBRARIES " 3167 "environment variable", file_name); 3168 /* 3169 * For some reason mapping files with zero size fails 3170 * so it has to be handled specially. 3171 */ 3172 if(stat_buf.st_size != 0){ 3173 if((r = map_fd((int)fd, (vm_offset_t)0, 3174 (vm_offset_t *)&file_addr, (boolean_t)TRUE, 3175 (vm_size_t)stat_buf.st_size)) != KERN_SUCCESS) 3176 mach_fatal(r, "can't map file: %s for LD_UNPREBOUND_LIBRARIES " 3177 "environment variable", file_name); 3178 } 3179 else 3180 fatal("Empty file: %s for LD_UNPREBOUND_LIBRARIES environment " 3181 "variable", file_name); 3182 close(fd); 3183 file_size = stat_buf.st_size; 3184 3185 /* 3186 * Got the file mapped now parse it. 3187 */ 3188 if(file_addr[file_size - 1] != '\n') 3189 fatal("file: %s for LD_UNPREBOUND_LIBRARIES environment variable " 3190 "does not end in new line", file_name); 3191 3192 line = 1; 3193 for(j = 0; j < file_size; /* no increment expression */ ){ 3194 /* Skip lines that start with '#' */ 3195 if(file_addr[j] == '#'){ 3196 j++; 3197 while(file_addr[j] != '\n') 3198 j++; 3199 continue; 3200 } 3201 /* Skip blank lines and leading white space */ 3202 while(file_addr[j] == ' ' || file_addr[j] == '\t') 3203 j++; 3204 if(file_addr[j] == '\n'){ 3205 j++; 3206 line++; 3207 continue; 3208 } 3209 if(j == file_size) 3210 fatal("missing library install name on line %lu in file: " 3211 "%s for LD_UNPREBOUND_LIBRARIES environment variable", 3212 line, file_name); 3213 3214 name = file_addr + j; 3215 while(file_addr[j] != '\n') 3216 j++; 3217 file_addr[j] = '\0'; 3218 end = file_addr + j; 3219 line++; 3220 j++; 3221 3222 /* Trim trailing spaces */ 3223 end--; 3224 while(end > name && (*end == ' ' || *end == '\t')){ 3225 *end = '\0'; 3226 end--; 3227 } 3228 3229 /* finally compare the name on this line with the library name */ 3230 if(strcmp(library_name, name) == 0) 3231 return(TRUE); 3232 } 3233 3234 return(FALSE); 3235} 3236 3237/* 3238 * ispoweroftwo() returns TRUE or FALSE depending if x is a power of two. 3239 */ 3240static 3241enum 3242bool 3243ispoweroftwo( 3244unsigned long x) 3245{ 3246 if(x == 0) 3247 return(TRUE); 3248 while((x & 0x1) != 0x1){ 3249 x >>= 1; 3250 } 3251 if((x & ~0x1) != 0) 3252 return(FALSE); 3253 else 3254 return(TRUE); 3255} 3256 3257/* 3258 * getprot() returns the vm_prot for the specified string passed to it. The 3259 * string may contain any of the following characters: 'r', 'w', 'x' and '-' 3260 * representing read, write, execute and no protections. The pointer pointed 3261 * to by endp is set to the first character that is not one of the above 3262 * characters. 3263 */ 3264static 3265vm_prot_t 3266getprot( 3267char *prot, 3268char **endp) 3269{ 3270 vm_prot_t vm_prot; 3271 3272 vm_prot = VM_PROT_NONE; 3273 while(*prot){ 3274 switch(*prot){ 3275 case 'r': 3276 case 'R': 3277 vm_prot |= VM_PROT_READ; 3278 break; 3279 case 'w': 3280 case 'W': 3281 vm_prot |= VM_PROT_WRITE; 3282 break; 3283 case 'x': 3284 case 'X': 3285 vm_prot |= VM_PROT_EXECUTE; 3286 break; 3287 case '-': 3288 break; 3289 default: 3290 *endp = prot; 3291 return(vm_prot); 3292 } 3293 prot++; 3294 } 3295 *endp = prot; 3296 return(vm_prot); 3297} 3298 3299/* 3300 * check_max_init_prot() checks to make sure that all protections in the initial 3301 * protection are also in the maximum protection. 3302 */ 3303static 3304enum bool 3305check_max_init_prot( 3306vm_prot_t maxprot, 3307vm_prot_t initprot) 3308{ 3309 if(((initprot & VM_PROT_READ) && !(maxprot & VM_PROT_READ)) || 3310 ((initprot & VM_PROT_WRITE) && !(maxprot & VM_PROT_WRITE)) || 3311 ((initprot & VM_PROT_EXECUTE) && !(maxprot & VM_PROT_EXECUTE)) ) 3312 return(FALSE); 3313 return(TRUE); 3314} 3315 3316/* 3317 * ld_exit() is use for all exit()s from the link editor. 3318 */ 3319static 3320void 3321ld_exit( 3322int exit_value) 3323{ 3324 exit(exit_value); 3325} 3326 3327/* 3328 * cleanup() is called by all routines handling fatal errors to remove the 3329 * output file if it had been created by the link editor and exit non-zero. 3330 */ 3331static 3332void 3333cleanup(void) 3334{ 3335 if(output_addr != NULL) 3336 unlink(outputfile); 3337 ld_exit(1); 3338} 3339 3340/* 3341 * handler() is the routine for catching SIGINT, SIGTERM, SIGBUG & SIGSEGV 3342 * signals. It cleans up and exit()'s non-zero. 3343 */ 3344static 3345void 3346handler( 3347int sig) 3348{ 3349#ifdef __MWERKS__ 3350 int dummy; 3351 dummy = sig; 3352#endif 3353 if(output_addr != NULL) 3354 unlink(outputfile); 3355 _exit(1); 3356} 3357 3358/* 3359 * allocate() is just a wrapper around malloc that prints and error message and 3360 * exits if the malloc fails. 3361 */ 3362__private_extern__ 3363void * 3364allocate( 3365unsigned long size) 3366{ 3367 void *p; 3368 3369 if(size == 0) 3370 return(NULL); 3371 if((p = malloc(size)) == NULL) 3372 system_fatal("virtual memory exhausted (malloc failed)"); 3373 return(p); 3374} 3375 3376/* 3377 * reallocate() is just a wrapper around realloc that prints and error message 3378 * and exits if the realloc fails. 3379 */ 3380__private_extern__ 3381void * 3382reallocate( 3383void *p, 3384unsigned long size) 3385{ 3386 if(p == NULL) 3387 return(allocate(size)); 3388 if((p = realloc(p, size)) == NULL) 3389 system_fatal("virtual memory exhausted (realloc failed)"); 3390 return(p); 3391} 3392 3393/* 3394 * savestr() malloc's space for the string passed to it, copys the string into 3395 * the space and returns a pointer to that space. 3396 */ 3397__private_extern__ 3398char * 3399savestr( 3400const char *s) 3401{ 3402 long len; 3403 char *r; 3404 3405 len = strlen(s) + 1; 3406 r = (char *)allocate(len); 3407 strcpy(r, s); 3408 return(r); 3409} 3410 3411/* 3412 * Mkstr() creates a string that is the concatenation of a variable number of 3413 * strings. It is pass a variable number of pointers to strings and the last 3414 * pointer is NULL. It returns the pointer to the string it created. The 3415 * storage for the string is malloc()'ed can be free()'ed when nolonger needed. 3416 */ 3417static 3418char * 3419mkstr( 3420const char *args, 3421...) 3422{ 3423 va_list ap; 3424 char *s, *p; 3425 unsigned long size; 3426 3427 size = 0; 3428 if(args != NULL){ 3429 size += strlen(args); 3430 va_start(ap, args); 3431 p = (char *)va_arg(ap, char *); 3432 while(p != NULL){ 3433 size += strlen(p); 3434 p = (char *)va_arg(ap, char *); 3435 } 3436 } 3437 s = allocate(size + 1); 3438 *s = '\0'; 3439 3440 if(args != NULL){ 3441 (void)strcat(s, args); 3442 va_start(ap, args); 3443 p = (char *)va_arg(ap, char *); 3444 while(p != NULL){ 3445 (void)strcat(s, p); 3446 p = (char *)va_arg(ap, char *); 3447 } 3448 va_end(ap); 3449 } 3450 return(s); 3451} 3452#endif /* !defined(RLD) */ 3453 3454/* 3455 * rnd() rounds v to a multiple of r. 3456 */ 3457__private_extern__ 3458unsigned long 3459rnd( 3460unsigned long v, 3461unsigned long r) 3462{ 3463 r--; 3464 v += r; 3465 v &= ~(long)r; 3466 return(v); 3467} 3468 3469#ifndef RLD 3470#include "stuff/unix_standard_mode.h" 3471/* 3472 * All printing of all messages goes through this function. 3473 */ 3474__private_extern__ 3475void 3476vprint( 3477const char *format, 3478va_list ap) 3479{ 3480 if(get_unix_standard_mode() == TRUE) 3481 vfprintf(stderr, format, ap); 3482 else 3483 vprintf(format, ap); 3484} 3485#endif /* !defined(RLD) */ 3486 3487/* 3488 * The print function that just calls the above vprint() function. 3489 */ 3490__private_extern__ 3491void 3492print( 3493const char *format, 3494...) 3495{ 3496 va_list ap; 3497 3498 va_start(ap, format); 3499 vprint(format, ap); 3500 va_end(ap); 3501} 3502 3503/* 3504 * The ld_trace function that logs things for B&I. 3505 */ 3506__private_extern__ 3507void 3508ld_trace( 3509const char *format, 3510...) 3511{ 3512#ifdef KLD 3513 va_list ap; 3514 3515 va_start(ap, format); 3516 vprint(format, ap); 3517 va_end(ap); 3518#else 3519 static int trace_file = -1; 3520 char trace_buffer[MAXPATHLEN * 2]; 3521 char *buffer_ptr; 3522 int length; 3523 ssize_t amount_written; 3524 3525 if(trace_file == -1){ 3526 if(trace_file_path != NULL){ 3527 trace_file = open(trace_file_path, O_WRONLY | O_APPEND | O_CREAT, 0666); 3528 if(trace_file == -1) 3529 fatal("Could not open or create trace file: %s\n", trace_file_path); 3530 } 3531 else{ 3532 trace_file = fileno(stderr); 3533 } 3534 } 3535 va_list ap; 3536 3537 va_start(ap, format); 3538 length = vsnprintf(trace_buffer, sizeof(trace_buffer), format, ap); 3539 va_end(ap); 3540 buffer_ptr = trace_buffer; 3541 while(length > 0){ 3542 amount_written = write(trace_file, buffer_ptr, length); 3543 if(amount_written == -1) 3544 /* Failure to write shouldn't fail the build. */ 3545 return; 3546 buffer_ptr += amount_written; 3547 length -= amount_written; 3548 } 3549#endif 3550} 3551 3552static 3553void 3554print_architecture_banner(void) 3555{ 3556 static enum bool printed = FALSE; 3557 3558 if(arch_multiple == TRUE && printed == FALSE && arch_flag.name != NULL){ 3559 print("%s: for architecture %s\n", progname, arch_flag.name); 3560 printed = TRUE; 3561 } 3562} 3563 3564/* 3565 * Print the warning message. This is non-fatal and does not set 'errors'. 3566 */ 3567__private_extern__ 3568void 3569warning( 3570const char *format, 3571...) 3572{ 3573 va_list ap; 3574 3575 if(nowarnings == TRUE) 3576 return; 3577 if(arch_multiple) 3578 print_architecture_banner(); 3579 va_start(ap, format); 3580 print("%s: warning ", progname); 3581 vprint(format, ap); 3582 print("\n"); 3583 va_end(ap); 3584} 3585 3586/* 3587 * Print the error message and set the 'error' indication. 3588 */ 3589__private_extern__ 3590void 3591error( 3592const char *format, 3593...) 3594{ 3595 va_list ap; 3596 3597 if(arch_multiple) 3598 print_architecture_banner(); 3599 va_start(ap, format); 3600 print("%s: ", progname); 3601 vprint(format, ap); 3602 print("\n"); 3603 va_end(ap); 3604 errors = 1; 3605} 3606 3607/* 3608 * Print the fatal error message, and exit non-zero. 3609 */ 3610__private_extern__ 3611void 3612fatal( 3613const char *format, 3614...) 3615{ 3616 va_list ap; 3617 3618 if(arch_multiple) 3619 print_architecture_banner(); 3620 va_start(ap, format); 3621 print("%s: ", progname); 3622 vprint(format, ap); 3623 print("\n"); 3624 va_end(ap); 3625 cleanup(); 3626} 3627 3628/* 3629 * Print the current object file name and warning message. 3630 */ 3631__private_extern__ 3632void 3633warning_with_cur_obj( 3634const char *format, 3635...) 3636{ 3637 va_list ap; 3638 3639 if(nowarnings == TRUE) 3640 return; 3641 if(arch_multiple) 3642 print_architecture_banner(); 3643 va_start(ap, format); 3644 print("%s: warning ", progname); 3645 print_obj_name(cur_obj); 3646 vprint(format, ap); 3647 print("\n"); 3648 va_end(ap); 3649} 3650 3651/* 3652 * Print the current object file name and error message, set the non-fatal 3653 * error indication. 3654 */ 3655__private_extern__ 3656void 3657error_with_cur_obj( 3658const char *format, 3659...) 3660{ 3661 va_list ap; 3662 3663 if(arch_multiple) 3664 print_architecture_banner(); 3665 va_start(ap, format); 3666 print("%s: ", progname); 3667 print_obj_name(cur_obj); 3668 vprint(format, ap); 3669 print("\n"); 3670 va_end(ap); 3671 errors = 1; 3672} 3673 3674#if !defined(SA_RLD) && !(defined(KLD) && defined(__STATIC__)) 3675/* 3676 * Print the warning message along with the system error message. 3677 */ 3678__private_extern__ 3679void 3680system_warning( 3681const char *format, 3682...) 3683{ 3684 va_list ap; 3685 int errnum; 3686 3687 if(arch_multiple) 3688 print_architecture_banner(); 3689 errnum = errno; 3690 va_start(ap, format); 3691 print("%s: warning ", progname); 3692 vprint(format, ap); 3693 print(" (%s, errno = %d)\n", strerror(errnum), errnum); 3694 va_end(ap); 3695} 3696 3697/* 3698 * Print the error message along with the system error message, set the 3699 * non-fatal error indication. 3700 */ 3701__private_extern__ 3702void 3703system_error( 3704const char *format, 3705...) 3706{ 3707 va_list ap; 3708 int errnum; 3709 3710 if(arch_multiple) 3711 print_architecture_banner(); 3712 errnum = errno; 3713 va_start(ap, format); 3714 print("%s: ", progname); 3715 vprint(format, ap); 3716 print(" (%s, errno = %d)\n", strerror(errnum), errnum); 3717 va_end(ap); 3718 errors = 1; 3719} 3720 3721/* 3722 * Print the fatal message along with the system error message, and exit 3723 * non-zero. 3724 */ 3725__private_extern__ 3726void 3727system_fatal( 3728const char *format, 3729...) 3730{ 3731 va_list ap; 3732 int errnum; 3733 3734 if(arch_multiple) 3735 print_architecture_banner(); 3736 errnum = errno; 3737 va_start(ap, format); 3738 print("%s: ", progname); 3739 vprint(format, ap); 3740 print(" (%s, errno = %d)\n", strerror(errnum), errnum); 3741 va_end(ap); 3742 cleanup(); 3743} 3744#endif /* !defined(SA_RLD) && !(defined(KLD) && defined(__STATIC__)) */ 3745 3746/* 3747 * Print the fatal error message along with the mach error string, and exit 3748 * non-zero. 3749 */ 3750__private_extern__ 3751void 3752mach_fatal( 3753kern_return_t r, 3754char *format, 3755...) 3756{ 3757 va_list ap; 3758 3759 if(arch_multiple) 3760 print_architecture_banner(); 3761 va_start(ap, format); 3762 print("%s: ", progname); 3763 vprint(format, ap); 3764 print(" (%s)\n", mach_error_string(r)); 3765 va_end(ap); 3766 cleanup(); 3767} 3768