1//===- WasmYAML.cpp - Wasm YAMLIO implementation --------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// This file defines classes for handling the YAML representation of wasm.
10//
11//===----------------------------------------------------------------------===//
12
13#include "llvm/ObjectYAML/WasmYAML.h"
14#include "llvm/ADT/StringRef.h"
15#include "llvm/BinaryFormat/Wasm.h"
16#include "llvm/Support/Casting.h"
17#include "llvm/Support/ErrorHandling.h"
18#include "llvm/Support/YAMLTraits.h"
19
20namespace llvm {
21
22namespace WasmYAML {
23
24// Declared here rather than in the header to comply with:
25// http://llvm.org/docs/CodingStandards.html#provide-a-virtual-method-anchor-for-classes-in-headers
26Section::~Section() = default;
27
28} // end namespace WasmYAML
29
30namespace yaml {
31
32void MappingTraits<WasmYAML::FileHeader>::mapping(
33 IO &IO, WasmYAML::FileHeader &FileHdr) {
34 IO.mapRequired(Key: "Version", Val&: FileHdr.Version);
35}
36
37void MappingTraits<WasmYAML::Object>::mapping(IO &IO,
38 WasmYAML::Object &Object) {
39 IO.setContext(&Object);
40 IO.mapTag(Tag: "!WASM", Default: true);
41 IO.mapRequired(Key: "FileHeader", Val&: Object.Header);
42 IO.mapOptional(Key: "Sections", Val&: Object.Sections);
43 IO.setContext(nullptr);
44}
45
46static void commonSectionMapping(IO &IO, WasmYAML::Section &Section) {
47 IO.mapRequired(Key: "Type", Val&: Section.Type);
48 IO.mapOptional(Key: "Relocations", Val&: Section.Relocations);
49 IO.mapOptional(Key: "HeaderSecSizeEncodingLen", Val&: Section.HeaderSecSizeEncodingLen);
50}
51
52static void sectionMapping(IO &IO, WasmYAML::DylinkSection &Section) {
53 commonSectionMapping(IO, Section);
54 IO.mapRequired(Key: "Name", Val&: Section.Name);
55 IO.mapRequired(Key: "MemorySize", Val&: Section.MemorySize);
56 IO.mapRequired(Key: "MemoryAlignment", Val&: Section.MemoryAlignment);
57 IO.mapRequired(Key: "TableSize", Val&: Section.TableSize);
58 IO.mapRequired(Key: "TableAlignment", Val&: Section.TableAlignment);
59 IO.mapRequired(Key: "Needed", Val&: Section.Needed);
60 IO.mapOptional(Key: "ImportInfo", Val&: Section.ImportInfo);
61 IO.mapOptional(Key: "ExportInfo", Val&: Section.ExportInfo);
62}
63
64static void sectionMapping(IO &IO, WasmYAML::NameSection &Section) {
65 commonSectionMapping(IO, Section);
66 IO.mapRequired(Key: "Name", Val&: Section.Name);
67 IO.mapOptional(Key: "FunctionNames", Val&: Section.FunctionNames);
68 IO.mapOptional(Key: "GlobalNames", Val&: Section.GlobalNames);
69 IO.mapOptional(Key: "DataSegmentNames", Val&: Section.DataSegmentNames);
70}
71
72static void sectionMapping(IO &IO, WasmYAML::LinkingSection &Section) {
73 commonSectionMapping(IO, Section);
74 IO.mapRequired(Key: "Name", Val&: Section.Name);
75 IO.mapRequired(Key: "Version", Val&: Section.Version);
76 IO.mapOptional(Key: "SymbolTable", Val&: Section.SymbolTable);
77 IO.mapOptional(Key: "SegmentInfo", Val&: Section.SegmentInfos);
78 IO.mapOptional(Key: "InitFunctions", Val&: Section.InitFunctions);
79 IO.mapOptional(Key: "Comdats", Val&: Section.Comdats);
80}
81
82static void sectionMapping(IO &IO, WasmYAML::ProducersSection &Section) {
83 commonSectionMapping(IO, Section);
84 IO.mapRequired(Key: "Name", Val&: Section.Name);
85 IO.mapOptional(Key: "Languages", Val&: Section.Languages);
86 IO.mapOptional(Key: "Tools", Val&: Section.Tools);
87 IO.mapOptional(Key: "SDKs", Val&: Section.SDKs);
88}
89
90static void sectionMapping(IO &IO, WasmYAML::TargetFeaturesSection &Section) {
91 commonSectionMapping(IO, Section);
92 IO.mapRequired(Key: "Name", Val&: Section.Name);
93 IO.mapRequired(Key: "Features", Val&: Section.Features);
94}
95
96static void sectionMapping(IO &IO, WasmYAML::CustomSection &Section) {
97 commonSectionMapping(IO, Section);
98 IO.mapRequired(Key: "Name", Val&: Section.Name);
99 IO.mapRequired(Key: "Payload", Val&: Section.Payload);
100}
101
102static void sectionMapping(IO &IO, WasmYAML::TypeSection &Section) {
103 commonSectionMapping(IO, Section);
104 IO.mapOptional(Key: "Signatures", Val&: Section.Signatures);
105}
106
107static void sectionMapping(IO &IO, WasmYAML::ImportSection &Section) {
108 commonSectionMapping(IO, Section);
109 IO.mapOptional(Key: "Imports", Val&: Section.Imports);
110}
111
112static void sectionMapping(IO &IO, WasmYAML::FunctionSection &Section) {
113 commonSectionMapping(IO, Section);
114 IO.mapOptional(Key: "FunctionTypes", Val&: Section.FunctionTypes);
115}
116
117static void sectionMapping(IO &IO, WasmYAML::TableSection &Section) {
118 commonSectionMapping(IO, Section);
119 IO.mapOptional(Key: "Tables", Val&: Section.Tables);
120}
121
122static void sectionMapping(IO &IO, WasmYAML::MemorySection &Section) {
123 commonSectionMapping(IO, Section);
124 IO.mapOptional(Key: "Memories", Val&: Section.Memories);
125}
126
127static void sectionMapping(IO &IO, WasmYAML::TagSection &Section) {
128 commonSectionMapping(IO, Section);
129 IO.mapOptional(Key: "TagTypes", Val&: Section.TagTypes);
130}
131
132static void sectionMapping(IO &IO, WasmYAML::GlobalSection &Section) {
133 commonSectionMapping(IO, Section);
134 IO.mapOptional(Key: "Globals", Val&: Section.Globals);
135}
136
137static void sectionMapping(IO &IO, WasmYAML::ExportSection &Section) {
138 commonSectionMapping(IO, Section);
139 IO.mapOptional(Key: "Exports", Val&: Section.Exports);
140}
141
142static void sectionMapping(IO &IO, WasmYAML::StartSection &Section) {
143 commonSectionMapping(IO, Section);
144 IO.mapOptional(Key: "StartFunction", Val&: Section.StartFunction);
145}
146
147static void sectionMapping(IO &IO, WasmYAML::ElemSection &Section) {
148 commonSectionMapping(IO, Section);
149 IO.mapOptional(Key: "Segments", Val&: Section.Segments);
150}
151
152static void sectionMapping(IO &IO, WasmYAML::CodeSection &Section) {
153 commonSectionMapping(IO, Section);
154 IO.mapRequired(Key: "Functions", Val&: Section.Functions);
155}
156
157static void sectionMapping(IO &IO, WasmYAML::DataSection &Section) {
158 commonSectionMapping(IO, Section);
159 IO.mapRequired(Key: "Segments", Val&: Section.Segments);
160}
161
162static void sectionMapping(IO &IO, WasmYAML::DataCountSection &Section) {
163 commonSectionMapping(IO, Section);
164 IO.mapRequired(Key: "Count", Val&: Section.Count);
165}
166
167void MappingTraits<std::unique_ptr<WasmYAML::Section>>::mapping(
168 IO &IO, std::unique_ptr<WasmYAML::Section> &Section) {
169 WasmYAML::SectionType SectionType;
170 if (IO.outputting())
171 SectionType = Section->Type;
172 else
173 IO.mapRequired(Key: "Type", Val&: SectionType);
174
175 switch (SectionType) {
176 case wasm::WASM_SEC_CUSTOM: {
177 StringRef SectionName;
178 if (IO.outputting()) {
179 auto CustomSection = cast<WasmYAML::CustomSection>(Val: Section.get());
180 SectionName = CustomSection->Name;
181 } else {
182 IO.mapRequired(Key: "Name", Val&: SectionName);
183 }
184 if (SectionName == "dylink" || SectionName == "dylink.0") {
185 if (!IO.outputting())
186 Section.reset(p: new WasmYAML::DylinkSection());
187 sectionMapping(IO, Section&: *cast<WasmYAML::DylinkSection>(Val: Section.get()));
188 } else if (SectionName == "linking") {
189 if (!IO.outputting())
190 Section.reset(p: new WasmYAML::LinkingSection());
191 sectionMapping(IO, Section&: *cast<WasmYAML::LinkingSection>(Val: Section.get()));
192 } else if (SectionName == "name") {
193 if (!IO.outputting())
194 Section.reset(p: new WasmYAML::NameSection());
195 sectionMapping(IO, Section&: *cast<WasmYAML::NameSection>(Val: Section.get()));
196 } else if (SectionName == "producers") {
197 if (!IO.outputting())
198 Section.reset(p: new WasmYAML::ProducersSection());
199 sectionMapping(IO, Section&: *cast<WasmYAML::ProducersSection>(Val: Section.get()));
200 } else if (SectionName == "target_features") {
201 if (!IO.outputting())
202 Section.reset(p: new WasmYAML::TargetFeaturesSection());
203 sectionMapping(IO, Section&: *cast<WasmYAML::TargetFeaturesSection>(Val: Section.get()));
204 } else {
205 if (!IO.outputting())
206 Section.reset(p: new WasmYAML::CustomSection(SectionName));
207 sectionMapping(IO, Section&: *cast<WasmYAML::CustomSection>(Val: Section.get()));
208 }
209 break;
210 }
211 case wasm::WASM_SEC_TYPE:
212 if (!IO.outputting())
213 Section.reset(p: new WasmYAML::TypeSection());
214 sectionMapping(IO, Section&: *cast<WasmYAML::TypeSection>(Val: Section.get()));
215 break;
216 case wasm::WASM_SEC_IMPORT:
217 if (!IO.outputting())
218 Section.reset(p: new WasmYAML::ImportSection());
219 sectionMapping(IO, Section&: *cast<WasmYAML::ImportSection>(Val: Section.get()));
220 break;
221 case wasm::WASM_SEC_FUNCTION:
222 if (!IO.outputting())
223 Section.reset(p: new WasmYAML::FunctionSection());
224 sectionMapping(IO, Section&: *cast<WasmYAML::FunctionSection>(Val: Section.get()));
225 break;
226 case wasm::WASM_SEC_TABLE:
227 if (!IO.outputting())
228 Section.reset(p: new WasmYAML::TableSection());
229 sectionMapping(IO, Section&: *cast<WasmYAML::TableSection>(Val: Section.get()));
230 break;
231 case wasm::WASM_SEC_MEMORY:
232 if (!IO.outputting())
233 Section.reset(p: new WasmYAML::MemorySection());
234 sectionMapping(IO, Section&: *cast<WasmYAML::MemorySection>(Val: Section.get()));
235 break;
236 case wasm::WASM_SEC_TAG:
237 if (!IO.outputting())
238 Section.reset(p: new WasmYAML::TagSection());
239 sectionMapping(IO, Section&: *cast<WasmYAML::TagSection>(Val: Section.get()));
240 break;
241 case wasm::WASM_SEC_GLOBAL:
242 if (!IO.outputting())
243 Section.reset(p: new WasmYAML::GlobalSection());
244 sectionMapping(IO, Section&: *cast<WasmYAML::GlobalSection>(Val: Section.get()));
245 break;
246 case wasm::WASM_SEC_EXPORT:
247 if (!IO.outputting())
248 Section.reset(p: new WasmYAML::ExportSection());
249 sectionMapping(IO, Section&: *cast<WasmYAML::ExportSection>(Val: Section.get()));
250 break;
251 case wasm::WASM_SEC_START:
252 if (!IO.outputting())
253 Section.reset(p: new WasmYAML::StartSection());
254 sectionMapping(IO, Section&: *cast<WasmYAML::StartSection>(Val: Section.get()));
255 break;
256 case wasm::WASM_SEC_ELEM:
257 if (!IO.outputting())
258 Section.reset(p: new WasmYAML::ElemSection());
259 sectionMapping(IO, Section&: *cast<WasmYAML::ElemSection>(Val: Section.get()));
260 break;
261 case wasm::WASM_SEC_CODE:
262 if (!IO.outputting())
263 Section.reset(p: new WasmYAML::CodeSection());
264 sectionMapping(IO, Section&: *cast<WasmYAML::CodeSection>(Val: Section.get()));
265 break;
266 case wasm::WASM_SEC_DATA:
267 if (!IO.outputting())
268 Section.reset(p: new WasmYAML::DataSection());
269 sectionMapping(IO, Section&: *cast<WasmYAML::DataSection>(Val: Section.get()));
270 break;
271 case wasm::WASM_SEC_DATACOUNT:
272 if (!IO.outputting())
273 Section.reset(p: new WasmYAML::DataCountSection());
274 sectionMapping(IO, Section&: *cast<WasmYAML::DataCountSection>(Val: Section.get()));
275 break;
276 default:
277 llvm_unreachable("Unknown section type");
278 }
279}
280
281void ScalarEnumerationTraits<WasmYAML::SectionType>::enumeration(
282 IO &IO, WasmYAML::SectionType &Type) {
283#define ECase(X) IO.enumCase(Type, #X, wasm::WASM_SEC_##X);
284 ECase(CUSTOM);
285 ECase(TYPE);
286 ECase(IMPORT);
287 ECase(FUNCTION);
288 ECase(TABLE);
289 ECase(MEMORY);
290 ECase(GLOBAL);
291 ECase(TAG);
292 ECase(EXPORT);
293 ECase(START);
294 ECase(ELEM);
295 ECase(CODE);
296 ECase(DATA);
297 ECase(DATACOUNT);
298#undef ECase
299}
300
301void MappingTraits<WasmYAML::Signature>::mapping(
302 IO &IO, WasmYAML::Signature &Signature) {
303 IO.mapRequired(Key: "Index", Val&: Signature.Index);
304 IO.mapRequired(Key: "ParamTypes", Val&: Signature.ParamTypes);
305 IO.mapRequired(Key: "ReturnTypes", Val&: Signature.ReturnTypes);
306}
307
308void MappingTraits<WasmYAML::Table>::mapping(IO &IO, WasmYAML::Table &Table) {
309 IO.mapRequired(Key: "Index", Val&: Table.Index);
310 IO.mapRequired(Key: "ElemType", Val&: Table.ElemType);
311 IO.mapRequired(Key: "Limits", Val&: Table.TableLimits);
312}
313
314void MappingTraits<WasmYAML::Function>::mapping(IO &IO,
315 WasmYAML::Function &Function) {
316 IO.mapRequired(Key: "Index", Val&: Function.Index);
317 IO.mapRequired(Key: "Locals", Val&: Function.Locals);
318 IO.mapRequired(Key: "Body", Val&: Function.Body);
319}
320
321void MappingTraits<WasmYAML::Relocation>::mapping(
322 IO &IO, WasmYAML::Relocation &Relocation) {
323 IO.mapRequired(Key: "Type", Val&: Relocation.Type);
324 IO.mapRequired(Key: "Index", Val&: Relocation.Index);
325 IO.mapRequired(Key: "Offset", Val&: Relocation.Offset);
326 IO.mapOptional(Key: "Addend", Val&: Relocation.Addend, Default: 0);
327}
328
329void MappingTraits<WasmYAML::NameEntry>::mapping(
330 IO &IO, WasmYAML::NameEntry &NameEntry) {
331 IO.mapRequired(Key: "Index", Val&: NameEntry.Index);
332 IO.mapRequired(Key: "Name", Val&: NameEntry.Name);
333}
334
335void MappingTraits<WasmYAML::ProducerEntry>::mapping(
336 IO &IO, WasmYAML::ProducerEntry &ProducerEntry) {
337 IO.mapRequired(Key: "Name", Val&: ProducerEntry.Name);
338 IO.mapRequired(Key: "Version", Val&: ProducerEntry.Version);
339}
340
341void ScalarEnumerationTraits<WasmYAML::FeaturePolicyPrefix>::enumeration(
342 IO &IO, WasmYAML::FeaturePolicyPrefix &Kind) {
343#define ECase(X) IO.enumCase(Kind, #X, wasm::WASM_FEATURE_PREFIX_##X);
344 ECase(USED);
345 ECase(REQUIRED);
346 ECase(DISALLOWED);
347#undef ECase
348}
349
350void MappingTraits<WasmYAML::FeatureEntry>::mapping(
351 IO &IO, WasmYAML::FeatureEntry &FeatureEntry) {
352 IO.mapRequired(Key: "Prefix", Val&: FeatureEntry.Prefix);
353 IO.mapRequired(Key: "Name", Val&: FeatureEntry.Name);
354}
355
356void MappingTraits<WasmYAML::SegmentInfo>::mapping(
357 IO &IO, WasmYAML::SegmentInfo &SegmentInfo) {
358 IO.mapRequired(Key: "Index", Val&: SegmentInfo.Index);
359 IO.mapRequired(Key: "Name", Val&: SegmentInfo.Name);
360 IO.mapRequired(Key: "Alignment", Val&: SegmentInfo.Alignment);
361 IO.mapRequired(Key: "Flags", Val&: SegmentInfo.Flags);
362}
363
364void MappingTraits<WasmYAML::LocalDecl>::mapping(
365 IO &IO, WasmYAML::LocalDecl &LocalDecl) {
366 IO.mapRequired(Key: "Type", Val&: LocalDecl.Type);
367 IO.mapRequired(Key: "Count", Val&: LocalDecl.Count);
368}
369
370void MappingTraits<WasmYAML::Limits>::mapping(IO &IO,
371 WasmYAML::Limits &Limits) {
372 IO.mapOptional(Key: "Flags", Val&: Limits.Flags, Default: 0);
373 IO.mapRequired(Key: "Minimum", Val&: Limits.Minimum);
374 if (!IO.outputting() || Limits.Flags & wasm::WASM_LIMITS_FLAG_HAS_MAX)
375 IO.mapOptional(Key: "Maximum", Val&: Limits.Maximum);
376}
377
378void MappingTraits<WasmYAML::ElemSegment>::mapping(
379 IO &IO, WasmYAML::ElemSegment &Segment) {
380 IO.mapOptional(Key: "Flags", Val&: Segment.Flags, Default: 0);
381 if (!IO.outputting() ||
382 Segment.Flags & wasm::WASM_ELEM_SEGMENT_HAS_TABLE_NUMBER)
383 IO.mapOptional(Key: "TableNumber", Val&: Segment.TableNumber);
384 if (!IO.outputting() ||
385 Segment.Flags & wasm::WASM_ELEM_SEGMENT_MASK_HAS_ELEM_KIND)
386 IO.mapOptional(Key: "ElemKind", Val&: Segment.ElemKind);
387 // TODO: Omit "offset" for passive segments? It's neither meaningful nor
388 // encoded.
389 IO.mapRequired(Key: "Offset", Val&: Segment.Offset);
390 IO.mapRequired(Key: "Functions", Val&: Segment.Functions);
391}
392
393void MappingTraits<WasmYAML::Import>::mapping(IO &IO,
394 WasmYAML::Import &Import) {
395 IO.mapRequired(Key: "Module", Val&: Import.Module);
396 IO.mapRequired(Key: "Field", Val&: Import.Field);
397 IO.mapRequired(Key: "Kind", Val&: Import.Kind);
398 if (Import.Kind == wasm::WASM_EXTERNAL_FUNCTION ||
399 Import.Kind == wasm::WASM_EXTERNAL_TAG) {
400 IO.mapRequired(Key: "SigIndex", Val&: Import.SigIndex);
401 } else if (Import.Kind == wasm::WASM_EXTERNAL_GLOBAL) {
402 IO.mapRequired(Key: "GlobalType", Val&: Import.GlobalImport.Type);
403 IO.mapRequired(Key: "GlobalMutable", Val&: Import.GlobalImport.Mutable);
404 } else if (Import.Kind == wasm::WASM_EXTERNAL_TABLE) {
405 IO.mapRequired(Key: "Table", Val&: Import.TableImport);
406 } else if (Import.Kind == wasm::WASM_EXTERNAL_MEMORY) {
407 IO.mapRequired(Key: "Memory", Val&: Import.Memory);
408 } else {
409 llvm_unreachable("unhandled import type");
410 }
411}
412
413void MappingTraits<WasmYAML::Export>::mapping(IO &IO,
414 WasmYAML::Export &Export) {
415 IO.mapRequired(Key: "Name", Val&: Export.Name);
416 IO.mapRequired(Key: "Kind", Val&: Export.Kind);
417 IO.mapRequired(Key: "Index", Val&: Export.Index);
418}
419
420void MappingTraits<WasmYAML::Global>::mapping(IO &IO,
421 WasmYAML::Global &Global) {
422 IO.mapRequired(Key: "Index", Val&: Global.Index);
423 IO.mapRequired(Key: "Type", Val&: Global.Type);
424 IO.mapRequired(Key: "Mutable", Val&: Global.Mutable);
425 IO.mapRequired(Key: "InitExpr", Val&: Global.Init);
426}
427
428void MappingTraits<WasmYAML::InitExpr>::mapping(IO &IO,
429 WasmYAML::InitExpr &Expr) {
430 IO.mapOptional(Key: "Extended", Val&: Expr.Extended, Default: false);
431 if (Expr.Extended) {
432 IO.mapRequired(Key: "Body", Val&: Expr.Body);
433 } else {
434 WasmYAML::Opcode Op = Expr.Inst.Opcode;
435 IO.mapRequired(Key: "Opcode", Val&: Op);
436 Expr.Inst.Opcode = Op;
437 switch (Expr.Inst.Opcode) {
438 case wasm::WASM_OPCODE_I32_CONST:
439 IO.mapRequired(Key: "Value", Val&: Expr.Inst.Value.Int32);
440 break;
441 case wasm::WASM_OPCODE_I64_CONST:
442 IO.mapRequired(Key: "Value", Val&: Expr.Inst.Value.Int64);
443 break;
444 case wasm::WASM_OPCODE_F32_CONST:
445 IO.mapRequired(Key: "Value", Val&: Expr.Inst.Value.Float32);
446 break;
447 case wasm::WASM_OPCODE_F64_CONST:
448 IO.mapRequired(Key: "Value", Val&: Expr.Inst.Value.Float64);
449 break;
450 case wasm::WASM_OPCODE_GLOBAL_GET:
451 IO.mapRequired(Key: "Index", Val&: Expr.Inst.Value.Global);
452 break;
453 case wasm::WASM_OPCODE_REF_NULL: {
454 WasmYAML::ValueType Ty = wasm::WASM_TYPE_EXTERNREF;
455 IO.mapRequired(Key: "Type", Val&: Ty);
456 break;
457 }
458 }
459 }
460}
461
462void MappingTraits<WasmYAML::DataSegment>::mapping(
463 IO &IO, WasmYAML::DataSegment &Segment) {
464 IO.mapOptional(Key: "SectionOffset", Val&: Segment.SectionOffset);
465 IO.mapRequired(Key: "InitFlags", Val&: Segment.InitFlags);
466 if (Segment.InitFlags & wasm::WASM_DATA_SEGMENT_HAS_MEMINDEX) {
467 IO.mapRequired(Key: "MemoryIndex", Val&: Segment.MemoryIndex);
468 } else {
469 Segment.MemoryIndex = 0;
470 }
471 if ((Segment.InitFlags & wasm::WASM_DATA_SEGMENT_IS_PASSIVE) == 0) {
472 IO.mapRequired(Key: "Offset", Val&: Segment.Offset);
473 } else {
474 Segment.Offset.Inst.Opcode = wasm::WASM_OPCODE_I32_CONST;
475 Segment.Offset.Inst.Value.Int32 = 0;
476 }
477 IO.mapRequired(Key: "Content", Val&: Segment.Content);
478}
479
480void MappingTraits<WasmYAML::InitFunction>::mapping(
481 IO &IO, WasmYAML::InitFunction &Init) {
482 IO.mapRequired(Key: "Priority", Val&: Init.Priority);
483 IO.mapRequired(Key: "Symbol", Val&: Init.Symbol);
484}
485
486void ScalarEnumerationTraits<WasmYAML::ComdatKind>::enumeration(
487 IO &IO, WasmYAML::ComdatKind &Kind) {
488#define ECase(X) IO.enumCase(Kind, #X, wasm::WASM_COMDAT_##X);
489 ECase(FUNCTION);
490 ECase(DATA);
491 ECase(SECTION);
492#undef ECase
493}
494
495void MappingTraits<WasmYAML::ComdatEntry>::mapping(
496 IO &IO, WasmYAML::ComdatEntry &ComdatEntry) {
497 IO.mapRequired(Key: "Kind", Val&: ComdatEntry.Kind);
498 IO.mapRequired(Key: "Index", Val&: ComdatEntry.Index);
499}
500
501void MappingTraits<WasmYAML::Comdat>::mapping(IO &IO,
502 WasmYAML::Comdat &Comdat) {
503 IO.mapRequired(Key: "Name", Val&: Comdat.Name);
504 IO.mapRequired(Key: "Entries", Val&: Comdat.Entries);
505}
506
507void MappingTraits<WasmYAML::SymbolInfo>::mapping(IO &IO,
508 WasmYAML::SymbolInfo &Info) {
509 IO.mapRequired(Key: "Index", Val&: Info.Index);
510 IO.mapRequired(Key: "Kind", Val&: Info.Kind);
511 if (Info.Kind != wasm::WASM_SYMBOL_TYPE_SECTION)
512 IO.mapRequired(Key: "Name", Val&: Info.Name);
513 IO.mapRequired(Key: "Flags", Val&: Info.Flags);
514 if (Info.Kind == wasm::WASM_SYMBOL_TYPE_FUNCTION) {
515 IO.mapRequired(Key: "Function", Val&: Info.ElementIndex);
516 } else if (Info.Kind == wasm::WASM_SYMBOL_TYPE_GLOBAL) {
517 IO.mapRequired(Key: "Global", Val&: Info.ElementIndex);
518 } else if (Info.Kind == wasm::WASM_SYMBOL_TYPE_TABLE) {
519 IO.mapRequired(Key: "Table", Val&: Info.ElementIndex);
520 } else if (Info.Kind == wasm::WASM_SYMBOL_TYPE_TAG) {
521 IO.mapRequired(Key: "Tag", Val&: Info.ElementIndex);
522 } else if (Info.Kind == wasm::WASM_SYMBOL_TYPE_DATA) {
523 if ((Info.Flags & wasm::WASM_SYMBOL_UNDEFINED) == 0) {
524 if ((Info.Flags & wasm::WASM_SYMBOL_ABSOLUTE) == 0) {
525 IO.mapRequired(Key: "Segment", Val&: Info.DataRef.Segment);
526 }
527 IO.mapOptional(Key: "Offset", Val&: Info.DataRef.Offset, Default: 0u);
528 IO.mapRequired(Key: "Size", Val&: Info.DataRef.Size);
529 }
530 } else if (Info.Kind == wasm::WASM_SYMBOL_TYPE_SECTION) {
531 IO.mapRequired(Key: "Section", Val&: Info.ElementIndex);
532 } else {
533 llvm_unreachable("unsupported symbol kind");
534 }
535}
536
537void MappingTraits<WasmYAML::DylinkImportInfo>::mapping(
538 IO &IO, WasmYAML::DylinkImportInfo &Info) {
539 IO.mapRequired(Key: "Module", Val&: Info.Module);
540 IO.mapRequired(Key: "Field", Val&: Info.Field);
541 IO.mapRequired(Key: "Flags", Val&: Info.Flags);
542}
543
544void MappingTraits<WasmYAML::DylinkExportInfo>::mapping(
545 IO &IO, WasmYAML::DylinkExportInfo &Info) {
546 IO.mapRequired(Key: "Name", Val&: Info.Name);
547 IO.mapRequired(Key: "Flags", Val&: Info.Flags);
548}
549
550void ScalarBitSetTraits<WasmYAML::LimitFlags>::bitset(
551 IO &IO, WasmYAML::LimitFlags &Value) {
552#define BCase(X) IO.bitSetCase(Value, #X, wasm::WASM_LIMITS_FLAG_##X)
553 BCase(HAS_MAX);
554 BCase(IS_SHARED);
555 BCase(IS_64);
556#undef BCase
557}
558
559void ScalarBitSetTraits<WasmYAML::SegmentFlags>::bitset(
560 IO &IO, WasmYAML::SegmentFlags &Value) {
561#define BCase(X) IO.bitSetCase(Value, #X, wasm::WASM_SEG_FLAG_##X)
562 BCase(STRINGS);
563 BCase(TLS);
564 BCase(RETAIN);
565#undef BCase
566}
567
568void ScalarBitSetTraits<WasmYAML::SymbolFlags>::bitset(
569 IO &IO, WasmYAML::SymbolFlags &Value) {
570#define BCaseMask(M, X) \
571 IO.maskedBitSetCase(Value, #X, wasm::WASM_SYMBOL_##X, wasm::WASM_SYMBOL_##M)
572 // BCaseMask(BINDING_MASK, BINDING_GLOBAL);
573 BCaseMask(BINDING_MASK, BINDING_WEAK);
574 BCaseMask(BINDING_MASK, BINDING_LOCAL);
575 // BCaseMask(VISIBILITY_MASK, VISIBILITY_DEFAULT);
576 BCaseMask(VISIBILITY_MASK, VISIBILITY_HIDDEN);
577 BCaseMask(UNDEFINED, UNDEFINED);
578 BCaseMask(EXPORTED, EXPORTED);
579 BCaseMask(EXPLICIT_NAME, EXPLICIT_NAME);
580 BCaseMask(NO_STRIP, NO_STRIP);
581 BCaseMask(TLS, TLS);
582 BCaseMask(ABSOLUTE, ABSOLUTE);
583#undef BCaseMask
584}
585
586void ScalarEnumerationTraits<WasmYAML::SymbolKind>::enumeration(
587 IO &IO, WasmYAML::SymbolKind &Kind) {
588#define ECase(X) IO.enumCase(Kind, #X, wasm::WASM_SYMBOL_TYPE_##X);
589 ECase(FUNCTION);
590 ECase(DATA);
591 ECase(GLOBAL);
592 ECase(TABLE);
593 ECase(SECTION);
594 ECase(TAG);
595#undef ECase
596}
597
598void ScalarEnumerationTraits<WasmYAML::ValueType>::enumeration(
599 IO &IO, WasmYAML::ValueType &Type) {
600#define CONCAT(X) (uint32_t) wasm::ValType::X
601#define ECase(X) IO.enumCase(Type, #X, CONCAT(X));
602 ECase(I32);
603 ECase(I64);
604 ECase(F32);
605 ECase(F64);
606 ECase(V128);
607 ECase(FUNCREF);
608 ECase(EXTERNREF);
609 ECase(EXNREF);
610 ECase(OTHERREF);
611#undef ECase
612}
613
614void ScalarEnumerationTraits<WasmYAML::ExportKind>::enumeration(
615 IO &IO, WasmYAML::ExportKind &Kind) {
616#define ECase(X) IO.enumCase(Kind, #X, wasm::WASM_EXTERNAL_##X);
617 ECase(FUNCTION);
618 ECase(TABLE);
619 ECase(MEMORY);
620 ECase(GLOBAL);
621 ECase(TAG);
622#undef ECase
623}
624
625void ScalarEnumerationTraits<WasmYAML::Opcode>::enumeration(
626 IO &IO, WasmYAML::Opcode &Code) {
627#define ECase(X) IO.enumCase(Code, #X, wasm::WASM_OPCODE_##X);
628 ECase(END);
629 ECase(I32_CONST);
630 ECase(I64_CONST);
631 ECase(F64_CONST);
632 ECase(F32_CONST);
633 ECase(GLOBAL_GET);
634 ECase(REF_NULL);
635#undef ECase
636}
637
638void ScalarEnumerationTraits<WasmYAML::TableType>::enumeration(
639 IO &IO, WasmYAML::TableType &Type) {
640#define CONCAT(X) (uint32_t) wasm::ValType::X
641#define ECase(X) IO.enumCase(Type, #X, CONCAT(X));
642 ECase(FUNCREF);
643 ECase(EXTERNREF);
644 ECase(EXNREF);
645 ECase(OTHERREF);
646#undef ECase
647}
648
649void ScalarEnumerationTraits<WasmYAML::RelocType>::enumeration(
650 IO &IO, WasmYAML::RelocType &Type) {
651#define WASM_RELOC(name, value) IO.enumCase(Type, #name, wasm::name);
652#include "llvm/BinaryFormat/WasmRelocs.def"
653#undef WASM_RELOC
654 IO.enumFallback<Hex32>(Val&: Type);
655}
656
657} // end namespace yaml
658
659} // end namespace llvm
660