]> git.saurik.com Git - apple/ld64.git/blame - src/ld/InputFiles.cpp
ld64-236.3.tar.gz
[apple/ld64.git] / src / ld / InputFiles.cpp
CommitLineData
f80fe69f 1
a645023d
A
2/* -*- mode: C++; c-basic-offset: 4; tab-width: 4 -*-*
3 *
afe874b1 4 * Copyright (c) 2009-2011 Apple Inc. All rights reserved.
a645023d
A
5 *
6 * @APPLE_LICENSE_HEADER_START@
7 *
8 * This file contains Original Code and/or Modifications of Original Code
9 * as defined in and that are subject to the Apple Public Source License
10 * Version 2.0 (the 'License'). You may not use this file except in
11 * compliance with the License. Please obtain a copy of the License at
12 * http://www.opensource.apple.com/apsl/ and read it before using this
13 * file.
14 *
15 * The Original Code and all software distributed under the License are
16 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
17 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
18 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
19 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
20 * Please see the License for the specific language governing rights and
21 * limitations under the License.
22 *
23 * @APPLE_LICENSE_HEADER_END@
24 */
25
26
27#include <stdlib.h>
28#include <sys/types.h>
29#include <sys/stat.h>
30#include <sys/mman.h>
31#include <sys/sysctl.h>
32#include <fcntl.h>
33#include <errno.h>
34#include <limits.h>
35#include <unistd.h>
36#include <mach/mach_time.h>
37#include <mach/vm_statistics.h>
38#include <mach/mach_init.h>
39#include <mach/mach_host.h>
40#include <dlfcn.h>
41#include <mach-o/dyld.h>
42#include <mach-o/fat.h>
ebf6f434
A
43#include <sys/sysctl.h>
44#include <libkern/OSAtomic.h>
a645023d
A
45
46#include <string>
47#include <map>
48#include <set>
49#include <string>
50#include <vector>
51#include <list>
52#include <algorithm>
a645023d
A
53#include <dlfcn.h>
54#include <AvailabilityMacros.h>
55
56#include "Options.h"
57
58#include "InputFiles.h"
59#include "macho_relocatable_file.h"
60#include "macho_dylib_file.h"
61#include "archive_file.h"
62#include "lto_file.h"
63#include "opaque_section_file.h"
f80fe69f 64#include "MachOFileAbstraction.hpp"
ebf6f434 65#include "Snapshot.h"
a645023d 66
ebf6f434 67const bool _s_logPThreads = false;
a645023d
A
68
69namespace ld {
70namespace tool {
71
ebf6f434
A
72class IgnoredFile : public ld::File {
73public:
74 IgnoredFile(const char* pth, time_t modTime, Ordinal ord, Type type) : ld::File(pth, modTime, ord, type) {};
75 virtual bool forEachAtom(AtomHandler&) const { return false; };
76 virtual bool justInTimeforEachAtom(const char* name, AtomHandler&) const { return false; };
77};
a645023d
A
78
79
80class DSOHandleAtom : public ld::Atom {
81public:
82 DSOHandleAtom(const char* nm, ld::Atom::Scope sc,
b1f7435d
A
83 ld::Atom::SymbolTableInclusion inc, ld::Section& sect=_s_section)
84 : ld::Atom(sect, ld::Atom::definitionRegular,
85 (sect == _s_section_text) ? ld::Atom::combineByName : ld::Atom::combineNever,
86 // make "weak def" so that link succeeds even if app defines __dso_handle
a645023d
A
87 sc, ld::Atom::typeUnclassified, inc, true, false, false,
88 ld::Atom::Alignment(1)), _name(nm) {}
89
90 virtual ld::File* file() const { return NULL; }
b1f7435d 91 virtual const char* name() const { return _name; }
a645023d
A
92 virtual uint64_t size() const { return 0; }
93 virtual uint64_t objectAddress() const { return 0; }
94 virtual void copyRawContent(uint8_t buffer[]) const
95 { }
96 virtual void setScope(Scope) { }
97
98 virtual ~DSOHandleAtom() {}
99
100 static ld::Section _s_section;
101 static ld::Section _s_section_preload;
b1f7435d 102 static ld::Section _s_section_text;
a645023d
A
103 static DSOHandleAtom _s_atomAll;
104 static DSOHandleAtom _s_atomExecutable;
105 static DSOHandleAtom _s_atomDylib;
106 static DSOHandleAtom _s_atomBundle;
107 static DSOHandleAtom _s_atomDyld;
108 static DSOHandleAtom _s_atomObjectFile;
109 static DSOHandleAtom _s_atomPreload;
b1f7435d 110 static DSOHandleAtom _s_atomPreloadDSO;
a645023d
A
111private:
112 const char* _name;
113};
114ld::Section DSOHandleAtom::_s_section("__TEXT", "__mach_header", ld::Section::typeMachHeader, true);
115ld::Section DSOHandleAtom::_s_section_preload("__HEADER", "__mach_header", ld::Section::typeMachHeader, true);
b1f7435d 116ld::Section DSOHandleAtom::_s_section_text("__TEXT", "__text", ld::Section::typeCode, false);
a645023d
A
117DSOHandleAtom DSOHandleAtom::_s_atomAll("___dso_handle", ld::Atom::scopeLinkageUnit, ld::Atom::symbolTableNotIn);
118DSOHandleAtom DSOHandleAtom::_s_atomExecutable("__mh_execute_header", ld::Atom::scopeGlobal, ld::Atom::symbolTableInAndNeverStrip);
119DSOHandleAtom DSOHandleAtom::_s_atomDylib("__mh_dylib_header", ld::Atom::scopeLinkageUnit, ld::Atom::symbolTableNotIn);
120DSOHandleAtom DSOHandleAtom::_s_atomBundle("__mh_bundle_header", ld::Atom::scopeLinkageUnit, ld::Atom::symbolTableNotIn);
121DSOHandleAtom DSOHandleAtom::_s_atomDyld("__mh_dylinker_header", ld::Atom::scopeLinkageUnit, ld::Atom::symbolTableNotIn);
122DSOHandleAtom DSOHandleAtom::_s_atomObjectFile("__mh_object_header", ld::Atom::scopeLinkageUnit, ld::Atom::symbolTableNotIn);
b1f7435d
A
123DSOHandleAtom DSOHandleAtom::_s_atomPreload("__mh_preload_header", ld::Atom::scopeLinkageUnit, ld::Atom::symbolTableNotIn, _s_section_preload);
124DSOHandleAtom DSOHandleAtom::_s_atomPreloadDSO("___dso_handle", ld::Atom::scopeLinkageUnit, ld::Atom::symbolTableNotIn, _s_section_text);
a645023d
A
125
126
127
128class PageZeroAtom : public ld::Atom {
129public:
130 PageZeroAtom(uint64_t sz)
131 : ld::Atom(_s_section, ld::Atom::definitionRegular, ld::Atom::combineNever,
132 ld::Atom::scopeTranslationUnit, ld::Atom::typeZeroFill,
133 symbolTableNotIn, true, false, false, ld::Atom::Alignment(12)),
134 _size(sz) {}
135
136 virtual ld::File* file() const { return NULL; }
a645023d
A
137 virtual const char* name() const { return "page zero"; }
138 virtual uint64_t size() const { return _size; }
139 virtual uint64_t objectAddress() const { return 0; }
140 virtual void copyRawContent(uint8_t buffer[]) const
141 { }
142 virtual void setScope(Scope) { }
143
144 virtual ~PageZeroAtom() {}
145
146 static ld::Section _s_section;
147 static DSOHandleAtom _s_atomAll;
148private:
149 uint64_t _size;
150};
151ld::Section PageZeroAtom::_s_section("__PAGEZERO", "__pagezero", ld::Section::typePageZero, true);
152
153
154class CustomStackAtom : public ld::Atom {
155public:
156 CustomStackAtom(uint64_t sz)
157 : ld::Atom(_s_section, ld::Atom::definitionRegular, ld::Atom::combineNever,
158 ld::Atom::scopeTranslationUnit, ld::Atom::typeZeroFill,
159 symbolTableNotIn, false, false, false, ld::Atom::Alignment(12)),
160 _size(sz) {}
161
162 virtual ld::File* file() const { return NULL; }
a645023d
A
163 virtual const char* name() const { return "custom stack"; }
164 virtual uint64_t size() const { return _size; }
165 virtual uint64_t objectAddress() const { return 0; }
166 virtual void copyRawContent(uint8_t buffer[]) const
167 { }
168 virtual void setScope(Scope) { }
169
170 virtual ~CustomStackAtom() {}
171
172private:
173 uint64_t _size;
174 static ld::Section _s_section;
175};
176ld::Section CustomStackAtom::_s_section("__UNIXSTACK", "__stack", ld::Section::typeStack, true);
177
178
179
180const char* InputFiles::fileArch(const uint8_t* p, unsigned len)
181{
182 const char* result = mach_o::relocatable::archName(p);
183 if ( result != NULL )
184 return result;
f80fe69f
A
185
186 result = mach_o::dylib::archName(p);
187 if ( result != NULL )
188 return result;
189
a645023d
A
190 result = lto::archName(p, len);
191 if ( result != NULL )
192 return result;
193
194 if ( strncmp((const char*)p, "!<arch>\n", 8) == 0 )
195 return "archive";
196
ebf6f434
A
197 char *unsupported = (char *)malloc(128);
198 strcpy(unsupported, "unsupported file format (");
199 for (unsigned i=0; i<len && i < 16; i++) {
200 char buf[8];
f80fe69f 201 sprintf(buf, " 0x%02X", p[i]);
ebf6f434
A
202 strcat(unsupported, buf);
203 }
204 strcat(unsupported, " )");
205 return unsupported;
a645023d
A
206}
207
208
afe874b1 209ld::File* InputFiles::makeFile(const Options::FileInfo& info, bool indirectDylib)
a645023d
A
210{
211 // map in whole file
212 uint64_t len = info.fileLen;
213 int fd = ::open(info.path, O_RDONLY, 0);
214 if ( fd == -1 )
215 throwf("can't open file, errno=%d", errno);
216 if ( info.fileLen < 20 )
f80fe69f 217 throwf("file too small (length=%llu)", info.fileLen);
a645023d
A
218
219 uint8_t* p = (uint8_t*)::mmap(NULL, info.fileLen, PROT_READ, MAP_FILE | MAP_PRIVATE, fd, 0);
220 if ( p == (uint8_t*)(-1) )
221 throwf("can't map file, errno=%d", errno);
222
223 // if fat file, skip to architecture we want
224 // Note: fat header is always big-endian
225 bool isFatFile = false;
ebf6f434 226 uint32_t sliceToUse, sliceCount;
a645023d
A
227 const fat_header* fh = (fat_header*)p;
228 if ( fh->magic == OSSwapBigToHostInt32(FAT_MAGIC) ) {
229 isFatFile = true;
230 const struct fat_arch* archs = (struct fat_arch*)(p + sizeof(struct fat_header));
a645023d 231 bool sliceFound = false;
ebf6f434 232 sliceCount = OSSwapBigToHostInt32(fh->nfat_arch);
a645023d
A
233 if ( _options.preferSubArchitecture() ) {
234 // first try to find a slice that match cpu-type and cpu-sub-type
ebf6f434 235 for (uint32_t i=0; i < sliceCount; ++i) {
a645023d
A
236 if ( (OSSwapBigToHostInt32(archs[i].cputype) == (uint32_t)_options.architecture())
237 && (OSSwapBigToHostInt32(archs[i].cpusubtype) == (uint32_t)_options.subArchitecture()) ) {
238 sliceToUse = i;
239 sliceFound = true;
240 break;
241 }
242 }
243 }
244 if ( !sliceFound ) {
245 // look for any slice that matches just cpu-type
ebf6f434 246 for (uint32_t i=0; i < sliceCount; ++i) {
a645023d
A
247 if ( OSSwapBigToHostInt32(archs[i].cputype) == (uint32_t)_options.architecture() ) {
248 sliceToUse = i;
249 sliceFound = true;
250 break;
251 }
252 }
253 }
254 if ( sliceFound ) {
255 uint32_t fileOffset = OSSwapBigToHostInt32(archs[sliceToUse].offset);
256 len = OSSwapBigToHostInt32(archs[sliceToUse].size);
257 if ( fileOffset+len > info.fileLen ) {
258 throwf("truncated fat file. Slice from %u to %llu is past end of file with length %llu",
259 fileOffset, fileOffset+len, info.fileLen);
260 }
261 // if requested architecture is page aligned within fat file, then remap just that portion of file
262 if ( (fileOffset & 0x00000FFF) == 0 ) {
263 // unmap whole file
264 munmap((caddr_t)p, info.fileLen);
265 // re-map just part we need
266 p = (uint8_t*)::mmap(NULL, len, PROT_READ, MAP_FILE | MAP_PRIVATE, fd, fileOffset);
267 if ( p == (uint8_t*)(-1) )
268 throwf("can't re-map file, errno=%d", errno);
269 }
270 else {
271 p = &p[fileOffset];
272 }
273 }
274 }
275 ::close(fd);
276
277 // see if it is an object file
278 mach_o::relocatable::ParserOptions objOpts;
279 objOpts.architecture = _options.architecture();
afe874b1 280 objOpts.objSubtypeMustMatch = !_options.allowSubArchitectureMismatches();
a645023d 281 objOpts.logAllFiles = _options.logAllFiles();
f80fe69f
A
282 objOpts.warnUnwindConversionProblems = _options.needsUnwindInfoSection();
283 objOpts.keepDwarfUnwind = _options.keepDwarfUnwind();
284 objOpts.forceDwarfConversion= (_options.outputKind() == Options::kDyld);
9543cb2f
A
285 objOpts.neverConvertDwarf = !_options.needsUnwindInfoSection();
286 objOpts.verboseOptimizationHints = _options.verboseOptimizationHints();
a645023d 287 objOpts.subType = _options.subArchitecture();
ebf6f434
A
288 ld::relocatable::File* objResult = mach_o::relocatable::parse(p, len, info.path, info.modTime, info.ordinal, objOpts);
289 if ( objResult != NULL ) {
290 OSAtomicAdd64(len, &_totalObjectSize);
291 OSAtomicIncrement32(&_totalObjectLoaded);
292 return objResult;
293 }
a645023d
A
294
295 // see if it is an llvm object file
9543cb2f 296 objResult = lto::parse(p, len, info.path, info.modTime, info.ordinal, _options.architecture(), _options.subArchitecture(), _options.logAllFiles(), _options.verboseOptimizationHints());
ebf6f434
A
297 if ( objResult != NULL ) {
298 OSAtomicAdd64(len, &_totalObjectSize);
299 OSAtomicIncrement32(&_totalObjectLoaded);
300 return objResult;
301 }
302
a645023d 303 // see if it is a dynamic library
ebf6f434
A
304 ld::dylib::File* dylibResult = mach_o::dylib::parse(p, len, info.path, info.modTime, _options, info.ordinal, info.options.fBundleLoader, indirectDylib);
305 if ( dylibResult != NULL ) {
306 return dylibResult;
307 }
a645023d
A
308
309 // see if it is a static library
afe874b1 310 ::archive::ParserOptions archOpts;
a645023d
A
311 archOpts.objOpts = objOpts;
312 archOpts.forceLoadThisArchive = info.options.fForceLoad;
313 archOpts.forceLoadAll = _options.fullyLoadArchives();
314 archOpts.forceLoadObjC = _options.loadAllObjcObjectsFromArchives();
afe874b1 315 archOpts.objcABI2 = _options.objCABIVersion2POverride();
a645023d
A
316 archOpts.verboseLoad = _options.whyLoad();
317 archOpts.logAllFiles = _options.logAllFiles();
ebf6f434 318 ld::archive::File* archiveResult = ::archive::parse(p, len, info.path, info.modTime, info.ordinal, archOpts);
afe874b1 319 if ( archiveResult != NULL ) {
ebf6f434
A
320 OSAtomicAdd64(len, &_totalArchiveSize);
321 OSAtomicIncrement32(&_totalArchivesLoaded);
322 return archiveResult;
afe874b1
A
323 }
324
a645023d
A
325 // does not seem to be any valid linker input file, check LTO misconfiguration problems
326 if ( lto::archName((uint8_t*)p, len) != NULL ) {
327 if ( lto::libLTOisLoaded() ) {
ebf6f434 328 throwf("lto file was built for %s which is not the architecture being linked (%s): %s", fileArch(p, len), _options.architectureName(), info.path);
a645023d
A
329 }
330 else {
331 const char* libLTO = "libLTO.dylib";
332 char ldPath[PATH_MAX];
333 char tmpPath[PATH_MAX];
334 char libLTOPath[PATH_MAX];
335 uint32_t bufSize = PATH_MAX;
ebf6f434
A
336 if ( _options.overridePathlibLTO() != NULL ) {
337 libLTO = _options.overridePathlibLTO();
338 }
339 else if ( _NSGetExecutablePath(ldPath, &bufSize) != -1 ) {
a645023d
A
340 if ( realpath(ldPath, tmpPath) != NULL ) {
341 char* lastSlash = strrchr(tmpPath, '/');
342 if ( lastSlash != NULL )
343 strcpy(lastSlash, "/../lib/libLTO.dylib");
344 libLTO = tmpPath;
345 if ( realpath(tmpPath, libLTOPath) != NULL )
346 libLTO = libLTOPath;
347 }
348 }
349 throwf("could not process llvm bitcode object file, because %s could not be loaded", libLTO);
350 }
351 }
352
353 // error handling
354 if ( ((fat_header*)p)->magic == OSSwapBigToHostInt32(FAT_MAGIC) ) {
ebf6f434 355 throwf("missing required architecture %s in file %s (%u slices)", _options.architectureName(), info.path, sliceCount);
a645023d
A
356 }
357 else {
358 if ( isFatFile )
ebf6f434 359 throwf("file is universal (%u slices) but does not contain a(n) %s slice: %s", sliceCount, _options.architectureName(), info.path);
a645023d 360 else
ebf6f434 361 throwf("file was built for %s which is not the architecture being linked (%s): %s", fileArch(p, len), _options.architectureName(), info.path);
a645023d
A
362 }
363}
364
365void InputFiles::logDylib(ld::File* file, bool indirect)
366{
367 if ( _options.traceDylibs() ) {
368 const char* fullPath = file->path();
369 char realName[MAXPATHLEN];
370 if ( realpath(fullPath, realName) != NULL )
371 fullPath = realName;
372 const ld::dylib::File* dylib = dynamic_cast<const ld::dylib::File*>(file);
373 if ( (dylib != NULL ) && dylib->willBeUpwardDylib() ) {
374 // don't log upward dylibs when XBS is computing dependencies
375 logTraceInfo("[Logging for XBS] Used upward dynamic library: %s\n", fullPath);
376 }
377 else {
f80fe69f 378 if ( indirect )
a645023d 379 logTraceInfo("[Logging for XBS] Used indirect dynamic library: %s\n", fullPath);
f80fe69f 380 else
a645023d
A
381 logTraceInfo("[Logging for XBS] Used dynamic library: %s\n", fullPath);
382 }
383 }
f80fe69f
A
384
385 if ( _options.dumpDependencyInfo() ) {
386 const ld::dylib::File* dylib = dynamic_cast<const ld::dylib::File*>(file);
387 if ( file == _bundleLoader ) {
388 _options.dumpDependency(Options::depBundleLoader, file->path());
389 }
390 else if ( (dylib != NULL ) && dylib->willBeUpwardDylib() ) {
391 if ( indirect )
392 _options.dumpDependency(Options::depUpwardIndirectDylib, file->path());
393 else
394 _options.dumpDependency(Options::depUpwardDirectDylib, file->path());
395 }
396 else {
397 if ( indirect )
398 _options.dumpDependency(Options::depIndirectDylib, file->path());
399 else
400 _options.dumpDependency(Options::depDirectDylib, file->path());
401 }
402 }
a645023d
A
403}
404
405void InputFiles::logArchive(ld::File* file) const
406{
407 if ( _options.traceArchives() && (_archiveFilesLogged.count(file) == 0) ) {
408 // <rdar://problem/4947347> LD_TRACE_ARCHIVES should only print out when a .o is actually used from an archive
409 _archiveFilesLogged.insert(file);
410 const char* fullPath = file->path();
411 char realName[MAXPATHLEN];
412 if ( realpath(fullPath, realName) != NULL )
413 fullPath = realName;
414 logTraceInfo("[Logging for XBS] Used static archive: %s\n", fullPath);
415 }
416}
417
418
419void InputFiles::logTraceInfo(const char* format, ...) const
420{
421 // one time open() of custom LD_TRACE_FILE
422 static int trace_file = -1;
423 if ( trace_file == -1 ) {
424 const char *trace_file_path = _options.traceOutputFile();
425 if ( trace_file_path != NULL ) {
426 trace_file = open(trace_file_path, O_WRONLY | O_APPEND | O_CREAT, 0666);
427 if ( trace_file == -1 )
f80fe69f 428 throwf("Could not open or create trace file (errno=%d): %s", errno, trace_file_path);
a645023d
A
429 }
430 else {
431 trace_file = fileno(stderr);
432 }
433 }
434
435 char trace_buffer[MAXPATHLEN * 2];
436 va_list ap;
437 va_start(ap, format);
438 int length = vsnprintf(trace_buffer, sizeof(trace_buffer), format, ap);
439 va_end(ap);
440 char* buffer_ptr = trace_buffer;
441
442 while (length > 0) {
443 ssize_t amount_written = write(trace_file, buffer_ptr, length);
444 if(amount_written == -1)
445 /* Failure to write shouldn't fail the build. */
446 return;
447 buffer_ptr += amount_written;
448 length -= amount_written;
449 }
450}
451
f80fe69f 452
a645023d
A
453ld::dylib::File* InputFiles::findDylib(const char* installPath, const char* fromPath)
454{
455 //fprintf(stderr, "findDylib(%s, %s)\n", installPath, fromPath);
456 InstallNameToDylib::iterator pos = _installPathToDylibs.find(installPath);
457 if ( pos != _installPathToDylibs.end() ) {
458 return pos->second;
459 }
460 else {
461 // allow -dylib_path option to override indirect library to use
462 for (std::vector<Options::DylibOverride>::const_iterator dit = _options.dylibOverrides().begin(); dit != _options.dylibOverrides().end(); ++dit) {
463 if ( strcmp(dit->installName,installPath) == 0 ) {
464 try {
465 Options::FileInfo info = _options.findFile(dit->useInstead);
ebf6f434
A
466 _indirectDylibOrdinal = _indirectDylibOrdinal.nextIndirectDylibOrdinal();
467 info.ordinal = _indirectDylibOrdinal;
f80fe69f 468 info.options.fIndirectDylib = true;
afe874b1 469 ld::File* reader = this->makeFile(info, true);
a645023d
A
470 ld::dylib::File* dylibReader = dynamic_cast<ld::dylib::File*>(reader);
471 if ( dylibReader != NULL ) {
ebf6f434 472 addDylib(dylibReader, info);
a645023d
A
473 //_installPathToDylibs[strdup(installPath)] = dylibReader;
474 this->logDylib(dylibReader, true);
475 return dylibReader;
476 }
477 else
478 throwf("indirect dylib at %s is not a dylib", dit->useInstead);
479 }
480 catch (const char* msg) {
481 warning("ignoring -dylib_file option, %s", msg);
482 }
483 }
484 }
485 char newPath[MAXPATHLEN];
486 // handle @loader_path
487 if ( strncmp(installPath, "@loader_path/", 13) == 0 ) {
488 strcpy(newPath, fromPath);
489 char* addPoint = strrchr(newPath,'/');
490 if ( addPoint != NULL )
491 strcpy(&addPoint[1], &installPath[13]);
492 else
493 strcpy(newPath, &installPath[13]);
494 installPath = newPath;
495 }
496 // note: @executable_path case is handled inside findFileUsingPaths()
497 // search for dylib using -F and -L paths
498 Options::FileInfo info = _options.findFileUsingPaths(installPath);
ebf6f434
A
499 _indirectDylibOrdinal = _indirectDylibOrdinal.nextIndirectDylibOrdinal();
500 info.ordinal = _indirectDylibOrdinal;
f80fe69f 501 info.options.fIndirectDylib = true;
a645023d 502 try {
afe874b1 503 ld::File* reader = this->makeFile(info, true);
a645023d
A
504 ld::dylib::File* dylibReader = dynamic_cast<ld::dylib::File*>(reader);
505 if ( dylibReader != NULL ) {
506 //assert(_installPathToDylibs.find(installPath) != _installPathToDylibs.end());
507 //_installPathToDylibs[strdup(installPath)] = dylibReader;
ebf6f434 508 addDylib(dylibReader, info);
a645023d
A
509 this->logDylib(dylibReader, true);
510 return dylibReader;
511 }
512 else
513 throwf("indirect dylib at %s is not a dylib", info.path);
514 }
515 catch (const char* msg) {
d425e388 516 throwf("in '%s', %s", info.path, msg);
a645023d
A
517 }
518 }
519}
520
521
f80fe69f
A
522// mark all dylibs initially specified as required, and check if they can be used
523void InputFiles::markExplicitlyLinkedDylibs()
524{
a645023d
A
525 for (InstallNameToDylib::iterator it=_installPathToDylibs.begin(); it != _installPathToDylibs.end(); it++) {
526 it->second->setExplicitlyLinked();
527 this->checkDylibClientRestrictions(it->second);
528 }
f80fe69f
A
529}
530
531bool InputFiles::libraryAlreadyLoaded(const char* path)
532{
533 for (std::vector<ld::File*>::const_iterator it = _inputFiles.begin(); it != _inputFiles.end(); ++it) {
534 if ( strcmp(path, (*it)->path()) == 0 )
535 return true;
536 }
537 return false;
538}
539
540
541void InputFiles::addLinkerOptionLibraries(ld::Internal& state)
542{
543 if ( _options.outputKind() == Options::kObjectFile )
544 return;
545
546 // process frameworks specified in .o linker options
547 for (CStringSet::const_iterator it = state.linkerOptionFrameworks.begin(); it != state.linkerOptionFrameworks.end(); ++it) {
548 const char* frameworkName = *it;
549 Options::FileInfo info = _options.findFramework(frameworkName);
550 if ( ! this->libraryAlreadyLoaded(info.path) ) {
551 info.ordinal = _linkerOptionOrdinal.nextLinkerOptionOrdinal();
552 try {
553 ld::File* reader = this->makeFile(info, true);
554 ld::dylib::File* dylibReader = dynamic_cast<ld::dylib::File*>(reader);
555 if ( dylibReader != NULL ) {
556 if ( ! dylibReader->installPathVersionSpecific() ) {
557 dylibReader->setImplicitlyLinked();
558 this->addDylib(dylibReader, info);
559 }
560 }
561 else {
562 throwf("framework linker option at %s is not a dylib", info.path);
563 }
564 }
565 catch (const char* msg) {
9543cb2f 566 warning("Auto-Linking supplied '%s', %s", info.path, msg);
f80fe69f
A
567 }
568 }
569 }
570 // process libraries specified in .o linker options
571 for (CStringSet::const_iterator it = state.linkerOptionLibraries.begin(); it != state.linkerOptionLibraries.end(); ++it) {
572 const char* libName = *it;
573 Options::FileInfo info = _options.findLibrary(libName);
574 if ( ! this->libraryAlreadyLoaded(info.path) ) {
575 info.ordinal = _linkerOptionOrdinal.nextLinkerOptionOrdinal();
576 try {
577 ld::File* reader = this->makeFile(info, true);
578 ld::dylib::File* dylibReader = dynamic_cast<ld::dylib::File*>(reader);
579 ld::archive::File* archiveReader = dynamic_cast<ld::archive::File*>(reader);
580 if ( dylibReader != NULL ) {
581 dylibReader->setImplicitlyLinked();
582 this->addDylib(dylibReader, info);
583 }
584 else if ( archiveReader != NULL ) {
585 _searchLibraries.push_back(LibraryInfo(archiveReader));
586 if ( _options.dumpDependencyInfo() )
587 _options.dumpDependency(Options::depArchive, archiveReader->path());
588 }
589 else {
590 throwf("linker option dylib at %s is not a dylib", info.path);
591 }
592 }
593 catch (const char* msg) {
9543cb2f 594 warning("Auto-Linking supplied '%s', %s", info.path, msg);
f80fe69f
A
595 }
596 }
597 }
598}
599
600void InputFiles::createIndirectDylibs()
601{
a645023d
A
602 // keep processing dylibs until no more dylibs are added
603 unsigned long lastMapSize = 0;
afe874b1 604 std::set<ld::dylib::File*> dylibsProcessed;
a645023d
A
605 while ( lastMapSize != _allDylibs.size() ) {
606 lastMapSize = _allDylibs.size();
607 // can't iterator _installPathToDylibs while modifying it, so use temp buffer
608 std::vector<ld::dylib::File*> unprocessedDylibs;
609 for (std::set<ld::dylib::File*>::iterator it=_allDylibs.begin(); it != _allDylibs.end(); it++) {
610 if ( dylibsProcessed.count(*it) == 0 )
611 unprocessedDylibs.push_back(*it);
612 }
613 for (std::vector<ld::dylib::File*>::iterator it=unprocessedDylibs.begin(); it != unprocessedDylibs.end(); it++) {
614 dylibsProcessed.insert(*it);
615 (*it)->processIndirectLibraries(this, _options.implicitlyLinkIndirectPublicDylibs());
616 }
617 }
618
619 // go back over original dylibs and mark sub frameworks as re-exported
620 if ( _options.outputKind() == Options::kDynamicLibrary ) {
621 const char* myLeaf = strrchr(_options.installPath(), '/');
622 if ( myLeaf != NULL ) {
623 for (std::vector<class ld::File*>::const_iterator it=_inputFiles.begin(); it != _inputFiles.end(); it++) {
624 ld::dylib::File* dylibReader = dynamic_cast<ld::dylib::File*>(*it);
625 if ( dylibReader != NULL ) {
626 const char* childParent = dylibReader->parentUmbrella();
627 if ( childParent != NULL ) {
628 if ( strcmp(childParent, &myLeaf[1]) == 0 ) {
629 // mark that this dylib will be re-exported
630 dylibReader->setWillBeReExported();
631 }
632 }
633 }
634 }
635 }
636 }
637
638}
639
640void InputFiles::createOpaqueFileSections()
641{
f80fe69f 642 // extra command line sections always at end
a645023d 643 for (Options::ExtraSection::const_iterator it=_options.extraSectionsBegin(); it != _options.extraSectionsEnd(); ++it) {
ebf6f434 644 _inputFiles.push_back(opaque_section::parse(it->segmentName, it->sectionName, it->path, it->data, it->dataLen));
f80fe69f
A
645 if ( _options.dumpDependencyInfo() )
646 _options.dumpDependency(Options::depSection, it->path);
a645023d
A
647 }
648
649}
650
651
652void InputFiles::checkDylibClientRestrictions(ld::dylib::File* dylib)
653{
654 // Check for any restrictions on who can link with this dylib
655 const char* dylibParentName = dylib->parentUmbrella() ;
656 const std::vector<const char*>* clients = dylib->allowableClients();
657 if ( (dylibParentName != NULL) || (clients != NULL) ) {
658 // only dylibs that are in an umbrella or have a client list need verification
659 const char* installName = _options.installPath();
660 const char* installNameLastSlash = strrchr(installName, '/');
661 bool isParent = false;
662 bool isSibling = false;
663 bool isAllowableClient = false;
664 // There are three cases:
665 if ( (dylibParentName != NULL) && (installNameLastSlash != NULL) ) {
666 // starts after last slash
667 const char* myName = &installNameLastSlash[1];
668 unsigned int myNameLen = strlen(myName);
669 if ( strncmp(myName, "lib", 3) == 0 )
670 myName = &myName[3];
671 // up to first dot
672 const char* firstDot = strchr(myName, '.');
673 if ( firstDot != NULL )
674 myNameLen = firstDot - myName;
675 // up to first underscore
676 const char* firstUnderscore = strchr(myName, '_');
677 if ( (firstUnderscore != NULL) && ((firstUnderscore - myName) < (int)myNameLen) )
678 myNameLen = firstUnderscore - myName;
679
680 // case 1) The dylib has a parent umbrella, and we are creating the parent umbrella
681 isParent = ( (strlen(dylibParentName) == myNameLen) && (strncmp(myName, dylibParentName, myNameLen) == 0) );
682
683 // case 2) The dylib has a parent umbrella, and we are creating a sibling with the same parent
684 isSibling = ( (_options.umbrellaName() != NULL) && (strcmp(_options.umbrellaName(), dylibParentName) == 0) );
685 }
686
687 if ( !isParent && !isSibling && (clients != NULL) ) {
688 // case 3) the dylib has a list of allowable clients, and we are creating one of them
689 const char* clientName = _options.clientName();
690 int clientNameLen = 0;
691 if ( clientName != NULL ) {
692 // use client name as specified on command line
693 clientNameLen = strlen(clientName);
694 }
695 else {
696 // infer client name from output path (e.g. xxx/libfoo_variant.A.dylib --> foo, Bar.framework/Bar_variant --> Bar)
697 clientName = installName;
698 clientNameLen = strlen(clientName);
699 // starts after last slash
700 if ( installNameLastSlash != NULL )
701 clientName = &installNameLastSlash[1];
702 if ( strncmp(clientName, "lib", 3) == 0 )
703 clientName = &clientName[3];
704 // up to first dot
705 const char* firstDot = strchr(clientName, '.');
706 if ( firstDot != NULL )
707 clientNameLen = firstDot - clientName;
708 // up to first underscore
709 const char* firstUnderscore = strchr(clientName, '_');
710 if ( (firstUnderscore != NULL) && ((firstUnderscore - clientName) < clientNameLen) )
711 clientNameLen = firstUnderscore - clientName;
712 }
713
714 // Use clientName to check if this dylib is able to link against the allowable clients.
715 for (std::vector<const char*>::const_iterator it = clients->begin(); it != clients->end(); it++) {
716 if ( strncmp(*it, clientName, clientNameLen) == 0 )
717 isAllowableClient = true;
718 }
719 }
720
721 if ( !isParent && !isSibling && !isAllowableClient ) {
722 if ( dylibParentName != NULL ) {
723 throwf("cannot link directly with %s. Link against the umbrella framework '%s.framework' instead.",
724 dylib->path(), dylibParentName);
725 }
726 else {
727 throwf("cannot link directly with %s", dylib->path());
728 }
729 }
730 }
731}
732
733
734void InputFiles::inferArchitecture(Options& opts, const char** archName)
735{
736 _inferredArch = true;
737 // scan all input files, looking for a thin .o file.
738 // the first one found is presumably the architecture to link
739 uint8_t buffer[sizeof(mach_header_64)];
740 const std::vector<Options::FileInfo>& files = opts.getInputFiles();
741 for (std::vector<Options::FileInfo>::const_iterator it = files.begin(); it != files.end(); ++it) {
742 int fd = ::open(it->path, O_RDONLY, 0);
743 if ( fd != -1 ) {
744 ssize_t amount = read(fd, buffer, sizeof(buffer));
745 ::close(fd);
746 if ( amount >= (ssize_t)sizeof(buffer) ) {
747 cpu_type_t type;
748 cpu_subtype_t subtype;
749 if ( mach_o::relocatable::isObjectFile(buffer, &type, &subtype) ) {
750 opts.setArchitecture(type, subtype);
751 *archName = opts.architectureName();
752 return;
753 }
754 }
755 }
756 }
757
758 // no thin .o files found, so default to same architecture this tool was built as
759 warning("-arch not specified");
b2fa67a8 760#if __i386__
a645023d 761 opts.setArchitecture(CPU_TYPE_I386, CPU_SUBTYPE_X86_ALL);
a645023d
A
762#elif __x86_64__
763 opts.setArchitecture(CPU_TYPE_X86_64, CPU_SUBTYPE_X86_64_ALL);
764#elif __arm__
765 opts.setArchitecture(CPU_TYPE_ARM, CPU_SUBTYPE_ARM_V6);
766#else
767 #error unknown default architecture
768#endif
769 *archName = opts.architectureName();
770}
771
772
773InputFiles::InputFiles(Options& opts, const char** archName)
774 : _totalObjectSize(0), _totalArchiveSize(0),
775 _totalObjectLoaded(0), _totalArchivesLoaded(0), _totalDylibsLoaded(0),
ebf6f434 776 _options(opts), _bundleLoader(NULL),
f80fe69f
A
777 _inferredArch(false),
778 _exception(NULL),
779 _indirectDylibOrdinal(ld::File::Ordinal::indirectDylibBase()),
780 _linkerOptionOrdinal(ld::File::Ordinal::linkeOptionBase())
a645023d
A
781{
782// fStartCreateReadersTime = mach_absolute_time();
783 if ( opts.architecture() == 0 ) {
784 // command line missing -arch, so guess arch
785 inferArchitecture(opts, archName);
786 }
ebf6f434
A
787#if HAVE_PTHREADS
788 pthread_mutex_init(&_parseLock, NULL);
789 pthread_cond_init(&_parseWorkReady, NULL);
790 pthread_cond_init(&_newFileAvailable, NULL);
791#endif
792 const std::vector<Options::FileInfo>& files = _options.getInputFiles();
a645023d
A
793 if ( files.size() == 0 )
794 throw "no object files specified";
ebf6f434 795
a645023d 796 _inputFiles.reserve(files.size());
ebf6f434
A
797#if HAVE_PTHREADS
798 unsigned int inputFileSlot = 0;
799 _availableInputFiles = 0;
800 _parseCursor = 0;
801#endif
802 Options::FileInfo* entry;
a645023d 803 for (std::vector<Options::FileInfo>::const_iterator it = files.begin(); it != files.end(); ++it) {
ebf6f434
A
804 entry = (Options::FileInfo*)&(*it);
805#if HAVE_PTHREADS
806 // Assign input file slots to all the FileInfos.
807 // Also chain all FileInfos into one big list to set up for worker threads to do parsing.
808 entry->inputFileSlot = inputFileSlot;
809 entry->readyToParse = !entry->fromFileList || !_options.pipelineEnabled();
810 if (entry->readyToParse)
811 _availableInputFiles++;
812 _inputFiles.push_back(NULL);
813 inputFileSlot++;
814#else
815 // In the non-threaded case just parse the file now.
816 _inputFiles.push_back(makeFile(*entry, false));
817#endif
818 }
819
820#if HAVE_PTHREADS
821 _remainingInputFiles = files.size();
822
823 // initialize info for parsing input files on worker threads
824 unsigned int ncpus;
825 int mib[2];
826 size_t len = sizeof(ncpus);
827 mib[0] = CTL_HW;
828 mib[1] = HW_NCPU;
829 if (sysctl(mib, 2, &ncpus, &len, NULL, 0) != 0) {
830 ncpus = 1;
831 }
832 _availableWorkers = MIN(ncpus, files.size()); // max # workers we permit
833 _idleWorkers = 0;
834
835 if (_options.pipelineEnabled()) {
836 // start up a thread to listen for available input files
837 startThread(InputFiles::waitForInputFiles);
a645023d
A
838 }
839
ebf6f434
A
840 // Start up one parser thread. More start on demand as parsed input files get consumed.
841 startThread(InputFiles::parseWorkerThread);
842 _availableWorkers--;
843#else
844 if (_options.pipelineEnabled()) {
845 throwf("pipelined linking not supported on this platform");
846 }
847#endif
a645023d
A
848}
849
850
ebf6f434
A
851#if HAVE_PTHREADS
852void InputFiles::startThread(void (*threadFunc)(InputFiles *)) const {
853 pthread_t thread;
854 pthread_attr_t attr;
855 pthread_attr_init(&attr);
856 // set a nice big stack (same as main thread) because some code uses potentially large stack buffers
857 pthread_attr_setstacksize(&attr, 8 * 1024 * 1024);
858 pthread_create(&thread, &attr, (void *(*)(void*))threadFunc, (void *)this);
859 pthread_detach(thread);
860 pthread_attr_destroy(&attr);
a645023d
A
861}
862
ebf6f434
A
863// Work loop for input file parsing threads
864void InputFiles::parseWorkerThread() {
865 ld::File *file;
866 const char *exception = NULL;
867 pthread_mutex_lock(&_parseLock);
868 const std::vector<Options::FileInfo>& files = _options.getInputFiles();
869 if (_s_logPThreads) printf("worker starting\n");
870 do {
871 if (_availableInputFiles == 0) {
872 _idleWorkers++;
873 pthread_cond_wait(&_parseWorkReady, &_parseLock);
874 _idleWorkers--;
875 } else {
876 int slot = _parseCursor;
877 while (slot < (int)files.size() && (_inputFiles[slot] != NULL || !files[slot].readyToParse))
878 slot++;
879 assert(slot < (int)files.size());
880 Options::FileInfo& entry = (Options::FileInfo&)files[slot];
881 _parseCursor = slot+1;
882 _availableInputFiles--;
883 entry.readyToParse = false; // to avoid multiple threads finding this file
884 pthread_mutex_unlock(&_parseLock);
885 if (_s_logPThreads) printf("parsing index %u\n", slot);
886 try {
887 file = makeFile(entry, false);
f80fe69f
A
888 }
889 catch (const char *msg) {
ebf6f434
A
890 if ( (strstr(msg, "architecture") != NULL) && !_options.errorOnOtherArchFiles() ) {
891 if ( _options.ignoreOtherArchInputFiles() ) {
892 // ignore, because this is about an architecture not in use
893 }
894 else {
895 warning("ignoring file %s, %s", entry.path, msg);
896 }
f80fe69f
A
897 }
898 else {
899 asprintf((char**)&exception, "%s file '%s'", msg, entry.path);
ebf6f434
A
900 }
901 file = new IgnoredFile(entry.path, entry.modTime, entry.ordinal, ld::File::Other);
902 }
903 pthread_mutex_lock(&_parseLock);
904 if (_remainingInputFiles > 0)
905 _remainingInputFiles--;
906 if (_s_logPThreads) printf("done with index %u, %d remaining\n", slot, _remainingInputFiles);
907 if (exception) {
908 // We are about to die, so set to zero to stop other threads from doing unneeded work.
909 _remainingInputFiles = 0;
910 _exception = exception;
f80fe69f
A
911 }
912 else {
ebf6f434
A
913 _inputFiles[slot] = file;
914 if (_neededFileSlot == slot)
915 pthread_cond_signal(&_newFileAvailable);
916 }
917 }
918 } while (_remainingInputFiles);
919 if (_s_logPThreads) printf("worker exiting\n");
920 pthread_cond_broadcast(&_parseWorkReady);
921 pthread_cond_signal(&_newFileAvailable);
922 pthread_mutex_unlock(&_parseLock);
923}
a645023d 924
a645023d 925
ebf6f434
A
926void InputFiles::parseWorkerThread(InputFiles *inputFiles) {
927 inputFiles->parseWorkerThread();
a645023d 928}
ebf6f434 929#endif
a645023d
A
930
931
ebf6f434 932ld::File* InputFiles::addDylib(ld::dylib::File* reader, const Options::FileInfo& info)
a645023d
A
933{
934 _allDylibs.insert(reader);
935
936 if ( (reader->installPath() == NULL) && !info.options.fBundleLoader ) {
937 // this is a "blank" stub
938 // silently ignore it
939 return reader;
940 }
941 // store options about how dylib will be used in dylib itself
942 if ( info.options.fWeakImport )
afe874b1 943 reader->setForcedWeakLinked();
a645023d
A
944 if ( info.options.fReExport )
945 reader->setWillBeReExported();
946 if ( info.options.fUpward ) {
947 if ( _options.outputKind() == Options::kDynamicLibrary )
948 reader->setWillBeUpwardDylib();
949 else
950 warning("ignoring upward dylib option for %s\n", info.path);
951 }
952 if ( info.options.fLazyLoad )
953 reader->setWillBeLazyLoadedDylb();
954
955 // add to map of loaded dylibs
956 const char* installPath = reader->installPath();
957 if ( installPath != NULL ) {
958 InstallNameToDylib::iterator pos = _installPathToDylibs.find(installPath);
959 if ( pos == _installPathToDylibs.end() ) {
960 _installPathToDylibs[strdup(installPath)] = reader;
961 }
962 else {
963 bool dylibOnCommandLineTwice = ( strcmp(pos->second->path(), reader->path()) == 0 );
964 bool isSymlink = false;
965 // ignore if this is a symlink to a dylib we've already loaded
966 if ( !dylibOnCommandLineTwice ) {
967 char existingDylibPath[PATH_MAX];
968 if ( realpath(pos->second->path(), existingDylibPath) != NULL ) {
969 char newDylibPath[PATH_MAX];
970 if ( realpath(reader->path(), newDylibPath) != NULL ) {
971 isSymlink = ( strcmp(existingDylibPath, newDylibPath) == 0 );
972 }
973 }
974 }
ebf6f434
A
975 // remove warning for <rdar://problem/10860629> Same install name for CoreServices and CFNetwork?
976 //if ( !dylibOnCommandLineTwice && !isSymlink )
f80fe69f 977 // warning("dylibs with same install name: %p %s and %p %s", pos->second, pos->second->path(), reader, reader->path());
a645023d
A
978 }
979 }
980 else if ( info.options.fBundleLoader )
981 _bundleLoader = reader;
982
983 // log direct readers
f80fe69f 984 if ( ! info.options.fIndirectDylib )
a645023d
A
985 this->logDylib(reader, false);
986
a645023d
A
987 // update stats
988 _totalDylibsLoaded++;
989
d425e388 990 // just add direct libraries to search-first list
f80fe69f 991 if ( ! info.options.fIndirectDylib )
d425e388 992 _searchLibraries.push_back(LibraryInfo(reader));
f80fe69f 993
a645023d
A
994 return reader;
995}
996
997
ebf6f434
A
998#if HAVE_PTHREADS
999// Called during pipelined linking to listen for available input files.
1000// Available files are enqueued for parsing.
1001void InputFiles::waitForInputFiles()
a645023d 1002{
ebf6f434
A
1003 if (_s_logPThreads) printf("starting pipeline listener\n");
1004 try {
1005 const char *fifo = _options.pipelineFifo();
1006 assert(fifo);
1007 std::map<const char *, const Options::FileInfo*, strcompclass> fileMap;
1008 const std::vector<Options::FileInfo>& files = _options.getInputFiles();
1009 for (std::vector<Options::FileInfo>::const_iterator it = files.begin(); it != files.end(); ++it) {
1010 const Options::FileInfo& entry = *it;
1011 if (entry.fromFileList) {
1012 fileMap[entry.path] = &entry;
1013 }
1014 }
1015 FILE *fileStream = fopen(fifo, "r");
1016 if (!fileStream)
1017 throwf("pipelined linking error - failed to open stream. fopen() returns %s for \"%s\"\n", strerror(errno), fifo);
1018 while (fileMap.size() > 0) {
1019 char path_buf[PATH_MAX+1];
1020 if (fgets(path_buf, PATH_MAX, fileStream) == NULL)
1021 throwf("pipelined linking error - %lu missing input files", fileMap.size());
1022 int len = strlen(path_buf);
1023 if (path_buf[len-1] == '\n')
1024 path_buf[len-1] = 0;
1025 std::map<const char *, const Options::FileInfo*, strcompclass>::iterator it = fileMap.find(path_buf);
1026 if (it == fileMap.end())
1027 throwf("pipelined linking error - not in file list: %s\n", path_buf);
1028 Options::FileInfo* inputInfo = (Options::FileInfo*)it->second;
f80fe69f 1029 if (!inputInfo->checkFileExists(_options))
ebf6f434
A
1030 throwf("pipelined linking error - file does not exist: %s\n", inputInfo->path);
1031 pthread_mutex_lock(&_parseLock);
1032 if (_idleWorkers)
1033 pthread_cond_signal(&_parseWorkReady);
1034 inputInfo->readyToParse = true;
1035 if (_parseCursor > inputInfo->inputFileSlot)
1036 _parseCursor = inputInfo->inputFileSlot;
1037 _availableInputFiles++;
1038 if (_s_logPThreads) printf("pipeline listener: %s slot=%d, _parseCursor=%d, _availableInputFiles = %d remaining = %ld\n", path_buf, inputInfo->inputFileSlot, _parseCursor, _availableInputFiles, fileMap.size()-1);
1039 pthread_mutex_unlock(&_parseLock);
1040 fileMap.erase(it);
a645023d 1041 }
ebf6f434
A
1042 } catch (const char *msg) {
1043 pthread_mutex_lock(&_parseLock);
1044 _exception = msg;
1045 pthread_cond_signal(&_newFileAvailable);
1046 pthread_mutex_unlock(&_parseLock);
a645023d 1047 }
a645023d
A
1048}
1049
1050
ebf6f434
A
1051void InputFiles::waitForInputFiles(InputFiles *inputFiles) {
1052 inputFiles->waitForInputFiles();
1053}
1054#endif
1055
1056
f80fe69f 1057void InputFiles::forEachInitialAtom(ld::File::AtomHandler& handler, ld::Internal& state)
a645023d 1058{
ebf6f434
A
1059 // add all direct object, archives, and dylibs
1060 const std::vector<Options::FileInfo>& files = _options.getInputFiles();
1061 size_t fileIndex;
1062 for (fileIndex=0; fileIndex<_inputFiles.size(); fileIndex++) {
1063 ld::File *file;
1064#if HAVE_PTHREADS
1065 pthread_mutex_lock(&_parseLock);
1066
1067 // this loop waits for the needed file to be ready (parsed by worker thread)
1068 while (_inputFiles[fileIndex] == NULL && _exception == NULL) {
1069 // We are starved for input. If there are still files to parse and we have
1070 // not maxed out the worker thread count start a new worker thread.
1071 if (_availableInputFiles > 0 && _availableWorkers > 0) {
1072 if (_s_logPThreads) printf("starting worker\n");
1073 startThread(InputFiles::parseWorkerThread);
1074 _availableWorkers--;
a645023d 1075 }
ebf6f434
A
1076 _neededFileSlot = fileIndex;
1077 if (_s_logPThreads) printf("consumer blocking for %lu: %s\n", fileIndex, files[fileIndex].path);
1078 pthread_cond_wait(&_newFileAvailable, &_parseLock);
a645023d 1079 }
ebf6f434
A
1080
1081 if (_exception)
1082 throw _exception;
1083
1084 // The input file is parsed. Assimilate it and call its atom iterator.
1085 if (_s_logPThreads) printf("consuming slot %lu\n", fileIndex);
1086 file = _inputFiles[fileIndex];
1087 pthread_mutex_unlock(&_parseLock);
1088#else
1089 file = _inputFiles[fileIndex];
1090#endif
1091 const Options::FileInfo& info = files[fileIndex];
1092 switch (file->type()) {
1093 case ld::File::Reloc:
1094 {
1095 ld::relocatable::File* reloc = (ld::relocatable::File*)file;
1096 _options.snapshot().recordObjectFile(reloc->path());
f80fe69f
A
1097 if ( _options.dumpDependencyInfo() )
1098 _options.dumpDependency(Options::depObjectFile, reloc->path());
afe874b1 1099 }
ebf6f434
A
1100 break;
1101 case ld::File::Dylib:
1102 {
1103 ld::dylib::File* dylib = (ld::dylib::File*)file;
1104 addDylib(dylib, info);
a645023d 1105 }
ebf6f434
A
1106 break;
1107 case ld::File::Archive:
1108 {
1109 ld::archive::File* archive = (ld::archive::File*)file;
1110 // <rdar://problem/9740166> force loaded archives should be in LD_TRACE
1111 if ( (info.options.fForceLoad || _options.fullyLoadArchives()) && _options.traceArchives() )
1112 logArchive(archive);
1113 _searchLibraries.push_back(LibraryInfo(archive));
f80fe69f
A
1114 if ( _options.dumpDependencyInfo() )
1115 _options.dumpDependency(Options::depArchive, archive->path());
ebf6f434
A
1116 }
1117 break;
1118 case ld::File::Other:
1119 break;
1120 default:
1121 {
1122 throwf("Unknown file type for %s", file->path());
1123 }
1124 break;
a645023d 1125 }
ebf6f434 1126 file->forEachAtom(handler);
a645023d
A
1127 }
1128
f80fe69f
A
1129 markExplicitlyLinkedDylibs();
1130 addLinkerOptionLibraries(state);
ebf6f434
A
1131 createIndirectDylibs();
1132 createOpaqueFileSections();
1133
1134 while (fileIndex < _inputFiles.size()) {
1135 ld::File *file = _inputFiles[fileIndex];
1136 file->forEachAtom(handler);
1137 fileIndex++;
1138 }
1139
1140 switch ( _options.outputKind() ) {
1141 case Options::kStaticExecutable:
1142 case Options::kDynamicExecutable:
1143 // add implicit __dso_handle label
1144 handler.doAtom(DSOHandleAtom::_s_atomExecutable);
1145 handler.doAtom(DSOHandleAtom::_s_atomAll);
1146 if ( _options.pageZeroSize() != 0 )
1147 handler.doAtom(*new PageZeroAtom(_options.pageZeroSize()));
1148 if ( _options.hasCustomStack() && !_options.needsEntryPointLoadCommand() )
1149 handler.doAtom(*new CustomStackAtom(_options.customStackSize()));
1150 break;
1151 case Options::kDynamicLibrary:
1152 // add implicit __dso_handle label
1153 handler.doAtom(DSOHandleAtom::_s_atomDylib);
1154 handler.doAtom(DSOHandleAtom::_s_atomAll);
1155 break;
1156 case Options::kDynamicBundle:
1157 // add implicit __dso_handle label
1158 handler.doAtom(DSOHandleAtom::_s_atomBundle);
1159 handler.doAtom(DSOHandleAtom::_s_atomAll);
1160 break;
1161 case Options::kDyld:
1162 // add implicit __dso_handle label
1163 handler.doAtom(DSOHandleAtom::_s_atomDyld);
1164 handler.doAtom(DSOHandleAtom::_s_atomAll);
1165 break;
1166 case Options::kPreload:
1167 // add implicit __mh_preload_header label
1168 handler.doAtom(DSOHandleAtom::_s_atomPreload);
b1f7435d
A
1169 // add implicit __dso_handle label, but put it in __text section because
1170 // with -preload the mach_header is no in the address space.
1171 handler.doAtom(DSOHandleAtom::_s_atomPreloadDSO);
ebf6f434
A
1172 break;
1173 case Options::kObjectFile:
1174 handler.doAtom(DSOHandleAtom::_s_atomObjectFile);
1175 break;
1176 case Options::kKextBundle:
1177 // add implicit __dso_handle label
1178 handler.doAtom(DSOHandleAtom::_s_atomAll);
1179 break;
1180 }
1181}
1182
1183
1184bool InputFiles::searchLibraries(const char* name, bool searchDylibs, bool searchArchives, bool dataSymbolOnly, ld::File::AtomHandler& handler) const
1185{
1186 // Check each input library.
d425e388
A
1187 for (std::vector<LibraryInfo>::const_iterator it=_searchLibraries.begin(); it != _searchLibraries.end(); ++it) {
1188 LibraryInfo lib = *it;
ebf6f434
A
1189 if (lib.isDylib()) {
1190 if (searchDylibs) {
1191 ld::dylib::File *dylibFile = lib.dylib();
1192 //fprintf(stderr, "searchLibraries(%s), looking in linked %s\n", name, dylibFile->path() );
1193 if ( dylibFile->justInTimeforEachAtom(name, handler) ) {
1194 // we found a definition in this dylib
1195 // done, unless it is a weak definition in which case we keep searching
1196 _options.snapshot().recordDylibSymbol(dylibFile, name);
1197 if ( !dylibFile->hasWeakExternals() || !dylibFile->hasWeakDefinition(name)) {
1198 return true;
1199 }
1200 // else continue search for a non-weak definition
1201 }
1202 }
1203 } else {
1204 if (searchArchives) {
1205 ld::archive::File *archiveFile = lib.archive();
1206 if ( dataSymbolOnly ) {
1207 if ( archiveFile->justInTimeDataOnlyforEachAtom(name, handler) ) {
1208 if ( _options.traceArchives() )
1209 logArchive(archiveFile);
1210 _options.snapshot().recordArchive(archiveFile->path());
1211 // found data definition in static library, done
f80fe69f 1212 return true;
ebf6f434
A
1213 }
1214 }
1215 else {
1216 if ( archiveFile->justInTimeforEachAtom(name, handler) ) {
1217 if ( _options.traceArchives() )
1218 logArchive(archiveFile);
1219 _options.snapshot().recordArchive(archiveFile->path());
1220 // found definition in static library, done
1221 return true;
1222 }
1223 }
1224 }
1225 }
ebf6f434
A
1226 }
1227
a645023d
A
1228 // search indirect dylibs
1229 if ( searchDylibs ) {
1230 for (InstallNameToDylib::const_iterator it=_installPathToDylibs.begin(); it != _installPathToDylibs.end(); ++it) {
1231 ld::dylib::File* dylibFile = it->second;
1232 bool searchThisDylib = false;
1233 if ( _options.nameSpace() == Options::kTwoLevelNameSpace ) {
1234 // for two level namesapce, just check all implicitly linked dylibs
1235 searchThisDylib = dylibFile->implicitlyLinked() && !dylibFile->explicitlyLinked();
1236 }
1237 else {
1238 // for flat namespace, check all indirect dylibs
1239 searchThisDylib = ! dylibFile->explicitlyLinked();
1240 }
1241 if ( searchThisDylib ) {
1242 //fprintf(stderr, "searchLibraries(%s), looking in implicitly linked %s\n", name, dylibFile->path() );
1243 if ( dylibFile->justInTimeforEachAtom(name, handler) ) {
1244 // we found a definition in this dylib
1245 // done, unless it is a weak definition in which case we keep searching
ebf6f434
A
1246 _options.snapshot().recordDylibSymbol(dylibFile, name);
1247 if ( !dylibFile->hasWeakExternals() || !dylibFile->hasWeakDefinition(name)) {
a645023d 1248 return true;
ebf6f434 1249 }
a645023d
A
1250 // else continue search for a non-weak definition
1251 }
1252 }
1253 }
1254 }
1255
1256 return false;
1257}
1258
1259
1260bool InputFiles::searchWeakDefInDylib(const char* name) const
1261{
f80fe69f 1262 // search all relevant dylibs to see if any have a weak-def with this name
a645023d
A
1263 for (InstallNameToDylib::const_iterator it=_installPathToDylibs.begin(); it != _installPathToDylibs.end(); ++it) {
1264 ld::dylib::File* dylibFile = it->second;
1265 if ( dylibFile->implicitlyLinked() || dylibFile->explicitlyLinked() ) {
1266 if ( dylibFile->hasWeakExternals() && dylibFile->hasWeakDefinition(name) ) {
1267 return true;
1268 }
1269 }
1270 }
1271 return false;
1272}
ebf6f434
A
1273
1274static bool vectorContains(const std::vector<ld::dylib::File*>& vec, ld::dylib::File* key)
1275{
1276 return std::find(vec.begin(), vec.end(), key) != vec.end();
1277}
a645023d
A
1278
1279void InputFiles::dylibs(ld::Internal& state)
1280{
afe874b1 1281 bool dylibsOK = false;
a645023d
A
1282 switch ( _options.outputKind() ) {
1283 case Options::kDynamicExecutable:
1284 case Options::kDynamicLibrary:
1285 case Options::kDynamicBundle:
1286 dylibsOK = true;
1287 break;
1288 case Options::kStaticExecutable:
1289 case Options::kDyld:
1290 case Options::kPreload:
1291 case Options::kObjectFile:
1292 case Options::kKextBundle:
1293 dylibsOK = false;
1294 break;
1295 }
1296
1297 // add command line dylibs in order
1298 for (std::vector<ld::File*>::const_iterator it=_inputFiles.begin(); it != _inputFiles.end(); ++it) {
1299 ld::dylib::File* dylibFile = dynamic_cast<ld::dylib::File*>(*it);
1300 // only add dylibs that are not "blank" dylib stubs
1301 if ( (dylibFile != NULL) && ((dylibFile->installPath() != NULL) || (dylibFile == _bundleLoader)) ) {
ebf6f434
A
1302 if ( dylibsOK ) {
1303 if ( ! vectorContains(state.dylibs, dylibFile) ) {
1304 state.dylibs.push_back(dylibFile);
1305 }
1306 }
a645023d
A
1307 else
1308 warning("unexpected dylib (%s) on link line", dylibFile->path());
1309 }
1310 }
1311 // add implicitly linked dylibs
1312 if ( _options.nameSpace() == Options::kTwoLevelNameSpace ) {
1313 for (InstallNameToDylib::const_iterator it=_installPathToDylibs.begin(); it != _installPathToDylibs.end(); ++it) {
1314 ld::dylib::File* dylibFile = it->second;
ebf6f434
A
1315 if ( dylibFile->implicitlyLinked() && dylibsOK ) {
1316 if ( ! vectorContains(state.dylibs, dylibFile) ) {
1317 state.dylibs.push_back(dylibFile);
1318 }
1319 }
a645023d
A
1320 }
1321 }
ebf6f434
A
1322
1323 //fprintf(stderr, "all dylibs:\n");
1324 //for(std::vector<ld::dylib::File*>::iterator it=state.dylibs.begin(); it != state.dylibs.end(); ++it) {
1325 // const ld::dylib::File* dylib = *it;
1326 // fprintf(stderr, " %p %s\n", dylib, dylib->path());
1327 //}
1328
a645023d
A
1329 // and -bundle_loader
1330 state.bundleLoader = _bundleLoader;
ebf6f434
A
1331
1332 // <rdar://problem/10807040> give an error when -nostdlib is used and libSystem is missing
1333 if ( (state.dylibs.size() == 0) && _options.needsEntryPointLoadCommand() )
1334 throw "dynamic main executables must link with libSystem.dylib";
a645023d
A
1335}
1336
1337
1338} // namespace tool
1339} // namespace ld
1340