llvm.org GIT mirror llvm / 93e2dfd
Object: Improve COFF irsymtab comdat representation. Change the representation of COFF comdats so that a COFF linker is able to accurately resolve comdats between IR and native object files. Specifically, apply name mangling to comdat names consistently with native object files, and do not export comdats with an internal leader because they do not affect symbol resolution. Differential Revision: https://reviews.llvm.org/D40278 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@318805 91177308-0d34-0410-b5e6-96231b3b80d8 Peter Collingbourne 2 years ago
2 changed file(s) with 57 addition(s) and 13 deletion(s). Raw diff Collapse all Expand all
7171 BumpPtrAllocator &Alloc)
7272 : Symtab(Symtab), StrtabBuilder(StrtabBuilder), Saver(Alloc) {}
7373
74 DenseMapunsigned> ComdatMap;
74 DenseMapint> ComdatMap;
7575 Mangler Mang;
7676 Triple TT;
7777
9595 Symtab.insert(Symtab.end(), reinterpret_cast(Objs.data()),
9696 reinterpret_cast(Objs.data() + Objs.size()));
9797 }
98
99 Expected getComdatIndex(const Comdat *C, const Module *M);
98100
99101 Error addModule(Module *M);
100102 Error addSymbol(const ModuleSymbolTable &Msymtab,
137139 return Err;
138140
139141 return Error::success();
142 }
143
144 Expected Builder::getComdatIndex(const Comdat *C, const Module *M) {
145 auto P = ComdatMap.insert(std::make_pair(C, Comdats.size()));
146 if (P.second) {
147 std::string Name;
148 if (TT.isOSBinFormatCOFF()) {
149 const GlobalValue *GV = M->getNamedValue(C->getName());
150 if (!GV)
151 return make_error("Could not find leader",
152 inconvertibleErrorCode());
153 // Internal leaders do not affect symbol resolution, therefore they do not
154 // appear in the symbol table.
155 if (GV->hasLocalLinkage()) {
156 P.first->second = -1;
157 return -1;
158 }
159 llvm::raw_string_ostream OS(Name);
160 Mang.getNameWithPrefix(OS, GV, false);
161 } else {
162 Name = C->getName();
163 }
164
165 storage::Comdat Comdat;
166 setStr(Comdat.Name, Saver.save(Name));
167 Comdats.push_back(Comdat);
168 }
169
170 return P.first->second;
140171 }
141172
142173 Error Builder::addSymbol(const ModuleSymbolTable &Msymtab,
215246 return make_error("Unable to determine comdat of alias!",
216247 inconvertibleErrorCode());
217248 if (const Comdat *C = Base->getComdat()) {
218 auto P = ComdatMap.insert(std::make_pair(C, Comdats.size()));
219 Sym.ComdatIndex = P.first->second;
220
221 if (P.second) {
222 storage::Comdat Comdat;
223 setStr(Comdat.Name, C->getName());
224 Comdats.push_back(Comdat);
225 }
249 Expected ComdatIndexOrErr = getComdatIndex(C, GV->getParent());
250 if (!ComdatIndexOrErr)
251 return ComdatIndexOrErr.takeError();
252 Sym.ComdatIndex = *ComdatIndexOrErr;
226253 }
227254
228255 if (TT.isOSBinFormatCOFF()) {
1414 ; CHECK: D------X _fun
1515 define i32 @fun() {
1616 ret i32 0
17 }
18
19 ; CHECK: D------X @fun2@8
20 ; CHECK-NEXT: comdat @fun2@8
21 $fun2 = comdat any
22 define x86_fastcallcc i32 @fun2(i32 inreg %a, i32 inreg %b) comdat {
23 entry:
24 %add = add nsw i32 %b, %a
25 ret i32 %add
1726 }
1827
1928 ; CHECK: H------- _g1
4251 @g8 = common global i32 0, align 8
4352
4453 ; CHECK: D------- _g9
45 ; CHECK-NEXT: comdat g9
54 ; CHECK-NEXT: comdat _g9
4655 $g9 = comdat any
4756 @g9 = global i32 0, comdat
4857
49 ; CHECK: D--WI--- _g10
50 ; CHECK-NEXT: comdat g9
58 ; CHECK-NOT: _g10
59 $g10 = comdat any
60 @g10 = internal global i32 0, comdat
61
62 ; CHECK: D------- _g11
63 ; CHECK-NOT: comdat
64 @g11 = global i32 0, comdat($g10)
65
66 ; CHECK: D--WI--- _a1
67 ; CHECK-NEXT: comdat _g9
5168 ; CHECK-NEXT: fallback _g9
52 @g10 = weak alias i32, i32* @g9
69 @a1 = weak alias i32, i32* @g9