diff options
| -rw-r--r-- | lld/COFF/Chunks.cpp | 44 | ||||
| -rw-r--r-- | lld/COFF/Chunks.h | 6 |
2 files changed, 30 insertions, 20 deletions
diff --git a/lld/COFF/Chunks.cpp b/lld/COFF/Chunks.cpp index 84854ab7051..9ee68460661 100644 --- a/lld/COFF/Chunks.cpp +++ b/lld/COFF/Chunks.cpp @@ -58,10 +58,8 @@ void SectionChunk::writeTo(uint8_t *Buf) { memcpy(Buf + FileOff, Data.data(), Data.size()); // Apply relocations. - for (const auto &I : getSectionRef().relocations()) { - const coff_relocation *Rel = File->getCOFFObj()->getCOFFRelocation(I); + for (const coff_relocation *Rel = relBegin(), *E = relEnd(); Rel != E; ++Rel) applyReloc(Buf, Rel); - } } void SectionChunk::mark() { @@ -69,8 +67,8 @@ void SectionChunk::mark() { Live = true; // Mark all symbols listed in the relocation table for this section. - for (const auto &I : getSectionRef().relocations()) { - const coff_relocation *Rel = File->getCOFFObj()->getCOFFRelocation(I); + for (const coff_relocation *Rel = relBegin(), *E = relEnd(); Rel != E; + ++Rel) { SymbolBody *B = File->getSymbolBody(Rel->SymbolTableIndex); if (auto *Def = dyn_cast<Defined>(B)) Def->markLive(); @@ -120,11 +118,11 @@ void SectionChunk::applyReloc(uint8_t *Buf, const coff_relocation *Rel) { // which need to be fixed by the loader if load-time relocation is needed. // Only called when base relocation is enabled. void SectionChunk::getBaserels(std::vector<uint32_t> *Res, Defined *ImageBase) { - for (const auto &I : getSectionRef().relocations()) { + for (const coff_relocation *Rel = relBegin(), *E = relEnd(); Rel != E; + ++Rel) { // ADDR64 relocations contain absolute addresses. // Symbol __ImageBase is special -- it's an absolute symbol, but its // address never changes even if image is relocated. - const coff_relocation *Rel = File->getCOFFObj()->getCOFFRelocation(I); if (Rel->Type != IMAGE_REL_AMD64_ADDR64) continue; SymbolBody *Body = File->getSymbolBody(Rel->SymbolTableIndex); @@ -156,12 +154,6 @@ void SectionChunk::printDiscardedMessage() { } } -SectionRef SectionChunk::getSectionRef() const { - DataRefImpl Ref; - Ref.p = uintptr_t(Header); - return SectionRef(Ref, File->getCOFFObj()); -} - StringRef SectionChunk::getDebugName() { return Sym->getName(); } @@ -196,12 +188,10 @@ bool SectionChunk::equals(const SectionChunk *X) const { return false; // Compare relocations - auto Range1 = getSectionRef().relocations(); - auto Range2 = X->getSectionRef().relocations(); - auto End = Range1.end(); - for (auto I = Range1.begin(), J = Range2.begin(); I != End; ++I, ++J) { - const coff_relocation *Rel1 = File->getCOFFObj()->getCOFFRelocation(*I); - const coff_relocation *Rel2 = X->File->getCOFFObj()->getCOFFRelocation(*J); + const coff_relocation *Rel1 = relBegin(); + const coff_relocation *End = relEnd(); + const coff_relocation *Rel2 = X->relBegin(); + for (; Rel1 != End; ++Rel1, ++Rel2) { if (Rel1->Type != Rel2->Type) return false; if (Rel1->VirtualAddress != Rel2->VirtualAddress) @@ -230,6 +220,22 @@ void SectionChunk::replaceWith(SectionChunk *Other) { Live = false; } +const coff_relocation *SectionChunk::relBegin() const { + if (!Reloc) { + DataRefImpl Ref; + Ref.p = uintptr_t(Header); + SectionRef Sref(Ref, File->getCOFFObj()); + relocation_iterator It = Sref.relocation_begin(); + Reloc = File->getCOFFObj()->getCOFFRelocation(*It); + } + return Reloc; +} + +const coff_relocation *SectionChunk::relEnd() const { + const coff_relocation *I = relBegin(); + return I + Header->NumberOfRelocations; +} + CommonChunk::CommonChunk(const COFFSymbolRef S) : Sym(S) { // Common symbols are aligned on natural boundaries up to 32 bytes. // This is what MSVC link.exe does. diff --git a/lld/COFF/Chunks.h b/lld/COFF/Chunks.h index f45add458a3..810793dc88c 100644 --- a/lld/COFF/Chunks.h +++ b/lld/COFF/Chunks.h @@ -149,12 +149,16 @@ public: private: void mark() override; - SectionRef getSectionRef() const; void applyReloc(uint8_t *Buf, const coff_relocation *Rel); // A file this chunk was created from. ObjectFile *File; + // A raw pointer to the relocation table. + mutable const coff_relocation *Reloc = nullptr; + const coff_relocation *relBegin() const; + const coff_relocation *relEnd() const; + // A pointer pointing to a replacement for this chunk. // Initially it points to "this" object. If this chunk is merged // with other chunk by ICF, it points to another chunk, |

