[swiftc] Fixed for Cygwin

Fixed for the difference of Cygwin with other Windows variants (MSVC,
Itanium, MinGW).

- The platform name is renamed to "cygwin" from "windows" which is used
  for searching the standard libraries.

- The consideration for DLL storage class (DllExport/DllImport) is not
  required for Cygwin and MinGW. There is no problem when linking in
  these environment.

- Cygwin should use large memory model as default.(This may be changed
  if someone ports to 32bit)

- Cygwin and MinGW should use the autolink feature in the sameway of
  Linux due to the linker's limit.
This commit is contained in:
Han Sangjin
2016-08-13 06:56:57 +09:00
parent 5a2474152b
commit b8dd577693
14 changed files with 74 additions and 43 deletions

View File

@@ -117,6 +117,11 @@ static clang::CodeGenerator *createClangCodeGenerator(ASTContext &Context,
return ClangCodeGen;
}
/// A helper for determining if the triple uses the DLL storage
static bool useDllStorage(const llvm::Triple &Triple) {
return Triple.isOSBinFormatCOFF() && !Triple.isOSCygMing();
}
IRGenModule::IRGenModule(IRGenerator &irgen,
std::unique_ptr<llvm::TargetMachine> &&target,
SourceFile *SF, llvm::LLVMContext &LLVMContext,
@@ -439,7 +444,7 @@ llvm::Constant *swift::getRuntimeFn(llvm::Module &Module,
if (auto fn = dyn_cast<llvm::Function>(cache)) {
fn->setCallingConv(cc);
if (llvm::Triple(Module.getTargetTriple()).isOSBinFormatCOFF() &&
if (::useDllStorage(llvm::Triple(Module.getTargetTriple())) &&
(fn->getLinkage() == llvm::GlobalValue::ExternalLinkage ||
fn->getLinkage() == llvm::GlobalValue::AvailableExternallyLinkage))
fn->setDLLStorageClass(llvm::GlobalValue::DLLImportStorageClass);
@@ -519,7 +524,7 @@ llvm::Constant *swift::getWrapperFn(llvm::Module &Module,
auto *globalFnPtr = new llvm::GlobalVariable(
Module, fnPtrTy, false, llvm::GlobalValue::ExternalLinkage, nullptr,
symbol);
if (llvm::Triple(Module.getTargetTriple()).isOSBinFormatCOFF())
if (::useDllStorage(llvm::Triple(Module.getTargetTriple())))
globalFnPtr->setDLLStorageClass(llvm::GlobalValue::DLLImportStorageClass);
// Forward all arguments.
@@ -638,7 +643,7 @@ llvm::Constant *IRGenModule::getEmptyTupleMetadata() {
EmptyTupleMetadata = Module.getOrInsertGlobal(
MANGLE_AS_STRING(METADATA_SYM(EMPTY_TUPLE_MANGLING)),
FullTypeMetadataStructTy);
if (Triple.isOSBinFormatCOFF())
if (useDllStorage())
cast<llvm::GlobalVariable>(EmptyTupleMetadata)
->setDLLStorageClass(llvm::GlobalValue::DLLImportStorageClass);
return EmptyTupleMetadata;
@@ -652,7 +657,7 @@ llvm::Constant *IRGenModule::getObjCEmptyCachePtr() {
// struct objc_cache _objc_empty_cache;
ObjCEmptyCachePtr = Module.getOrInsertGlobal("_objc_empty_cache",
OpaquePtrTy->getElementType());
if (Triple.isOSBinFormatCOFF())
if (useDllStorage())
cast<llvm::GlobalVariable>(ObjCEmptyCachePtr)
->setDLLStorageClass(llvm::GlobalValue::DLLImportStorageClass);
} else {
@@ -685,7 +690,7 @@ Address IRGenModule::getAddrOfObjCISAMask() {
assert(TargetInfo.hasISAMasking());
if (!ObjCISAMaskPtr) {
ObjCISAMaskPtr = Module.getOrInsertGlobal("swift_isaMask", IntPtrTy);
if (Triple.isOSBinFormatCOFF())
if (useDllStorage())
cast<llvm::GlobalVariable>(ObjCISAMaskPtr)
->setDLLStorageClass(llvm::GlobalValue::DLLImportStorageClass);
}
@@ -851,7 +856,7 @@ void IRGenModule::addLinkLibrary(const LinkLibrary &linkLib) {
llvm::SmallString<64> buf;
encodeForceLoadSymbolName(buf, linkLib.getName());
auto symbolAddr = Module.getOrInsertGlobal(buf.str(), Int1Ty);
if (Triple.isOSBinFormatCOFF())
if (useDllStorage())
cast<llvm::GlobalVariable>(symbolAddr)
->setDLLStorageClass(llvm::GlobalValue::DLLImportStorageClass);
@@ -916,9 +921,9 @@ void IRGenModule::emitAutolinkInfo() {
}),
AutolinkEntries.end());
if (TargetInfo.OutputObjectFormat == llvm::Triple::COFF ||
TargetInfo.OutputObjectFormat == llvm::Triple::MachO ||
Triple.isPS4()) {
if ((TargetInfo.OutputObjectFormat == llvm::Triple::COFF &&
!Triple.isOSCygMing()) ||
TargetInfo.OutputObjectFormat == llvm::Triple::MachO || Triple.isPS4()) {
llvm::LLVMContext &ctx = Module.getContext();
if (!LinkerOptions) {
@@ -935,8 +940,9 @@ void IRGenModule::emitAutolinkInfo() {
assert(FoundOldEntry && "Could not replace old linker options entry?");
}
} else {
assert(TargetInfo.OutputObjectFormat == llvm::Triple::ELF &&
"expected ELF output format");
assert((TargetInfo.OutputObjectFormat == llvm::Triple::ELF ||
Triple.isOSCygMing()) &&
"expected ELF output format or COFF format for Cygwin/MinGW");
// Merge the entries into null-separated string.
llvm::SmallString<64> EntriesString;
@@ -969,7 +975,7 @@ void IRGenModule::emitAutolinkInfo() {
llvm::GlobalValue::CommonLinkage,
llvm::Constant::getNullValue(Int1Ty),
buf.str());
if (Triple.isOSBinFormatCOFF())
if (useDllStorage())
symbol->setDLLStorageClass(llvm::GlobalValue::DLLExportStorageClass);
}
}
@@ -1072,6 +1078,8 @@ void IRGenModule::error(SourceLoc loc, const Twine &message) {
message.toStringRef(buffer));
}
bool IRGenModule::useDllStorage() { return ::useDllStorage(Triple); }
void IRGenerator::addGenModule(SourceFile *SF, IRGenModule *IGM) {
assert(GenModules.count(SF) == 0);
GenModules[SF] = IGM;