1use crate::core::*;
16use crate::AstCustomization;
17use std::io::Write;
18use wasmparser::{BinaryReader, Operator, OperatorsReader, Parser, Payload};
19
20impl TryFrom<wasmparser::RefType> for RefType {
21 type Error = String;
22
23 fn try_from(value: wasmparser::RefType) -> Result<Self, Self::Error> {
24 match value {
25 wasmparser::RefType::FUNCREF => Ok(RefType::FuncRef),
26 wasmparser::RefType::EXTERNREF => Ok(RefType::ExternRef),
27 _ => Err("Unsupported reference type: {value:?}".to_string()),
28 }
29 }
30}
31
32impl TryFrom<wasmparser::ValType> for ValType {
33 type Error = String;
34
35 fn try_from(value: wasmparser::ValType) -> Result<Self, Self::Error> {
36 match value {
37 wasmparser::ValType::I32 => Ok(ValType::Num(NumType::I32)),
38 wasmparser::ValType::I64 => Ok(ValType::Num(NumType::I64)),
39 wasmparser::ValType::F32 => Ok(ValType::Num(NumType::F32)),
40 wasmparser::ValType::F64 => Ok(ValType::Num(NumType::F64)),
41 wasmparser::ValType::V128 => Ok(ValType::Vec(VecType::V128)),
42 wasmparser::ValType::Ref(r) => Ok(ValType::Ref(r.try_into()?)),
43 }
44 }
45}
46
47impl TryFrom<&[wasmparser::ValType]> for ResultType {
48 type Error = String;
49
50 fn try_from(value: &[wasmparser::ValType]) -> Result<Self, Self::Error> {
51 let values = value
52 .iter()
53 .map(|v| (*v).try_into())
54 .collect::<Result<Vec<ValType>, Self::Error>>()?;
55 Ok(ResultType { values })
56 }
57}
58
59impl TryFrom<wasmparser::FuncType> for FuncType {
60 type Error = String;
61
62 fn try_from(value: wasmparser::FuncType) -> Result<Self, Self::Error> {
63 let params = value.params().try_into()?;
64 let results = value.results().try_into()?;
65 Ok(FuncType {
66 input: params,
67 output: results,
68 })
69 }
70}
71
72impl TryFrom<wasmparser::TableType> for TableType {
73 type Error = String;
74
75 fn try_from(value: wasmparser::TableType) -> Result<Self, Self::Error> {
76 Ok(TableType {
77 limits: Limits {
78 min: value.initial,
79 max: value.maximum,
80 },
81 elements: value.element_type.try_into()?,
82 })
83 }
84}
85
86impl TryFrom<wasmparser::MemoryType> for MemType {
87 type Error = String;
88
89 fn try_from(value: wasmparser::MemoryType) -> Result<Self, Self::Error> {
90 if value.memory64 {
91 Err("64-bit memories are not supported".to_string())
92 } else {
93 Ok(MemType {
94 limits: Limits {
95 min: value.initial,
96 max: value.maximum,
97 },
98 })
99 }
100 }
101}
102
103impl TryFrom<wasmparser::GlobalType> for GlobalType {
104 type Error = String;
105
106 fn try_from(value: wasmparser::GlobalType) -> Result<Self, Self::Error> {
107 Ok(GlobalType {
108 mutability: if value.mutable { Mut::Var } else { Mut::Const },
109 val_type: value.content_type.try_into()?,
110 })
111 }
112}
113
114impl TryFrom<wasmparser::TypeRef> for TypeRef {
115 type Error = String;
116
117 fn try_from(value: wasmparser::TypeRef) -> Result<Self, Self::Error> {
118 match value {
119 wasmparser::TypeRef::Func(func_idx) => Ok(TypeRef::Func(func_idx)),
120 wasmparser::TypeRef::Table(table_type) => Ok(TypeRef::Table(table_type.try_into()?)),
121 wasmparser::TypeRef::Memory(mem_type) => Ok(TypeRef::Mem(mem_type.try_into()?)),
122 wasmparser::TypeRef::Global(global_type) => {
123 Ok(TypeRef::Global(global_type.try_into()?))
124 }
125 wasmparser::TypeRef::Tag(_) => {
126 Err("Exception handling proposal is not supported".to_string())
127 }
128 }
129 }
130}
131
132impl TryFrom<wasmparser::Import<'_>> for Import {
133 type Error = String;
134
135 fn try_from(value: wasmparser::Import) -> Result<Self, Self::Error> {
136 Ok(Import {
137 module: value.module.to_string(),
138 name: value.name.to_string(),
139 desc: value.ty.try_into()?,
140 })
141 }
142}
143
144impl TryFrom<wasmparser::Table<'_>> for Table {
145 type Error = String;
146
147 fn try_from(value: wasmparser::Table) -> Result<Self, Self::Error> {
148 Ok(Table {
149 table_type: value.ty.try_into()?,
150 })
151 }
152}
153
154impl TryFrom<wasmparser::MemoryType> for Mem {
155 type Error = String;
156
157 fn try_from(value: wasmparser::MemoryType) -> Result<Self, Self::Error> {
158 Ok(Mem {
159 mem_type: value.try_into()?,
160 })
161 }
162}
163
164impl<'a> TryFrom<wasmparser::Global<'a>> for Global {
165 type Error = String;
166
167 fn try_from(value: wasmparser::Global<'a>) -> Result<Self, Self::Error> {
168 let op_reader = value.init_expr.get_operators_reader();
169 let init = op_reader.try_into()?;
170 Ok(Global {
171 global_type: value.ty.try_into()?,
172 init,
173 })
174 }
175}
176
177impl TryFrom<wasmparser::BlockType> for BlockType {
178 type Error = String;
179
180 fn try_from(value: wasmparser::BlockType) -> Result<Self, Self::Error> {
181 match value {
182 wasmparser::BlockType::Empty => Ok(BlockType::None),
183 wasmparser::BlockType::Type(val_type) => Ok(BlockType::Value(val_type.try_into()?)),
184 wasmparser::BlockType::FuncType(type_idx) => Ok(BlockType::Index(type_idx)),
185 }
186 }
187}
188
189impl TryFrom<wasmparser::MemArg> for MemArg {
190 type Error = String;
191
192 fn try_from(value: wasmparser::MemArg) -> Result<Self, Self::Error> {
193 if value.offset > (u32::MAX as u64) {
194 Err("64-bit memories are not supported".to_string())
195 } else {
196 Ok(MemArg {
197 offset: value.offset as u32,
198 align: value.align,
199 })
200 }
201 }
202}
203
204impl TryFrom<wasmparser::HeapType> for RefType {
205 type Error = String;
206
207 fn try_from(value: wasmparser::HeapType) -> Result<Self, Self::Error> {
208 if value == wasmparser::HeapType::EXTERN {
209 Ok(RefType::ExternRef)
210 } else if value == wasmparser::HeapType::FUNC {
211 Ok(RefType::FuncRef)
212 } else {
213 Err("GC proposal is not supported".to_string())
214 }
215 }
216}
217
218impl TryFrom<wasmparser::Export<'_>> for Export {
219 type Error = String;
220
221 fn try_from(value: wasmparser::Export) -> Result<Self, Self::Error> {
222 let desc = match value.kind {
223 wasmparser::ExternalKind::Func => Ok(ExportDesc::Func(value.index)),
224 wasmparser::ExternalKind::Table => Ok(ExportDesc::Table(value.index)),
225 wasmparser::ExternalKind::Memory => Ok(ExportDesc::Mem(value.index)),
226 wasmparser::ExternalKind::Global => Ok(ExportDesc::Global(value.index)),
227 wasmparser::ExternalKind::Tag => {
228 Err("Exception handling proposal is not supported".to_string())
229 }
230 }?;
231 Ok(Export {
232 name: value.name.to_string(),
233 desc,
234 })
235 }
236}
237
238impl TryFrom<wasmparser::ElementKind<'_>> for ElemMode {
239 type Error = String;
240
241 fn try_from(value: wasmparser::ElementKind) -> Result<Self, Self::Error> {
242 match value {
243 wasmparser::ElementKind::Passive => Ok(ElemMode::Passive),
244 wasmparser::ElementKind::Active {
245 table_index,
246 offset_expr,
247 } => Ok(ElemMode::Active {
248 table_idx: table_index.unwrap_or(0),
249 offset: offset_expr.get_operators_reader().try_into()?,
250 }),
251 wasmparser::ElementKind::Declared => Ok(ElemMode::Declarative),
252 }
253 }
254}
255
256impl<T: TryFromExprSource> TryFrom<wasmparser::Element<'_>> for Elem<T> {
257 type Error = String;
258
259 fn try_from(value: wasmparser::Element) -> Result<Self, Self::Error> {
260 let r: Result<(RefType, Vec<T>), String> = match value.items {
261 wasmparser::ElementItems::Functions(indices) => {
262 let mut init = Vec::new();
263 for func_idx in indices {
264 let func_idx = func_idx
265 .map_err(|e| format!("Error parsing core module element: {e:?}"))?;
266 let expr_source = RefFuncExprSource::new(func_idx);
267 init.push(T::try_from(expr_source)?);
268 }
269 Ok((RefType::FuncRef, init))
270 }
271 wasmparser::ElementItems::Expressions(ref_type, exprs) => {
272 let mut init = Vec::new();
273 for expr in exprs {
274 let expr =
275 expr.map_err(|e| format!("Error parsing core module element: {e:?}"))?;
276 let expr_source = OperatorsReaderExprSource::new(expr.get_operators_reader());
277 let expr: T = T::try_from(expr_source)?;
278 init.push(expr);
279 }
280 Ok((ref_type.try_into()?, init))
281 }
282 };
283 let (ref_type, init) = r?;
284
285 Ok(Elem {
286 ref_type,
287 mode: value.kind.try_into()?,
288 init,
289 })
290 }
291}
292
293impl<T: TryFromExprSource + Debug + Clone + PartialEq> TryFrom<wasmparser::DataKind<'_>>
294 for DataMode<T>
295{
296 type Error = String;
297
298 fn try_from(value: wasmparser::DataKind) -> Result<Self, Self::Error> {
299 match value {
300 wasmparser::DataKind::Passive => Ok(DataMode::Passive),
301 wasmparser::DataKind::Active {
302 memory_index,
303 offset_expr,
304 } => {
305 let operators_reader =
306 OperatorsReaderExprSource::new(offset_expr.get_operators_reader());
307 Ok(DataMode::Active {
308 memory: memory_index,
309 offset: T::try_from(operators_reader)?,
310 })
311 }
312 }
313 }
314}
315
316impl<T: TryFromExprSource + Debug + Clone + PartialEq> TryFrom<wasmparser::Data<'_>> for Data<T> {
317 type Error = String;
318
319 fn try_from(value: wasmparser::Data) -> Result<Self, Self::Error> {
320 Ok(Data {
321 init: value.data.to_vec(),
322 mode: value.kind.try_into()?,
323 })
324 }
325}
326
327impl<T: TryFromExprSource> TryFrom<wasmparser::FunctionBody<'_>> for FuncCode<T> {
328 type Error = String;
329
330 fn try_from(value: wasmparser::FunctionBody) -> Result<Self, Self::Error> {
331 let mut locals = Vec::new();
332
333 for local_groups in value
334 .get_locals_reader()
335 .map_err(|e| format!("Error parsing core module function body: {e:?}"))?
336 {
337 let (count, val_type) = local_groups
338 .map_err(|e| format!("Error parsing core module function body: {e:?}"))?;
339 let val_type: ValType = val_type.try_into()?;
340 for _ in 0..count {
341 locals.push(val_type.clone());
342 }
343 }
344
345 let expr_source = OperatorsReaderExprSource::new(
346 value
347 .get_operators_reader()
348 .map_err(|e| format!("Error parsing core module function body: {e:?}"))?,
349 );
350 let body: T = T::try_from(expr_source)?;
351
352 Ok(FuncCode { locals, body })
353 }
354}
355
356enum OperatorTarget {
357 TopLevel(Vec<Instr>),
358 Block(BlockType, Vec<Instr>),
359 Loop(BlockType, Vec<Instr>),
360 If(BlockType, Vec<Instr>),
361 Else(BlockType, Vec<Instr>, Vec<Instr>),
362}
363
364impl OperatorTarget {
365 pub fn push(&mut self, instr: Instr) {
366 match self {
367 OperatorTarget::TopLevel(instructions) => instructions.push(instr),
368 OperatorTarget::Block(_, instructions) => instructions.push(instr),
369 OperatorTarget::Loop(_, instructions) => instructions.push(instr),
370 OperatorTarget::If(_, instructions) => instructions.push(instr),
371 OperatorTarget::Else(_, _, instructions) => instructions.push(instr),
372 }
373 }
374}
375
376impl TryFrom<OperatorsReader<'_>> for Expr {
377 type Error = String;
378
379 fn try_from(value: OperatorsReader) -> Result<Self, Self::Error> {
380 let mut stack = vec![OperatorTarget::TopLevel(Vec::new())];
381
382 for op in value {
383 let op = op.map_err(|e| format!("Error parsing core module instruction: {e:?}"))?;
384
385 let instr = match op {
386 Operator::Unreachable => Some(Instr::Unreachable),
387 Operator::Nop => Some(Instr::Nop),
388 Operator::Block { blockty } => {
389 let block_type = blockty.try_into()?;
390 stack.push(OperatorTarget::Block(block_type, Vec::new()));
391 None
392 }
393 Operator::Loop { blockty } => {
394 let block_type = blockty.try_into()?;
395 stack.push(OperatorTarget::Loop(block_type, Vec::new()));
396 None
397 }
398 Operator::If { blockty } => {
399 let block_type = blockty.try_into()?;
400 stack.push(OperatorTarget::If(block_type, Vec::new()));
401 None
402 }
403 Operator::Else => {
404 match stack.pop() {
405 Some(OperatorTarget::If(block_type, true_instrs)) => {
406 stack.push(OperatorTarget::Else(block_type, true_instrs, Vec::new()));
407 }
408 _ => {
409 return Err(
410 "Else operator must be preceded by an if operator".to_string()
411 );
412 }
413 }
414 None
415 }
416 Operator::Try { .. } => {
417 return Err("Exception handling proposal is not supported".to_string());
418 }
419 Operator::Catch { .. } => {
420 return Err("Exception handling proposal is not supported".to_string());
421 }
422 Operator::Throw { .. } => {
423 return Err("Exception handling proposal is not supported".to_string());
424 }
425 Operator::Rethrow { .. } => {
426 return Err("Exception handling proposal is not supported".to_string());
427 }
428 Operator::End => match stack.pop() {
429 Some(OperatorTarget::Block(block_type, instrs)) => {
430 Some(Instr::Block(block_type, instrs))
431 }
432 Some(OperatorTarget::Loop(block_type, instrs)) => {
433 Some(Instr::Loop(block_type, instrs))
434 }
435 Some(OperatorTarget::If(block_type, true_instrs)) => {
436 Some(Instr::If(block_type, true_instrs, Vec::new()))
437 }
438 Some(OperatorTarget::Else(block_type, true_instrs, false_instrs)) => {
439 Some(Instr::If(block_type, true_instrs, false_instrs))
440 }
441 Some(OperatorTarget::TopLevel(instrs)) => {
442 stack.push(OperatorTarget::TopLevel(instrs));
443 None
444 }
445 None => {
446 return Err(
447 "End operator must be preceded by a block, loop, or if operator"
448 .to_string(),
449 );
450 }
451 },
452 Operator::Br { relative_depth } => Some(Instr::Br(relative_depth)),
453 Operator::BrIf { relative_depth } => Some(Instr::BrIf(relative_depth)),
454 Operator::BrTable { targets } => {
455 let labels: Vec<LabelIdx> = targets
456 .targets()
457 .map(|r| r.map_err(|err| format!("Failed to read brtable labels: {err:?}")))
458 .collect::<Result<Vec<LabelIdx>, String>>()?;
459 Some(Instr::BrTable(labels, targets.default()))
460 }
461 Operator::Return => Some(Instr::Return),
462 Operator::Call { function_index } => Some(Instr::Call(function_index)),
463 Operator::CallIndirect {
464 type_index,
465 table_index,
466 ..
467 } => Some(Instr::CallIndirect(table_index, type_index)),
468 Operator::ReturnCall { .. } => {
469 return Err("Tail call proposal is not supported".to_string());
470 }
471 Operator::ReturnCallIndirect { .. } => {
472 return Err("Tail call proposal is not supported".to_string());
473 }
474 Operator::Delegate { .. } => {
475 return Err("Exception handling proposal is not supported".to_string());
476 }
477 Operator::CatchAll => {
478 return Err("Exception handling proposal is not supported".to_string());
479 }
480 Operator::Drop => Some(Instr::Drop),
481 Operator::Select => Some(Instr::Select(None)),
482 Operator::TypedSelect { ty } => Some(Instr::Select(Some(vec![ty.try_into()?]))),
483 Operator::LocalGet { local_index } => Some(Instr::LocalGet(local_index)),
484 Operator::LocalSet { local_index } => Some(Instr::LocalSet(local_index)),
485 Operator::LocalTee { local_index } => Some(Instr::LocalTee(local_index)),
486 Operator::GlobalGet { global_index } => Some(Instr::GlobalGet(global_index)),
487 Operator::GlobalSet { global_index } => Some(Instr::GlobalSet(global_index)),
488 Operator::I32Load { memarg } => Some(Instr::Load(
489 NumOrVecType::Num(NumType::I32),
490 memarg.try_into()?,
491 )),
492 Operator::I64Load { memarg } => Some(Instr::Load(
493 NumOrVecType::Num(NumType::I64),
494 memarg.try_into()?,
495 )),
496 Operator::F32Load { memarg } => Some(Instr::Load(
497 NumOrVecType::Num(NumType::F32),
498 memarg.try_into()?,
499 )),
500 Operator::F64Load { memarg } => Some(Instr::Load(
501 NumOrVecType::Num(NumType::F64),
502 memarg.try_into()?,
503 )),
504 Operator::I32Load8S { memarg } => Some(Instr::Load8(
505 NumType::I32,
506 Signedness::Signed,
507 memarg.try_into()?,
508 )),
509 Operator::I32Load8U { memarg } => Some(Instr::Load8(
510 NumType::I32,
511 Signedness::Unsigned,
512 memarg.try_into()?,
513 )),
514 Operator::I32Load16S { memarg } => Some(Instr::Load16(
515 NumType::I32,
516 Signedness::Signed,
517 memarg.try_into()?,
518 )),
519 Operator::I32Load16U { memarg } => Some(Instr::Load16(
520 NumType::I32,
521 Signedness::Unsigned,
522 memarg.try_into()?,
523 )),
524 Operator::I64Load8S { memarg } => Some(Instr::Load8(
525 NumType::I64,
526 Signedness::Signed,
527 memarg.try_into()?,
528 )),
529 Operator::I64Load8U { memarg } => Some(Instr::Load8(
530 NumType::I64,
531 Signedness::Unsigned,
532 memarg.try_into()?,
533 )),
534 Operator::I64Load16S { memarg } => Some(Instr::Load16(
535 NumType::I64,
536 Signedness::Signed,
537 memarg.try_into()?,
538 )),
539 Operator::I64Load16U { memarg } => Some(Instr::Load16(
540 NumType::I64,
541 Signedness::Unsigned,
542 memarg.try_into()?,
543 )),
544 Operator::I64Load32S { memarg } => {
545 Some(Instr::Load32(Signedness::Signed, memarg.try_into()?))
546 }
547 Operator::I64Load32U { memarg } => {
548 Some(Instr::Load32(Signedness::Unsigned, memarg.try_into()?))
549 }
550 Operator::I32Store { memarg } => Some(Instr::Store(
551 NumOrVecType::Num(NumType::I32),
552 memarg.try_into()?,
553 )),
554 Operator::I64Store { memarg } => Some(Instr::Store(
555 NumOrVecType::Num(NumType::I64),
556 memarg.try_into()?,
557 )),
558 Operator::F32Store { memarg } => Some(Instr::Store(
559 NumOrVecType::Num(NumType::F32),
560 memarg.try_into()?,
561 )),
562 Operator::F64Store { memarg } => Some(Instr::Store(
563 NumOrVecType::Num(NumType::F64),
564 memarg.try_into()?,
565 )),
566 Operator::I32Store8 { memarg } => {
567 Some(Instr::Store8(NumType::I32, memarg.try_into()?))
568 }
569 Operator::I32Store16 { memarg } => {
570 Some(Instr::Store16(NumType::I32, memarg.try_into()?))
571 }
572 Operator::I64Store8 { memarg } => {
573 Some(Instr::Store8(NumType::I64, memarg.try_into()?))
574 }
575 Operator::I64Store16 { memarg } => {
576 Some(Instr::Store16(NumType::I64, memarg.try_into()?))
577 }
578 Operator::I64Store32 { memarg } => Some(Instr::Store32(memarg.try_into()?)),
579 Operator::MemorySize { .. } => Some(Instr::MemorySize),
580 Operator::MemoryGrow { .. } => Some(Instr::MemoryGrow),
581 Operator::I32Const { value } => Some(Instr::I32Const(value)),
582 Operator::I64Const { value } => Some(Instr::I64Const(value)),
583 Operator::F32Const { value } => Some(Instr::F32Const(f32::from_bits(value.bits()))),
584 Operator::F64Const { value } => Some(Instr::F64Const(f64::from_bits(value.bits()))),
585 Operator::RefNull { hty } => Some(Instr::RefNull(hty.try_into()?)),
586 Operator::RefIsNull => Some(Instr::RefIsNull),
587 Operator::RefFunc { function_index } => Some(Instr::RefFunc(function_index)),
588 Operator::I32Eqz => Some(Instr::IEqz(IntWidth::I32)),
589 Operator::I32Eq => Some(Instr::IEq(IntWidth::I32)),
590 Operator::I32Ne => Some(Instr::INe(IntWidth::I32)),
591 Operator::I32LtS => Some(Instr::ILt(IntWidth::I32, Signedness::Signed)),
592 Operator::I32LtU => Some(Instr::ILt(IntWidth::I32, Signedness::Unsigned)),
593 Operator::I32GtS => Some(Instr::IGt(IntWidth::I32, Signedness::Signed)),
594 Operator::I32GtU => Some(Instr::IGt(IntWidth::I32, Signedness::Unsigned)),
595 Operator::I32LeS => Some(Instr::ILe(IntWidth::I32, Signedness::Signed)),
596 Operator::I32LeU => Some(Instr::ILe(IntWidth::I32, Signedness::Unsigned)),
597 Operator::I32GeS => Some(Instr::IGe(IntWidth::I32, Signedness::Signed)),
598 Operator::I32GeU => Some(Instr::IGe(IntWidth::I32, Signedness::Unsigned)),
599 Operator::I64Eqz => Some(Instr::IEqz(IntWidth::I64)),
600 Operator::I64Eq => Some(Instr::IEq(IntWidth::I64)),
601 Operator::I64Ne => Some(Instr::INe(IntWidth::I64)),
602 Operator::I64LtS => Some(Instr::ILt(IntWidth::I64, Signedness::Signed)),
603 Operator::I64LtU => Some(Instr::ILt(IntWidth::I64, Signedness::Unsigned)),
604 Operator::I64GtS => Some(Instr::IGt(IntWidth::I64, Signedness::Signed)),
605 Operator::I64GtU => Some(Instr::IGt(IntWidth::I64, Signedness::Unsigned)),
606 Operator::I64LeS => Some(Instr::ILe(IntWidth::I64, Signedness::Signed)),
607 Operator::I64LeU => Some(Instr::ILe(IntWidth::I64, Signedness::Unsigned)),
608 Operator::I64GeS => Some(Instr::IGe(IntWidth::I64, Signedness::Signed)),
609 Operator::I64GeU => Some(Instr::IGe(IntWidth::I64, Signedness::Unsigned)),
610 Operator::F32Eq => Some(Instr::FEq(FloatWidth::F32)),
611 Operator::F32Ne => Some(Instr::FNe(FloatWidth::F32)),
612 Operator::F32Lt => Some(Instr::FLt(FloatWidth::F32)),
613 Operator::F32Gt => Some(Instr::FGt(FloatWidth::F32)),
614 Operator::F32Le => Some(Instr::FLe(FloatWidth::F32)),
615 Operator::F32Ge => Some(Instr::FGe(FloatWidth::F32)),
616 Operator::F64Eq => Some(Instr::FEq(FloatWidth::F64)),
617 Operator::F64Ne => Some(Instr::FNe(FloatWidth::F64)),
618 Operator::F64Lt => Some(Instr::FLt(FloatWidth::F64)),
619 Operator::F64Gt => Some(Instr::FGt(FloatWidth::F64)),
620 Operator::F64Le => Some(Instr::FLe(FloatWidth::F64)),
621 Operator::F64Ge => Some(Instr::FGe(FloatWidth::F64)),
622 Operator::I32Clz => Some(Instr::IClz(IntWidth::I32)),
623 Operator::I32Ctz => Some(Instr::ICtz(IntWidth::I32)),
624 Operator::I32Popcnt => Some(Instr::IPopCnt(IntWidth::I32)),
625 Operator::I32Add => Some(Instr::IAdd(IntWidth::I32)),
626 Operator::I32Sub => Some(Instr::ISub(IntWidth::I32)),
627 Operator::I32Mul => Some(Instr::IMul(IntWidth::I32)),
628 Operator::I32DivS => Some(Instr::IDiv(IntWidth::I32, Signedness::Signed)),
629 Operator::I32DivU => Some(Instr::IDiv(IntWidth::I32, Signedness::Unsigned)),
630 Operator::I32RemS => Some(Instr::IRem(IntWidth::I32, Signedness::Signed)),
631 Operator::I32RemU => Some(Instr::IRem(IntWidth::I32, Signedness::Unsigned)),
632 Operator::I32And => Some(Instr::IAnd(IntWidth::I32)),
633 Operator::I32Or => Some(Instr::IOr(IntWidth::I32)),
634 Operator::I32Xor => Some(Instr::IXor(IntWidth::I32)),
635 Operator::I32Shl => Some(Instr::IShl(IntWidth::I32)),
636 Operator::I32ShrS => Some(Instr::IShr(IntWidth::I32, Signedness::Signed)),
637 Operator::I32ShrU => Some(Instr::IShr(IntWidth::I32, Signedness::Unsigned)),
638 Operator::I32Rotl => Some(Instr::IRotL(IntWidth::I32)),
639 Operator::I32Rotr => Some(Instr::IRotR(IntWidth::I32)),
640 Operator::I64Clz => Some(Instr::IClz(IntWidth::I64)),
641 Operator::I64Ctz => Some(Instr::ICtz(IntWidth::I64)),
642 Operator::I64Popcnt => Some(Instr::IPopCnt(IntWidth::I64)),
643 Operator::I64Add => Some(Instr::IAdd(IntWidth::I64)),
644 Operator::I64Sub => Some(Instr::ISub(IntWidth::I64)),
645 Operator::I64Mul => Some(Instr::IMul(IntWidth::I64)),
646 Operator::I64DivS => Some(Instr::IDiv(IntWidth::I64, Signedness::Signed)),
647 Operator::I64DivU => Some(Instr::IDiv(IntWidth::I64, Signedness::Unsigned)),
648 Operator::I64RemS => Some(Instr::IRem(IntWidth::I64, Signedness::Signed)),
649 Operator::I64RemU => Some(Instr::IRem(IntWidth::I64, Signedness::Unsigned)),
650 Operator::I64And => Some(Instr::IAnd(IntWidth::I64)),
651 Operator::I64Or => Some(Instr::IOr(IntWidth::I64)),
652 Operator::I64Xor => Some(Instr::IXor(IntWidth::I64)),
653 Operator::I64Shl => Some(Instr::IShl(IntWidth::I64)),
654 Operator::I64ShrS => Some(Instr::IShr(IntWidth::I64, Signedness::Signed)),
655 Operator::I64ShrU => Some(Instr::IShr(IntWidth::I64, Signedness::Unsigned)),
656 Operator::I64Rotl => Some(Instr::IRotL(IntWidth::I64)),
657 Operator::I64Rotr => Some(Instr::IRotR(IntWidth::I64)),
658 Operator::F32Abs => Some(Instr::FAbs(FloatWidth::F32)),
659 Operator::F32Neg => Some(Instr::FNeg(FloatWidth::F32)),
660 Operator::F32Ceil => Some(Instr::FCeil(FloatWidth::F32)),
661 Operator::F32Floor => Some(Instr::FFloor(FloatWidth::F32)),
662 Operator::F32Trunc => Some(Instr::FTrunc(FloatWidth::F32)),
663 Operator::F32Nearest => Some(Instr::FNearest(FloatWidth::F32)),
664 Operator::F32Sqrt => Some(Instr::FSqrt(FloatWidth::F32)),
665 Operator::F32Add => Some(Instr::FAdd(FloatWidth::F32)),
666 Operator::F32Sub => Some(Instr::FSub(FloatWidth::F32)),
667 Operator::F32Mul => Some(Instr::FMul(FloatWidth::F32)),
668 Operator::F32Div => Some(Instr::FDiv(FloatWidth::F32)),
669 Operator::F32Min => Some(Instr::FMin(FloatWidth::F32)),
670 Operator::F32Max => Some(Instr::FMax(FloatWidth::F32)),
671 Operator::F32Copysign => Some(Instr::FCopySign(FloatWidth::F32)),
672 Operator::F64Abs => Some(Instr::FAbs(FloatWidth::F64)),
673 Operator::F64Neg => Some(Instr::FNeg(FloatWidth::F64)),
674 Operator::F64Ceil => Some(Instr::FCeil(FloatWidth::F64)),
675 Operator::F64Floor => Some(Instr::FFloor(FloatWidth::F64)),
676 Operator::F64Trunc => Some(Instr::FTrunc(FloatWidth::F64)),
677 Operator::F64Nearest => Some(Instr::FNearest(FloatWidth::F64)),
678 Operator::F64Sqrt => Some(Instr::FSqrt(FloatWidth::F64)),
679 Operator::F64Add => Some(Instr::FAdd(FloatWidth::F64)),
680 Operator::F64Sub => Some(Instr::FSub(FloatWidth::F64)),
681 Operator::F64Mul => Some(Instr::FMul(FloatWidth::F64)),
682 Operator::F64Div => Some(Instr::FDiv(FloatWidth::F64)),
683 Operator::F64Min => Some(Instr::FMin(FloatWidth::F64)),
684 Operator::F64Max => Some(Instr::FMax(FloatWidth::F64)),
685 Operator::F64Copysign => Some(Instr::FCopySign(FloatWidth::F64)),
686 Operator::I32WrapI64 => Some(Instr::I32WrapI64),
687 Operator::I32TruncF32S => Some(Instr::ITruncF(
688 IntWidth::I32,
689 FloatWidth::F32,
690 Signedness::Signed,
691 )),
692 Operator::I32TruncF32U => Some(Instr::ITruncF(
693 IntWidth::I32,
694 FloatWidth::F32,
695 Signedness::Unsigned,
696 )),
697 Operator::I32TruncF64S => Some(Instr::ITruncF(
698 IntWidth::I32,
699 FloatWidth::F64,
700 Signedness::Signed,
701 )),
702 Operator::I32TruncF64U => Some(Instr::ITruncF(
703 IntWidth::I32,
704 FloatWidth::F64,
705 Signedness::Unsigned,
706 )),
707 Operator::I64ExtendI32S => Some(Instr::I64ExtendI32(Signedness::Signed)),
708 Operator::I64ExtendI32U => Some(Instr::I64ExtendI32(Signedness::Unsigned)),
709 Operator::I64TruncF32S => Some(Instr::ITruncF(
710 IntWidth::I64,
711 FloatWidth::F32,
712 Signedness::Signed,
713 )),
714 Operator::I64TruncF32U => Some(Instr::ITruncF(
715 IntWidth::I64,
716 FloatWidth::F32,
717 Signedness::Unsigned,
718 )),
719 Operator::I64TruncF64S => Some(Instr::ITruncF(
720 IntWidth::I64,
721 FloatWidth::F64,
722 Signedness::Signed,
723 )),
724 Operator::I64TruncF64U => Some(Instr::ITruncF(
725 IntWidth::I64,
726 FloatWidth::F64,
727 Signedness::Unsigned,
728 )),
729 Operator::F32ConvertI32S => Some(Instr::FConvertI(
730 FloatWidth::F32,
731 IntWidth::I32,
732 Signedness::Signed,
733 )),
734 Operator::F32ConvertI32U => Some(Instr::FConvertI(
735 FloatWidth::F32,
736 IntWidth::I32,
737 Signedness::Unsigned,
738 )),
739 Operator::F32ConvertI64S => Some(Instr::FConvertI(
740 FloatWidth::F32,
741 IntWidth::I64,
742 Signedness::Signed,
743 )),
744 Operator::F32ConvertI64U => Some(Instr::FConvertI(
745 FloatWidth::F32,
746 IntWidth::I64,
747 Signedness::Unsigned,
748 )),
749 Operator::F32DemoteF64 => Some(Instr::F32DemoteF64),
750 Operator::F64ConvertI32S => Some(Instr::FConvertI(
751 FloatWidth::F64,
752 IntWidth::I32,
753 Signedness::Signed,
754 )),
755 Operator::F64ConvertI32U => Some(Instr::FConvertI(
756 FloatWidth::F64,
757 IntWidth::I32,
758 Signedness::Unsigned,
759 )),
760 Operator::F64ConvertI64S => Some(Instr::FConvertI(
761 FloatWidth::F64,
762 IntWidth::I64,
763 Signedness::Signed,
764 )),
765 Operator::F64ConvertI64U => Some(Instr::FConvertI(
766 FloatWidth::F64,
767 IntWidth::I64,
768 Signedness::Unsigned,
769 )),
770 Operator::F64PromoteF32 => Some(Instr::F64PromoteF32),
771 Operator::I32ReinterpretF32 => Some(Instr::IReinterpretF(IntWidth::I32)),
772 Operator::I64ReinterpretF64 => Some(Instr::IReinterpretF(IntWidth::I64)),
773 Operator::F32ReinterpretI32 => Some(Instr::FReinterpretI(FloatWidth::F32)),
774 Operator::F64ReinterpretI64 => Some(Instr::FReinterpretI(FloatWidth::F64)),
775 Operator::I32Extend8S => Some(Instr::IExtend8S(IntWidth::I32)),
776 Operator::I32Extend16S => Some(Instr::IExtend16S(IntWidth::I32)),
777 Operator::I64Extend8S => Some(Instr::IExtend8S(IntWidth::I64)),
778 Operator::I64Extend16S => Some(Instr::IExtend16S(IntWidth::I64)),
779 Operator::I64Extend32S => Some(Instr::I64Extend32S),
780 Operator::RefI31 => {
781 return Err("GC proposal is not supported".to_string());
782 }
783 Operator::I31GetS => {
784 return Err("GC proposal is not supported".to_string());
785 }
786 Operator::I31GetU => {
787 return Err("GC proposal is not supported".to_string());
788 }
789 Operator::I32TruncSatF32S => Some(Instr::ITruncSatF(
790 IntWidth::I32,
791 FloatWidth::F32,
792 Signedness::Signed,
793 )),
794 Operator::I32TruncSatF32U => Some(Instr::ITruncSatF(
795 IntWidth::I32,
796 FloatWidth::F32,
797 Signedness::Unsigned,
798 )),
799 Operator::I32TruncSatF64S => Some(Instr::ITruncSatF(
800 IntWidth::I32,
801 FloatWidth::F64,
802 Signedness::Signed,
803 )),
804 Operator::I32TruncSatF64U => Some(Instr::ITruncSatF(
805 IntWidth::I32,
806 FloatWidth::F64,
807 Signedness::Unsigned,
808 )),
809 Operator::I64TruncSatF32S => Some(Instr::ITruncSatF(
810 IntWidth::I64,
811 FloatWidth::F32,
812 Signedness::Signed,
813 )),
814 Operator::I64TruncSatF32U => Some(Instr::ITruncSatF(
815 IntWidth::I64,
816 FloatWidth::F32,
817 Signedness::Unsigned,
818 )),
819 Operator::I64TruncSatF64S => Some(Instr::ITruncSatF(
820 IntWidth::I64,
821 FloatWidth::F64,
822 Signedness::Signed,
823 )),
824 Operator::I64TruncSatF64U => Some(Instr::ITruncSatF(
825 IntWidth::I64,
826 FloatWidth::F64,
827 Signedness::Unsigned,
828 )),
829 Operator::MemoryInit { data_index, .. } => Some(Instr::MemoryInit(data_index)),
830 Operator::DataDrop { data_index } => Some(Instr::DataDrop(data_index)),
831 Operator::MemoryCopy { .. } => Some(Instr::MemoryCopy),
832 Operator::MemoryFill { .. } => Some(Instr::MemoryFill),
833 Operator::TableInit { elem_index, table } => {
834 Some(Instr::TableInit(table, elem_index))
835 }
836 Operator::ElemDrop { elem_index } => Some(Instr::ElemDrop(elem_index)),
837 Operator::TableCopy {
838 dst_table,
839 src_table,
840 } => Some(Instr::TableCopy {
841 source: src_table,
842 destination: dst_table,
843 }),
844 Operator::TableFill { table } => Some(Instr::TableFill(table)),
845 Operator::TableGet { table } => Some(Instr::TableGet(table)),
846 Operator::TableSet { table } => Some(Instr::TableSet(table)),
847 Operator::TableGrow { table } => Some(Instr::TableGrow(table)),
848 Operator::TableSize { table } => Some(Instr::TableSize(table)),
849 Operator::MemoryDiscard { .. } => {
850 return Err(
851 "Fine grained control of memory proposal is not supported".to_string()
852 );
853 }
854 Operator::MemoryAtomicNotify { .. } => {
855 return Err("Threads proposal is not supported".to_string());
856 }
857 Operator::MemoryAtomicWait32 { .. } => {
858 return Err("Threads proposal is not supported".to_string());
859 }
860 Operator::MemoryAtomicWait64 { .. } => {
861 return Err("Threads proposal is not supported".to_string());
862 }
863 Operator::AtomicFence => {
864 return Err("Threads proposal is not supported".to_string());
865 }
866 Operator::I32AtomicLoad { .. } => {
867 return Err("Threads proposal is not supported".to_string());
868 }
869 Operator::I64AtomicLoad { .. } => {
870 return Err("Threads proposal is not supported".to_string());
871 }
872 Operator::I32AtomicLoad8U { .. } => {
873 return Err("Threads proposal is not supported".to_string());
874 }
875 Operator::I32AtomicLoad16U { .. } => {
876 return Err("Threads proposal is not supported".to_string());
877 }
878 Operator::I64AtomicLoad8U { .. } => {
879 return Err("Threads proposal is not supported".to_string());
880 }
881 Operator::I64AtomicLoad16U { .. } => {
882 return Err("Threads proposal is not supported".to_string());
883 }
884 Operator::I64AtomicLoad32U { .. } => {
885 return Err("Threads proposal is not supported".to_string());
886 }
887 Operator::I32AtomicStore { .. } => {
888 return Err("Threads proposal is not supported".to_string());
889 }
890 Operator::I64AtomicStore { .. } => {
891 return Err("Threads proposal is not supported".to_string());
892 }
893 Operator::I32AtomicStore8 { .. } => {
894 return Err("Threads proposal is not supported".to_string());
895 }
896 Operator::I32AtomicStore16 { .. } => {
897 return Err("Threads proposal is not supported".to_string());
898 }
899 Operator::I64AtomicStore8 { .. } => {
900 return Err("Threads proposal is not supported".to_string());
901 }
902 Operator::I64AtomicStore16 { .. } => {
903 return Err("Threads proposal is not supported".to_string());
904 }
905 Operator::I64AtomicStore32 { .. } => {
906 return Err("Threads proposal is not supported".to_string());
907 }
908 Operator::I32AtomicRmwAdd { .. } => {
909 return Err("Threads proposal is not supported".to_string());
910 }
911 Operator::I64AtomicRmwAdd { .. } => {
912 return Err("Threads proposal is not supported".to_string());
913 }
914 Operator::I32AtomicRmw8AddU { .. } => {
915 return Err("Threads proposal is not supported".to_string());
916 }
917 Operator::I32AtomicRmw16AddU { .. } => {
918 return Err("Threads proposal is not supported".to_string());
919 }
920 Operator::I64AtomicRmw8AddU { .. } => {
921 return Err("Threads proposal is not supported".to_string());
922 }
923 Operator::I64AtomicRmw16AddU { .. } => {
924 return Err("Threads proposal is not supported".to_string());
925 }
926 Operator::I64AtomicRmw32AddU { .. } => {
927 return Err("Threads proposal is not supported".to_string());
928 }
929 Operator::I32AtomicRmwSub { .. } => {
930 return Err("Threads proposal is not supported".to_string());
931 }
932 Operator::I64AtomicRmwSub { .. } => {
933 return Err("Threads proposal is not supported".to_string());
934 }
935 Operator::I32AtomicRmw8SubU { .. } => {
936 return Err("Threads proposal is not supported".to_string());
937 }
938 Operator::I32AtomicRmw16SubU { .. } => {
939 return Err("Threads proposal is not supported".to_string());
940 }
941 Operator::I64AtomicRmw8SubU { .. } => {
942 return Err("Threads proposal is not supported".to_string());
943 }
944 Operator::I64AtomicRmw16SubU { .. } => {
945 return Err("Threads proposal is not supported".to_string());
946 }
947 Operator::I64AtomicRmw32SubU { .. } => {
948 return Err("Threads proposal is not supported".to_string());
949 }
950 Operator::I32AtomicRmwAnd { .. } => {
951 return Err("Threads proposal is not supported".to_string());
952 }
953 Operator::I64AtomicRmwAnd { .. } => {
954 return Err("Threads proposal is not supported".to_string());
955 }
956 Operator::I32AtomicRmw8AndU { .. } => {
957 return Err("Threads proposal is not supported".to_string());
958 }
959 Operator::I32AtomicRmw16AndU { .. } => {
960 return Err("Threads proposal is not supported".to_string());
961 }
962 Operator::I64AtomicRmw8AndU { .. } => {
963 return Err("Threads proposal is not supported".to_string());
964 }
965 Operator::I64AtomicRmw16AndU { .. } => {
966 return Err("Threads proposal is not supported".to_string());
967 }
968 Operator::I64AtomicRmw32AndU { .. } => {
969 return Err("Threads proposal is not supported".to_string());
970 }
971 Operator::I32AtomicRmwOr { .. } => {
972 return Err("Threads proposal is not supported".to_string());
973 }
974 Operator::I64AtomicRmwOr { .. } => {
975 return Err("Threads proposal is not supported".to_string());
976 }
977 Operator::I32AtomicRmw8OrU { .. } => {
978 return Err("Threads proposal is not supported".to_string());
979 }
980 Operator::I32AtomicRmw16OrU { .. } => {
981 return Err("Threads proposal is not supported".to_string());
982 }
983 Operator::I64AtomicRmw8OrU { .. } => {
984 return Err("Threads proposal is not supported".to_string());
985 }
986 Operator::I64AtomicRmw16OrU { .. } => {
987 return Err("Threads proposal is not supported".to_string());
988 }
989 Operator::I64AtomicRmw32OrU { .. } => {
990 return Err("Threads proposal is not supported".to_string());
991 }
992 Operator::I32AtomicRmwXor { .. } => {
993 return Err("Threads proposal is not supported".to_string());
994 }
995 Operator::I64AtomicRmwXor { .. } => {
996 return Err("Threads proposal is not supported".to_string());
997 }
998 Operator::I32AtomicRmw8XorU { .. } => {
999 return Err("Threads proposal is not supported".to_string());
1000 }
1001 Operator::I32AtomicRmw16XorU { .. } => {
1002 return Err("Threads proposal is not supported".to_string());
1003 }
1004 Operator::I64AtomicRmw8XorU { .. } => {
1005 return Err("Threads proposal is not supported".to_string());
1006 }
1007 Operator::I64AtomicRmw16XorU { .. } => {
1008 return Err("Threads proposal is not supported".to_string());
1009 }
1010 Operator::I64AtomicRmw32XorU { .. } => {
1011 return Err("Threads proposal is not supported".to_string());
1012 }
1013 Operator::I32AtomicRmwXchg { .. } => {
1014 return Err("Threads proposal is not supported".to_string());
1015 }
1016 Operator::I64AtomicRmwXchg { .. } => {
1017 return Err("Threads proposal is not supported".to_string());
1018 }
1019 Operator::I32AtomicRmw8XchgU { .. } => {
1020 return Err("Threads proposal is not supported".to_string());
1021 }
1022 Operator::I32AtomicRmw16XchgU { .. } => {
1023 return Err("Threads proposal is not supported".to_string());
1024 }
1025 Operator::I64AtomicRmw8XchgU { .. } => {
1026 return Err("Threads proposal is not supported".to_string());
1027 }
1028 Operator::I64AtomicRmw16XchgU { .. } => {
1029 return Err("Threads proposal is not supported".to_string());
1030 }
1031 Operator::I64AtomicRmw32XchgU { .. } => {
1032 return Err("Threads proposal is not supported".to_string());
1033 }
1034 Operator::I32AtomicRmwCmpxchg { .. } => {
1035 return Err("Threads proposal is not supported".to_string());
1036 }
1037 Operator::I64AtomicRmwCmpxchg { .. } => {
1038 return Err("Threads proposal is not supported".to_string());
1039 }
1040 Operator::I32AtomicRmw8CmpxchgU { .. } => {
1041 return Err("Threads proposal is not supported".to_string());
1042 }
1043 Operator::I32AtomicRmw16CmpxchgU { .. } => {
1044 return Err("Threads proposal is not supported".to_string());
1045 }
1046 Operator::I64AtomicRmw8CmpxchgU { .. } => {
1047 return Err("Threads proposal is not supported".to_string());
1048 }
1049 Operator::I64AtomicRmw16CmpxchgU { .. } => {
1050 return Err("Threads proposal is not supported".to_string());
1051 }
1052 Operator::I64AtomicRmw32CmpxchgU { .. } => {
1053 return Err("Threads proposal is not supported".to_string());
1054 }
1055 Operator::V128Load { memarg } => Some(Instr::Load(
1056 NumOrVecType::Vec(VecType::V128),
1057 memarg.try_into()?,
1058 )),
1059 Operator::V128Load8x8S { memarg } => {
1060 Some(Instr::V128Load8x8(Signedness::Signed, memarg.try_into()?))
1061 }
1062 Operator::V128Load8x8U { memarg } => {
1063 Some(Instr::V128Load8x8(Signedness::Unsigned, memarg.try_into()?))
1064 }
1065 Operator::V128Load16x4S { memarg } => {
1066 Some(Instr::V128Load16x4(Signedness::Signed, memarg.try_into()?))
1067 }
1068 Operator::V128Load16x4U { memarg } => Some(Instr::V128Load16x4(
1069 Signedness::Unsigned,
1070 memarg.try_into()?,
1071 )),
1072 Operator::V128Load32x2S { memarg } => {
1073 Some(Instr::V128Load32x2(Signedness::Signed, memarg.try_into()?))
1074 }
1075 Operator::V128Load32x2U { memarg } => Some(Instr::V128Load32x2(
1076 Signedness::Unsigned,
1077 memarg.try_into()?,
1078 )),
1079 Operator::V128Load8Splat { memarg } => Some(Instr::V128LoadSplat(
1080 VectorLoadShape::WW8,
1081 memarg.try_into()?,
1082 )),
1083 Operator::V128Load16Splat { memarg } => Some(Instr::V128LoadSplat(
1084 VectorLoadShape::WW16,
1085 memarg.try_into()?,
1086 )),
1087 Operator::V128Load32Splat { memarg } => Some(Instr::V128LoadSplat(
1088 VectorLoadShape::WW32,
1089 memarg.try_into()?,
1090 )),
1091 Operator::V128Load64Splat { memarg } => Some(Instr::V128LoadSplat(
1092 VectorLoadShape::WW64,
1093 memarg.try_into()?,
1094 )),
1095 Operator::V128Load32Zero { memarg } => {
1096 Some(Instr::V128Load32Zero(memarg.try_into()?))
1097 }
1098 Operator::V128Load64Zero { memarg } => {
1099 Some(Instr::V128Load64Zero(memarg.try_into()?))
1100 }
1101 Operator::V128Store { memarg } => Some(Instr::Store(
1102 NumOrVecType::Vec(VecType::V128),
1103 memarg.try_into()?,
1104 )),
1105 Operator::V128Load8Lane { memarg, lane } => Some(Instr::V128LoadLane(
1106 VectorLoadShape::WW8,
1107 memarg.try_into()?,
1108 lane,
1109 )),
1110 Operator::V128Load16Lane { memarg, lane } => Some(Instr::V128LoadLane(
1111 VectorLoadShape::WW16,
1112 memarg.try_into()?,
1113 lane,
1114 )),
1115 Operator::V128Load32Lane { memarg, lane } => Some(Instr::V128LoadLane(
1116 VectorLoadShape::WW32,
1117 memarg.try_into()?,
1118 lane,
1119 )),
1120 Operator::V128Load64Lane { memarg, lane } => Some(Instr::V128LoadLane(
1121 VectorLoadShape::WW64,
1122 memarg.try_into()?,
1123 lane,
1124 )),
1125 Operator::V128Store8Lane { memarg, lane } => Some(Instr::V128StoreLane(
1126 VectorLoadShape::WW8,
1127 memarg.try_into()?,
1128 lane,
1129 )),
1130 Operator::V128Store16Lane { memarg, lane } => Some(Instr::V128StoreLane(
1131 VectorLoadShape::WW16,
1132 memarg.try_into()?,
1133 lane,
1134 )),
1135 Operator::V128Store32Lane { memarg, lane } => Some(Instr::V128StoreLane(
1136 VectorLoadShape::WW32,
1137 memarg.try_into()?,
1138 lane,
1139 )),
1140 Operator::V128Store64Lane { memarg, lane } => Some(Instr::V128StoreLane(
1141 VectorLoadShape::WW64,
1142 memarg.try_into()?,
1143 lane,
1144 )),
1145 Operator::V128Const { value } => Some(Instr::V128Const(value.i128())),
1146 Operator::I8x16Shuffle { lanes } => Some(Instr::VI8x16Shuffle(lanes)),
1147 Operator::I8x16ExtractLaneS { lane } => {
1148 Some(Instr::VI8x16ExtractLane(Signedness::Signed, lane))
1149 }
1150 Operator::I8x16ExtractLaneU { lane } => {
1151 Some(Instr::VI8x16ExtractLane(Signedness::Unsigned, lane))
1152 }
1153 Operator::I8x16ReplaceLane { lane } => {
1154 Some(Instr::VReplaceLane(Shape::Int(IShape::I8x16), lane))
1155 }
1156 Operator::I16x8ExtractLaneS { lane } => {
1157 Some(Instr::VI16x8ExtractLane(Signedness::Signed, lane))
1158 }
1159 Operator::I16x8ExtractLaneU { lane } => {
1160 Some(Instr::VI16x8ExtractLane(Signedness::Unsigned, lane))
1161 }
1162 Operator::I16x8ReplaceLane { lane } => {
1163 Some(Instr::VReplaceLane(Shape::Int(IShape::I16x8), lane))
1164 }
1165 Operator::I32x4ExtractLane { lane } => Some(Instr::VI32x4ExtractLane(lane)),
1166 Operator::I32x4ReplaceLane { lane } => {
1167 Some(Instr::VReplaceLane(Shape::Int(IShape::I32x4), lane))
1168 }
1169 Operator::I64x2ExtractLane { lane } => Some(Instr::VI64x2ExtractLane(lane)),
1170 Operator::I64x2ReplaceLane { lane } => {
1171 Some(Instr::VReplaceLane(Shape::Int(IShape::I64x2), lane))
1172 }
1173 Operator::F32x4ExtractLane { lane } => {
1174 Some(Instr::VFExtractLane(FShape::F32x4, lane))
1175 }
1176 Operator::F32x4ReplaceLane { lane } => {
1177 Some(Instr::VReplaceLane(Shape::Float(FShape::F32x4), lane))
1178 }
1179 Operator::F64x2ExtractLane { lane } => {
1180 Some(Instr::VFExtractLane(FShape::F64x2, lane))
1181 }
1182 Operator::F64x2ReplaceLane { lane } => {
1183 Some(Instr::VReplaceLane(Shape::Float(FShape::F64x2), lane))
1184 }
1185 Operator::I8x16Swizzle => Some(Instr::VI18x16Swizzle),
1186 Operator::I8x16Splat => Some(Instr::VSplat(Shape::Int(IShape::I8x16))),
1187 Operator::I16x8Splat => Some(Instr::VSplat(Shape::Int(IShape::I16x8))),
1188 Operator::I32x4Splat => Some(Instr::VSplat(Shape::Int(IShape::I32x4))),
1189 Operator::I64x2Splat => Some(Instr::VSplat(Shape::Int(IShape::I64x2))),
1190 Operator::F32x4Splat => Some(Instr::VSplat(Shape::Float(FShape::F32x4))),
1191 Operator::F64x2Splat => Some(Instr::VSplat(Shape::Float(FShape::F64x2))),
1192 Operator::I8x16Eq => Some(Instr::VIEq(IShape::I8x16)),
1193 Operator::I8x16Ne => Some(Instr::VIEq(IShape::I8x16)),
1194 Operator::I8x16LtS => Some(Instr::VILt(IShape::I8x16, Signedness::Signed)),
1195 Operator::I8x16LtU => Some(Instr::VILt(IShape::I8x16, Signedness::Unsigned)),
1196 Operator::I8x16GtS => Some(Instr::VIGt(IShape::I8x16, Signedness::Signed)),
1197 Operator::I8x16GtU => Some(Instr::VIGt(IShape::I8x16, Signedness::Unsigned)),
1198 Operator::I8x16LeS => Some(Instr::VILe(IShape::I8x16, Signedness::Signed)),
1199 Operator::I8x16LeU => Some(Instr::VILe(IShape::I8x16, Signedness::Unsigned)),
1200 Operator::I8x16GeS => Some(Instr::VIGe(IShape::I8x16, Signedness::Signed)),
1201 Operator::I8x16GeU => Some(Instr::VIGe(IShape::I8x16, Signedness::Unsigned)),
1202 Operator::I16x8Eq => Some(Instr::VIEq(IShape::I16x8)),
1203 Operator::I16x8Ne => Some(Instr::VIEq(IShape::I16x8)),
1204 Operator::I16x8LtS => Some(Instr::VILt(IShape::I16x8, Signedness::Signed)),
1205 Operator::I16x8LtU => Some(Instr::VILt(IShape::I16x8, Signedness::Unsigned)),
1206 Operator::I16x8GtS => Some(Instr::VIGt(IShape::I16x8, Signedness::Signed)),
1207 Operator::I16x8GtU => Some(Instr::VIGt(IShape::I16x8, Signedness::Unsigned)),
1208 Operator::I16x8LeS => Some(Instr::VILe(IShape::I16x8, Signedness::Signed)),
1209 Operator::I16x8LeU => Some(Instr::VILe(IShape::I16x8, Signedness::Unsigned)),
1210 Operator::I16x8GeS => Some(Instr::VIGe(IShape::I16x8, Signedness::Signed)),
1211 Operator::I16x8GeU => Some(Instr::VIGe(IShape::I16x8, Signedness::Unsigned)),
1212 Operator::I32x4Eq => Some(Instr::VIEq(IShape::I32x4)),
1213 Operator::I32x4Ne => Some(Instr::VIEq(IShape::I32x4)),
1214 Operator::I32x4LtS => Some(Instr::VILt(IShape::I32x4, Signedness::Signed)),
1215 Operator::I32x4LtU => Some(Instr::VILt(IShape::I32x4, Signedness::Unsigned)),
1216 Operator::I32x4GtS => Some(Instr::VIGt(IShape::I32x4, Signedness::Signed)),
1217 Operator::I32x4GtU => Some(Instr::VIGt(IShape::I32x4, Signedness::Unsigned)),
1218 Operator::I32x4LeS => Some(Instr::VILe(IShape::I32x4, Signedness::Signed)),
1219 Operator::I32x4LeU => Some(Instr::VILe(IShape::I32x4, Signedness::Unsigned)),
1220 Operator::I32x4GeS => Some(Instr::VIGe(IShape::I32x4, Signedness::Signed)),
1221 Operator::I32x4GeU => Some(Instr::VIGe(IShape::I32x4, Signedness::Unsigned)),
1222 Operator::I64x2Eq => Some(Instr::VIEq(IShape::I64x2)),
1223 Operator::I64x2Ne => Some(Instr::VIEq(IShape::I64x2)),
1224 Operator::I64x2LtS => Some(Instr::VILt(IShape::I64x2, Signedness::Signed)),
1225 Operator::I64x2GtS => Some(Instr::VIGt(IShape::I64x2, Signedness::Signed)),
1226 Operator::I64x2LeS => Some(Instr::VILe(IShape::I64x2, Signedness::Signed)),
1227 Operator::I64x2GeS => Some(Instr::VIGe(IShape::I64x2, Signedness::Signed)),
1228 Operator::F32x4Eq => Some(Instr::VFEq(FShape::F32x4)),
1229 Operator::F32x4Ne => Some(Instr::VFEq(FShape::F32x4)),
1230 Operator::F32x4Lt => Some(Instr::VFLt(FShape::F32x4)),
1231 Operator::F32x4Gt => Some(Instr::VFGt(FShape::F32x4)),
1232 Operator::F32x4Le => Some(Instr::VFLe(FShape::F32x4)),
1233 Operator::F32x4Ge => Some(Instr::VFGe(FShape::F32x4)),
1234 Operator::F64x2Eq => Some(Instr::VFEq(FShape::F64x2)),
1235 Operator::F64x2Ne => Some(Instr::VFEq(FShape::F64x2)),
1236 Operator::F64x2Lt => Some(Instr::VFLt(FShape::F64x2)),
1237 Operator::F64x2Gt => Some(Instr::VFGt(FShape::F64x2)),
1238 Operator::F64x2Le => Some(Instr::VFLe(FShape::F64x2)),
1239 Operator::F64x2Ge => Some(Instr::VFGe(FShape::F64x2)),
1240 Operator::V128Not => Some(Instr::V128Not),
1241 Operator::V128And => Some(Instr::V128And),
1242 Operator::V128AndNot => Some(Instr::V128AndNot),
1243 Operator::V128Or => Some(Instr::V128Or),
1244 Operator::V128Xor => Some(Instr::V128XOr),
1245 Operator::V128Bitselect => Some(Instr::V128BitSelect),
1246 Operator::V128AnyTrue => Some(Instr::V128AnyTrue),
1247 Operator::I8x16Abs => Some(Instr::VIAbs(IShape::I8x16)),
1248 Operator::I8x16Neg => Some(Instr::VINeg(IShape::I8x16)),
1249 Operator::I8x16Popcnt => Some(Instr::VI8x16PopCnt),
1250 Operator::I8x16AllTrue => Some(Instr::VIAllTrue(IShape::I8x16)),
1251 Operator::I8x16Bitmask => Some(Instr::VIBitMask(IShape::I8x16)),
1252 Operator::I8x16NarrowI16x8S => Some(Instr::VI8x16NarrowI16x8(Signedness::Signed)),
1253 Operator::I8x16NarrowI16x8U => Some(Instr::VI8x16NarrowI16x8(Signedness::Unsigned)),
1254 Operator::I8x16Shl => Some(Instr::VIShl(IShape::I8x16)),
1255 Operator::I8x16ShrS => Some(Instr::VIShr(IShape::I8x16, Signedness::Signed)),
1256 Operator::I8x16ShrU => Some(Instr::VIShr(IShape::I8x16, Signedness::Unsigned)),
1257 Operator::I8x16Add => Some(Instr::VIAdd(IShape::I8x16)),
1258 Operator::I8x16AddSatS => Some(Instr::VIAddSat(IShape::I8x16, Signedness::Signed)),
1259 Operator::I8x16AddSatU => {
1260 Some(Instr::VIAddSat(IShape::I8x16, Signedness::Unsigned))
1261 }
1262 Operator::I8x16Sub => Some(Instr::VISub(IShape::I8x16)),
1263 Operator::I8x16SubSatS => Some(Instr::VISubSat(IShape::I8x16, Signedness::Signed)),
1264 Operator::I8x16SubSatU => {
1265 Some(Instr::VISubSat(IShape::I8x16, Signedness::Unsigned))
1266 }
1267 Operator::I8x16MinS => Some(Instr::VIMin(IShape::I8x16, Signedness::Signed)),
1268 Operator::I8x16MinU => Some(Instr::VIMin(IShape::I8x16, Signedness::Unsigned)),
1269 Operator::I8x16MaxS => Some(Instr::VIMax(IShape::I8x16, Signedness::Signed)),
1270 Operator::I8x16MaxU => Some(Instr::VIMax(IShape::I8x16, Signedness::Unsigned)),
1271 Operator::I8x16AvgrU => Some(Instr::VIAvgr(IShape::I8x16)),
1272 Operator::I16x8ExtAddPairwiseI8x16S => {
1273 Some(Instr::VIExtAddPairwise(IShape::I16x8, Signedness::Signed))
1274 }
1275 Operator::I16x8ExtAddPairwiseI8x16U => {
1276 Some(Instr::VIExtAddPairwise(IShape::I16x8, Signedness::Unsigned))
1277 }
1278 Operator::I16x8Abs => Some(Instr::VIAbs(IShape::I16x8)),
1279 Operator::I16x8Neg => Some(Instr::VINeg(IShape::I16x8)),
1280 Operator::I16x8Q15MulrSatS => Some(Instr::VI16x8Q15MulrSat),
1281 Operator::I16x8AllTrue => Some(Instr::VIAllTrue(IShape::I16x8)),
1282 Operator::I16x8Bitmask => Some(Instr::VIBitMask(IShape::I16x8)),
1283 Operator::I16x8NarrowI32x4S => Some(Instr::VI16x8NarrowI32x4(Signedness::Signed)),
1284 Operator::I16x8NarrowI32x4U => Some(Instr::VI16x8NarrowI32x4(Signedness::Unsigned)),
1285 Operator::I16x8ExtendLowI8x16S => {
1286 Some(Instr::VI16x8ExtendI8x16(Half::Low, Signedness::Signed))
1287 }
1288 Operator::I16x8ExtendHighI8x16S => {
1289 Some(Instr::VI16x8ExtendI8x16(Half::High, Signedness::Signed))
1290 }
1291 Operator::I16x8ExtendLowI8x16U => {
1292 Some(Instr::VI16x8ExtendI8x16(Half::Low, Signedness::Unsigned))
1293 }
1294 Operator::I16x8ExtendHighI8x16U => {
1295 Some(Instr::VI16x8ExtendI8x16(Half::High, Signedness::Unsigned))
1296 }
1297 Operator::I16x8Shl => Some(Instr::VIShl(IShape::I16x8)),
1298 Operator::I16x8ShrS => Some(Instr::VIShr(IShape::I16x8, Signedness::Signed)),
1299 Operator::I16x8ShrU => Some(Instr::VIShr(IShape::I16x8, Signedness::Unsigned)),
1300 Operator::I16x8Add => Some(Instr::VIAdd(IShape::I16x8)),
1301 Operator::I16x8AddSatS => Some(Instr::VIAddSat(IShape::I16x8, Signedness::Signed)),
1302 Operator::I16x8AddSatU => {
1303 Some(Instr::VIAddSat(IShape::I16x8, Signedness::Unsigned))
1304 }
1305 Operator::I16x8Sub => Some(Instr::VISub(IShape::I16x8)),
1306 Operator::I16x8SubSatS => Some(Instr::VISubSat(IShape::I16x8, Signedness::Signed)),
1307 Operator::I16x8SubSatU => {
1308 Some(Instr::VISubSat(IShape::I16x8, Signedness::Unsigned))
1309 }
1310 Operator::I16x8Mul => Some(Instr::VIMul(IShape::I16x8)),
1311 Operator::I16x8MinS => Some(Instr::VIMin(IShape::I16x8, Signedness::Signed)),
1312 Operator::I16x8MinU => Some(Instr::VIMin(IShape::I16x8, Signedness::Unsigned)),
1313 Operator::I16x8MaxS => Some(Instr::VIMax(IShape::I16x8, Signedness::Signed)),
1314 Operator::I16x8MaxU => Some(Instr::VIMax(IShape::I16x8, Signedness::Unsigned)),
1315 Operator::I16x8AvgrU => Some(Instr::VIAvgr(IShape::I16x8)),
1316 Operator::I16x8ExtMulLowI8x16S => Some(Instr::VIExtMul(
1317 IShape::I16x8,
1318 Half::Low,
1319 Signedness::Signed,
1320 )),
1321 Operator::I16x8ExtMulHighI8x16S => Some(Instr::VIExtMul(
1322 IShape::I16x8,
1323 Half::High,
1324 Signedness::Signed,
1325 )),
1326 Operator::I16x8ExtMulLowI8x16U => Some(Instr::VIExtMul(
1327 IShape::I16x8,
1328 Half::Low,
1329 Signedness::Unsigned,
1330 )),
1331 Operator::I16x8ExtMulHighI8x16U => Some(Instr::VIExtMul(
1332 IShape::I16x8,
1333 Half::High,
1334 Signedness::Unsigned,
1335 )),
1336 Operator::I32x4ExtAddPairwiseI16x8S => {
1337 Some(Instr::VIExtAddPairwise(IShape::I32x4, Signedness::Signed))
1338 }
1339 Operator::I32x4ExtAddPairwiseI16x8U => {
1340 Some(Instr::VIExtAddPairwise(IShape::I32x4, Signedness::Unsigned))
1341 }
1342 Operator::I32x4Abs => Some(Instr::VIAbs(IShape::I32x4)),
1343 Operator::I32x4Neg => Some(Instr::VINeg(IShape::I32x4)),
1344 Operator::I32x4AllTrue => Some(Instr::VIAllTrue(IShape::I32x4)),
1345 Operator::I32x4Bitmask => Some(Instr::VIBitMask(IShape::I32x4)),
1346 Operator::I32x4ExtendLowI16x8S => {
1347 Some(Instr::VI32x4ExtendI16x8(Half::Low, Signedness::Signed))
1348 }
1349 Operator::I32x4ExtendHighI16x8S => {
1350 Some(Instr::VI32x4ExtendI16x8(Half::High, Signedness::Signed))
1351 }
1352 Operator::I32x4ExtendLowI16x8U => {
1353 Some(Instr::VI32x4ExtendI16x8(Half::Low, Signedness::Unsigned))
1354 }
1355 Operator::I32x4ExtendHighI16x8U => {
1356 Some(Instr::VI32x4ExtendI16x8(Half::High, Signedness::Unsigned))
1357 }
1358 Operator::I32x4Shl => Some(Instr::VIShl(IShape::I32x4)),
1359 Operator::I32x4ShrS => Some(Instr::VIShr(IShape::I32x4, Signedness::Signed)),
1360 Operator::I32x4ShrU => Some(Instr::VIShr(IShape::I32x4, Signedness::Unsigned)),
1361 Operator::I32x4Add => Some(Instr::VIAdd(IShape::I32x4)),
1362 Operator::I32x4Sub => Some(Instr::VISub(IShape::I32x4)),
1363 Operator::I32x4Mul => Some(Instr::VIMul(IShape::I32x4)),
1364 Operator::I32x4MinS => Some(Instr::VIMin(IShape::I32x4, Signedness::Signed)),
1365 Operator::I32x4MinU => Some(Instr::VIMin(IShape::I32x4, Signedness::Unsigned)),
1366 Operator::I32x4MaxS => Some(Instr::VIMax(IShape::I32x4, Signedness::Signed)),
1367 Operator::I32x4MaxU => Some(Instr::VIMax(IShape::I32x4, Signedness::Unsigned)),
1368 Operator::I32x4DotI16x8S => Some(Instr::VI32x4DotI16x8),
1369 Operator::I32x4ExtMulLowI16x8S => Some(Instr::VIExtMul(
1370 IShape::I32x4,
1371 Half::Low,
1372 Signedness::Signed,
1373 )),
1374 Operator::I32x4ExtMulHighI16x8S => Some(Instr::VIExtMul(
1375 IShape::I32x4,
1376 Half::High,
1377 Signedness::Signed,
1378 )),
1379 Operator::I32x4ExtMulLowI16x8U => Some(Instr::VIExtMul(
1380 IShape::I32x4,
1381 Half::Low,
1382 Signedness::Unsigned,
1383 )),
1384 Operator::I32x4ExtMulHighI16x8U => Some(Instr::VIExtMul(
1385 IShape::I32x4,
1386 Half::High,
1387 Signedness::Unsigned,
1388 )),
1389 Operator::I64x2Abs => Some(Instr::VIAbs(IShape::I64x2)),
1390 Operator::I64x2Neg => Some(Instr::VINeg(IShape::I64x2)),
1391 Operator::I64x2AllTrue => Some(Instr::VIAllTrue(IShape::I64x2)),
1392 Operator::I64x2Bitmask => Some(Instr::VIBitMask(IShape::I64x2)),
1393 Operator::I64x2ExtendLowI32x4S => {
1394 Some(Instr::VI64x2ExtendI32x4(Half::Low, Signedness::Signed))
1395 }
1396 Operator::I64x2ExtendHighI32x4S => {
1397 Some(Instr::VI64x2ExtendI32x4(Half::High, Signedness::Signed))
1398 }
1399 Operator::I64x2ExtendLowI32x4U => {
1400 Some(Instr::VI64x2ExtendI32x4(Half::Low, Signedness::Unsigned))
1401 }
1402 Operator::I64x2ExtendHighI32x4U => {
1403 Some(Instr::VI64x2ExtendI32x4(Half::High, Signedness::Unsigned))
1404 }
1405 Operator::I64x2Shl => Some(Instr::VIShl(IShape::I64x2)),
1406 Operator::I64x2ShrS => Some(Instr::VIShr(IShape::I64x2, Signedness::Signed)),
1407 Operator::I64x2ShrU => Some(Instr::VIShr(IShape::I64x2, Signedness::Unsigned)),
1408 Operator::I64x2Add => Some(Instr::VIAdd(IShape::I64x2)),
1409 Operator::I64x2Sub => Some(Instr::VISub(IShape::I64x2)),
1410 Operator::I64x2Mul => Some(Instr::VIMul(IShape::I64x2)),
1411 Operator::I64x2ExtMulLowI32x4S => Some(Instr::VIExtMul(
1412 IShape::I64x2,
1413 Half::Low,
1414 Signedness::Signed,
1415 )),
1416 Operator::I64x2ExtMulHighI32x4S => Some(Instr::VIExtMul(
1417 IShape::I64x2,
1418 Half::High,
1419 Signedness::Signed,
1420 )),
1421 Operator::I64x2ExtMulLowI32x4U => Some(Instr::VIExtMul(
1422 IShape::I64x2,
1423 Half::Low,
1424 Signedness::Unsigned,
1425 )),
1426 Operator::I64x2ExtMulHighI32x4U => Some(Instr::VIExtMul(
1427 IShape::I64x2,
1428 Half::High,
1429 Signedness::Unsigned,
1430 )),
1431 Operator::F32x4Ceil => Some(Instr::VFCeil(FShape::F32x4)),
1432 Operator::F32x4Floor => Some(Instr::VFFloor(FShape::F32x4)),
1433 Operator::F32x4Trunc => Some(Instr::VFTrunc(FShape::F32x4)),
1434 Operator::F32x4Nearest => Some(Instr::VFNearest(FShape::F32x4)),
1435 Operator::F32x4Abs => Some(Instr::VFAbs(FShape::F32x4)),
1436 Operator::F32x4Neg => Some(Instr::VFNeg(FShape::F32x4)),
1437 Operator::F32x4Sqrt => Some(Instr::VFSqrt(FShape::F32x4)),
1438 Operator::F32x4Add => Some(Instr::VFAdd(FShape::F32x4)),
1439 Operator::F32x4Sub => Some(Instr::VFSub(FShape::F32x4)),
1440 Operator::F32x4Mul => Some(Instr::VFMul(FShape::F32x4)),
1441 Operator::F32x4Div => Some(Instr::VFDiv(FShape::F32x4)),
1442 Operator::F32x4Min => Some(Instr::VFMin(FShape::F32x4)),
1443 Operator::F32x4Max => Some(Instr::VFMax(FShape::F32x4)),
1444 Operator::F32x4PMin => Some(Instr::VFPMin(FShape::F32x4)),
1445 Operator::F32x4PMax => Some(Instr::VFPMax(FShape::F32x4)),
1446 Operator::F64x2Ceil => Some(Instr::VFCeil(FShape::F64x2)),
1447 Operator::F64x2Floor => Some(Instr::VFFloor(FShape::F64x2)),
1448 Operator::F64x2Trunc => Some(Instr::VFTrunc(FShape::F64x2)),
1449 Operator::F64x2Nearest => Some(Instr::VFNearest(FShape::F64x2)),
1450 Operator::F64x2Abs => Some(Instr::VFAbs(FShape::F64x2)),
1451 Operator::F64x2Neg => Some(Instr::VFNeg(FShape::F64x2)),
1452 Operator::F64x2Sqrt => Some(Instr::VFSqrt(FShape::F64x2)),
1453 Operator::F64x2Add => Some(Instr::VFAdd(FShape::F64x2)),
1454 Operator::F64x2Sub => Some(Instr::VFSub(FShape::F64x2)),
1455 Operator::F64x2Mul => Some(Instr::VFMul(FShape::F64x2)),
1456 Operator::F64x2Div => Some(Instr::VFDiv(FShape::F64x2)),
1457 Operator::F64x2Min => Some(Instr::VFMin(FShape::F64x2)),
1458 Operator::F64x2Max => Some(Instr::VFMax(FShape::F64x2)),
1459 Operator::F64x2PMin => Some(Instr::VFPMin(FShape::F64x2)),
1460 Operator::F64x2PMax => Some(Instr::VFPMax(FShape::F64x2)),
1461 Operator::I32x4TruncSatF32x4S => Some(Instr::ITruncSatF(
1462 IntWidth::I32,
1463 FloatWidth::F32,
1464 Signedness::Signed,
1465 )),
1466 Operator::I32x4TruncSatF32x4U => Some(Instr::ITruncSatF(
1467 IntWidth::I32,
1468 FloatWidth::F32,
1469 Signedness::Unsigned,
1470 )),
1471 Operator::F32x4ConvertI32x4S => Some(Instr::FConvertI(
1472 FloatWidth::F32,
1473 IntWidth::I32,
1474 Signedness::Signed,
1475 )),
1476 Operator::F32x4ConvertI32x4U => Some(Instr::FConvertI(
1477 FloatWidth::F32,
1478 IntWidth::I32,
1479 Signedness::Unsigned,
1480 )),
1481 Operator::I32x4TruncSatF64x2SZero => Some(Instr::ITruncSatF(
1482 IntWidth::I32,
1483 FloatWidth::F64,
1484 Signedness::Signed,
1485 )),
1486 Operator::I32x4TruncSatF64x2UZero => Some(Instr::ITruncSatF(
1487 IntWidth::I32,
1488 FloatWidth::F64,
1489 Signedness::Unsigned,
1490 )),
1491 Operator::F64x2ConvertLowI32x4S => Some(Instr::FConvertI(
1492 FloatWidth::F64,
1493 IntWidth::I32,
1494 Signedness::Signed,
1495 )),
1496 Operator::F64x2ConvertLowI32x4U => Some(Instr::FConvertI(
1497 FloatWidth::F64,
1498 IntWidth::I32,
1499 Signedness::Unsigned,
1500 )),
1501 Operator::F32x4DemoteF64x2Zero => Some(Instr::F32DemoteF64),
1502 Operator::F64x2PromoteLowF32x4 => Some(Instr::F64PromoteF32),
1503 Operator::I8x16RelaxedSwizzle => {
1504 return Err("Relaxed SIMD instructions are not supported".to_string());
1505 }
1506 Operator::I32x4RelaxedTruncF32x4S => {
1507 return Err("Relaxed SIMD instructions are not supported".to_string());
1508 }
1509 Operator::I32x4RelaxedTruncF32x4U => {
1510 return Err("Relaxed SIMD instructions are not supported".to_string());
1511 }
1512 Operator::I32x4RelaxedTruncF64x2SZero => {
1513 return Err("Relaxed SIMD instructions are not supported".to_string());
1514 }
1515 Operator::I32x4RelaxedTruncF64x2UZero => {
1516 return Err("Relaxed SIMD instructions are not supported".to_string());
1517 }
1518 Operator::F32x4RelaxedMadd => {
1519 return Err("Relaxed SIMD instructions are not supported".to_string());
1520 }
1521 Operator::F32x4RelaxedNmadd => {
1522 return Err("Relaxed SIMD instructions are not supported".to_string());
1523 }
1524 Operator::F64x2RelaxedMadd => {
1525 return Err("Relaxed SIMD instructions are not supported".to_string());
1526 }
1527 Operator::F64x2RelaxedNmadd => {
1528 return Err("Relaxed SIMD instructions are not supported".to_string());
1529 }
1530 Operator::I8x16RelaxedLaneselect => {
1531 return Err("Relaxed SIMD instructions are not supported".to_string());
1532 }
1533 Operator::I16x8RelaxedLaneselect => {
1534 return Err("Relaxed SIMD instructions are not supported".to_string());
1535 }
1536 Operator::I32x4RelaxedLaneselect => {
1537 return Err("Relaxed SIMD instructions are not supported".to_string());
1538 }
1539 Operator::I64x2RelaxedLaneselect => {
1540 return Err("Relaxed SIMD instructions are not supported".to_string());
1541 }
1542 Operator::F32x4RelaxedMin => {
1543 return Err("Relaxed SIMD instructions are not supported".to_string());
1544 }
1545 Operator::F32x4RelaxedMax => {
1546 return Err("Relaxed SIMD instructions are not supported".to_string());
1547 }
1548 Operator::F64x2RelaxedMin => {
1549 return Err("Relaxed SIMD instructions are not supported".to_string());
1550 }
1551 Operator::F64x2RelaxedMax => {
1552 return Err("Relaxed SIMD instructions are not supported".to_string());
1553 }
1554 Operator::I16x8RelaxedQ15mulrS => {
1555 return Err("Relaxed SIMD instructions are not supported".to_string());
1556 }
1557 Operator::I16x8RelaxedDotI8x16I7x16S => {
1558 return Err("Relaxed SIMD instructions are not supported".to_string());
1559 }
1560 Operator::I32x4RelaxedDotI8x16I7x16AddS => {
1561 return Err("Relaxed SIMD instructions are not supported".to_string());
1562 }
1563 Operator::CallRef { .. } => {
1564 return Err("Function Reference Types Proposal is not supported".to_string());
1565 }
1566 Operator::ReturnCallRef { .. } => {
1567 return Err("Function Reference Types Proposal is not supported".to_string());
1568 }
1569 Operator::RefAsNonNull => {
1570 return Err("Function Reference Types Proposal is not supported".to_string());
1571 }
1572 Operator::BrOnNull { .. } => {
1573 return Err("Function Reference Types Proposal is not supported".to_string());
1574 }
1575 Operator::BrOnNonNull { .. } => {
1576 return Err("Function Reference Types Proposal is not supported".to_string());
1577 }
1578 Operator::TryTable { .. } => {
1579 return Err("Exception Handling Proposal is not supported".to_string());
1580 }
1581 Operator::ThrowRef { .. } => {
1582 return Err("Exception Handling Proposal is not supported".to_string());
1583 }
1584 Operator::RefEq => {
1585 return Err("GC Proposal is not supported".to_string());
1586 }
1587 Operator::StructNew { .. } => {
1588 return Err("GC Proposal is not supported".to_string());
1589 }
1590 Operator::StructNewDefault { .. } => {
1591 return Err("GC Proposal is not supported".to_string());
1592 }
1593 Operator::StructGet { .. } => {
1594 return Err("GC Proposal is not supported".to_string());
1595 }
1596 Operator::StructGetS { .. } => {
1597 return Err("GC Proposal is not supported".to_string());
1598 }
1599 Operator::StructGetU { .. } => {
1600 return Err("GC Proposal is not supported".to_string());
1601 }
1602 Operator::StructSet { .. } => {
1603 return Err("GC Proposal is not supported".to_string());
1604 }
1605 Operator::ArrayNew { .. } => {
1606 return Err("GC Proposal is not supported".to_string());
1607 }
1608 Operator::ArrayNewDefault { .. } => {
1609 return Err("GC Proposal is not supported".to_string());
1610 }
1611 Operator::ArrayNewFixed { .. } => {
1612 return Err("GC Proposal is not supported".to_string());
1613 }
1614 Operator::ArrayNewData { .. } => {
1615 return Err("GC Proposal is not supported".to_string());
1616 }
1617 Operator::ArrayNewElem { .. } => {
1618 return Err("GC Proposal is not supported".to_string());
1619 }
1620 Operator::ArrayGet { .. } => {
1621 return Err("GC Proposal is not supported".to_string());
1622 }
1623 Operator::ArrayGetS { .. } => {
1624 return Err("GC Proposal is not supported".to_string());
1625 }
1626 Operator::ArrayGetU { .. } => {
1627 return Err("GC Proposal is not supported".to_string());
1628 }
1629 Operator::ArraySet { .. } => {
1630 return Err("GC Proposal is not supported".to_string());
1631 }
1632 Operator::ArrayLen => {
1633 return Err("GC Proposal is not supported".to_string());
1634 }
1635 Operator::ArrayFill { .. } => {
1636 return Err("GC Proposal is not supported".to_string());
1637 }
1638 Operator::ArrayCopy { .. } => {
1639 return Err("GC Proposal is not supported".to_string());
1640 }
1641 Operator::ArrayInitData { .. } => {
1642 return Err("GC Proposal is not supported".to_string());
1643 }
1644 Operator::ArrayInitElem { .. } => {
1645 return Err("GC Proposal is not supported".to_string());
1646 }
1647 Operator::RefTestNonNull { .. } => {
1648 return Err("GC Proposal is not supported".to_string());
1649 }
1650 Operator::RefTestNullable { .. } => {
1651 return Err("GC Proposal is not supported".to_string());
1652 }
1653 Operator::RefCastNonNull { .. } => {
1654 return Err("GC Proposal is not supported".to_string());
1655 }
1656 Operator::RefCastNullable { .. } => {
1657 return Err("GC Proposal is not supported".to_string());
1658 }
1659 Operator::BrOnCast { .. } => {
1660 return Err("GC Proposal is not supported".to_string());
1661 }
1662 Operator::BrOnCastFail { .. } => {
1663 return Err("GC Proposal is not supported".to_string());
1664 }
1665 Operator::AnyConvertExtern => {
1666 return Err("GC Proposal is not supported".to_string());
1667 }
1668 Operator::ExternConvertAny => {
1669 return Err("GC Proposal is not supported".to_string());
1670 }
1671 Operator::GlobalAtomicGet { .. } => {
1672 return Err("Shared Everything Threads proposal is not supported".to_string());
1673 }
1674 Operator::GlobalAtomicSet { .. } => {
1675 return Err("Shared Everything Threads proposal is not supported".to_string());
1676 }
1677 Operator::GlobalAtomicRmwAdd { .. } => {
1678 return Err("Shared Everything Threads proposal is not supported".to_string());
1679 }
1680 Operator::GlobalAtomicRmwSub { .. } => {
1681 return Err("Shared Everything Threads proposal is not supported".to_string());
1682 }
1683 Operator::GlobalAtomicRmwAnd { .. } => {
1684 return Err("Shared Everything Threads proposal is not supported".to_string());
1685 }
1686 Operator::GlobalAtomicRmwOr { .. } => {
1687 return Err("Shared Everything Threads proposal is not supported".to_string());
1688 }
1689 Operator::GlobalAtomicRmwXor { .. } => {
1690 return Err("Shared Everything Threads proposal is not supported".to_string());
1691 }
1692 Operator::GlobalAtomicRmwXchg { .. } => {
1693 return Err("Shared Everything Threads proposal is not supported".to_string());
1694 }
1695 Operator::GlobalAtomicRmwCmpxchg { .. } => {
1696 return Err("Shared Everything Threads proposal is not supported".to_string());
1697 }
1698 Operator::TableAtomicGet { .. } => {
1699 return Err("Shared Everything Threads proposal is not supported".to_string());
1700 }
1701 Operator::TableAtomicSet { .. } => {
1702 return Err("Shared Everything Threads proposal is not supported".to_string());
1703 }
1704 Operator::TableAtomicRmwXchg { .. } => {
1705 return Err("Shared Everything Threads proposal is not supported".to_string());
1706 }
1707 Operator::TableAtomicRmwCmpxchg { .. } => {
1708 return Err("Shared Everything Threads proposal is not supported".to_string());
1709 }
1710 Operator::StructAtomicGet { .. } => {
1711 return Err("Shared Everything Threads proposal is not supported".to_string());
1712 }
1713 Operator::StructAtomicGetS { .. } => {
1714 return Err("Shared Everything Threads proposal is not supported".to_string());
1715 }
1716 Operator::StructAtomicGetU { .. } => {
1717 return Err("Shared Everything Threads proposal is not supported".to_string());
1718 }
1719 Operator::StructAtomicSet { .. } => {
1720 return Err("Shared Everything Threads proposal is not supported".to_string());
1721 }
1722 Operator::StructAtomicRmwAdd { .. } => {
1723 return Err("Shared Everything Threads proposal is not supported".to_string());
1724 }
1725 Operator::StructAtomicRmwSub { .. } => {
1726 return Err("Shared Everything Threads proposal is not supported".to_string());
1727 }
1728 Operator::StructAtomicRmwAnd { .. } => {
1729 return Err("Shared Everything Threads proposal is not supported".to_string());
1730 }
1731 Operator::StructAtomicRmwOr { .. } => {
1732 return Err("Shared Everything Threads proposal is not supported".to_string());
1733 }
1734 Operator::StructAtomicRmwXor { .. } => {
1735 return Err("Shared Everything Threads proposal is not supported".to_string());
1736 }
1737 Operator::StructAtomicRmwXchg { .. } => {
1738 return Err("Shared Everything Threads proposal is not supported".to_string());
1739 }
1740 Operator::StructAtomicRmwCmpxchg { .. } => {
1741 return Err("Shared Everything Threads proposal is not supported".to_string());
1742 }
1743 Operator::ArrayAtomicGet { .. } => {
1744 return Err("Shared Everything Threads proposal is not supported".to_string());
1745 }
1746 Operator::ArrayAtomicGetS { .. } => {
1747 return Err("Shared Everything Threads proposal is not supported".to_string());
1748 }
1749 Operator::ArrayAtomicGetU { .. } => {
1750 return Err("Shared Everything Threads proposal is not supported".to_string());
1751 }
1752 Operator::ArrayAtomicSet { .. } => {
1753 return Err("Shared Everything Threads proposal is not supported".to_string());
1754 }
1755 Operator::ArrayAtomicRmwAdd { .. } => {
1756 return Err("Shared Everything Threads proposal is not supported".to_string());
1757 }
1758 Operator::ArrayAtomicRmwSub { .. } => {
1759 return Err("Shared Everything Threads proposal is not supported".to_string());
1760 }
1761 Operator::ArrayAtomicRmwAnd { .. } => {
1762 return Err("Shared Everything Threads proposal is not supported".to_string());
1763 }
1764 Operator::ArrayAtomicRmwOr { .. } => {
1765 return Err("Shared Everything Threads proposal is not supported".to_string());
1766 }
1767 Operator::ArrayAtomicRmwXor { .. } => {
1768 return Err("Shared Everything Threads proposal is not supported".to_string());
1769 }
1770 Operator::ArrayAtomicRmwXchg { .. } => {
1771 return Err("Shared Everything Threads proposal is not supported".to_string());
1772 }
1773 Operator::ArrayAtomicRmwCmpxchg { .. } => {
1774 return Err("Shared Everything Threads proposal is not supported".to_string());
1775 }
1776 Operator::RefI31Shared => {
1777 return Err("Shared Everything Threads proposal is not supported".to_string());
1778 }
1779 Operator::ContNew { .. } => {
1780 return Err("Task Switching proposal is not supported".to_string());
1781 }
1782 Operator::ContBind { .. } => {
1783 return Err("Task Switching proposal is not supported".to_string());
1784 }
1785 Operator::Suspend { .. } => {
1786 return Err("Task Switching proposal is not supported".to_string());
1787 }
1788 Operator::Resume { .. } => {
1789 return Err("Task Switching proposal is not supported".to_string());
1790 }
1791 Operator::ResumeThrow { .. } => {
1792 return Err("Task Switching proposal is not supported".to_string());
1793 }
1794 Operator::Switch { .. } => {
1795 return Err("Task Switching proposal is not supported".to_string());
1796 }
1797 Operator::I64Add128 => {
1798 return Err("Wide Arithmetic proposal is not supported".to_string());
1799 }
1800 Operator::I64Sub128 => {
1801 return Err("Wide Arithmetic proposal is not supported".to_string());
1802 }
1803 Operator::I64MulWideS => {
1804 return Err("Wide Arithmetic proposal is not supported".to_string());
1805 }
1806 Operator::I64MulWideU => {
1807 return Err("Wide Arithmetic proposal is not supported".to_string());
1808 }
1809 _ => return Err(format!("Unsupported operator: {op:?}")),
1810 };
1811
1812 if let Some(instr) = instr {
1813 stack.last_mut().unwrap().push(instr);
1814 }
1815 }
1816
1817 match stack.into_iter().next() {
1818 Some(OperatorTarget::TopLevel(instrs)) => Ok(Expr { instrs }),
1819 _ => Err("Unexpected stack state".to_string()),
1820 }
1821 }
1822}
1823
1824impl<Ast> TryFrom<(Parser, &[u8])> for Sections<CoreIndexSpace, CoreSectionType, CoreSection<Ast>>
1825where
1826 Ast: AstCustomization,
1827 Ast::Expr: TryFromExprSource,
1828 Ast::Data: From<Data<Ast::Expr>>,
1829 Ast::Custom: From<Custom>,
1830{
1831 type Error = String;
1832
1833 fn try_from(value: (Parser, &[u8])) -> Result<Self, Self::Error> {
1834 let (parser, data) = value;
1835 let mut sections = Vec::new();
1836 for payload in parser.parse_all(data) {
1837 let payload = payload.map_err(|e| format!("Error parsing core module: {e:?}"))?;
1838 match payload {
1839 Payload::Version { .. } => {}
1840 Payload::TypeSection(reader) => {
1841 for tpe in reader.into_iter_err_on_gc_types() {
1842 let tpe = tpe.map_err(|e| format!("Error parsing core module type section: {e:?}"))?;
1843 sections.push(CoreSection::Type(tpe.try_into()?));
1844 }
1845 }
1846 Payload::ImportSection(reader) => {
1847 for import in reader {
1848 let import = import.map_err(|e| format!("Error parsing core module import section: {e:?}"))?;
1849 sections.push(CoreSection::Import(import.try_into()?))
1850 }
1851 }
1852 Payload::FunctionSection(reader) => {
1853 for function in reader {
1854 let type_idx = function.map_err(|e| format!("Error parsing core module function section: {e:?}"))?;
1855 sections.push(CoreSection::Func(FuncTypeRef { type_idx }));
1856 }
1857 }
1858 Payload::TableSection(reader) => {
1859 for table in reader {
1860 let table = table.map_err(|e| format!("Error parsing core module table section: {e:?}"))?;
1861 sections.push(CoreSection::Table(table.try_into()?))
1862 }
1863 }
1864 Payload::MemorySection(reader) => {
1865 for mem_type in reader {
1866 let memory = mem_type.map_err(|e| format!("Error parsing core module memory section: {e:?}"))?;
1867 sections.push(CoreSection::Mem(memory.try_into()?))
1868 }
1869 }
1870 Payload::TagSection(_) =>
1871 return Err("Unexpected tag section in core module; exception handling proposal is not supported".to_string()),
1872 Payload::GlobalSection(reader) => {
1873 for global in reader {
1874 let global = global.map_err(|e| format!("Error parsing core module global section: {e:?}"))?;
1875 sections.push(CoreSection::Global(global.try_into()?))
1876 }
1877 }
1878 Payload::ExportSection(reader) => {
1879 for export in reader {
1880 let export = export.map_err(|e| format!("Error parsing core module export section: {e:?}"))?;
1881 sections.push(CoreSection::Export(export.try_into()?))
1882 }
1883 }
1884 Payload::StartSection { func, .. } => {
1885 sections.push(CoreSection::Start(Start { func }))
1886 }
1887 Payload::ElementSection(reader) => {
1888 for element in reader {
1889 let element = element.map_err(|e| format!("Error parsing core module element section: {e:?}"))?;
1890 sections.push(CoreSection::Elem(element.try_into()?))
1891 }
1892 }
1893 Payload::DataCountSection { count, .. } => {
1894 sections.push(CoreSection::DataCount(DataCount { count }))
1895 }
1896 Payload::DataSection(reader) => {
1897 for data in reader {
1898 let data = data.map_err(|e| format!("Error parsing core module data section: {e:?}"))?;
1899 let data: Data<Ast::Expr> = data.try_into()?;
1900 sections.push(CoreSection::Data(data.into()));
1901 }
1902 }
1903 Payload::CodeSectionStart { .. } => {
1904 }
1906 Payload::CodeSectionEntry(function_body) => {
1907 sections.push(CoreSection::Code(function_body.try_into()?))
1908 }
1909 Payload::CustomSection(reader) => {
1910 sections.push(CoreSection::Custom(Custom {
1911 name: reader.name().to_string(),
1912 data: reader.data().to_vec(),
1913 }.into()))
1914 }
1915 Payload::End(_) => {}
1916 Payload::InstanceSection(_) =>
1917 return Err("Unexpected component section in core module".to_string()),
1918 Payload::CoreTypeSection(_) =>
1919 return Err("Unexpected component section in core module".to_string()),
1920 Payload::ModuleSection { .. } =>
1921 return Err("Unexpected module section in core module".to_string()),
1922 Payload::ComponentSection { .. } =>
1923 return Err("Unexpected component section in core module".to_string()),
1924 Payload::ComponentInstanceSection(_) =>
1925 return Err("Unexpected component instance section in core module".to_string()),
1926 Payload::ComponentAliasSection(_) =>
1927 return Err("Unexpected component alias section in core module".to_string()),
1928 Payload::ComponentTypeSection(_) =>
1929 return Err("Unexpected component type section in core module".to_string()),
1930 Payload::ComponentCanonicalSection(_) =>
1931 return Err("Unexpected component canonical section in core module".to_string()),
1932 Payload::ComponentStartSection { .. } =>
1933 return Err("Unexpected component start section in core module".to_string()),
1934 Payload::ComponentImportSection(_) =>
1935 return Err("Unexpected component import section in core module".to_string()),
1936 Payload::ComponentExportSection(_) =>
1937 return Err("Unexpected component export section in core module".to_string()),
1938 Payload::UnknownSection { .. } =>
1939 return Err("Unexpected unknown section in core module".to_string()),
1940 _ => return Err("Unexpected payload in core module".to_string()),
1941 }
1942 }
1943 Ok(Sections::from_flat(sections))
1944 }
1945}
1946
1947impl<Ast> TryFrom<(Parser, &[u8])> for Module<Ast>
1948where
1949 Ast: AstCustomization,
1950 Ast::Expr: TryFromExprSource,
1951 Ast::Data: From<Data<Ast::Expr>>,
1952 Ast::Custom: From<Custom>,
1953{
1954 type Error = String;
1955
1956 fn try_from(value: (Parser, &[u8])) -> Result<Self, Self::Error> {
1957 let sections =
1958 Sections::<CoreIndexSpace, CoreSectionType, CoreSection<Ast>>::try_from(value)?;
1959 Ok(sections.into())
1960 }
1961}
1962
1963struct OperatorsReaderExprSource<'a> {
1964 reader: OperatorsReader<'a>,
1965}
1966
1967impl<'a> OperatorsReaderExprSource<'a> {
1968 pub fn new(reader: OperatorsReader<'a>) -> Self {
1969 Self { reader }
1970 }
1971}
1972
1973impl ExprSource for OperatorsReaderExprSource<'_> {
1974 fn unparsed(self) -> Result<Vec<u8>, String> {
1975 let binary_reader: BinaryReader = self.reader.get_binary_reader();
1976 let range = binary_reader.range();
1977 let bytes = self.reader.get_binary_reader().read_bytes(range.count());
1978 bytes
1979 .map_err(|e| format!("Error reading bytes from binary reader: {e:?}"))
1980 .map(|bytes| bytes.to_vec())
1981 }
1982}
1983
1984impl IntoIterator for OperatorsReaderExprSource<'_> {
1985 type Item = Result<Instr, String>;
1986 type IntoIter = Box<dyn Iterator<Item = Result<Instr, String>>>;
1987
1988 fn into_iter(self) -> Self::IntoIter {
1989 let expr: Result<Expr, String> = self.reader.try_into();
1991 match expr {
1992 Err(err) => Box::new(vec![Err(err)].into_iter()),
1993 Ok(expr) => Box::new(expr.instrs.into_iter().map(Ok)),
1994 }
1995 }
1996}
1997
1998struct RefFuncExprSource {
1999 func_idx: FuncIdx,
2000}
2001
2002impl RefFuncExprSource {
2003 pub fn new(func_idx: FuncIdx) -> Self {
2004 Self { func_idx }
2005 }
2006}
2007
2008impl ExprSource for RefFuncExprSource {
2009 fn unparsed(self) -> Result<Vec<u8>, String> {
2010 let mut result: Vec<u8> = Vec::new();
2011 result.write_all(&[0xd2u8]).unwrap();
2012 leb128::write::unsigned(&mut result, self.func_idx as u64).unwrap();
2013 result.write_all(&[0x0bu8]).unwrap();
2014 Ok(result)
2015 }
2016}
2017
2018impl IntoIterator for RefFuncExprSource {
2019 type Item = Result<Instr, String>;
2020 type IntoIter = Box<dyn Iterator<Item = Result<Instr, String>>>;
2021
2022 fn into_iter(self) -> Self::IntoIter {
2023 Box::new(vec![Instr::RefFunc(self.func_idx)].into_iter().map(Ok))
2024 }
2025}