Skip to content

Commit 4a2289d

Browse files
vt-altherbertx
authored andcommitted
crypto: ecc - make ecc into separate module
ecc.c have algorithms that could be used togeter by ecdh and ecrdsa. Make it separate module. Add CRYPTO_ECC into Kconfig. EXPORT_SYMBOL and document to what seems appropriate. Move structs ecc_point and ecc_curve from ecc_curve_defs.h into ecc.h. No code changes. Signed-off-by: Vitaly Chikunov <[email protected]> Signed-off-by: Herbert Xu <[email protected]>
1 parent 3d6228a commit 4a2289d

File tree

5 files changed

+122
-23
lines changed

5 files changed

+122
-23
lines changed

crypto/Kconfig

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -248,8 +248,12 @@ config CRYPTO_DH
248248
help
249249
Generic implementation of the Diffie-Hellman algorithm.
250250

251+
config CRYPTO_ECC
252+
tristate
253+
251254
config CRYPTO_ECDH
252255
tristate "ECDH algorithm"
256+
select CRYPTO_ECC
253257
select CRYPTO_KPP
254258
select CRYPTO_RNG_DEFAULT
255259
help

crypto/Makefile

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -147,8 +147,8 @@ obj-$(CONFIG_CRYPTO_USER_API_RNG) += algif_rng.o
147147
obj-$(CONFIG_CRYPTO_USER_API_AEAD) += algif_aead.o
148148
obj-$(CONFIG_CRYPTO_ZSTD) += zstd.o
149149
obj-$(CONFIG_CRYPTO_OFB) += ofb.o
150+
obj-$(CONFIG_CRYPTO_ECC) += ecc.o
150151

151-
ecdh_generic-y := ecc.o
152152
ecdh_generic-y += ecdh.o
153153
ecdh_generic-y += ecdh_helper.o
154154
obj-$(CONFIG_CRYPTO_ECDH) += ecdh_generic.o

crypto/ecc.c

Lines changed: 18 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@
2424
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
2525
*/
2626

27+
#include <linux/module.h>
2728
#include <linux/random.h>
2829
#include <linux/slab.h>
2930
#include <linux/swab.h>
@@ -112,7 +113,7 @@ static void vli_clear(u64 *vli, unsigned int ndigits)
112113
}
113114

114115
/* Returns true if vli == 0, false otherwise. */
115-
static bool vli_is_zero(const u64 *vli, unsigned int ndigits)
116+
bool vli_is_zero(const u64 *vli, unsigned int ndigits)
116117
{
117118
int i;
118119

@@ -123,6 +124,7 @@ static bool vli_is_zero(const u64 *vli, unsigned int ndigits)
123124

124125
return true;
125126
}
127+
EXPORT_SYMBOL(vli_is_zero);
126128

127129
/* Returns nonzero if bit bit of vli is set. */
128130
static u64 vli_test_bit(const u64 *vli, unsigned int bit)
@@ -171,7 +173,7 @@ static void vli_set(u64 *dest, const u64 *src, unsigned int ndigits)
171173
}
172174

173175
/* Returns sign of left - right. */
174-
static int vli_cmp(const u64 *left, const u64 *right, unsigned int ndigits)
176+
int vli_cmp(const u64 *left, const u64 *right, unsigned int ndigits)
175177
{
176178
int i;
177179

@@ -184,6 +186,7 @@ static int vli_cmp(const u64 *left, const u64 *right, unsigned int ndigits)
184186

185187
return 0;
186188
}
189+
EXPORT_SYMBOL(vli_cmp);
187190

