[COFF] Remove undefined behavior from ObjectFile::createWeakExternal
LLD type-punned an integral type and a pointer type using a pointer field. This is problematic because the pointer type has alignment greater than some of the integral values. This would be less problematic if a union was used but it turns out the integral values are only present for a short, transient, amount of time. Let's remove this undefined behavior by skipping the punning altogether by storing the state in a separate memory location: a vector which informs us which symbols to process for weak externs. llvm-svn: 263918
This commit is contained in:
parent
4af44f3c13
commit
2aa29ee7c1
|
@ -149,7 +149,7 @@ void ObjectFile::initializeSymbols() {
|
|||
uint32_t NumSymbols = COFFObj->getNumberOfSymbols();
|
||||
SymbolBodies.reserve(NumSymbols);
|
||||
SparseSymbolBodies.resize(NumSymbols);
|
||||
llvm::SmallVector<Undefined *, 8> WeakAliases;
|
||||
llvm::SmallVector<std::pair<Undefined *, uint32_t>, 8> WeakAliases;
|
||||
int32_t LastSectionNumber = 0;
|
||||
for (uint32_t I = 0; I < NumSymbols; ++I) {
|
||||
// Get a COFFSymbolRef object.
|
||||
|
@ -167,8 +167,10 @@ void ObjectFile::initializeSymbols() {
|
|||
if (Sym.isUndefined()) {
|
||||
Body = createUndefined(Sym);
|
||||
} else if (Sym.isWeakExternal()) {
|
||||
Body = createWeakExternal(Sym, AuxP);
|
||||
WeakAliases.push_back((Undefined *)Body);
|
||||
Body = createUndefined(Sym);
|
||||
uint32_t TagIndex =
|
||||
static_cast<const coff_aux_weak_external *>(AuxP)->TagIndex;
|
||||
WeakAliases.emplace_back((Undefined *)Body, TagIndex);
|
||||
} else {
|
||||
Body = createDefined(Sym, AuxP, IsFirst);
|
||||
}
|
||||
|
@ -179,8 +181,8 @@ void ObjectFile::initializeSymbols() {
|
|||
I += Sym.getNumberOfAuxSymbols();
|
||||
LastSectionNumber = Sym.getSectionNumber();
|
||||
}
|
||||
for (Undefined *U : WeakAliases)
|
||||
U->WeakAlias = SparseSymbolBodies[(uintptr_t)U->WeakAlias];
|
||||
for (auto WeakAlias : WeakAliases)
|
||||
WeakAlias.first->WeakAlias = SparseSymbolBodies[WeakAlias.second];
|
||||
}
|
||||
|
||||
Undefined *ObjectFile::createUndefined(COFFSymbolRef Sym) {
|
||||
|
@ -189,15 +191,6 @@ Undefined *ObjectFile::createUndefined(COFFSymbolRef Sym) {
|
|||
return new (Alloc) Undefined(Name);
|
||||
}
|
||||
|
||||
Undefined *ObjectFile::createWeakExternal(COFFSymbolRef Sym, const void *AuxP) {
|
||||
StringRef Name;
|
||||
COFFObj->getSymbolName(Sym, Name);
|
||||
auto *U = new (Alloc) Undefined(Name);
|
||||
auto *Aux = (const coff_aux_weak_external *)AuxP;
|
||||
U->WeakAlias = (Undefined *)(uintptr_t)Aux->TagIndex;
|
||||
return U;
|
||||
}
|
||||
|
||||
Defined *ObjectFile::createDefined(COFFSymbolRef Sym, const void *AuxP,
|
||||
bool IsFirst) {
|
||||
StringRef Name;
|
||||
|
|
|
@ -147,7 +147,6 @@ private:
|
|||
|
||||
Defined *createDefined(COFFSymbolRef Sym, const void *Aux, bool IsFirst);
|
||||
Undefined *createUndefined(COFFSymbolRef Sym);
|
||||
Undefined *createWeakExternal(COFFSymbolRef Sym, const void *Aux);
|
||||
|
||||
std::unique_ptr<COFFObjectFile> COFFObj;
|
||||
llvm::BumpPtrAllocator Alloc;
|
||||
|
|
Loading…
Reference in New Issue