23 #ifndef CRYPTO_BIGNUMBERUTIL_h
24 #define CRYPTO_BIGNUMBERUTIL_h
32 #define BIGNUMBER_LIMB_8BIT 0
33 #define BIGNUMBER_LIMB_16BIT 1
34 #define BIGNUMBER_LIMB_32BIT 0
35 #define BIGNUMBER_LIMB_64BIT 0
36 #elif defined(__GNUC__) && __WORDSIZE == 64
38 #define BIGNUMBER_LIMB_8BIT 0
39 #define BIGNUMBER_LIMB_16BIT 0
40 #define BIGNUMBER_LIMB_32BIT 0
41 #define BIGNUMBER_LIMB_64BIT 1
44 #define BIGNUMBER_LIMB_8BIT 0
45 #define BIGNUMBER_LIMB_16BIT 0
46 #define BIGNUMBER_LIMB_32BIT 1
47 #define BIGNUMBER_LIMB_64BIT 0
51 #if BIGNUMBER_LIMB_8BIT
52 typedef uint8_t limb_t;
53 typedef int8_t slimb_t;
54 typedef uint16_t dlimb_t;
55 #elif BIGNUMBER_LIMB_16BIT
56 typedef uint16_t limb_t;
57 typedef int16_t slimb_t;
58 typedef uint32_t dlimb_t;
59 #elif BIGNUMBER_LIMB_32BIT
60 typedef uint32_t limb_t;
61 typedef int32_t slimb_t;
62 typedef uint64_t dlimb_t;
63 #elif BIGNUMBER_LIMB_64BIT
64 typedef uint64_t limb_t;
65 typedef int64_t slimb_t;
66 typedef unsigned __int128 dlimb_t;
68 #error "limb_t must be 8, 16, 32, or 64 bits in size"
74 static void unpackLE(limb_t *limbs,
size_t count,
75 const uint8_t *bytes,
size_t len);
76 static void unpackBE(limb_t *limbs,
size_t count,
77 const uint8_t *bytes,
size_t len);
78 static void packLE(uint8_t *bytes,
size_t len,
79 const limb_t *limbs,
size_t count);
80 static void packBE(uint8_t *bytes,
size_t len,
81 const limb_t *limbs,
size_t count);
83 static limb_t
add(limb_t *result,
const limb_t *x,
84 const limb_t *y,
size_t size);
85 static limb_t
sub(limb_t *result,
const limb_t *x,
86 const limb_t *y,
size_t size);
87 static void mul(limb_t *result,
const limb_t *x,
size_t xcount,
88 const limb_t *y,
size_t ycount);
89 static void reduceQuick(limb_t *result,
const limb_t *x,
90 const limb_t *y,
size_t size);
92 static limb_t
add_P(limb_t *result,
const limb_t *x,
93 const limb_t *y,
size_t size);
94 static limb_t
sub_P(limb_t *result,
const limb_t *x,
95 const limb_t *y,
size_t size);
96 static void mul_P(limb_t *result,
const limb_t *x,
size_t xcount,
97 const limb_t *y,
size_t ycount);
99 const limb_t *y,
size_t size);
101 static limb_t
isZero(
const limb_t *x,
size_t size);
static void reduceQuick_P(limb_t *result, const limb_t *x, const limb_t *y, size_t size)
Reduces x modulo y using subtraction where y is in program memory.
static limb_t add(limb_t *result, const limb_t *x, const limb_t *y, size_t size)
Adds two big numbers.
static limb_t sub_P(limb_t *result, const limb_t *x, const limb_t *y, size_t size)
Subtracts one big number from another where one is in program memory.
static void reduceQuick(limb_t *result, const limb_t *x, const limb_t *y, size_t size)
Reduces x modulo y using subtraction.
static limb_t sub(limb_t *result, const limb_t *x, const limb_t *y, size_t size)
Subtracts one big number from another.
Utilities to assist with implementing big number arithmetic.
static void mul_P(limb_t *result, const limb_t *x, size_t xcount, const limb_t *y, size_t ycount)
Multiplies two big numbers where one is in program memory.
static void packBE(uint8_t *bytes, size_t len, const limb_t *limbs, size_t count)
Packs the big-endian byte representation of a big number into a byte array.
static void unpackLE(limb_t *limbs, size_t count, const uint8_t *bytes, size_t len)
Unpacks the little-endian byte representation of a big number into a limb array.
static void mul(limb_t *result, const limb_t *x, size_t xcount, const limb_t *y, size_t ycount)
Multiplies two big numbers.
static void unpackBE(limb_t *limbs, size_t count, const uint8_t *bytes, size_t len)
Unpacks the big-endian byte representation of a big number into a limb array.
static void packLE(uint8_t *bytes, size_t len, const limb_t *limbs, size_t count)
Packs the little-endian byte representation of a big number into a byte array.
static limb_t isZero(const limb_t *x, size_t size)
Determine if a big number is zero.
static limb_t add_P(limb_t *result, const limb_t *x, const limb_t *y, size_t size)
Adds two big numbers where one of them is in program memory.