Add support for zcash_script_transparent_output_address() (#29)

* add support for zcash_script_transparent_output_address()

* try using x86_64-pc-windows-gnu on windows

* update zcash to version which returns address type
This commit is contained in:
Conrado Gouvea 2022-03-03 10:52:35 -03:00 committed by GitHub
parent 270d32d192
commit b7801e4027
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 163 additions and 6 deletions

View File

@ -69,11 +69,25 @@ jobs:
echo "C:\Program Files\LLVM\bin" | Out-File -FilePath $env:GITHUB_PATH -Encoding utf8 -Append
echo "LIBCLANG_PATH=C:\Program Files\LLVM\bin" | Out-File -FilePath $env:GITHUB_ENV -Encoding utf8 -Append
- uses: actions-rs/toolchain@v1
if: matrix.os == 'windows-latest'
with:
target: x86_64-pc-windows-gnu
toolchain: stable
profile: minimal
override: true
- uses: actions-rs/toolchain@v1
if: matrix.os != 'windows-latest'
with:
toolchain: stable
profile: minimal
override: true
- uses: actions-rs/cargo@v1
if: matrix.os == 'windows-latest'
with:
command: test
args: --target x86_64-pc-windows-gnu
- uses: actions-rs/cargo@v1
if: matrix.os != 'windows-latest'
with:
command: test

1
.gitmodules vendored
View File

@ -1,3 +1,4 @@
[submodule "depend/zcash"]
path = depend/zcash
url = https://github.com/ZcashFoundation/zcashd.git
branch = get-address-from-output

@ -1 +1 @@
Subproject commit 43b12f1aa5a06f4f2abfd12a5b68205b1e22eab8
Subproject commit e4ce035e830c12ef1045ca3b95db47d46e39e15c

View File

@ -21,6 +21,8 @@ mod tests {
lazy_static::lazy_static! {
pub static ref SCRIPT_PUBKEY: Vec<u8> = <Vec<u8>>::from_hex("76a914f47cac1e6fec195c055994e8064ffccce0044dd788ac").unwrap();
pub static ref SCRIPT_TX: Vec<u8> = <Vec<u8>>::from_hex("0400008085202f8901fcaf44919d4a17f6181a02a7ebe0420be6f7dad1ef86755b81d5a9567456653c010000006a473044022035224ed7276e61affd53315eca059c92876bc2df61d84277cafd7af61d4dbf4002203ed72ea497a9f6b38eb29df08e830d99e32377edb8a574b8a289024f0241d7c40121031f54b095eae066d96b2557c1f99e40e967978a5fd117465dbec0986ca74201a6feffffff020050d6dc0100000017a9141b8a9bda4b62cd0d0582b55455d0778c86f8628f870d03c812030000001976a914e4ff5512ffafe9287992a1cd177ca6e408e0300388ac62070d0095070d000000000000000000000000").expect("Block bytes are in valid hex representation");
// Created by changing the byte before the hash inside the lock script, in each output, to 0xff
pub static ref SCRIPT_TX_INVALID: Vec<u8> = <Vec<u8>>::from_hex("0400008085202f8901fcaf44919d4a17f6181a02a7ebe0420be6f7dad1ef86755b81d5a9567456653c010000006a473044022035224ed7276e61affd53315eca059c92876bc2df61d84277cafd7af61d4dbf4002203ed72ea497a9f6b38eb29df08e830d99e32377edb8a574b8a289024f0241d7c40121031f54b095eae066d96b2557c1f99e40e967978a5fd117465dbec0986ca74201a6feffffff020050d6dc0100000017a9ff1b8a9bda4b62cd0d0582b55455d0778c86f8628f870d03c812030000001976a9ffe4ff5512ffafe9287992a1cd177ca6e408e0300388ac62070d0095070d000000000000000000000000").expect("Block bytes are in valid hex representation");
}
pub fn verify_script(
@ -98,7 +100,7 @@ mod tests {
}
#[test]
fn it_works() {
fn verify_script_works() {
let coin = i64::pow(10, 8);
let script_pub_key = &*SCRIPT_PUBKEY;
let amount = 212 * coin;
@ -111,7 +113,7 @@ mod tests {
}
#[test]
fn it_works_precomputed() {
fn verify_script_works_precomputed() {
let coin = i64::pow(10, 8);
let script_pub_key = &*SCRIPT_PUBKEY;
let amount = 212 * coin;
@ -124,7 +126,7 @@ mod tests {
}
#[test]
fn it_doesnt_work() {
fn verify_script_doesnt_work() {
let coin = i64::pow(10, 8);
let script_pub_key = &*SCRIPT_PUBKEY;
let amount = 212 * coin;
@ -137,7 +139,7 @@ mod tests {
}
#[test]
fn it_doesnt_work_precomputed() {
fn verify_script_doesnt_work_precomputed() {
let coin = i64::pow(10, 8);
let script_pub_key = &*SCRIPT_PUBKEY;
let amount = 212 * coin;
@ -148,4 +150,144 @@ mod tests {
verify_script_precompute(script_pub_key, amount, tx_to, nIn, flags, branch_id).unwrap_err();
}
pub fn transparent_output_address(
tx_to: &[u8],
nOut: u32,
) -> Result<(super::zcash_script_uint160_t, super::zcash_script_type_t), zcash_script_error_t>
{
let tx_to_ptr = tx_to.as_ptr();
let tx_to_len = tx_to.len();
let mut addrType = 0;
let mut err = 0;
let address = unsafe {
super::zcash_script_transparent_output_address(
tx_to_ptr,
tx_to_len as u32,
nOut,
&mut addrType,
&mut err,
)
};
if err == 0 {
Ok((address, addrType))
} else {
Err(err)
}
}
pub fn transparent_output_address_precomputed(
tx_to: &[u8],
nOut: u32,
) -> Result<(super::zcash_script_uint160_t, super::zcash_script_type_t), zcash_script_error_t>
{
let tx_to_ptr = tx_to.as_ptr();
let tx_to_len = tx_to.len();
let mut addrType = 0;
let mut err = 0;
let precomputed =
unsafe { super::zcash_script_new_precomputed_tx(tx_to_ptr, tx_to_len as _, &mut err) };
let address = unsafe {
super::zcash_script_transparent_output_address_precomputed(
precomputed,
nOut,
&mut addrType,
&mut err,
)
};
if err == 0 {
Ok((address, addrType))
} else {
Err(err)
}
}
#[test]
fn transparent_output_address_works() {
let tx_to = &*SCRIPT_TX;
// Expected values manually extracted from the transaction
// (parsed with zebra-chain, then manually extracted from lock_script)
let (address, addrType) = transparent_output_address(tx_to, 0).unwrap();
let expected_address = hex::decode("1b8a9bda4b62cd0d0582b55455d0778c86f8628f").unwrap();
assert_eq!(Vec::<u8>::from(address.value), expected_address);
assert_eq!(addrType, super::zcash_script_type_t_zcash_script_TYPE_P2SH);
let (address, addrType) = transparent_output_address(tx_to, 1).unwrap();
let expected_address = hex::decode("e4ff5512ffafe9287992a1cd177ca6e408e03003").unwrap();
assert_eq!(Vec::<u8>::from(address.value), expected_address);
assert_eq!(addrType, super::zcash_script_type_t_zcash_script_TYPE_P2PKH);
}
#[test]
fn transparent_output_address_works_precomputed() {
let tx_to = &*SCRIPT_TX;
// Expected values manually extracted from the transaction
// (parsed with zebra-chain, then manually extracted from lock_script)
let (address, addrType) = transparent_output_address_precomputed(tx_to, 0).unwrap();
let expected_address = hex::decode("1b8a9bda4b62cd0d0582b55455d0778c86f8628f").unwrap();
assert_eq!(Vec::<u8>::from(address.value), expected_address);
assert_eq!(addrType, super::zcash_script_type_t_zcash_script_TYPE_P2SH);
let (address, addrType) = transparent_output_address_precomputed(tx_to, 1).unwrap();
let expected_address = hex::decode("e4ff5512ffafe9287992a1cd177ca6e408e03003").unwrap();
assert_eq!(Vec::<u8>::from(address.value), expected_address);
assert_eq!(addrType, super::zcash_script_type_t_zcash_script_TYPE_P2PKH);
}
#[test]
fn transparent_output_address_doesnt_work() {
let tx_to = &*SCRIPT_TX;
let ret = transparent_output_address(tx_to, 2).unwrap_err();
assert_eq!(ret, super::zcash_script_error_t_zcash_script_ERR_TX_INDEX);
let tx_to = &*SCRIPT_TX_INVALID;
let ret = transparent_output_address(tx_to, 0).unwrap_err();
assert_eq!(
ret,
super::zcash_script_error_t_zcash_script_ERR_TX_INVALID_SCRIPT
);
let ret = transparent_output_address(tx_to, 1).unwrap_err();
assert_eq!(
ret,
super::zcash_script_error_t_zcash_script_ERR_TX_INVALID_SCRIPT
);
}
#[test]
fn transparent_output_address_precomputed_doesnt_work() {
let tx_to = &*SCRIPT_TX;
let ret = transparent_output_address_precomputed(tx_to, 2).unwrap_err();
assert_eq!(ret, super::zcash_script_error_t_zcash_script_ERR_TX_INDEX);
let tx_to = &*SCRIPT_TX_INVALID;
let ret = transparent_output_address_precomputed(tx_to, 0).unwrap_err();
assert_eq!(
ret,
super::zcash_script_error_t_zcash_script_ERR_TX_INVALID_SCRIPT
);
let ret = transparent_output_address_precomputed(tx_to, 1).unwrap_err();
assert_eq!(
ret,
super::zcash_script_error_t_zcash_script_ERR_TX_INVALID_SCRIPT
);
}
}

View File

@ -1 +1 @@
include!("../depend/zcash/src/rust/src/orchard_ffi/mod.rs");
include!("../depend/zcash/src/rust/src/orchard_ffi.rs");