forked from OSchip/llvm-project
[WebAssembly] Refactor order of creation for SyntheticFunction
Previously we created __wasm_call_ctors with null InputFunction, and added the InputFunction later. Now we create the SyntheticFunction with null body, and set the body later. Differential Revision: https://reviews.llvm.org/D44206 llvm-svn: 327149
This commit is contained in:
parent
3e4a82ffa2
commit
ebda41f812
|
@ -9,6 +9,7 @@
|
|||
|
||||
#include "lld/Common/Driver.h"
|
||||
#include "Config.h"
|
||||
#include "InputChunks.h"
|
||||
#include "InputGlobal.h"
|
||||
#include "MarkLive.h"
|
||||
#include "SymbolTable.h"
|
||||
|
@ -295,9 +296,11 @@ void LinkerDriver::link(ArrayRef<const char *> ArgsArr) {
|
|||
StackPointer->Live = true;
|
||||
|
||||
static WasmSignature NullSignature = {{}, WASM_TYPE_NORESULT};
|
||||
|
||||
// Add synthetic symbols before any others
|
||||
WasmSym::CallCtors = Symtab->addSyntheticFunction(
|
||||
"__wasm_call_ctors", &NullSignature, WASM_SYMBOL_VISIBILITY_HIDDEN);
|
||||
"__wasm_call_ctors", WASM_SYMBOL_VISIBILITY_HIDDEN,
|
||||
make<SyntheticFunction>(NullSignature, "__wasm_call_ctors"));
|
||||
WasmSym::StackPointer = Symtab->addSyntheticGlobal(
|
||||
"__stack_pointer", WASM_SYMBOL_VISIBILITY_HIDDEN, StackPointer);
|
||||
WasmSym::HeapBase = Symtab->addSyntheticDataSymbol("__heap_base", 0);
|
||||
|
|
|
@ -44,7 +44,7 @@ class OutputSegment;
|
|||
|
||||
class InputChunk {
|
||||
public:
|
||||
enum Kind { DataSegment, Function };
|
||||
enum Kind { DataSegment, Function, SyntheticFunction };
|
||||
|
||||
Kind kind() const { return SectionKind; }
|
||||
|
||||
|
@ -120,7 +120,8 @@ public:
|
|||
: InputChunk(F, InputChunk::Function), Signature(S), Function(Func) {}
|
||||
|
||||
static bool classof(const InputChunk *C) {
|
||||
return C->kind() == InputChunk::Function;
|
||||
return C->kind() == InputChunk::Function ||
|
||||
C->kind() == InputChunk::SyntheticFunction;
|
||||
}
|
||||
|
||||
StringRef getName() const override { return Function->Name; }
|
||||
|
@ -150,13 +151,20 @@ protected:
|
|||
|
||||
class SyntheticFunction : public InputFunction {
|
||||
public:
|
||||
SyntheticFunction(const WasmSignature &S, ArrayRef<uint8_t> Body,
|
||||
StringRef Name)
|
||||
: InputFunction(S, nullptr, nullptr), Name(Name), Body(Body) {}
|
||||
SyntheticFunction(const WasmSignature &S, StringRef Name)
|
||||
: InputFunction(S, nullptr, nullptr), Name(Name) {
|
||||
SectionKind = InputChunk::SyntheticFunction;
|
||||
}
|
||||
|
||||
static bool classof(const InputChunk *C) {
|
||||
return C->kind() == InputChunk::SyntheticFunction;
|
||||
}
|
||||
|
||||
StringRef getName() const override { return Name; }
|
||||
StringRef getComdat() const override { return StringRef(); }
|
||||
|
||||
void setBody(ArrayRef<uint8_t> Body_) { Body = Body_; }
|
||||
|
||||
protected:
|
||||
ArrayRef<uint8_t> data() const override { return Body; }
|
||||
|
||||
|
|
|
@ -119,11 +119,13 @@ static void checkDataType(const Symbol *Existing, const InputFile *File) {
|
|||
}
|
||||
|
||||
DefinedFunction *SymbolTable::addSyntheticFunction(StringRef Name,
|
||||
const WasmSignature *Type,
|
||||
uint32_t Flags) {
|
||||
uint32_t Flags,
|
||||
InputFunction *Function) {
|
||||
DEBUG(dbgs() << "addSyntheticFunction: " << Name << "\n");
|
||||
assert(!find(Name));
|
||||
return replaceSymbol<DefinedFunction>(insert(Name).first, Name, Flags, Type);
|
||||
SyntheticFunctions.emplace_back(Function);
|
||||
return replaceSymbol<DefinedFunction>(insert(Name).first, Name, Flags,
|
||||
nullptr, Function);
|
||||
}
|
||||
|
||||
DefinedData *SymbolTable::addSyntheticDataSymbol(StringRef Name,
|
||||
|
@ -137,6 +139,7 @@ DefinedGlobal *SymbolTable::addSyntheticGlobal(StringRef Name, uint32_t Flags,
|
|||
InputGlobal *Global) {
|
||||
DEBUG(dbgs() << "addSyntheticGlobal: " << Name << " -> " << Global << "\n");
|
||||
assert(!find(Name));
|
||||
SyntheticGlobals.emplace_back(Global);
|
||||
return replaceSymbol<DefinedGlobal>(insert(Name).first, Name, Flags, nullptr,
|
||||
Global);
|
||||
}
|
||||
|
|
|
@ -41,6 +41,8 @@ public:
|
|||
void addFile(InputFile *File);
|
||||
|
||||
std::vector<ObjFile *> ObjectFiles;
|
||||
std::vector<InputFunction *> SyntheticFunctions;
|
||||
std::vector<InputGlobal *> SyntheticGlobals;
|
||||
|
||||
void reportRemainingUndefines();
|
||||
|
||||
|
@ -68,9 +70,8 @@ public:
|
|||
DefinedData *addSyntheticDataSymbol(StringRef Name, uint32_t Flags);
|
||||
DefinedGlobal *addSyntheticGlobal(StringRef Name, uint32_t Flags,
|
||||
InputGlobal *Global);
|
||||
DefinedFunction *addSyntheticFunction(StringRef Name,
|
||||
const WasmSignature *Type,
|
||||
uint32_t Flags);
|
||||
DefinedFunction *addSyntheticFunction(StringRef Name, uint32_t Flags,
|
||||
InputFunction *Function);
|
||||
|
||||
private:
|
||||
std::pair<Symbol *, bool> insert(StringRef Name);
|
||||
|
|
|
@ -134,14 +134,9 @@ protected:
|
|||
|
||||
class DefinedFunction : public FunctionSymbol {
|
||||
public:
|
||||
// Primary constructor for file-defined functions.
|
||||
DefinedFunction(StringRef Name, uint32_t Flags, InputFile *F,
|
||||
InputFunction *Function);
|
||||
|
||||
// Second constructor used when creating synthetic functions.
|
||||
DefinedFunction(StringRef Name, uint32_t Flags, const WasmSignature *Type)
|
||||
: FunctionSymbol(Name, DefinedFunctionKind, Flags, nullptr, Type) {}
|
||||
|
||||
static bool classof(const Symbol *S) {
|
||||
return S->kind() == DefinedFunctionKind;
|
||||
}
|
||||
|
|
|
@ -750,16 +750,24 @@ void Writer::calculateTypes() {
|
|||
|
||||
void Writer::assignIndexes() {
|
||||
uint32_t FunctionIndex = NumImportedFunctions + InputFunctions.size();
|
||||
auto AddDefinedFunction = [&](InputFunction *Func) {
|
||||
if (!Func->Live)
|
||||
return;
|
||||
InputFunctions.emplace_back(Func);
|
||||
Func->setOutputIndex(FunctionIndex++);
|
||||
};
|
||||
|
||||
for (ObjFile *File : Symtab->ObjectFiles) {
|
||||
DEBUG(dbgs() << "Functions: " << File->getName() << "\n");
|
||||
for (InputFunction *Func : File->Functions) {
|
||||
if (!Func->Live)
|
||||
continue;
|
||||
InputFunctions.emplace_back(Func);
|
||||
Func->setOutputIndex(FunctionIndex++);
|
||||
}
|
||||
for (InputFunction *Func : File->Functions)
|
||||
AddDefinedFunction(Func);
|
||||
}
|
||||
|
||||
// TODO Move synthetic functions to come before (so __wasm_call_ctors can be
|
||||
// compiled immediately by the browser). Will reorder tests.
|
||||
for (InputFunction *Func : Symtab->SyntheticFunctions)
|
||||
AddDefinedFunction(Func);
|
||||
|
||||
uint32_t TableIndex = kInitialTableOffset;
|
||||
auto HandleRelocs = [&](InputChunk *Chunk) {
|
||||
if (!Chunk->Live)
|
||||
|
@ -806,8 +814,8 @@ void Writer::assignIndexes() {
|
|||
}
|
||||
};
|
||||
|
||||
if (WasmSym::StackPointer)
|
||||
AddDefinedGlobal(WasmSym::StackPointer->Global);
|
||||
for (InputGlobal *Global : Symtab->SyntheticGlobals)
|
||||
AddDefinedGlobal(Global);
|
||||
|
||||
for (ObjFile *File : Symtab->ObjectFiles) {
|
||||
DEBUG(dbgs() << "Globals: " << File->getName() << "\n");
|
||||
|
@ -852,8 +860,6 @@ static const int OPCODE_END = 0xb;
|
|||
// Create synthetic "__wasm_call_ctors" function based on ctor functions
|
||||
// in input object.
|
||||
void Writer::createCtorFunction() {
|
||||
uint32_t FunctionIndex = NumImportedFunctions + InputFunctions.size();
|
||||
|
||||
// First write the body's contents to a string.
|
||||
std::string BodyContent;
|
||||
{
|
||||
|
@ -874,15 +880,8 @@ void Writer::createCtorFunction() {
|
|||
OS << BodyContent;
|
||||
}
|
||||
|
||||
const WasmSignature *Sig = WasmSym::CallCtors->getFunctionType();
|
||||
SyntheticFunction *F =
|
||||
make<SyntheticFunction>(*Sig, toArrayRef(Saver.save(FunctionBody)),
|
||||
WasmSym::CallCtors->getName());
|
||||
|
||||
F->setOutputIndex(FunctionIndex);
|
||||
F->Live = true;
|
||||
WasmSym::CallCtors->Function = F;
|
||||
InputFunctions.emplace_back(F);
|
||||
ArrayRef<uint8_t> Body = toArrayRef(Saver.save(FunctionBody));
|
||||
cast<SyntheticFunction>(WasmSym::CallCtors->Function)->setBody(Body);
|
||||
}
|
||||
|
||||
// Populate InitFunctions vector with init functions from all input objects.
|
||||
|
|
Loading…
Reference in New Issue