Mercurial > dropbear
comparison libtomcrypt/src/pk/ecc/ecc_import.c @ 1471:6dba84798cd5
Update to libtomcrypt 1.18.1, merged with Dropbear changes
author | Matt Johnston <matt@ucc.asn.au> |
---|---|
date | Fri, 09 Feb 2018 21:44:05 +0800 |
parents | f849a5ca2efc |
children |
comparison
equal
deleted
inserted
replaced
1470:8bba51a55704 | 1471:6dba84798cd5 |
---|---|
3 * LibTomCrypt is a library that provides various cryptographic | 3 * LibTomCrypt is a library that provides various cryptographic |
4 * algorithms in a highly modular and flexible manner. | 4 * algorithms in a highly modular and flexible manner. |
5 * | 5 * |
6 * The library is free for all purposes without any express | 6 * The library is free for all purposes without any express |
7 * guarantee it works. | 7 * guarantee it works. |
8 * | |
9 * Tom St Denis, [email protected], http://libtom.org | |
10 */ | 8 */ |
11 | 9 |
12 /* Implements ECC over Z/pZ for curve y^2 = x^3 - 3x + b | 10 /* Implements ECC over Z/pZ for curve y^2 = x^3 - 3x + b |
13 * | 11 * |
14 * All curves taken from NIST recommendation paper of July 1999 | 12 * All curves taken from NIST recommendation paper of July 1999 |
17 #include "tomcrypt.h" | 15 #include "tomcrypt.h" |
18 | 16 |
19 /** | 17 /** |
20 @file ecc_import.c | 18 @file ecc_import.c |
21 ECC Crypto, Tom St Denis | 19 ECC Crypto, Tom St Denis |
22 */ | 20 */ |
23 | 21 |
24 #if defined(LTC_MECC) && defined(LTC_DER) | 22 #if defined(LTC_MECC) && defined(LTC_DER) |
25 | 23 |
26 static int is_point(ecc_key *key) | 24 static int _is_point(ecc_key *key) |
27 { | 25 { |
28 void *prime, *b, *t1, *t2; | 26 void *prime, *b, *t1, *t2; |
29 int err; | 27 int err; |
30 | 28 |
31 if ((err = mp_init_multi(&prime, &b, &t1, &t2, NULL)) != CRYPT_OK) { | 29 if ((err = mp_init_multi(&prime, &b, &t1, &t2, NULL)) != CRYPT_OK) { |
32 return err; | 30 return err; |
33 } | 31 } |
34 | 32 |
35 /* load prime and b */ | 33 /* load prime and b */ |
36 if ((err = mp_read_radix(prime, key->dp->prime, 16)) != CRYPT_OK) { goto error; } | 34 if ((err = mp_read_radix(prime, key->dp->prime, 16)) != CRYPT_OK) { goto error; } |
37 if ((err = mp_read_radix(b, key->dp->B, 16)) != CRYPT_OK) { goto error; } | 35 if ((err = mp_read_radix(b, key->dp->B, 16)) != CRYPT_OK) { goto error; } |
38 | 36 |
39 /* compute y^2 */ | 37 /* compute y^2 */ |
40 if ((err = mp_sqr(key->pubkey.y, t1)) != CRYPT_OK) { goto error; } | 38 if ((err = mp_sqr(key->pubkey.y, t1)) != CRYPT_OK) { goto error; } |
41 | 39 |
42 /* compute x^3 */ | 40 /* compute x^3 */ |
43 if ((err = mp_sqr(key->pubkey.x, t2)) != CRYPT_OK) { goto error; } | 41 if ((err = mp_sqr(key->pubkey.x, t2)) != CRYPT_OK) { goto error; } |
44 if ((err = mp_mod(t2, prime, t2)) != CRYPT_OK) { goto error; } | 42 if ((err = mp_mod(t2, prime, t2)) != CRYPT_OK) { goto error; } |
45 if ((err = mp_mul(key->pubkey.x, t2, t2)) != CRYPT_OK) { goto error; } | 43 if ((err = mp_mul(key->pubkey.x, t2, t2)) != CRYPT_OK) { goto error; } |
46 | 44 |
47 /* compute y^2 - x^3 */ | 45 /* compute y^2 - x^3 */ |
48 if ((err = mp_sub(t1, t2, t1)) != CRYPT_OK) { goto error; } | 46 if ((err = mp_sub(t1, t2, t1)) != CRYPT_OK) { goto error; } |
49 | 47 |
50 /* compute y^2 - x^3 + 3x */ | 48 /* compute y^2 - x^3 + 3x */ |
51 if ((err = mp_add(t1, key->pubkey.x, t1)) != CRYPT_OK) { goto error; } | 49 if ((err = mp_add(t1, key->pubkey.x, t1)) != CRYPT_OK) { goto error; } |
52 if ((err = mp_add(t1, key->pubkey.x, t1)) != CRYPT_OK) { goto error; } | 50 if ((err = mp_add(t1, key->pubkey.x, t1)) != CRYPT_OK) { goto error; } |
53 if ((err = mp_add(t1, key->pubkey.x, t1)) != CRYPT_OK) { goto error; } | 51 if ((err = mp_add(t1, key->pubkey.x, t1)) != CRYPT_OK) { goto error; } |
54 if ((err = mp_mod(t1, prime, t1)) != CRYPT_OK) { goto error; } | 52 if ((err = mp_mod(t1, prime, t1)) != CRYPT_OK) { goto error; } |
56 if ((err = mp_add(t1, prime, t1)) != CRYPT_OK) { goto error; } | 54 if ((err = mp_add(t1, prime, t1)) != CRYPT_OK) { goto error; } |
57 } | 55 } |
58 while (mp_cmp(t1, prime) != LTC_MP_LT) { | 56 while (mp_cmp(t1, prime) != LTC_MP_LT) { |
59 if ((err = mp_sub(t1, prime, t1)) != CRYPT_OK) { goto error; } | 57 if ((err = mp_sub(t1, prime, t1)) != CRYPT_OK) { goto error; } |
60 } | 58 } |
61 | 59 |
62 /* compare to b */ | 60 /* compare to b */ |
63 if (mp_cmp(t1, b) != LTC_MP_EQ) { | 61 if (mp_cmp(t1, b) != LTC_MP_EQ) { |
64 err = CRYPT_INVALID_PACKET; | 62 err = CRYPT_INVALID_PACKET; |
65 } else { | 63 } else { |
66 err = CRYPT_OK; | 64 err = CRYPT_OK; |
67 } | 65 } |
68 | 66 |
69 error: | 67 error: |
70 mp_clear_multi(prime, b, t1, t2, NULL); | 68 mp_clear_multi(prime, b, t1, t2, NULL); |
71 return err; | 69 return err; |
72 } | 70 } |
73 | 71 |
105 if (mp_init_multi(&key->pubkey.x, &key->pubkey.y, &key->pubkey.z, &key->k, NULL) != CRYPT_OK) { | 103 if (mp_init_multi(&key->pubkey.x, &key->pubkey.y, &key->pubkey.z, &key->k, NULL) != CRYPT_OK) { |
106 return CRYPT_MEM; | 104 return CRYPT_MEM; |
107 } | 105 } |
108 | 106 |
109 /* find out what type of key it is */ | 107 /* find out what type of key it is */ |
110 if ((err = der_decode_sequence_multi(in, inlen, | 108 err = der_decode_sequence_multi(in, inlen, LTC_ASN1_BIT_STRING, 1UL, flags, |
111 LTC_ASN1_BIT_STRING, 1UL, &flags, | 109 LTC_ASN1_EOL, 0UL, NULL); |
112 LTC_ASN1_EOL, 0UL, NULL)) != CRYPT_OK) { | 110 if (err != CRYPT_OK && err != CRYPT_INPUT_TOO_LONG) { |
113 goto done; | 111 goto done; |
114 } | 112 } |
115 | 113 |
116 | 114 |
117 if (flags[0] == 1) { | 115 if (flags[0] == 1) { |
124 LTC_ASN1_INTEGER, 1UL, key->pubkey.y, | 122 LTC_ASN1_INTEGER, 1UL, key->pubkey.y, |
125 LTC_ASN1_INTEGER, 1UL, key->k, | 123 LTC_ASN1_INTEGER, 1UL, key->k, |
126 LTC_ASN1_EOL, 0UL, NULL)) != CRYPT_OK) { | 124 LTC_ASN1_EOL, 0UL, NULL)) != CRYPT_OK) { |
127 goto done; | 125 goto done; |
128 } | 126 } |
129 } else { | 127 } else if (flags[0] == 0) { |
130 /* public key */ | 128 /* public key */ |
131 key->type = PK_PUBLIC; | 129 key->type = PK_PUBLIC; |
132 if ((err = der_decode_sequence_multi(in, inlen, | 130 if ((err = der_decode_sequence_multi(in, inlen, |
133 LTC_ASN1_BIT_STRING, 1UL, flags, | 131 LTC_ASN1_BIT_STRING, 1UL, flags, |
134 LTC_ASN1_SHORT_INTEGER, 1UL, &key_size, | 132 LTC_ASN1_SHORT_INTEGER, 1UL, &key_size, |
135 LTC_ASN1_INTEGER, 1UL, key->pubkey.x, | 133 LTC_ASN1_INTEGER, 1UL, key->pubkey.x, |
136 LTC_ASN1_INTEGER, 1UL, key->pubkey.y, | 134 LTC_ASN1_INTEGER, 1UL, key->pubkey.y, |
137 LTC_ASN1_EOL, 0UL, NULL)) != CRYPT_OK) { | 135 LTC_ASN1_EOL, 0UL, NULL)) != CRYPT_OK) { |
138 goto done; | 136 goto done; |
139 } | 137 } |
138 } | |
139 else { | |
140 err = CRYPT_INVALID_PACKET; | |
141 goto done; | |
140 } | 142 } |
141 | 143 |
142 if (dp == NULL) { | 144 if (dp == NULL) { |
143 /* find the idx */ | 145 /* find the idx */ |
144 for (key->idx = 0; ltc_ecc_sets[key->idx].size && (unsigned long)ltc_ecc_sets[key->idx].size != key_size; ++key->idx); | 146 for (key->idx = 0; ltc_ecc_sets[key->idx].size && (unsigned long)ltc_ecc_sets[key->idx].size != key_size; ++key->idx); |
151 key->idx = -1; | 153 key->idx = -1; |
152 key->dp = dp; | 154 key->dp = dp; |
153 } | 155 } |
154 /* set z */ | 156 /* set z */ |
155 if ((err = mp_set(key->pubkey.z, 1)) != CRYPT_OK) { goto done; } | 157 if ((err = mp_set(key->pubkey.z, 1)) != CRYPT_OK) { goto done; } |
156 | 158 |
157 /* is it a point on the curve? */ | 159 /* is it a point on the curve? */ |
158 if ((err = is_point(key)) != CRYPT_OK) { | 160 if ((err = _is_point(key)) != CRYPT_OK) { |
159 goto done; | 161 goto done; |
160 } | 162 } |
161 | 163 |
162 /* we're good */ | 164 /* we're good */ |
163 return CRYPT_OK; | 165 return CRYPT_OK; |
164 done: | 166 done: |
165 mp_clear_multi(key->pubkey.x, key->pubkey.y, key->pubkey.z, key->k, NULL); | 167 mp_clear_multi(key->pubkey.x, key->pubkey.y, key->pubkey.z, key->k, NULL); |
166 return err; | 168 return err; |
167 } | 169 } |
168 #endif | 170 #endif |
169 /* $Source$ */ | 171 /* ref: $Format:%D$ */ |
170 /* $Revision$ */ | 172 /* git commit: $Format:%H$ */ |
171 /* $Date$ */ | 173 /* commit time: $Format:%ai$ */ |
172 | 174 |