[lld] r197851 - [mach-o] add MachOLinkingContext::configure(type, arch, os)
Nick Kledzik
kledzik at apple.com
Fri Dec 20 17:47:17 PST 2013
Author: kledzik
Date: Fri Dec 20 19:47:17 2013
New Revision: 197851
URL: http://llvm.org/viewvc/llvm-project?rev=197851&view=rev
Log:
[mach-o] add MachOLinkingContext::configure(type, arch, os)
It will configure resonable defaults for other settings in the
MachOLinkingContext object based on the parameters.
Patch by Joe Ranieri
Modified:
lld/trunk/include/lld/ReaderWriter/MachOLinkingContext.h
lld/trunk/lib/Driver/DarwinLdDriver.cpp
lld/trunk/lib/ReaderWriter/MachO/MachOLinkingContext.cpp
Modified: lld/trunk/include/lld/ReaderWriter/MachOLinkingContext.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/include/lld/ReaderWriter/MachOLinkingContext.h?rev=197851&r1=197850&r2=197851&view=diff
==============================================================================
--- lld/trunk/include/lld/ReaderWriter/MachOLinkingContext.h (original)
+++ lld/trunk/include/lld/ReaderWriter/MachOLinkingContext.h Fri Dec 20 19:47:17 2013
@@ -30,6 +30,28 @@ public:
MachOLinkingContext();
~MachOLinkingContext();
+ enum Arch {
+ arch_unknown,
+ arch_ppc,
+ arch_x86,
+ arch_x86_64,
+ arch_armv6,
+ arch_armv7,
+ arch_armv7s,
+ };
+
+ enum class OS {
+ unknown,
+ macOSX,
+ iOS,
+ iOS_simulator
+ };
+
+ /// Initializes the context to sane default values given the specified output
+ /// file type, arch, os, and minimum os version. This should be called before
+ /// other setXXX() methods.
+ void configure(HeaderFileType type, Arch arch, OS os, uint32_t minOSVersion);
+
virtual void addPasses(PassManager &pm);
virtual bool validateImpl(raw_ostream &diagnostics);
@@ -48,27 +70,10 @@ public:
HeaderFileType outputFileType() const { return _outputFileType; }
- enum Arch {
- arch_unknown,
- arch_ppc,
- arch_x86,
- arch_x86_64,
- arch_armv6,
- arch_armv7,
- arch_armv7s,
- };
-
- enum class OS {
- unknown, macOSX, iOS, iOS_simulator
- };
-
Arch arch() const { return _arch; }
StringRef archName() const { return nameFromArch(_arch); }
OS os() const { return _os; }
- void setOutputFileType(HeaderFileType type) { _outputFileType = type; }
- void setArch(Arch arch) { _arch = arch; }
- bool setOS(OS os, StringRef minOSVersion);
bool minOS(StringRef mac, StringRef iOS) const;
void setDoNothing(bool value) { _doNothing = value; }
bool doNothing() const { return _doNothing; }
@@ -145,7 +150,6 @@ private:
};
static ArchInfo _s_archInfos[];
- static const uint64_t unspecifiedPageZeroSize = UINT64_MAX;
HeaderFileType _outputFileType; // e.g MH_EXECUTE
bool _outputFileTypeStatic; // Disambiguate static vs dynamic prog
Modified: lld/trunk/lib/Driver/DarwinLdDriver.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/Driver/DarwinLdDriver.cpp?rev=197851&r1=197850&r2=197851&view=diff
==============================================================================
--- lld/trunk/lib/Driver/DarwinLdDriver.cpp (original)
+++ lld/trunk/lib/Driver/DarwinLdDriver.cpp Fri Dec 20 19:47:17 2013
@@ -111,30 +111,79 @@ bool DarwinLdDriver::parse(int argc, con
}
// Figure out output kind ( -dylib, -r, -bundle, -preload, or -static )
+ llvm::MachO::HeaderFileType fileType = llvm::MachO::MH_EXECUTE;
if ( llvm::opt::Arg *kind = parsedArgs->getLastArg(OPT_dylib, OPT_relocatable,
OPT_bundle, OPT_static, OPT_preload)) {
switch (kind->getOption().getID()) {
case OPT_dylib:
- ctx.setOutputFileType(llvm::MachO::MH_DYLIB);
- ctx.setGlobalsAreDeadStripRoots(true);
+ fileType = llvm::MachO::MH_DYLIB;
break;
case OPT_relocatable:
- ctx.setPrintRemainingUndefines(false);
- ctx.setAllowRemainingUndefines(true);
- ctx.setOutputFileType(llvm::MachO::MH_OBJECT);
+ fileType = llvm::MachO::MH_OBJECT;
break;
case OPT_bundle:
- ctx.setOutputFileType(llvm::MachO::MH_BUNDLE);
+ fileType = llvm::MachO::MH_BUNDLE;
break;
case OPT_static:
- ctx.setOutputFileType(llvm::MachO::MH_EXECUTE);
+ fileType = llvm::MachO::MH_EXECUTE;
break;
case OPT_preload:
- ctx.setOutputFileType(llvm::MachO::MH_PRELOAD);
+ fileType = llvm::MachO::MH_PRELOAD;
break;
}
}
+ // Handle -arch xxx
+ MachOLinkingContext::Arch arch = MachOLinkingContext::arch_unknown;
+ if (llvm::opt::Arg *archStr = parsedArgs->getLastArg(OPT_arch)) {
+ arch = MachOLinkingContext::archFromName(archStr->getValue());
+ if (arch == MachOLinkingContext::arch_unknown) {
+ diagnostics << "error: unknown arch named '" << archStr->getValue()
+ << "'\n";
+ return false;
+ }
+ }
+
+ // Handle -macosx_version_min or -ios_version_min
+ MachOLinkingContext::OS os = MachOLinkingContext::OS::macOSX;
+ uint32_t minOSVersion = 0;
+ if (llvm::opt::Arg *minOS =
+ parsedArgs->getLastArg(OPT_macosx_version_min, OPT_ios_version_min,
+ OPT_ios_simulator_version_min)) {
+ switch (minOS->getOption().getID()) {
+ case OPT_macosx_version_min:
+ os = MachOLinkingContext::OS::macOSX;
+ if (MachOLinkingContext::parsePackedVersion(minOS->getValue(),
+ minOSVersion)) {
+ diagnostics << "error: malformed macosx_version_min value\n";
+ return false;
+ }
+ break;
+ case OPT_ios_version_min:
+ os = MachOLinkingContext::OS::iOS;
+ if (MachOLinkingContext::parsePackedVersion(minOS->getValue(),
+ minOSVersion)) {
+ diagnostics << "error: malformed ios_version_min value\n";
+ return false;
+ }
+ break;
+ case OPT_ios_simulator_version_min:
+ os = MachOLinkingContext::OS::iOS_simulator;
+ if (MachOLinkingContext::parsePackedVersion(minOS->getValue(),
+ minOSVersion)) {
+ diagnostics << "error: malformed ios_simulator_version_min value\n";
+ return false;
+ }
+ break;
+ }
+ } else {
+ // No min-os version on command line, check environment variables
+ }
+
+ // Now that there's enough information parsed in, let the linking context
+ // set up default values.
+ ctx.configure(fileType, arch, os, minOSVersion);
+
// Handle -e xxx
if (llvm::opt::Arg *entry = parsedArgs->getLastArg(OPT_entry))
ctx.setEntrySymbolName(entry->getValue());
@@ -192,47 +241,6 @@ bool DarwinLdDriver::parse(int argc, con
if (llvm::opt::Arg *loader = parsedArgs->getLastArg(OPT_bundle_loader))
ctx.setBundleLoader(loader->getValue());
- // Handle -arch xxx
- if (llvm::opt::Arg *archStr = parsedArgs->getLastArg(OPT_arch)) {
- ctx.setArch(MachOLinkingContext::archFromName(archStr->getValue()));
- if (ctx.arch() == MachOLinkingContext::arch_unknown) {
- diagnostics << "error: unknown arch named '" << archStr->getValue()
- << "'\n";
- return false;
- }
- }
-
- // Handle -macosx_version_min or -ios_version_min
- if (llvm::opt::Arg *minOS = parsedArgs->getLastArg(
- OPT_macosx_version_min,
- OPT_ios_version_min,
- OPT_ios_simulator_version_min)) {
- switch (minOS->getOption().getID()) {
- case OPT_macosx_version_min:
- if (ctx.setOS(MachOLinkingContext::OS::macOSX, minOS->getValue())) {
- diagnostics << "error: malformed macosx_version_min value\n";
- return false;
- }
- break;
- case OPT_ios_version_min:
- if (ctx.setOS(MachOLinkingContext::OS::iOS, minOS->getValue())) {
- diagnostics << "error: malformed ios_version_min value\n";
- return false;
- }
- break;
- case OPT_ios_simulator_version_min:
- if (ctx.setOS(MachOLinkingContext::OS::iOS_simulator,
- minOS->getValue())) {
- diagnostics << "error: malformed ios_simulator_version_min value\n";
- return false;
- }
- break;
- }
- }
- else {
- // No min-os version on command line, check environment variables
- }
-
// Handle -help
if (parsedArgs->getLastArg(OPT_help)) {
table.PrintHelp(llvm::outs(), argv[0], "LLVM Darwin Linker", false);
Modified: lld/trunk/lib/ReaderWriter/MachO/MachOLinkingContext.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/MachO/MachOLinkingContext.cpp?rev=197851&r1=197850&r2=197851&view=diff
==============================================================================
--- lld/trunk/lib/ReaderWriter/MachO/MachOLinkingContext.cpp (original)
+++ lld/trunk/lib/ReaderWriter/MachO/MachOLinkingContext.cpp Fri Dec 20 19:47:17 2013
@@ -121,13 +121,50 @@ uint32_t MachOLinkingContext::cpuSubtype
MachOLinkingContext::MachOLinkingContext()
: _outputFileType(MH_EXECUTE), _outputFileTypeStatic(false),
_doNothing(false), _arch(arch_unknown), _os(OS::macOSX), _osMinVersion(0),
- _pageZeroSize(unspecifiedPageZeroSize),
- _pageSize(4096),
- _compatibilityVersion(0), _currentVersion(0),
- _deadStrippableDylib(false), _kindHandler(nullptr) {}
+ _pageZeroSize(0), _pageSize(4096), _compatibilityVersion(0),
+ _currentVersion(0), _deadStrippableDylib(false), _kindHandler(nullptr) {}
MachOLinkingContext::~MachOLinkingContext() {}
+void MachOLinkingContext::configure(HeaderFileType type, Arch arch, OS os,
+ uint32_t minOSVersion) {
+ _outputFileType = type;
+ _arch = arch;
+ _os = os;
+ _osMinVersion = minOSVersion;
+
+ switch (_outputFileType) {
+ case llvm::MachO::MH_EXECUTE:
+ // If targeting newer OS, use _main
+ if (minOS("10.8", "6.0")) {
+ _entrySymbolName = "_main";
+ } else {
+ // If targeting older OS, use start (in crt1.o)
+ _entrySymbolName = "start";
+ }
+
+ // __PAGEZERO defaults to 4GB on 64-bit (except for PP64 which lld does not
+ // support) and 4KB on 32-bit.
+ if (is64Bit(_arch)) {
+ _pageZeroSize = 0x100000000;
+ } else {
+ _pageZeroSize = 0x1000;
+ }
+
+ break;
+ case llvm::MachO::MH_DYLIB:
+ _globalsAreDeadStripRoots = true;
+ break;
+ case llvm::MachO::MH_BUNDLE:
+ break;
+ case llvm::MachO::MH_OBJECT:
+ _printRemainingUndefines = false;
+ _allowRemainingUndefines = true;
+ default:
+ break;
+ }
+}
+
uint32_t MachOLinkingContext::getCPUType() const {
return cpuTypeFromArch(_arch);
}
@@ -225,29 +262,8 @@ bool MachOLinkingContext::addUnixThreadL
}
bool MachOLinkingContext::validateImpl(raw_ostream &diagnostics) {
- if ((_outputFileType == MH_EXECUTE) && _entrySymbolName.empty()){
- if (_outputFileTypeStatic) {
- _entrySymbolName = "start";
- } else if (addUnixThreadLoadCommand()) {
- // If targeting older OS, use start (in crt1.o)
- _entrySymbolName = "start";
- } else if (addEntryPointLoadCommand()) {
- // If targeting newer OS, use _main
- _entrySymbolName = "_main";
- }
- }
-
// TODO: if -arch not specified, look at arch of first .o file.
- // Set default __PAGEZERO for main executables
- if ((_outputFileType == MH_EXECUTE) && !_outputFileTypeStatic
- && (_pageZeroSize == unspecifiedPageZeroSize)) {
- if (is64Bit(_arch))
- _pageZeroSize = 0x100000000;
- else
- _pageZeroSize = 0x00010000;
- }
-
if (_currentVersion && _outputFileType != MH_DYLIB) {
diagnostics << "error: -current_version can only be used with dylibs\n";
return false;
@@ -274,11 +290,6 @@ bool MachOLinkingContext::validateImpl(r
return true;
}
-bool MachOLinkingContext::setOS(OS os, StringRef minOSVersion) {
- _os = os;
- return parsePackedVersion(minOSVersion, _osMinVersion);
-}
-
void MachOLinkingContext::addPasses(PassManager &pm) {
if (outputFileType() != MH_OBJECT) {
pm.add(std::unique_ptr<Pass>(new mach_o::GOTPass));
More information about the llvm-commits
mailing list