1
0
mirror of https://github.com/RPCS3/llvm-mirror.git synced 2025-01-31 20:51:52 +01:00

[WebAssembly] Move event section before global section

Summary:
https://github.com/WebAssembly/exception-handling/issues/98

Also this moves many parts of code to make code align with the section
order, even if they don't affect the output.

Reviewers: tlively

Subscribers: dschuff, sbc100, hiraditya, sunfish, llvm-commits

Tags: #llvm

Differential Revision: https://reviews.llvm.org/D76752
This commit is contained in:
Heejin Ahn 2020-03-24 19:36:13 -07:00
parent cf74eac3d0
commit 58a2f8e25d
6 changed files with 116 additions and 96 deletions

View File

@ -242,8 +242,8 @@ private:
Error parseFunctionSection(ReadContext &Ctx);
Error parseTableSection(ReadContext &Ctx);
Error parseMemorySection(ReadContext &Ctx);
Error parseGlobalSection(ReadContext &Ctx);
Error parseEventSection(ReadContext &Ctx);
Error parseGlobalSection(ReadContext &Ctx);
Error parseExportSection(ReadContext &Ctx);
Error parseStartSection(ReadContext &Ctx);
Error parseElemSection(ReadContext &Ctx);
@ -290,8 +290,8 @@ private:
uint32_t NumImportedEvents = 0;
uint32_t CodeSection = 0;
uint32_t DataSection = 0;
uint32_t GlobalSection = 0;
uint32_t EventSection = 0;
uint32_t GlobalSection = 0;
};
class WasmSectionOrderChecker {
@ -307,8 +307,8 @@ public:
WASM_SEC_ORDER_FUNCTION,
WASM_SEC_ORDER_TABLE,
WASM_SEC_ORDER_MEMORY,
WASM_SEC_ORDER_GLOBAL,
WASM_SEC_ORDER_EVENT,
WASM_SEC_ORDER_GLOBAL,
WASM_SEC_ORDER_EXPORT,
WASM_SEC_ORDER_START,
WASM_SEC_ORDER_ELEM,

View File

@ -309,16 +309,6 @@ struct MemorySection : Section {
std::vector<Limits> Memories;
};
struct GlobalSection : Section {
GlobalSection() : Section(wasm::WASM_SEC_GLOBAL) {}
static bool classof(const Section *S) {
return S->Type == wasm::WASM_SEC_GLOBAL;
}
std::vector<Global> Globals;
};
struct EventSection : Section {
EventSection() : Section(wasm::WASM_SEC_EVENT) {}
@ -329,6 +319,16 @@ struct EventSection : Section {
std::vector<Event> Events;
};
struct GlobalSection : Section {
GlobalSection() : Section(wasm::WASM_SEC_GLOBAL) {}
static bool classof(const Section *S) {
return S->Type == wasm::WASM_SEC_GLOBAL;
}
std::vector<Global> Globals;
};
struct ExportSection : Section {
ExportSection() : Section(wasm::WASM_SEC_EXPORT) {}

View File

@ -302,10 +302,10 @@ Error WasmObjectFile::parseSection(WasmSection &Sec) {
return parseTableSection(Ctx);
case wasm::WASM_SEC_MEMORY:
return parseMemorySection(Ctx);
case wasm::WASM_SEC_GLOBAL:
return parseGlobalSection(Ctx);
case wasm::WASM_SEC_EVENT:
return parseEventSection(Ctx);
case wasm::WASM_SEC_GLOBAL:
return parseGlobalSection(Ctx);
case wasm::WASM_SEC_EXPORT:
return parseExportSection(Ctx);
case wasm::WASM_SEC_START:
@ -993,6 +993,24 @@ Error WasmObjectFile::parseMemorySection(ReadContext &Ctx) {
return Error::success();
}
Error WasmObjectFile::parseEventSection(ReadContext &Ctx) {
EventSection = Sections.size();
uint32_t Count = readVarint32(Ctx);
Events.reserve(Count);
while (Count--) {
wasm::WasmEvent Event;
Event.Index = NumImportedEvents + Events.size();
Event.Type.Attribute = readVaruint32(Ctx);
Event.Type.SigIndex = readVarint32(Ctx);
Events.push_back(Event);
}
if (Ctx.Ptr != Ctx.End)
return make_error<GenericBinaryError>("Event section ended prematurely",
object_error::parse_failed);
return Error::success();
}
Error WasmObjectFile::parseGlobalSection(ReadContext &Ctx) {
GlobalSection = Sections.size();
uint32_t Count = readVaruint32(Ctx);
@ -1012,24 +1030,6 @@ Error WasmObjectFile::parseGlobalSection(ReadContext &Ctx) {
return Error::success();
}
Error WasmObjectFile::parseEventSection(ReadContext &Ctx) {
EventSection = Sections.size();
uint32_t Count = readVarint32(Ctx);
Events.reserve(Count);
while (Count--) {
wasm::WasmEvent Event;
Event.Index = NumImportedEvents + Events.size();
Event.Type.Attribute = readVaruint32(Ctx);
Event.Type.SigIndex = readVarint32(Ctx);
Events.push_back(Event);
}
if (Ctx.Ptr != Ctx.End)
return make_error<GenericBinaryError>("Event section ended prematurely",
object_error::parse_failed);
return Error::success();
}
Error WasmObjectFile::parseExportSection(ReadContext &Ctx) {
uint32_t Count = readVaruint32(Ctx);
Exports.reserve(Count);
@ -1622,30 +1622,50 @@ int WasmSectionOrderChecker::getSectionOrder(unsigned ID,
// Represents the edges in a directed graph where any node B reachable from node
// A is not allowed to appear before A in the section ordering, but may appear
// afterward.
int WasmSectionOrderChecker::DisallowedPredecessors[WASM_NUM_SEC_ORDERS][WASM_NUM_SEC_ORDERS] = {
{}, // WASM_SEC_ORDER_NONE
{WASM_SEC_ORDER_TYPE, WASM_SEC_ORDER_IMPORT}, // WASM_SEC_ORDER_TYPE,
{WASM_SEC_ORDER_IMPORT, WASM_SEC_ORDER_FUNCTION}, // WASM_SEC_ORDER_IMPORT,
{WASM_SEC_ORDER_FUNCTION, WASM_SEC_ORDER_TABLE}, // WASM_SEC_ORDER_FUNCTION,
{WASM_SEC_ORDER_TABLE, WASM_SEC_ORDER_MEMORY}, // WASM_SEC_ORDER_TABLE,
{WASM_SEC_ORDER_MEMORY, WASM_SEC_ORDER_GLOBAL}, // WASM_SEC_ORDER_MEMORY,
{WASM_SEC_ORDER_GLOBAL, WASM_SEC_ORDER_EVENT}, // WASM_SEC_ORDER_GLOBAL,
{WASM_SEC_ORDER_EVENT, WASM_SEC_ORDER_EXPORT}, // WASM_SEC_ORDER_EVENT,
{WASM_SEC_ORDER_EXPORT, WASM_SEC_ORDER_START}, // WASM_SEC_ORDER_EXPORT,
{WASM_SEC_ORDER_START, WASM_SEC_ORDER_ELEM}, // WASM_SEC_ORDER_START,
{WASM_SEC_ORDER_ELEM, WASM_SEC_ORDER_DATACOUNT}, // WASM_SEC_ORDER_ELEM,
{WASM_SEC_ORDER_DATACOUNT, WASM_SEC_ORDER_CODE}, // WASM_SEC_ORDER_DATACOUNT,
{WASM_SEC_ORDER_CODE, WASM_SEC_ORDER_DATA}, // WASM_SEC_ORDER_CODE,
{WASM_SEC_ORDER_DATA, WASM_SEC_ORDER_LINKING}, // WASM_SEC_ORDER_DATA,
int WasmSectionOrderChecker::DisallowedPredecessors
[WASM_NUM_SEC_ORDERS][WASM_NUM_SEC_ORDERS] = {
// WASM_SEC_ORDER_NONE
{},
// WASM_SEC_ORDER_TYPE
{WASM_SEC_ORDER_TYPE, WASM_SEC_ORDER_IMPORT},
// WASM_SEC_ORDER_IMPORT
{WASM_SEC_ORDER_IMPORT, WASM_SEC_ORDER_FUNCTION},
// WASM_SEC_ORDER_FUNCTION
{WASM_SEC_ORDER_FUNCTION, WASM_SEC_ORDER_TABLE},
// WASM_SEC_ORDER_TABLE
{WASM_SEC_ORDER_TABLE, WASM_SEC_ORDER_MEMORY},
// WASM_SEC_ORDER_MEMORY
{WASM_SEC_ORDER_MEMORY, WASM_SEC_ORDER_EVENT},
// WASM_SEC_ORDER_EVENT
{WASM_SEC_ORDER_EVENT, WASM_SEC_ORDER_GLOBAL},
// WASM_SEC_ORDER_GLOBAL
{WASM_SEC_ORDER_GLOBAL, WASM_SEC_ORDER_EXPORT},
// WASM_SEC_ORDER_EXPORT
{WASM_SEC_ORDER_EXPORT, WASM_SEC_ORDER_START},
// WASM_SEC_ORDER_START
{WASM_SEC_ORDER_START, WASM_SEC_ORDER_ELEM},
// WASM_SEC_ORDER_ELEM
{WASM_SEC_ORDER_ELEM, WASM_SEC_ORDER_DATACOUNT},
// WASM_SEC_ORDER_DATACOUNT
{WASM_SEC_ORDER_DATACOUNT, WASM_SEC_ORDER_CODE},
// WASM_SEC_ORDER_CODE
{WASM_SEC_ORDER_CODE, WASM_SEC_ORDER_DATA},
// WASM_SEC_ORDER_DATA
{WASM_SEC_ORDER_DATA, WASM_SEC_ORDER_LINKING},
// Custom Sections
{WASM_SEC_ORDER_DYLINK, WASM_SEC_ORDER_TYPE}, // WASM_SEC_ORDER_DYLINK,
{WASM_SEC_ORDER_LINKING, WASM_SEC_ORDER_RELOC, WASM_SEC_ORDER_NAME}, // WASM_SEC_ORDER_LINKING,
{}, // WASM_SEC_ORDER_RELOC (can be repeated),
{WASM_SEC_ORDER_NAME, WASM_SEC_ORDER_PRODUCERS}, // WASM_SEC_ORDER_NAME,
{WASM_SEC_ORDER_PRODUCERS, WASM_SEC_ORDER_TARGET_FEATURES}, // WASM_SEC_ORDER_PRODUCERS,
{WASM_SEC_ORDER_TARGET_FEATURES} // WASM_SEC_ORDER_TARGET_FEATURES
};
// Custom Sections
// WASM_SEC_ORDER_DYLINK
{WASM_SEC_ORDER_DYLINK, WASM_SEC_ORDER_TYPE},
// WASM_SEC_ORDER_LINKING
{WASM_SEC_ORDER_LINKING, WASM_SEC_ORDER_RELOC, WASM_SEC_ORDER_NAME},
// WASM_SEC_ORDER_RELOC (can be repeated)
{},
// WASM_SEC_ORDER_NAME
{WASM_SEC_ORDER_NAME, WASM_SEC_ORDER_PRODUCERS},
// WASM_SEC_ORDER_PRODUCERS
{WASM_SEC_ORDER_PRODUCERS, WASM_SEC_ORDER_TARGET_FEATURES},
// WASM_SEC_ORDER_TARGET_FEATURES
{WASM_SEC_ORDER_TARGET_FEATURES}};
bool WasmSectionOrderChecker::isValidSectionOrder(unsigned ID,
StringRef CustomSectionName) {

View File

@ -41,8 +41,8 @@ private:
void writeSectionContent(raw_ostream &OS, WasmYAML::FunctionSection &Section);
void writeSectionContent(raw_ostream &OS, WasmYAML::TableSection &Section);
void writeSectionContent(raw_ostream &OS, WasmYAML::MemorySection &Section);
void writeSectionContent(raw_ostream &OS, WasmYAML::GlobalSection &Section);
void writeSectionContent(raw_ostream &OS, WasmYAML::EventSection &Section);
void writeSectionContent(raw_ostream &OS, WasmYAML::GlobalSection &Section);
void writeSectionContent(raw_ostream &OS, WasmYAML::ExportSection &Section);
void writeSectionContent(raw_ostream &OS, WasmYAML::StartSection &Section);
void writeSectionContent(raw_ostream &OS, WasmYAML::ElemSection &Section);
@ -414,6 +414,21 @@ void WasmWriter::writeSectionContent(raw_ostream &OS,
writeLimits(Mem, OS);
}
void WasmWriter::writeSectionContent(raw_ostream &OS,
WasmYAML::EventSection &Section) {
encodeULEB128(Section.Events.size(), OS);
uint32_t ExpectedIndex = NumImportedEvents;
for (auto &Event : Section.Events) {
if (Event.Index != ExpectedIndex) {
reportError("unexpected event index: " + Twine(Event.Index));
return;
}
++ExpectedIndex;
encodeULEB128(Event.Attribute, OS);
encodeULEB128(Event.SigIndex, OS);
}
}
void WasmWriter::writeSectionContent(raw_ostream &OS,
WasmYAML::GlobalSection &Section) {
encodeULEB128(Section.Globals.size(), OS);
@ -430,21 +445,6 @@ void WasmWriter::writeSectionContent(raw_ostream &OS,
}
}
void WasmWriter::writeSectionContent(raw_ostream &OS,
WasmYAML::EventSection &Section) {
encodeULEB128(Section.Events.size(), OS);
uint32_t ExpectedIndex = NumImportedEvents;
for (auto &Event : Section.Events) {
if (Event.Index != ExpectedIndex) {
reportError("unexpected event index: " + Twine(Event.Index));
return;
}
++ExpectedIndex;
encodeULEB128(Event.Attribute, OS);
encodeULEB128(Event.SigIndex, OS);
}
}
void WasmWriter::writeSectionContent(raw_ostream &OS,
WasmYAML::ElemSection &Section) {
encodeULEB128(Section.Segments.size(), OS);
@ -571,10 +571,10 @@ bool WasmWriter::writeWasm(raw_ostream &OS) {
writeSectionContent(StringStream, *S);
else if (auto S = dyn_cast<WasmYAML::MemorySection>(Sec.get()))
writeSectionContent(StringStream, *S);
else if (auto S = dyn_cast<WasmYAML::GlobalSection>(Sec.get()))
writeSectionContent(StringStream, *S);
else if (auto S = dyn_cast<WasmYAML::EventSection>(Sec.get()))
writeSectionContent(StringStream, *S);
else if (auto S = dyn_cast<WasmYAML::GlobalSection>(Sec.get()))
writeSectionContent(StringStream, *S);
else if (auto S = dyn_cast<WasmYAML::ExportSection>(Sec.get()))
writeSectionContent(StringStream, *S);
else if (auto S = dyn_cast<WasmYAML::StartSection>(Sec.get()))

View File

@ -118,16 +118,16 @@ static void sectionMapping(IO &IO, WasmYAML::MemorySection &Section) {
IO.mapOptional("Memories", Section.Memories);
}
static void sectionMapping(IO &IO, WasmYAML::GlobalSection &Section) {
commonSectionMapping(IO, Section);
IO.mapOptional("Globals", Section.Globals);
}
static void sectionMapping(IO &IO, WasmYAML::EventSection &Section) {
commonSectionMapping(IO, Section);
IO.mapOptional("Events", Section.Events);
}
static void sectionMapping(IO &IO, WasmYAML::GlobalSection &Section) {
commonSectionMapping(IO, Section);
IO.mapOptional("Globals", Section.Globals);
}
static void sectionMapping(IO &IO, WasmYAML::ExportSection &Section) {
commonSectionMapping(IO, Section);
IO.mapOptional("Exports", Section.Exports);
@ -227,16 +227,16 @@ void MappingTraits<std::unique_ptr<WasmYAML::Section>>::mapping(
Section.reset(new WasmYAML::MemorySection());
sectionMapping(IO, *cast<WasmYAML::MemorySection>(Section.get()));
break;
case wasm::WASM_SEC_GLOBAL:
if (!IO.outputting())
Section.reset(new WasmYAML::GlobalSection());
sectionMapping(IO, *cast<WasmYAML::GlobalSection>(Section.get()));
break;
case wasm::WASM_SEC_EVENT:
if (!IO.outputting())
Section.reset(new WasmYAML::EventSection());
sectionMapping(IO, *cast<WasmYAML::EventSection>(Section.get()));
break;
case wasm::WASM_SEC_GLOBAL:
if (!IO.outputting())
Section.reset(new WasmYAML::GlobalSection());
sectionMapping(IO, *cast<WasmYAML::GlobalSection>(Section.get()));
break;
case wasm::WASM_SEC_EXPORT:
if (!IO.outputting())
Section.reset(new WasmYAML::ExportSection());

View File

@ -262,6 +262,18 @@ ErrorOr<WasmYAML::Object *> WasmDumper::dump() {
S = std::move(MemorySec);
break;
}
case wasm::WASM_SEC_EVENT: {
auto EventSec = std::make_unique<WasmYAML::EventSection>();
for (auto &Event : Obj.events()) {
WasmYAML::Event E;
E.Index = Event.Index;
E.Attribute = Event.Type.Attribute;
E.SigIndex = Event.Type.SigIndex;
EventSec->Events.push_back(E);
}
S = std::move(EventSec);
break;
}
case wasm::WASM_SEC_GLOBAL: {
auto GlobalSec = std::make_unique<WasmYAML::GlobalSection>();
for (auto &Global : Obj.globals()) {
@ -275,18 +287,6 @@ ErrorOr<WasmYAML::Object *> WasmDumper::dump() {
S = std::move(GlobalSec);
break;
}
case wasm::WASM_SEC_EVENT: {
auto EventSec = std::make_unique<WasmYAML::EventSection>();
for (auto &Event : Obj.events()) {
WasmYAML::Event E;
E.Index = Event.Index;
E.Attribute = Event.Type.Attribute;
E.SigIndex = Event.Type.SigIndex;
EventSec->Events.push_back(E);
}
S = std::move(EventSec);
break;
}
case wasm::WASM_SEC_START: {
auto StartSec = std::make_unique<WasmYAML::StartSection>();
StartSec->StartFunction = Obj.startFunction();