From 172df860b9b8c9e8ff3e643cbbd982ae3d721acd Mon Sep 17 00:00:00 2001 From: Christof Petig Date: Sat, 19 Apr 2025 13:05:27 +0200 Subject: [PATCH 01/13] more fixed size implementation --- crates/c/src/lib.rs | 10 +++++++ crates/core/src/abi.rs | 35 ++++++++++++++++++++++++- crates/core/src/lib.rs | 5 +++- crates/core/src/types.rs | 4 ++- crates/csharp/src/function.rs | 2 ++ crates/moonbit/src/lib.rs | 2 ++ crates/rust/src/bindgen.rs | 2 ++ crates/rust/src/interface.rs | 10 +++++++ tests/runtime/fixed-size-list/runner.rs | 6 +++++ tests/runtime/fixed-size-list/test.rs | 8 ++++++ tests/runtime/fixed-size-list/test.wit | 21 +++++++++++++++ 11 files changed, 102 insertions(+), 3 deletions(-) create mode 100644 tests/runtime/fixed-size-list/runner.rs create mode 100644 tests/runtime/fixed-size-list/test.rs create mode 100644 tests/runtime/fixed-size-list/test.wit diff --git a/crates/c/src/lib.rs b/crates/c/src/lib.rs index d1d11ddc8..8999112d5 100644 --- a/crates/c/src/lib.rs +++ b/crates/c/src/lib.rs @@ -1706,6 +1706,16 @@ impl<'a> wit_bindgen_core::AnonymousTypeGenerator<'a> for InterfaceGenerator<'a> fn anonymous_type_type(&mut self, _id: TypeId, _ty: &Type, _docs: &Docs) { todo!("print_anonymous_type for type"); } + + fn anonymous_type_fixed_size_list( + &mut self, + _id: TypeId, + _ty: &Type, + _size: u32, + _docs: &Docs, + ) { + todo!("print_anonymous_type for fixed size list"); + } } pub enum CTypeNameInfo<'a> { diff --git a/crates/core/src/abi.rs b/crates/core/src/abi.rs index 98e2bf998..f1fca1fcc 100644 --- a/crates/core/src/abi.rs +++ b/crates/core/src/abi.rs @@ -309,6 +309,21 @@ def_instruction! { ty: TypeId, } : [2] => [1], + /// Pops all fields for a fixed list off the stack and then composes them + /// into an array. + FixedSizeListLift { + elements: &'a Type, + size: u32, + id: TypeId, + } : [*size as usize] => [1], + + /// Pops an array off the stack, decomposes the elements and then pushes them onto the stack. + FixedSizeListLower { + elements: &'a Type, + size: u32, + id: TypeId, + } : [1] => [*size as usize], + /// Pushes an operand onto the stack representing the list item from /// each iteration of the list. /// @@ -1735,7 +1750,25 @@ impl<'a, B: Bindgen> Generator<'a, B> { }); } TypeDefKind::Unknown => unreachable!(), - TypeDefKind::FixedSizeList(..) => todo!(), + TypeDefKind::FixedSizeList(ty, size) => { + let mut temp = Vec::new(); + self.resolve.push_flat(&Type::Id(id), &mut temp); + let mut args = self + .stack + .drain(self.stack.len() - temp.len()..) + .collect::>(); + for _ in 0..*size { + temp.truncate(0); + self.resolve.push_flat(ty, &mut temp); + self.stack.extend(args.drain(..temp.len())); + self.lift(ty); + } + self.emit(&FixedSizeListLift { + elements: ty, + size: *size, + id, + }); + } }, } } diff --git a/crates/core/src/lib.rs b/crates/core/src/lib.rs index 993583b06..ff54d2815 100644 --- a/crates/core/src/lib.rs +++ b/crates/core/src/lib.rs @@ -195,6 +195,7 @@ pub trait AnonymousTypeGenerator<'a> { fn anonymous_type_option(&mut self, id: TypeId, ty: &Type, docs: &Docs); fn anonymous_type_result(&mut self, id: TypeId, ty: &Result_, docs: &Docs); fn anonymous_type_list(&mut self, id: TypeId, ty: &Type, docs: &Docs); + fn anonymous_type_fixed_size_list(&mut self, id: TypeId, ty: &Type, size: u32, docs: &Docs); fn anonymous_type_future(&mut self, id: TypeId, ty: &Option, docs: &Docs); fn anonymous_type_stream(&mut self, id: TypeId, ty: &Option, docs: &Docs); fn anonymous_type_type(&mut self, id: TypeId, ty: &Type, docs: &Docs); @@ -217,7 +218,9 @@ pub trait AnonymousTypeGenerator<'a> { TypeDefKind::Future(f) => self.anonymous_type_future(id, f, &ty.docs), TypeDefKind::Stream(s) => self.anonymous_type_stream(id, s, &ty.docs), TypeDefKind::Handle(handle) => self.anonymous_type_handle(id, handle, &ty.docs), - TypeDefKind::FixedSizeList(..) => todo!(), + TypeDefKind::FixedSizeList(t, size) => { + self.anonymous_type_fixed_size_list(id, t, *size, &ty.docs) + } TypeDefKind::Unknown => unreachable!(), } } diff --git a/crates/core/src/types.rs b/crates/core/src/types.rs index 35d6f5f6c..c3e4e107c 100644 --- a/crates/core/src/types.rs +++ b/crates/core/src/types.rs @@ -203,7 +203,9 @@ impl Types { // should use the same ownership semantics as `own` info.has_own_handle = true; } - TypeDefKind::FixedSizeList(..) => todo!(), + TypeDefKind::FixedSizeList(ty, _) => { + info = self.type_info(resolve, ty); + } TypeDefKind::Unknown => unreachable!(), } let prev = self.type_info.insert(ty, info); diff --git a/crates/csharp/src/function.rs b/crates/csharp/src/function.rs index c22389c2a..187a2bf76 100644 --- a/crates/csharp/src/function.rs +++ b/crates/csharp/src/function.rs @@ -1391,6 +1391,8 @@ impl Bindgen for FunctionBindgen<'_, '_> { | Instruction::ErrorContextLower { .. } | Instruction::ErrorContextLift { .. } | Instruction::DropHandle { .. } + | Instruction::FixedSizeListLift { .. } + | Instruction::FixedSizeListLower { .. } => { dbg!(inst); todo!() diff --git a/crates/moonbit/src/lib.rs b/crates/moonbit/src/lib.rs index 36368150c..26a81eeeb 100644 --- a/crates/moonbit/src/lib.rs +++ b/crates/moonbit/src/lib.rs @@ -2696,6 +2696,8 @@ impl Bindgen for FunctionBindgen<'_, '_> { Instruction::ErrorContextLower { .. } | Instruction::ErrorContextLift { .. } | Instruction::DropHandle { .. } => todo!(), + Instruction::FixedSizeListLift { .. } => todo!(), + Instruction::FixedSizeListLower { .. } => todo!(), } } diff --git a/crates/rust/src/bindgen.rs b/crates/rust/src/bindgen.rs index df3623476..cb3958195 100644 --- a/crates/rust/src/bindgen.rs +++ b/crates/rust/src/bindgen.rs @@ -1211,6 +1211,8 @@ impl Bindgen for FunctionBindgen<'_, '_> { Instruction::DropHandle { .. } => { uwriteln!(self.src, "let _ = {};", operands[0]); } + Instruction::FixedSizeListLift { .. } => todo!(), + Instruction::FixedSizeListLower { .. } => todo!(), } } } diff --git a/crates/rust/src/interface.rs b/crates/rust/src/interface.rs index c9a55eb14..8fe13d9f1 100644 --- a/crates/rust/src/interface.rs +++ b/crates/rust/src/interface.rs @@ -3017,4 +3017,14 @@ impl<'a, 'b> wit_bindgen_core::AnonymousTypeGenerator<'a> for AnonTypeGenerator< self.interface.print_optional_ty(ty.as_ref(), mode); self.interface.push_str(">"); } + + fn anonymous_type_fixed_size_list( + &mut self, + _id: TypeId, + _ty: &Type, + _size: u32, + _docs: &Docs, + ) { + todo!() + } } diff --git a/tests/runtime/fixed-size-list/runner.rs b/tests/runtime/fixed-size-list/runner.rs new file mode 100644 index 000000000..c0e587f9c --- /dev/null +++ b/tests/runtime/fixed-size-list/runner.rs @@ -0,0 +1,6 @@ +include!(env!("BINDINGS")); + +use test::lists::to_test::*; + +fn main() { +} diff --git a/tests/runtime/fixed-size-list/test.rs b/tests/runtime/fixed-size-list/test.rs new file mode 100644 index 000000000..58794dfa2 --- /dev/null +++ b/tests/runtime/fixed-size-list/test.rs @@ -0,0 +1,8 @@ +include!(env!("BINDINGS")); + +struct Component; + +export!(Component); + +impl exports::test::lists::to_test::Guest for Component { +} diff --git a/tests/runtime/fixed-size-list/test.wit b/tests/runtime/fixed-size-list/test.wit new file mode 100644 index 000000000..86df7f78d --- /dev/null +++ b/tests/runtime/fixed-size-list/test.wit @@ -0,0 +1,21 @@ +package test:lists; + +interface to-test { + list-param: func(a: list); + list-param2: func(a: list, 2>); + list-result: func() -> list; + + list-minmax16: func(a: list, b: list) -> tuple, list>; + list-minmax-float: func(a: list, b: list) + -> tuple, list>; + + list-roundtrip: func(a: list) -> list; +} + +world test { + export to-test; +} + +world runner { + import to-test; +} From d3167846320634eb990e0d091064c284ea1e2ea1 Mon Sep 17 00:00:00 2001 From: Christof Petig Date: Sat, 19 Apr 2025 14:38:04 +0200 Subject: [PATCH 02/13] more fixed list implementation --- crates/core/src/abi.rs | 46 +++++++++++++++++++++++--- crates/rust/src/bindgen.rs | 26 +++++++++++++-- crates/rust/src/interface.rs | 19 ++++++----- tests/runtime/fixed-size-list/test.wit | 1 + 4 files changed, 78 insertions(+), 14 deletions(-) diff --git a/crates/core/src/abi.rs b/crates/core/src/abi.rs index f1fca1fcc..d9442d7a0 100644 --- a/crates/core/src/abi.rs +++ b/crates/core/src/abi.rs @@ -1567,7 +1567,21 @@ impl<'a, B: Bindgen> Generator<'a, B> { }); } TypeDefKind::Unknown => unreachable!(), - TypeDefKind::FixedSizeList(..) => todo!(), + TypeDefKind::FixedSizeList(ty, size) => { + self.emit(&FixedSizeListLower { + elements: ty, + size: *size, + id, + }); + let mut values = self + .stack + .drain(self.stack.len() - (*size as usize)..) + .collect::>(); + for value in values.drain(..) { + self.stack.push(value); + self.lower(ty); + } + } }, } } @@ -1950,7 +1964,19 @@ impl<'a, B: Bindgen> Generator<'a, B> { } TypeDefKind::Unknown => unreachable!(), - TypeDefKind::FixedSizeList(..) => todo!(), + TypeDefKind::FixedSizeList(ty, size) => { + let increment = self.bindgen.sizes().size(ty); + let mut position = offset; + for _ in 0..*size { + self.write_to_memory(ty, addr.clone(), position); + position = position + increment; + } + self.emit(&FixedSizeListLower { + elements: ty, + size: *size, + id, + }); + } }, } } @@ -2137,7 +2163,19 @@ impl<'a, B: Bindgen> Generator<'a, B> { } TypeDefKind::Unknown => unreachable!(), - TypeDefKind::FixedSizeList(..) => todo!(), + TypeDefKind::FixedSizeList(ty, size) => { + let increment = self.bindgen.sizes().size(ty); + let mut position = offset; + for _ in 0..*size { + self.read_from_memory(ty, addr.clone(), position); + position = position + increment; + } + self.emit(&FixedSizeListLift { + elements: ty, + size: *size, + id, + }); + } }, } } @@ -2446,7 +2484,7 @@ impl<'a, B: Bindgen> Generator<'a, B> { TypeDefKind::Future(_) => unreachable!(), TypeDefKind::Stream(_) => unreachable!(), TypeDefKind::Unknown => unreachable!(), - TypeDefKind::FixedSizeList(..) => todo!(), + TypeDefKind::FixedSizeList(_, _) => {} }, } } diff --git a/crates/rust/src/bindgen.rs b/crates/rust/src/bindgen.rs index cb3958195..82ac0dbdb 100644 --- a/crates/rust/src/bindgen.rs +++ b/crates/rust/src/bindgen.rs @@ -1211,8 +1211,30 @@ impl Bindgen for FunctionBindgen<'_, '_> { Instruction::DropHandle { .. } => { uwriteln!(self.src, "let _ = {};", operands[0]); } - Instruction::FixedSizeListLift { .. } => todo!(), - Instruction::FixedSizeListLower { .. } => todo!(), + Instruction::FixedSizeListLift { + elements: _, + size, + id: _, + } => { + let tmp = self.tmp(); + let result = format!("result{tmp}"); + self.push_str(&format!("let mut {result} = [",)); + for a in operands.drain(0..(*size as usize)) { + self.push_str(&a); + self.push_str(", "); + } + self.push_str("];\n"); + results.push(result); + } + Instruction::FixedSizeListLower { + elements: _, + size, + id: _, + } => { + for i in 0..(*size as usize) { + results.push(format!("{}[{i}]", operands[0])); + } + } } } } diff --git a/crates/rust/src/interface.rs b/crates/rust/src/interface.rs index 8fe13d9f1..95a588f8c 100644 --- a/crates/rust/src/interface.rs +++ b/crates/rust/src/interface.rs @@ -3018,13 +3018,16 @@ impl<'a, 'b> wit_bindgen_core::AnonymousTypeGenerator<'a> for AnonTypeGenerator< self.interface.push_str(">"); } - fn anonymous_type_fixed_size_list( - &mut self, - _id: TypeId, - _ty: &Type, - _size: u32, - _docs: &Docs, - ) { - todo!() + fn anonymous_type_fixed_size_list(&mut self, _id: TypeId, ty: &Type, size: u32, _docs: &Docs) { + self.interface.push_str("["); + self.interface.print_ty( + ty, + TypeMode { + lifetime: None, + lists_borrowed: false, + style: TypeOwnershipStyle::Owned, + }, + ); + self.interface.push_str(&format!(", {size}]")); } } diff --git a/tests/runtime/fixed-size-list/test.wit b/tests/runtime/fixed-size-list/test.wit index 86df7f78d..f6280c809 100644 --- a/tests/runtime/fixed-size-list/test.wit +++ b/tests/runtime/fixed-size-list/test.wit @@ -3,6 +3,7 @@ package test:lists; interface to-test { list-param: func(a: list); list-param2: func(a: list, 2>); + list-param3: func(a: list); list-result: func() -> list; list-minmax16: func(a: list, b: list) -> tuple, list>; From 0858f71047c1718135f4683843f46cb993302d0b Mon Sep 17 00:00:00 2001 From: Christof Petig Date: Sun, 20 Apr 2025 14:32:33 +0200 Subject: [PATCH 03/13] test passes with modified wasmtime --- crates/core/src/abi.rs | 15 +++++++++------ crates/rust/src/bindgen.rs | 2 +- crates/rust/src/interface.rs | 2 +- tests/runtime/fixed-size-list/runner.rs | 4 +++- tests/runtime/fixed-size-list/test.rs | 5 ++++- tests/runtime/fixed-size-list/test.wit | 14 +++++++------- 6 files changed, 25 insertions(+), 17 deletions(-) diff --git a/crates/core/src/abi.rs b/crates/core/src/abi.rs index d9442d7a0..e06dd434f 100644 --- a/crates/core/src/abi.rs +++ b/crates/core/src/abi.rs @@ -1965,12 +1965,15 @@ impl<'a, B: Bindgen> Generator<'a, B> { TypeDefKind::Unknown => unreachable!(), TypeDefKind::FixedSizeList(ty, size) => { - let increment = self.bindgen.sizes().size(ty); - let mut position = offset; - for _ in 0..*size { - self.write_to_memory(ty, addr.clone(), position); - position = position + increment; - } + // let increment = self.bindgen.sizes().size(ty); + // let mut position = offset; + // let resultvar = self.stack[0]; + // for _ in 0..*size { + // // push index + // self.stack.push("", ); + // self.write_to_memory(ty, addr.clone(), position); + // position = position + increment; + // } self.emit(&FixedSizeListLower { elements: ty, size: *size, diff --git a/crates/rust/src/bindgen.rs b/crates/rust/src/bindgen.rs index 82ac0dbdb..aeb42c542 100644 --- a/crates/rust/src/bindgen.rs +++ b/crates/rust/src/bindgen.rs @@ -1218,7 +1218,7 @@ impl Bindgen for FunctionBindgen<'_, '_> { } => { let tmp = self.tmp(); let result = format!("result{tmp}"); - self.push_str(&format!("let mut {result} = [",)); + self.push_str(&format!("let {result} = [",)); for a in operands.drain(0..(*size as usize)) { self.push_str(&a); self.push_str(", "); diff --git a/crates/rust/src/interface.rs b/crates/rust/src/interface.rs index 95a588f8c..d54e72be0 100644 --- a/crates/rust/src/interface.rs +++ b/crates/rust/src/interface.rs @@ -3028,6 +3028,6 @@ impl<'a, 'b> wit_bindgen_core::AnonymousTypeGenerator<'a> for AnonTypeGenerator< style: TypeOwnershipStyle::Owned, }, ); - self.interface.push_str(&format!(", {size}]")); + self.interface.push_str(&format!("; {size}]")); } } diff --git a/tests/runtime/fixed-size-list/runner.rs b/tests/runtime/fixed-size-list/runner.rs index c0e587f9c..97b7d1bbc 100644 --- a/tests/runtime/fixed-size-list/runner.rs +++ b/tests/runtime/fixed-size-list/runner.rs @@ -1,6 +1,8 @@ include!(env!("BINDINGS")); -use test::lists::to_test::*; +use test::fixed_size_lists::to_test::*; fn main() { + list_param([1,2,3,4]); + list_param2([[1,2],[3,4]]); } diff --git a/tests/runtime/fixed-size-list/test.rs b/tests/runtime/fixed-size-list/test.rs index 58794dfa2..27fd86b22 100644 --- a/tests/runtime/fixed-size-list/test.rs +++ b/tests/runtime/fixed-size-list/test.rs @@ -4,5 +4,8 @@ struct Component; export!(Component); -impl exports::test::lists::to_test::Guest for Component { +impl exports::test::fixed_size_lists::to_test::Guest for Component { + fn list_param(_a: [u32; 4]) {} + fn list_param2(_a: [[u32; 2]; 2]) {} + // fn list_param3(_a: [i32; 20]) {} } diff --git a/tests/runtime/fixed-size-list/test.wit b/tests/runtime/fixed-size-list/test.wit index f6280c809..6e71e900d 100644 --- a/tests/runtime/fixed-size-list/test.wit +++ b/tests/runtime/fixed-size-list/test.wit @@ -1,16 +1,16 @@ -package test:lists; +package test:fixed-size-lists; interface to-test { list-param: func(a: list); list-param2: func(a: list, 2>); - list-param3: func(a: list); - list-result: func() -> list; + // list-param3: func(a: list);s + //list-result: func() -> list; - list-minmax16: func(a: list, b: list) -> tuple, list>; - list-minmax-float: func(a: list, b: list) - -> tuple, list>; + // list-minmax16: func(a: list, b: list) -> tuple, list>; + // list-minmax-float: func(a: list, b: list) + // -> tuple, list>; - list-roundtrip: func(a: list) -> list; + // list-roundtrip: func(a: list) -> list; } world test { From 2152db17f3dc7043bdfa43da43d0604ea6ef5bdf Mon Sep 17 00:00:00 2001 From: Christof Petig Date: Sun, 20 Apr 2025 16:15:49 +0200 Subject: [PATCH 04/13] document and compare test --- tests/runtime/fixed-size-list/runner.rs | 4 ++-- tests/runtime/fixed-size-list/test.rs | 8 ++++++-- tests/runtime/fixed-size-list/test.wit | 2 ++ 3 files changed, 10 insertions(+), 4 deletions(-) diff --git a/tests/runtime/fixed-size-list/runner.rs b/tests/runtime/fixed-size-list/runner.rs index 97b7d1bbc..d31e0c327 100644 --- a/tests/runtime/fixed-size-list/runner.rs +++ b/tests/runtime/fixed-size-list/runner.rs @@ -3,6 +3,6 @@ include!(env!("BINDINGS")); use test::fixed_size_lists::to_test::*; fn main() { - list_param([1,2,3,4]); - list_param2([[1,2],[3,4]]); + list_param([1, 2, 3, 4]); + list_param2([[1, 2], [3, 4]]); } diff --git a/tests/runtime/fixed-size-list/test.rs b/tests/runtime/fixed-size-list/test.rs index 27fd86b22..4b66e9850 100644 --- a/tests/runtime/fixed-size-list/test.rs +++ b/tests/runtime/fixed-size-list/test.rs @@ -5,7 +5,11 @@ struct Component; export!(Component); impl exports::test::fixed_size_lists::to_test::Guest for Component { - fn list_param(_a: [u32; 4]) {} - fn list_param2(_a: [[u32; 2]; 2]) {} + fn list_param(a: [u32; 4]) { + assert_eq!(a, [1, 2, 3, 4]); + } + fn list_param2(a: [[u32; 2]; 2]) { + assert_eq!(a, [[1, 2], [3, 4]]); + } // fn list_param3(_a: [i32; 20]) {} } diff --git a/tests/runtime/fixed-size-list/test.wit b/tests/runtime/fixed-size-list/test.wit index 6e71e900d..c344b7f86 100644 --- a/tests/runtime/fixed-size-list/test.wit +++ b/tests/runtime/fixed-size-list/test.wit @@ -1,3 +1,5 @@ +// run with "--runner wasmtime -W component-model-fixed-size-list" + package test:fixed-size-lists; interface to-test { From 7eac7c90d3625aa8a42256972c4801d75cf878f3 Mon Sep 17 00:00:00 2001 From: Christof Petig Date: Sun, 20 Apr 2025 21:13:51 +0200 Subject: [PATCH 05/13] returning a fixed size list works --- crates/core/src/abi.rs | 45 ++++++++++++++++++++----- crates/csharp/src/function.rs | 1 + crates/moonbit/src/lib.rs | 1 + crates/rust/src/bindgen.rs | 29 ++++++++++++++-- tests/runtime/fixed-size-list/runner.rs | 8 +++-- tests/runtime/fixed-size-list/test.rs | 15 +++++---- tests/runtime/fixed-size-list/test.wit | 6 ++-- 7 files changed, 84 insertions(+), 21 deletions(-) diff --git a/crates/core/src/abi.rs b/crates/core/src/abi.rs index e06dd434f..a62d788b7 100644 --- a/crates/core/src/abi.rs +++ b/crates/core/src/abi.rs @@ -312,18 +312,25 @@ def_instruction! { /// Pops all fields for a fixed list off the stack and then composes them /// into an array. FixedSizeListLift { - elements: &'a Type, + element: &'a Type, size: u32, id: TypeId, } : [*size as usize] => [1], /// Pops an array off the stack, decomposes the elements and then pushes them onto the stack. FixedSizeListLower { - elements: &'a Type, + element: &'a Type, size: u32, id: TypeId, } : [1] => [*size as usize], + /// Pops an array and an address off the stack, passes each element to a block + FixedSizeListLowerBlock { + element: &'a Type, + size: u32, + id: TypeId, + } : [2] => [0], + /// Pushes an operand onto the stack representing the list item from /// each iteration of the list. /// @@ -1569,7 +1576,7 @@ impl<'a, B: Bindgen> Generator<'a, B> { TypeDefKind::Unknown => unreachable!(), TypeDefKind::FixedSizeList(ty, size) => { self.emit(&FixedSizeListLower { - elements: ty, + element: ty, size: *size, id, }); @@ -1778,7 +1785,7 @@ impl<'a, B: Bindgen> Generator<'a, B> { self.lift(ty); } self.emit(&FixedSizeListLift { - elements: ty, + element: ty, size: *size, id, }); @@ -1964,7 +1971,7 @@ impl<'a, B: Bindgen> Generator<'a, B> { } TypeDefKind::Unknown => unreachable!(), - TypeDefKind::FixedSizeList(ty, size) => { + TypeDefKind::FixedSizeList(element, size) => { // let increment = self.bindgen.sizes().size(ty); // let mut position = offset; // let resultvar = self.stack[0]; @@ -1974,11 +1981,33 @@ impl<'a, B: Bindgen> Generator<'a, B> { // self.write_to_memory(ty, addr.clone(), position); // position = position + increment; // } - self.emit(&FixedSizeListLower { - elements: ty, + // @@@@ + // self.emit(&FixedSizeListLower { + // elements: ty, + // size: *size, + // id, + // }); + + // resembles write_list_to_memory + self.push_block(); + self.emit(&IterElem { element }); + self.emit(&IterBasePointer); + let elem_addr = self.stack.pop().unwrap(); + self.write_to_memory(element, elem_addr, Default::default()); + self.finish_block(0); + // let target = self.stack.pop().unwrap(); + self.stack.push(addr); + self.emit(&FixedSizeListLowerBlock { + element, size: *size, id, }); + + // for idx in 0..*size { + // //self.write_fields_to_memory(tuple.types.iter(), addr, offset); + // self.emit(&FixedSizeListLowerElement { elements: ty, idx, }); + // self.write_to_memory(ty, addr.clone(), offset + (field_offset)); + // } } }, } @@ -2174,7 +2203,7 @@ impl<'a, B: Bindgen> Generator<'a, B> { position = position + increment; } self.emit(&FixedSizeListLift { - elements: ty, + element: ty, size: *size, id, }); diff --git a/crates/csharp/src/function.rs b/crates/csharp/src/function.rs index 187a2bf76..d3d944d8c 100644 --- a/crates/csharp/src/function.rs +++ b/crates/csharp/src/function.rs @@ -1393,6 +1393,7 @@ impl Bindgen for FunctionBindgen<'_, '_> { | Instruction::DropHandle { .. } | Instruction::FixedSizeListLift { .. } | Instruction::FixedSizeListLower { .. } + | Instruction::FixedSizeListLowerBlock { .. } => { dbg!(inst); todo!() diff --git a/crates/moonbit/src/lib.rs b/crates/moonbit/src/lib.rs index 26a81eeeb..5b7986ba6 100644 --- a/crates/moonbit/src/lib.rs +++ b/crates/moonbit/src/lib.rs @@ -2698,6 +2698,7 @@ impl Bindgen for FunctionBindgen<'_, '_> { | Instruction::DropHandle { .. } => todo!(), Instruction::FixedSizeListLift { .. } => todo!(), Instruction::FixedSizeListLower { .. } => todo!(), + Instruction::FixedSizeListLowerBlock { .. } => todo!(), } } diff --git a/crates/rust/src/bindgen.rs b/crates/rust/src/bindgen.rs index aeb42c542..3239fcbcb 100644 --- a/crates/rust/src/bindgen.rs +++ b/crates/rust/src/bindgen.rs @@ -784,6 +784,31 @@ impl Bindgen for FunctionBindgen<'_, '_> { results.push(len); } + Instruction::FixedSizeListLowerBlock { + element, + size: _, + id: _, + } => { + let body = self.blocks.pop().unwrap(); + // let tmp = self.tmp(); + let vec = operands[0].clone(); + //format!("vec{tmp}"); + // self.push_str(&format!( + // "let {vec} = {operand0};\n", + // operand0 = operands[0] + // )); + let size = self.r#gen.sizes.size(element); + let target = operands[1].clone(); + // let align = self.r#gen.sizes.align(element); + self.push_str(&format!("for (i, e) in {vec}.into_iter().enumerate() {{\n",)); + self.push_str(&format!( + "let base = {target}.add(i * {});\n", + size.format(POINTER_SIZE_EXPRESSION) + )); + self.push_str(&body); + self.push_str("\n}\n"); + } + Instruction::ListLift { element, .. } => { let body = self.blocks.pop().unwrap(); let tmp = self.tmp(); @@ -1212,7 +1237,7 @@ impl Bindgen for FunctionBindgen<'_, '_> { uwriteln!(self.src, "let _ = {};", operands[0]); } Instruction::FixedSizeListLift { - elements: _, + element: _, size, id: _, } => { @@ -1227,7 +1252,7 @@ impl Bindgen for FunctionBindgen<'_, '_> { results.push(result); } Instruction::FixedSizeListLower { - elements: _, + element: _, size, id: _, } => { diff --git a/tests/runtime/fixed-size-list/runner.rs b/tests/runtime/fixed-size-list/runner.rs index d31e0c327..7850a13db 100644 --- a/tests/runtime/fixed-size-list/runner.rs +++ b/tests/runtime/fixed-size-list/runner.rs @@ -3,6 +3,10 @@ include!(env!("BINDINGS")); use test::fixed_size_lists::to_test::*; fn main() { - list_param([1, 2, 3, 4]); - list_param2([[1, 2], [3, 4]]); + // list_param([1, 2, 3, 4]); + // list_param2([[1, 2], [3, 4]]); + { + let result = list_result(); + assert_eq!(result, [b'0', b'1', b'A', b'B', b'a', b'b', 128, 255]); + } } diff --git a/tests/runtime/fixed-size-list/test.rs b/tests/runtime/fixed-size-list/test.rs index 4b66e9850..c5ddb7bbe 100644 --- a/tests/runtime/fixed-size-list/test.rs +++ b/tests/runtime/fixed-size-list/test.rs @@ -5,11 +5,14 @@ struct Component; export!(Component); impl exports::test::fixed_size_lists::to_test::Guest for Component { - fn list_param(a: [u32; 4]) { - assert_eq!(a, [1, 2, 3, 4]); - } - fn list_param2(a: [[u32; 2]; 2]) { - assert_eq!(a, [[1, 2], [3, 4]]); - } + // fn list_param(a: [u32; 4]) { + // assert_eq!(a, [1, 2, 3, 4]); + // } + // fn list_param2(a: [[u32; 2]; 2]) { + // assert_eq!(a, [[1, 2], [3, 4]]); + // } // fn list_param3(_a: [i32; 20]) {} + fn list_result() -> [u8; 8] { + [b'0', b'1', b'A', b'B', b'a', b'b', 128, 255] + } } diff --git a/tests/runtime/fixed-size-list/test.wit b/tests/runtime/fixed-size-list/test.wit index c344b7f86..f4663ab79 100644 --- a/tests/runtime/fixed-size-list/test.wit +++ b/tests/runtime/fixed-size-list/test.wit @@ -3,10 +3,10 @@ package test:fixed-size-lists; interface to-test { - list-param: func(a: list); - list-param2: func(a: list, 2>); + // list-param: func(a: list); + // list-param2: func(a: list, 2>); // list-param3: func(a: list);s - //list-result: func() -> list; + list-result: func() -> list; // list-minmax16: func(a: list, b: list) -> tuple, list>; // list-minmax-float: func(a: list, b: list) From 343c6d9291281776931c7998e0d7c8c830d81dcb Mon Sep 17 00:00:00 2001 From: Christof Petig Date: Sun, 20 Apr 2025 21:15:27 +0200 Subject: [PATCH 06/13] re-enable normal parameters --- tests/runtime/fixed-size-list/runner.rs | 4 ++-- tests/runtime/fixed-size-list/test.rs | 12 ++++++------ tests/runtime/fixed-size-list/test.wit | 4 ++-- 3 files changed, 10 insertions(+), 10 deletions(-) diff --git a/tests/runtime/fixed-size-list/runner.rs b/tests/runtime/fixed-size-list/runner.rs index 7850a13db..5a41b6f5b 100644 --- a/tests/runtime/fixed-size-list/runner.rs +++ b/tests/runtime/fixed-size-list/runner.rs @@ -3,8 +3,8 @@ include!(env!("BINDINGS")); use test::fixed_size_lists::to_test::*; fn main() { - // list_param([1, 2, 3, 4]); - // list_param2([[1, 2], [3, 4]]); + list_param([1, 2, 3, 4]); + list_param2([[1, 2], [3, 4]]); { let result = list_result(); assert_eq!(result, [b'0', b'1', b'A', b'B', b'a', b'b', 128, 255]); diff --git a/tests/runtime/fixed-size-list/test.rs b/tests/runtime/fixed-size-list/test.rs index c5ddb7bbe..b49870610 100644 --- a/tests/runtime/fixed-size-list/test.rs +++ b/tests/runtime/fixed-size-list/test.rs @@ -5,12 +5,12 @@ struct Component; export!(Component); impl exports::test::fixed_size_lists::to_test::Guest for Component { - // fn list_param(a: [u32; 4]) { - // assert_eq!(a, [1, 2, 3, 4]); - // } - // fn list_param2(a: [[u32; 2]; 2]) { - // assert_eq!(a, [[1, 2], [3, 4]]); - // } + fn list_param(a: [u32; 4]) { + assert_eq!(a, [1, 2, 3, 4]); + } + fn list_param2(a: [[u32; 2]; 2]) { + assert_eq!(a, [[1, 2], [3, 4]]); + } // fn list_param3(_a: [i32; 20]) {} fn list_result() -> [u8; 8] { [b'0', b'1', b'A', b'B', b'a', b'b', 128, 255] diff --git a/tests/runtime/fixed-size-list/test.wit b/tests/runtime/fixed-size-list/test.wit index f4663ab79..0c358ee4e 100644 --- a/tests/runtime/fixed-size-list/test.wit +++ b/tests/runtime/fixed-size-list/test.wit @@ -3,8 +3,8 @@ package test:fixed-size-lists; interface to-test { - // list-param: func(a: list); - // list-param2: func(a: list, 2>); + list-param: func(a: list); + list-param2: func(a: list, 2>); // list-param3: func(a: list);s list-result: func() -> list; From aa908760ddb11365fa8c2845221caf8d7e1db13d Mon Sep 17 00:00:00 2001 From: Christof Petig Date: Sun, 20 Apr 2025 21:26:46 +0200 Subject: [PATCH 07/13] clean up and use wac fork --- Cargo.lock | 388 ++++++++++++++++++++++++++++++++++--- crates/core/src/abi.rs | 25 +-- crates/rust/src/bindgen.rs | 9 +- crates/test/Cargo.toml | 6 +- 4 files changed, 364 insertions(+), 64 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index acf2468ef..f8617a683 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2,6 +2,12 @@ # It is not intended for manual editing. version = 4 +[[package]] +name = "adler2" +version = "2.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "320119579fcad9c21884f5c4861d16174d0e06250625266f50fe6898340abefa" + [[package]] name = "aho-corasick" version = "1.1.4" @@ -67,6 +73,18 @@ version = "1.0.100" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a23eb6b1614318a8071c9b2521f36b424b2c83db5eb3a0fead4a6c0809af6e61" +[[package]] +name = "auditable-serde" +version = "0.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5c7bf8143dfc3c0258df908843e169b5cc5fcf76c7718bd66135ef4a9cd558c5" +dependencies = [ + "semver", + "serde", + "serde_json", + "topological-sort", +] + [[package]] name = "beef" version = "0.5.2" @@ -161,6 +179,15 @@ version = "1.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b05b61dc5112cbb17e4b6cd61790d9845d13888356391624cbe7e41efeac1e75" +[[package]] +name = "crc32fast" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9481c1c90cbf2ac953f07c8d4a58aa3945c425b7185c9154d67a65e4230da511" +dependencies = [ + "cfg-if", +] + [[package]] name = "crossbeam-deque" version = "0.8.6" @@ -186,6 +213,17 @@ version = "0.8.21" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d0a5c400df2834b80a4c3327b3aad3a4c4cd4de0629063962b03235697506a28" +[[package]] +name = "displaydoc" +version = "0.2.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "97369cbbc041bc366949bc74d34658d6cda5621039731c6310521892a3a20ae0" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] + [[package]] name = "either" version = "1.15.0" @@ -237,6 +275,16 @@ version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0ce7134b9999ecaf8bcd65542e436736ef32ddca1b3e06094cb6ec5755203b80" +[[package]] +name = "flate2" +version = "1.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bfe33edd8e85a12a67454e37f8c75e730830d83e313556ab9ebf9ee7fbeb3bfb" +dependencies = [ + "crc32fast", + "miniz_oxide", +] + [[package]] name = "fnv" version = "1.0.7" @@ -249,6 +297,15 @@ version = "0.1.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d9c4f5dac5e15c24eb999c26181a6ca40b39fe946cbe4c263c7209467bc83af2" +[[package]] +name = "form_urlencoded" +version = "1.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cb4cb245038516f5f85277875cdaa4f7d2c9a0fa0468de06ed190163b1581fcf" +dependencies = [ + "percent-encoding", +] + [[package]] name = "futures" version = "0.3.31" @@ -360,12 +417,114 @@ version = "0.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2304e00983f87ffb38b55b444b5e3b60a884b5d30c0fca7d82fe33449bbe55ea" +[[package]] +name = "icu_collections" +version = "2.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4c6b649701667bbe825c3b7e6388cb521c23d88644678e83c0c4d0a621a34b43" +dependencies = [ + "displaydoc", + "potential_utf", + "yoke", + "zerofrom", + "zerovec", +] + +[[package]] +name = "icu_locale_core" +version = "2.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "edba7861004dd3714265b4db54a3c390e880ab658fec5f7db895fae2046b5bb6" +dependencies = [ + "displaydoc", + "litemap", + "tinystr", + "writeable", + "zerovec", +] + +[[package]] +name = "icu_normalizer" +version = "2.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5f6c8828b67bf8908d82127b2054ea1b4427ff0230ee9141c54251934ab1b599" +dependencies = [ + "icu_collections", + "icu_normalizer_data", + "icu_properties", + "icu_provider", + "smallvec", + "zerovec", +] + +[[package]] +name = "icu_normalizer_data" +version = "2.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7aedcccd01fc5fe81e6b489c15b247b8b0690feb23304303a9e560f37efc560a" + +[[package]] +name = "icu_properties" +version = "2.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "020bfc02fe870ec3a66d93e677ccca0562506e5872c650f893269e08615d74ec" +dependencies = [ + "icu_collections", + "icu_locale_core", + "icu_properties_data", + "icu_provider", + "zerotrie", + "zerovec", +] + +[[package]] +name = "icu_properties_data" +version = "2.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "616c294cf8d725c6afcd8f55abc17c56464ef6211f9ed59cccffe534129c77af" + +[[package]] +name = "icu_provider" +version = "2.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "85962cf0ce02e1e0a629cc34e7ca3e373ce20dda4c4d7294bbd0bf1fdb59e614" +dependencies = [ + "displaydoc", + "icu_locale_core", + "writeable", + "yoke", + "zerofrom", + "zerotrie", + "zerovec", +] + [[package]] name = "id-arena" version = "2.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "25a2bc672d1148e28034f176e01fffebb08b35768468cc954630da77a1449005" +[[package]] +name = "idna" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3b0875f23caa03898994f6ddc501886a45c7d3d62d04d2d90788d47be1b1e4de" +dependencies = [ + "idna_adapter", + "smallvec", + "utf8_iter", +] + +[[package]] +name = "idna_adapter" +version = "1.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3acae9609540aa318d1bc588455225fb2085b9ed0c4f6bd0d9d5bcd86f1a0344" +dependencies = [ + "icu_normalizer", + "icu_properties", +] + [[package]] name = "im-rc" version = "15.1.0" @@ -434,12 +593,6 @@ version = "1.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bbd2bcb4c963f2ddae06a2efc7e9f3591312473c50c6685e1f298068316e66fe" -[[package]] -name = "leb128" -version = "0.2.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "884e2677b40cc8c339eaefcb701c32ef1fd2493d71118dc0ca4b6a736c93bd67" - [[package]] name = "leb128fmt" version = "0.1.0" @@ -458,6 +611,12 @@ version = "0.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "df1d3c3b53da64cf5760482273a98e575c651a67eec7f77df96b5b642de8f039" +[[package]] +name = "litemap" +version = "0.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6373607a59f0be73a39b6fe456b8192fcc3585f602af20751600e974dd455e77" + [[package]] name = "log" version = "0.4.28" @@ -526,12 +685,28 @@ dependencies = [ "syn", ] +[[package]] +name = "miniz_oxide" +version = "0.8.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1fa76a2c86f704bdb222d66965fb3d63269ce38518b83cb0575fca855ebb6316" +dependencies = [ + "adler2", + "simd-adler32", +] + [[package]] name = "once_cell_polyfill" version = "1.70.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "384b8ab6d37215f3c5301a95a4accb5d64aa607f1fcb26a11b5303878451b4fe" +[[package]] +name = "percent-encoding" +version = "2.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9b4f627cb1b25917193a259e49bdad08f671f8d9708acfd5fe0a8c1455d87220" + [[package]] name = "petgraph" version = "0.6.5" @@ -569,6 +744,15 @@ dependencies = [ "portable-atomic", ] +[[package]] +name = "potential_utf" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b73949432f5e2a09657003c25bca5e19a0e9c84f8058ca374f49e0ebe605af77" +dependencies = [ + "zerovec", +] + [[package]] name = "prettyplease" version = "0.2.37" @@ -778,6 +962,12 @@ dependencies = [ "unsafe-libyaml", ] +[[package]] +name = "simd-adler32" +version = "0.3.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e320a6c5ad31d271ad523dcf3ad13e2767ad8b1cb8f047f75a8aeaf8da139da2" + [[package]] name = "sized-chunks" version = "0.6.5" @@ -809,6 +999,12 @@ dependencies = [ "smallvec", ] +[[package]] +name = "stable_deref_trait" +version = "1.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6ce2be8dc25455e1f91df71bfa12ad37d7af1092ae736f3a6cd0e37bc7810596" + [[package]] name = "strsim" version = "0.11.1" @@ -826,6 +1022,17 @@ dependencies = [ "unicode-ident", ] +[[package]] +name = "synstructure" +version = "0.13.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "728a70f3dbaf5bab7f0c4b1ac8d7ae5ea60a4b5549c8a5914361c99147a709d2" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] + [[package]] name = "terminal_size" version = "0.4.3" @@ -867,6 +1074,16 @@ dependencies = [ "syn", ] +[[package]] +name = "tinystr" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "42d3e9c45c09de15d06dd8acf5f4e0e399e85927b7f00711024eb7ae10fa4869" +dependencies = [ + "displaydoc", + "zerovec", +] + [[package]] name = "toml" version = "0.8.23" @@ -908,6 +1125,12 @@ version = "0.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5d99f8c9a7727884afe522e9bd5edbfc91a3312b36a77b5fb8926e4c31a41801" +[[package]] +name = "topological-sort" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ea68304e134ecd095ac6c3574494fc62b909f416c4fca77e440530221e549d3d" + [[package]] name = "typenum" version = "1.19.0" @@ -950,6 +1173,24 @@ version = "0.2.11" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "673aac59facbab8a9007c7f6108d11f63b603f7cabff99fabf650fea5c32b861" +[[package]] +name = "url" +version = "2.5.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "08bc136a29a3d1758e07a9cca267be308aeebf5cfd5a10f3f67ab2097683ef5b" +dependencies = [ + "form_urlencoded", + "idna", + "percent-encoding", + "serde", +] + +[[package]] +name = "utf8_iter" +version = "1.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b6c140620e7ffbb22c2dee59cafe6084a59b5ffc27a8859a5f0d494b5d52b6be" + [[package]] name = "utf8parse" version = "0.2.2" @@ -964,9 +1205,9 @@ checksum = "0b928f33d975fc6ad9f86c8f283853ad26bdd5b10b7f1542aa2fa15e2289105a" [[package]] name = "wac-graph" -version = "0.6.1" +version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d94268a683b67ae20210565b5f91e106fe05034c36b931e739fe90377ed80b98" +checksum = "d511e0c9462a5f6369e7e17e9f0f3b566eab2a235076a23f2db19ca7bf36d32c" dependencies = [ "anyhow", "id-arena", @@ -976,16 +1217,16 @@ dependencies = [ "semver", "thiserror", "wac-types", - "wasm-encoder 0.202.0", - "wasm-metadata 0.202.0", - "wasmparser 0.202.0", + "wasm-encoder 0.239.0", + "wasm-metadata 0.239.0", + "wasmparser 0.239.0", ] [[package]] name = "wac-parser" -version = "0.6.1" +version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "616ec0c4f63641fa095b4a551263fe35a15c72c9680b650b8f08f70db0fdbd19" +checksum = "b47c29a894f9f82c4da2d036d410babb3bd5aed0acfb4c3d779b536a4316cba0" dependencies = [ "anyhow", "id-arena", @@ -997,23 +1238,23 @@ dependencies = [ "serde", "thiserror", "wac-graph", - "wasm-encoder 0.202.0", - "wasm-metadata 0.202.0", - "wasmparser 0.202.0", + "wasm-encoder 0.239.0", + "wasm-metadata 0.239.0", + "wasmparser 0.239.0", ] [[package]] name = "wac-types" -version = "0.6.1" +version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f5028a15e266f4c8fed48beb95aebb76af5232dcd554fd849a305a4e5cce1563" +checksum = "64fdef742a5198856c7c754944b329ed684f703dca477d0a77b474b37d990121" dependencies = [ "anyhow", "id-arena", "indexmap", "semver", - "wasm-encoder 0.202.0", - "wasmparser 0.202.0", + "wasm-encoder 0.239.0", + "wasmparser 0.239.0", ] [[package]] @@ -1045,11 +1286,12 @@ dependencies = [ [[package]] name = "wasm-encoder" -version = "0.202.0" +version = "0.239.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bfd106365a7f5f7aa3c1916a98cbb3ad477f5ff96ddb130285a91c6e7429e67a" +checksum = "5be00faa2b4950c76fe618c409d2c3ea5a3c9422013e079482d78544bb2d184c" dependencies = [ - "leb128", + "leb128fmt", + "wasmparser 0.239.0", ] [[package]] @@ -1064,18 +1306,21 @@ dependencies = [ [[package]] name = "wasm-metadata" -version = "0.202.0" +version = "0.239.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "094aea3cb90e09f16ee25a4c0e324b3e8c934e7fd838bfa039aef5352f44a917" +checksum = "20b3ec880a9ac69ccd92fbdbcf46ee833071cf09f82bb005b2327c7ae6025ae2" dependencies = [ "anyhow", + "auditable-serde", + "flate2", "indexmap", "serde", "serde_derive", "serde_json", "spdx", - "wasm-encoder 0.202.0", - "wasmparser 0.202.0", + "url", + "wasm-encoder 0.239.0", + "wasmparser 0.239.0", ] [[package]] @@ -1092,13 +1337,15 @@ dependencies = [ [[package]] name = "wasmparser" -version = "0.202.0" +version = "0.239.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d6998515d3cf3f8b980ef7c11b29a9b1017d4cf86b99ae93b546992df9931413" +checksum = "8c9d90bb93e764f6beabf1d02028c70a2156a6583e63ac4218dd07ef733368b0" dependencies = [ "bitflags", + "hashbrown 0.15.5", "indexmap", "semver", + "serde", ] [[package]] @@ -1450,3 +1697,86 @@ dependencies = [ "unicode-xid", "wasmparser 0.243.0", ] + +[[package]] +name = "writeable" +version = "0.6.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9edde0db4769d2dc68579893f2306b26c6ecfbe0ef499b013d731b7b9247e0b9" + +[[package]] +name = "yoke" +version = "0.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "72d6e5c6afb84d73944e5cedb052c4680d5657337201555f9f2a16b7406d4954" +dependencies = [ + "stable_deref_trait", + "yoke-derive", + "zerofrom", +] + +[[package]] +name = "yoke-derive" +version = "0.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b659052874eb698efe5b9e8cf382204678a0086ebf46982b79d6ca3182927e5d" +dependencies = [ + "proc-macro2", + "quote", + "syn", + "synstructure", +] + +[[package]] +name = "zerofrom" +version = "0.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "50cc42e0333e05660c3587f3bf9d0478688e15d870fab3346451ce7f8c9fbea5" +dependencies = [ + "zerofrom-derive", +] + +[[package]] +name = "zerofrom-derive" +version = "0.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d71e5d6e06ab090c67b5e44993ec16b72dcbaabc526db883a360057678b48502" +dependencies = [ + "proc-macro2", + "quote", + "syn", + "synstructure", +] + +[[package]] +name = "zerotrie" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2a59c17a5562d507e4b54960e8569ebee33bee890c70aa3fe7b97e85a9fd7851" +dependencies = [ + "displaydoc", + "yoke", + "zerofrom", +] + +[[package]] +name = "zerovec" +version = "0.11.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6c28719294829477f525be0186d13efa9a3c602f7ec202ca9e353d310fb9a002" +dependencies = [ + "yoke", + "zerofrom", + "zerovec-derive", +] + +[[package]] +name = "zerovec-derive" +version = "0.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "eadce39539ca5cb3985590102671f2567e659fca9666581ad3411d59207951f3" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] diff --git a/crates/core/src/abi.rs b/crates/core/src/abi.rs index a62d788b7..c56cb854c 100644 --- a/crates/core/src/abi.rs +++ b/crates/core/src/abi.rs @@ -324,7 +324,7 @@ def_instruction! { id: TypeId, } : [1] => [*size as usize], - /// Pops an array and an address off the stack, passes each element to a block + /// Pops an array and an address off the stack, passes each element to a block storing it FixedSizeListLowerBlock { element: &'a Type, size: u32, @@ -1972,22 +1972,6 @@ impl<'a, B: Bindgen> Generator<'a, B> { TypeDefKind::Unknown => unreachable!(), TypeDefKind::FixedSizeList(element, size) => { - // let increment = self.bindgen.sizes().size(ty); - // let mut position = offset; - // let resultvar = self.stack[0]; - // for _ in 0..*size { - // // push index - // self.stack.push("", ); - // self.write_to_memory(ty, addr.clone(), position); - // position = position + increment; - // } - // @@@@ - // self.emit(&FixedSizeListLower { - // elements: ty, - // size: *size, - // id, - // }); - // resembles write_list_to_memory self.push_block(); self.emit(&IterElem { element }); @@ -1995,19 +1979,12 @@ impl<'a, B: Bindgen> Generator<'a, B> { let elem_addr = self.stack.pop().unwrap(); self.write_to_memory(element, elem_addr, Default::default()); self.finish_block(0); - // let target = self.stack.pop().unwrap(); self.stack.push(addr); self.emit(&FixedSizeListLowerBlock { element, size: *size, id, }); - - // for idx in 0..*size { - // //self.write_fields_to_memory(tuple.types.iter(), addr, offset); - // self.emit(&FixedSizeListLowerElement { elements: ty, idx, }); - // self.write_to_memory(ty, addr.clone(), offset + (field_offset)); - // } } }, } diff --git a/crates/rust/src/bindgen.rs b/crates/rust/src/bindgen.rs index 3239fcbcb..6899b6705 100644 --- a/crates/rust/src/bindgen.rs +++ b/crates/rust/src/bindgen.rs @@ -790,16 +790,9 @@ impl Bindgen for FunctionBindgen<'_, '_> { id: _, } => { let body = self.blocks.pop().unwrap(); - // let tmp = self.tmp(); let vec = operands[0].clone(); - //format!("vec{tmp}"); - // self.push_str(&format!( - // "let {vec} = {operand0};\n", - // operand0 = operands[0] - // )); - let size = self.r#gen.sizes.size(element); let target = operands[1].clone(); - // let align = self.r#gen.sizes.align(element); + let size = self.r#gen.sizes.size(element); self.push_str(&format!("for (i, e) in {vec}.into_iter().enumerate() {{\n",)); self.push_str(&format!( "let base = {target}.add(i * {});\n", diff --git a/crates/test/Cargo.toml b/crates/test/Cargo.toml index fb8f45aca..f17d7b46f 100644 --- a/crates/test/Cargo.toml +++ b/crates/test/Cargo.toml @@ -25,9 +25,9 @@ regex = "1.11.1" serde = { workspace = true } toml = "0.8.20" wasi-preview1-component-adapter-provider = "37.0.2" -wac-parser = "0.6.1" -wac-types = "0.6.1" -wac-graph = "0.6.1" +wac-parser = "0.8.1" +wac-types = "0.8.1" +wac-graph = "0.8.1" wasm-compose = { workspace = true } indexmap = { workspace = true } wasm-encoder = { workspace = true } From 506ca03b9cd30f5a4df5919653eeb441eb8c7bb3 Mon Sep 17 00:00:00 2001 From: Christof Petig Date: Sun, 20 Apr 2025 21:52:47 +0200 Subject: [PATCH 08/13] another testcase passing --- tests/runtime/fixed-size-list/runner.rs | 3 +++ tests/runtime/fixed-size-list/test.rs | 7 ++++++- tests/runtime/fixed-size-list/test.wit | 2 +- 3 files changed, 10 insertions(+), 2 deletions(-) diff --git a/tests/runtime/fixed-size-list/runner.rs b/tests/runtime/fixed-size-list/runner.rs index 5a41b6f5b..37457ef86 100644 --- a/tests/runtime/fixed-size-list/runner.rs +++ b/tests/runtime/fixed-size-list/runner.rs @@ -5,6 +5,9 @@ use test::fixed_size_lists::to_test::*; fn main() { list_param([1, 2, 3, 4]); list_param2([[1, 2], [3, 4]]); + list_param3([ + -1, 2, -3, 4, -5, 6, -7, 8, -9, 10, -11, 12, -13, 14, -15, 16, -17, 18, -19, 20, + ]); { let result = list_result(); assert_eq!(result, [b'0', b'1', b'A', b'B', b'a', b'b', 128, 255]); diff --git a/tests/runtime/fixed-size-list/test.rs b/tests/runtime/fixed-size-list/test.rs index b49870610..35d94631d 100644 --- a/tests/runtime/fixed-size-list/test.rs +++ b/tests/runtime/fixed-size-list/test.rs @@ -11,7 +11,12 @@ impl exports::test::fixed_size_lists::to_test::Guest for Component { fn list_param2(a: [[u32; 2]; 2]) { assert_eq!(a, [[1, 2], [3, 4]]); } - // fn list_param3(_a: [i32; 20]) {} + fn list_param3(a: [i32; 20]) { + assert_eq!( + a, + [-1, 2, -3, 4, -5, 6, -7, 8, -9, 10, -11, 12, -13, 14, -15, 16, -17, 18, -19, 20] + ); + } fn list_result() -> [u8; 8] { [b'0', b'1', b'A', b'B', b'a', b'b', 128, 255] } diff --git a/tests/runtime/fixed-size-list/test.wit b/tests/runtime/fixed-size-list/test.wit index 0c358ee4e..3d8867922 100644 --- a/tests/runtime/fixed-size-list/test.wit +++ b/tests/runtime/fixed-size-list/test.wit @@ -5,7 +5,7 @@ package test:fixed-size-lists; interface to-test { list-param: func(a: list); list-param2: func(a: list, 2>); - // list-param3: func(a: list);s + list-param3: func(a: list); list-result: func() -> list; // list-minmax16: func(a: list, b: list) -> tuple, list>; From 1340c9890a0e53f8f4ac0953ef4ae83062ce068d Mon Sep 17 00:00:00 2001 From: Christof Petig Date: Sun, 20 Apr 2025 22:06:15 +0200 Subject: [PATCH 09/13] oh, two failing tests --- tests/runtime/fixed-size-list/runner.rs | 15 +++++++++++++++ tests/runtime/fixed-size-list/test.rs | 9 +++++++++ tests/runtime/fixed-size-list/test.wit | 8 ++++---- 3 files changed, 28 insertions(+), 4 deletions(-) diff --git a/tests/runtime/fixed-size-list/runner.rs b/tests/runtime/fixed-size-list/runner.rs index 37457ef86..b1d356821 100644 --- a/tests/runtime/fixed-size-list/runner.rs +++ b/tests/runtime/fixed-size-list/runner.rs @@ -12,4 +12,19 @@ fn main() { let result = list_result(); assert_eq!(result, [b'0', b'1', b'A', b'B', b'a', b'b', 128, 255]); } + { + let _result = list_minmax16([0, 1024, 32768, 65535], [1, 2048, -32767, -2]); + // assert_eq!(result, ([0, 1024, 32768, 65535], [1, 2048, -32767, -2])); + } + { + let _result = list_minmax_float([2.0, -42.0], [0.25, -0.125]); + // assert_eq!(result, ([2.0, -42.0], [0.25, -0.125])); + } + { + let result = list_roundtrip([b'a', b'b', b'c', b'd', 0, 1, 2, 3, b'A', b'B', b'Y', b'Z']); + assert_eq!( + result, + [b'a', b'b', b'c', b'd', 0, 1, 2, 3, b'A', b'B', b'Y', b'Z'] + ); + } } diff --git a/tests/runtime/fixed-size-list/test.rs b/tests/runtime/fixed-size-list/test.rs index 35d94631d..930f70572 100644 --- a/tests/runtime/fixed-size-list/test.rs +++ b/tests/runtime/fixed-size-list/test.rs @@ -17,6 +17,15 @@ impl exports::test::fixed_size_lists::to_test::Guest for Component { [-1, 2, -3, 4, -5, 6, -7, 8, -9, 10, -11, 12, -13, 14, -15, 16, -17, 18, -19, 20] ); } + fn list_minmax16(a: [u16; 4], b: [i16; 4]) -> ([u16; 4], [i16; 4]) { + (a, b) + } + fn list_minmax_float(a: [f32; 2], b: [f64; 2]) -> ([f32; 2], [f64; 2]) { + (a, b) + } + fn list_roundtrip(a: [u8; 12]) -> [u8; 12] { + a + } fn list_result() -> [u8; 8] { [b'0', b'1', b'A', b'B', b'a', b'b', 128, 255] } diff --git a/tests/runtime/fixed-size-list/test.wit b/tests/runtime/fixed-size-list/test.wit index 3d8867922..8da40dc3e 100644 --- a/tests/runtime/fixed-size-list/test.wit +++ b/tests/runtime/fixed-size-list/test.wit @@ -8,11 +8,11 @@ interface to-test { list-param3: func(a: list); list-result: func() -> list; - // list-minmax16: func(a: list, b: list) -> tuple, list>; - // list-minmax-float: func(a: list, b: list) - // -> tuple, list>; + list-minmax16: func(a: list, b: list) -> tuple, list>; + list-minmax-float: func(a: list, b: list) + -> tuple, list>; - // list-roundtrip: func(a: list) -> list; + list-roundtrip: func(a: list) -> list; } world test { From a7c386c482830658ec29d4ea551df052087cccb0 Mon Sep 17 00:00:00 2001 From: Christof Petig Date: Sun, 20 Jul 2025 16:24:52 +0200 Subject: [PATCH 10/13] integrate changes from symmetric branch --- Cargo.lock | 35 +++++++++---- crates/core/src/abi.rs | 21 ++++---- crates/cpp/src/lib.rs | 66 +++++++++++++++++++++++-- crates/moonbit/src/lib.rs | 2 +- crates/rust/src/bindgen.rs | 2 +- tests/runtime/fixed-size-list/runner.rs | 43 ++++++++++++++-- tests/runtime/fixed-size-list/test.cpp | 51 +++++++++++++++++++ tests/runtime/fixed-size-list/test.rs | 11 +++++ tests/runtime/fixed-size-list/test.wit | 9 ++++ 9 files changed, 210 insertions(+), 30 deletions(-) create mode 100644 tests/runtime/fixed-size-list/test.cpp diff --git a/Cargo.lock b/Cargo.lock index f8617a683..10d8fa4ba 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -106,6 +106,15 @@ dependencies = [ "typenum", ] +[[package]] +name = "bitmaps" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "031043d04099746d8db04daf1fa424b2bc8bd69d92b25962dcde24da39ab64a2" +dependencies = [ + "typenum", +] + [[package]] name = "bumpalo" version = "3.19.0" @@ -153,7 +162,7 @@ version = "4.5.49" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2a0b5487afeab2deb2ff4e03a807ad1a03ac532ff5a2cee5d86884440c7f7671" dependencies = [ - "heck", + "heck 0.5.0", "proc-macro2", "quote", "syn", @@ -169,7 +178,7 @@ checksum = "a1d728cc89cf3aee9ff92b05e62b19ee65a02b5702cff7d5a377e32c6ae29d8d" name = "codegen-macro" version = "0.0.0" dependencies = [ - "heck", + "heck 0.5.0", "quote", ] @@ -411,6 +420,12 @@ version = "0.16.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "841d1cc9bed7f9236f321df977030373f4a4163ae1a7dbfe1a51a2c1a51d9100" +[[package]] +name = "heck" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "95505c38b4572b2d910cecb0281560f54b440a19336cbbcb27bf6ce6adc6f5a8" + [[package]] name = "heck" version = "0.5.0" @@ -1498,7 +1513,7 @@ version = "0.49.0" dependencies = [ "anyhow", "clap", - "heck", + "heck 0.5.0", "indexmap", "wasm-encoder 0.243.0", "wasm-metadata 0.243.0", @@ -1532,7 +1547,7 @@ version = "0.49.0" dependencies = [ "anyhow", "clap", - "heck", + "heck 0.5.0", "serde", "wit-parser", ] @@ -1543,7 +1558,7 @@ version = "0.49.0" dependencies = [ "anyhow", "clap", - "heck", + "heck 0.5.0", "test-helpers", "wasm-encoder 0.243.0", "wasm-metadata 0.243.0", @@ -1558,7 +1573,7 @@ version = "0.49.0" dependencies = [ "anyhow", "clap", - "heck", + "heck 0.5.0", "indexmap", "wasm-metadata 0.243.0", "wit-bindgen-core", @@ -1585,7 +1600,7 @@ version = "0.49.0" dependencies = [ "anyhow", "clap", - "heck", + "heck 0.5.0", "pulldown-cmark", "wit-bindgen-core", ] @@ -1596,7 +1611,7 @@ version = "0.49.0" dependencies = [ "anyhow", "clap", - "heck", + "heck 0.5.0", "wit-bindgen-core", ] @@ -1608,7 +1623,7 @@ dependencies = [ "bytes", "clap", "futures", - "heck", + "heck 0.5.0", "indexmap", "prettyplease", "serde", @@ -1640,7 +1655,7 @@ version = "0.49.0" dependencies = [ "anyhow", "clap", - "heck", + "heck 0.5.0", "indexmap", "log", "rayon", diff --git a/crates/core/src/abi.rs b/crates/core/src/abi.rs index c56cb854c..d0c91e41b 100644 --- a/crates/core/src/abi.rs +++ b/crates/core/src/abi.rs @@ -325,7 +325,7 @@ def_instruction! { } : [1] => [*size as usize], /// Pops an array and an address off the stack, passes each element to a block storing it - FixedSizeListLowerBlock { + FixedSizeListLowerMemory { element: &'a Type, size: u32, id: TypeId, @@ -862,7 +862,7 @@ fn needs_deallocate(resolve: &Resolve, ty: &Type, what: Deallocate) -> bool { TypeDefKind::Flags(_) | TypeDefKind::Enum(_) => false, TypeDefKind::Future(_) | TypeDefKind::Stream(_) => what.handles(), TypeDefKind::Unknown => unreachable!(), - TypeDefKind::FixedSizeList(..) => todo!(), + TypeDefKind::FixedSizeList(t, _) => needs_deallocate(resolve, t, what), }, Type::Bool @@ -1772,16 +1772,15 @@ impl<'a, B: Bindgen> Generator<'a, B> { } TypeDefKind::Unknown => unreachable!(), TypeDefKind::FixedSizeList(ty, size) => { - let mut temp = Vec::new(); - self.resolve.push_flat(&Type::Id(id), &mut temp); - let mut args = self + let temp = flat_types(self.resolve, ty).unwrap(); + let flat_per_elem = temp.to_vec().len(); + let flatsize = flat_per_elem * (*size as usize); + let mut lowered_args = self .stack - .drain(self.stack.len() - temp.len()..) + .drain(self.stack.len() - flatsize..) .collect::>(); for _ in 0..*size { - temp.truncate(0); - self.resolve.push_flat(ty, &mut temp); - self.stack.extend(args.drain(..temp.len())); + self.stack.extend(lowered_args.drain(..flat_per_elem)); self.lift(ty); } self.emit(&FixedSizeListLift { @@ -1977,10 +1976,10 @@ impl<'a, B: Bindgen> Generator<'a, B> { self.emit(&IterElem { element }); self.emit(&IterBasePointer); let elem_addr = self.stack.pop().unwrap(); - self.write_to_memory(element, elem_addr, Default::default()); + self.write_to_memory(element, elem_addr, offset); self.finish_block(0); self.stack.push(addr); - self.emit(&FixedSizeListLowerBlock { + self.emit(&FixedSizeListLowerMemory { element, size: *size, id, diff --git a/crates/cpp/src/lib.rs b/crates/cpp/src/lib.rs index cc2f8e98b..685fefa57 100644 --- a/crates/cpp/src/lib.rs +++ b/crates/cpp/src/lib.rs @@ -74,6 +74,7 @@ struct Includes { // needs wit types needs_wit: bool, needs_memory: bool, + needs_array: bool, } #[derive(Default)] @@ -415,6 +416,9 @@ impl Cpp { if self.dependencies.needs_memory { self.include(""); } + if self.dependencies.needs_array { + self.include(""); + } if self.dependencies.needs_bit { self.include(""); } @@ -1667,7 +1671,13 @@ impl CppInterfaceGenerator<'_> { TypeDefKind::Future(_) => todo!(), TypeDefKind::Stream(_) => todo!(), TypeDefKind::Type(ty) => self.type_name(ty, from_namespace, flavor), - TypeDefKind::FixedSizeList(_, _) => todo!(), + TypeDefKind::FixedSizeList(ty, size) => { + self.r#gen.dependencies.needs_array = true; + format!( + "std::array<{}, {size}>", + self.type_name(ty, from_namespace, flavor) + ) + } TypeDefKind::Unknown => todo!(), }, Type::ErrorContext => todo!(), @@ -2616,7 +2626,57 @@ impl<'a, 'b> Bindgen for FunctionBindgen<'a, 'b> { results.push(move_if_necessary(&result)); } } - abi::Instruction::IterElem { .. } => results.push("IterElem".to_string()), + abi::Instruction::FixedSizeListLift { + element, + size, + id: _, + } => { + let tmp = self.tmp(); + let result = format!("result{tmp}"); + let typename = self + .r#gen + .type_name(element, &self.namespace, Flavor::InStruct); + self.push_str(&format!("std::array<{typename}, {size}> {result} = {{",)); + for a in operands.drain(0..(*size as usize)) { + self.push_str(&a); + self.push_str(", "); + } + self.push_str("};\n"); + results.push(result); + } + abi::Instruction::FixedSizeListLower { .. } => todo!(), + abi::Instruction::FixedSizeListLowerMemory { + element, + size: elemsize, + id: _, + } => { + let body = self.blocks.pop().unwrap(); + let vec = operands[0].clone(); + let target = operands[1].clone(); + let size = self.r#gen.sizes.size(element); + let size_str = size.format(POINTER_SIZE_EXPRESSION); + let typename = self + .r#gen + .type_name(element, &self.namespace, Flavor::InStruct); + let ptr_type = self.r#gen.r#gen.opts.ptr_type(); + self.push_str(&format!( + "{{ + {ptr_type} outer_base = {target};\n" + )); + let target: String = "outer_base".into(); + self.push_str(&format!( + "std::array<{typename}, {elemsize}>& outer_vec = {vec};\n" + )); + let vec: String = "outer_vec".into(); + self.push_str(&format!("for (unsigned i = 0; i<{vec}.size(); ++i) {{\n",)); + self.push_str(&format!( + "{ptr_type} base = {target} + i * {size_str}; + {typename}& iter_elem = {vec}[i];\n" + )); + self.push_str(&body.0); + self.push_str("\n}\n}\n"); + } + abi::Instruction::IterElem { .. } => results.push("iter_elem".to_string()), abi::Instruction::IterBasePointer => results.push("base".to_string()), abi::Instruction::RecordLower { record, .. } => { let op = &operands[0]; @@ -3222,7 +3282,7 @@ impl<'a, 'b> Bindgen for FunctionBindgen<'a, 'b> { self.src.push_str(">("); } if *amt == 1 { - if operands[0].starts_with("std::move(") { + if operands[0].starts_with("std::move(") && !operands[0].contains('.') { // remove the std::move due to return value optimization (and complex rules about when std::move harms) self.src.push_str(&operands[0][9..]); } else { diff --git a/crates/moonbit/src/lib.rs b/crates/moonbit/src/lib.rs index 5b7986ba6..792f738ac 100644 --- a/crates/moonbit/src/lib.rs +++ b/crates/moonbit/src/lib.rs @@ -2698,7 +2698,7 @@ impl Bindgen for FunctionBindgen<'_, '_> { | Instruction::DropHandle { .. } => todo!(), Instruction::FixedSizeListLift { .. } => todo!(), Instruction::FixedSizeListLower { .. } => todo!(), - Instruction::FixedSizeListLowerBlock { .. } => todo!(), + Instruction::FixedSizeListLowerMemory { .. } => todo!(), } } diff --git a/crates/rust/src/bindgen.rs b/crates/rust/src/bindgen.rs index 6899b6705..d4a9497d8 100644 --- a/crates/rust/src/bindgen.rs +++ b/crates/rust/src/bindgen.rs @@ -784,7 +784,7 @@ impl Bindgen for FunctionBindgen<'_, '_> { results.push(len); } - Instruction::FixedSizeListLowerBlock { + Instruction::FixedSizeListLowerMemory { element, size: _, id: _, diff --git a/tests/runtime/fixed-size-list/runner.rs b/tests/runtime/fixed-size-list/runner.rs index b1d356821..d72b653ca 100644 --- a/tests/runtime/fixed-size-list/runner.rs +++ b/tests/runtime/fixed-size-list/runner.rs @@ -13,12 +13,12 @@ fn main() { assert_eq!(result, [b'0', b'1', b'A', b'B', b'a', b'b', 128, 255]); } { - let _result = list_minmax16([0, 1024, 32768, 65535], [1, 2048, -32767, -2]); - // assert_eq!(result, ([0, 1024, 32768, 65535], [1, 2048, -32767, -2])); + let result = list_minmax16([0, 1024, 32768, 65535], [1, 2048, -32767, -2]); + assert_eq!(result, ([0, 1024, 32768, 65535], [1, 2048, -32767, -2])); } { - let _result = list_minmax_float([2.0, -42.0], [0.25, -0.125]); - // assert_eq!(result, ([2.0, -42.0], [0.25, -0.125])); + let result = list_minmax_float([2.0, -42.0], [0.25, -0.125]); + assert_eq!(result, ([2.0, -42.0], [0.25, -0.125])); } { let result = list_roundtrip([b'a', b'b', b'c', b'd', 0, 1, 2, 3, b'A', b'B', b'Y', b'Z']); @@ -27,4 +27,39 @@ fn main() { [b'a', b'b', b'c', b'd', 0, 1, 2, 3, b'A', b'B', b'Y', b'Z'] ); } + { + let result = nested_roundtrip([[1, 5], [42, 1_000_000]], [[-1, 3], [-2_000_000, 4711]]); + assert_eq!( + result, + ([[1, 5], [42, 1_000_000]], [[-1, 3], [-2_000_000, 4711]]) + ); + } + { + let result = large_roundtrip( + [[1, 5], [42, 1_000_000]], + [ + [-1, 3, -2, 4], + [-2_000_000, 4711, 99_999, -5], + [-6, 7, 8, -9], + [50, -5, 500, -5000], + ], + ); + assert_eq!( + result, + ( + [[1, 5], [42, 1_000_000]], + [ + [-1, 3, -2, 4], + [-2_000_000, 4711, 99_999, -5], + [-6, 7, 8, -9], + [50, -5, 500, -5000] + ] + ) + ); + } + { + let result = nightmare_on_cpp([Nested { l: [1, -1] }, Nested { l: [2, -2] }]); + assert_eq!(result[0].l, [1, -1]); + assert_eq!(result[1].l, [2, -2]); + } } diff --git a/tests/runtime/fixed-size-list/test.cpp b/tests/runtime/fixed-size-list/test.cpp new file mode 100644 index 000000000..3848d766a --- /dev/null +++ b/tests/runtime/fixed-size-list/test.cpp @@ -0,0 +1,51 @@ +#include +#include +// #include +// #include + +void exports::test::fixed_size_lists::to_test::ListParam(std::array a) { + std::array b = std::array{1, 2, 3, 4}; + assert(a == b); +} +void exports::test::fixed_size_lists::to_test::ListParam2(std::array, 2> a) { + std::array, 2> b = std::array, 2>{std::array{1, 2}, std::array{3, 4}}; + assert(a == b); +} +void exports::test::fixed_size_lists::to_test::ListParam3(std::array a) { + std::array b = std::array{-1, 2, -3, 4, -5, 6, -7, 8, -9, 10, -11, 12, -13, 14, -15, 16, -17, 18, -19, 20}; + assert(a == b); +} +std::array exports::test::fixed_size_lists::to_test::ListResult() { + return std::array{'0', '1', 'A', 'B', 'a', 'b', 128, 255}; +} +std::tuple, std::array> +exports::test::fixed_size_lists::to_test::ListMinmax16(std::array a, std::array b) { + return std::tuple, std::array>(a, b); +} +std::tuple, std::array> +exports::test::fixed_size_lists::to_test::ListMinmaxFloat(std::array a, std::array b) { + return std::tuple, std::array>(a,b); +} +std::array exports::test::fixed_size_lists::to_test::ListRoundtrip(std::array a) { + return a; +} + +std::tuple, 2>, + std::array, 2>> +exports::test::fixed_size_lists::to_test::NestedRoundtrip(std::array, 2> a, + std::array, 2> b) { + return std::tuple, 2>, + std::array, 2>>(a, b); +} + +std::tuple, 2>, + std::array, 4>> +exports::test::fixed_size_lists::to_test::LargeRoundtrip(std::array, 2> a, + std::array, 4> b) { + return std::tuple, 2>, + std::array, 4>>(a, b); +} +std::array<::test::fixed_size_lists::to_test::Nested, 2> +exports::test::fixed_size_lists::to_test::NightmareOnCpp(std::array<::test::fixed_size_lists::to_test::Nested, 2> a) { + return a; +} diff --git a/tests/runtime/fixed-size-list/test.rs b/tests/runtime/fixed-size-list/test.rs index 930f70572..669e4b858 100644 --- a/tests/runtime/fixed-size-list/test.rs +++ b/tests/runtime/fixed-size-list/test.rs @@ -4,6 +4,8 @@ struct Component; export!(Component); +use crate::exports::test::fixed_size_lists::to_test::Nested; + impl exports::test::fixed_size_lists::to_test::Guest for Component { fn list_param(a: [u32; 4]) { assert_eq!(a, [1, 2, 3, 4]); @@ -29,4 +31,13 @@ impl exports::test::fixed_size_lists::to_test::Guest for Component { fn list_result() -> [u8; 8] { [b'0', b'1', b'A', b'B', b'a', b'b', 128, 255] } + fn nested_roundtrip(a: [[u32; 2]; 2], b: [[i32; 2]; 2]) -> ([[u32; 2]; 2], [[i32; 2]; 2]) { + (a, b) + } + fn large_roundtrip(a: [[u32; 2]; 2], b: [[i32; 4]; 4]) -> ([[u32; 2]; 2], [[i32; 4]; 4]) { + (a, b) + } + fn nightmare_on_cpp(a: [Nested; 2]) -> [Nested; 2] { + a + } } diff --git a/tests/runtime/fixed-size-list/test.wit b/tests/runtime/fixed-size-list/test.wit index 8da40dc3e..5f5bbd84c 100644 --- a/tests/runtime/fixed-size-list/test.wit +++ b/tests/runtime/fixed-size-list/test.wit @@ -13,6 +13,15 @@ interface to-test { -> tuple, list>; list-roundtrip: func(a: list) -> list; + + nested-roundtrip: func(a: list, 2>, b: list, 2>) -> tuple,2>, list, 2>>; + large-roundtrip: func(a: list, 2>, b: list, 4>) -> tuple,2>, list, 4>>; + + record nested { + l: list, + } + + nightmare-on-cpp: func(a: list) -> list; } world test { From 49f8f1e4bfa7855bf1dafde7dc7e183fde02871c Mon Sep 17 00:00:00 2001 From: Christof Petig Date: Sun, 20 Jul 2025 16:34:23 +0200 Subject: [PATCH 11/13] adapt and simplify C++ example --- tests/runtime/fixed-size-list/test.cpp | 26 +++++++++++++------------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/tests/runtime/fixed-size-list/test.cpp b/tests/runtime/fixed-size-list/test.cpp index 3848d766a..abfeabbdd 100644 --- a/tests/runtime/fixed-size-list/test.cpp +++ b/tests/runtime/fixed-size-list/test.cpp @@ -1,38 +1,38 @@ #include #include -// #include -// #include -void exports::test::fixed_size_lists::to_test::ListParam(std::array a) { +using namespace exports::test::fixed_size_lists; + +void to_test::ListParam(std::array a) { std::array b = std::array{1, 2, 3, 4}; assert(a == b); } -void exports::test::fixed_size_lists::to_test::ListParam2(std::array, 2> a) { +void to_test::ListParam2(std::array, 2> a) { std::array, 2> b = std::array, 2>{std::array{1, 2}, std::array{3, 4}}; assert(a == b); } -void exports::test::fixed_size_lists::to_test::ListParam3(std::array a) { +void to_test::ListParam3(std::array a) { std::array b = std::array{-1, 2, -3, 4, -5, 6, -7, 8, -9, 10, -11, 12, -13, 14, -15, 16, -17, 18, -19, 20}; assert(a == b); } -std::array exports::test::fixed_size_lists::to_test::ListResult() { +std::array to_test::ListResult() { return std::array{'0', '1', 'A', 'B', 'a', 'b', 128, 255}; } std::tuple, std::array> -exports::test::fixed_size_lists::to_test::ListMinmax16(std::array a, std::array b) { +to_test::ListMinmax16(std::array a, std::array b) { return std::tuple, std::array>(a, b); } std::tuple, std::array> -exports::test::fixed_size_lists::to_test::ListMinmaxFloat(std::array a, std::array b) { +to_test::ListMinmaxFloat(std::array a, std::array b) { return std::tuple, std::array>(a,b); } -std::array exports::test::fixed_size_lists::to_test::ListRoundtrip(std::array a) { +std::array to_test::ListRoundtrip(std::array a) { return a; } std::tuple, 2>, std::array, 2>> -exports::test::fixed_size_lists::to_test::NestedRoundtrip(std::array, 2> a, +to_test::NestedRoundtrip(std::array, 2> a, std::array, 2> b) { return std::tuple, 2>, std::array, 2>>(a, b); @@ -40,12 +40,12 @@ exports::test::fixed_size_lists::to_test::NestedRoundtrip(std::array, 2>, std::array, 4>> -exports::test::fixed_size_lists::to_test::LargeRoundtrip(std::array, 2> a, +to_test::LargeRoundtrip(std::array, 2> a, std::array, 4> b) { return std::tuple, 2>, std::array, 4>>(a, b); } -std::array<::test::fixed_size_lists::to_test::Nested, 2> -exports::test::fixed_size_lists::to_test::NightmareOnCpp(std::array<::test::fixed_size_lists::to_test::Nested, 2> a) { +std::array +to_test::NightmareOnCpp(std::array a) { return a; } From 8b281f5afa4cb3cdba564de57ba1734d5048f22d Mon Sep 17 00:00:00 2001 From: Christof Petig Date: Tue, 16 Dec 2025 19:21:35 +0100 Subject: [PATCH 12/13] modernize code --- Cargo.lock | 35 +++----- crates/core/src/abi.rs | 2 +- crates/csharp/src/function.rs | 2 +- tests/runtime/fixed-size-list/runner.rs | 115 +++++++++++++----------- tests/runtime/fixed-size-list/test.wit | 2 + 5 files changed, 75 insertions(+), 81 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 10d8fa4ba..f8617a683 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -106,15 +106,6 @@ dependencies = [ "typenum", ] -[[package]] -name = "bitmaps" -version = "2.1.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "031043d04099746d8db04daf1fa424b2bc8bd69d92b25962dcde24da39ab64a2" -dependencies = [ - "typenum", -] - [[package]] name = "bumpalo" version = "3.19.0" @@ -162,7 +153,7 @@ version = "4.5.49" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2a0b5487afeab2deb2ff4e03a807ad1a03ac532ff5a2cee5d86884440c7f7671" dependencies = [ - "heck 0.5.0", + "heck", "proc-macro2", "quote", "syn", @@ -178,7 +169,7 @@ checksum = "a1d728cc89cf3aee9ff92b05e62b19ee65a02b5702cff7d5a377e32c6ae29d8d" name = "codegen-macro" version = "0.0.0" dependencies = [ - "heck 0.5.0", + "heck", "quote", ] @@ -420,12 +411,6 @@ version = "0.16.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "841d1cc9bed7f9236f321df977030373f4a4163ae1a7dbfe1a51a2c1a51d9100" -[[package]] -name = "heck" -version = "0.4.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "95505c38b4572b2d910cecb0281560f54b440a19336cbbcb27bf6ce6adc6f5a8" - [[package]] name = "heck" version = "0.5.0" @@ -1513,7 +1498,7 @@ version = "0.49.0" dependencies = [ "anyhow", "clap", - "heck 0.5.0", + "heck", "indexmap", "wasm-encoder 0.243.0", "wasm-metadata 0.243.0", @@ -1547,7 +1532,7 @@ version = "0.49.0" dependencies = [ "anyhow", "clap", - "heck 0.5.0", + "heck", "serde", "wit-parser", ] @@ -1558,7 +1543,7 @@ version = "0.49.0" dependencies = [ "anyhow", "clap", - "heck 0.5.0", + "heck", "test-helpers", "wasm-encoder 0.243.0", "wasm-metadata 0.243.0", @@ -1573,7 +1558,7 @@ version = "0.49.0" dependencies = [ "anyhow", "clap", - "heck 0.5.0", + "heck", "indexmap", "wasm-metadata 0.243.0", "wit-bindgen-core", @@ -1600,7 +1585,7 @@ version = "0.49.0" dependencies = [ "anyhow", "clap", - "heck 0.5.0", + "heck", "pulldown-cmark", "wit-bindgen-core", ] @@ -1611,7 +1596,7 @@ version = "0.49.0" dependencies = [ "anyhow", "clap", - "heck 0.5.0", + "heck", "wit-bindgen-core", ] @@ -1623,7 +1608,7 @@ dependencies = [ "bytes", "clap", "futures", - "heck 0.5.0", + "heck", "indexmap", "prettyplease", "serde", @@ -1655,7 +1640,7 @@ version = "0.49.0" dependencies = [ "anyhow", "clap", - "heck 0.5.0", + "heck", "indexmap", "log", "rayon", diff --git a/crates/core/src/abi.rs b/crates/core/src/abi.rs index d0c91e41b..790745d73 100644 --- a/crates/core/src/abi.rs +++ b/crates/core/src/abi.rs @@ -1772,7 +1772,7 @@ impl<'a, B: Bindgen> Generator<'a, B> { } TypeDefKind::Unknown => unreachable!(), TypeDefKind::FixedSizeList(ty, size) => { - let temp = flat_types(self.resolve, ty).unwrap(); + let temp = flat_types(self.resolve, ty, None).unwrap(); let flat_per_elem = temp.to_vec().len(); let flatsize = flat_per_elem * (*size as usize); let mut lowered_args = self diff --git a/crates/csharp/src/function.rs b/crates/csharp/src/function.rs index d3d944d8c..7829b8530 100644 --- a/crates/csharp/src/function.rs +++ b/crates/csharp/src/function.rs @@ -1393,7 +1393,7 @@ impl Bindgen for FunctionBindgen<'_, '_> { | Instruction::DropHandle { .. } | Instruction::FixedSizeListLift { .. } | Instruction::FixedSizeListLower { .. } - | Instruction::FixedSizeListLowerBlock { .. } + | Instruction::FixedSizeListLowerMemory { .. } => { dbg!(inst); todo!() diff --git a/tests/runtime/fixed-size-list/runner.rs b/tests/runtime/fixed-size-list/runner.rs index d72b653ca..b004d8b23 100644 --- a/tests/runtime/fixed-size-list/runner.rs +++ b/tests/runtime/fixed-size-list/runner.rs @@ -2,64 +2,71 @@ include!(env!("BINDINGS")); use test::fixed_size_lists::to_test::*; -fn main() { - list_param([1, 2, 3, 4]); - list_param2([[1, 2], [3, 4]]); - list_param3([ - -1, 2, -3, 4, -5, 6, -7, 8, -9, 10, -11, 12, -13, 14, -15, 16, -17, 18, -19, 20, - ]); - { - let result = list_result(); - assert_eq!(result, [b'0', b'1', b'A', b'B', b'a', b'b', 128, 255]); - } - { - let result = list_minmax16([0, 1024, 32768, 65535], [1, 2048, -32767, -2]); - assert_eq!(result, ([0, 1024, 32768, 65535], [1, 2048, -32767, -2])); - } - { - let result = list_minmax_float([2.0, -42.0], [0.25, -0.125]); - assert_eq!(result, ([2.0, -42.0], [0.25, -0.125])); - } - { - let result = list_roundtrip([b'a', b'b', b'c', b'd', 0, 1, 2, 3, b'A', b'B', b'Y', b'Z']); - assert_eq!( - result, - [b'a', b'b', b'c', b'd', 0, 1, 2, 3, b'A', b'B', b'Y', b'Z'] - ); - } - { - let result = nested_roundtrip([[1, 5], [42, 1_000_000]], [[-1, 3], [-2_000_000, 4711]]); - assert_eq!( - result, - ([[1, 5], [42, 1_000_000]], [[-1, 3], [-2_000_000, 4711]]) - ); - } - { - let result = large_roundtrip( - [[1, 5], [42, 1_000_000]], - [ - [-1, 3, -2, 4], - [-2_000_000, 4711, 99_999, -5], - [-6, 7, 8, -9], - [50, -5, 500, -5000], - ], - ); - assert_eq!( - result, - ( +struct Component; + +export!(Component); + +impl Guest for Component { + fn run() { + list_param([1, 2, 3, 4]); + list_param2([[1, 2], [3, 4]]); + list_param3([ + -1, 2, -3, 4, -5, 6, -7, 8, -9, 10, -11, 12, -13, 14, -15, 16, -17, 18, -19, 20, + ]); + { + let result = list_result(); + assert_eq!(result, [b'0', b'1', b'A', b'B', b'a', b'b', 128, 255]); + } + { + let result = list_minmax16([0, 1024, 32768, 65535], [1, 2048, -32767, -2]); + assert_eq!(result, ([0, 1024, 32768, 65535], [1, 2048, -32767, -2])); + } + { + let result = list_minmax_float([2.0, -42.0], [0.25, -0.125]); + assert_eq!(result, ([2.0, -42.0], [0.25, -0.125])); + } + { + let result = + list_roundtrip([b'a', b'b', b'c', b'd', 0, 1, 2, 3, b'A', b'B', b'Y', b'Z']); + assert_eq!( + result, + [b'a', b'b', b'c', b'd', 0, 1, 2, 3, b'A', b'B', b'Y', b'Z'] + ); + } + { + let result = nested_roundtrip([[1, 5], [42, 1_000_000]], [[-1, 3], [-2_000_000, 4711]]); + assert_eq!( + result, + ([[1, 5], [42, 1_000_000]], [[-1, 3], [-2_000_000, 4711]]) + ); + } + { + let result = large_roundtrip( [[1, 5], [42, 1_000_000]], [ [-1, 3, -2, 4], [-2_000_000, 4711, 99_999, -5], [-6, 7, 8, -9], - [50, -5, 500, -5000] - ] - ) - ); - } - { - let result = nightmare_on_cpp([Nested { l: [1, -1] }, Nested { l: [2, -2] }]); - assert_eq!(result[0].l, [1, -1]); - assert_eq!(result[1].l, [2, -2]); + [50, -5, 500, -5000], + ], + ); + assert_eq!( + result, + ( + [[1, 5], [42, 1_000_000]], + [ + [-1, 3, -2, 4], + [-2_000_000, 4711, 99_999, -5], + [-6, 7, 8, -9], + [50, -5, 500, -5000] + ] + ) + ); + } + { + let result = nightmare_on_cpp([Nested { l: [1, -1] }, Nested { l: [2, -2] }]); + assert_eq!(result[0].l, [1, -1]); + assert_eq!(result[1].l, [2, -2]); + } } } diff --git a/tests/runtime/fixed-size-list/test.wit b/tests/runtime/fixed-size-list/test.wit index 5f5bbd84c..496e4470f 100644 --- a/tests/runtime/fixed-size-list/test.wit +++ b/tests/runtime/fixed-size-list/test.wit @@ -30,4 +30,6 @@ world test { world runner { import to-test; + + export run: func(); } From ed27ed65ba7da8a10e84c0b586cce7d7466e503b Mon Sep 17 00:00:00 2001 From: Christof Petig Date: Tue, 16 Dec 2025 22:05:12 +0100 Subject: [PATCH 13/13] linear code size for fixed size arrays (except when flattened) --- crates/core/src/abi.rs | 29 ++++++++++++++++++++--------- crates/cpp/src/lib.rs | 31 ++++++++++++++++++++++++++++++- crates/csharp/src/function.rs | 3 ++- crates/moonbit/src/lib.rs | 3 ++- crates/rust/src/bindgen.rs | 25 ++++++++++++++++++++++++- 5 files changed, 78 insertions(+), 13 deletions(-) diff --git a/crates/core/src/abi.rs b/crates/core/src/abi.rs index 790745d73..245644ceb 100644 --- a/crates/core/src/abi.rs +++ b/crates/core/src/abi.rs @@ -325,12 +325,23 @@ def_instruction! { } : [1] => [*size as usize], /// Pops an array and an address off the stack, passes each element to a block storing it - FixedSizeListLowerMemory { + FixedSizeListLowerToMemory { element: &'a Type, size: u32, id: TypeId, } : [2] => [0], + /// Pops base address, pushes an array + /// + /// This will also pop a block from the block stack which is how to + /// read each individual element from the list. + FixedSizeListLiftFromMemory { + element: &'a Type, + size: u32, + id: TypeId, + } : [1] => [1], + + /// Pushes an operand onto the stack representing the list item from /// each iteration of the list. /// @@ -1979,7 +1990,7 @@ impl<'a, B: Bindgen> Generator<'a, B> { self.write_to_memory(element, elem_addr, offset); self.finish_block(0); self.stack.push(addr); - self.emit(&FixedSizeListLowerMemory { + self.emit(&FixedSizeListLowerToMemory { element, size: *size, id, @@ -2172,13 +2183,13 @@ impl<'a, B: Bindgen> Generator<'a, B> { TypeDefKind::Unknown => unreachable!(), TypeDefKind::FixedSizeList(ty, size) => { - let increment = self.bindgen.sizes().size(ty); - let mut position = offset; - for _ in 0..*size { - self.read_from_memory(ty, addr.clone(), position); - position = position + increment; - } - self.emit(&FixedSizeListLift { + self.push_block(); + self.emit(&IterBasePointer); + let elemaddr = self.stack.pop().unwrap(); + self.read_from_memory(ty, elemaddr, Default::default()); + self.finish_block(1); + self.stack.push(addr.clone()); + self.emit(&FixedSizeListLiftFromMemory { element: ty, size: *size, id, diff --git a/crates/cpp/src/lib.rs b/crates/cpp/src/lib.rs index 685fefa57..415200170 100644 --- a/crates/cpp/src/lib.rs +++ b/crates/cpp/src/lib.rs @@ -2644,8 +2644,37 @@ impl<'a, 'b> Bindgen for FunctionBindgen<'a, 'b> { self.push_str("};\n"); results.push(result); } + abi::Instruction::FixedSizeListLiftFromMemory { + element, + size: elemsize, + id: _, + } => { + let body = self.blocks.pop().unwrap(); + let tmp = self.tmp(); + let vec = format!("array{tmp}"); + let source = operands[0].clone(); + let size = self.r#gen.sizes.size(element); + let size_str = size.format(POINTER_SIZE_EXPRESSION); + let typename = self + .r#gen + .type_name(element, &self.namespace, Flavor::InStruct); + let ptr_type = self.r#gen.r#gen.opts.ptr_type(); + self.push_str(&format!("std::array<{typename}, {elemsize}> {vec};\n")); + self.push_str(&format!( + "{{ + {ptr_type} outer_base = {source};\n" + )); + let source: String = "outer_base".into(); + // let vec: String = "outer_vec".into(); + self.push_str(&format!("for (unsigned i = 0; i<{elemsize}; ++i) {{\n",)); + self.push_str(&format!("{ptr_type} base = {source} + i * {size_str};\n")); + self.push_str(&body.0); + self.push_str(&format!("{vec}[i] = {};", body.1[0])); + self.push_str("\n}\n}\n"); + results.push(vec); + } abi::Instruction::FixedSizeListLower { .. } => todo!(), - abi::Instruction::FixedSizeListLowerMemory { + abi::Instruction::FixedSizeListLowerToMemory { element, size: elemsize, id: _, diff --git a/crates/csharp/src/function.rs b/crates/csharp/src/function.rs index 7829b8530..3c4f58eae 100644 --- a/crates/csharp/src/function.rs +++ b/crates/csharp/src/function.rs @@ -1393,7 +1393,8 @@ impl Bindgen for FunctionBindgen<'_, '_> { | Instruction::DropHandle { .. } | Instruction::FixedSizeListLift { .. } | Instruction::FixedSizeListLower { .. } - | Instruction::FixedSizeListLowerMemory { .. } + | Instruction::FixedSizeListLowerToMemory { .. } + | Instruction::FixedSizeListLiftFromMemory { .. } => { dbg!(inst); todo!() diff --git a/crates/moonbit/src/lib.rs b/crates/moonbit/src/lib.rs index 792f738ac..28b741a63 100644 --- a/crates/moonbit/src/lib.rs +++ b/crates/moonbit/src/lib.rs @@ -2698,7 +2698,8 @@ impl Bindgen for FunctionBindgen<'_, '_> { | Instruction::DropHandle { .. } => todo!(), Instruction::FixedSizeListLift { .. } => todo!(), Instruction::FixedSizeListLower { .. } => todo!(), - Instruction::FixedSizeListLowerMemory { .. } => todo!(), + Instruction::FixedSizeListLowerToMemory { .. } => todo!(), + Instruction::FixedSizeListLiftFromMemory { .. } => todo!(), } } diff --git a/crates/rust/src/bindgen.rs b/crates/rust/src/bindgen.rs index d4a9497d8..7513176e1 100644 --- a/crates/rust/src/bindgen.rs +++ b/crates/rust/src/bindgen.rs @@ -784,7 +784,7 @@ impl Bindgen for FunctionBindgen<'_, '_> { results.push(len); } - Instruction::FixedSizeListLowerMemory { + Instruction::FixedSizeListLowerToMemory { element, size: _, id: _, @@ -1253,6 +1253,29 @@ impl Bindgen for FunctionBindgen<'_, '_> { results.push(format!("{}[{i}]", operands[0])); } } + Instruction::FixedSizeListLiftFromMemory { + element, + size, + id: _, + } => { + let body = self.blocks.pop().unwrap(); + let elemsize = self + .r#gen + .sizes + .size(element) + .format(POINTER_SIZE_EXPRESSION); + let base = operands[0].clone(); + let tmp = self.tmp(); + let index_var = format!("idx{tmp}"); + self.push_str(&format!( + " let array{tmp}: [_; {size}] = core::array::from_fn(|{index_var}| {{ + let base = {base}.add({index_var} * {elemsize}); + {body} + }});" + )); + let result = format!("array{tmp}"); + results.push(result); + } } } }