1 /* -*- mode: C++; c-basic-offset: 4; tab-width: 4 -*-*
3 * Copyright (c) 2009-2010 Apple Inc. All rights reserved.
5 * @APPLE_LICENSE_HEADER_START@
7 * This file contains Original Code and/or Modifications of Original Code
8 * as defined in and that are subject to the Apple Public Source License
9 * Version 2.0 (the 'License'). You may not use this file except in
10 * compliance with the License. Please obtain a copy of the License at
11 * http://www.opensource.apple.com/apsl/ and read it before using this
14 * The Original Code and all software distributed under the License are
15 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
16 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
17 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
19 * Please see the License for the specific language governing rights and
20 * limitations under the License.
22 * @APPLE_LICENSE_HEADER_END@
27 #include <sys/types.h>
30 #include <sys/sysctl.h>
35 #include <mach/mach_time.h>
36 #include <mach/vm_statistics.h>
37 #include <mach/mach_init.h>
38 #include <mach/mach_host.h>
40 #include <mach-o/dyld.h>
41 #include <mach-o/fat.h>
51 #include <AvailabilityMacros.h>
55 #include "Bitcode.hpp"
56 #include "InputFiles.h"
57 #include "SymbolTable.h"
59 #include "parsers/lto_file.h"
61 #include "configure.h"
64 #define STRINGIFY(x) VAL(x)
71 // An ExportAtom has no content. It exists so that the linker can track which imported
72 // symbols came from which dynamic libraries.
74 class UndefinedProxyAtom
: public ld::Atom
77 UndefinedProxyAtom(const char* nm
)
78 : ld::Atom(_s_section
, ld::Atom::definitionProxy
,
79 ld::Atom::combineNever
, ld::Atom::scopeLinkageUnit
,
80 ld::Atom::typeUnclassified
,
81 ld::Atom::symbolTableIn
, false, false, false, ld::Atom::Alignment(0)),
83 // overrides of ld::Atom
84 virtual const ld::File
* file() const { return NULL
; }
85 virtual const char* name() const { return _name
; }
86 virtual uint64_t size() const { return 0; }
87 virtual uint64_t objectAddress() const { return 0; }
88 virtual void copyRawContent(uint8_t buffer
[]) const { }
89 virtual void setScope(Scope
) { }
93 virtual ~UndefinedProxyAtom() {}
97 static ld::Section _s_section
;
100 ld::Section
UndefinedProxyAtom::_s_section("__TEXT", "__import", ld::Section::typeImportProxies
, true);
105 class AliasAtom
: public ld::Atom
108 AliasAtom(const ld::Atom
& target
, const char* nm
) :
109 ld::Atom(target
.section(), target
.definition(), ld::Atom::combineNever
,
110 ld::Atom::scopeGlobal
, target
.contentType(),
111 target
.symbolTableInclusion(), target
.dontDeadStrip(),
112 target
.isThumb(), true, target
.alignment()),
115 _fixup(0, ld::Fixup::k1of1
, ld::Fixup::kindNoneFollowOn
, &target
) { }
117 // overrides of ld::Atom
118 virtual const ld::File
* file() const { return _aliasOf
.file(); }
119 virtual const char* translationUnitSource() const
120 { return _aliasOf
.translationUnitSource(); }
121 virtual const char* name() const { return _name
; }
122 virtual uint64_t size() const { return 0; }
123 virtual uint64_t objectAddress() const { return _aliasOf
.objectAddress(); }
124 virtual void copyRawContent(uint8_t buffer
[]) const { }
125 virtual const uint8_t* rawContentPointer() const { return NULL
; }
126 virtual unsigned long contentHash(const class ld::IndirectBindingTable
& ibt
) const
127 { return _aliasOf
.contentHash(ibt
); }
128 virtual bool canCoalesceWith(const ld::Atom
& rhs
, const class ld::IndirectBindingTable
& ibt
) const
129 { return _aliasOf
.canCoalesceWith(rhs
,ibt
); }
130 virtual ld::Fixup::iterator
fixupsBegin() const { return (ld::Fixup
*)&_fixup
; }
131 virtual ld::Fixup::iterator
fixupsEnd() const { return &((ld::Fixup
*)&_fixup
)[1]; }
132 virtual ld::Atom::UnwindInfo::iterator
beginUnwind() const { return NULL
; }
133 virtual ld::Atom::UnwindInfo::iterator
endUnwind() const { return NULL
; }
134 virtual ld::Atom::LineInfo::iterator
beginLineInfo() const { return NULL
; }
135 virtual ld::Atom::LineInfo::iterator
endLineInfo() const { return NULL
; }
137 void setFinalAliasOf() const {
138 (const_cast<AliasAtom
*>(this))->setAttributesFromAtom(_aliasOf
);
139 (const_cast<AliasAtom
*>(this))->setScope(ld::Atom::scopeGlobal
);
144 const ld::Atom
& _aliasOf
;
150 class SectionBoundaryAtom
: public ld::Atom
153 static SectionBoundaryAtom
* makeSectionBoundaryAtom(const char* name
, bool start
, const char* segSectName
);
154 static SectionBoundaryAtom
* makeOldSectionBoundaryAtom(const char* name
, bool start
);
156 // overrides of ld::Atom
157 virtual const ld::File
* file() const { return NULL
; }
158 virtual const char* name() const { return _name
; }
159 virtual uint64_t size() const { return 0; }
160 virtual void copyRawContent(uint8_t buffer
[]) const { }
161 virtual const uint8_t* rawContentPointer() const { return NULL
; }
162 virtual uint64_t objectAddress() const { return 0; }
166 SectionBoundaryAtom(const char* nm
, const ld::Section
& sect
,
167 ld::Atom::ContentType cont
) :
169 ld::Atom::definitionRegular
,
170 ld::Atom::combineNever
,
171 ld::Atom::scopeLinkageUnit
,
173 ld::Atom::symbolTableNotIn
,
174 false, false, true, ld::Atom::Alignment(0)),
180 SectionBoundaryAtom
* SectionBoundaryAtom::makeSectionBoundaryAtom(const char* name
, bool start
, const char* segSectName
)
183 const char* segSectDividor
= strrchr(segSectName
, '$');
184 if ( segSectDividor
== NULL
)
185 throwf("malformed section$ symbol name: %s", name
);
186 const char* sectionName
= segSectDividor
+ 1;
187 int segNameLen
= segSectDividor
- segSectName
;
188 if ( segNameLen
> 16 )
189 throwf("malformed section$ symbol name: %s", name
);
191 strlcpy(segName
, segSectName
, segNameLen
+1);
193 ld::Section::Type sectType
= ld::Section::typeUnclassified
;
194 if (!strcmp(segName
, "__TEXT") && !strcmp(sectionName
, "__thread_starts"))
195 sectType
= ld::Section::typeThreadStarts
;
197 const ld::Section
* section
= new ld::Section(strdup(segName
), sectionName
, sectType
);
198 return new SectionBoundaryAtom(name
, *section
, (start
? ld::Atom::typeSectionStart
: typeSectionEnd
));
201 SectionBoundaryAtom
* SectionBoundaryAtom::makeOldSectionBoundaryAtom(const char* name
, bool start
)
203 // e.g. __DATA__bss__begin
205 strlcpy(segName
, name
, 7);
208 int nameLen
= strlen(name
);
209 strlcpy(sectName
, &name
[6], (start
? nameLen
-12 : nameLen
-10));
210 warning("grandfathering in old symbol '%s' as alias for 'section$%s$%s$%s'", name
, start
? "start" : "end", segName
, sectName
);
211 const ld::Section
* section
= new ld::Section(strdup(segName
), strdup(sectName
), ld::Section::typeUnclassified
);
212 return new SectionBoundaryAtom(name
, *section
, (start
? ld::Atom::typeSectionStart
: typeSectionEnd
));
218 class SegmentBoundaryAtom
: public ld::Atom
221 static SegmentBoundaryAtom
* makeSegmentBoundaryAtom(const char* name
, bool start
, const char* segName
);
222 static SegmentBoundaryAtom
* makeOldSegmentBoundaryAtom(const char* name
, bool start
);
224 // overrides of ld::Atom
225 virtual const ld::File
* file() const { return NULL
; }
226 virtual const char* name() const { return _name
; }
227 virtual uint64_t size() const { return 0; }
228 virtual void copyRawContent(uint8_t buffer
[]) const { }
229 virtual const uint8_t* rawContentPointer() const { return NULL
; }
230 virtual uint64_t objectAddress() const { return 0; }
234 SegmentBoundaryAtom(const char* nm
, const ld::Section
& sect
,
235 ld::Atom::ContentType cont
) :
237 ld::Atom::definitionRegular
,
238 ld::Atom::combineNever
,
239 ld::Atom::scopeLinkageUnit
,
241 ld::Atom::symbolTableNotIn
,
242 false, false, true, ld::Atom::Alignment(0)),
248 SegmentBoundaryAtom
* SegmentBoundaryAtom::makeSegmentBoundaryAtom(const char* name
, bool start
, const char* segName
)
250 if ( *segName
== '\0' )
251 throwf("malformed segment$ symbol name: %s", name
);
252 if ( strlen(segName
) > 16 )
253 throwf("malformed segment$ symbol name: %s", name
);
256 const ld::Section
* section
= new ld::Section(segName
, "__start", ld::Section::typeFirstSection
, true);
257 return new SegmentBoundaryAtom(name
, *section
, ld::Atom::typeSectionStart
);
260 const ld::Section
* section
= new ld::Section(segName
, "__end", ld::Section::typeLastSection
, true);
261 return new SegmentBoundaryAtom(name
, *section
, ld::Atom::typeSectionEnd
);
265 SegmentBoundaryAtom
* SegmentBoundaryAtom::makeOldSegmentBoundaryAtom(const char* name
, bool start
)
267 // e.g. __DATA__begin
269 strlcpy(temp
, name
, 7);
270 char* segName
= strdup(temp
);
272 warning("grandfathering in old symbol '%s' as alias for 'segment$%s$%s'", name
, start
? "start" : "end", segName
);
275 const ld::Section
* section
= new ld::Section(segName
, "__start", ld::Section::typeFirstSection
, true);
276 return new SegmentBoundaryAtom(name
, *section
, ld::Atom::typeSectionStart
);
279 const ld::Section
* section
= new ld::Section(segName
, "__end", ld::Section::typeLastSection
, true);
280 return new SegmentBoundaryAtom(name
, *section
, ld::Atom::typeSectionEnd
);
284 void Resolver::initializeState()
286 _internal
.cpuSubType
= _options
.subArchitecture();
288 // In -r mode, look for -linker_option additions
289 if ( _options
.outputKind() == Options::kObjectFile
) {
290 ld::relocatable::File::LinkerOptionsList lo
= _options
.linkerOptions();
291 for (relocatable::File::LinkerOptionsList::const_iterator it
=lo
.begin(); it
!= lo
.end(); ++it
) {
292 doLinkerOption(*it
, "command line");
295 #ifdef LD64_VERSION_NUM
296 uint32_t packedNum
= Options::parseVersionNumber32(STRINGIFY(LD64_VERSION_NUM
));
297 uint64_t combined
= (uint64_t)TOOL_LD
<< 32 | packedNum
;
298 _internal
.toolsVersions
.insert(combined
);
302 void Resolver::buildAtomList()
304 // each input files contributes initial atoms
305 _atoms
.reserve(1024);
306 _inputFiles
.forEachInitialAtom(*this, _internal
);
308 _completedInitialObjectFiles
= true;
310 //_symbolTable.printStatistics();
314 void Resolver::doLinkerOption(const std::vector
<const char*>& linkerOption
, const char* fileName
)
316 if ( linkerOption
.size() == 1 ) {
317 const char* lo1
= linkerOption
.front();
318 if ( strncmp(lo1
, "-l", 2) == 0) {
319 if (_internal
.linkerOptionLibraries
.count(&lo1
[2]) == 0) {
320 _internal
.unprocessedLinkerOptionLibraries
.insert(&lo1
[2]);
324 warning("unknown linker option from object file ignored: '%s' in %s", lo1
, fileName
);
327 else if ( linkerOption
.size() == 2 ) {
328 const char* lo2a
= linkerOption
[0];
329 const char* lo2b
= linkerOption
[1];
330 if ( strcmp(lo2a
, "-framework") == 0) {
331 if (_internal
.linkerOptionFrameworks
.count(lo2b
) == 0) {
332 _internal
.unprocessedLinkerOptionFrameworks
.insert(lo2b
);
336 warning("unknown linker option from object file ignored: '%s' '%s' from %s", lo2a
, lo2b
, fileName
);
340 warning("unknown linker option from object file ignored, starting with: '%s' from %s", linkerOption
.front(), fileName
);
345 void Resolver::doFile(const ld::File
& file
)
347 const ld::relocatable::File
* objFile
= dynamic_cast<const ld::relocatable::File
*>(&file
);
348 const ld::dylib::File
* dylibFile
= dynamic_cast<const ld::dylib::File
*>(&file
);
350 if ( objFile
!= NULL
) {
351 // if file has linker options, process them
352 ld::relocatable::File::LinkerOptionsList
* lo
= objFile
->linkerOptions();
353 if ( lo
!= NULL
&& !_options
.ignoreAutoLink() ) {
354 for (relocatable::File::LinkerOptionsList::const_iterator it
=lo
->begin(); it
!= lo
->end(); ++it
) {
355 this->doLinkerOption(*it
, file
.path());
357 // <rdar://problem/23053404> process any additional linker-options introduced by this new archive member being loaded
358 if ( _completedInitialObjectFiles
) {
359 _inputFiles
.addLinkerOptionLibraries(_internal
, *this);
360 _inputFiles
.createIndirectDylibs();
363 // update which form of ObjC is being used
364 if ( objFile
->hasObjC() )
365 _internal
.hasObjC
= true;
367 // Resolve bitcode section in the object file
368 if ( _options
.bundleBitcode() ) {
369 if ( objFile
->getBitcode() == NULL
) {
370 // Handle the special case for compiler_rt objects. Add the file to the list to be process.
371 if ( objFile
->sourceKind() == ld::relocatable::File::kSourceCompilerArchive
) {
372 _internal
.filesFromCompilerRT
.push_back(objFile
);
373 } else if (objFile
->sourceKind() != ld::relocatable::File::kSourceLTO
) {
374 // No bitcode section, figure out if the object file comes from LTO/compiler static library
375 _options
.platforms().forEach(^(ld::Platform platform
, uint32_t version
, bool &stop
) {
376 switch ( platform
) {
377 case ld::kPlatform_macOS
:
378 case ld::kPlatform_bridgeOS
:
379 case ld::kPlatform_iOSMac
:
380 case ld::kPlatform_unknown
:
381 warning("all bitcode will be dropped because '%s' was built without bitcode. "
382 "You must rebuild it with bitcode enabled (Xcode setting ENABLE_BITCODE), obtain an updated library from the vendor, or disable bitcode for this target. ", file
.path());
383 _internal
.filesWithBitcode
.clear();
384 _internal
.dropAllBitcode
= true;
386 case ld::kPlatform_iOS
:
387 case ld::kPlatform_iOSSimulator
:
388 throwf("'%s' does not contain bitcode. "
389 "You must rebuild it with bitcode enabled (Xcode setting ENABLE_BITCODE), obtain an updated library from the vendor, or disable bitcode for this target.", file
.path());
391 case ld::kPlatform_watchOS
:
392 case ld::kPlatform_watchOSSimulator
:
393 case ld::kPlatform_tvOS
:
394 case ld::kPlatform_tvOSSimulator
:
395 throwf("'%s' does not contain bitcode. "
396 "You must rebuild it with bitcode enabled (Xcode setting ENABLE_BITCODE) or obtain an updated library from the vendor", file
.path());
402 // contains bitcode, check if it is just a marker
403 if ( objFile
->getBitcode()->isMarker() ) {
404 // if -bitcode_verify_bundle is used, check if all the object files participate in the linking have full bitcode embedded.
405 // error on any marker encountered.
406 if ( _options
.verifyBitcode() )
407 throwf("bitcode bundle could not be generated because '%s' was built without full bitcode. "
408 "All object files and libraries for bitcode must be generated from Xcode Archive or Install build",
410 // update the internal state that marker is encountered.
411 _internal
.embedMarkerOnly
= true;
412 _internal
.filesWithBitcode
.clear();
413 _internal
.dropAllBitcode
= true;
414 } else if ( !_internal
.dropAllBitcode
)
415 _internal
.filesWithBitcode
.push_back(objFile
);
419 // verify all files use same version of Swift language
420 if ( file
.swiftVersion() != 0 ) {
421 _internal
.someObjectFileHasSwift
= true;
422 if ( _internal
.swiftVersion
== 0 ) {
423 _internal
.swiftVersion
= file
.swiftVersion();
425 else if ( file
.swiftVersion() != _internal
.swiftVersion
) {
426 char fileVersion
[64];
427 char otherVersion
[64];
428 Options::userReadableSwiftVersion(file
.swiftVersion(), fileVersion
);
429 Options::userReadableSwiftVersion(_internal
.swiftVersion
, otherVersion
);
430 if ( file
.swiftVersion() > _internal
.swiftVersion
) {
431 if ( _options
.warnOnSwiftABIVersionMismatches() ) {
432 warning("%s compiled with newer version of Swift language (%s) than previous files (%s)",
433 file
.path(), fileVersion
, otherVersion
);
435 throwf("%s compiled with newer version of Swift language (%s) than previous files (%s)",
436 file
.path(), fileVersion
, otherVersion
);
440 if ( _options
.warnOnSwiftABIVersionMismatches() ) {
441 warning("%s compiled with older version of Swift language (%s) than previous files (%s)",
442 file
.path(), fileVersion
, otherVersion
);
444 throwf("%s compiled with older version of Swift language (%s) than previous files (%s)",
445 file
.path(), fileVersion
, otherVersion
);
451 // in -r mode, if any .o files have dwarf then add UUID to output .o file
452 if ( objFile
->debugInfo() == ld::relocatable::File::kDebugInfoDwarf
)
453 _internal
.someObjectFileHasDwarf
= true;
455 // remember if any .o file did not have MH_SUBSECTIONS_VIA_SYMBOLS bit set
456 if ( ! objFile
->canScatterAtoms() )
457 _internal
.allObjectFilesScatterable
= false;
459 // remember if building for profiling (so we don't warn about initializers)
460 if ( objFile
->hasllvmProfiling() )
461 _havellvmProfiling
= true;
464 // update minOSVersion off all .o files
465 uint32_t objMinOS
= objFile
->minOSVersion();
467 _internal
.objectFileFoundWithNoVersion
= true;
468 if ( (_options
.outputKind() == Options::kObjectFile
) && (objMinOS
> _internal
.minOSVersion
) )
469 _internal
.minOSVersion
= objMinOS
;
472 auto objPlatforms
= objFile
->platforms();
473 if ( (!objPlatforms
.empty()) && (_options
.outputKind() == Options::kObjectFile
) && (_internal
.derivedPlatforms
.empty()) )
474 _internal
.derivedPlatforms
= objPlatforms
;
475 // update set of known tools used
476 for (const std::pair
<uint32_t,uint32_t>& entry
: objFile
->toolVersions()) {
477 uint64_t combined
= (uint64_t)entry
.first
<< 32 | entry
.second
;
478 _internal
.toolsVersions
.insert(combined
);
481 // update cpu-sub-type
482 cpu_subtype_t nextObjectSubType
= file
.cpuSubType();
483 switch ( _options
.architecture() ) {
485 if ( _options
.subArchitecture() != nextObjectSubType
) {
486 if ( (_options
.subArchitecture() == CPU_SUBTYPE_ARM_ALL
) && _options
.forceCpuSubtypeAll() ) {
487 // hack to support gcc multillib build that tries to make sub-type-all slice
489 else if ( nextObjectSubType
== CPU_SUBTYPE_ARM_ALL
) {
490 warning("CPU_SUBTYPE_ARM_ALL subtype is deprecated: %s", file
.path());
492 else if ( _options
.allowSubArchitectureMismatches() ) {
493 //warning("object file %s was built for different arm sub-type (%d) than link command line (%d)",
494 // file.path(), nextObjectSubType, _options.subArchitecture());
497 throwf("object file %s was built for different arm sub-type (%d) than link command line (%d)",
498 file
.path(), nextObjectSubType
, _options
.subArchitecture());
504 if ( _options
.subArchitecture() != nextObjectSubType
) {
505 if ( _options
.allowSubArchitectureMismatches() ) {
506 warning("object file %s was built for different arm64 sub-type (%d) than link command line (%d)",
507 file
.path(), nextObjectSubType
, _options
.subArchitecture());
510 throwf("object file %s was built for different arm64 sub-type (%d) than link command line (%d)",
511 file
.path(), nextObjectSubType
, _options
.subArchitecture());
517 _internal
.cpuSubType
= CPU_SUBTYPE_I386_ALL
;
520 case CPU_TYPE_X86_64
:
521 if ( _options
.subArchitecture() != nextObjectSubType
) {
522 if ( _options
.allowSubArchitectureMismatches() ) {
523 warning("object file %s was built for different x86_64 sub-type (%d) than link command line (%d)",
524 file
.path(), nextObjectSubType
, _options
.subArchitecture());
527 throwf("object file %s was built for different x86_64 sub-type (%d) than link command line (%d)",
528 file
.path(), nextObjectSubType
, _options
.subArchitecture());
534 if ( dylibFile
!= NULL
) {
535 // Check dylib for bitcode, if the library install path is relative path or @rpath, it has to contain bitcode
536 if ( _options
.bundleBitcode() ) {
537 bool isSystemFramework
= ( dylibFile
->installPath() != NULL
) && ( dylibFile
->installPath()[0] == '/' );
538 if ( dylibFile
->getBitcode() == NULL
&& !isSystemFramework
) {
539 // Check if the dylib is from toolchain by checking the path
540 char tcLibPath
[PATH_MAX
];
541 char ldPath
[PATH_MAX
];
542 char tempPath
[PATH_MAX
];
543 uint32_t bufSize
= PATH_MAX
;
544 // toolchain library path should pointed to *.xctoolchain/usr/lib
545 if ( _NSGetExecutablePath(ldPath
, &bufSize
) != -1 ) {
546 if ( realpath(ldPath
, tempPath
) != NULL
) {
547 char* lastSlash
= strrchr(tempPath
, '/');
548 if ( lastSlash
!= NULL
)
549 strcpy(lastSlash
, "/../lib");
552 // Compare toolchain library path to the dylib path
553 if ( realpath(tempPath
, tcLibPath
) == NULL
||
554 realpath(dylibFile
->path(), tempPath
) == NULL
||
555 strncmp(tcLibPath
, tempPath
, strlen(tcLibPath
)) != 0 ) {
556 _options
.platforms().forEach(^(ld::Platform platform
, uint32_t version
, bool &stop
) {
557 switch ( platform
) {
558 case ld::kPlatform_macOS
:
559 case ld::kPlatform_bridgeOS
:
560 case ld::kPlatform_iOSMac
:
561 case ld::kPlatform_unknown
:
562 warning("all bitcode will be dropped because '%s' was built without bitcode. "
563 "You must rebuild it with bitcode enabled (Xcode setting ENABLE_BITCODE), obtain an updated library from the vendor, or disable bitcode for this target.", file
.path());
564 _internal
.filesWithBitcode
.clear();
565 _internal
.dropAllBitcode
= true;
567 case ld::kPlatform_iOS
:
568 case ld::kPlatform_iOSSimulator
:
569 throwf("'%s' does not contain bitcode. "
570 "You must rebuild it with bitcode enabled (Xcode setting ENABLE_BITCODE), obtain an updated library from the vendor, or disable bitcode for this target.", file
.path());
572 case ld::kPlatform_watchOS
:
573 case ld::kPlatform_watchOSSimulator
:
574 case ld::kPlatform_tvOS
:
575 case ld::kPlatform_tvOSSimulator
:
576 throwf("'%s' does not contain bitcode. "
577 "You must rebuild it with bitcode enabled (Xcode setting ENABLE_BITCODE) or obtain an updated library from the vendor", file
.path());
583 // Error on bitcode marker in non-system frameworks if -bitcode_verify is used
584 if ( _options
.verifyBitcode() && !isSystemFramework
&&
585 dylibFile
->getBitcode() != NULL
&& dylibFile
->getBitcode()->isMarker() )
586 throwf("bitcode bundle could not be generated because '%s' was built without full bitcode. "
587 "All frameworks and dylibs for bitcode must be generated from Xcode Archive or Install build",
591 // Don't allow swift frameworks to link other swift frameworks.
592 if ( !_internal
.firstSwiftDylibFile
&& _options
.outputKind() == Options::kDynamicLibrary
593 && file
.swiftVersion() != 0 && getenv("LD_DISALLOW_SWIFT_LINKING_SWIFT")) {
594 // Check that we aren't a whitelisted path.
595 bool inWhiteList
= false;
596 const char *whitelistedPaths
[] = { "/System/Library/PrivateFrameworks/Swift" };
597 for (auto whitelistedPath
: whitelistedPaths
) {
598 if (!strncmp(whitelistedPath
, dylibFile
->installPath(), strlen(whitelistedPath
))) {
604 _internal
.firstSwiftDylibFile
= dylibFile
;
608 // <rdar://problem/25680358> verify dylibs use same version of Swift language
609 if ( file
.swiftVersion() != 0 ) {
610 if ( _internal
.swiftVersion
== 0 ) {
611 _internal
.swiftVersion
= file
.swiftVersion();
613 else if ( file
.swiftVersion() != _internal
.swiftVersion
) {
614 char fileVersion
[64];
615 char otherVersion
[64];
616 Options::userReadableSwiftVersion(file
.swiftVersion(), fileVersion
);
617 Options::userReadableSwiftVersion(_internal
.swiftVersion
, otherVersion
);
618 if ( file
.swiftVersion() > _internal
.swiftVersion
) {
619 if ( _options
.warnOnSwiftABIVersionMismatches() ) {
620 warning("%s compiled with newer version of Swift language (%s) than previous files (%s)",
621 file
.path(), fileVersion
, otherVersion
);
623 throwf("%s compiled with newer version of Swift language (%s) than previous files (%s)",
624 file
.path(), fileVersion
, otherVersion
);
628 if ( _options
.warnOnSwiftABIVersionMismatches() ) {
629 warning("%s compiled with older version of Swift language (%s) than previous files (%s)",
630 file
.path(), fileVersion
, otherVersion
);
632 throwf("%s compiled with older version of Swift language (%s) than previous files (%s)",
633 file
.path(), fileVersion
, otherVersion
);
639 if ( _options
.checkDylibsAreAppExtensionSafe() && !dylibFile
->appExtensionSafe() ) {
640 warning("linking against a dylib which is not safe for use in application extensions: %s", file
.path());
642 const char* depInstallName
= dylibFile
->installPath();
643 // <rdar://problem/17229513> embedded frameworks are only supported on iOS 8 and later
644 if ( (depInstallName
!= NULL
) && (depInstallName
[0] != '/') ) {
645 if ( _options
.platforms().contains(ld::kPlatform_iOS
) && !_options
.platforms().minOS(iOS_8_0
) ) {
646 // <rdar://problem/17598404> only warn about linking against embedded dylib if it is built for iOS 8 or later
647 if ( dylibFile
->platforms().minOS(ld::iOS_8_0
) )
648 throwf("embedded dylibs/frameworks are only supported on iOS 8.0 and later (%s)", depInstallName
);
651 if ( _options
.sharedRegionEligible() ) {
652 assert(depInstallName
!= NULL
);
653 if ( depInstallName
[0] == '@' ) {
654 warning("invalid -install_name (%s) in dependent dylib (%s). Dylibs/frameworks which might go in dyld shared cache "
655 "cannot link with dylib that uses @rpath, @loader_path, etc.", depInstallName
, dylibFile
->path());
656 } else if ( (strncmp(depInstallName
, "/usr/lib/", 9) != 0) && (strncmp(depInstallName
, "/System/Library/", 16) != 0) ) {
657 warning("invalid -install_name (%s) in dependent dylib (%s). Dylibs/frameworks which might go in dyld shared cache "
658 "cannot link with dylibs that won't be in the shared cache", depInstallName
, dylibFile
->path());
664 void Resolver::doAtom(const ld::Atom
& atom
)
666 //fprintf(stderr, "Resolver::doAtom(%p), name=%s, sect=%s, scope=%d\n", &atom, atom.name(), atom.section().sectionName(), atom.scope());
667 if ( _ltoCodeGenFinished
&& (atom
.contentType() == ld::Atom::typeLTOtemporary
) && (atom
.scope() != ld::Atom::scopeTranslationUnit
) )
668 warning("'%s' is implemented in bitcode, but it was loaded too late", atom
.name());
670 // add to list of known atoms
671 _atoms
.push_back(&atom
);
674 if ( _options
.hasExportRestrictList() || _options
.hasReExportList() ) {
675 const char* name
= atom
.name();
676 switch ( atom
.scope() ) {
677 case ld::Atom::scopeTranslationUnit
:
679 case ld::Atom::scopeLinkageUnit
:
680 if ( _options
.hasExportMaskList() && _options
.shouldExport(name
) ) {
681 // <rdar://problem/5062685> ld does not report error when -r is used and exported symbols are not defined.
682 if ( _options
.outputKind() == Options::kObjectFile
)
683 throwf("cannot export hidden symbol %s", name
);
684 // .objc_class_name_* symbols are special
685 if ( atom
.section().type() != ld::Section::typeObjC1Classes
) {
686 if ( atom
.definition() == ld::Atom::definitionProxy
) {
687 // .exp file says to export a symbol, but that symbol is in some dylib being linked
688 if ( _options
.canReExportSymbols() ) {
689 // marking proxy atom as global triggers the re-export
690 (const_cast<ld::Atom
*>(&atom
))->setScope(ld::Atom::scopeGlobal
);
692 else if ( _options
.outputKind() == Options::kDynamicLibrary
) {
693 if ( atom
.file() != NULL
)
694 warning("target OS does not support re-exporting symbol %s from %s\n", _options
.demangleSymbol(name
), atom
.safeFilePath());
696 warning("target OS does not support re-exporting symbol %s\n", _options
.demangleSymbol(name
));
700 if ( atom
.file() != NULL
)
701 warning("cannot export hidden symbol %s from %s", _options
.demangleSymbol(name
), atom
.safeFilePath());
703 warning("cannot export hidden symbol %s", _options
.demangleSymbol(name
));
707 else if ( _options
.shouldReExport(name
) && _options
.canReExportSymbols() ) {
708 if ( atom
.definition() == ld::Atom::definitionProxy
) {
709 // marking proxy atom as global triggers the re-export
710 (const_cast<ld::Atom
*>(&atom
))->setScope(ld::Atom::scopeGlobal
);
713 throwf("requested re-export symbol %s is not from a dylib, but from %s\n", _options
.demangleSymbol(name
), atom
.safeFilePath());
717 case ld::Atom::scopeGlobal
:
718 // check for globals that are downgraded to hidden
719 if ( ! _options
.shouldExport(name
) ) {
720 (const_cast<ld::Atom
*>(&atom
))->setScope(ld::Atom::scopeLinkageUnit
);
721 //fprintf(stderr, "demote %s to hidden\n", name);
723 if ( _options
.canReExportSymbols() && _options
.shouldReExport(name
) ) {
724 throwf("requested re-export symbol %s is not from a dylib, but from %s\n", _options
.demangleSymbol(name
), atom
.safeFilePath());
730 // work around for kernel that uses 'l' labels in assembly code
731 if ( (atom
.symbolTableInclusion() == ld::Atom::symbolTableNotInFinalLinkedImages
)
732 && (atom
.name()[0] == 'l') && (_options
.outputKind() == Options::kStaticExecutable
)
733 && (strncmp(atom
.name(), "ltmp", 4) != 0) )
734 (const_cast<ld::Atom
*>(&atom
))->setSymbolTableInclusion(ld::Atom::symbolTableIn
);
737 // tell symbol table about non-static atoms
738 if ( atom
.scope() != ld::Atom::scopeTranslationUnit
) {
739 _symbolTable
.add(atom
, _options
.deadCodeStrip() && (_completedInitialObjectFiles
|| _options
.allowDeadDuplicates()));
741 // add symbol aliases defined on the command line
742 if ( _options
.haveCmdLineAliases() ) {
743 const std::vector
<Options::AliasPair
>& aliases
= _options
.cmdLineAliases();
744 for (std::vector
<Options::AliasPair
>::const_iterator it
=aliases
.begin(); it
!= aliases
.end(); ++it
) {
745 if ( strcmp(it
->realName
, atom
.name()) == 0 ) {
746 if ( strcmp(it
->realName
, it
->alias
) == 0 ) {
747 warning("ignoring alias of itself '%s'", it
->realName
);
750 const AliasAtom
* alias
= new AliasAtom(atom
, it
->alias
);
751 _aliasesFromCmdLine
.push_back(alias
);
752 this->doAtom(*alias
);
759 // convert references by-name or by-content to by-slot
760 this->convertReferencesToIndirect(atom
);
762 // remember if any atoms are proxies that require LTO
763 if ( atom
.contentType() == ld::Atom::typeLTOtemporary
)
764 _haveLLVMObjs
= true;
766 // remember if any atoms are aliases
767 if ( atom
.section().type() == ld::Section::typeTempAlias
)
770 // error or warn about initializers
771 if ( (atom
.section().type() == ld::Section::typeInitializerPointers
) && !_havellvmProfiling
) {
772 switch ( _options
.initializersTreatment() ) {
773 case Options::kError
:
774 throwf("static initializer found in '%s'",atom
.safeFilePath());
775 case Options::kWarning
:
776 warning("static initializer found in '%s'. Use -no_inits to make this an error. Use -no_warn_inits to suppress warning",atom
.safeFilePath());
783 if ( _options
.deadCodeStrip() ) {
784 // add to set of dead-strip-roots, all symbols that the compiler marks as don't strip
785 if ( atom
.dontDeadStrip() )
786 _deadStripRoots
.insert(&atom
);
787 else if ( atom
.dontDeadStripIfReferencesLive() )
788 _dontDeadStripIfReferencesLive
.push_back(&atom
);
790 if ( atom
.scope() == ld::Atom::scopeGlobal
) {
791 // <rdar://problem/5524973> -exported_symbols_list that has wildcards and -dead_strip
792 // in dylibs, every global atom in initial .o files is a root
793 if ( _options
.hasWildCardExportRestrictList() || _options
.allGlobalsAreDeadStripRoots() ) {
794 if ( _options
.shouldExport(atom
.name()) )
795 _deadStripRoots
.insert(&atom
);
801 bool Resolver::isDtraceProbe(ld::Fixup::Kind kind
)
804 case ld::Fixup::kindStoreX86DtraceCallSiteNop
:
805 case ld::Fixup::kindStoreX86DtraceIsEnableSiteClear
:
806 case ld::Fixup::kindStoreARMDtraceCallSiteNop
:
807 case ld::Fixup::kindStoreARMDtraceIsEnableSiteClear
:
808 case ld::Fixup::kindStoreARM64DtraceCallSiteNop
:
809 case ld::Fixup::kindStoreARM64DtraceIsEnableSiteClear
:
810 case ld::Fixup::kindStoreThumbDtraceCallSiteNop
:
811 case ld::Fixup::kindStoreThumbDtraceIsEnableSiteClear
:
812 case ld::Fixup::kindDtraceExtra
:
820 void Resolver::convertReferencesToIndirect(const ld::Atom
& atom
)
822 // convert references by-name or by-content to by-slot
823 SymbolTable::IndirectBindingSlot slot
;
824 const ld::Atom
* dummy
;
825 ld::Fixup::iterator end
= atom
.fixupsEnd();
826 for (ld::Fixup::iterator fit
=atom
.fixupsBegin(); fit
!= end
; ++fit
) {
827 if ( fit
->kind
== ld::Fixup::kindLinkerOptimizationHint
)
828 _internal
.someObjectHasOptimizationHints
= true;
829 switch ( fit
->binding
) {
830 case ld::Fixup::bindingByNameUnbound
:
831 if ( isDtraceProbe(fit
->kind
) && (_options
.outputKind() != Options::kObjectFile
) ) {
832 // in final linked images, remove reference
833 fit
->binding
= ld::Fixup::bindingNone
;
836 slot
= _symbolTable
.findSlotForName(fit
->u
.name
);
837 fit
->binding
= ld::Fixup::bindingsIndirectlyBound
;
838 fit
->u
.bindingIndex
= slot
;
841 case ld::Fixup::bindingByContentBound
:
842 switch ( fit
->u
.target
->combine() ) {
843 case ld::Atom::combineNever
:
844 case ld::Atom::combineByName
:
845 assert(0 && "wrong combine type for bind by content");
847 case ld::Atom::combineByNameAndContent
:
848 slot
= _symbolTable
.findSlotForContent(fit
->u
.target
, &dummy
);
849 fit
->binding
= ld::Fixup::bindingsIndirectlyBound
;
850 fit
->u
.bindingIndex
= slot
;
852 case ld::Atom::combineByNameAndReferences
:
853 slot
= _symbolTable
.findSlotForReferences(fit
->u
.target
, &dummy
);
854 fit
->binding
= ld::Fixup::bindingsIndirectlyBound
;
855 fit
->u
.bindingIndex
= slot
;
859 case ld::Fixup::bindingNone
:
860 case ld::Fixup::bindingDirectlyBound
:
861 case ld::Fixup::bindingsIndirectlyBound
:
868 void Resolver::addInitialUndefines()
870 // add initial undefines from -u option
871 for (Options::UndefinesIterator it
=_options
.initialUndefinesBegin(); it
!= _options
.initialUndefinesEnd(); ++it
) {
872 _symbolTable
.findSlotForName(*it
);
876 void Resolver::resolveUndefines()
878 // keep looping until no more undefines were added in last loop
879 unsigned int undefineGenCount
= 0xFFFFFFFF;
880 while ( undefineGenCount
!= _symbolTable
.updateCount() ) {
881 undefineGenCount
= _symbolTable
.updateCount();
882 std::vector
<const char*> undefineNames
;
883 _symbolTable
.undefines(undefineNames
);
884 for(std::vector
<const char*>::iterator it
= undefineNames
.begin(); it
!= undefineNames
.end(); ++it
) {
885 const char* undef
= *it
;
886 // load for previous undefine may also have loaded this undefine, so check again
887 if ( ! _symbolTable
.hasName(undef
) ) {
888 _inputFiles
.searchLibraries(undef
, true, true, false, *this);
889 if ( !_symbolTable
.hasName(undef
) && (_options
.outputKind() != Options::kObjectFile
) ) {
890 if ( strncmp(undef
, "section$", 8) == 0 ) {
891 if ( strncmp(undef
, "section$start$", 14) == 0 ) {
892 this->doAtom(*SectionBoundaryAtom::makeSectionBoundaryAtom(undef
, true, &undef
[14]));
894 else if ( strncmp(undef
, "section$end$", 12) == 0 ) {
895 this->doAtom(*SectionBoundaryAtom::makeSectionBoundaryAtom(undef
, false, &undef
[12]));
898 else if ( strncmp(undef
, "segment$", 8) == 0 ) {
899 if ( strncmp(undef
, "segment$start$", 14) == 0 ) {
900 this->doAtom(*SegmentBoundaryAtom::makeSegmentBoundaryAtom(undef
, true, &undef
[14]));
902 else if ( strncmp(undef
, "segment$end$", 12) == 0 ) {
903 this->doAtom(*SegmentBoundaryAtom::makeSegmentBoundaryAtom(undef
, false, &undef
[12]));
906 else if ( _options
.outputKind() == Options::kPreload
) {
907 // for iBoot grandfather in old style section labels
908 int undefLen
= strlen(undef
);
909 if ( strcmp(&undef
[undefLen
-7], "__begin") == 0 ) {
911 this->doAtom(*SectionBoundaryAtom::makeOldSectionBoundaryAtom(undef
, true));
913 this->doAtom(*SegmentBoundaryAtom::makeOldSegmentBoundaryAtom(undef
, true));
915 else if ( strcmp(&undef
[undefLen
-5], "__end") == 0 ) {
917 this->doAtom(*SectionBoundaryAtom::makeOldSectionBoundaryAtom(undef
, false));
919 this->doAtom(*SegmentBoundaryAtom::makeOldSegmentBoundaryAtom(undef
, false));
925 // <rdar://problem/5894163> need to search archives for overrides of common symbols
926 if ( _symbolTable
.hasExternalTentativeDefinitions() ) {
927 bool searchDylibs
= (_options
.commonsMode() == Options::kCommonsOverriddenByDylibs
);
928 std::vector
<const char*> tents
;
929 _symbolTable
.tentativeDefs(tents
);
930 for(std::vector
<const char*>::iterator it
= tents
.begin(); it
!= tents
.end(); ++it
) {
931 // load for previous tentative may also have loaded this tentative, so check again
932 const ld::Atom
* curAtom
= _symbolTable
.atomForSlot(_symbolTable
.findSlotForName(*it
));
933 assert(curAtom
!= NULL
);
934 if ( curAtom
->definition() == ld::Atom::definitionTentative
) {
935 _inputFiles
.searchLibraries(*it
, searchDylibs
, true, true, *this);
941 // Use linker options to resolve any remaining undefined symbols
942 if ( !_internal
.linkerOptionLibraries
.empty() || !_internal
.linkerOptionFrameworks
.empty() ) {
943 std::vector
<const char*> undefineNames
;
944 _symbolTable
.undefines(undefineNames
);
945 if ( undefineNames
.size() != 0 ) {
946 for (std::vector
<const char*>::iterator it
= undefineNames
.begin(); it
!= undefineNames
.end(); ++it
) {
947 const char* undef
= *it
;
948 if ( ! _symbolTable
.hasName(undef
) ) {
949 _inputFiles
.searchLibraries(undef
, true, true, false, *this);
955 // create proxies as needed for undefined symbols
956 if ( (_options
.undefinedTreatment() != Options::kUndefinedError
) || (_options
.outputKind() == Options::kObjectFile
) ) {
957 std::vector
<const char*> undefineNames
;
958 _symbolTable
.undefines(undefineNames
);
959 for(std::vector
<const char*>::iterator it
= undefineNames
.begin(); it
!= undefineNames
.end(); ++it
) {
960 const char* undefName
= *it
;
961 // <rdar://problem/14547001> "ld -r -exported_symbol _foo" has wrong error message if _foo is undefined
962 bool makeProxy
= true;
963 if ( (_options
.outputKind() == Options::kObjectFile
) && _options
.hasExportMaskList() && _options
.shouldExport(undefName
) )
967 this->doAtom(*new UndefinedProxyAtom(undefName
));
972 if ( _options
.someAllowedUndefines() ) {
973 std::vector
<const char*> undefineNames
;
974 _symbolTable
.undefines(undefineNames
);
975 for(std::vector
<const char*>::iterator it
= undefineNames
.begin(); it
!= undefineNames
.end(); ++it
) {
976 if ( _options
.allowedUndefined(*it
) ) {
978 this->doAtom(*new UndefinedProxyAtom(*it
));
983 // After resolving all the undefs within the linkageUnit, record all the remaining undefs and all the proxies.
984 if (_options
.bundleBitcode() && _options
.hideSymbols())
985 _symbolTable
.mustPreserveForBitcode(_internal
.allUndefProxies
);
990 void Resolver::markLive(const ld::Atom
& atom
, WhyLiveBackChain
* previous
)
992 //fprintf(stderr, "markLive(%p) %s\n", &atom, atom.name());
993 // if -why_live cares about this symbol, then dump chain
994 if ( (previous
->referer
!= NULL
) && _options
.printWhyLive(atom
.name()) ) {
995 fprintf(stderr
, "%s from %s\n", atom
.name(), atom
.safeFilePath());
997 for(WhyLiveBackChain
* p
= previous
; p
!= NULL
; p
= p
->previous
, ++depth
) {
998 for(int i
=depth
; i
> 0; --i
)
999 fprintf(stderr
, " ");
1000 fprintf(stderr
, "%s from %s\n", p
->referer
->name(), p
->referer
->safeFilePath());
1004 // if already marked live, then done (stop recursion)
1008 // mark this atom is live
1009 (const_cast<ld::Atom
*>(&atom
))->setLive();
1011 // mark all atoms it references as live
1012 WhyLiveBackChain thisChain
;
1013 thisChain
.previous
= previous
;
1014 thisChain
.referer
= &atom
;
1015 for (ld::Fixup::iterator fit
= atom
.fixupsBegin(), end
=atom
.fixupsEnd(); fit
!= end
; ++fit
) {
1016 const ld::Atom
* target
;
1017 switch ( fit
->kind
) {
1018 case ld::Fixup::kindNone
:
1019 case ld::Fixup::kindNoneFollowOn
:
1020 case ld::Fixup::kindNoneGroupSubordinate
:
1021 case ld::Fixup::kindNoneGroupSubordinateFDE
:
1022 case ld::Fixup::kindNoneGroupSubordinateLSDA
:
1023 case ld::Fixup::kindNoneGroupSubordinatePersonality
:
1024 case ld::Fixup::kindSetTargetAddress
:
1025 case ld::Fixup::kindSubtractTargetAddress
:
1026 case ld::Fixup::kindStoreTargetAddressLittleEndian32
:
1027 case ld::Fixup::kindStoreTargetAddressLittleEndian64
:
1028 #if SUPPORT_ARCH_arm64e
1029 case ld::Fixup::kindStoreTargetAddressLittleEndianAuth64
:
1031 case ld::Fixup::kindStoreTargetAddressBigEndian32
:
1032 case ld::Fixup::kindStoreTargetAddressBigEndian64
:
1033 case ld::Fixup::kindStoreTargetAddressX86PCRel32
:
1034 case ld::Fixup::kindStoreTargetAddressX86BranchPCRel32
:
1035 case ld::Fixup::kindStoreTargetAddressX86PCRel32GOTLoad
:
1036 case ld::Fixup::kindStoreTargetAddressX86PCRel32GOTLoadNowLEA
:
1037 case ld::Fixup::kindStoreTargetAddressX86PCRel32TLVLoad
:
1038 case ld::Fixup::kindStoreTargetAddressX86PCRel32TLVLoadNowLEA
:
1039 case ld::Fixup::kindStoreTargetAddressX86Abs32TLVLoad
:
1040 case ld::Fixup::kindStoreTargetAddressX86Abs32TLVLoadNowLEA
:
1041 case ld::Fixup::kindStoreTargetAddressARMBranch24
:
1042 case ld::Fixup::kindStoreTargetAddressThumbBranch22
:
1043 #if SUPPORT_ARCH_arm64
1044 case ld::Fixup::kindStoreTargetAddressARM64Branch26
:
1045 case ld::Fixup::kindStoreTargetAddressARM64Page21
:
1046 case ld::Fixup::kindStoreTargetAddressARM64GOTLoadPage21
:
1047 case ld::Fixup::kindStoreTargetAddressARM64GOTLeaPage21
:
1048 case ld::Fixup::kindStoreTargetAddressARM64TLVPLoadPage21
:
1049 case ld::Fixup::kindStoreTargetAddressARM64TLVPLoadNowLeaPage21
:
1051 if ( fit
->binding
== ld::Fixup::bindingByContentBound
) {
1052 // normally this was done in convertReferencesToIndirect()
1053 // but a archive loaded .o file may have a forward reference
1054 SymbolTable::IndirectBindingSlot slot
;
1055 const ld::Atom
* dummy
;
1056 switch ( fit
->u
.target
->combine() ) {
1057 case ld::Atom::combineNever
:
1058 case ld::Atom::combineByName
:
1059 assert(0 && "wrong combine type for bind by content");
1061 case ld::Atom::combineByNameAndContent
:
1062 slot
= _symbolTable
.findSlotForContent(fit
->u
.target
, &dummy
);
1063 fit
->binding
= ld::Fixup::bindingsIndirectlyBound
;
1064 fit
->u
.bindingIndex
= slot
;
1066 case ld::Atom::combineByNameAndReferences
:
1067 slot
= _symbolTable
.findSlotForReferences(fit
->u
.target
, &dummy
);
1068 fit
->binding
= ld::Fixup::bindingsIndirectlyBound
;
1069 fit
->u
.bindingIndex
= slot
;
1073 switch ( fit
->binding
) {
1074 case ld::Fixup::bindingDirectlyBound
:
1075 markLive(*(fit
->u
.target
), &thisChain
);
1077 case ld::Fixup::bindingByNameUnbound
:
1078 // doAtom() did not convert to indirect in dead-strip mode, so that now
1079 fit
->u
.bindingIndex
= _symbolTable
.findSlotForName(fit
->u
.name
);
1080 fit
->binding
= ld::Fixup::bindingsIndirectlyBound
;
1081 // fall into next case
1082 case ld::Fixup::bindingsIndirectlyBound
:
1083 target
= _internal
.indirectBindingTable
[fit
->u
.bindingIndex
];
1084 if ( target
== NULL
) {
1085 const char* targetName
= _symbolTable
.indirectName(fit
->u
.bindingIndex
);
1086 _inputFiles
.searchLibraries(targetName
, true, true, false, *this);
1087 target
= _internal
.indirectBindingTable
[fit
->u
.bindingIndex
];
1089 if ( target
!= NULL
) {
1090 if ( target
->definition() == ld::Atom::definitionTentative
) {
1091 // <rdar://problem/5894163> need to search archives for overrides of common symbols
1092 bool searchDylibs
= (_options
.commonsMode() == Options::kCommonsOverriddenByDylibs
);
1093 _inputFiles
.searchLibraries(target
->name(), searchDylibs
, true, true, *this);
1094 // recompute target since it may have been overridden by searchLibraries()
1095 target
= _internal
.indirectBindingTable
[fit
->u
.bindingIndex
];
1097 this->markLive(*target
, &thisChain
);
1100 _atomsWithUnresolvedReferences
.push_back(&atom
);
1104 assert(0 && "bad binding during dead stripping");
1116 bool operator()(const ld::Atom
* atom
) const {
1117 if (atom
->live() || atom
->dontDeadStrip() )
1119 // don't kill combinable atoms in first pass
1120 switch ( atom
->combine() ) {
1121 case ld::Atom::combineByNameAndContent
:
1122 case ld::Atom::combineByNameAndReferences
:
1130 void Resolver::deadStripOptimize(bool force
)
1132 // only do this optimization with -dead_strip
1133 if ( ! _options
.deadCodeStrip() )
1136 // add entry point (main) to live roots
1137 const ld::Atom
* entry
= this->entryPoint(true);
1138 if ( entry
!= NULL
)
1139 _deadStripRoots
.insert(entry
);
1141 // add -exported_symbols_list, -init, and -u entries to live roots
1142 for (Options::UndefinesIterator uit
=_options
.initialUndefinesBegin(); uit
!= _options
.initialUndefinesEnd(); ++uit
) {
1143 SymbolTable::IndirectBindingSlot slot
= _symbolTable
.findSlotForName(*uit
);
1144 if ( _internal
.indirectBindingTable
[slot
] == NULL
) {
1145 _inputFiles
.searchLibraries(*uit
, false, true, false, *this);
1147 if ( _internal
.indirectBindingTable
[slot
] != NULL
)
1148 _deadStripRoots
.insert(_internal
.indirectBindingTable
[slot
]);
1151 // this helper is only referenced by synthesize stubs, assume it will be used
1152 if ( _internal
.classicBindingHelper
!= NULL
)
1153 _deadStripRoots
.insert(_internal
.classicBindingHelper
);
1155 // this helper is only referenced by synthesize stubs, assume it will be used
1156 if ( _internal
.compressedFastBinderProxy
!= NULL
)
1157 _deadStripRoots
.insert(_internal
.compressedFastBinderProxy
);
1159 // this helper is only referenced by synthesized lazy stubs, assume it will be used
1160 if ( _internal
.lazyBindingHelper
!= NULL
)
1161 _deadStripRoots
.insert(_internal
.lazyBindingHelper
);
1163 // add all dont-dead-strip atoms as roots
1164 for (std::vector
<const ld::Atom
*>::const_iterator it
=_atoms
.begin(); it
!= _atoms
.end(); ++it
) {
1165 const ld::Atom
* atom
= *it
;
1166 if ( atom
->dontDeadStrip() ) {
1167 //fprintf(stderr, "dont dead strip: %p %s %s\n", atom, atom->section().sectionName(), atom->name());
1168 _deadStripRoots
.insert(atom
);
1169 // unset liveness, so markLive() will recurse
1170 (const_cast<ld::Atom
*>(atom
))->setLive(0);
1174 // mark all roots as live, and all atoms they reference
1175 for (std::set
<const ld::Atom
*>::iterator it
=_deadStripRoots
.begin(); it
!= _deadStripRoots
.end(); ++it
) {
1176 WhyLiveBackChain rootChain
;
1177 rootChain
.previous
= NULL
;
1178 rootChain
.referer
= *it
;
1179 this->markLive(**it
, &rootChain
);
1182 // special case atoms that need to be live if they reference something live
1183 if ( ! _dontDeadStripIfReferencesLive
.empty() ) {
1184 for (std::vector
<const ld::Atom
*>::iterator it
=_dontDeadStripIfReferencesLive
.begin(); it
!= _dontDeadStripIfReferencesLive
.end(); ++it
) {
1185 const Atom
* liveIfRefLiveAtom
= *it
;
1186 //fprintf(stderr, "live-if-live atom: %s\n", liveIfRefLiveAtom->name());
1187 if ( liveIfRefLiveAtom
->live() )
1189 bool hasLiveRef
= false;
1190 for (ld::Fixup::iterator fit
=liveIfRefLiveAtom
->fixupsBegin(); fit
!= liveIfRefLiveAtom
->fixupsEnd(); ++fit
) {
1191 const Atom
* target
= NULL
;
1192 switch ( fit
->binding
) {
1193 case ld::Fixup::bindingDirectlyBound
:
1194 target
= fit
->u
.target
;
1196 case ld::Fixup::bindingsIndirectlyBound
:
1197 target
= _internal
.indirectBindingTable
[fit
->u
.bindingIndex
];
1202 if ( (target
!= NULL
) && target
->live() )
1206 WhyLiveBackChain rootChain
;
1207 rootChain
.previous
= NULL
;
1208 rootChain
.referer
= liveIfRefLiveAtom
;
1209 this->markLive(*liveIfRefLiveAtom
, &rootChain
);
1214 // now remove all non-live atoms from _atoms
1215 const bool log
= false;
1217 fprintf(stderr
, "deadStripOptimize() all %ld atoms with liveness:\n", _atoms
.size());
1218 for (std::vector
<const ld::Atom
*>::const_iterator it
=_atoms
.begin(); it
!= _atoms
.end(); ++it
) {
1219 const ld::File
* file
= (*it
)->file();
1220 fprintf(stderr
, " live=%d atom=%p name=%s from=%s\n", (*it
)->live(), *it
, (*it
)->name(), (file
? file
->path() : "<internal>"));
1224 if ( _haveLLVMObjs
&& !force
) {
1225 std::copy_if(_atoms
.begin(), _atoms
.end(), std::back_inserter(_internal
.deadAtoms
), NotLiveLTO() );
1226 // <rdar://problem/9777977> don't remove combinable atoms, they may come back in lto output
1227 _atoms
.erase(std::remove_if(_atoms
.begin(), _atoms
.end(), NotLiveLTO()), _atoms
.end());
1228 _symbolTable
.removeDeadAtoms();
1231 std::copy_if(_atoms
.begin(), _atoms
.end(), std::back_inserter(_internal
.deadAtoms
), NotLive() );
1232 _atoms
.erase(std::remove_if(_atoms
.begin(), _atoms
.end(), NotLive()), _atoms
.end());
1236 fprintf(stderr
, "deadStripOptimize() %ld remaining atoms\n", _atoms
.size());
1237 for (std::vector
<const ld::Atom
*>::const_iterator it
=_atoms
.begin(); it
!= _atoms
.end(); ++it
) {
1238 fprintf(stderr
, " live=%d atom=%p name=%s\n", (*it
)->live(), *it
, (*it
)->name());
1244 // This is called when LTO is used but -dead_strip is not used.
1245 // Some undefines were eliminated by LTO, but others were not.
1246 void Resolver::remainingUndefines(std::vector
<const char*>& undefs
)
1249 // search all atoms for references that are unbound
1250 for (std::vector
<const ld::Atom
*>::const_iterator it
=_atoms
.begin(); it
!= _atoms
.end(); ++it
) {
1251 const ld::Atom
* atom
= *it
;
1252 for (ld::Fixup::iterator fit
=atom
->fixupsBegin(); fit
!= atom
->fixupsEnd(); ++fit
) {
1253 switch ( (ld::Fixup::TargetBinding
)fit
->binding
) {
1254 case ld::Fixup::bindingByNameUnbound
:
1255 assert(0 && "should not be by-name this late");
1256 undefSet
.insert(fit
->u
.name
);
1258 case ld::Fixup::bindingsIndirectlyBound
:
1259 if ( _internal
.indirectBindingTable
[fit
->u
.bindingIndex
] == NULL
) {
1260 undefSet
.insert(_symbolTable
.indirectName(fit
->u
.bindingIndex
));
1263 case ld::Fixup::bindingByContentBound
:
1264 case ld::Fixup::bindingNone
:
1265 case ld::Fixup::bindingDirectlyBound
:
1270 // look for any initial undefines that are still undefined
1271 for (Options::UndefinesIterator uit
=_options
.initialUndefinesBegin(); uit
!= _options
.initialUndefinesEnd(); ++uit
) {
1272 if ( ! _symbolTable
.hasName(*uit
) ) {
1273 undefSet
.insert(*uit
);
1277 // copy set to vector
1278 for (StringSet::const_iterator it
=undefSet
.begin(); it
!= undefSet
.end(); ++it
) {
1279 fprintf(stderr
, "undef: %s\n", *it
);
1280 undefs
.push_back(*it
);
1284 void Resolver::liveUndefines(std::vector
<const char*>& undefs
)
1287 // search all live atoms for references that are unbound
1288 for (std::vector
<const ld::Atom
*>::const_iterator it
=_atoms
.begin(); it
!= _atoms
.end(); ++it
) {
1289 const ld::Atom
* atom
= *it
;
1290 if ( ! atom
->live() )
1292 for (ld::Fixup::iterator fit
=atom
->fixupsBegin(); fit
!= atom
->fixupsEnd(); ++fit
) {
1293 switch ( (ld::Fixup::TargetBinding
)fit
->binding
) {
1294 case ld::Fixup::bindingByNameUnbound
:
1295 assert(0 && "should not be by-name this late");
1296 undefSet
.insert(fit
->u
.name
);
1298 case ld::Fixup::bindingsIndirectlyBound
:
1299 if ( _internal
.indirectBindingTable
[fit
->u
.bindingIndex
] == NULL
) {
1300 undefSet
.insert(_symbolTable
.indirectName(fit
->u
.bindingIndex
));
1303 case ld::Fixup::bindingByContentBound
:
1304 case ld::Fixup::bindingNone
:
1305 case ld::Fixup::bindingDirectlyBound
:
1310 // look for any initial undefines that are still undefined
1311 for (Options::UndefinesIterator uit
=_options
.initialUndefinesBegin(); uit
!= _options
.initialUndefinesEnd(); ++uit
) {
1312 if ( ! _symbolTable
.hasName(*uit
) ) {
1313 undefSet
.insert(*uit
);
1317 // copy set to vector
1318 for (StringSet::const_iterator it
=undefSet
.begin(); it
!= undefSet
.end(); ++it
) {
1319 undefs
.push_back(*it
);
1325 // <rdar://problem/8252819> warn when .objc_class_name_* symbol missing
1326 class ExportedObjcClass
1329 ExportedObjcClass(const Options
& opt
) : _options(opt
) {}
1331 bool operator()(const char* name
) const {
1332 if ( (strncmp(name
, ".objc_class_name_", 17) == 0) && _options
.shouldExport(name
) ) {
1333 warning("ignoring undefined symbol %s from -exported_symbols_list", name
);
1336 const char* s
= strstr(name
, "CLASS_$_");
1338 char temp
[strlen(name
)+16];
1339 strcpy(temp
, ".objc_class_name_");
1340 strcat(temp
, &s
[8]);
1341 if ( _options
.wasRemovedExport(temp
) ) {
1342 warning("ignoring undefined symbol %s from -exported_symbols_list", temp
);
1349 const Options
& _options
;
1353 // temp hack for undefined aliases
1354 class UndefinedAlias
1357 UndefinedAlias(const Options
& opt
) : _aliases(opt
.cmdLineAliases()) {}
1359 bool operator()(const char* name
) const {
1360 for (std::vector
<Options::AliasPair
>::const_iterator it
=_aliases
.begin(); it
!= _aliases
.end(); ++it
) {
1361 if ( strcmp(it
->realName
, name
) == 0 ) {
1362 warning("undefined base symbol '%s' for alias '%s'", name
, it
->alias
);
1369 const std::vector
<Options::AliasPair
>& _aliases
;
1374 static const char* pathLeafName(const char* path
)
1376 const char* shortPath
= strrchr(path
, '/');
1377 if ( shortPath
== NULL
)
1380 return &shortPath
[1];
1383 bool Resolver::printReferencedBy(const char* name
, SymbolTable::IndirectBindingSlot slot
)
1385 unsigned foundReferenceCount
= 0;
1386 for (std::vector
<const ld::Atom
*>::const_iterator it
=_atoms
.begin(); it
!= _atoms
.end(); ++it
) {
1387 const ld::Atom
* atom
= *it
;
1388 for (ld::Fixup::iterator fit
=atom
->fixupsBegin(); fit
!= atom
->fixupsEnd(); ++fit
) {
1389 if ( fit
->binding
== ld::Fixup::bindingsIndirectlyBound
) {
1390 if ( fit
->u
.bindingIndex
== slot
) {
1391 if ( atom
->contentType() == ld::Atom::typeNonLazyPointer
) {
1392 const ld::Atom
* existingAtom
;
1393 unsigned int nlSlot
= _symbolTable
.findSlotForReferences(atom
, &existingAtom
);
1394 if ( printReferencedBy(name
, nlSlot
) )
1395 ++foundReferenceCount
;
1397 else if ( atom
->contentType() == ld::Atom::typeCFI
) {
1398 fprintf(stderr
, " Dwarf Exception Unwind Info (__eh_frame) in %s\n", pathLeafName(atom
->safeFilePath()));
1399 ++foundReferenceCount
;
1402 fprintf(stderr
, " %s in %s\n", _options
.demangleSymbol(atom
->name()), pathLeafName(atom
->safeFilePath()));
1403 ++foundReferenceCount
;
1404 break; // if undefined used twice in a function, only show first
1409 if ( foundReferenceCount
> 6 ) {
1410 fprintf(stderr
, " ...\n");
1411 break; // only show first six uses of undefined symbol
1414 return (foundReferenceCount
!= 0);
1417 void Resolver::checkUndefines(bool force
)
1419 // when using LTO, undefines are checked after bitcode is optimized
1420 if ( _haveLLVMObjs
&& !force
)
1423 // error out on any remaining undefines
1424 bool doPrint
= true;
1425 bool doError
= true;
1426 switch ( _options
.undefinedTreatment() ) {
1427 case Options::kUndefinedError
:
1429 case Options::kUndefinedDynamicLookup
:
1432 case Options::kUndefinedWarning
:
1435 case Options::kUndefinedSuppress
:
1440 std::vector
<const char*> unresolvableUndefines
;
1441 if ( _options
.deadCodeStrip() )
1442 this->liveUndefines(unresolvableUndefines
);
1443 else if( _haveLLVMObjs
)
1444 this->remainingUndefines(unresolvableUndefines
); // <rdar://problem/10052396> LTO may have eliminated need for some undefines
1446 _symbolTable
.undefines(unresolvableUndefines
);
1448 // <rdar://problem/8252819> assert when .objc_class_name_* symbol missing
1449 if ( _options
.hasExportMaskList() ) {
1450 unresolvableUndefines
.erase(std::remove_if(unresolvableUndefines
.begin(), unresolvableUndefines
.end(), ExportedObjcClass(_options
)), unresolvableUndefines
.end());
1453 // hack to temporarily make missing aliases a warning
1454 if ( _options
.haveCmdLineAliases() ) {
1455 unresolvableUndefines
.erase(std::remove_if(unresolvableUndefines
.begin(), unresolvableUndefines
.end(), UndefinedAlias(_options
)), unresolvableUndefines
.end());
1458 const int unresolvableCount
= unresolvableUndefines
.size();
1459 int unresolvableExportsCount
= 0;
1460 if ( unresolvableCount
!= 0 ) {
1462 for (const auto& lib
: _internal
.missingLinkerOptionLibraries
)
1463 warning("Could not find auto-linked library '%s'", lib
);
1464 for (const auto& frm
: _internal
.missingLinkerOptionFrameworks
)
1465 warning("Could not find auto-linked framework '%s'", frm
);
1466 if ( _options
.printArchPrefix() )
1467 fprintf(stderr
, "Undefined symbols for architecture %s:\n", _options
.architectureName());
1469 fprintf(stderr
, "Undefined symbols:\n");
1470 for (int i
=0; i
< unresolvableCount
; ++i
) {
1471 const char* name
= unresolvableUndefines
[i
];
1472 unsigned int slot
= _symbolTable
.findSlotForName(name
);
1473 fprintf(stderr
, " \"%s\", referenced from:\n", _options
.demangleSymbol(name
));
1474 // scan all atoms for references
1475 bool foundAtomReference
= printReferencedBy(name
, slot
);
1476 // scan command line options
1477 if ( !foundAtomReference
) {
1478 // might be from -init command line option
1479 if ( (_options
.initFunctionName() != NULL
) && (strcmp(name
, _options
.initFunctionName()) == 0) ) {
1480 fprintf(stderr
, " -init command line option\n");
1482 // or might be from exported symbol option
1483 else if ( _options
.hasExportMaskList() && _options
.shouldExport(name
) ) {
1484 fprintf(stderr
, " -exported_symbol[s_list] command line option\n");
1486 // or might be from re-exported symbol option
1487 else if ( _options
.hasReExportList() && _options
.shouldReExport(name
) ) {
1488 fprintf(stderr
, " -reexported_symbols_list command line option\n");
1490 else if ( (_options
.outputKind() == Options::kDynamicExecutable
)
1491 && (_options
.entryName() != NULL
) && (strcmp(name
, _options
.entryName()) == 0) ) {
1492 fprintf(stderr
, " implicit entry/start for main executable\n");
1495 bool isInitialUndefine
= false;
1496 for (Options::UndefinesIterator uit
=_options
.initialUndefinesBegin(); uit
!= _options
.initialUndefinesEnd(); ++uit
) {
1497 if ( strcmp(*uit
, name
) == 0 ) {
1498 isInitialUndefine
= true;
1502 if ( isInitialUndefine
)
1503 fprintf(stderr
, " -u command line option\n");
1505 ++unresolvableExportsCount
;
1507 // be helpful and check for typos
1508 bool printedStart
= false;
1509 for (SymbolTable::byNameIterator sit
=_symbolTable
.begin(); sit
!= _symbolTable
.end(); sit
++) {
1510 const ld::Atom
* atom
= *sit
;
1511 if ( (atom
!= NULL
) && (atom
->symbolTableInclusion() == ld::Atom::symbolTableIn
) && (strstr(atom
->name(), name
) != NULL
) ) {
1512 if ( ! printedStart
) {
1513 fprintf(stderr
, " (maybe you meant: %s", atom
->name());
1514 printedStart
= true;
1517 fprintf(stderr
, ", %s ", atom
->name());
1522 fprintf(stderr
, ")\n");
1523 // <rdar://problem/8989530> Add comment to error message when __ZTV symbols are undefined
1524 if ( strncmp(name
, "__ZTV", 5) == 0 ) {
1525 fprintf(stderr
, " NOTE: a missing vtable usually means the first non-inline virtual member function has no definition.\n");
1530 throw "symbol(s) not found";
1537 void Resolver::checkDylibSymbolCollisions()
1539 for (SymbolTable::byNameIterator it
=_symbolTable
.begin(); it
!= _symbolTable
.end(); it
++) {
1540 const ld::Atom
* atom
= *it
;
1543 if ( atom
->scope() == ld::Atom::scopeGlobal
) {
1544 // <rdar://problem/5048861> No warning about tentative definition conflicting with dylib definition
1545 // for each tentative definition in symbol table look for dylib that exports same symbol name
1546 if ( atom
->definition() == ld::Atom::definitionTentative
) {
1547 _inputFiles
.searchLibraries(atom
->name(), true, false, false, *this);
1549 // record any overrides of weak symbols in any linked dylib
1550 if ( (atom
->definition() == ld::Atom::definitionRegular
) && (atom
->symbolTableInclusion() == ld::Atom::symbolTableIn
) ) {
1551 if ( _inputFiles
.searchWeakDefInDylib(atom
->name()) )
1552 (const_cast<ld::Atom
*>(atom
))->setOverridesDylibsWeakDef();
1559 const ld::Atom
* Resolver::entryPoint(bool searchArchives
)
1561 const char* symbolName
= NULL
;
1562 bool makingDylib
= false;
1563 switch ( _options
.outputKind() ) {
1564 case Options::kDynamicExecutable
:
1565 case Options::kStaticExecutable
:
1566 case Options::kDyld
:
1567 case Options::kPreload
:
1568 symbolName
= _options
.entryName();
1570 case Options::kDynamicLibrary
:
1571 symbolName
= _options
.initFunctionName();
1574 case Options::kObjectFile
:
1575 case Options::kDynamicBundle
:
1576 case Options::kKextBundle
:
1580 if ( symbolName
!= NULL
) {
1581 SymbolTable::IndirectBindingSlot slot
= _symbolTable
.findSlotForName(symbolName
);
1582 if ( (_internal
.indirectBindingTable
[slot
] == NULL
) && searchArchives
) {
1583 // <rdar://problem/7043256> ld64 can not find a -e entry point from an archive
1584 _inputFiles
.searchLibraries(symbolName
, false, true, false, *this);
1586 if ( _internal
.indirectBindingTable
[slot
] == NULL
) {
1587 if ( strcmp(symbolName
, "start") == 0 )
1588 throwf("entry point (%s) undefined. Usually in crt1.o", symbolName
);
1590 throwf("entry point (%s) undefined.", symbolName
);
1592 else if ( _internal
.indirectBindingTable
[slot
]->definition() == ld::Atom::definitionProxy
) {
1594 throwf("-init function (%s) found in linked dylib, must be in dylib being linked", symbolName
);
1596 return _internal
.indirectBindingTable
[slot
];
1602 void Resolver::fillInHelpersInInternalState()
1604 // look up well known atoms
1605 bool needsStubHelper
= true;
1606 switch ( _options
.outputKind() ) {
1607 case Options::kDynamicExecutable
:
1608 case Options::kDynamicLibrary
:
1609 case Options::kDynamicBundle
:
1610 needsStubHelper
= true;
1612 case Options::kDyld
:
1613 case Options::kKextBundle
:
1614 case Options::kObjectFile
:
1615 case Options::kStaticExecutable
:
1616 case Options::kPreload
:
1617 needsStubHelper
= false;
1621 _internal
.classicBindingHelper
= NULL
;
1622 // FIXME: What about fMakeThreadedStartsSection?
1623 if ( needsStubHelper
&& !_options
.makeCompressedDyldInfo() ) {
1624 // "dyld_stub_binding_helper" comes from .o file, so should already exist in symbol table
1625 if ( _symbolTable
.hasName("dyld_stub_binding_helper") ) {
1626 SymbolTable::IndirectBindingSlot slot
= _symbolTable
.findSlotForName("dyld_stub_binding_helper");
1627 _internal
.classicBindingHelper
= _internal
.indirectBindingTable
[slot
];
1631 _internal
.lazyBindingHelper
= NULL
;
1632 if ( _options
.usingLazyDylibLinking() ) {
1633 // "dyld_lazy_dylib_stub_binding_helper" comes from lazydylib1.o file, so should already exist in symbol table
1634 if ( _symbolTable
.hasName("dyld_lazy_dylib_stub_binding_helper") ) {
1635 SymbolTable::IndirectBindingSlot slot
= _symbolTable
.findSlotForName("dyld_lazy_dylib_stub_binding_helper");
1636 _internal
.lazyBindingHelper
= _internal
.indirectBindingTable
[slot
];
1638 if ( _internal
.lazyBindingHelper
== NULL
)
1639 throw "symbol dyld_lazy_dylib_stub_binding_helper not defined (usually in lazydylib1.o)";
1642 _internal
.compressedFastBinderProxy
= NULL
;
1643 // FIXME: What about fMakeThreadedStartsSection?
1644 if ( needsStubHelper
&& _options
.makeCompressedDyldInfo() ) {
1645 // "dyld_stub_binder" comes from libSystem.dylib so will need to manually resolve
1646 if ( !_symbolTable
.hasName("dyld_stub_binder") ) {
1647 _inputFiles
.searchLibraries("dyld_stub_binder", true, false, false, *this);
1649 if ( _symbolTable
.hasName("dyld_stub_binder") ) {
1650 SymbolTable::IndirectBindingSlot slot
= _symbolTable
.findSlotForName("dyld_stub_binder");
1651 _internal
.compressedFastBinderProxy
= _internal
.indirectBindingTable
[slot
];
1653 if ( _internal
.compressedFastBinderProxy
== NULL
) {
1654 if ( _options
.undefinedTreatment() != Options::kUndefinedError
) {
1656 _internal
.compressedFastBinderProxy
= new UndefinedProxyAtom("dyld_stub_binder");
1657 this->doAtom(*_internal
.compressedFastBinderProxy
);
1664 void Resolver::fillInInternalState()
1666 // store atoms into their final section
1667 for (std::vector
<const ld::Atom
*>::iterator it
= _atoms
.begin(); it
!= _atoms
.end(); ++it
) {
1668 _internal
.addAtom(**it
);
1671 // <rdar://problem/7783918> make sure there is a __text section so that codesigning works
1672 if ( (_options
.outputKind() == Options::kDynamicLibrary
) || (_options
.outputKind() == Options::kDynamicBundle
) )
1673 _internal
.getFinalSection(*new ld::Section("__TEXT", "__text", ld::Section::typeCode
));
1675 // Don't allow swift frameworks to link other swift frameworks.
1676 if ( _internal
.someObjectFileHasSwift
&& _internal
.firstSwiftDylibFile
!= nullptr )
1677 throwf("linking swift frameworks against other swift frameworks (%s) is not permitted",
1678 _internal
.firstSwiftDylibFile
->path());
1681 void Resolver::fillInEntryPoint()
1683 _internal
.entryPoint
= this->entryPoint(true);
1686 void Resolver::syncAliases()
1688 if ( !_haveAliases
|| (_options
.outputKind() == Options::kObjectFile
) )
1691 // Set attributes of alias to match its found target
1692 for (std::vector
<const ld::Atom
*>::iterator it
= _atoms
.begin(); it
!= _atoms
.end(); ++it
) {
1693 const ld::Atom
* atom
= *it
;
1694 if ( atom
->section().type() == ld::Section::typeTempAlias
) {
1695 assert(atom
->fixupsBegin() != atom
->fixupsEnd());
1696 for (ld::Fixup::iterator fit
= atom
->fixupsBegin(); fit
!= atom
->fixupsEnd(); ++fit
) {
1697 const ld::Atom
* target
;
1698 ld::Atom::Scope scope
;
1699 assert(fit
->kind
== ld::Fixup::kindNoneFollowOn
);
1700 switch ( fit
->binding
) {
1701 case ld::Fixup::bindingByNameUnbound
:
1703 case ld::Fixup::bindingsIndirectlyBound
:
1704 target
= _internal
.indirectBindingTable
[fit
->u
.bindingIndex
];
1705 assert(target
!= NULL
);
1706 scope
= atom
->scope();
1707 (const_cast<Atom
*>(atom
))->setAttributesFromAtom(*target
);
1708 // alias has same attributes as target, except for scope
1709 (const_cast<Atom
*>(atom
))->setScope(scope
);
1712 assert(0 && "internal error: unexpected alias binding");
1719 void Resolver::removeCoalescedAwayAtoms()
1721 const bool log
= false;
1723 fprintf(stderr
, "removeCoalescedAwayAtoms() starts with %lu atoms\n", _atoms
.size());
1725 _atoms
.erase(std::remove_if(_atoms
.begin(), _atoms
.end(), AtomCoalescedAway()), _atoms
.end());
1727 fprintf(stderr
, "removeCoalescedAwayAtoms() after removing coalesced atoms, %lu remain\n", _atoms
.size());
1728 for (std::vector
<const ld::Atom
*>::const_iterator it
=_atoms
.begin(); it
!= _atoms
.end(); ++it
) {
1729 fprintf(stderr
, " atom=%p %s\n", *it
, (*it
)->name());
1734 void Resolver::linkTimeOptimize()
1736 // only do work here if some llvm obj files where loaded
1737 if ( ! _haveLLVMObjs
)
1740 // <rdar://problem/15314161> LTO: Symbol multiply defined error should specify exactly where the symbol is found
1741 _symbolTable
.checkDuplicateSymbols();
1743 // run LLVM lto code-gen
1744 lto::OptimizeOptions optOpt
;
1745 optOpt
.outputFilePath
= _options
.outputFilePath();
1746 optOpt
.tmpObjectFilePath
= _options
.tempLtoObjectPath();
1747 optOpt
.ltoCachePath
= _options
.ltoCachePath();
1748 optOpt
.ltoPruneIntervalOverwrite
= _options
.ltoPruneIntervalOverwrite();
1749 optOpt
.ltoPruneInterval
= _options
.ltoPruneInterval();
1750 optOpt
.ltoPruneAfter
= _options
.ltoPruneAfter();
1751 optOpt
.ltoMaxCacheSize
= _options
.ltoMaxCacheSize();
1752 optOpt
.preserveAllGlobals
= _options
.allGlobalsAreDeadStripRoots() || _options
.hasExportRestrictList();
1753 optOpt
.verbose
= _options
.verbose();
1754 optOpt
.saveTemps
= _options
.saveTempFiles();
1755 optOpt
.ltoCodegenOnly
= _options
.ltoCodegenOnly();
1756 optOpt
.pie
= _options
.positionIndependentExecutable();
1757 optOpt
.mainExecutable
= _options
.linkingMainExecutable();;
1758 optOpt
.staticExecutable
= (_options
.outputKind() == Options::kStaticExecutable
);
1759 optOpt
.preload
= (_options
.outputKind() == Options::kPreload
);
1760 optOpt
.relocatable
= (_options
.outputKind() == Options::kObjectFile
);
1761 optOpt
.allowTextRelocs
= _options
.allowTextRelocs();
1762 optOpt
.linkerDeadStripping
= _options
.deadCodeStrip();
1763 optOpt
.needsUnwindInfoSection
= _options
.needsUnwindInfoSection();
1764 optOpt
.keepDwarfUnwind
= _options
.keepDwarfUnwind();
1765 optOpt
.verboseOptimizationHints
= _options
.verboseOptimizationHints();
1766 optOpt
.armUsesZeroCostExceptions
= _options
.armUsesZeroCostExceptions();
1767 optOpt
.simulator
= _options
.targetIOSSimulator();
1768 optOpt
.ignoreMismatchPlatform
= ((_options
.outputKind() == Options::kPreload
) || (_options
.outputKind() == Options::kStaticExecutable
));
1769 #if SUPPORT_ARCH_arm64e
1770 optOpt
.supportsAuthenticatedPointers
= _options
.supportsAuthenticatedPointers();
1772 optOpt
.bitcodeBundle
= (_options
.bundleBitcode() && (_options
.bitcodeKind() != Options::kBitcodeMarker
));
1773 optOpt
.maxDefaultCommonAlignment
= _options
.maxDefaultCommonAlign();
1774 optOpt
.arch
= _options
.architecture();
1775 optOpt
.mcpu
= _options
.mcpuLTO();
1776 optOpt
.platforms
= _options
.platforms();
1777 optOpt
.llvmOptions
= &_options
.llvmOptions();
1778 optOpt
.initialUndefines
= &_options
.initialUndefines();
1780 std::vector
<const ld::Atom
*> newAtoms
;
1781 std::vector
<const char*> additionalUndefines
;
1782 if ( ! lto::optimize(_atoms
, _internal
, optOpt
, *this, newAtoms
, additionalUndefines
) )
1783 return; // if nothing done
1784 _ltoCodeGenFinished
= true;
1786 // add all newly created atoms to _atoms and update symbol table
1787 for(std::vector
<const ld::Atom
*>::iterator it
= newAtoms
.begin(); it
!= newAtoms
.end(); ++it
)
1790 // some atoms might have been optimized way (marked coalesced), remove them
1791 this->removeCoalescedAwayAtoms();
1793 // run through all atoms again and make sure newly codegened atoms have references bound
1794 for (std::vector
<const ld::Atom
*>::const_iterator it
=_atoms
.begin(); it
!= _atoms
.end(); ++it
)
1795 this->convertReferencesToIndirect(**it
);
1797 // adjust section of any new
1798 for (std::vector
<const AliasAtom
*>::const_iterator it
=_aliasesFromCmdLine
.begin(); it
!= _aliasesFromCmdLine
.end(); ++it
) {
1799 const AliasAtom
* aliasAtom
= *it
;
1800 // update fields in AliasAtom to match newly constructed mach-o atom
1801 aliasAtom
->setFinalAliasOf();
1804 // <rdar://problem/14609792> add any auto-link libraries requested by LTO output to dylibs to search
1805 _inputFiles
.addLinkerOptionLibraries(_internal
, *this);
1806 _inputFiles
.createIndirectDylibs();
1808 // resolve new undefines (e.g calls to _malloc and _memcpy that llvm compiler conjures up)
1809 for(std::vector
<const char*>::iterator uit
= additionalUndefines
.begin(); uit
!= additionalUndefines
.end(); ++uit
) {
1810 const char *targetName
= *uit
;
1811 // these symbols may or may not already be in linker's symbol table
1812 if ( ! _symbolTable
.hasName(targetName
) ) {
1813 _inputFiles
.searchLibraries(targetName
, true, true, false, *this);
1817 // if -dead_strip on command line
1818 if ( _options
.deadCodeStrip() ) {
1819 // run through all atoms again and make live_section LTO atoms are preserved from dead_stripping if needed
1820 _dontDeadStripIfReferencesLive
.clear();
1821 for (std::vector
<const ld::Atom
*>::const_iterator it
=_atoms
.begin(); it
!= _atoms
.end(); ++it
) {
1822 const ld::Atom
* atom
= *it
;
1823 if ( atom
->dontDeadStripIfReferencesLive() ) {
1824 _dontDeadStripIfReferencesLive
.push_back(atom
);
1827 // clear liveness bit
1828 (const_cast<ld::Atom
*>(*it
))->setLive((*it
)->dontDeadStrip());
1830 // and re-compute dead code
1831 this->deadStripOptimize(true);
1834 // <rdar://problem/12386559> if -exported_symbols_list on command line, re-force scope
1835 if ( _options
.hasExportMaskList() ) {
1836 for (std::vector
<const ld::Atom
*>::const_iterator it
=_atoms
.begin(); it
!= _atoms
.end(); ++it
) {
1837 const ld::Atom
* atom
= *it
;
1838 if ( atom
->scope() == ld::Atom::scopeGlobal
) {
1839 if ( !_options
.shouldExport(atom
->name()) ) {
1840 (const_cast<ld::Atom
*>(atom
))->setScope(ld::Atom::scopeLinkageUnit
);
1846 if ( _options
.outputKind() == Options::kObjectFile
) {
1847 // if -r mode, add proxies for new undefines (e.g. ___stack_chk_fail)
1848 this->resolveUndefines();
1851 // last chance to check for undefines
1852 this->resolveUndefines();
1853 this->checkUndefines(true);
1855 // check new code does not override some dylib
1856 this->checkDylibSymbolCollisions();
1858 // <rdar://problem/33853815> remove undefs from LTO objects that gets optimized away
1859 std::unordered_set
<const ld::Atom
*> mustPreserve
;
1860 if ( _internal
.classicBindingHelper
!= NULL
)
1861 mustPreserve
.insert(_internal
.classicBindingHelper
);
1862 if ( _internal
.compressedFastBinderProxy
!= NULL
)
1863 mustPreserve
.insert(_internal
.compressedFastBinderProxy
);
1864 if ( _internal
.lazyBindingHelper
!= NULL
)
1865 mustPreserve
.insert(_internal
.lazyBindingHelper
);
1866 if ( const ld::Atom
* entry
= this->entryPoint(true) )
1867 mustPreserve
.insert(entry
);
1868 for (Options::UndefinesIterator uit
=_options
.initialUndefinesBegin(); uit
!= _options
.initialUndefinesEnd(); ++uit
) {
1869 SymbolTable::IndirectBindingSlot slot
= _symbolTable
.findSlotForName(*uit
);
1870 if ( _internal
.indirectBindingTable
[slot
] != NULL
)
1871 mustPreserve
.insert(_internal
.indirectBindingTable
[slot
]);
1873 _symbolTable
.removeDeadUndefs(_atoms
, mustPreserve
);
1878 void Resolver::tweakWeakness()
1880 // <rdar://problem/7977374> Add command line options to control symbol weak-def bit on exported symbols
1881 if ( _options
.hasWeakBitTweaks() ) {
1882 for (std::vector
<ld::Internal::FinalSection
*>::iterator sit
= _internal
.sections
.begin(); sit
!= _internal
.sections
.end(); ++sit
) {
1883 ld::Internal::FinalSection
* sect
= *sit
;
1884 for (std::vector
<const ld::Atom
*>::iterator ait
= sect
->atoms
.begin(); ait
!= sect
->atoms
.end(); ++ait
) {
1885 const ld::Atom
* atom
= *ait
;
1886 if ( atom
->definition() != ld::Atom::definitionRegular
)
1888 const char* name
= atom
->name();
1889 if ( atom
->scope() == ld::Atom::scopeGlobal
) {
1890 if ( atom
->combine() == ld::Atom::combineNever
) {
1891 if ( _options
.forceWeak(name
) )
1892 (const_cast<ld::Atom
*>(atom
))->setCombine(ld::Atom::combineByName
);
1894 else if ( atom
->combine() == ld::Atom::combineByName
) {
1895 if ( _options
.forceNotWeak(name
) )
1896 (const_cast<ld::Atom
*>(atom
))->setCombine(ld::Atom::combineNever
);
1900 if ( _options
.forceWeakNonWildCard(name
) )
1901 warning("cannot force to be weak, non-external symbol %s", name
);
1902 else if ( _options
.forceNotWeakNonWildcard(name
) )
1903 warning("cannot force to be not-weak, non-external symbol %s", name
);
1910 void Resolver::buildArchivesList()
1912 // Determine which archives were linked and update the internal state.
1913 _inputFiles
.archives(_internal
);
1916 void Resolver::dumpAtoms()
1918 fprintf(stderr
, "Resolver all atoms:\n");
1919 for (std::vector
<const ld::Atom
*>::const_iterator it
=_atoms
.begin(); it
!= _atoms
.end(); ++it
) {
1920 const ld::Atom
* atom
= *it
;
1921 fprintf(stderr
, " %p name=%s, def=%d\n", atom
, atom
->name(), atom
->definition());
1925 void Resolver::resolve()
1927 this->initializeState();
1928 this->buildAtomList();
1929 this->addInitialUndefines();
1930 this->fillInHelpersInInternalState();
1931 this->resolveUndefines();
1932 this->deadStripOptimize();
1933 this->checkUndefines();
1934 this->checkDylibSymbolCollisions();
1935 this->syncAliases();
1936 this->removeCoalescedAwayAtoms();
1937 this->fillInEntryPoint();
1938 this->linkTimeOptimize();
1939 this->fillInInternalState();
1940 this->tweakWeakness();
1941 _symbolTable
.checkDuplicateSymbols();
1942 this->buildArchivesList();