diff --git a/c/auth.c b/c/auth.c index ba35332..410cd38 100644 --- a/c/auth.c +++ b/c/auth.c @@ -93,7 +93,8 @@ int md_string(const mbedtls_md_info_t *md_info, const uint8_t *buf, size_t n, static int _recover_secp256k1_pubkey(const uint8_t *sig, size_t sig_len, const uint8_t *msg, size_t msg_len, uint8_t *out_pubkey, - size_t *out_pubkey_size, int recid, bool compressed) { + size_t *out_pubkey_size, int recid, + bool compressed) { int ret = 0; if (sig_len != SECP256K1_SIGNATURE_SIZE) { @@ -208,18 +209,23 @@ static int _recover_secp256k1_pubkey_btc(const uint8_t *sig, size_t sig_len, if (v_type == BTCVType_P2PKHUncompressed) { *out_pubkey_size = UNCOMPRESSED_SECP256K1_PUBKEY_SIZE; flag = SECP256K1_EC_UNCOMPRESSED; - if (secp256k1_ec_pubkey_serialize(&context, out_pubkey, out_pubkey_size, &pubkey, flag) != 1) { + if (secp256k1_ec_pubkey_serialize(&context, out_pubkey, out_pubkey_size, + &pubkey, flag) != 1) { return ERROR_WRONG_STATE; } - } else if (v_type == BTCVType_P2PKHCompressed || v_type == BTCVType_SegwitBech32 || v_type == BTCVType_SegwitP2SH) { + } else if (v_type == BTCVType_P2PKHCompressed || + v_type == BTCVType_SegwitBech32 || + v_type == BTCVType_SegwitP2SH) { *out_pubkey_size = SECP256K1_PUBKEY_SIZE; flag = SECP256K1_EC_COMPRESSED; - if (secp256k1_ec_pubkey_serialize(&context, out_pubkey, out_pubkey_size, &pubkey, flag) != 1) { + if (secp256k1_ec_pubkey_serialize(&context, out_pubkey, out_pubkey_size, + &pubkey, flag) != 1) { return ERROR_WRONG_STATE; } if (v_type == BTCVType_SegwitP2SH) { - const mbedtls_md_info_t *md_info = mbedtls_md_info_from_type(MBEDTLS_MD_SHA256); + const mbedtls_md_info_t *md_info = + mbedtls_md_info_from_type(MBEDTLS_MD_SHA256); unsigned char temp[SHA256_SIZE]; int err = md_string(md_info, out_pubkey, *out_pubkey_size, temp); if (err) return err; @@ -250,7 +256,8 @@ int validate_signature_ckb(void *prefilled_data, const uint8_t *sig, uint8_t out_pubkey[SECP256K1_PUBKEY_SIZE]; size_t out_pubkey_size = SECP256K1_PUBKEY_SIZE; - ret = _recover_secp256k1_pubkey(sig, sig_len, msg, msg_len, out_pubkey, &out_pubkey_size, sig[RECID_INDEX], true); + ret = _recover_secp256k1_pubkey(sig, sig_len, msg, msg_len, out_pubkey, + &out_pubkey_size, sig[RECID_INDEX], true); if (ret != 0) return ret; blake2b_state ctx; @@ -292,7 +299,8 @@ int validate_signature_eth(void *prefilled_data, const uint8_t *sig, return ERROR_INVALID_ARG; } - ret = _recover_secp256k1_pubkey(sig, sig_len, msg, msg_len, out_pubkey, &out_pubkey_size, recid, false); + ret = _recover_secp256k1_pubkey(sig, sig_len, msg, msg_len, out_pubkey, + &out_pubkey_size, recid, false); if (ret != 0) return ret; // here are the 2 differences than validate_signature_secp256k1 @@ -307,7 +315,8 @@ int validate_signature_eth(void *prefilled_data, const uint8_t *sig, return ret; } -int validate_signature_eos(void *prefilled_data, const uint8_t *sig, size_t sig_len, const uint8_t *msg, size_t msg_len, +int validate_signature_eos(void *prefilled_data, const uint8_t *sig, + size_t sig_len, const uint8_t *msg, size_t msg_len, uint8_t *output, size_t *output_len) { int err = 0; if (*output_len < AUTH160_SIZE) { @@ -315,7 +324,8 @@ int validate_signature_eos(void *prefilled_data, const uint8_t *sig, size_t sig_ } uint8_t out_pubkey[UNCOMPRESSED_SECP256K1_PUBKEY_SIZE]; size_t out_pubkey_size = UNCOMPRESSED_SECP256K1_PUBKEY_SIZE; - err = _recover_secp256k1_pubkey_btc(sig, sig_len, msg, msg_len, out_pubkey, &out_pubkey_size); + err = _recover_secp256k1_pubkey_btc(sig, sig_len, msg, msg_len, out_pubkey, + &out_pubkey_size); CHECK(err); blake2b_state ctx; @@ -476,10 +486,11 @@ size_t write_varint(uint8_t *dest, size_t n) { } // Read uint16_t from varint buffer -// See https://github.com/solana-labs/solana/blob/3b0b0ba07d345ef86e270187a1a7d99bd0da7f4c/sdk/program/src/short_vec.rs#L120-L148 +// See +// https://github.com/solana-labs/solana/blob/3b0b0ba07d345ef86e270187a1a7d99bd0da7f4c/sdk/program/src/short_vec.rs#L120-L148 int read_varint_u16(uint8_t **src, size_t src_size, uint16_t *result) { size_t maximum_full_bytes = sizeof(uint16_t) * 8 / 7; - + uint8_t *ptr = *src; uint16_t acc = 0; for (size_t i = 0; i <= maximum_full_bytes; i++) { @@ -487,9 +498,11 @@ int read_varint_u16(uint8_t **src, size_t src_size, uint16_t *result) { return -1; } uint8_t current_value = *ptr; - size_t bits = (i < maximum_full_bytes) ? 7 : sizeof(uint16_t)*8 - maximum_full_bytes*7; + size_t bits = (i < maximum_full_bytes) + ? 7 + : sizeof(uint16_t) * 8 - maximum_full_bytes * 7; uint8_t maximum_value = (1 << bits) - 1; - acc += ((uint16_t)(current_value & maximum_value) << (i*7)); + acc += ((uint16_t)(current_value & maximum_value) << (i * 7)); ptr = ptr + 1; if (current_value < 0x80 && i < maximum_full_bytes) { *src = ptr; @@ -619,24 +632,37 @@ int validate_signature_monero(void *prefilled_data, const uint8_t *sig, return err; } -int validate_solana_signed_message(const uint8_t *signed_msg, size_t signed_msg_len, const uint8_t *pub_key, - const uint8_t *blockhash) { +int validate_solana_signed_message(const uint8_t *signed_msg, + size_t signed_msg_len, + const uint8_t *pub_key, + const uint8_t *blockhash) { int err = 0; // Official solana transaction structure documentation. - // [Transactions | Solana Docs](https://docs.solana.com/developing/programming-model/transactions) + // [Transactions | Solana + // Docs](https://docs.solana.com/developing/programming-model/transactions) // See also // https://github.com/solana-labs/solana/blob/3b0b0ba07d345ef86e270187a1a7d99bd0da7f4c/sdk/program/src/message/legacy.rs#L90-L129 - CHECK2(signed_msg_len > SOLANA_MESSAGE_HEADER_SIZE + SOLANA_BLOCKHASH_SIZE, ERROR_INVALID_ARG); + CHECK2(signed_msg_len > SOLANA_MESSAGE_HEADER_SIZE + SOLANA_BLOCKHASH_SIZE, + ERROR_INVALID_ARG); uint8_t num_signers = *signed_msg; uint16_t num_keys = 0; uint8_t *pub_key_ptr = (uint8_t *)(signed_msg + SOLANA_MESSAGE_HEADER_SIZE); - CHECK2(read_varint_u16(&pub_key_ptr, signed_msg_len - SOLANA_MESSAGE_HEADER_SIZE, &num_keys) == 0, ERROR_INVALID_ARG); - size_t pub_key_size = (pub_key_ptr - (uint8_t *)(signed_msg + SOLANA_MESSAGE_HEADER_SIZE)) + SOLANA_PUBKEY_SIZE * num_keys; - CHECK2(signed_msg_len > SOLANA_MESSAGE_HEADER_SIZE + pub_key_size + SOLANA_BLOCKHASH_SIZE, ERROR_INVALID_ARG); - const uint8_t *blockhash_ptr = signed_msg + SOLANA_MESSAGE_HEADER_SIZE + pub_key_size; - CHECK2(memcmp(blockhash_ptr, blockhash, SOLANA_BLOCKHASH_SIZE) == 0, ERROR_INVALID_ARG); - for (uint8_t i=0; i SOLANA_MESSAGE_HEADER_SIZE + pub_key_size + + SOLANA_BLOCKHASH_SIZE, + ERROR_INVALID_ARG); + const uint8_t *blockhash_ptr = + signed_msg + SOLANA_MESSAGE_HEADER_SIZE + pub_key_size; + CHECK2(memcmp(blockhash_ptr, blockhash, SOLANA_BLOCKHASH_SIZE) == 0, + ERROR_INVALID_ARG); + for (uint8_t i = 0; i < num_signers; i++) { + uint8_t *tmp_pub_key = pub_key_ptr + i * SOLANA_PUBKEY_SIZE; if (memcmp(tmp_pub_key, pub_key, SOLANA_PUBKEY_SIZE) == 0) { return 0; } @@ -657,14 +683,17 @@ int validate_signature_solana(void *prefilled_data, const uint8_t *sig, sig_len = (size_t)sig[0] | ((size_t)sig[1] << 8); CHECK2(sig_len <= SOLANA_UNWRAPPED_SIGNATURE_SIZE, ERROR_INVALID_ARG); const uint8_t *signature_ptr = sig + 2; - const uint8_t *pub_key_ptr = signature_ptr + SOLANA_SIGNATURE_SIZE; - const uint8_t *signed_msg_ptr = signature_ptr + SOLANA_SIGNATURE_SIZE + SOLANA_PUBKEY_SIZE; - size_t signed_msg_len = sig_len - SOLANA_SIGNATURE_SIZE - SOLANA_PUBKEY_SIZE; - - CHECK(validate_solana_signed_message(signed_msg_ptr, signed_msg_len, pub_key_ptr, msg)); + const uint8_t *pub_key_ptr = signature_ptr + SOLANA_SIGNATURE_SIZE; + const uint8_t *signed_msg_ptr = + signature_ptr + SOLANA_SIGNATURE_SIZE + SOLANA_PUBKEY_SIZE; + size_t signed_msg_len = + sig_len - SOLANA_SIGNATURE_SIZE - SOLANA_PUBKEY_SIZE; + CHECK(validate_solana_signed_message(signed_msg_ptr, signed_msg_len, + pub_key_ptr, msg)); - int suc = ed25519_verify(signature_ptr, signed_msg_ptr, signed_msg_len, pub_key_ptr); + int suc = ed25519_verify(signature_ptr, signed_msg_ptr, signed_msg_len, + pub_key_ptr); CHECK2(suc == 1, ERROR_WRONG_STATE); blake2b_state ctx; @@ -679,49 +708,51 @@ int validate_signature_solana(void *prefilled_data, const uint8_t *sig, return err; } - // Ton uses ed25519 to sign messages. The message to be signed is // message = utf8_encode("ton-proof-item-v2/") ++ // Address ++ // AppDomain ++ // Timestamp ++ // Payload -// signature = Ed25519Sign(privkey, sha256(0xffff ++ utf8_encode("ton-connect") ++ sha256(message))) -// where -// Prefix = 18 bytes "ton-proof-item-v2/" without trailing null -// Address = Big endian work chain (uint32) + address (32 bytes) -// AppDomain = Little endian domain length (uint32) + domain (string without trailling null) -// Timestamp = Epoch seconds Little endian uint64 -// Payload = Arbitrary bytes, we use block hash here -// See ton official document on ton-proof https://docs.ton.org/develop/dapps/ton-connect/sign -int get_toncoin_message(const uint8_t *signed_msg, size_t signed_msg_len, const uint8_t *blockhash, uint8_t output[32]) { +// signature = Ed25519Sign(privkey, sha256(0xffff ++ utf8_encode("ton-connect") +// ++ sha256(message))) where Prefix = 18 bytes "ton-proof-item-v2/" without +// trailing null Address = Big endian work chain (uint32) + address (32 bytes) +// AppDomain = Little endian domain length (uint32) + domain (string without +// trailling null) Timestamp = Epoch seconds Little endian uint64 Payload = +// Arbitrary bytes, we use block hash here See ton official document on +// ton-proof https://docs.ton.org/develop/dapps/ton-connect/sign +int get_toncoin_message(const uint8_t *signed_msg, size_t signed_msg_len, + const uint8_t *blockhash, uint8_t output[32]) { int err = 0; uint8_t preimage1[TONCOIN_MAX_PREIMAGE_SIZE]; uint8_t preimage2[TONCOIN_PREIMAGE2_SIZE]; - int preimage1_size = signed_msg_len + TONCOIN_MESSAGE_PREFIX_SIZE + TONCOIN_BLOCKHASH_SIZE; + int preimage1_size = + signed_msg_len + TONCOIN_MESSAGE_PREFIX_SIZE + TONCOIN_BLOCKHASH_SIZE; CHECK2(preimage1_size <= TONCOIN_MAX_PREIMAGE_SIZE, ERROR_INVALID_ARG); const mbedtls_md_info_t *md_info = mbedtls_md_info_from_type(MBEDTLS_MD_SHA256); memcpy(preimage1, "ton-proof-item-v2/", TONCOIN_MESSAGE_PREFIX_SIZE); - memcpy(preimage1+TONCOIN_MESSAGE_PREFIX_SIZE, signed_msg, signed_msg_len); - memcpy(preimage1+TONCOIN_MESSAGE_PREFIX_SIZE+signed_msg_len, blockhash, TONCOIN_BLOCKHASH_SIZE); + memcpy(preimage1 + TONCOIN_MESSAGE_PREFIX_SIZE, signed_msg, signed_msg_len); + memcpy(preimage1 + TONCOIN_MESSAGE_PREFIX_SIZE + signed_msg_len, blockhash, + TONCOIN_BLOCKHASH_SIZE); preimage2[0] = 0xff; preimage2[1] = 0xff; - memcpy(preimage2+2, "ton-connect", TONCOIN_MESSAGE_PREFIX2_SIZE); + memcpy(preimage2 + 2, "ton-connect", TONCOIN_MESSAGE_PREFIX2_SIZE); - CHECK(md_string(md_info, preimage1, preimage1_size, preimage2+2+TONCOIN_MESSAGE_PREFIX2_SIZE)); + CHECK(md_string(md_info, preimage1, preimage1_size, + preimage2 + 2 + TONCOIN_MESSAGE_PREFIX2_SIZE)); CHECK(md_string(md_info, preimage2, TONCOIN_PREIMAGE2_SIZE, output)); exit: return err; } int validate_signature_toncoin(void *prefilled_data, const uint8_t *sig, - size_t sig_len, const uint8_t *msg, - size_t msg_len, uint8_t *output, - size_t *output_len) { + size_t sig_len, const uint8_t *msg, + size_t msg_len, uint8_t *output, + size_t *output_len) { int err = 0; CHECK2(sig_len == TONCOIN_WRAPPED_SIGNATURE_SIZE, ERROR_INVALID_ARG); @@ -729,14 +760,17 @@ int validate_signature_toncoin(void *prefilled_data, const uint8_t *sig, sig_len = (size_t)sig[0] | ((size_t)sig[1] << 8); CHECK2(sig_len <= TONCOIN_UNWRAPPED_SIGNATURE_SIZE, ERROR_INVALID_ARG); const uint8_t *signature_ptr = sig + 2; - const uint8_t *pub_key_ptr = signature_ptr + TONCOIN_SIGNATURE_SIZE; - const uint8_t *signed_msg_ptr = signature_ptr + TONCOIN_SIGNATURE_SIZE + TONCOIN_PUBKEY_SIZE; - size_t signed_msg_len = sig_len - TONCOIN_SIGNATURE_SIZE - TONCOIN_PUBKEY_SIZE; + const uint8_t *pub_key_ptr = signature_ptr + TONCOIN_SIGNATURE_SIZE; + const uint8_t *signed_msg_ptr = + signature_ptr + TONCOIN_SIGNATURE_SIZE + TONCOIN_PUBKEY_SIZE; + size_t signed_msg_len = + sig_len - TONCOIN_SIGNATURE_SIZE - TONCOIN_PUBKEY_SIZE; uint8_t message[32]; CHECK(get_toncoin_message(signed_msg_ptr, signed_msg_len, msg, message)); - int suc = ed25519_verify(signature_ptr, message, sizeof(message), pub_key_ptr); + int suc = + ed25519_verify(signature_ptr, message, sizeof(message), pub_key_ptr); CHECK2(suc == 1, ERROR_WRONG_STATE); blake2b_state ctx; @@ -753,7 +787,6 @@ int validate_signature_toncoin(void *prefilled_data, const uint8_t *sig, return err; } - int convert_copy(const uint8_t *msg, size_t msg_len, uint8_t *new_msg, size_t new_msg_len) { if (msg_len != new_msg_len || msg_len != BLAKE2B_BLOCK_SIZE) @@ -1189,5 +1222,3 @@ int main(int argc, char *argv[]) { return ckb_auth_validate_with_func(argc, argv, *ckb_auth_validate); } - - diff --git a/c/auth_libecc.c b/c/auth_libecc.c index 3cdfee8..aaf0c51 100644 --- a/c/auth_libecc.c +++ b/c/auth_libecc.c @@ -16,11 +16,40 @@ #undef CKB_SUCCESS // clang-format on - int validate_signature_secp256r1(void *prefilled_data, const uint8_t *sig, - size_t sig_len, const uint8_t *msg, - size_t msg_len, uint8_t *output, - size_t *output_len) { + size_t sig_len, const uint8_t *msg, + size_t msg_len, uint8_t *output, + size_t *output_len) { + int err = 0; + + if (*output_len < AUTH160_SIZE) { + return ERROR_INVALID_ARG; + } + CHECK2(msg_len == BLAKE2B_BLOCK_SIZE, ERROR_INVALID_ARG); + CHECK2(sig_len == SECP256R1_DATA_SIZE, ERROR_INVALID_ARG); + const uint8_t *pub_key_ptr = sig; + const uint8_t *signature_ptr = pub_key_ptr + SECP256R1_PUBKEY_SIZE; + + CHECK(secp256r1_verify_signature(signature_ptr, SECP256R1_SIGNATURE_SIZE, + pub_key_ptr, SECP256R1_PUBKEY_SIZE, msg, + msg_len)); + + blake2b_state ctx; + uint8_t pubkey_hash[BLAKE2B_BLOCK_SIZE] = {0}; + blake2b_init(&ctx, BLAKE2B_BLOCK_SIZE); + blake2b_update(&ctx, pub_key_ptr, SECP256R1_PUBKEY_SIZE); + blake2b_final(&ctx, pubkey_hash, sizeof(pubkey_hash)); + + memcpy(output, pubkey_hash, AUTH160_SIZE); + *output_len = AUTH160_SIZE; +exit: + return err; +} + +int validate_signature_secp256r1_raw(void *prefilled_data, const uint8_t *sig, + size_t sig_len, const uint8_t *msg, + size_t msg_len, uint8_t *output, + size_t *output_len) { int err = 0; if (*output_len < AUTH160_SIZE) { @@ -29,9 +58,11 @@ int validate_signature_secp256r1(void *prefilled_data, const uint8_t *sig, CHECK2(msg_len == BLAKE2B_BLOCK_SIZE, ERROR_INVALID_ARG); CHECK2(sig_len == SECP256R1_DATA_SIZE, ERROR_INVALID_ARG); const uint8_t *pub_key_ptr = sig; - const uint8_t *signature_ptr = pub_key_ptr + SECP256R1_PUBKEY_SIZE; + const uint8_t *signature_ptr = pub_key_ptr + SECP256R1_PUBKEY_SIZE; - CHECK(secp256r1_verify_signature(signature_ptr, SECP256R1_SIGNATURE_SIZE, pub_key_ptr, SECP256R1_PUBKEY_SIZE, msg, msg_len )); + CHECK(secp256r1_raw_verify_signature(signature_ptr, + SECP256R1_SIGNATURE_SIZE, pub_key_ptr, + SECP256R1_PUBKEY_SIZE, msg, msg_len)); blake2b_state ctx; uint8_t pubkey_hash[BLAKE2B_BLOCK_SIZE] = {0}; @@ -75,7 +106,6 @@ static int verify(uint8_t *pubkey_hash, const uint8_t *sig, uint32_t sig_len, return err; } - // dynamic linking entry __attribute__((visibility("default"))) int ckb_auth_validate( uint8_t auth_algorithm_id, const uint8_t *signature, @@ -91,6 +121,11 @@ __attribute__((visibility("default"))) int ckb_auth_validate( err = verify(pubkey_hash, signature, signature_size, message, message_size, validate_signature_secp256r1, convert_copy); CHECK(err); + } else if (auth_algorithm_id == AuthAlgorithmIdSecp256R1Raw) { + err = verify(pubkey_hash, signature, signature_size, message, + message_size, validate_signature_secp256r1_raw, + convert_copy); + CHECK(err); } else { CHECK2(false, ERROR_NOT_IMPLEMENTED); } diff --git a/c/ckb_auth.h b/c/ckb_auth.h index 20ad52e..2221c59 100644 --- a/c/ckb_auth.h +++ b/c/ckb_auth.h @@ -1,13 +1,13 @@ #ifndef CKB_PRODUCTION_SCRIPTS_CKB_AUTH_H_ #define CKB_PRODUCTION_SCRIPTS_CKB_AUTH_H_ +#include +#include + #include "ckb_consts.h" #include "ckb_dlfcn.h" #include "ckb_hex.h" -#include -#include - // secp256k1 also defines this macros #undef CHECK2 #undef CHECK @@ -101,6 +101,7 @@ enum AuthAlgorithmIdType { AuthAlgorithmIdRipple = 14, AuthAlgorithmIdSecp256R1 = 15, AuthAlgorithmIdToncoin = 16, + AuthAlgorithmIdSecp256R1Raw = 17, AuthAlgorithmIdOwnerLock = 0xFC, }; @@ -224,22 +225,21 @@ int ckb_auth(CkbEntryType *entry, CkbAuthType *id, const uint8_t *signature, uint32_t bin2hex_output_len = 0; if (ckb_bin2hex(&id->algorithm_id, 1, algorithm_id_str, - sizeof(algorithm_id_str), &bin2hex_output_len, - true)) { + sizeof(algorithm_id_str), &bin2hex_output_len, true)) { return CKB_INVALID_DATA; } if (ckb_bin2hex(signature, signature_size, signature_str, - sizeof(signature_str), &bin2hex_output_len, true)) { + sizeof(signature_str), &bin2hex_output_len, true)) { return CKB_INVALID_DATA; } - if (ckb_bin2hex(message32, BLAKE2B_BLOCK_SIZE, message_str, sizeof(message_str), - &bin2hex_output_len, true)) { + if (ckb_bin2hex(message32, BLAKE2B_BLOCK_SIZE, message_str, + sizeof(message_str), &bin2hex_output_len, true)) { return CKB_INVALID_DATA; } if (ckb_bin2hex(id->content, AUTH160_SIZE, pubkey_hash_str, - sizeof(pubkey_hash_str), &bin2hex_output_len, true)) { + sizeof(pubkey_hash_str), &bin2hex_output_len, true)) { return CKB_INVALID_DATA; } @@ -278,7 +278,7 @@ int setup_elf() { uint64_t *phoff = (uint64_t *)OFFSETOF(Elf64_Ehdr, e_phoff); uint16_t *phnum = (uint16_t *)OFFSETOF(Elf64_Ehdr, e_phnum); Elf64_Phdr *program_headers = (Elf64_Phdr *)(*phoff); - + for (int i = 0; i < *phnum; i++) { Elf64_Phdr *program_header = &program_headers[i]; if (program_header->p_type == PT_DYNAMIC) { @@ -357,7 +357,8 @@ int setup_elf() { #endif } -static int ckb_auth_validate_with_func(int argc, char *argv[], ckb_auth_validate_t validate_func) { +static int ckb_auth_validate_with_func(int argc, char *argv[], + ckb_auth_validate_t validate_func) { int err = 0; if (argc != 4) { @@ -413,7 +414,7 @@ static int ckb_auth_validate_with_func(int argc, char *argv[], ckb_auth_validate ERROR_SPAWN_INVALID_PUBKEY); err = validate_func(algorithm_id, signature, signature_len, message, - message_len, pubkey_hash, pubkey_hash_len); + message_len, pubkey_hash, pubkey_hash_len); CHECK(err); exit: diff --git a/c/secp256r1.h b/c/secp256r1.h index f72a91d..73b037e 100644 --- a/c/secp256r1.h +++ b/c/secp256r1.h @@ -10,109 +10,125 @@ static const char *ec_name = "SECP256R1"; static const char *ec_sig_name = "ECDSA"; -static const char *hash_algorithm = "SHA256"; +static const char *sha256_hash_algorithm_name = "SHA256"; +static const char *copy256_hash_algorithm_name = "COPY256"; const uint32_t projective_buffer_size = 96; const uint32_t affine_buffer_size = 64; int get_random(unsigned char *buf, u16 len) { - for (int i = 0; i < len; i++) { - buf[i] = 0; - } - return 0; + for (int i = 0; i < len; i++) { + buf[i] = 0; + } + return 0; } static int string_to_params(const char *ec_name, const char *ec_sig_name, ec_sig_alg_type *sig_type, const ec_str_params **ec_str_p, const char *hash_name, hash_alg_type *hash_type) { - const ec_str_params *curve_params; - const ec_sig_mapping *sm; - const hash_mapping *hm; - uint32_t curve_name_len; - - if (sig_type != NULL) { - sm = get_sig_by_name(ec_sig_name); - if (!sm) { - return ERROR_INVALID_ARG; + const ec_str_params *curve_params; + const ec_sig_mapping *sm; + const hash_mapping *hm; + uint32_t curve_name_len; + + if (sig_type != NULL) { + sm = get_sig_by_name(ec_sig_name); + if (!sm) { + return ERROR_INVALID_ARG; + } + *sig_type = sm->type; } - *sig_type = sm->type; - } - if (ec_str_p != NULL) { - curve_name_len = local_strlen((const char *)ec_name) + 1; - if (curve_name_len > 255) { - return ERROR_INVALID_ARG; - } - curve_params = ec_get_curve_params_by_name((const uint8_t *)ec_name, - (uint8_t)curve_name_len); - if (!curve_params) { - return ERROR_INVALID_ARG; + if (ec_str_p != NULL) { + curve_name_len = local_strlen((const char *)ec_name) + 1; + if (curve_name_len > 255) { + return ERROR_INVALID_ARG; + } + curve_params = ec_get_curve_params_by_name((const uint8_t *)ec_name, + (uint8_t)curve_name_len); + if (!curve_params) { + return ERROR_INVALID_ARG; + } + *ec_str_p = curve_params; } - *ec_str_p = curve_params; - } - if (hash_type != NULL) { - hm = get_hash_by_name(hash_name); - if (!hm) { - return ERROR_INVALID_ARG; + if (hash_type != NULL) { + hm = get_hash_by_name(hash_name); + if (!hm) { + return ERROR_INVALID_ARG; + } + *hash_type = hm->type; } - *hash_type = hm->type; - } - return 0; + return 0; } int convert_aff_buf_to_prj_buf(const uint8_t *aff_buf, uint32_t aff_buf_len, uint8_t *prj_buf, uint32_t prj_buf_len) { - static const uint8_t z_buf[] = { - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01}; - if (aff_buf_len != affine_buffer_size || - prj_buf_len != projective_buffer_size) { - return ERROR_INVALID_ARG; - } - memcpy(prj_buf, aff_buf, aff_buf_len); - memcpy(prj_buf + aff_buf_len, z_buf, sizeof(z_buf)); - return 0; + static const uint8_t z_buf[] = { + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01}; + if (aff_buf_len != affine_buffer_size || + prj_buf_len != projective_buffer_size) { + return ERROR_INVALID_ARG; + } + memcpy(prj_buf, aff_buf, aff_buf_len); + memcpy(prj_buf + aff_buf_len, z_buf, sizeof(z_buf)); + return 0; +} + +int do_secp256r1_verify_signature(const uint8_t *sig, uint8_t siglen, + const uint8_t *pk, uint32_t pklen, + const uint8_t *m, uint32_t mlen, + const char *hash_algorithm) { + const ec_str_params *ec_str_p; + ec_sig_alg_type sig_type; + hash_alg_type hash_type; + ec_pub_key pub_key; + ec_params params; + int ret; + + uint8_t pj_pk_buf[projective_buffer_size]; + ret = convert_aff_buf_to_prj_buf(pk, pklen, pj_pk_buf, sizeof(pj_pk_buf)); + if (ret) { + return ERROR_INVALID_ARG; + } + + MUST_HAVE(ec_name != NULL); + + ret = string_to_params(ec_name, ec_sig_name, &sig_type, &ec_str_p, + hash_algorithm, &hash_type); + if (ret) { + return ERROR_INVALID_ARG; + } + import_params(¶ms, ec_str_p); + + ret = ec_pub_key_import_from_buf(&pub_key, ¶ms, pj_pk_buf, + sizeof(pj_pk_buf), sig_type); + if (ret) { + return ERROR_INVALID_ARG; + } + + ret = ec_verify(sig, siglen, &pub_key, m, mlen, sig_type, hash_type); + if (ret) { + return ERROR_SPAWN_INVALID_SIG; + } + + return 0; } int secp256r1_verify_signature(const uint8_t *sig, uint8_t siglen, const uint8_t *pk, uint32_t pklen, const uint8_t *m, uint32_t mlen) { - const ec_str_params *ec_str_p; - ec_sig_alg_type sig_type; - hash_alg_type hash_type; - ec_pub_key pub_key; - ec_params params; - int ret; - - uint8_t pj_pk_buf[projective_buffer_size]; - ret = convert_aff_buf_to_prj_buf(pk, pklen, pj_pk_buf, sizeof(pj_pk_buf)); - if (ret) { - return ERROR_INVALID_ARG; - } - - MUST_HAVE(ec_name != NULL); - - ret = string_to_params(ec_name, ec_sig_name, &sig_type, &ec_str_p, - hash_algorithm, &hash_type); - if (ret) { - return ERROR_INVALID_ARG; - } - import_params(¶ms, ec_str_p); - - ret = ec_pub_key_import_from_buf(&pub_key, ¶ms, pj_pk_buf, - sizeof(pj_pk_buf), sig_type); - if (ret) { - return ERROR_INVALID_ARG; - } - - ret = ec_verify(sig, siglen, &pub_key, m, mlen, sig_type, hash_type); - if (ret) { - return ERROR_SPAWN_INVALID_SIG; - } - - return 0; + return do_secp256r1_verify_signature(sig, siglen, pk, pklen, m, mlen, + sha256_hash_algorithm_name); +} + +int secp256r1_raw_verify_signature(const uint8_t *sig, uint8_t siglen, + const uint8_t *pk, uint32_t pklen, + const uint8_t *m, uint32_t mlen) { + return do_secp256r1_verify_signature(sig, siglen, pk, pklen, m, mlen, + copy256_hash_algorithm_name); } diff --git a/ckb-auth-rs/src/lib.rs b/ckb-auth-rs/src/lib.rs index ac26db7..cba96b7 100644 --- a/ckb-auth-rs/src/lib.rs +++ b/ckb-auth-rs/src/lib.rs @@ -44,6 +44,8 @@ pub enum AuthAlgorithmIdType { Solana = 13, Ripple = 14, Secp256r1 = 15, + Toncoin = 16, + Secp256r1Raw = 17, OwnerLock = 0xFC, } @@ -57,7 +59,7 @@ impl TryFrom for AuthAlgorithmIdType { type Error = CkbAuthError; fn try_from(value: u8) -> Result { if (value >= AuthAlgorithmIdType::Ckb.into() - && value <= AuthAlgorithmIdType::Secp256r1.into()) + && value <= AuthAlgorithmIdType::Secp256r1Raw.into()) || value == AuthAlgorithmIdType::OwnerLock.into() { Ok(unsafe { transmute(value) }) @@ -95,7 +97,7 @@ impl From for CkbAuthError { } } -#[derive(Clone)] +#[derive(Clone, Copy, Debug)] pub enum EntryCategoryType { Exec = 0, #[cfg(feature = "enable-dynamic-library")] diff --git a/deps/libecc b/deps/libecc index e60c718..d5e4789 160000 --- a/deps/libecc +++ b/deps/libecc @@ -1 +1 @@ -Subproject commit e60c718a6f37abf0622cd25ced998691790d0ea9 +Subproject commit d5e47897c65c573ac2f232292f601377275ae02b diff --git a/docs/secp256r1.md b/docs/secp256r1.md index 4b474b2..0c9ffc1 100644 --- a/docs/secp256r1.md +++ b/docs/secp256r1.md @@ -87,7 +87,7 @@ by concatenating the R and S value in the last two lines. Running the following command would save such signature to the file `signature.raw` ``` -openssl asn1parse -dump -inform DER -in signature | awk -F: '/33 prim: INTEGER/ {print $NF}' | xxd -r -p > signature.raw +openssl asn1parse -dump -inform DER -in signature | awk -F: '/prim:\s*INTEGER/ {print $NF}' | xxd -r -p > signature.raw ``` The final signature field of the ckb transaction should be this public key concatenated with the above signature. diff --git a/docs/secp256r1raw.md b/docs/secp256r1raw.md new file mode 100644 index 0000000..368d10f --- /dev/null +++ b/docs/secp256r1raw.md @@ -0,0 +1,20 @@ +# verify secp256r1 signature signed to a raw message (without hashing) + +This is the raw message version of [./secp256r1.md](./secp256r1.md), i.e. +we are using the message as it is without calculating the sha256 digest of the message first. + +We can sign the message as shown in [./secp256r1.md](./secp256r1.md), and then +calculate the message digest, and put the digest in place of message, and the +create transactions as in [./secp256r1.md](./secp256r1.md). + +For example, given the same message `29553f9e37fa16e45f1d3e616ac5366f6afd9936477f2d6fc870f49bdf540157` +as in [./secp256r1.md](./secp256r1.md). + +All we need to do is change the algorithm ID to 17 and the replace `29553f9e37fa16e45f1d3e616ac5366f6afd9936477f2d6fc870f49bdf540157` +with `4fb7632dfcd5ed376b5dc1e454846628b3cd95b10a8a79d6b6fea56c633ec490`, the sha256 hash +obtained by the following command. + +``` +xxd -r -p <<< 29553f9e37fa16e45f1d3e616ac5366f6afd9936477f2d6fc870f49bdf540157 | sha256sum +4fb7632dfcd5ed376b5dc1e454846628b3cd95b10a8a79d6b6fea56c633ec490 - +``` diff --git a/tests/auth-c-tests/src/lib.rs b/tests/auth-c-tests/src/lib.rs index 565c419..5066b32 100644 --- a/tests/auth-c-tests/src/lib.rs +++ b/tests/auth-c-tests/src/lib.rs @@ -19,7 +19,7 @@ use ckb_types::{ use dyn_clone::{clone_trait_object, DynClone}; use hex; use log::{Metadata, Record}; -use rand::{distributions::Standard, thread_rng, Rng}; +use rand::{distributions::Standard, Rng}; use secp256k1; use serde::{Deserialize, Serialize}; use sha3::{Digest, Keccak256}; @@ -39,7 +39,6 @@ type BtcNetwork = bitcoin::Network; pub const MAX_CYCLES: u64 = std::u64::MAX; pub const SIGNATURE_SIZE: usize = 65; -pub const RNG_SEED: u64 = 42; pub const SOLANA_MAXIMUM_UNWRAPPED_SIGNATURE_SIZE: usize = 510; pub const SOLANA_MAXIMUM_WRAPPED_SIGNATURE_SIZE: usize = SOLANA_MAXIMUM_UNWRAPPED_SIGNATURE_SIZE + 2; @@ -97,6 +96,32 @@ pub mod auth_program { } } +pub use rng::get_rng; +pub mod rng { + use rand::{thread_rng, RngCore}; + use ref_thread_local::ref_thread_local; + use ref_thread_local::RefThreadLocal; + + ref_thread_local! { + static managed RNG_SEED: Option = None; + } + + pub fn get_rng() -> rand::rngs::SmallRng { + let seed = RNG_SEED.borrow().unwrap_or(thread_rng().next_u64()); + rand::SeedableRng::seed_from_u64(seed) + } + + pub fn set_seed(seed: u64) { + let mut p = RNG_SEED.borrow_mut(); + *p = Some(seed); + } + + pub fn clear_seed() { + let mut p = RNG_SEED.borrow_mut(); + *p = None; + } +} + fn _dbg_print_mem(data: &Vec, name: &str) { print!("rustdbg {}: (size:{})\n", name, data.len()); let mut count = 0; @@ -274,7 +299,7 @@ pub fn sign_tx_by_input_group( begin_index: usize, len: usize, ) -> TransactionView { - let mut rng = thread_rng(); + let mut rng = get_rng(); let tx_hash = tx.hash(); let mut signed_witnesses: Vec = tx .inputs() @@ -454,7 +479,7 @@ pub fn gen_tx_with_pub_key_hash( let lock_args = gen_args_with_pub_key_hash(&config, hash); // Note that we use deterministic here to ensure the same transaction structure // is generated. - let mut rng: rand::rngs::SmallRng = rand::SeedableRng::seed_from_u64(RNG_SEED); + let mut rng = get_rng(); gen_tx_with_grouped_args( dummy, @@ -467,7 +492,7 @@ pub fn gen_tx_with_pub_key_hash( pub fn gen_tx(dummy: &mut DummyDataLoader, config: &TestConfig) -> TransactionView { let lock_args = gen_args(&config); - let mut rng = thread_rng(); + let mut rng = get_rng(); gen_tx_with_grouped_args( dummy, vec![(lock_args, config.sign_size as usize)], @@ -544,7 +569,7 @@ pub enum TestConfigIncorrectSing { Smaller, } -#[derive(PartialEq, Eq)] +#[derive(PartialEq, Eq, Clone, Debug)] pub enum TestConfigAuthLockType { C, Rust, @@ -625,7 +650,7 @@ pub fn do_gen_args(config: &TestConfig, pub_key_hash: Option>) -> Bytes .pubkey_hash .copy_from_slice(pub_hash.as_slice()); } else { - let mut rng = thread_rng(); + let mut rng = get_rng(); let incorrect_pubkey = { let mut buf = [0u8; 32]; rng.fill(&mut buf); @@ -824,6 +849,10 @@ pub fn auth_builder(t: AuthAlgorithmIdType, official: bool) -> result::Result { return Ok(Secp256r1Auth::new()); } + AuthAlgorithmIdType::Toncoin => todo!("Toncoin tests currectly unimplemented"), + AuthAlgorithmIdType::Secp256r1Raw => { + return Ok(Secp256r1RawAuth::new()); + } AuthAlgorithmIdType::OwnerLock => { return Ok(OwnerLockAuth::new()); } @@ -880,7 +909,7 @@ pub struct EthereumAuth { impl EthereumAuth { fn new() -> Box { let generator: secp256k1::Secp256k1 = secp256k1::Secp256k1::new(); - let mut rng = thread_rng(); + let mut rng = get_rng(); let (privkey, pubkey) = generator.generate_keypair(&mut rng); Box::new(EthereumAuth { privkey, @@ -989,7 +1018,7 @@ pub struct TronAuth { impl TronAuth { fn new() -> Box { let generator: secp256k1::Secp256k1 = secp256k1::Secp256k1::new(); - let mut rng = thread_rng(); + let mut rng = get_rng(); let (privkey, pubkey) = generator.generate_keypair(&mut rng); Box::new(TronAuth { privkey, pubkey }) } @@ -1047,7 +1076,7 @@ impl BitcoinAuth { } pub fn new_rng_key(v_type: BitcoinSignVType, btc_network: BtcNetwork) -> Self { - let mut rng = thread_rng(); + let mut rng = get_rng(); let mut secret_key = [0u8; 32]; rng.fill(&mut secret_key); @@ -1442,7 +1471,7 @@ pub struct MoneroAuth { impl MoneroAuth { pub fn new() -> Box { fn get_random_key_pair() -> monero::KeyPair { - let mut rng = thread_rng(); + let mut rng = get_rng(); let mut seed = vec![0; 32]; let spend_key = loop { rng.fill(seed.as_mut_slice()); @@ -1846,9 +1875,9 @@ impl Secp256r1Auth { pub fn new() -> Box { use p256::ecdsa::SigningKey; const SECRET_KEY: [u8; 32] = [ - 0x51, 0x9b, 0x42, 0x3d, 0x71, 0x5f, 0x8b, 0x58, 0x1f, 0x4f, 0xa8, 0xee, 0x59, 0xf4, - 0x77, 0x1a, 0x5b, 0x44, 0xc8, 0x13, 0x0b, 0x4e, 0x3e, 0xac, 0xca, 0x54, 0xa5, 0x6d, - 0xda, 0x72, 0xb4, 0x64, + 0x11, 0x2c, 0x32, 0xbc, 0xd5, 0x03, 0xcb, 0x62, 0x10, 0x2b, 0x1d, 0x98, 0x37, 0x9a, + 0xf3, 0x80, 0xc2, 0x26, 0xa1, 0x0a, 0xb3, 0x44, 0xca, 0x47, 0x88, 0xa4, 0xa6, 0x52, + 0x63, 0x5e, 0xcf, 0xfd, ]; let sk = SigningKey::from_bytes(&SECRET_KEY).unwrap(); @@ -1899,6 +1928,99 @@ impl Auth for Secp256r1Auth { } } +#[derive(Clone)] +pub struct Secp256r1RawAuth { + pub key: Arc, + pub signature_to_messages: HashMap, Vec>, +} + +impl Secp256r1RawAuth { + pub fn rng_seed() -> u64 { + 42 + } + pub fn new() -> Box { + use p256::ecdsa::SigningKey; + const SECRET_KEY: [u8; 32] = [ + 0x11, 0x2c, 0x32, 0xbc, 0xd5, 0x03, 0xcb, 0x62, 0x10, 0x2b, 0x1d, 0x98, 0x37, 0x9a, + 0xf3, 0x80, 0xc2, 0x26, 0xa1, 0x0a, 0xb3, 0x44, 0xca, 0x47, 0x88, 0xa4, 0xa6, 0x52, + 0x63, 0x5e, 0xcf, 0xfd, + ]; + + let sk = SigningKey::from_bytes(&SECRET_KEY).unwrap(); + // A few pre-created signatures to the messages. + let mut signature_to_messages = HashMap::new(); + signature_to_messages.insert( + hex::decode("4098dc9ac1815fbe9287f9f74748688b06a09bedf5aef07b667c2a979282d24f").unwrap(), + hex::decode( + "05279a8551a7453b982842150e3c58dce6f6eae399d6835e2b5a9ac5e41559f9e76f5d21e8f85ec959b6a4a089cd0dc9509649bbf57704b61abfe50c79d1da86").unwrap(), + ); + Box::new(Self { + key: Arc::new(sk), + signature_to_messages, + }) + } + pub fn get_pub_key(&self) -> p256::ecdsa::VerifyingKey { + let pk = self.key.verifying_key(); + pk + } + pub fn get_pub_key_bytes(&self) -> Vec { + let pub_key = self.get_pub_key(); + let encoded_point = pub_key.to_encoded_point(false); + let bytes = encoded_point.as_bytes(); + // The first byte is always 0x04, which is the tag for Uncompressed point. + // See https://docs.rs/sec1/latest/sec1/point/enum.Tag.html#variants + // Discard it as we always use x, y coordinates to encode pubkey. + bytes[1..].to_vec() + } +} +impl Auth for Secp256r1RawAuth { + fn get_pub_key_hash(&self) -> Vec { + let pub_key = self.get_pub_key_bytes(); + let hash = ckb_hash::blake2b_256(&pub_key); + Vec::from(&hash[..20]) + } + fn get_algorithm_type(&self) -> u8 { + AuthAlgorithmIdType::Secp256r1Raw as u8 + } + fn convert_message(&self, message: &[u8; 32]) -> H256 { + H256::from(message.clone()) + } + fn sign(&self, msg: &H256) -> Bytes { + let pub_key = self.get_pub_key_bytes(); + dbg!(hex::encode(&msg)); + + // TODO: we need to sign the message without hashing first, + // i.e. the method https://docs.rs/ecdsa/latest/ecdsa/struct.SigningKey.html#method.sign_prehash + // which is not available in current p256 version. + // Here we use the hard coded signature and message. + let signature = self.signature_to_messages.get(&msg.0.to_vec()).expect( + &format!(r#" + message {0} unexpected. + Make sure you have not changed the way we generate transactions (thus changed the message to sign) + and set the rng seed with `crate::rng::sed_seed(Secp256r1Raw::rng_seed())`. + In case of updating messages, build ec_utils from https://github.com/contrun/libecc/tree/secp256-copy-sign + and generate and output new signatures with the following commands + + printf 010104{1} | xxd -r -p > private_key.bin + printf {0} | xxd -r -p > message.bin + ./build/ec_utils sign SECP256R1 ECDSA SHA256 message.bin private_key.bin signature.bin + xxd -p signature.bin | tr -d '\n' + "#, + hex::encode(msg.0), + hex::encode(self.key.to_bytes()) + ) + ); + dbg!(hex::encode(signature), signature.len(), pub_key.len()); + let signature: Vec = pub_key.iter().chain(signature).map(|x| *x).collect(); + + dbg!(hex::encode(&signature)); + signature.into() + } + fn get_sign_size(&self) -> usize { + 128 + } +} + #[derive(Clone)] pub struct CkbMultisigAuth { pub pubkeys_cnt: u8, @@ -1984,7 +2106,7 @@ pub struct SchnorrAuth { impl SchnorrAuth { pub fn new() -> Box { let generator: secp256k1::Secp256k1 = secp256k1::Secp256k1::new(); - let mut rng = thread_rng(); + let mut rng = get_rng(); let (privkey, pubkey) = generator.generate_keypair(&mut rng); Box::new(SchnorrAuth { privkey, pubkey }) } diff --git a/tests/auth-c-tests/src/tests/mod.rs b/tests/auth-c-tests/src/tests/mod.rs index 614e4c1..50ac7ad 100644 --- a/tests/auth-c-tests/src/tests/mod.rs +++ b/tests/auth-c-tests/src/tests/mod.rs @@ -1,6 +1,7 @@ #![allow(unused_imports)] #![allow(dead_code)] +use crate::{get_rng, Secp256r1RawAuth}; use ckb_auth_rs::EntryCategoryType; use ckb_chain_spec::consensus::{Consensus, ConsensusBuilder}; use ckb_crypto::secp::{Generator, Privkey, Pubkey}; @@ -11,7 +12,7 @@ use ckb_types::{ H256, }; use log::{Level, LevelFilter, Metadata, Record}; -use rand::{thread_rng, Rng}; +use rand::Rng; use sha3::{digest::generic_array::typenum::private::IsEqualPrivate, Digest, Keccak256}; use std::sync::Arc; @@ -64,9 +65,12 @@ fn assert_result_error(res: Result, des: &str, err_codes: } fn unit_test_success(auth: &Box, run_type: EntryCategoryType) { + dbg!(&run_type); let mut config = TestConfig::new(auth, run_type, 1); + dbg!(&config.auth_lock_type); assert_result_ok(verify_unit(&config), ""); config.auth_lock_type = TestConfigAuthLockType::Rust; + dbg!(&config.auth_lock_type); assert_result_ok(verify_unit(&config), ""); } @@ -81,7 +85,7 @@ fn unit_test_multiple_group(auth: &Box, run_type: EntryCategoryType) { let config = TestConfig::new(auth, run_type, 1); - let mut rng = thread_rng(); + let mut rng = get_rng(); let tx = gen_tx_with_grouped_args( &mut data_loader, vec![ @@ -264,7 +268,7 @@ fn bitcoin_pubkey_recid_verify() { let sign = priv_key.sign_recoverable(&msg).expect("sign").serialize(); assert_eq!(sign.len(), 65); - let mut rng = rand::thread_rng(); + let mut rng = get_rng(); let mut recid: u8 = rng.gen_range(0, 4); while recid == sign[64] && recid < 31 { recid = rng.gen_range(0, 4); @@ -333,9 +337,20 @@ fn ripple_verify() { #[test] fn secp256r1_verify() { use_libecc(); + crate::rng::set_seed(Secp256r1RawAuth::rng_seed()); unit_test_common(AuthAlgorithmIdType::Secp256r1); } +#[test] +fn secp256r1_raw_verify_succeed() { + use_libecc(); + crate::rng::set_seed(Secp256r1RawAuth::rng_seed()); + let algorithm_type = AuthAlgorithmIdType::Secp256r1Raw; + let auth = auth_builder(algorithm_type, false).unwrap(); + let run_type = EntryCategoryType::DynamicLibrary; + unit_test_success(&auth, run_type); +} + #[test] fn convert_eth_error() { #[derive(Clone)] @@ -362,7 +377,7 @@ fn convert_eth_error() { } let generator: secp256k1::Secp256k1 = secp256k1::Secp256k1::new(); - let mut rng = thread_rng(); + let mut rng = get_rng(); let (privkey, pubkey) = generator.generate_keypair(&mut rng); let auth: Box = Box::new(EthConverFaileAuth { @@ -408,7 +423,7 @@ fn convert_tron_error() { } let generator: secp256k1::Secp256k1 = secp256k1::Secp256k1::new(); - let mut rng = thread_rng(); + let mut rng = get_rng(); let (privkey, pubkey) = generator.generate_keypair(&mut rng); let auth: Box = Box::new(TronConverFaileAuth { 0: TronAuth { privkey, pubkey },