Skip to content
This repository was archived by the owner on Feb 14, 2021. It is now read-only.

Alternate multiresult implementation #68

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
35 changes: 32 additions & 3 deletions derive/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -145,13 +145,27 @@ fn generate_eth_client(client_name: &str, intf: &items::Interface) -> quote::Tok
syn::FunctionRetTy::Default => quote!{
let mut result = Vec::new();
},
syn::FunctionRetTy::Ty(syn::Ty::Tup(ref tys)) => {
let result_len = tys.len() * 32;
quote!{
let mut result = [0u8; #result_len];
}
},
syn::FunctionRetTy::Ty(_) => quote!{
let mut result = [0u8; 32];
},
};

let result_pop = match signature.method_sig.decl.output {
syn::FunctionRetTy::Default => None,
syn::FunctionRetTy::Ty(syn::Ty::Tup(ref result_types)) => {
Some(quote!{
let mut stream = pwasm_abi::eth::Stream::new(&result);
(
#( stream.pop::<#result_types>().expect("failed decode call output") ),*
)
})
},
syn::FunctionRetTy::Ty(_) => Some(quote!{
let mut stream = pwasm_abi::eth::Stream::new(&result);
stream.pop().expect("failed decode call output")
Expand Down Expand Up @@ -262,16 +276,31 @@ fn generate_eth_endpoint(endpoint_name: &str, intf: &items::Interface) -> quote:
let ident = &signature.name;
let arg_types = signature.arguments.iter().map(|&(_, ref ty)| quote! { #ty });
let check_value_if_payable = if signature.is_payable { quote! {} } else { quote! {#check_value_code} };
if !signature.return_types.is_empty() {
let return_count_literal = syn::Lit::Int(signature.return_types.len() as u64, syn::IntTy::Usize);
let return_types_len = signature.return_types.len();
if return_types_len > 1 {
let return_types_it : Vec<_> = (0..return_types_len).into_iter()
.map(|i|syn::Ident::new(i.to_string())).collect();
Some(quote! {
#hash_literal => {
#check_value_if_payable
let mut stream = pwasm_abi::eth::Stream::new(method_payload);
let result = inner.#ident(
#(stream.pop::<#arg_types>().expect("argument decoding failed")),*
);
let mut sink = pwasm_abi::eth::Sink::new(#return_types_len);
#( sink.push(result.#return_types_it); )*
sink.finalize_panicking()
}
})
} else if return_types_len == 1 {
Some(quote! {
#hash_literal => {
#check_value_if_payable
let mut stream = pwasm_abi::eth::Stream::new(method_payload);
let result = inner.#ident(
#(stream.pop::<#arg_types>().expect("argument decoding failed")),*
);
let mut sink = pwasm_abi::eth::Sink::new(#return_count_literal);
let mut sink = pwasm_abi::eth::Sink::new(1);
sink.push(result);
sink.finalize_panicking()
}
Expand Down
75 changes: 0 additions & 75 deletions src/eth/common.rs
Original file line number Diff line number Diff line change
Expand Up @@ -258,81 +258,6 @@ macro_rules! abi_type_fixed_impl {
}
}

impl<T1: AbiType, T2: AbiType> AbiType for (T1, T2) {
fn decode(_stream: &mut Stream) -> Result<Self, Error> {
panic!("Tuples allow only encoding, not decoding (for supporting multiple return types)")
}

fn encode(self, sink: &mut Sink) {
sink.push(self.0);
sink.push(self.1);
}

const IS_FIXED: bool = true;
}

impl<T1: AbiType, T2: AbiType, T3: AbiType> AbiType for (T1, T2, T3) {
fn decode(_stream: &mut Stream) -> Result<Self, Error> {
panic!("Tuples allow only encoding, not decoding (for supporting multiple return types)")
}

fn encode(self, sink: &mut Sink) {
sink.push(self.0);
sink.push(self.1);
sink.push(self.2);
}

const IS_FIXED: bool = true;
}

impl<T1: AbiType, T2: AbiType, T3: AbiType, T4: AbiType> AbiType for (T1, T2, T3, T4) {
fn decode(_stream: &mut Stream) -> Result<Self, Error> {
panic!("Tuples allow only encoding, not decoding (for supporting multiple return types)")
}

fn encode(self, sink: &mut Sink) {
sink.push(self.0);
sink.push(self.1);
sink.push(self.2);
sink.push(self.3);
}

const IS_FIXED: bool = true;
}

impl<T1: AbiType, T2: AbiType, T3: AbiType, T4: AbiType, T5: AbiType> AbiType for (T1, T2, T3, T4, T5) {
fn decode(_stream: &mut Stream) -> Result<Self, Error> {
panic!("Tuples allow only encoding, not decoding (for supporting multiple return types)")
}

fn encode(self, sink: &mut Sink) {
sink.push(self.0);
sink.push(self.1);
sink.push(self.2);
sink.push(self.3);
sink.push(self.4);
}

const IS_FIXED: bool = true;
}

impl<T1: AbiType, T2: AbiType, T3: AbiType, T4: AbiType, T5: AbiType, T6: AbiType> AbiType for (T1, T2, T3, T4, T5, T6) {
fn decode(_stream: &mut Stream) -> Result<Self, Error> {
panic!("Tuples allow only encoding, not decoding (for supporting multiple return types)")
}

fn encode(self, sink: &mut Sink) {
sink.push(self.0);
sink.push(self.1);
sink.push(self.2);
sink.push(self.3);
sink.push(self.4);
sink.push(self.5);
}

const IS_FIXED: bool = true;
}

abi_type_fixed_impl!(1);
abi_type_fixed_impl!(2);
abi_type_fixed_impl!(3);
Expand Down