Skip to content

Commit 50cc6ab

Browse files
committed
Merge pull request #178
941e221 Add tests for handling of the nonce function in signing. (Gregory Maxwell)
2 parents 10c81ff + 941e221 commit 50cc6ab

File tree

2 files changed

+99
-1
lines changed

2 files changed

+99
-1
lines changed

src/bench_sign.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ static void bench_sign(void* arg) {
2626
unsigned char sig[64];
2727
for (int i=0; i<20000; i++) {
2828
int recid = 0;
29-
secp256k1_ecdsa_sign_compact(data->msg, sig, data->key, NULL, NULL, &recid);
29+
CHECK(secp256k1_ecdsa_sign_compact(data->msg, sig, data->key, NULL, NULL, &recid));
3030
for (int j = 0; j < 32; j++) {
3131
data->msg[j] = sig[j]; /* Move former R to message. */
3232
data->key[j] = sig[j + 32]; /* Move former S to key. */

src/tests.c

Lines changed: 98 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1119,6 +1119,36 @@ static int precomputed_nonce_function(unsigned char *nonce32, const unsigned cha
11191119
return (counter == 0);
11201120
}
11211121

1122+
static int nonce_function_test_fail(unsigned char *nonce32, const unsigned char *msg32, const unsigned char *key32, unsigned int counter, const void *data) {
1123+
/* Dummy nonce generator that has a fatal error on the first counter value. */
1124+
if (counter == 0) return 0;
1125+
return nonce_function_rfc6979(nonce32, msg32, key32, counter - 1, data);
1126+
}
1127+
1128+
static int nonce_function_test_retry(unsigned char *nonce32, const unsigned char *msg32, const unsigned char *key32, unsigned int counter, const void *data) {
1129+
/* Dummy nonce generator that produces unacceptable nonces for the first several counter values. */
1130+
if (counter < 3) {
1131+
memset(nonce32, counter==0 ? 0 : 255, 32);
1132+
if (counter == 2) nonce32[31]--;
1133+
return 1;
1134+
}
1135+
if (counter < 5) {
1136+
static const unsigned char order[] = {
1137+
0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,
1138+
0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFE,
1139+
0xBA,0xAE,0xDC,0xE6,0xAF,0x48,0xA0,0x3B,
1140+
0xBF,0xD2,0x5E,0x8C,0xD0,0x36,0x41,0x41
1141+
};
1142+
memcpy(nonce32, order, 32);
1143+
if (counter == 4) nonce32[31]++;
1144+
return 1;
1145+
}
1146+
/* Retry rate of 6979 is negligible esp. as we only call this in determinstic tests. */
1147+
/* If someone does fine a case where it retries for secp256k1, we'd like to know. */
1148+
if (counter > 5) return 0;
1149+
return nonce_function_rfc6979(nonce32, msg32, key32, counter - 5, data);
1150+
}
1151+
11221152
void test_ecdsa_end_to_end(void) {
11231153
unsigned char privkey[32];
11241154
unsigned char message[32];
@@ -1438,6 +1468,12 @@ void test_ecdsa_edge_cases(void) {
14381468
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
14391469
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01,
14401470
};
1471+
static const unsigned char nonce2[32] = {
1472+
0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,
1473+
0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFE,
1474+
0xBA,0xAE,0xDC,0xE6,0xAF,0x48,0xA0,0x3B,
1475+
0xBF,0xD2,0x5E,0x8C,0xD0,0x36,0x41,0x40
1476+
};
14411477
const unsigned char key[32] = {
14421478
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
14431479
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
@@ -1453,13 +1489,75 @@ void test_ecdsa_edge_cases(void) {
14531489
unsigned char sig[72];
14541490
int siglen = 72;
14551491
CHECK(secp256k1_ecdsa_sign(msg, sig, &siglen, key, precomputed_nonce_function, nonce) == 0);
1492+
CHECK(secp256k1_ecdsa_sign(msg, sig, &siglen, key, precomputed_nonce_function, nonce2) == 0);
14561493
msg[31] = 0xaa;
14571494
siglen = 72;
14581495
CHECK(secp256k1_ecdsa_sign(msg, sig, &siglen, key, precomputed_nonce_function, nonce) == 1);
1496+
CHECK(secp256k1_ecdsa_sign(msg, sig, &siglen, key, precomputed_nonce_function, nonce2) == 1);
14591497
siglen = 10;
14601498
CHECK(secp256k1_ecdsa_sign(msg, sig, &siglen, key, precomputed_nonce_function, nonce) != 1);
14611499
}
14621500

1501+
/* Nonce function corner cases. */
1502+
{
1503+
unsigned char key[32];
1504+
unsigned char msg[32];
1505+
unsigned char sig[72];
1506+
memset(key, 0, 32);
1507+
memset(msg, 0, 32);
1508+
key[31] = 1;
1509+
msg[31] = 1;
1510+
int siglen = 72;
1511+
int recid;
1512+
/* Nonce function failure results in signature failure. */
1513+
CHECK(secp256k1_ecdsa_sign(msg, sig, &siglen, key, nonce_function_test_fail, NULL) == 0);
1514+
CHECK(secp256k1_ecdsa_sign_compact(msg, sig, key, nonce_function_test_fail, NULL, &recid) == 0);
1515+
/* The retry loop successfully makes its way to the first good value. */
1516+
unsigned char sig2[72];
1517+
int siglen2 = 72;
1518+
siglen = 72;
1519+
CHECK(secp256k1_ecdsa_sign(msg, sig, &siglen, key, nonce_function_test_retry, NULL) == 1);
1520+
CHECK(secp256k1_ecdsa_sign(msg, sig2, &siglen2, key, nonce_function_rfc6979, NULL) == 1);
1521+
CHECK((siglen == siglen2) && (memcmp(sig, sig2, siglen) == 0));
1522+
int recid2;
1523+
CHECK(secp256k1_ecdsa_sign_compact(msg, sig, key, nonce_function_test_retry, NULL, &recid) == 1);
1524+
CHECK(secp256k1_ecdsa_sign_compact(msg, sig2, key, nonce_function_rfc6979, NULL, &recid2) == 1);
1525+
CHECK((recid == recid2) && (memcmp(sig, sig2, 64) == 0));
1526+
/* The default nonce function is determinstic. */
1527+
siglen = 72;
1528+
siglen2 = 72;
1529+
CHECK(secp256k1_ecdsa_sign(msg, sig, &siglen, key, NULL, NULL) == 1);
1530+
CHECK(secp256k1_ecdsa_sign(msg, sig2, &siglen2, key, NULL, NULL) == 1);
1531+
CHECK((siglen == siglen2) && (memcmp(sig, sig2, siglen) == 0));
1532+
CHECK(secp256k1_ecdsa_sign_compact(msg, sig, key, NULL, NULL, &recid) == 1);
1533+
CHECK(secp256k1_ecdsa_sign_compact(msg, sig2, key, NULL, NULL, &recid2) == 1);
1534+
CHECK((recid == recid2) && (memcmp(sig, sig2, 64) == 0));
1535+
/* The default nonce function changes output with different messages. */
1536+
secp256k1_ecdsa_sig_t s[512];
1537+
for(int i=0; i<256; i++) {
1538+
siglen2 = 72;
1539+
msg[0] = i;
1540+
CHECK(secp256k1_ecdsa_sign(msg, sig2, &siglen2, key, NULL, NULL) == 1);
1541+
CHECK(secp256k1_ecdsa_sig_parse(&s[i], sig2, siglen2));
1542+
for (int j=0; j<i; j++) {
1543+
CHECK(!secp256k1_scalar_eq(&s[i].r, &s[j].r));
1544+
}
1545+
}
1546+
msg[0] = 0;
1547+
msg[31] = 2;
1548+
/* The default nonce function changes output with different keys. */
1549+
for(int i=256; i<512; i++) {
1550+
siglen2 = 72;
1551+
key[0] = i - 256;
1552+
CHECK(secp256k1_ecdsa_sign(msg, sig2, &siglen2, key, NULL, NULL) == 1);
1553+
CHECK(secp256k1_ecdsa_sig_parse(&s[i], sig2, siglen2));
1554+
for (int j=0; j<i; j++) {
1555+
CHECK(!secp256k1_scalar_eq(&s[i].r, &s[j].r));
1556+
}
1557+
}
1558+
key[0] = 0;
1559+
}
1560+
14631561
/* Privkey export where pubkey is the point at infinity. */
14641562
{
14651563
unsigned char privkey[300];

0 commit comments

Comments
 (0)