^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) * Copyright (c) 2013, Kenneth MacKay
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) * All rights reserved.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) * Redistribution and use in source and binary forms, with or without
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) * modification, are permitted provided that the following conditions are
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) * met:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) * * Redistributions of source code must retain the above copyright
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) * notice, this list of conditions and the following disclaimer.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) * * Redistributions in binary form must reproduce the above copyright
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) * notice, this list of conditions and the following disclaimer in the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) * documentation and/or other materials provided with the distribution.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) #ifndef _CRYPTO_ECC_H
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) #define _CRYPTO_ECC_H
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) /* One digit is u64 qword. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) #define ECC_CURVE_NIST_P192_DIGITS 3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) #define ECC_CURVE_NIST_P256_DIGITS 4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) #define ECC_MAX_DIGITS (512 / 64)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) #define ECC_DIGITS_TO_BYTES_SHIFT 3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) * struct ecc_point - elliptic curve point in affine coordinates
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) * @x: X coordinate in vli form.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) * @y: Y coordinate in vli form.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) * @ndigits: Length of vlis in u64 qwords.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) struct ecc_point {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) u64 *x;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) u64 *y;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) u8 ndigits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) #define ECC_POINT_INIT(x, y, ndigits) (struct ecc_point) { x, y, ndigits }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) * struct ecc_curve - definition of elliptic curve
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) * @name: Short name of the curve.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) * @g: Generator point of the curve.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) * @p: Prime number, if Barrett's reduction is used for this curve
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) * pre-calculated value 'mu' is appended to the @p after ndigits.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) * Use of Barrett's reduction is heuristically determined in
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) * vli_mmod_fast().
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) * @n: Order of the curve group.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) * @a: Curve parameter a.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) * @b: Curve parameter b.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) struct ecc_curve {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) char *name;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) struct ecc_point g;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) u64 *p;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) u64 *n;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) u64 *a;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) u64 *b;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) * ecc_is_key_valid() - Validate a given ECDH private key
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) * @curve_id: id representing the curve to use
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) * @ndigits: curve's number of digits
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) * @private_key: private key to be used for the given curve
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) * @private_key_len: private key length
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) * Returns 0 if the key is acceptable, a negative value otherwise
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) int ecc_is_key_valid(unsigned int curve_id, unsigned int ndigits,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) const u64 *private_key, unsigned int private_key_len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) * ecc_gen_privkey() - Generates an ECC private key.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) * The private key is a random integer in the range 0 < random < n, where n is a
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) * prime that is the order of the cyclic subgroup generated by the distinguished
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) * point G.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) * @curve_id: id representing the curve to use
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) * @ndigits: curve number of digits
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) * @private_key: buffer for storing the generated private key
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) * Returns 0 if the private key was generated successfully, a negative value
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) * if an error occurred.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) int ecc_gen_privkey(unsigned int curve_id, unsigned int ndigits, u64 *privkey);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) * ecc_make_pub_key() - Compute an ECC public key
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) * @curve_id: id representing the curve to use
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) * @ndigits: curve's number of digits
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) * @private_key: pregenerated private key for the given curve
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) * @public_key: buffer for storing the generated public key
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) * Returns 0 if the public key was generated successfully, a negative value
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) * if an error occurred.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) int ecc_make_pub_key(const unsigned int curve_id, unsigned int ndigits,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) const u64 *private_key, u64 *public_key);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) * crypto_ecdh_shared_secret() - Compute a shared secret
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) * @curve_id: id representing the curve to use
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) * @ndigits: curve's number of digits
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) * @private_key: private key of part A
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) * @public_key: public key of counterpart B
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) * @secret: buffer for storing the calculated shared secret
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) * Note: It is recommended that you hash the result of crypto_ecdh_shared_secret
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) * before using it for symmetric encryption or HMAC.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) * Returns 0 if the shared secret was generated successfully, a negative value
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) * if an error occurred.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) int crypto_ecdh_shared_secret(unsigned int curve_id, unsigned int ndigits,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) const u64 *private_key, const u64 *public_key,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) u64 *secret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) * ecc_is_pubkey_valid_partial() - Partial public key validation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) * @curve: elliptic curve domain parameters
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) * @pk: public key as a point
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) * Valdiate public key according to SP800-56A section 5.6.2.3.4 ECC Partial
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) * Public-Key Validation Routine.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) * Note: There is no check that the public key is in the correct elliptic curve
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) * subgroup.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) * Return: 0 if validation is successful, -EINVAL if validation is failed.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) int ecc_is_pubkey_valid_partial(const struct ecc_curve *curve,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) struct ecc_point *pk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) * ecc_is_pubkey_valid_full() - Full public key validation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) * @curve: elliptic curve domain parameters
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) * @pk: public key as a point
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) * Valdiate public key according to SP800-56A section 5.6.2.3.3 ECC Full
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) * Public-Key Validation Routine.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) * Return: 0 if validation is successful, -EINVAL if validation is failed.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) int ecc_is_pubkey_valid_full(const struct ecc_curve *curve,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) struct ecc_point *pk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) * vli_is_zero() - Determine is vli is zero
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) * @vli: vli to check.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) * @ndigits: length of the @vli
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) bool vli_is_zero(const u64 *vli, unsigned int ndigits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) * vli_cmp() - compare left and right vlis
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) * @left: vli
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) * @right: vli
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) * @ndigits: length of both vlis
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) * Returns sign of @left - @right, i.e. -1 if @left < @right,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) * 0 if @left == @right, 1 if @left > @right.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) int vli_cmp(const u64 *left, const u64 *right, unsigned int ndigits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) * vli_sub() - Subtracts right from left
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) * @result: where to write result
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) * @left: vli
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) * @right vli
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) * @ndigits: length of all vlis
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) * Note: can modify in-place.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) * Return: carry bit.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) u64 vli_sub(u64 *result, const u64 *left, const u64 *right,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) unsigned int ndigits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) * vli_from_be64() - Load vli from big-endian u64 array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) * @dest: destination vli
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) * @src: source array of u64 BE values
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) * @ndigits: length of both vli and array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) void vli_from_be64(u64 *dest, const void *src, unsigned int ndigits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) * vli_from_le64() - Load vli from little-endian u64 array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) * @dest: destination vli
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) * @src: source array of u64 LE values
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) * @ndigits: length of both vli and array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) void vli_from_le64(u64 *dest, const void *src, unsigned int ndigits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) * vli_mod_inv() - Modular inversion
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) * @result: where to write vli number
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) * @input: vli value to operate on
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) * @mod: modulus
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) * @ndigits: length of all vlis
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) void vli_mod_inv(u64 *result, const u64 *input, const u64 *mod,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) unsigned int ndigits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) * vli_mod_mult_slow() - Modular multiplication
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) * @result: where to write result value
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) * @left: vli number to multiply with @right
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) * @right: vli number to multiply with @left
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) * @mod: modulus
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) * @ndigits: length of all vlis
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) * Note: Assumes that mod is big enough curve order.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) void vli_mod_mult_slow(u64 *result, const u64 *left, const u64 *right,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) const u64 *mod, unsigned int ndigits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) * ecc_point_mult_shamir() - Add two points multiplied by scalars
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) * @result: resulting point
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) * @x: scalar to multiply with @p
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) * @p: point to multiply with @x
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) * @y: scalar to multiply with @q
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) * @q: point to multiply with @y
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) * @curve: curve
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) * Returns result = x * p + x * q over the curve.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) * This works faster than two multiplications and addition.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) void ecc_point_mult_shamir(const struct ecc_point *result,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) const u64 *x, const struct ecc_point *p,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) const u64 *y, const struct ecc_point *q,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) const struct ecc_curve *curve);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) #endif