summaryrefslogtreecommitdiffstats
path: root/llvm/lib/MC
diff options
context:
space:
mode:
Diffstat (limited to 'llvm/lib/MC')
-rw-r--r--llvm/lib/MC/MCParser/WasmAsmParser.cpp46
-rw-r--r--llvm/lib/MC/MCSectionWasm.cpp3
-rw-r--r--llvm/lib/MC/WasmObjectWriter.cpp20
3 files changed, 58 insertions, 11 deletions
diff --git a/llvm/lib/MC/MCParser/WasmAsmParser.cpp b/llvm/lib/MC/MCParser/WasmAsmParser.cpp
index 17d86aa0d64..a8a48d1cd69 100644
--- a/llvm/lib/MC/MCParser/WasmAsmParser.cpp
+++ b/llvm/lib/MC/MCParser/WasmAsmParser.cpp
@@ -81,13 +81,53 @@ public:
return false;
}
+ bool parseSectionFlags(StringRef FlagStr, bool &Passive) {
+ SmallVector<StringRef, 2> Flags;
+ // If there are no flags, keep Flags empty
+ FlagStr.split(Flags, ",", -1, false);
+ for (auto &Flag : Flags) {
+ if (Flag == "passive")
+ Passive = true;
+ else
+ return error("Expected section flags, instead got: ", Lexer->getTok());
+ }
+ return false;
+ }
+
bool parseSectionDirective(StringRef, SMLoc) {
StringRef Name;
if (Parser->parseIdentifier(Name))
return TokError("expected identifier in directive");
- // FIXME: currently requiring this very fixed format.
- if (expect(AsmToken::Comma, ",") || expect(AsmToken::String, "string") ||
- expect(AsmToken::Comma, ",") || expect(AsmToken::At, "@") ||
+
+ if (expect(AsmToken::Comma, ","))
+ return true;
+
+ if (Lexer->isNot(AsmToken::String))
+ return error("expected string in directive, instead got: ", Lexer->getTok());
+
+ SectionKind Kind = StringSwitch<SectionKind>(Name)
+ .StartsWith(".data", SectionKind::getData())
+ .StartsWith(".rodata", SectionKind::getReadOnly())
+ .StartsWith(".text", SectionKind::getText())
+ .StartsWith(".custom_section", SectionKind::getMetadata());
+
+ MCSectionWasm* Section = getContext().getWasmSection(Name, Kind);
+
+ // Update section flags if present in this .section directive
+ bool Passive = false;
+ if (parseSectionFlags(getTok().getStringContents(), Passive))
+ return true;
+
+ if (Passive) {
+ if (!Section->isWasmData())
+ return Parser->Error(getTok().getLoc(),
+ "Only data sections can be passive");
+ Section->setPassive();
+ }
+
+ Lex();
+
+ if (expect(AsmToken::Comma, ",") || expect(AsmToken::At, "@") ||
expect(AsmToken::EndOfStatement, "eol"))
return true;
// This is done automatically by the assembler for text sections currently,
diff --git a/llvm/lib/MC/MCSectionWasm.cpp b/llvm/lib/MC/MCSectionWasm.cpp
index 164ded9a1f8..8633c10a73f 100644
--- a/llvm/lib/MC/MCSectionWasm.cpp
+++ b/llvm/lib/MC/MCSectionWasm.cpp
@@ -62,7 +62,8 @@ void MCSectionWasm::PrintSwitchToSection(const MCAsmInfo &MAI, const Triple &T,
printName(OS, getSectionName());
OS << ",\"";
- // TODO: Print section flags.
+ if (IsPassive)
+ OS << "passive";
OS << '"';
diff --git a/llvm/lib/MC/WasmObjectWriter.cpp b/llvm/lib/MC/WasmObjectWriter.cpp
index 600928c05bc..10f16ba3c8f 100644
--- a/llvm/lib/MC/WasmObjectWriter.cpp
+++ b/llvm/lib/MC/WasmObjectWriter.cpp
@@ -106,9 +106,10 @@ struct WasmSignatureDenseMapInfo {
struct WasmDataSegment {
MCSectionWasm *Section;
StringRef Name;
+ uint32_t InitFlags;
uint32_t Offset;
uint32_t Alignment;
- uint32_t Flags;
+ uint32_t LinkerFlags;
SmallVector<char, 4> Data;
};
@@ -899,10 +900,14 @@ void WasmObjectWriter::writeDataSection() {
encodeULEB128(DataSegments.size(), W.OS); // count
for (const WasmDataSegment &Segment : DataSegments) {
- encodeULEB128(0, W.OS); // memory index
- W.OS << char(wasm::WASM_OPCODE_I32_CONST);
- encodeSLEB128(Segment.Offset, W.OS); // offset
- W.OS << char(wasm::WASM_OPCODE_END);
+ encodeULEB128(Segment.InitFlags, W.OS); // flags
+ if (Segment.InitFlags & wasm::WASM_SEGMENT_HAS_MEMINDEX)
+ encodeULEB128(0, W.OS); // memory index
+ if ((Segment.InitFlags & wasm::WASM_SEGMENT_IS_PASSIVE) == 0) {
+ W.OS << char(wasm::WASM_OPCODE_I32_CONST);
+ encodeSLEB128(Segment.Offset, W.OS); // offset
+ W.OS << char(wasm::WASM_OPCODE_END);
+ }
encodeULEB128(Segment.Data.size(), W.OS); // size
Segment.Section->setSectionOffset(W.OS.tell() - Section.ContentsOffset);
W.OS << Segment.Data; // data
@@ -1013,7 +1018,7 @@ void WasmObjectWriter::writeLinkingMetaDataSection(
for (const WasmDataSegment &Segment : DataSegments) {
writeString(Segment.Name);
encodeULEB128(Segment.Alignment, W.OS);
- encodeULEB128(Segment.Flags, W.OS);
+ encodeULEB128(Segment.LinkerFlags, W.OS);
}
endSection(SubSection);
}
@@ -1253,11 +1258,12 @@ uint64_t WasmObjectWriter::writeObject(MCAssembler &Asm,
DataSegments.emplace_back();
WasmDataSegment &Segment = DataSegments.back();
Segment.Name = SectionName;
+ Segment.InitFlags = Section.getPassive() ? wasm::WASM_SEGMENT_IS_PASSIVE : 0;
Segment.Offset = DataSize;
Segment.Section = &Section;
addData(Segment.Data, Section);
Segment.Alignment = Log2_32(Section.getAlignment());
- Segment.Flags = 0;
+ Segment.LinkerFlags = 0;
DataSize += Segment.Data.size();
Section.setSegmentIndex(SegmentIndex);
OpenPOWER on IntegriCloud