188191
/* Computes result = in << c, returning carry. Can modify in place
189192
* (if result == in). 0 < shift < 64.
@@ -240,7 +243,7 @@ static u64 vli_add(u64 *result, const u64 *left, const u64 *right,
240243
}
241244

242245
/* Computes result = left - right, returning borrow. Can modify in place. */
243-
static u64 vli_sub(u64 *result, const u64 *left, const u64 *right,
246+
u64 vli_sub(u64 *result, const u64 *left, const u64 *right,
244247
unsigned int ndigits)
245248
{
246249
u64 borrow = 0;
@@ -258,6 +261,7 @@ static u64 vli_sub(u64 *result, const u64 *left, const u64 *right,
258261

259262
return borrow;
260263
}
264+
EXPORT_SYMBOL(vli_sub);
261265

262266
static uint128_t mul_64_64(u64 left, u64 right)
263267
{
@@ -557,7 +561,7 @@ static void vli_mod_square_fast(u64 *result, const u64 *left,
557561
* See "From Euclid's GCD to Montgomery Multiplication to the Great Divide"
558562
* https://labs.oracle.com/techrep/2001/smli_tr-2001-95.pdf
559563
*/
560-
static void vli_mod_inv(u64 *result, const u64 *input, const u64 *mod,
564+
void vli_mod_inv(u64 *result, const u64 *input, const u64 *mod,
561565
unsigned int ndigits)
562566
{
563567
u64 a[ECC_MAX_DIGITS], b[ECC_MAX_DIGITS];
@@ -630,6 +634,7 @@ static void vli_mod_inv(u64 *result, const u64 *input, const u64 *mod,
630634

631635
vli_set(result, u, ndigits);
632636
}
637+
EXPORT_SYMBOL(vli_mod_inv);
633638

634639
/* ------ Point operations ------ */
635640

@@ -948,6 +953,7 @@ int ecc_is_key_valid(unsigned int curve_id, unsigned int ndigits,
948953

949954
return __ecc_is_key_valid(curve, private_key, ndigits);
950955
}
956+
EXPORT_SYMBOL(ecc_is_key_valid);
951957

952958
/*
953959
* ECC private keys are generated using the method of extra random bits,
@@ -1000,6 +1006,7 @@ int ecc_gen_privkey(unsigned int curve_id, unsigned int ndigits, u64 *privkey)
10001006

10011007
return 0;
10021008
}
1009+
EXPORT_SYMBOL(ecc_gen_privkey);
10031010

10041011
int ecc_make_pub_key(unsigned int curve_id, unsigned int ndigits,
10051012
const u64 *private_key, u64 *public_key)
@@ -1036,10 +1043,11 @@ int ecc_make_pub_key(unsigned int curve_id, unsigned int ndigits,
10361043
out:
10371044
return ret;
10381045
}
1046+
EXPORT_SYMBOL(ecc_make_pub_key);
10391047

10401048
/* SP800-56A section 5.6.2.3.4 partial verification: ephemeral keys only */
1041-
static int ecc_is_pubkey_valid_partial(const struct ecc_curve *curve,
1042-
struct ecc_point *pk)
1049+
int ecc_is_pubkey_valid_partial(const struct ecc_curve *curve,
1050+
struct ecc_point *pk)
10431051
{
10441052
u64 yy[ECC_MAX_DIGITS], xxx[ECC_MAX_DIGITS], w[ECC_MAX_DIGITS];
10451053

@@ -1064,8 +1072,8 @@ static int ecc_is_pubkey_valid_partial(const struct ecc_curve *curve,
10641072
return -EINVAL;
10651073

10661074
return 0;
1067-
10681075
}
1076+
EXPORT_SYMBOL(ecc_is_pubkey_valid_partial);
10691077

10701078
int crypto_ecdh_shared_secret(unsigned int curve_id, unsigned int ndigits,
10711079
const u64 *private_key, const u64 *public_key,
@@ -1121,3 +1129,6 @@ int crypto_ecdh_shared_secret(unsigned int curve_id, unsigned int ndigits,
11211129
out:
11221130
return ret;
11231131
}
1132+
EXPORT_SYMBOL(crypto_ecdh_shared_secret);
1133+
1134+
MODULE_LICENSE("Dual BSD/GPL");

crypto/ecc.h

Lines changed: 99 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,41 @@
3232

3333
#define ECC_DIGITS_TO_BYTES_SHIFT 3
3434

35+
/**
36+
* struct ecc_point - elliptic curve point in affine coordinates
37+
*
38+
* @x: X coordinate in vli form.
39+
* @y: Y coordinate in vli form.
40+
* @ndigits: Length of vlis in u64 qwords.
41+
*/
42+
struct ecc_point {
43+
u64 *x;
44+
u64 *y;
45+
u8 ndigits;
46+
};
47+
48+
/**
49+
* struct ecc_curve - definition of elliptic curve
50+
*
51+
* @name: Short name of the curve.
52+
* @g: Generator point of the curve.
53+
* @p: Prime number, if Barrett's reduction is used for this curve
54+
* pre-calculated value 'mu' is appended to the @p after ndigits.
55+
* Use of Barrett's reduction is heuristically determined in
56+
* vli_mmod_fast().
57+
* @n: Order of the curve group.
58+
* @a: Curve parameter a.
59+
* @b: Curve parameter b.
60+
*/
61+
struct ecc_curve {
62+
char *name;
63+
struct ecc_point g;
64+
u64 *p;
65+
u64 *n;
66+
u64 *a;
67+
u64 *b;
68+
};
69+
3570
/**
3671
* ecc_is_key_valid() - Validate a given ECDH private key
3772
*
@@ -91,4 +126,68 @@ int ecc_make_pub_key(const unsigned int curve_id, unsigned int ndigits,
91126
int crypto_ecdh_shared_secret(unsigned int curve_id, unsigned int ndigits,
92127
const u64 *private_key, const u64 *public_key,
93128
u64 *secret);
129+
130+
/**
131+
* ecc_is_pubkey_valid_partial() - Partial public key validation
132+
*
133+
* @curve: elliptic curve domain parameters
134+
* @pk: public key as a point
135+
*
136+
* Valdiate public key according to SP800-56A section 5.6.2.3.4 ECC Partial
137+
* Public-Key Validation Routine.
138+
*
139+
* Note: There is no check that the public key is in the correct elliptic curve
140+
* subgroup.
141+
*
142+
* Return: 0 if validation is successful, -EINVAL if validation is failed.
143+
*/
144+
int ecc_is_pubkey_valid_partial(const struct ecc_curve *curve,
145+
struct ecc_point *pk);
146+
147+
/**
148+
* vli_is_zero() - Determine is vli is zero
149+
*
150+
* @vli: vli to check.
151+
* @ndigits: length of the @vli
152+
*/
153+
bool vli_is_zero(const u64 *vli, unsigned int ndigits);
154+
155+
/**
156+
* vli_cmp() - compare left and right vlis
157+
*
158+
* @left: vli
159+
* @right: vli
160+
* @ndigits: length of both vlis
161+
*
162+
* Returns sign of @left - @right, i.e. -1 if @left < @right,
163+
* 0 if @left == @right, 1 if @left > @right.
164+
*/
165+
int vli_cmp(const u64 *left, const u64 *right, unsigned int ndigits);
166+
167+
/**
168+
* vli_sub() - Subtracts right from left
169+
*
170+
* @result: where to write result
171+
* @left: vli
172+
* @right vli
173+
* @ndigits: length of all vlis
174+
*
175+
* Note: can modify in-place.
176+
*
177+
* Return: carry bit.
178+
*/
179+
u64 vli_sub(u64 *result, const u64 *left, const u64 *right,
180+
unsigned int ndigits);
181+
182+
/**
183+
* vli_mod_inv() - Modular inversion
184+
*
185+
* @result: where to write vli number
186+
* @input: vli value to operate on
187+
* @mod: modulus
188+
* @ndigits: length of all vlis
189+
*/
190+
void vli_mod_inv(u64 *result, const u64 *input, const u64 *mod,
191+
unsigned int ndigits);
192+
94193
#endif

crypto/ecc_curve_defs.h

Lines changed: 0 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -2,21 +2,6 @@
22
#ifndef _CRYTO_ECC_CURVE_DEFS_H
33
#define _CRYTO_ECC_CURVE_DEFS_H
44

5-
struct ecc_point {
6-
u64 *x;
7-
u64 *y;
8-
u8 ndigits;
9-
};
10-
11-
struct ecc_curve {
12-
char *name;
13-
struct ecc_point g;
14-
u64 *p;
15-
u64 *n;
16-
u64 *a;
17-
u64 *b;
18-
};
19-
205
/* NIST P-192: a = p - 3 */
216
static u64 nist_p192_g_x[] = { 0xF4FF0AFD82FF1012ull, 0x7CBF20EB43A18800ull,
227
0x188DA80EB03090F6ull };

0 commit comments

Comments
 (0)