diff --git a/librustzcash-wrapper/src/lib.rs b/librustzcash-wrapper/src/lib.rs index bd0e0e3..10bf8d6 100644 --- a/librustzcash-wrapper/src/lib.rs +++ b/librustzcash-wrapper/src/lib.rs @@ -95,6 +95,20 @@ impl ToHaskell for RawData { //} //} +#[derive(BorshSerialize, BorshDeserialize)] +pub struct HrawTx { + bytes: Vec, + s: bool, + o: bool +} + +impl ToHaskell for HrawTx { + fn to_haskell(&self, writer: &mut W, _tag: PhantomData) -> Result<()> { + self.serialize(writer)?; + Ok(()) + } +} + #[derive(BorshSerialize, BorshDeserialize)] pub struct HshieldedOutput { cv: Vec, @@ -112,6 +126,20 @@ impl FromHaskell for HshieldedOutput { } } +impl ToHaskell for HshieldedOutput { + fn to_haskell(&self, writer: &mut W, _tag: PhantomData) -> Result<()> { + self.serialize(writer)?; + Ok(()) + } +} + +impl HshieldedOutput { + fn from_object(s: OutputDescription) -> Result { + let o = HshieldedOutput { cv: s.cv().to_bytes().to_vec(), cmu: s.cmu().to_bytes().to_vec(), eph_key: s.ephemeral_key().0.to_vec(), enc_txt: s.enc_ciphertext().to_vec(), out_txt: s.out_ciphertext().to_vec(), proof: s.zkproof().to_vec() }; + Ok(o) + } +} + #[derive(BorshSerialize, BorshDeserialize)] pub struct Haction { nf: Vec, @@ -403,3 +431,62 @@ pub extern "C" fn rust_wrapper_orchard_note_decrypt( } } } + +#[no_mangle] +pub extern "C" fn rust_wrapper_tx_parse( + tx: *const u8, + tx_len: usize, + out: *mut u8, + out_len: &mut usize + ){ + let tx_input: Vec = marshall_from_haskell_var(tx, tx_len, RW); + let tx_bytes: Vec = tx_input.clone(); + let mut tx_reader = Cursor::new(tx_input); + let s_o = false; + let o_a = false; + let parsed_tx = Transaction::read(&mut tx_reader, Nu5); + match parsed_tx { + Ok(t) => { + let s_bundle = t.sapling_bundle(); + let o_bundle = t.orchard_bundle(); + match s_bundle { + Some(sb) => { + let s_o = true; + match o_bundle { + Some(ob) => { + let o_a = true; + let x = HrawTx { bytes: tx_bytes, s: s_o, o: o_a}; + marshall_to_haskell_var(&x, out, out_len, RW); + }, + None => { + let o_a = false; + let x = HrawTx { bytes: tx_bytes, s: s_o, o: o_a}; + marshall_to_haskell_var(&x, out, out_len, RW); + } + } + + }, + None => { + let s_o = false; + match o_bundle { + Some(ob) => { + let o_a = true; + let x = HrawTx { bytes: tx_bytes, s: s_o, o: o_a}; + marshall_to_haskell_var(&x, out, out_len, RW); + }, + None => { + let o_a = false; + let x = HrawTx { bytes: tx_bytes, s: s_o, o: o_a}; + marshall_to_haskell_var(&x, out, out_len, RW); + } + } + } + } + + }, + Err(_e) => { + let y = HrawTx { bytes: vec![0], s: false, o: false}; + marshall_to_haskell_var(&y, out, out_len, RW); + } + } +} diff --git a/src/C/Zcash.chs b/src/C/Zcash.chs index 76e7889..9ce0ea2 100644 --- a/src/C/Zcash.chs +++ b/src/C/Zcash.chs @@ -94,3 +94,4 @@ import ZcashHaskell.Types } -> `()' #} + diff --git a/src/ZcashHaskell/Types.hs b/src/ZcashHaskell/Types.hs index 233a991..0824ea1 100644 --- a/src/ZcashHaskell/Types.hs +++ b/src/ZcashHaskell/Types.hs @@ -59,6 +59,7 @@ instance FromJSON BlockResponse where -- | Type to represent response from the `zcashd` RPC `getrawtransaction` data RawTxResponse = RawTxResponse { rt_id :: T.Text + , rt_hex :: BS.ByteString , rt_shieldedOutputs :: [ShieldedOutput] , rt_orchardActions :: [OrchardAction] } deriving (Prelude.Show, Eq) @@ -69,8 +70,9 @@ instance FromJSON RawTxResponse where i <- obj .: "txid" s <- obj .: "vShieldedOutput" o <- obj .: "orchard" + h <- obj .: "hex" a <- o .: "actions" - pure $ RawTxResponse i s a + pure $ RawTxResponse i (decodeHexText h) s a -- * Sapling -- | Type to represent a Sapling Shielded Output as provided by the @getrawtransaction@ RPC method of @zcashd@.