Alien-libsecp256k1
view release on metacpan or search on metacpan
libsecp256k1/src/tests.c view on Meta::CPAN
}
if (nlen[n] == 32 && !nlow[n]) {
/* Special extra 16 0xFF bytes in "high" 32-byte numbers */
int i;
for (i = 0; i < 16; i++) {
sig[(*len)++] = 0xFF;
}
nlen[n] -= 16;
}
/* Write first byte of number */
if (nlen[n] > 0) {
sig[(*len)++] = nhbyte[n];
nlen[n]--;
}
/* Generate remaining random bytes of number */
testrand_bytes_test(sig + *len, nlen[n]);
*len += nlen[n];
nlen[n] = 0;
}
/* Generate random garbage inside tuple. */
testrand_bytes_test(sig + *len, elen);
*len += elen;
/* Generate end-of-contents bytes. */
if (indet) {
sig[(*len)++] = 0;
sig[(*len)++] = 0;
tlen += 2;
}
CHECK(tlen + glen <= 1121);
/* Generate random garbage outside tuple. */
testrand_bytes_test(sig + *len, glen);
*len += glen;
tlen += glen;
CHECK(tlen <= 1121);
CHECK(tlen == *len);
}
static void run_ecdsa_der_parse(void) {
int i,j;
for (i = 0; i < 200 * COUNT; i++) {
unsigned char buffer[2048];
size_t buflen = 0;
int certainly_der = 0;
int certainly_not_der = 0;
random_ber_signature(buffer, &buflen, &certainly_der, &certainly_not_der);
CHECK(buflen <= 2048);
for (j = 0; j < 16; j++) {
int ret = 0;
if (j > 0) {
damage_array(buffer, &buflen);
/* We don't know anything anymore about the DERness of the result */
certainly_der = 0;
certainly_not_der = 0;
}
ret = test_ecdsa_der_parse(buffer, buflen, certainly_der, certainly_not_der);
if (ret != 0) {
size_t k;
fprintf(stderr, "Failure %x on ", ret);
for (k = 0; k < buflen; k++) {
fprintf(stderr, "%02x ", buffer[k]);
}
fprintf(stderr, "\n");
}
CHECK(ret == 0);
}
}
}
/* Tests several edge cases. */
static void test_ecdsa_edge_cases(void) {
int t;
secp256k1_ecdsa_signature sig;
/* Test the case where ECDSA recomputes a point that is infinity. */
{
secp256k1_gej keyj;
secp256k1_ge key;
secp256k1_scalar msg;
secp256k1_scalar sr, ss;
secp256k1_scalar_set_int(&ss, 1);
secp256k1_scalar_negate(&ss, &ss);
secp256k1_scalar_inverse(&ss, &ss);
secp256k1_scalar_set_int(&sr, 1);
secp256k1_ecmult_gen(&CTX->ecmult_gen_ctx, &keyj, &sr);
secp256k1_ge_set_gej(&key, &keyj);
msg = ss;
CHECK(secp256k1_ecdsa_sig_verify(&sr, &ss, &key, &msg) == 0);
}
/* Verify signature with r of zero fails. */
{
const unsigned char pubkey_mods_zero[33] = {
0x02, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xfe, 0xba, 0xae, 0xdc, 0xe6, 0xaf, 0x48, 0xa0,
0x3b, 0xbf, 0xd2, 0x5e, 0x8c, 0xd0, 0x36, 0x41,
0x41
};
secp256k1_ge key;
secp256k1_scalar msg;
secp256k1_scalar sr, ss;
secp256k1_scalar_set_int(&ss, 1);
secp256k1_scalar_set_int(&msg, 0);
secp256k1_scalar_set_int(&sr, 0);
CHECK(secp256k1_eckey_pubkey_parse(&key, pubkey_mods_zero, 33));
CHECK(secp256k1_ecdsa_sig_verify( &sr, &ss, &key, &msg) == 0);
}
/* Verify signature with s of zero fails. */
{
const unsigned char pubkey[33] = {
0x02, 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
};
secp256k1_ge key;
secp256k1_scalar msg;
secp256k1_scalar sr, ss;
secp256k1_scalar_set_int(&ss, 0);
secp256k1_scalar_set_int(&msg, 0);
libsecp256k1/src/tests.c view on Meta::CPAN
CHECK(secp256k1_memcmp_var(&r, &max, sizeof(r)) == 0);
a = secp256k1_scalar_zero;
secp256k1_scalar_cmov(&r, &a, 1);
CHECK(secp256k1_memcmp_var(&r, &secp256k1_scalar_zero, sizeof(r)) == 0);
a = secp256k1_scalar_one;
secp256k1_scalar_cmov(&r, &a, 1);
CHECK(secp256k1_memcmp_var(&r, &secp256k1_scalar_one, sizeof(r)) == 0);
r = secp256k1_scalar_one; a = secp256k1_scalar_zero;
secp256k1_scalar_cmov(&r, &a, 0);
CHECK(secp256k1_memcmp_var(&r, &secp256k1_scalar_one, sizeof(r)) == 0);
}
static void ge_storage_cmov_test(void) {
static const secp256k1_ge_storage zero = SECP256K1_GE_STORAGE_CONST(0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);
static const secp256k1_ge_storage one = SECP256K1_GE_STORAGE_CONST(0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1);
static const secp256k1_ge_storage max = SECP256K1_GE_STORAGE_CONST(
0xFFFFFFFFUL, 0xFFFFFFFFUL, 0xFFFFFFFFUL, 0xFFFFFFFFUL,
0xFFFFFFFFUL, 0xFFFFFFFFUL, 0xFFFFFFFFUL, 0xFFFFFFFFUL,
0xFFFFFFFFUL, 0xFFFFFFFFUL, 0xFFFFFFFFUL, 0xFFFFFFFFUL,
0xFFFFFFFFUL, 0xFFFFFFFFUL, 0xFFFFFFFFUL, 0xFFFFFFFFUL
);
secp256k1_ge_storage r = max;
secp256k1_ge_storage a = zero;
secp256k1_ge_storage_cmov(&r, &a, 0);
CHECK(secp256k1_memcmp_var(&r, &max, sizeof(r)) == 0);
r = zero; a = max;
secp256k1_ge_storage_cmov(&r, &a, 1);
CHECK(secp256k1_memcmp_var(&r, &max, sizeof(r)) == 0);
a = zero;
secp256k1_ge_storage_cmov(&r, &a, 1);
CHECK(secp256k1_memcmp_var(&r, &zero, sizeof(r)) == 0);
a = one;
secp256k1_ge_storage_cmov(&r, &a, 1);
CHECK(secp256k1_memcmp_var(&r, &one, sizeof(r)) == 0);
r = one; a = zero;
secp256k1_ge_storage_cmov(&r, &a, 0);
CHECK(secp256k1_memcmp_var(&r, &one, sizeof(r)) == 0);
}
static void run_cmov_tests(void) {
int_cmov_test();
fe_cmov_test();
fe_storage_cmov_test();
scalar_cmov_test();
ge_storage_cmov_test();
}
int main(int argc, char **argv) {
/* Disable buffering for stdout to improve reliability of getting
* diagnostic information. Happens right at the start of main because
* setbuf must be used before any other operation on the stream. */
setbuf(stdout, NULL);
/* Also disable buffering for stderr because it's not guaranteed that it's
* unbuffered on all systems. */
setbuf(stderr, NULL);
/* find iteration count */
if (argc > 1) {
COUNT = strtol(argv[1], NULL, 0);
} else {
const char* env = getenv("SECP256K1_TEST_ITERS");
if (env && strlen(env) > 0) {
COUNT = strtol(env, NULL, 0);
}
}
if (COUNT <= 0) {
fputs("An iteration count of 0 or less is not allowed.\n", stderr);
return EXIT_FAILURE;
}
printf("test count = %i\n", COUNT);
/* run test RNG tests (must run before we really initialize the test RNG) */
run_xoshiro256pp_tests();
/* find random seed */
testrand_init(argc > 2 ? argv[2] : NULL);
/*** Setup test environment ***/
/* Create a global context available to all tests */
CTX = secp256k1_context_create(SECP256K1_CONTEXT_NONE);
/* Randomize the context only with probability 15/16
to make sure we test without context randomization from time to time.
TODO Reconsider this when recalibrating the tests. */
if (testrand_bits(4)) {
unsigned char rand32[32];
testrand256(rand32);
CHECK(secp256k1_context_randomize(CTX, rand32));
}
/* Make a writable copy of secp256k1_context_static in order to test the effect of API functions
that write to the context. The API does not support cloning the static context, so we use
memcpy instead. The user is not supposed to copy a context but we should still ensure that
the API functions handle copies of the static context gracefully. */
STATIC_CTX = malloc(sizeof(*secp256k1_context_static));
CHECK(STATIC_CTX != NULL);
memcpy(STATIC_CTX, secp256k1_context_static, sizeof(secp256k1_context));
CHECK(!secp256k1_context_is_proper(STATIC_CTX));
/*** Run actual tests ***/
/* selftest tests */
run_selftest_tests();
/* context tests */
run_proper_context_tests(0); run_proper_context_tests(1);
run_static_context_tests(0); run_static_context_tests(1);
run_deprecated_context_flags_test();
/* scratch tests */
run_scratch_tests();
/* integer arithmetic tests */
#ifdef SECP256K1_WIDEMUL_INT128
run_int128_tests();
#endif
run_ctz_tests();
run_modinv_tests();
run_inverse_tests();
/* sorting tests */
run_hsort_tests();
/* hash tests */
run_sha256_known_output_tests();
run_sha256_counter_tests();
run_hmac_sha256_tests();
run_rfc6979_hmac_sha256_tests();
( run in 1.865 second using v1.01-cache-2.11-cpan-ceb78f64989 )