diff --git a/framework/base/src/abi/type_abi.rs b/framework/base/src/abi/type_abi.rs index 25d4e92b46..3e4c451b48 100644 --- a/framework/base/src/abi/type_abi.rs +++ b/framework/base/src/abi/type_abi.rs @@ -9,7 +9,7 @@ use alloc::{format, string::ToString, vec::Vec}; /// /// Will be automatically implemented for struct ad enum types via the `#[type_abi]` annotation. pub trait TypeAbi: TypeAbiFrom { - type Unmanaged: TypeAbiFrom; + type Unmanaged; fn type_names() -> TypeNames { TypeNames { diff --git a/framework/base/src/abi/type_abi_impl_basic.rs b/framework/base/src/abi/type_abi_impl_basic.rs index 878a09bc87..2961604bb9 100644 --- a/framework/base/src/abi/type_abi_impl_basic.rs +++ b/framework/base/src/abi/type_abi_impl_basic.rs @@ -22,7 +22,7 @@ impl TypeAbi for () { impl TypeAbiFrom<&U> for &T where T: TypeAbiFrom {} impl TypeAbi for &T { - type Unmanaged = Self; + type Unmanaged = T::Unmanaged; fn type_name() -> TypeName { T::type_name() @@ -58,7 +58,7 @@ impl TypeAbi for Box { impl TypeAbiFrom<&[T]> for &[U] where T: TypeAbiFrom {} impl TypeAbi for &[T] { - type Unmanaged = Self; + type Unmanaged = Vec; fn type_name() -> TypeName { let t_name = T::type_name(); @@ -84,7 +84,7 @@ impl TypeAbi for &[T] { impl TypeAbiFrom> for Vec where T: TypeAbiFrom {} impl TypeAbi for Vec { - type Unmanaged = Self; + type Unmanaged = Vec; fn type_name() -> TypeName { <&[T]>::type_name() @@ -209,6 +209,7 @@ type_abi_name_only!(i64, "i64"); type_abi_name_only!(core::num::NonZeroUsize, "NonZeroUsize"); type_abi_name_only!(bool, "bool"); +type_abi_name_only!(f64, "f64"); // Unsigned integer types: the contract can return a smaller capacity result and and we can interpret it as a larger capacity type. @@ -244,10 +245,13 @@ impl TypeAbiFrom for isize {} impl TypeAbiFrom for i16 {} -impl TypeAbiFrom> for Option where T: TypeAbiFrom {} +impl TypeAbiFrom> for Option where T: TypeAbiFrom {} -impl TypeAbi for Option { - type Unmanaged = Self; +impl TypeAbi for Option +where + T: TypeAbi, +{ + type Unmanaged = Option; fn type_name() -> TypeName { format!("Option<{}>", T::type_name()) @@ -262,10 +266,10 @@ impl TypeAbi for Option { } } -impl TypeAbiFrom> for Result where T: TypeAbiFrom {} +impl TypeAbiFrom for Result {} impl TypeAbi for Result { - type Unmanaged = Self; + type Unmanaged = Result; fn type_name() -> TypeName { T::type_name() @@ -301,7 +305,7 @@ macro_rules! tuple_impls { where $($name: TypeAbi,)+ { - type Unmanaged = Self; + type Unmanaged = ($($name::Unmanaged,)+); fn type_name() -> TypeName { let mut repr = TypeName::from("tuple<"); @@ -356,10 +360,10 @@ tuple_impls! { 16 => (0 T0 1 T1 2 T2 3 T3 4 T4 5 T5 6 T6 7 T7 8 T8 9 T9 10 T10 11 T11 12 T12 13 T13 14 T14 15 T15) } -impl TypeAbiFrom<[T; N]> for [U; N] where T: TypeAbiFrom {} +impl TypeAbiFrom<[U; N]> for [T; N] where T: TypeAbiFrom {} impl TypeAbi for [T; N] { - type Unmanaged = Self; + type Unmanaged = [T::Unmanaged; N]; fn type_name() -> TypeName { let mut repr = TypeName::from("array"); diff --git a/framework/base/src/abi/type_abi_impl_codec_multi.rs b/framework/base/src/abi/type_abi_impl_codec_multi.rs index 6b1cf9ab72..7fcfa89ae5 100644 --- a/framework/base/src/abi/type_abi_impl_codec_multi.rs +++ b/framework/base/src/abi/type_abi_impl_codec_multi.rs @@ -15,7 +15,7 @@ where #[cfg(feature = "alloc")] impl TypeAbi for crate::codec::multi_types::MultiValueVec { - type Unmanaged = Self; + type Unmanaged = crate::codec::multi_types::MultiValueVec; fn type_name() -> TypeName { super::type_name_variadic::() @@ -52,10 +52,10 @@ impl TypeAbi for IgnoreValue { } } -impl TypeAbiFrom> for OptionalValue where T: TypeAbiFrom {} +impl TypeAbiFrom> for OptionalValue where T: TypeAbiFrom {} impl TypeAbi for OptionalValue { - type Unmanaged = Self; + type Unmanaged = OptionalValue; fn type_name() -> TypeName { super::type_name_optional::() diff --git a/framework/base/src/storage/mappers/single_value_mapper.rs b/framework/base/src/storage/mappers/single_value_mapper.rs index 8d7694c070..1f121250ff 100644 --- a/framework/base/src/storage/mappers/single_value_mapper.rs +++ b/framework/base/src/storage/mappers/single_value_mapper.rs @@ -220,7 +220,7 @@ where SA: StorageMapperApi, T: TopEncode + TopDecode + TypeAbi, { - type Unmanaged = Self; + type Unmanaged = T::Unmanaged; fn type_name() -> TypeName { T::type_name() diff --git a/framework/base/src/types/heap/arg_buffer.rs b/framework/base/src/types/heap/arg_buffer.rs index 9313157c77..c27be12f2c 100644 --- a/framework/base/src/types/heap/arg_buffer.rs +++ b/framework/base/src/types/heap/arg_buffer.rs @@ -1,6 +1,8 @@ use crate::{ + abi::{TypeAbiFrom, TypeName}, api::ManagedTypeApi, codec::TopEncodeOutput, + proxy_imports::TypeAbi, types::{heap::BoxedBytes, ManagedArgBuffer}, }; use alloc::vec::Vec; @@ -111,6 +113,21 @@ impl Clone for ArgBuffer { } } +impl TypeAbiFrom for ArgBuffer {} + +impl TypeAbi for ArgBuffer { + type Unmanaged = Self; + + /// It is semantically equivalent to any list of `T`. + fn type_name() -> TypeName { + <&[Vec] as TypeAbi>::type_name() + } + + fn type_name_rust() -> TypeName { + "ArgBuffer".into() + } +} + impl TopEncodeOutput for &mut ArgBuffer { type NestedBuffer = Vec; diff --git a/framework/base/src/types/heap/boxed_bytes.rs b/framework/base/src/types/heap/boxed_bytes.rs index 3bc0d690c6..336b0874a8 100644 --- a/framework/base/src/types/heap/boxed_bytes.rs +++ b/framework/base/src/types/heap/boxed_bytes.rs @@ -1,4 +1,9 @@ -use alloc::{alloc::{alloc, Layout, realloc}, boxed::Box, vec, vec::Vec}; +use alloc::{ + alloc::{alloc, realloc, Layout}, + boxed::Box, + vec, + vec::Vec, +}; use crate::{ abi::{TypeAbi, TypeAbiFrom, TypeName}, diff --git a/framework/base/src/types/managed/multi_value/multi_value_encoded.rs b/framework/base/src/types/managed/multi_value/multi_value_encoded.rs index 18a9498da4..f06a6fcbdc 100644 --- a/framework/base/src/types/managed/multi_value/multi_value_encoded.rs +++ b/framework/base/src/types/managed/multi_value/multi_value_encoded.rs @@ -244,6 +244,10 @@ where M: ManagedTypeApi, T: TypeAbi, { + #[cfg(feature = "alloc")] + type Unmanaged = MultiValueVec; + + #[cfg(not(feature = "alloc"))] type Unmanaged = Self; fn type_name() -> TypeName { diff --git a/framework/base/src/types/managed/multi_value/multi_value_managed_vec.rs b/framework/base/src/types/managed/multi_value/multi_value_managed_vec.rs index a7f1337080..0c1f094cb6 100644 --- a/framework/base/src/types/managed/multi_value/multi_value_managed_vec.rs +++ b/framework/base/src/types/managed/multi_value/multi_value_managed_vec.rs @@ -222,6 +222,10 @@ where M: ManagedTypeApi, T: ManagedVecItem, { + #[cfg(feature = "alloc")] + type Unmanaged = multiversx_sc_codec::multi_types::MultiValueVec; + + #[cfg(not(feature = "alloc"))] type Unmanaged = Self; fn type_name() -> TypeName { diff --git a/framework/base/src/types/managed/wrapped/managed_vec_item_payload.rs b/framework/base/src/types/managed/wrapped/managed_vec_item_payload.rs index 4d544e8d75..07adc31a08 100644 --- a/framework/base/src/types/managed/wrapped/managed_vec_item_payload.rs +++ b/framework/base/src/types/managed/wrapped/managed_vec_item_payload.rs @@ -76,7 +76,7 @@ impl ManagedVecItemPayloadAdd } /// Replaces a const generic expression. -/// +/// /// Remove once const generic expressions are stabilized in Rust. macro_rules! payload_add { ($dec1:expr, $dec2:expr, $result_add:expr) => { diff --git a/tools/payload-macro-generator/src/main.rs b/tools/payload-macro-generator/src/main.rs index 6991a6816e..12a0d4c581 100644 --- a/tools/payload-macro-generator/src/main.rs +++ b/tools/payload-macro-generator/src/main.rs @@ -8,7 +8,7 @@ const MAX_X: usize = 48; const MAX_Y: usize = 128; /// Generates the payload_add! macros in the ManagedVecItem implem,entation. -/// +/// /// TODO: remove once generic const expressions are stabilized in Rust. fn main() -> io::Result<()> { let mut file = File::create("output.rs")?; @@ -17,11 +17,7 @@ fn main() -> io::Result<()> { for x in MIN..=MAX_X { for y in MIN..=MAX_Y { let sum = x + y; - writeln!( - file, - "payload_add!({}usize, {}usize, {}usize);", - x, y, sum - )?; + writeln!(file, "payload_add!({}usize, {}usize, {}usize);", x, y, sum)?; } }