github.com/luckypickle/go-ethereum-vet@v1.14.2/crypto/secp256k1/libsecp256k1/src/modules/recovery/tests_impl.h (about) 1 /********************************************************************** 2 * Copyright (c) 2013-2015 Pieter Wuille * 3 * Distributed under the MIT software license, see the accompanying * 4 * file COPYING or http://www.opensource.org/licenses/mit-license.php.* 5 **********************************************************************/ 6 7 #ifndef _SECP256K1_MODULE_RECOVERY_TESTS_ 8 #define _SECP256K1_MODULE_RECOVERY_TESTS_ 9 10 static int recovery_test_nonce_function(unsigned char *nonce32, const unsigned char *msg32, const unsigned char *key32, const unsigned char *algo16, void *data, unsigned int counter) { 11 (void) msg32; 12 (void) key32; 13 (void) algo16; 14 (void) data; 15 16 /* On the first run, return 0 to force a second run */ 17 if (counter == 0) { 18 memset(nonce32, 0, 32); 19 return 1; 20 } 21 /* On the second run, return an overflow to force a third run */ 22 if (counter == 1) { 23 memset(nonce32, 0xff, 32); 24 return 1; 25 } 26 /* On the next run, return a valid nonce, but flip a coin as to whether or not to fail signing. */ 27 memset(nonce32, 1, 32); 28 return vet_secp256k1_rand_bits(1); 29 } 30 31 void test_ecdsa_recovery_api(void) { 32 /* Setup contexts that just count errors */ 33 vet_secp256k1_context *none = vet_secp256k1_context_create(SECP256K1_CONTEXT_NONE); 34 vet_secp256k1_context *sign = vet_secp256k1_context_create(SECP256K1_CONTEXT_SIGN); 35 vet_secp256k1_context *vrfy = vet_secp256k1_context_create(SECP256K1_CONTEXT_VERIFY); 36 vet_secp256k1_context *both = vet_secp256k1_context_create(SECP256K1_CONTEXT_SIGN | SECP256K1_CONTEXT_VERIFY); 37 vet_secp256k1_pubkey pubkey; 38 vet_secp256k1_pubkey recpubkey; 39 vet_secp256k1_ecdsa_signature normal_sig; 40 vet_secp256k1_ecdsa_recoverable_signature recsig; 41 unsigned char privkey[32] = { 1 }; 42 unsigned char message[32] = { 2 }; 43 int32_t ecount = 0; 44 int recid = 0; 45 unsigned char sig[74]; 46 unsigned char zero_privkey[32] = { 0 }; 47 unsigned char over_privkey[32] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 48 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 49 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 50 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff }; 51 52 vet_secp256k1_context_set_error_callback(none, counting_illegal_callback_fn, &ecount); 53 vet_secp256k1_context_set_error_callback(sign, counting_illegal_callback_fn, &ecount); 54 vet_secp256k1_context_set_error_callback(vrfy, counting_illegal_callback_fn, &ecount); 55 vet_secp256k1_context_set_error_callback(both, counting_illegal_callback_fn, &ecount); 56 vet_secp256k1_context_set_illegal_callback(none, counting_illegal_callback_fn, &ecount); 57 vet_secp256k1_context_set_illegal_callback(sign, counting_illegal_callback_fn, &ecount); 58 vet_secp256k1_context_set_illegal_callback(vrfy, counting_illegal_callback_fn, &ecount); 59 vet_secp256k1_context_set_illegal_callback(both, counting_illegal_callback_fn, &ecount); 60 61 /* Construct and verify corresponding public key. */ 62 CHECK(vet_secp256k1_ec_seckey_verify(ctx, privkey) == 1); 63 CHECK(vet_secp256k1_ec_pubkey_create(ctx, &pubkey, privkey) == 1); 64 65 /* Check bad contexts and NULLs for signing */ 66 ecount = 0; 67 CHECK(vet_secp256k1_ecdsa_sign_recoverable(none, &recsig, message, privkey, NULL, NULL) == 0); 68 CHECK(ecount == 1); 69 CHECK(vet_secp256k1_ecdsa_sign_recoverable(sign, &recsig, message, privkey, NULL, NULL) == 1); 70 CHECK(ecount == 1); 71 CHECK(vet_secp256k1_ecdsa_sign_recoverable(vrfy, &recsig, message, privkey, NULL, NULL) == 0); 72 CHECK(ecount == 2); 73 CHECK(vet_secp256k1_ecdsa_sign_recoverable(both, &recsig, message, privkey, NULL, NULL) == 1); 74 CHECK(ecount == 2); 75 CHECK(vet_secp256k1_ecdsa_sign_recoverable(both, NULL, message, privkey, NULL, NULL) == 0); 76 CHECK(ecount == 3); 77 CHECK(vet_secp256k1_ecdsa_sign_recoverable(both, &recsig, NULL, privkey, NULL, NULL) == 0); 78 CHECK(ecount == 4); 79 CHECK(vet_secp256k1_ecdsa_sign_recoverable(both, &recsig, message, NULL, NULL, NULL) == 0); 80 CHECK(ecount == 5); 81 /* This will fail or succeed randomly, and in either case will not ARG_CHECK failure */ 82 vet_secp256k1_ecdsa_sign_recoverable(both, &recsig, message, privkey, recovery_test_nonce_function, NULL); 83 CHECK(ecount == 5); 84 /* These will all fail, but not in ARG_CHECK way */ 85 CHECK(vet_secp256k1_ecdsa_sign_recoverable(both, &recsig, message, zero_privkey, NULL, NULL) == 0); 86 CHECK(vet_secp256k1_ecdsa_sign_recoverable(both, &recsig, message, over_privkey, NULL, NULL) == 0); 87 /* This one will succeed. */ 88 CHECK(vet_secp256k1_ecdsa_sign_recoverable(both, &recsig, message, privkey, NULL, NULL) == 1); 89 CHECK(ecount == 5); 90 91 /* Check signing with a goofy nonce function */ 92 93 /* Check bad contexts and NULLs for recovery */ 94 ecount = 0; 95 CHECK(vet_secp256k1_ecdsa_recover(none, &recpubkey, &recsig, message) == 0); 96 CHECK(ecount == 1); 97 CHECK(vet_secp256k1_ecdsa_recover(sign, &recpubkey, &recsig, message) == 0); 98 CHECK(ecount == 2); 99 CHECK(vet_secp256k1_ecdsa_recover(vrfy, &recpubkey, &recsig, message) == 1); 100 CHECK(ecount == 2); 101 CHECK(vet_secp256k1_ecdsa_recover(both, &recpubkey, &recsig, message) == 1); 102 CHECK(ecount == 2); 103 CHECK(vet_secp256k1_ecdsa_recover(both, NULL, &recsig, message) == 0); 104 CHECK(ecount == 3); 105 CHECK(vet_secp256k1_ecdsa_recover(both, &recpubkey, NULL, message) == 0); 106 CHECK(ecount == 4); 107 CHECK(vet_secp256k1_ecdsa_recover(both, &recpubkey, &recsig, NULL) == 0); 108 CHECK(ecount == 5); 109 110 /* Check NULLs for conversion */ 111 CHECK(vet_secp256k1_ecdsa_sign(both, &normal_sig, message, privkey, NULL, NULL) == 1); 112 ecount = 0; 113 CHECK(vet_secp256k1_ecdsa_recoverable_signature_convert(both, NULL, &recsig) == 0); 114 CHECK(ecount == 1); 115 CHECK(vet_secp256k1_ecdsa_recoverable_signature_convert(both, &normal_sig, NULL) == 0); 116 CHECK(ecount == 2); 117 CHECK(vet_secp256k1_ecdsa_recoverable_signature_convert(both, &normal_sig, &recsig) == 1); 118 119 /* Check NULLs for de/serialization */ 120 CHECK(vet_secp256k1_ecdsa_sign_recoverable(both, &recsig, message, privkey, NULL, NULL) == 1); 121 ecount = 0; 122 CHECK(vet_secp256k1_ecdsa_recoverable_signature_serialize_compact(both, NULL, &recid, &recsig) == 0); 123 CHECK(ecount == 1); 124 CHECK(vet_secp256k1_ecdsa_recoverable_signature_serialize_compact(both, sig, NULL, &recsig) == 0); 125 CHECK(ecount == 2); 126 CHECK(vet_secp256k1_ecdsa_recoverable_signature_serialize_compact(both, sig, &recid, NULL) == 0); 127 CHECK(ecount == 3); 128 CHECK(vet_secp256k1_ecdsa_recoverable_signature_serialize_compact(both, sig, &recid, &recsig) == 1); 129 130 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(both, NULL, sig, recid) == 0); 131 CHECK(ecount == 4); 132 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(both, &recsig, NULL, recid) == 0); 133 CHECK(ecount == 5); 134 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(both, &recsig, sig, -1) == 0); 135 CHECK(ecount == 6); 136 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(both, &recsig, sig, 5) == 0); 137 CHECK(ecount == 7); 138 /* overflow in signature will fail but not affect ecount */ 139 memcpy(sig, over_privkey, 32); 140 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(both, &recsig, sig, recid) == 0); 141 CHECK(ecount == 7); 142 143 /* cleanup */ 144 vet_secp256k1_context_destroy(none); 145 vet_secp256k1_context_destroy(sign); 146 vet_secp256k1_context_destroy(vrfy); 147 vet_secp256k1_context_destroy(both); 148 } 149 150 void test_ecdsa_recovery_end_to_end(void) { 151 unsigned char extra[32] = {0x00}; 152 unsigned char privkey[32]; 153 unsigned char message[32]; 154 vet_secp256k1_ecdsa_signature signature[5]; 155 vet_secp256k1_ecdsa_recoverable_signature rsignature[5]; 156 unsigned char sig[74]; 157 vet_secp256k1_pubkey pubkey; 158 vet_secp256k1_pubkey recpubkey; 159 int recid = 0; 160 161 /* Generate a random key and message. */ 162 { 163 vet_secp256k1_scalar msg, key; 164 random_scalar_order_test(&msg); 165 random_scalar_order_test(&key); 166 vet_secp256k1_scalar_get_b32(privkey, &key); 167 vet_secp256k1_scalar_get_b32(message, &msg); 168 } 169 170 /* Construct and verify corresponding public key. */ 171 CHECK(vet_secp256k1_ec_seckey_verify(ctx, privkey) == 1); 172 CHECK(vet_secp256k1_ec_pubkey_create(ctx, &pubkey, privkey) == 1); 173 174 /* Serialize/parse compact and verify/recover. */ 175 extra[0] = 0; 176 CHECK(vet_secp256k1_ecdsa_sign_recoverable(ctx, &rsignature[0], message, privkey, NULL, NULL) == 1); 177 CHECK(vet_secp256k1_ecdsa_sign(ctx, &signature[0], message, privkey, NULL, NULL) == 1); 178 CHECK(vet_secp256k1_ecdsa_sign_recoverable(ctx, &rsignature[4], message, privkey, NULL, NULL) == 1); 179 CHECK(vet_secp256k1_ecdsa_sign_recoverable(ctx, &rsignature[1], message, privkey, NULL, extra) == 1); 180 extra[31] = 1; 181 CHECK(vet_secp256k1_ecdsa_sign_recoverable(ctx, &rsignature[2], message, privkey, NULL, extra) == 1); 182 extra[31] = 0; 183 extra[0] = 1; 184 CHECK(vet_secp256k1_ecdsa_sign_recoverable(ctx, &rsignature[3], message, privkey, NULL, extra) == 1); 185 CHECK(vet_secp256k1_ecdsa_recoverable_signature_serialize_compact(ctx, sig, &recid, &rsignature[4]) == 1); 186 CHECK(vet_secp256k1_ecdsa_recoverable_signature_convert(ctx, &signature[4], &rsignature[4]) == 1); 187 CHECK(memcmp(&signature[4], &signature[0], 64) == 0); 188 CHECK(vet_secp256k1_ecdsa_verify(ctx, &signature[4], message, &pubkey) == 1); 189 memset(&rsignature[4], 0, sizeof(rsignature[4])); 190 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(ctx, &rsignature[4], sig, recid) == 1); 191 CHECK(vet_secp256k1_ecdsa_recoverable_signature_convert(ctx, &signature[4], &rsignature[4]) == 1); 192 CHECK(vet_secp256k1_ecdsa_verify(ctx, &signature[4], message, &pubkey) == 1); 193 /* Parse compact (with recovery id) and recover. */ 194 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(ctx, &rsignature[4], sig, recid) == 1); 195 CHECK(vet_secp256k1_ecdsa_recover(ctx, &recpubkey, &rsignature[4], message) == 1); 196 CHECK(memcmp(&pubkey, &recpubkey, sizeof(pubkey)) == 0); 197 /* Serialize/destroy/parse signature and verify again. */ 198 CHECK(vet_secp256k1_ecdsa_recoverable_signature_serialize_compact(ctx, sig, &recid, &rsignature[4]) == 1); 199 sig[vet_secp256k1_rand_bits(6)] += 1 + vet_secp256k1_rand_int(255); 200 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(ctx, &rsignature[4], sig, recid) == 1); 201 CHECK(vet_secp256k1_ecdsa_recoverable_signature_convert(ctx, &signature[4], &rsignature[4]) == 1); 202 CHECK(vet_secp256k1_ecdsa_verify(ctx, &signature[4], message, &pubkey) == 0); 203 /* Recover again */ 204 CHECK(vet_secp256k1_ecdsa_recover(ctx, &recpubkey, &rsignature[4], message) == 0 || 205 memcmp(&pubkey, &recpubkey, sizeof(pubkey)) != 0); 206 } 207 208 /* Tests several edge cases. */ 209 void test_ecdsa_recovery_edge_cases(void) { 210 const unsigned char msg32[32] = { 211 'T', 'h', 'i', 's', ' ', 'i', 's', ' ', 212 'a', ' ', 'v', 'e', 'r', 'y', ' ', 's', 213 'e', 'c', 'r', 'e', 't', ' ', 'm', 'e', 214 's', 's', 'a', 'g', 'e', '.', '.', '.' 215 }; 216 const unsigned char sig64[64] = { 217 /* Generated by signing the above message with nonce 'This is the nonce we will use...' 218 * and secret key 0 (which is not valid), resulting in recid 0. */ 219 0x67, 0xCB, 0x28, 0x5F, 0x9C, 0xD1, 0x94, 0xE8, 220 0x40, 0xD6, 0x29, 0x39, 0x7A, 0xF5, 0x56, 0x96, 221 0x62, 0xFD, 0xE4, 0x46, 0x49, 0x99, 0x59, 0x63, 222 0x17, 0x9A, 0x7D, 0xD1, 0x7B, 0xD2, 0x35, 0x32, 223 0x4B, 0x1B, 0x7D, 0xF3, 0x4C, 0xE1, 0xF6, 0x8E, 224 0x69, 0x4F, 0xF6, 0xF1, 0x1A, 0xC7, 0x51, 0xDD, 225 0x7D, 0xD7, 0x3E, 0x38, 0x7E, 0xE4, 0xFC, 0x86, 226 0x6E, 0x1B, 0xE8, 0xEC, 0xC7, 0xDD, 0x95, 0x57 227 }; 228 vet_secp256k1_pubkey pubkey; 229 /* signature (r,s) = (4,4), which can be recovered with all 4 recids. */ 230 const unsigned char sigb64[64] = { 231 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 232 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 233 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 234 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 235 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 236 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 237 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 238 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 239 }; 240 vet_secp256k1_pubkey pubkeyb; 241 vet_secp256k1_ecdsa_recoverable_signature rsig; 242 vet_secp256k1_ecdsa_signature sig; 243 int recid; 244 245 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(ctx, &rsig, sig64, 0)); 246 CHECK(!vet_secp256k1_ecdsa_recover(ctx, &pubkey, &rsig, msg32)); 247 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(ctx, &rsig, sig64, 1)); 248 CHECK(vet_secp256k1_ecdsa_recover(ctx, &pubkey, &rsig, msg32)); 249 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(ctx, &rsig, sig64, 2)); 250 CHECK(!vet_secp256k1_ecdsa_recover(ctx, &pubkey, &rsig, msg32)); 251 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(ctx, &rsig, sig64, 3)); 252 CHECK(!vet_secp256k1_ecdsa_recover(ctx, &pubkey, &rsig, msg32)); 253 254 for (recid = 0; recid < 4; recid++) { 255 int i; 256 int recid2; 257 /* (4,4) encoded in DER. */ 258 unsigned char sigbder[8] = {0x30, 0x06, 0x02, 0x01, 0x04, 0x02, 0x01, 0x04}; 259 unsigned char sigcder_zr[7] = {0x30, 0x05, 0x02, 0x00, 0x02, 0x01, 0x01}; 260 unsigned char sigcder_zs[7] = {0x30, 0x05, 0x02, 0x01, 0x01, 0x02, 0x00}; 261 unsigned char sigbderalt1[39] = { 262 0x30, 0x25, 0x02, 0x20, 0x00, 0x00, 0x00, 0x00, 263 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 264 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 265 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 266 0x00, 0x00, 0x00, 0x04, 0x02, 0x01, 0x04, 267 }; 268 unsigned char sigbderalt2[39] = { 269 0x30, 0x25, 0x02, 0x01, 0x04, 0x02, 0x20, 0x00, 270 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 271 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 272 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 273 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 274 }; 275 unsigned char sigbderalt3[40] = { 276 0x30, 0x26, 0x02, 0x21, 0x00, 0x00, 0x00, 0x00, 277 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 278 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 279 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 280 0x00, 0x00, 0x00, 0x00, 0x04, 0x02, 0x01, 0x04, 281 }; 282 unsigned char sigbderalt4[40] = { 283 0x30, 0x26, 0x02, 0x01, 0x04, 0x02, 0x21, 0x00, 284 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 285 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 286 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 287 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 288 }; 289 /* (order + r,4) encoded in DER. */ 290 unsigned char sigbderlong[40] = { 291 0x30, 0x26, 0x02, 0x21, 0x00, 0xFF, 0xFF, 0xFF, 292 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 293 0xFF, 0xFF, 0xFF, 0xFF, 0xFE, 0xBA, 0xAE, 0xDC, 294 0xE6, 0xAF, 0x48, 0xA0, 0x3B, 0xBF, 0xD2, 0x5E, 295 0x8C, 0xD0, 0x36, 0x41, 0x45, 0x02, 0x01, 0x04 296 }; 297 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(ctx, &rsig, sigb64, recid) == 1); 298 CHECK(vet_secp256k1_ecdsa_recover(ctx, &pubkeyb, &rsig, msg32) == 1); 299 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigbder, sizeof(sigbder)) == 1); 300 CHECK(vet_secp256k1_ecdsa_verify(ctx, &sig, msg32, &pubkeyb) == 1); 301 for (recid2 = 0; recid2 < 4; recid2++) { 302 vet_secp256k1_pubkey pubkey2b; 303 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(ctx, &rsig, sigb64, recid2) == 1); 304 CHECK(vet_secp256k1_ecdsa_recover(ctx, &pubkey2b, &rsig, msg32) == 1); 305 /* Verifying with (order + r,4) should always fail. */ 306 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigbderlong, sizeof(sigbderlong)) == 1); 307 CHECK(vet_secp256k1_ecdsa_verify(ctx, &sig, msg32, &pubkeyb) == 0); 308 } 309 /* DER parsing tests. */ 310 /* Zero length r/s. */ 311 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigcder_zr, sizeof(sigcder_zr)) == 0); 312 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigcder_zs, sizeof(sigcder_zs)) == 0); 313 /* Leading zeros. */ 314 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigbderalt1, sizeof(sigbderalt1)) == 0); 315 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigbderalt2, sizeof(sigbderalt2)) == 0); 316 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigbderalt3, sizeof(sigbderalt3)) == 0); 317 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigbderalt4, sizeof(sigbderalt4)) == 0); 318 sigbderalt3[4] = 1; 319 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigbderalt3, sizeof(sigbderalt3)) == 1); 320 CHECK(vet_secp256k1_ecdsa_verify(ctx, &sig, msg32, &pubkeyb) == 0); 321 sigbderalt4[7] = 1; 322 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigbderalt4, sizeof(sigbderalt4)) == 1); 323 CHECK(vet_secp256k1_ecdsa_verify(ctx, &sig, msg32, &pubkeyb) == 0); 324 /* Damage signature. */ 325 sigbder[7]++; 326 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigbder, sizeof(sigbder)) == 1); 327 CHECK(vet_secp256k1_ecdsa_verify(ctx, &sig, msg32, &pubkeyb) == 0); 328 sigbder[7]--; 329 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigbder, 6) == 0); 330 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigbder, sizeof(sigbder) - 1) == 0); 331 for(i = 0; i < 8; i++) { 332 int c; 333 unsigned char orig = sigbder[i]; 334 /*Try every single-byte change.*/ 335 for (c = 0; c < 256; c++) { 336 if (c == orig ) { 337 continue; 338 } 339 sigbder[i] = c; 340 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigbder, sizeof(sigbder)) == 0 || vet_secp256k1_ecdsa_verify(ctx, &sig, msg32, &pubkeyb) == 0); 341 } 342 sigbder[i] = orig; 343 } 344 } 345 346 /* Test r/s equal to zero */ 347 { 348 /* (1,1) encoded in DER. */ 349 unsigned char sigcder[8] = {0x30, 0x06, 0x02, 0x01, 0x01, 0x02, 0x01, 0x01}; 350 unsigned char sigc64[64] = { 351 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 352 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 353 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 354 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 355 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 356 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 357 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 358 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 359 }; 360 vet_secp256k1_pubkey pubkeyc; 361 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(ctx, &rsig, sigc64, 0) == 1); 362 CHECK(vet_secp256k1_ecdsa_recover(ctx, &pubkeyc, &rsig, msg32) == 1); 363 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigcder, sizeof(sigcder)) == 1); 364 CHECK(vet_secp256k1_ecdsa_verify(ctx, &sig, msg32, &pubkeyc) == 1); 365 sigcder[4] = 0; 366 sigc64[31] = 0; 367 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(ctx, &rsig, sigc64, 0) == 1); 368 CHECK(vet_secp256k1_ecdsa_recover(ctx, &pubkeyb, &rsig, msg32) == 0); 369 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigcder, sizeof(sigcder)) == 1); 370 CHECK(vet_secp256k1_ecdsa_verify(ctx, &sig, msg32, &pubkeyc) == 0); 371 sigcder[4] = 1; 372 sigcder[7] = 0; 373 sigc64[31] = 1; 374 sigc64[63] = 0; 375 CHECK(vet_secp256k1_ecdsa_recoverable_signature_parse_compact(ctx, &rsig, sigc64, 0) == 1); 376 CHECK(vet_secp256k1_ecdsa_recover(ctx, &pubkeyb, &rsig, msg32) == 0); 377 CHECK(vet_secp256k1_ecdsa_signature_parse_der(ctx, &sig, sigcder, sizeof(sigcder)) == 1); 378 CHECK(vet_secp256k1_ecdsa_verify(ctx, &sig, msg32, &pubkeyc) == 0); 379 } 380 } 381 382 void run_recovery_tests(void) { 383 int i; 384 for (i = 0; i < count; i++) { 385 test_ecdsa_recovery_api(); 386 } 387 for (i = 0; i < 64*count; i++) { 388 test_ecdsa_recovery_end_to_end(); 389 } 390 test_ecdsa_recovery_edge_cases(); 391 } 392 393 #endif