Skip to content

Commit

Permalink
feat: add P2WSH tests (#262)
Browse files Browse the repository at this point in the history
<!-- enter the gh issue after hash -->

- [x] issue #250 
- [x] follows contribution
[guide](https://github.com/keep-starknet-strange/shinigami/blob/main/CONTRIBUTING.md)
- [x] code change includes tests

<!-- PR description below -->
Add tests for P2WSH:
- transaction validation is OK
- script execution failed 
- wrong hash for witness script

---------

Co-authored-by: Brandon Roberts <[email protected]>
  • Loading branch information
ptisserand and b-j-roberts authored Oct 20, 2024
1 parent 20915c8 commit 0bf0bef
Show file tree
Hide file tree
Showing 2 changed files with 168 additions and 0 deletions.
1 change: 1 addition & 0 deletions packages/tests/src/lib.cairo
Original file line number Diff line number Diff line change
Expand Up @@ -19,5 +19,6 @@ pub mod tests {
mod test_transactions;
mod test_p2pk;
mod test_p2pkh;
mod test_p2wsh;
mod test_p2ms;
}
167 changes: 167 additions & 0 deletions packages/tests/src/tests/test_p2wsh.cairo
Original file line number Diff line number Diff line change
@@ -0,0 +1,167 @@
use shinigami_engine::transaction::EngineInternalTransactionTrait;
use shinigami_engine::flags::ScriptFlags;
use shinigami_engine::errors::Error;

use crate::validate;
use crate::utxo::UTXO;
use shinigami_utils::bytecode::hex_to_bytecode;

// P2WSH with P2MS
// https://learnmeabitcoin.com/explorer/tx/b38a88b073743bcc84170071cff4b68dec6fb5dc0bc8ffcb3d4ca632c2c78255
#[ignore]
#[test]
fn test_learnmeabitcoin_usage() {
let prevout_pk_script =
"0x002065f91a53cb7120057db3d378bd0f7d944167d43a7dcbff15d6afc4823f1d3ed3";
let prev_out = UTXO {
amount: 53519352, pubkey_script: hex_to_bytecode(@prevout_pk_script), block_height: 630000,
};

let raw_transaction_hex =
"0x010000000001016542b657eea04a75b1582969b5b532b3110b392b4b553297435a11b064e2eb460100000000ffffffff02c454fd000000000017a9145e7be6ec3e2382c669aaf3c71da1056f47b9024d875b07330200000000220020ea166bf0492c6f908e45404932e0f39c0571a71007c22b872548cd20f19a92f504004730440220415899bbee08e42376d06e8f86c92b4987613c2816352fe09cd1479fd639f18c02200db57f508f69e266d76c23891708158bda18690c165a41b0aa88303b97609f780147304402203973de2303e8787767090dd25c8a4dc97ce1aa7eb4c0962f13952ed4e856ff8e02203f1bb425def789eea8be46407d10b3c8730407176aef4dc2c29865eb5e5542bf0169522103848e308569b644372a5eb26665f1a8c34ca393c130b376db2fae75c43500013c2103cec1ee615c17e06d4f4b0a08617dffb8e568936bdff18fb057832a58ad4d1b752103eed7ae80c34d70f5ba93f93965f69f3c691da0f4607f242f4fd6c7a48789233e53aeee9c0900";
let raw_transaction = hex_to_bytecode(@raw_transaction_hex);
let transaction = EngineInternalTransactionTrait::deserialize(raw_transaction);

let utxo_hints = array![prev_out];
let flags: u32 = ScriptFlags::ScriptVerifyWitness.into() | ScriptFlags::ScriptBip16.into();
let res = validate::validate_transaction(@transaction, flags, utxo_hints);
assert!(res.is_ok(), "Transaction validation failed");
}

// https://learnmeabitcoin.com/explorer/tx/b38a88b073743bcc84170071cff4b68dec6fb5dc0bc8ffcb3d4ca632c2c78255
#[test]
fn test_learnmeabitcoin_usage_wrong_hash_in_pubkey_script() {
// original hash script
// "0x002065f91a53cb7120057db3d378bd0f7d944167d43a7dcbff15d6afc4823f1d3ed3";
let prevout_pk_script =
"0x0020f5f91a53cb7120057db3d378bd0f7d944167d43a7dcbff15d6afc4823f1d3ed3";
let prev_out = UTXO {
amount: 53519352, pubkey_script: hex_to_bytecode(@prevout_pk_script), block_height: 630000,
};

let raw_transaction_hex =
"0x010000000001016542b657eea04a75b1582969b5b532b3110b392b4b553297435a11b064e2eb460100000000ffffffff02c454fd000000000017a9145e7be6ec3e2382c669aaf3c71da1056f47b9024d875b07330200000000220020ea166bf0492c6f908e45404932e0f39c0571a71007c22b872548cd20f19a92f504004730440220415899bbee08e42376d06e8f86c92b4987613c2816352fe09cd1479fd639f18c02200db57f508f69e266d76c23891708158bda18690c165a41b0aa88303b97609f780147304402203973de2303e8787767090dd25c8a4dc97ce1aa7eb4c0962f13952ed4e856ff8e02203f1bb425def789eea8be46407d10b3c8730407176aef4dc2c29865eb5e5542bf0169522103848e308569b644372a5eb26665f1a8c34ca393c130b376db2fae75c43500013c2103cec1ee615c17e06d4f4b0a08617dffb8e568936bdff18fb057832a58ad4d1b752103eed7ae80c34d70f5ba93f93965f69f3c691da0f4607f242f4fd6c7a48789233e53aeee9c0900";
let raw_transaction = hex_to_bytecode(@raw_transaction_hex);
let transaction = EngineInternalTransactionTrait::deserialize(raw_transaction);

let utxo_hints = array![prev_out];
let flags: u32 = ScriptFlags::ScriptVerifyWitness.into() | ScriptFlags::ScriptBip16.into();
let res = validate::validate_transaction(@transaction, flags, utxo_hints);
assert!(res.is_err(), "Transaction validation should fail");
assert!(res.unwrap_err() == Error::WITNESS_PROGRAM_MISMATCH, "Wrong error");
}

// https://learnmeabitcoin.com/explorer/tx/b38a88b073743bcc84170071cff4b68dec6fb5dc0bc8ffcb3d4ca632c2c78255
#[test]
fn test_learnmeabitcoin_usage_different_witness_script_from_hash() {
let prevout_pk_script =
"0x002065f91a53cb7120057db3d378bd0f7d944167d43a7dcbff15d6afc4823f1d3ed3";
let prev_out = UTXO {
amount: 53519352, pubkey_script: hex_to_bytecode(@prevout_pk_script), block_height: 630000,
};

// original witness script
// 522103848e308569b644372a5eb26665f1a8c34ca393c130b376db2fae75c43500013c2103cec1ee615c17e06d4f4b0a08617dffb8e568936bdff18fb057832a58ad4d1b752103eed7ae80c34d70f5ba93f93965f69f3c691da0f4607f242f4fd6c7a48789233e53ae
// modificed witness script (first public key is different)
// 522103f48e308569b644372a5eb26665f1a8c34ca393c130b376db2fae75c43500013c2103cec1ee615c17e06d4f4b0a08617dffb8e568936bdff18fb057832a58ad4d1b752103eed7ae80c34d70f5ba93f93965f69f3c691da0f4607f242f4fd6c7a48789233e53ae
let raw_transaction_hex =
"0x010000000001016542b657eea04a75b1582969b5b532b3110b392b4b553297435a11b064e2eb460100000000ffffffff02c454fd000000000017a9145e7be6ec3e2382c669aaf3c71da1056f47b9024d875b07330200000000220020ea166bf0492c6f908e45404932e0f39c0571a71007c22b872548cd20f19a92f504004730440220415899bbee08e42376d06e8f86c92b4987613c2816352fe09cd1479fd639f18c02200db57f508f69e266d76c23891708158bda18690c165a41b0aa88303b97609f780147304402203973de2303e8787767090dd25c8a4dc97ce1aa7eb4c0962f13952ed4e856ff8e02203f1bb425def789eea8be46407d10b3c8730407176aef4dc2c29865eb5e5542bf0169522103f48e308569b644372a5eb26665f1a8c34ca393c130b376db2fae75c43500013c2103cec1ee615c17e06d4f4b0a08617dffb8e568936bdff18fb057832a58ad4d1b752103eed7ae80c34d70f5ba93f93965f69f3c691da0f4607f242f4fd6c7a48789233e53aeee9c0900";
let raw_transaction = hex_to_bytecode(@raw_transaction_hex);
let transaction = EngineInternalTransactionTrait::deserialize(raw_transaction);

let utxo_hints = array![prev_out];
let flags: u32 = ScriptFlags::ScriptVerifyWitness.into() | ScriptFlags::ScriptBip16.into();
let res = validate::validate_transaction(@transaction, flags, utxo_hints);
assert!(res.is_err(), "Transaction validation should fail");
assert!(res.unwrap_err() == Error::WITNESS_PROGRAM_MISMATCH, "Wrong error");
}

// P2WSH with custom script
// https://learnmeabitcoin.com/explorer/tx/64f427122f7951687aea608b5474509a30616d4e5773a83bc1ed8b8271ad1991
#[test]
fn test_custom_hash_puzzle() {
let prevout_pk_script =
"0x0020ee4fd29ce2f9ca8411778f8e94687d5e75ec3e86cc530ca9ad1787e5208cc996";
let prev_out = UTXO {
amount: 30000, pubkey_script: hex_to_bytecode(@prevout_pk_script), block_height: 802087
};

let raw_transaction_hex =
"0x020000000001018a39b5cdd48c7d45a31a89cd675a95f5de78aebeeda1e55ac35d7110c3bacfc60000000000ffffffff01204e0000000000001976a914ee63c8c790952de677d1f8019c9474d84098d6e188ac0202123423aa20a23421f2ba909c885a3077bb6f8eb4312487797693bbcfe7e311f797e3c5b8fa8700000000";
let raw_transaction = hex_to_bytecode(@raw_transaction_hex);
let transaction = EngineInternalTransactionTrait::deserialize(raw_transaction);

let utxo_hints = array![prev_out];
let flags: u32 = ScriptFlags::ScriptVerifyWitness.into() | ScriptFlags::ScriptBip16.into();
let res = validate::validate_transaction(@transaction, flags, utxo_hints);
assert!(res.is_ok(), "Transaction validation failed");
}

// https://learnmeabitcoin.com/explorer/tx/64f427122f7951687aea608b5474509a30616d4e5773a83bc1ed8b8271ad1991
#[test]
fn test_custom_hash_puzzle_invalid_unlock_code() {
let prevout_pk_script =
"0x0020ee4fd29ce2f9ca8411778f8e94687d5e75ec3e86cc530ca9ad1787e5208cc996";
let prev_out = UTXO {
amount: 30000, pubkey_script: hex_to_bytecode(@prevout_pk_script), block_height: 802087
};

// replace unlock code 1234 by 2345
let raw_transaction_hex =
"0x020000000001018a39b5cdd48c7d45a31a89cd675a95f5de78aebeeda1e55ac35d7110c3bacfc60000000000ffffffff01204e0000000000001976a914ee63c8c790952de677d1f8019c9474d84098d6e188ac0202234523aa20a23421f2ba909c885a3077bb6f8eb4312487797693bbcfe7e311f797e3c5b8fa8700000000";
let raw_transaction = hex_to_bytecode(@raw_transaction_hex);
let transaction = EngineInternalTransactionTrait::deserialize(raw_transaction);

let utxo_hints = array![prev_out];
let flags: u32 = ScriptFlags::ScriptVerifyWitness.into() | ScriptFlags::ScriptBip16.into();
let res = validate::validate_transaction(@transaction, flags, utxo_hints);
assert!(res.is_err(), "Transaction validation should fail");
assert!(res.unwrap_err() == Error::SCRIPT_FAILED, "Wrong error");
}

// https://learnmeabitcoin.com/explorer/tx/64f427122f7951687aea608b5474509a30616d4e5773a83bc1ed8b8271ad1991
#[test]
fn test_custom_hash_puzzle_wrong_hash_script_in_pubkey_script() {
// original hash script "0x0020ee4fd29ce2f9ca8411778f8e94687d5e75ec3e86cc530ca9ad1787e5208cc996"
let prevout_pk_script =
"0x0020fe4fd29ce2f9ca8411778f8e94687d5e75ec3e86cc530ca9ad1787e5208cc996";
let prev_out = UTXO {
amount: 30000, pubkey_script: hex_to_bytecode(@prevout_pk_script), block_height: 802087
};

let raw_transaction_hex =
"0x020000000001018a39b5cdd48c7d45a31a89cd675a95f5de78aebeeda1e55ac35d7110c3bacfc60000000000ffffffff01204e0000000000001976a914ee63c8c790952de677d1f8019c9474d84098d6e188ac0202123423aa20a23421f2ba909c885a3077bb6f8eb4312487797693bbcfe7e311f797e3c5b8fa8700000000";
let raw_transaction = hex_to_bytecode(@raw_transaction_hex);
let transaction = EngineInternalTransactionTrait::deserialize(raw_transaction);

let utxo_hints = array![prev_out];
let flags: u32 = ScriptFlags::ScriptVerifyWitness.into() | ScriptFlags::ScriptBip16.into();
let res = validate::validate_transaction(@transaction, flags, utxo_hints);
assert!(res.is_err(), "Transaction validation should fail");
assert!(res.unwrap_err() == Error::WITNESS_PROGRAM_MISMATCH, "Wrong error");
}

// https://learnmeabitcoin.com/explorer/tx/64f427122f7951687aea608b5474509a30616d4e5773a83bc1ed8b8271ad1991
#[test]
fn test_custom_hash_puzzle_different_witness_script_from_hash() {
let prevout_pk_script =
"0x0020ee4fd29ce2f9ca8411778f8e94687d5e75ec3e86cc530ca9ad1787e5208cc996";
let prev_out = UTXO {
amount: 30000, pubkey_script: hex_to_bytecode(@prevout_pk_script), block_height: 802087
};

// original witness script
// aa20a23421f2ba909c885a3077bb6f8eb4312487797693bbcfe7e311f797e3c5b8fa87
// modified witness script (hash is different)
// aa20b23421f2ba909c885a3077bb6f8eb4312487797693bbcfe7e311f797e3c5b8fa87
let raw_transaction_hex =
"0x020000000001018a39b5cdd48c7d45a31a89cd675a95f5de78aebeeda1e55ac35d7110c3bacfc60000000000ffffffff01204e0000000000001976a914ee63c8c790952de677d1f8019c9474d84098d6e188ac0202123423ba20a23421f2ba909c885a3077bb6f8eb4312487797693bbcfe7e311f797e3c5b8fa8700000000";
let raw_transaction = hex_to_bytecode(@raw_transaction_hex);
let transaction = EngineInternalTransactionTrait::deserialize(raw_transaction);

let utxo_hints = array![prev_out];
let flags: u32 = ScriptFlags::ScriptVerifyWitness.into() | ScriptFlags::ScriptBip16.into();
let res = validate::validate_transaction(@transaction, flags, utxo_hints);
assert!(res.is_err(), "Transaction validation should fail");
assert!(res.unwrap_err() == Error::WITNESS_PROGRAM_MISMATCH, "Wrong error");
}

0 comments on commit 0bf0bef

Please sign in to comment.