diff --git a/conanfile.py b/conanfile.py index 8374cb7..90644eb 100644 --- a/conanfile.py +++ b/conanfile.py @@ -40,7 +40,7 @@ class KnuthPyNative(ConanFile): # Single unified Knuth package; previously this used the standalone # c-api/@kth/stable recipe, which no longer exists. def requirements(self): - self.requires("kth/0.80.0", transitive_headers=True, transitive_libs=True) + self.requires("kth/0.81.0", transitive_headers=True, transitive_libs=True) def generate(self): # Stage headers and static libs from kth AND all its transitive diff --git a/include/kth/py-native/utils.h b/include/kth/py-native/utils.h index 4b6d842..09b1d54 100644 --- a/include/kth/py-native/utils.h +++ b/include/kth/py-native/utils.h @@ -35,6 +35,11 @@ PyObject* to_py_str(char const* str); // `py_self` via `PyCapsule_SetContext`. void kth_py_native_borrowed_parent_dtor(PyObject* capsule); +// The wallet-wrapper stack-scrub helper now lives in the C-API as +// `kth_core_secure_zero` (kth/capi/secure_memory.h). Every high-level +// binding shares the same portable implementation; removing the +// py-native copy avoids drift across bindings. + #ifdef __cplusplus } //extern "C" #endif diff --git a/src/chain/double_spend_proof_spender.cpp b/src/chain/double_spend_proof_spender.cpp index ac834e0..b5fc310 100644 --- a/src/chain/double_spend_proof_spender.cpp +++ b/src/chain/double_spend_proof_spender.cpp @@ -169,7 +169,7 @@ kth_py_native_chain_double_spend_proof_spender_set_prev_outs_hash(PyObject* self } kth_hash_t value; memcpy(value.hash, value_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - kth_chain_double_spend_proof_spender_set_prev_outs_hash(self_handle, value); + kth_chain_double_spend_proof_spender_set_prev_outs_hash(self_handle, &value); Py_RETURN_NONE; } @@ -199,7 +199,7 @@ kth_py_native_chain_double_spend_proof_spender_set_sequence_hash(PyObject* self, } kth_hash_t value; memcpy(value.hash, value_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - kth_chain_double_spend_proof_spender_set_sequence_hash(self_handle, value); + kth_chain_double_spend_proof_spender_set_sequence_hash(self_handle, &value); Py_RETURN_NONE; } @@ -229,7 +229,7 @@ kth_py_native_chain_double_spend_proof_spender_set_outputs_hash(PyObject* self, } kth_hash_t value; memcpy(value.hash, value_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - kth_chain_double_spend_proof_spender_set_outputs_hash(self_handle, value); + kth_chain_double_spend_proof_spender_set_outputs_hash(self_handle, &value); Py_RETURN_NONE; } diff --git a/src/chain/get_blocks.cpp b/src/chain/get_blocks.cpp index 4e05e4c..3356440 100644 --- a/src/chain/get_blocks.cpp +++ b/src/chain/get_blocks.cpp @@ -78,7 +78,7 @@ kth_py_native_chain_get_blocks_construct(PyObject* self, PyObject* args, PyObjec } kth_hash_t stop; memcpy(stop.hash, stop_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - auto const result = kth_chain_get_blocks_construct(start_handle, stop); + auto const result = kth_chain_get_blocks_construct(start_handle, &stop); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; @@ -198,7 +198,7 @@ kth_py_native_chain_get_blocks_set_stop_hash(PyObject* self, PyObject* args, PyO } kth_hash_t value; memcpy(value.hash, value_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - kth_chain_get_blocks_set_stop_hash(self_handle, value); + kth_chain_get_blocks_set_stop_hash(self_handle, &value); Py_RETURN_NONE; } diff --git a/src/chain/get_headers.cpp b/src/chain/get_headers.cpp index 5f4964b..dbb1f8c 100644 --- a/src/chain/get_headers.cpp +++ b/src/chain/get_headers.cpp @@ -78,7 +78,7 @@ kth_py_native_chain_get_headers_construct(PyObject* self, PyObject* args, PyObje } kth_hash_t stop; memcpy(stop.hash, stop_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - auto const result = kth_chain_get_headers_construct(start_handle, stop); + auto const result = kth_chain_get_headers_construct(start_handle, &stop); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; @@ -198,7 +198,7 @@ kth_py_native_chain_get_headers_set_stop_hash(PyObject* self, PyObject* args, Py } kth_hash_t value; memcpy(value.hash, value_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - kth_chain_get_headers_set_stop_hash(self_handle, value); + kth_chain_get_headers_set_stop_hash(self_handle, &value); Py_RETURN_NONE; } diff --git a/src/chain/header.cpp b/src/chain/header.cpp index ffd721e..33a8411 100644 --- a/src/chain/header.cpp +++ b/src/chain/header.cpp @@ -87,7 +87,7 @@ kth_py_native_chain_header_construct(PyObject* self, PyObject* args, PyObject* k } kth_hash_t merkle; memcpy(merkle.hash, merkle_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - auto const result = kth_chain_header_construct((uint32_t)version, previous_block_hash, merkle, (uint32_t)timestamp, (uint32_t)bits, (uint32_t)nonce); + auto const result = kth_chain_header_construct((uint32_t)version, &previous_block_hash, &merkle, (uint32_t)timestamp, (uint32_t)bits, (uint32_t)nonce); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; @@ -194,7 +194,7 @@ kth_py_native_chain_header_set_previous_block_hash(PyObject* self, PyObject* arg } kth_hash_t value; memcpy(value.hash, value_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - kth_chain_header_set_previous_block_hash(self_handle, value); + kth_chain_header_set_previous_block_hash(self_handle, &value); Py_RETURN_NONE; } @@ -215,7 +215,7 @@ kth_py_native_chain_header_set_merkle(PyObject* self, PyObject* args, PyObject* } kth_hash_t value; memcpy(value.hash, value_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - kth_chain_header_set_merkle(self_handle, value); + kth_chain_header_set_merkle(self_handle, &value); Py_RETURN_NONE; } diff --git a/src/chain/output_point.cpp b/src/chain/output_point.cpp index 5ba7a6f..2e3af3e 100644 --- a/src/chain/output_point.cpp +++ b/src/chain/output_point.cpp @@ -76,7 +76,7 @@ kth_py_native_chain_output_point_construct_from_hash_index(PyObject* self, PyObj } kth_hash_t hash; memcpy(hash.hash, hash_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - auto const result = kth_chain_output_point_construct_from_hash_index(hash, (uint32_t)index); + auto const result = kth_chain_output_point_construct_from_hash_index(&hash, (uint32_t)index); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; @@ -245,7 +245,7 @@ kth_py_native_chain_output_point_set_hash(PyObject* self, PyObject* args, PyObje } kth_hash_t value; memcpy(value.hash, value_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - kth_chain_output_point_set_hash(self_handle, value); + kth_chain_output_point_set_hash(self_handle, &value); Py_RETURN_NONE; } diff --git a/src/chain/point.cpp b/src/chain/point.cpp index de4d610..afcd6a6 100644 --- a/src/chain/point.cpp +++ b/src/chain/point.cpp @@ -76,7 +76,7 @@ kth_py_native_chain_point_construct(PyObject* self, PyObject* args, PyObject* kw } kth_hash_t hash; memcpy(hash.hash, hash_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - auto const result = kth_chain_point_construct(hash, (uint32_t)index); + auto const result = kth_chain_point_construct(&hash, (uint32_t)index); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; @@ -224,7 +224,7 @@ kth_py_native_chain_point_set_hash(PyObject* self, PyObject* args, PyObject* kwd } kth_hash_t value; memcpy(value.hash, value_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - kth_chain_point_set_hash(self_handle, value); + kth_chain_point_set_hash(self_handle, &value); Py_RETURN_NONE; } diff --git a/src/chain/script.cpp b/src/chain/script.cpp index 393e3ae..05b1419 100644 --- a/src/chain/script.cpp +++ b/src/chain/script.cpp @@ -377,7 +377,8 @@ kth_py_native_chain_script_create_endorsement(PyObject* self, PyObject* args, Py if (tx_handle == NULL) return NULL; uint8_t* out = NULL; kth_size_t out_size = 0; - kth_error_code_t result = kth_chain_script_create_endorsement(secret, prevout_script_handle, tx_handle, (uint32_t)input_index, (uint8_t)sighash_type, (kth_script_flags_t)active_flags, (uint64_t)value, (kth_endorsement_type_t)type, &out, &out_size); + kth_error_code_t result = kth_chain_script_create_endorsement(&secret, prevout_script_handle, tx_handle, (uint32_t)input_index, (uint8_t)sighash_type, (kth_script_flags_t)active_flags, (uint64_t)value, (kth_endorsement_type_t)type, &out, &out_size); + kth_core_secure_zero((void*)&secret, sizeof(kth_hash_t)); if (result != kth_ec_success) { PyErr_Format(PyExc_RuntimeError, "kth error code %d", (int)result); return NULL; @@ -569,7 +570,7 @@ kth_py_native_chain_script_to_pay_public_key_hash_pattern(PyObject* self, PyObje } kth_shorthash_t hash; memcpy(hash.hash, hash_buf, (size_t)KTH_BITCOIN_SHORT_HASH_SIZE); - auto const result = kth_chain_script_to_pay_public_key_hash_pattern(hash); + auto const result = kth_chain_script_to_pay_public_key_hash_pattern(&hash); if (result == NULL) { PyErr_SetString(PyExc_RuntimeError, "kth: NULL list returned"); return NULL; @@ -674,7 +675,7 @@ kth_py_native_chain_script_to_pay_script_hash_pattern(PyObject* self, PyObject* } kth_shorthash_t hash; memcpy(hash.hash, hash_buf, (size_t)KTH_BITCOIN_SHORT_HASH_SIZE); - auto const result = kth_chain_script_to_pay_script_hash_pattern(hash); + auto const result = kth_chain_script_to_pay_script_hash_pattern(&hash); if (result == NULL) { PyErr_SetString(PyExc_RuntimeError, "kth: NULL list returned"); return NULL; @@ -701,7 +702,7 @@ kth_py_native_chain_script_to_pay_script_hash_32_pattern(PyObject* self, PyObjec } kth_hash_t hash; memcpy(hash.hash, hash_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - auto const result = kth_chain_script_to_pay_script_hash_32_pattern(hash); + auto const result = kth_chain_script_to_pay_script_hash_32_pattern(&hash); if (result == NULL) { PyErr_SetString(PyExc_RuntimeError, "kth: NULL list returned"); return NULL; diff --git a/src/chain/stealth_compact.cpp b/src/chain/stealth_compact.cpp index 2dbfadb..93c2220 100644 --- a/src/chain/stealth_compact.cpp +++ b/src/chain/stealth_compact.cpp @@ -77,7 +77,7 @@ kth_py_native_chain_stealth_compact_set_ephemeral_public_key_hash(PyObject* self } kth_hash_t value; memcpy(value.hash, value_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - kth_chain_stealth_compact_set_ephemeral_public_key_hash(self_handle, value); + kth_chain_stealth_compact_set_ephemeral_public_key_hash(self_handle, &value); Py_RETURN_NONE; } @@ -107,7 +107,7 @@ kth_py_native_chain_stealth_compact_set_public_key_hash(PyObject* self, PyObject } kth_shorthash_t value; memcpy(value.hash, value_buf, (size_t)KTH_BITCOIN_SHORT_HASH_SIZE); - kth_chain_stealth_compact_set_public_key_hash(self_handle, value); + kth_chain_stealth_compact_set_public_key_hash(self_handle, &value); Py_RETURN_NONE; } @@ -137,7 +137,7 @@ kth_py_native_chain_stealth_compact_set_transaction_hash(PyObject* self, PyObjec } kth_hash_t value; memcpy(value.hash, value_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - kth_chain_stealth_compact_set_transaction_hash(self_handle, value); + kth_chain_stealth_compact_set_transaction_hash(self_handle, &value); Py_RETURN_NONE; } diff --git a/src/chain/token_data.cpp b/src/chain/token_data.cpp index 58c46e9..3c03617 100644 --- a/src/chain/token_data.cpp +++ b/src/chain/token_data.cpp @@ -99,7 +99,7 @@ kth_py_native_chain_token_data_set_id(PyObject* self, PyObject* args, PyObject* } kth_hash_t value; memcpy(value.hash, value_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - kth_chain_token_data_set_id(self_handle, value); + kth_chain_token_data_set_id(self_handle, &value); Py_RETURN_NONE; } @@ -134,7 +134,7 @@ kth_py_native_chain_token_data_make_fungible(PyObject* self, PyObject* args, PyO } kth_hash_t id; memcpy(id.hash, id_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - auto const result = kth_chain_token_make_fungible(id, (uint64_t)amount); + auto const result = kth_chain_token_make_fungible(&id, (uint64_t)amount); if (result == NULL) { PyErr_SetString(PyExc_RuntimeError, "kth: NULL handle returned"); return NULL; @@ -164,7 +164,7 @@ kth_py_native_chain_token_data_make_non_fungible(PyObject* self, PyObject* args, } kth_hash_t id; memcpy(id.hash, id_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - auto const result = kth_chain_token_make_non_fungible(id, (kth_token_capability_t)capability, (uint8_t const*)commitment_buf, (kth_size_t)commitment_size); + auto const result = kth_chain_token_make_non_fungible(&id, (kth_token_capability_t)capability, (uint8_t const*)commitment_buf, (kth_size_t)commitment_size); if (result == NULL) { PyErr_SetString(PyExc_RuntimeError, "kth: NULL handle returned"); return NULL; @@ -195,7 +195,7 @@ kth_py_native_chain_token_data_make_both(PyObject* self, PyObject* args, PyObjec } kth_hash_t id; memcpy(id.hash, id_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - auto const result = kth_chain_token_make_both(id, (uint64_t)amount, (kth_token_capability_t)capability, (uint8_t const*)commitment_buf, (kth_size_t)commitment_size); + auto const result = kth_chain_token_make_both(&id, (uint64_t)amount, (kth_token_capability_t)capability, (uint8_t const*)commitment_buf, (kth_size_t)commitment_size); if (result == NULL) { PyErr_SetString(PyExc_RuntimeError, "kth: NULL handle returned"); return NULL; diff --git a/src/chain/transaction.cpp b/src/chain/transaction.cpp index 21eecae..2e5bb29 100644 --- a/src/chain/transaction.cpp +++ b/src/chain/transaction.cpp @@ -105,7 +105,7 @@ kth_py_native_chain_transaction_construct_from_transaction_hash(PyObject* self, } kth_hash_t hash; memcpy(hash.hash, hash_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - auto const result = kth_chain_transaction_construct_from_transaction_hash(x_handle, hash); + auto const result = kth_chain_transaction_construct_from_transaction_hash(x_handle, &hash); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; diff --git a/src/wallet/ec_private.cpp b/src/wallet/ec_private.cpp index 456d554..e7237c9 100644 --- a/src/wallet/ec_private.cpp +++ b/src/wallet/ec_private.cpp @@ -74,7 +74,8 @@ kth_py_native_wallet_ec_private_construct_from_wif_compressed_version(PyObject* } kth_wif_compressed_t wif_compressed; memcpy(wif_compressed.data, wif_compressed_buf, (size_t)KTH_WIF_COMPRESSED_SIZE); - auto const result = kth_wallet_ec_private_construct_from_wif_compressed_version(wif_compressed, (uint8_t)version); + auto const result = kth_wallet_ec_private_construct_from_wif_compressed_version(&wif_compressed, (uint8_t)version); + kth_core_secure_zero((void*)&wif_compressed, sizeof(kth_wif_compressed_t)); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; @@ -102,7 +103,8 @@ kth_py_native_wallet_ec_private_construct_from_wif_uncompressed_version(PyObject } kth_wif_uncompressed_t wif_uncompressed; memcpy(wif_uncompressed.data, wif_uncompressed_buf, (size_t)KTH_WIF_UNCOMPRESSED_SIZE); - auto const result = kth_wallet_ec_private_construct_from_wif_uncompressed_version(wif_uncompressed, (uint8_t)version); + auto const result = kth_wallet_ec_private_construct_from_wif_uncompressed_version(&wif_uncompressed, (uint8_t)version); + kth_core_secure_zero((void*)&wif_uncompressed, sizeof(kth_wif_uncompressed_t)); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; @@ -131,7 +133,8 @@ kth_py_native_wallet_ec_private_construct_from_secret_version_compress(PyObject* } kth_hash_t secret; memcpy(secret.hash, secret_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - auto const result = kth_wallet_ec_private_construct_from_secret_version_compress(secret, (uint16_t)version, (kth_bool_t)compress); + auto const result = kth_wallet_ec_private_construct_from_secret_version_compress(&secret, (uint16_t)version, (kth_bool_t)compress); + kth_core_secure_zero((void*)&secret, sizeof(kth_hash_t)); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; @@ -264,8 +267,10 @@ kth_py_native_wallet_ec_private_secret(PyObject* self, PyObject* py_arg0) { PyObject* py_self = py_arg0; kth_ec_private_const_t self_handle = (kth_ec_private_const_t)PyCapsule_GetPointer(py_self, KTH_PY_CAPSULE_WALLET_EC_PRIVATE); if (self_handle == NULL) return NULL; - auto const result = kth_wallet_ec_private_secret(self_handle); - return Py_BuildValue("y#", result.hash, (Py_ssize_t)KTH_BITCOIN_HASH_SIZE); + auto result = kth_wallet_ec_private_secret(self_handle); + PyObject* py_result = Py_BuildValue("y#", result.hash, (Py_ssize_t)KTH_BITCOIN_HASH_SIZE); + kth_core_secure_zero((void*)&result, sizeof(kth_hash_t)); + return py_result; } PyObject* diff --git a/src/wallet/ec_public.cpp b/src/wallet/ec_public.cpp index 54df52b..91b4b2b 100644 --- a/src/wallet/ec_public.cpp +++ b/src/wallet/ec_public.cpp @@ -112,7 +112,7 @@ kth_py_native_wallet_ec_public_construct_from_compressed_point_compress(PyObject } kth_ec_compressed_t compressed_point; memcpy(compressed_point.data, compressed_point_buf, (size_t)KTH_EC_COMPRESSED_SIZE); - auto const result = kth_wallet_ec_public_construct_from_compressed_point_compress(compressed_point, (kth_bool_t)compress); + auto const result = kth_wallet_ec_public_construct_from_compressed_point_compress(&compressed_point, (kth_bool_t)compress); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; @@ -140,7 +140,7 @@ kth_py_native_wallet_ec_public_construct_from_uncompressed_point_compress(PyObje } kth_ec_uncompressed_t uncompressed_point; memcpy(uncompressed_point.data, uncompressed_point_buf, (size_t)KTH_BITCOIN_EC_UNCOMPRESSED_SIZE); - auto const result = kth_wallet_ec_public_construct_from_uncompressed_point_compress(uncompressed_point, (kth_bool_t)compress); + auto const result = kth_wallet_ec_public_construct_from_uncompressed_point_compress(&uncompressed_point, (kth_bool_t)compress); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; diff --git a/src/wallet/hd_private.cpp b/src/wallet/hd_private.cpp index 1b5cbf3..c031650 100644 --- a/src/wallet/hd_private.cpp +++ b/src/wallet/hd_private.cpp @@ -74,7 +74,8 @@ kth_py_native_wallet_hd_private_construct_from_private_key(PyObject* self, PyObj } kth_hd_key_t private_key; memcpy(private_key.data, private_key_buf, (size_t)KTH_HD_KEY_SIZE); - auto const result = kth_wallet_hd_private_construct_from_private_key(private_key); + auto const result = kth_wallet_hd_private_construct_from_private_key(&private_key); + kth_core_secure_zero((void*)&private_key, sizeof(kth_hd_key_t)); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; @@ -102,7 +103,8 @@ kth_py_native_wallet_hd_private_construct_from_private_key_prefixes(PyObject* se } kth_hd_key_t private_key; memcpy(private_key.data, private_key_buf, (size_t)KTH_HD_KEY_SIZE); - auto const result = kth_wallet_hd_private_construct_from_private_key_prefixes(private_key, (uint64_t)prefixes); + auto const result = kth_wallet_hd_private_construct_from_private_key_prefixes(&private_key, (uint64_t)prefixes); + kth_core_secure_zero((void*)&private_key, sizeof(kth_hd_key_t)); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; @@ -130,7 +132,8 @@ kth_py_native_wallet_hd_private_construct_from_private_key_prefix(PyObject* self } kth_hd_key_t private_key; memcpy(private_key.data, private_key_buf, (size_t)KTH_HD_KEY_SIZE); - auto const result = kth_wallet_hd_private_construct_from_private_key_prefix(private_key, (uint32_t)prefix); + auto const result = kth_wallet_hd_private_construct_from_private_key_prefix(&private_key, (uint32_t)prefix); + kth_core_secure_zero((void*)&private_key, sizeof(kth_hd_key_t)); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; @@ -293,8 +296,10 @@ kth_py_native_wallet_hd_private_secret(PyObject* self, PyObject* py_arg0) { PyObject* py_self = py_arg0; kth_hd_private_const_t self_handle = (kth_hd_private_const_t)PyCapsule_GetPointer(py_self, KTH_PY_CAPSULE_WALLET_HD_PRIVATE); if (self_handle == NULL) return NULL; - auto const result = kth_wallet_hd_private_secret(self_handle); - return Py_BuildValue("y#", result.hash, (Py_ssize_t)KTH_BITCOIN_HASH_SIZE); + auto result = kth_wallet_hd_private_secret(self_handle); + PyObject* py_result = Py_BuildValue("y#", result.hash, (Py_ssize_t)KTH_BITCOIN_HASH_SIZE); + kth_core_secure_zero((void*)&result, sizeof(kth_hash_t)); + return py_result; } PyObject* @@ -302,8 +307,10 @@ kth_py_native_wallet_hd_private_to_hd_key(PyObject* self, PyObject* py_arg0) { PyObject* py_self = py_arg0; kth_hd_private_const_t self_handle = (kth_hd_private_const_t)PyCapsule_GetPointer(py_self, KTH_PY_CAPSULE_WALLET_HD_PRIVATE); if (self_handle == NULL) return NULL; - auto const result = kth_wallet_hd_private_to_hd_key(self_handle); - return Py_BuildValue("y#", result.data, (Py_ssize_t)KTH_HD_KEY_SIZE); + auto result = kth_wallet_hd_private_to_hd_key(self_handle); + PyObject* py_result = Py_BuildValue("y#", result.data, (Py_ssize_t)KTH_HD_KEY_SIZE); + kth_core_secure_zero((void*)&result, sizeof(kth_hd_key_t)); + return py_result; } PyObject* @@ -384,8 +391,10 @@ kth_py_native_wallet_hd_private_chain_code(PyObject* self, PyObject* py_arg0) { PyObject* py_self = py_arg0; kth_hd_private_const_t self_handle = (kth_hd_private_const_t)PyCapsule_GetPointer(py_self, KTH_PY_CAPSULE_WALLET_HD_PRIVATE); if (self_handle == NULL) return NULL; - auto const result = kth_wallet_hd_private_chain_code(self_handle); - return Py_BuildValue("y#", result.hash, (Py_ssize_t)KTH_BITCOIN_HASH_SIZE); + auto result = kth_wallet_hd_private_chain_code(self_handle); + PyObject* py_result = Py_BuildValue("y#", result.hash, (Py_ssize_t)KTH_BITCOIN_HASH_SIZE); + kth_core_secure_zero((void*)&result, sizeof(kth_hash_t)); + return py_result; } PyObject* @@ -402,8 +411,10 @@ kth_py_native_wallet_hd_private_point(PyObject* self, PyObject* py_arg0) { PyObject* py_self = py_arg0; kth_hd_private_const_t self_handle = (kth_hd_private_const_t)PyCapsule_GetPointer(py_self, KTH_PY_CAPSULE_WALLET_HD_PRIVATE); if (self_handle == NULL) return NULL; - auto const result = kth_wallet_hd_private_point(self_handle); - return Py_BuildValue("y#", result.data, (Py_ssize_t)KTH_EC_COMPRESSED_SIZE); + auto result = kth_wallet_hd_private_point(self_handle); + PyObject* py_result = Py_BuildValue("y#", result.data, (Py_ssize_t)KTH_EC_COMPRESSED_SIZE); + kth_core_secure_zero((void*)&result, sizeof(kth_ec_compressed_t)); + return py_result; } PyMethodDef kth_py_native_wallet_hd_private_methods[] = { diff --git a/src/wallet/hd_public.cpp b/src/wallet/hd_public.cpp index d65f0d2..7014bf7 100644 --- a/src/wallet/hd_public.cpp +++ b/src/wallet/hd_public.cpp @@ -52,7 +52,7 @@ kth_py_native_wallet_hd_public_construct_from_public_key(PyObject* self, PyObjec } kth_hd_key_t public_key; memcpy(public_key.data, public_key_buf, (size_t)KTH_HD_KEY_SIZE); - auto const result = kth_wallet_hd_public_construct_from_public_key(public_key); + auto const result = kth_wallet_hd_public_construct_from_public_key(&public_key); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; @@ -80,7 +80,7 @@ kth_py_native_wallet_hd_public_construct_from_public_key_prefix(PyObject* self, } kth_hd_key_t public_key; memcpy(public_key.data, public_key_buf, (size_t)KTH_HD_KEY_SIZE); - auto const result = kth_wallet_hd_public_construct_from_public_key_prefix(public_key, (uint32_t)prefix); + auto const result = kth_wallet_hd_public_construct_from_public_key_prefix(&public_key, (uint32_t)prefix); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; diff --git a/src/wallet/payment_address.cpp b/src/wallet/payment_address.cpp index 00602bb..520f718 100644 --- a/src/wallet/payment_address.cpp +++ b/src/wallet/payment_address.cpp @@ -52,7 +52,7 @@ kth_py_native_wallet_payment_address_construct_from_decoded(PyObject* self, PyOb } kth_payment_t decoded; memcpy(decoded.hash, decoded_buf, (size_t)KTH_BITCOIN_PAYMENT_SIZE); - auto const result = kth_wallet_payment_address_construct_from_decoded(decoded); + auto const result = kth_wallet_payment_address_construct_from_decoded(&decoded); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; @@ -139,7 +139,7 @@ kth_py_native_wallet_payment_address_construct_from_short_hash_version(PyObject* } kth_shorthash_t short_hash; memcpy(short_hash.hash, short_hash_buf, (size_t)KTH_BITCOIN_SHORT_HASH_SIZE); - auto const result = kth_wallet_payment_address_construct_from_short_hash_version(short_hash, (uint8_t)version); + auto const result = kth_wallet_payment_address_construct_from_short_hash_version(&short_hash, (uint8_t)version); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; @@ -167,7 +167,7 @@ kth_py_native_wallet_payment_address_construct_from_hash_version(PyObject* self, } kth_hash_t hash; memcpy(hash.hash, hash_buf, (size_t)KTH_BITCOIN_HASH_SIZE); - auto const result = kth_wallet_payment_address_construct_from_hash_version(hash, (uint8_t)version); + auto const result = kth_wallet_payment_address_construct_from_hash_version(&hash, (uint8_t)version); if (result == NULL) { PyErr_SetString(PyExc_MemoryError, "kth: allocation failed"); return NULL; diff --git a/src/wallet/wallet_data.cpp b/src/wallet/wallet_data.cpp index 777060d..c402026 100644 --- a/src/wallet/wallet_data.cpp +++ b/src/wallet/wallet_data.cpp @@ -130,8 +130,10 @@ kth_py_native_wallet_wallet_data_encrypted_seed(PyObject* self, PyObject* py_arg PyObject* py_self = py_arg0; kth_wallet_data_const_t self_handle = (kth_wallet_data_const_t)PyCapsule_GetPointer(py_self, KTH_PY_CAPSULE_WALLET_WALLET_DATA); if (self_handle == NULL) return NULL; - auto const result = kth_wallet_wallet_data_encrypted_seed(self_handle); - return Py_BuildValue("y#", result.hash, (Py_ssize_t)KTH_BITCOIN_ENCRYPTED_SEED_SIZE); + auto result = kth_wallet_wallet_data_encrypted_seed(self_handle); + PyObject* py_result = Py_BuildValue("y#", result.hash, (Py_ssize_t)KTH_BITCOIN_ENCRYPTED_SEED_SIZE); + kth_core_secure_zero((void*)&result, sizeof(kth_encrypted_seed_t)); + return py_result; } PyObject* @@ -151,7 +153,8 @@ kth_py_native_wallet_wallet_data_set_encrypted_seed(PyObject* self, PyObject* ar } kth_encrypted_seed_t value; memcpy(value.hash, value_buf, (size_t)KTH_BITCOIN_ENCRYPTED_SEED_SIZE); - kth_wallet_wallet_data_set_encrypted_seed(self_handle, value); + kth_wallet_wallet_data_set_encrypted_seed(self_handle, &value); + kth_core_secure_zero((void*)&value, sizeof(kth_encrypted_seed_t)); Py_RETURN_NONE; }