diff options
author | Dimitry Andric <dim@FreeBSD.org> | 2019-01-19 10:05:49 +0000 |
---|---|---|
committer | Dimitry Andric <dim@FreeBSD.org> | 2019-01-19 10:05:49 +0000 |
commit | e2fd426bdafe9f5c10066d3926ece6e342184a67 (patch) | |
tree | bfbbb5fd38554e6b8988b7a217e9fd0623728d7d /wasm/InputFiles.cpp | |
parent | 84c4061b34e048f47e5eb4fbabc1558495e8157c (diff) |
Vendor import of lld trunk r351319 (just before the release_80 branchvendor/lld/lld-trunk-r351319
Notes
Notes:
svn path=/vendor/lld/dist/; revision=343179
svn path=/vendor/lld/lld-trunk-r351319/; revision=343180; tag=vendor/lld/lld-trunk-r351319
Diffstat (limited to 'wasm/InputFiles.cpp')
-rw-r--r-- | wasm/InputFiles.cpp | 93 |
1 files changed, 71 insertions, 22 deletions
diff --git a/wasm/InputFiles.cpp b/wasm/InputFiles.cpp index 53a24c3cffd4..e5da23db3773 100644 --- a/wasm/InputFiles.cpp +++ b/wasm/InputFiles.cpp @@ -10,6 +10,7 @@ #include "InputFiles.h" #include "Config.h" #include "InputChunks.h" +#include "InputEvent.h" #include "InputGlobal.h" #include "SymbolTable.h" #include "lld/Common/ErrorHandler.h" @@ -57,12 +58,13 @@ void ObjFile::dumpInfo() const { log("info for: " + getName() + "\n Symbols : " + Twine(Symbols.size()) + "\n Function Imports : " + Twine(WasmObj->getNumImportedFunctions()) + - "\n Global Imports : " + Twine(WasmObj->getNumImportedGlobals())); + "\n Global Imports : " + Twine(WasmObj->getNumImportedGlobals()) + + "\n Event Imports : " + Twine(WasmObj->getNumImportedEvents())); } // Relocations contain either symbol or type indices. This function takes a // relocation and returns relocated index (i.e. translates from the input -// sybmol/type space to the output symbol/type space). +// symbol/type space to the output symbol/type space). uint32_t ObjFile::calcNewIndex(const WasmRelocation &Reloc) const { if (Reloc.Type == R_WEBASSEMBLY_TYPE_INDEX_LEB) { assert(TypeIsUsed[Reloc.Index]); @@ -94,16 +96,17 @@ uint32_t ObjFile::calcExpectedValue(const WasmRelocation &Reloc) const { switch (Reloc.Type) { case R_WEBASSEMBLY_TABLE_INDEX_I32: case R_WEBASSEMBLY_TABLE_INDEX_SLEB: { - const WasmSymbol& Sym = WasmObj->syms()[Reloc.Index]; + const WasmSymbol &Sym = WasmObj->syms()[Reloc.Index]; return TableEntries[Sym.Info.ElementIndex]; } case R_WEBASSEMBLY_MEMORY_ADDR_SLEB: case R_WEBASSEMBLY_MEMORY_ADDR_I32: case R_WEBASSEMBLY_MEMORY_ADDR_LEB: { - const WasmSymbol& Sym = WasmObj->syms()[Reloc.Index]; + const WasmSymbol &Sym = WasmObj->syms()[Reloc.Index]; if (Sym.isUndefined()) return 0; - const WasmSegment& Segment = WasmObj->dataSegments()[Sym.Info.DataRef.Segment]; + const WasmSegment &Segment = + WasmObj->dataSegments()[Sym.Info.DataRef.Segment]; return Segment.Data.Offset.Value.Int32 + Sym.Info.DataRef.Offset + Reloc.Addend; } @@ -118,8 +121,9 @@ uint32_t ObjFile::calcExpectedValue(const WasmRelocation &Reloc) const { case R_WEBASSEMBLY_TYPE_INDEX_LEB: return Reloc.Index; case R_WEBASSEMBLY_FUNCTION_INDEX_LEB: - case R_WEBASSEMBLY_GLOBAL_INDEX_LEB: { - const WasmSymbol& Sym = WasmObj->syms()[Reloc.Index]; + case R_WEBASSEMBLY_GLOBAL_INDEX_LEB: + case R_WEBASSEMBLY_EVENT_INDEX_LEB: { + const WasmSymbol &Sym = WasmObj->syms()[Reloc.Index]; return Sym.Info.ElementIndex; } default: @@ -146,10 +150,13 @@ uint32_t ObjFile::calcNewValue(const WasmRelocation &Reloc) const { return getFunctionSymbol(Reloc.Index)->getFunctionIndex(); case R_WEBASSEMBLY_GLOBAL_INDEX_LEB: return getGlobalSymbol(Reloc.Index)->getGlobalIndex(); + case R_WEBASSEMBLY_EVENT_INDEX_LEB: + return getEventSymbol(Reloc.Index)->getEventIndex(); case R_WEBASSEMBLY_FUNCTION_OFFSET_I32: if (auto *Sym = dyn_cast<DefinedFunction>(getFunctionSymbol(Reloc.Index))) { - return Sym->Function->OutputOffset + - Sym->Function->getFunctionCodeOffset() + Reloc.Addend; + if (Sym->isLive()) + return Sym->Function->OutputOffset + + Sym->Function->getFunctionCodeOffset() + Reloc.Addend; } return 0; case R_WEBASSEMBLY_SECTION_OFFSET_I32: @@ -159,6 +166,37 @@ uint32_t ObjFile::calcNewValue(const WasmRelocation &Reloc) const { } } +template <class T> +static void setRelocs(const std::vector<T *> &Chunks, + const WasmSection *Section) { + if (!Section) + return; + + ArrayRef<WasmRelocation> Relocs = Section->Relocations; + assert(std::is_sorted(Relocs.begin(), Relocs.end(), + [](const WasmRelocation &R1, const WasmRelocation &R2) { + return R1.Offset < R2.Offset; + })); + assert(std::is_sorted( + Chunks.begin(), Chunks.end(), [](InputChunk *C1, InputChunk *C2) { + return C1->getInputSectionOffset() < C2->getInputSectionOffset(); + })); + + auto RelocsNext = Relocs.begin(); + auto RelocsEnd = Relocs.end(); + auto RelocLess = [](const WasmRelocation &R, uint32_t Val) { + return R.Offset < Val; + }; + for (InputChunk *C : Chunks) { + auto RelocsStart = std::lower_bound(RelocsNext, RelocsEnd, + C->getInputSectionOffset(), RelocLess); + RelocsNext = std::lower_bound( + RelocsStart, RelocsEnd, C->getInputSectionOffset() + C->getInputSize(), + RelocLess); + C->setRelocations(ArrayRef<WasmRelocation>(RelocsStart, RelocsNext)); + } +} + void ObjFile::parse() { // Parse a memory buffer as a wasm file. LLVM_DEBUG(dbgs() << "Parsing object: " << toString(this) << "\n"); @@ -200,7 +238,7 @@ void ObjFile::parse() { DataSection = &Section; } else if (Section.Type == WASM_SEC_CUSTOM) { CustomSections.emplace_back(make<InputSection>(Section, this)); - CustomSections.back()->copyRelocations(Section); + CustomSections.back()->setRelocations(Section.Relocations); CustomSectionsByIndex[SectionIndex] = CustomSections.back(); } SectionIndex++; @@ -215,11 +253,9 @@ void ObjFile::parse() { UsedComdats[I] = Symtab->addComdat(Comdats[I]); // Populate `Segments`. - for (const WasmSegment &S : WasmObj->dataSegments()) { - InputSegment *Seg = make<InputSegment>(S, this); - Seg->copyRelocations(*DataSection); - Segments.emplace_back(Seg); - } + for (const WasmSegment &S : WasmObj->dataSegments()) + Segments.emplace_back(make<InputSegment>(S, this)); + setRelocs(Segments, DataSection); // Populate `Functions`. ArrayRef<WasmFunction> Funcs = WasmObj->functions(); @@ -227,17 +263,19 @@ void ObjFile::parse() { ArrayRef<WasmSignature> Types = WasmObj->types(); Functions.reserve(Funcs.size()); - for (size_t I = 0, E = Funcs.size(); I != E; ++I) { - InputFunction *F = - make<InputFunction>(Types[FuncTypes[I]], &Funcs[I], this); - F->copyRelocations(*CodeSection); - Functions.emplace_back(F); - } + for (size_t I = 0, E = Funcs.size(); I != E; ++I) + Functions.emplace_back( + make<InputFunction>(Types[FuncTypes[I]], &Funcs[I], this)); + setRelocs(Functions, CodeSection); // Populate `Globals`. for (const WasmGlobal &G : WasmObj->globals()) Globals.emplace_back(make<InputGlobal>(G, this)); + // Populate `Events`. + for (const WasmEvent &E : WasmObj->events()) + Events.emplace_back(make<InputEvent>(Types[E.Type.SigIndex], E, this)); + // Populate `Symbols` based on the WasmSymbols in the object. Symbols.reserve(WasmObj->getNumberOfSymbols()); for (const SymbolRef &Sym : WasmObj->symbols()) { @@ -264,6 +302,10 @@ GlobalSymbol *ObjFile::getGlobalSymbol(uint32_t Index) const { return cast<GlobalSymbol>(Symbols[Index]); } +EventSymbol *ObjFile::getEventSymbol(uint32_t Index) const { + return cast<EventSymbol>(Symbols[Index]); +} + SectionSymbol *ObjFile::getSectionSymbol(uint32_t Index) const { return cast<SectionSymbol>(Symbols[Index]); } @@ -318,6 +360,13 @@ Symbol *ObjFile::createDefined(const WasmSymbol &Sym) { assert(Sym.isBindingLocal()); return make<SectionSymbol>(Name, Flags, Section, this); } + case WASM_SYMBOL_TYPE_EVENT: { + InputEvent *Event = + Events[Sym.Info.ElementIndex - WasmObj->getNumImportedEvents()]; + if (Sym.isBindingLocal()) + return make<DefinedEvent>(Name, Flags, this, Event); + return Symtab->addDefinedEvent(Name, Flags, this, Event); + } } llvm_unreachable("unknown symbol kind"); } @@ -328,7 +377,7 @@ Symbol *ObjFile::createUndefined(const WasmSymbol &Sym) { switch (Sym.Info.Kind) { case WASM_SYMBOL_TYPE_FUNCTION: - return Symtab->addUndefinedFunction(Name, Flags, this, Sym.FunctionType); + return Symtab->addUndefinedFunction(Name, Flags, this, Sym.Signature); case WASM_SYMBOL_TYPE_DATA: return Symtab->addUndefinedData(Name, Flags, this); case WASM_SYMBOL_TYPE_GLOBAL: |