1 //===- MinGW.cpp ----------------------------------------------------------===//
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
11 #include "SymbolTable.h"
12 #include "lld/Common/ErrorHandler.h"
13 #include "llvm/Object/COFF.h"
14 #include "llvm/Support/Path.h"
15 #include "llvm/Support/raw_ostream.h"
18 using namespace lld::coff;
20 using namespace llvm::COFF;
22 void AutoExporter::initSymbolExcludes() {
23 ExcludeSymbolPrefixes = {
26 "__IMPORT_DESCRIPTOR_",
27 // Extra import symbols from GNU import libraries
32 // Artifical symbols such as .refptr
35 ExcludeSymbolSuffixes = {
39 if (Config->Machine == I386) {
41 "__NULL_IMPORT_DESCRIPTOR",
42 "__pei386_runtime_relocator",
49 // These are the MinGW names that differ from the standard
50 // ones (lacking an extra underscore).
53 "_DllMainCRTStartup@12",
55 ExcludeSymbolPrefixes.insert("__head_");
58 "__NULL_IMPORT_DESCRIPTOR",
59 "_pei386_runtime_relocator",
66 // These are the MinGW names that differ from the standard
67 // ones (lacking an extra underscore).
72 ExcludeSymbolPrefixes.insert("_head_");
76 AutoExporter::AutoExporter() {
87 "libclang_rt.builtins",
88 "libclang_rt.builtins-aarch64",
89 "libclang_rt.builtins-arm",
90 "libclang_rt.builtins-i386",
91 "libclang_rt.builtins-x86_64",
114 void AutoExporter::addWholeArchive(StringRef Path) {
115 StringRef LibName = sys::path::filename(Path);
116 // Drop the file extension, to match the processing below.
117 LibName = LibName.substr(0, LibName.rfind('.'));
118 ExcludeLibs.erase(LibName);
121 bool AutoExporter::shouldExport(Defined *Sym) const {
122 if (!Sym || !Sym->isLive() || !Sym->getChunk())
125 // Only allow the symbol kinds that make sense to export; in particular,
126 // disallow import symbols.
127 if (!isa<DefinedRegular>(Sym) && !isa<DefinedCommon>(Sym))
129 if (ExcludeSymbols.count(Sym->getName()))
132 for (StringRef Prefix : ExcludeSymbolPrefixes.keys())
133 if (Sym->getName().startswith(Prefix))
135 for (StringRef Suffix : ExcludeSymbolSuffixes.keys())
136 if (Sym->getName().endswith(Suffix))
139 // If a corresponding __imp_ symbol exists and is defined, don't export it.
140 if (Symtab->find(("__imp_" + Sym->getName()).str()))
143 // Check that file is non-null before dereferencing it, symbols not
144 // originating in regular object files probably shouldn't be exported.
148 StringRef LibName = sys::path::filename(Sym->getFile()->ParentName);
150 // Drop the file extension.
151 LibName = LibName.substr(0, LibName.rfind('.'));
152 if (!LibName.empty())
153 return !ExcludeLibs.count(LibName);
155 StringRef FileName = sys::path::filename(Sym->getFile()->getName());
156 return !ExcludeObjects.count(FileName);
159 void coff::writeDefFile(StringRef Name) {
161 raw_fd_ostream OS(Name, EC, sys::fs::F_None);
163 fatal("cannot open " + Name + ": " + EC.message());
166 for (Export &E : Config->Exports) {
167 OS << " " << E.ExportName << " "
169 if (auto *Def = dyn_cast_or_null<Defined>(E.Sym)) {
170 if (Def && Def->getChunk() &&
171 !(Def->getChunk()->getOutputCharacteristics() & IMAGE_SCN_MEM_EXECUTE))