1/*
2 *  ccn.h
3 *  corecrypto
4 *
5 *  Created by Michael Brouwer on 7/25/10.
6 *  Copyright 2010,2011 Apple Inc. All rights reserved.
7 *
8 */
9
10#ifndef _CORECRYPTO_CCN_H_
11#define _CORECRYPTO_CCN_H_
12
13#include <corecrypto/cc_config.h>
14#include <corecrypto/cc_priv.h>  /* TODO: Get rid of this include in this header. */
15#include <stdint.h>
16#include <stdarg.h>
17
18
19typedef uint8_t cc_byte;
20typedef size_t cc_size;
21
22#if  CCN_UNIT_SIZE == 8
23typedef uint64_t cc_unit;          // 64 bit unit
24//typedef uint128_t cc_dunit;         // 128 bit double width unit
25#define CCN_LOG2_BITS_PER_UNIT  6  // 2^6 = 64 bits
26#define CC_UNIT_C(x) UINT64_C(x)
27#elif  CCN_UNIT_SIZE == 4
28typedef uint32_t cc_unit;          // 32 bit unit
29typedef uint64_t cc_dunit;         // 64 bit double width unit
30#define CCN_LOG2_BITS_PER_UNIT  5  // 2^5 = 32 bits
31#define CC_UNIT_C(x) UINT32_C(x)
32#elif CCN_UNIT_SIZE == 2
33typedef uint16_t cc_unit;          // 16 bit unit
34typedef uint32_t cc_dunit;         // 32 bit double width unit
35#define CCN_LOG2_BITS_PER_UNIT  4  // 2^4 = 16 bits
36#define CC_UNIT_C(x) UINT16_C(x)
37#elif CCN_UNIT_SIZE == 1
38typedef uint8_t cc_unit;           // 8 bit unit
39typedef uint16_t cc_dunit;         // 16 bit double width unit
40#define CCN_LOG2_BITS_PER_UNIT  3  // 2^3 = 8 bits
41#define CC_UNIT_C(x) UINT8_C(x)
42#else
43#error invalid CCN_UNIT_SIZE
44#endif
45
46// All mp types have units in little endian unit order.
47typedef cc_unit *ccn_t;                // n unit long mp
48typedef cc_unit *ccnp1_t;              // n + 1 unit long mp
49typedef cc_unit *cc2n_t;               // 2 * n unit long mp
50typedef cc_unit *cc2np2_t;             // 2 * n + 2 unit long mp
51typedef const cc_unit *ccn_in_t;       // n unit long mp
52typedef const cc_unit *ccnp1_in_t;     // n + 1 unit long mp
53typedef const cc_unit *cc2n_in_t;      // 2 * n unit long mp
54typedef const cc_unit *cc2np2_in_t;    // 2 * n + 2 unit long mp
55
56#define CCN_UNIT_BITS  (sizeof(cc_unit) * 8)
57#define CCN_UNIT_MASK  ((cc_unit)~0)
58
59
60/* Conversions between n sizeof and bits */
61
62/* Returns the sizeof a ccn vector of length _n_ units. */
63#define ccn_sizeof_n(_n_)  (sizeof(cc_unit) * (_n_))
64
65/* Returns the count (n) of a ccn vector that can represent _bits_. */
66#define ccn_nof(_bits_)  (((_bits_) + CCN_UNIT_BITS - 1) / CCN_UNIT_BITS)
67
68/* Returns the sizeof a ccn vector that can represent _bits_. */
69#define ccn_sizeof(_bits_)  (ccn_sizeof_n(ccn_nof(_bits_)))
70
71/* Returns the count (n) of a ccn vector that can represent _size_ bytes. */
72#define ccn_nof_size(_size_)  (((_size_) + CCN_UNIT_SIZE - 1) / CCN_UNIT_SIZE)
73
74/* Return the max number of bits a ccn vector of _n_ units can hold. */
75#define ccn_bitsof_n(_n_)  ((_n_) * CCN_UNIT_BITS)
76
77/* Return the max number of bits a ccn vector of _size_ bytes can hold. */
78#define ccn_bitsof_size(_size_)  ((_size_) * 8)
79
80/* Return the size of a ccn of size bytes in bytes. */
81#define ccn_sizeof_size(_size_)  ccn_sizeof_n(ccn_nof_size(_size_))
82
83/* Returns the value of bit _k_ of _ccn_, both are only evaluated once.  */
84#define ccn_bit(_ccn_, _k_) ({__typeof__ (_k_) __k = (_k_); \
85    1 & ((_ccn_)[__k / CCN_UNIT_BITS] >> (__k & (CCN_UNIT_BITS - 1)));})
86
87#define ccn_set_bit(_ccn_, _k_, _v_) ({__typeof__ (_k_) __k = (_k_);        \
88    if (_v_)                                                                \
89        (_ccn_)[__k/CCN_UNIT_BITS] |= CC_UNIT_C(1) << (__k & (CCN_UNIT_BITS - 1));     \
90    else                                                                    \
91        (_ccn_)[__k/CCN_UNIT_BITS] &= ~(CC_UNIT_C(1) << (__k & (CCN_UNIT_BITS - 1)));  \
92    })
93
94/* Macros for making ccn constants.  You must use list of CCN64_C() instances
95 separated by commas, with an optional smaller sized CCN32_C, CCN16_C, or
96 CCN8_C() instance at the end of the list, when making macros to declare
97 larger sized constants. */
98#define CCN8_C(a0) CC_UNIT_C(0x##a0)
99
100#if CCN_UNIT_SIZE >= 2
101#define CCN16_C(a1,a0) CC_UNIT_C(0x##a1##a0)
102#define ccn16_v(a0)  (a0)
103#elif CCN_UNIT_SIZE == 1
104#define CCN16_C(a1,a0) CCN8_C(a0),CCN8_C(a1)
105#define ccn16_v(a0)  (a0 & UINT8_C(0xff)),(a0 >> 8)
106#endif
107
108#if CCN_UNIT_SIZE >= 4
109#define CCN32_C(a3,a2,a1,a0) CC_UNIT_C(0x##a3##a2##a1##a0)
110#define ccn32_v(a0)  (a0)
111#else
112#define CCN32_C(a3,a2,a1,a0) CCN16_C(a1,a0),CCN16_C(a3,a2)
113#define ccn32_v(a0)  ccn16_v(a0 & UINT16_C(0xffff)),ccn16_v(a0 >> 16)
114#endif
115
116#if CCN_UNIT_SIZE == 8
117#define CCN64_C(a7,a6,a5,a4,a3,a2,a1,a0) CC_UNIT_C(0x##a7##a6##a5##a4##a3##a2##a1##a0)
118#define CCN40_C(a4,a3,a2,a1,a0) CC_UNIT_C(0x##a4##a3##a2##a1##a0)
119#define ccn64_v(a0)  (a0)
120//#define ccn64_32(a1,a0)  ((a1 << 32) | a0)
121//#define ccn_uint64(a,i) (a[i])
122#else
123#define CCN64_C(a7,a6,a5,a4,a3,a2,a1,a0) CCN32_C(a3,a2,a1,a0),CCN32_C(a7,a6,a5,a4)
124#define CCN40_C(a4,a3,a2,a1,a0) CCN32_C(a3,a2,a1,a0),CCN8_C(a4)
125#define ccn64_v(a0)  ccn32_v((uint64_t)a0 & UINT32_C(0xffffffff)),ccn32_v((uint64_t)a0 >> 32)
126//#define ccn64_32(a1,a0)  ccn32_v(a0),ccn32_v(a1)
127//#define ccn_uint64(a,i) ((uint64_t)ccn_uint32(a, i << 1 + 1) << 32 | (uint64_t)ccn_uint32(a, i << 1))
128#endif
129
130/* Macro's for reading uint32_t and uint64_t from ccns, the index is in 32 or
131   64 bit units respectively. */
132#if CCN_UNIT_SIZE == 8
133/* #define ccn_uint16(a,i) ((i & 3) == 3 ? ((uint16_t)(a[i >> 2] >> 48)) : \
134     (i & 3) == 2 ? ((uint16_t)(a[i >> 2] >> 32) & UINT16_C(0xffff)) : \
135     (i & 3) == 1 ? ((uint16_t)(a[i >> 2] >> 16) & UINT16_C(0xffff)) : \
136     ((uint16_t)(a[i >> 1] & UINT16_C(0xffff))))
137*/
138//#define ccn_uint32(a,i) (i & 1 ? ((uint32_t)(a[i >> 1] >> 32)) : ((uint32_t)(a[i >> 1] & UINT32_C(0xffffffff))))
139#elif CCN_UNIT_SIZE == 4
140//#define ccn16_v(a0)  (a0)
141//#define ccn32_v(a0)  (a0)
142//#define ccn_uint16(a,i) (i & 1 ? ((uint16_t)(a[i >> 1] >> 16)) : ((uint16_t)(a[i >> 1] & UINT16_C(0xffff))))
143//#define ccn_uint32(a,i) (a[i])
144#elif CCN_UNIT_SIZE == 2
145//#define ccn16_v(a0)  (a0)
146//#define ccn32_v(a0,a1)  (a1,a0)
147//#define ccn_uint16(a,i) (a[i])
148//#define ccn_uint32(a,i) (((uint32_t)a[i << 1 + 1]) << 16 | (uint32_t)a[i << 1]))
149#elif CCN_UNIT_SIZE == 1
150//#define ccn16_v(a0)  (a0 & UINT8_C(0xff)),(a0 >> 8)
151//#define ccn_uint16(a,i) ((uint16_t)((a[i << 1 + 1] << 8) | a[i << 1]))
152//#define ccn_uint32(a,i) ((uint32_t)ccn_uint16(a, i << 1 + 1) << 16 | (uint32_t)ccn_uint16(a, i << 1))
153#endif
154
155/* Macro's for reading uint32_t and uint64_t from ccns, the index is in 32 or
156 64 bit units respectively. */
157#if CCN_UNIT_SIZE == 8
158
159#define ccn64_32(a1,a0) (((cc_unit)a1) << 32 | ((cc_unit)a0))
160#define ccn32_32(a0) a0
161#if __LITTLE_ENDIAN__
162#define ccn32_32_parse(p,i) (((uint32_t *)p)[i])
163#else
164#define ccn32_32_parse(p,i) (((uint32_t *)p)[i^1])
165#endif
166#define ccn32_32_null 0
167
168#define ccn64_64(a0) a0
169#define ccn64_64_parse(p,i) p[i]
170#define ccn64_64_null 0
171
172#elif CCN_UNIT_SIZE == 4
173
174#define ccn32_32(a0) a0
175#define ccn32_32_parse(p,i) p[i]
176#define ccn32_32_null 0
177#define ccn64_32(a1,a0) ccn32_32(a0),ccn32_32(a1)
178
179#define ccn64_64(a1,a0) a0,a1
180#define ccn64_64_parse(p,i) p[1+(i<<1)],p[i<<1]
181#define ccn64_64_null 0,0
182
183#elif CCN_UNIT_SIZE == 2
184
185#define ccn32_32(a1,a0) a0,a1
186#define ccn32_32_parse(p,i) p[1+(i<<1)],p[i<<1]
187#define ccn32_32_null 0,0
188#define ccn64_32(a3,a2,a1,a0) ccn32_32(a1,a0),ccn32_32(a3,a2)
189
190#define ccn64_64(a3,a2,a1,a0) a0,a1,a2,a3
191#define ccn64_64_parse(p,i) p[3+(i<<2)],p[2+(i<<2)],p[1+(i<<2)],p[i<<2]
192#define ccn64_64_null 0,0,0,0
193
194#elif CCN_UNIT_SIZE == 1
195
196#define ccn32_32(a3,a2,a1,a0) a0,a1,a2,a3
197#define ccn32_32_parse(p,i) p[3+(i<<2)],p[2+(i<<2)],p[1+(i<<2)],p[i<<2]
198#define ccn32_32_null 0,0,0,0
199#define ccn64_32(a7,a6,a5,a4,a3,a2,a1,a0) ccn32_32(a3,a2,a1,a0),ccn32_32(a7,a6,a5,a4)
200
201#define ccn64_64(a7,a6,a5,a4,a3,a2,a1,a0) a0,a1,a2,a3,a4,a5,a6,a7
202#define ccn64_64_parse(p,i)  p[7+(i<<3)],p[6+(i<<3)],p[5+(i<<3)],p[4+(i<<3)],p[3+(i<<3)],p[2+(i<<3)],p[1+(i<<3)],p[i<<3]
203#define ccn64_64_null  0,0,0,0,0,0,0,0
204
205#endif
206
207
208/* Macros to construct fixed size ccn arrays from 64 or 32 bit quantities. */
209#define ccn192_64(a2,a1,a0) ccn64_64(a0),ccn64_64(a1),ccn64_64(a2)
210#define ccn224_32(a6,a5,a4,a3,a2,a1,a0) ccn64_32(a1,a0),ccn64_32(a3,a2),ccn64_32(a5,a4),ccn32_32(a6)
211#define ccn256_32(a7,a6,a5,a4,a3,a2,a1,a0) ccn64_32(a1,a0),ccn64_32(a3,a2),ccn64_32(a5,a4),ccn64_32(a7,a6)
212#define ccn384_32(a11,a10,a9,a8,a7,a6,a5,a4,a3,a2,a1,a0) ccn64_32(a1,a0),ccn64_32(a3,a2),ccn64_32(a5,a4),ccn64_32(a7,a6),ccn64_32(a9,a8),ccn64_32(a11,a10)
213
214
215#define CCN192_C(c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0) \
216    CCN64_C(a7,a6,a5,a4,a3,a2,a1,a0),\
217    CCN64_C(b7,b6,b5,b4,b3,b2,b1,b0),\
218    CCN64_C(c7,c6,c5,c4,c3,c2,c1,c0)
219
220#define CCN200_C(d0,c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0) \
221    CCN192_C(c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0),\
222    CCN8_C(d0)
223
224#define CCN224_C(d3,d2,d1,d0,c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0) \
225    CCN192_C(c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0),\
226    CCN32_C(d3,d2,d1,d0)
227
228#define CCN232_C(d4,d3,d2,d1,d0,c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0) \
229    CCN192_C(c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0),\
230    CCN40_C(d4,d3,d2,d1,d0)
231
232#define CCN256_C(d7,d6,d5,d4,d3,d2,d1,d0,c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0) \
233    CCN192_C(c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0),\
234    CCN64_C(d7,d6,d5,d4,d3,d2,d1,d0)
235
236#define CCN264_C(e0,d7,d6,d5,d4,d3,d2,d1,d0,c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0) \
237    CCN256_C(d7,d6,d5,d4,d3,d2,d1,d0,c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0),\
238    CCN8_C(e0)
239
240#define CCN384_C(f7,f6,f5,f4,f3,f2,f1,f0,e7,e6,e5,e4,e3,e2,e1,e0,d7,d6,d5,d4,d3,d2,d1,d0,c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0) \
241    CCN256_C(d7,d6,d5,d4,d3,d2,d1,d0,c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0),\
242    CCN64_C(e7,e6,e5,e4,e3,e2,e1,e0),\
243    CCN64_C(f7,f6,f5,f4,f3,f2,f1,f0)
244
245#define CCN392_C(g0,f7,f6,f5,f4,f3,f2,f1,f0,e7,e6,e5,e4,e3,e2,e1,e0,d7,d6,d5,d4,d3,d2,d1,d0,c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0) \
246    CCN384_C(f7,f6,f5,f4,f3,f2,f1,f0,e7,e6,e5,e4,e3,e2,e1,e0,d7,d6,d5,d4,d3,d2,d1,d0,c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0),\
247    CCN8_C(g0)
248
249#define CCN528_C(i1,i0,h7,h6,h5,h4,h3,h2,h1,h0,g7,g6,g5,g4,g3,g2,g1,g0,f7,f6,f5,f4,f3,f2,f1,f0,e7,e6,e5,e4,e3,e2,e1,e0,d7,d6,d5,d4,d3,d2,d1,d0,c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0) \
250    CCN256_C(d7,d6,d5,d4,d3,d2,d1,d0,c7,c6,c5,c4,c3,c2,c1,c0,b7,b6,b5,b4,b3,b2,b1,b0,a7,a6,a5,a4,a3,a2,a1,a0),\
251    CCN256_C(h7,h6,h5,h4,h3,h2,h1,h0,g7,g6,g5,g4,g3,g2,g1,g0,f7,f6,f5,f4,f3,f2,f1,f0,e7,e6,e5,e4,e3,e2,e1,e0),\
252    CCN16_C(i1,i0)
253
254#define CCN192_N  ccn_nof(192)
255#define CCN224_N  ccn_nof(224)
256#define CCN256_N  ccn_nof(256)
257#define CCN384_N  ccn_nof(384)
258#define CCN521_N  ccn_nof(521)
259
260#if defined(_ARM_ARCH_6) || defined(_ARM_ARCH_7)
261#if CCN_USE_BUILTIN_CLZ
262CC_INLINE CC_CONST
263cc_unit cc_clz(cc_unit data)
264{
265    return __builtin_clzl(data);
266}
267#else
268CC_INLINE CC_CONST
269cc_unit cc_clz(cc_unit data)
270{
271    __asm__ ("clz %0, %1\n" : "=l" (data) : "l" (data));
272    return data;
273}
274#endif /* CCN_USE_BUILTIN_CLZ */
275#endif /* !defined(_ARM_ARCH_6) && !defined(_ARM_ARCH_7) */
276
277
278#if CCN_N_INLINE
279/* Return the number of used units after stripping leading 0 units.  */
280CC_INLINE CC_PURE CC_NONNULL2
281cc_size ccn_n(cc_size n, const cc_unit *s) {
282#if 1
283    while (n-- && s[n] == 0) {}
284    return n + 1;
285#elif 0
286    while (n && s[n - 1] == 0) {
287        n -= 1;
288    }
289    return n;
290#else
291    if (n & 1) {
292        if (s[n - 1])
293            return n;
294        n &= ~1;
295    }
296    if (n & 2) {
297        cc_unit a[2] = { s[n - 1], s[n - 2] };
298        if (a[0])
299            return n - 1;
300        if (a[1])
301            return n - 2;
302        n &= ~2;
303    }
304    while (n) {
305        cc_unit a[4] = { s[n - 1], s[n - 2], s[n - 3], s[n - 4] };
306        if (a[0])
307            return n - 1;
308        if (a[1])
309            return n - 2;
310        if (a[2])
311            return n - 3;
312        if (a[3])
313            return n - 4;
314        n -= 4;
315    }
316    return n;
317#endif
318}
319#else
320/* Return the number of used units after stripping leading 0 units.  */
321CC_PURE CC_NONNULL2
322cc_size ccn_n(cc_size n, const cc_unit *s);
323#endif
324
325/* s >> k -> r return bits shifted out of least significant word in bits [0, n>
326 { N bit, scalar -> N bit } N = n * sizeof(cc_unit) * 8
327 the _multi version doesn't return the shifted bits, but does support multiple
328 word shifts.  */
329CC_NONNULL((2, 3))
330cc_unit ccn_shift_right(cc_size n, cc_unit *r, const cc_unit *s, size_t k);
331CC_NONNULL((2, 3))
332void ccn_shift_right_multi(cc_size n, cc_unit *r,const cc_unit *s, size_t k);
333
334/* s << k -> r return bits shifted out of most significant word in bits [0, n>
335 { N bit, scalar -> N bit } N = n * sizeof(cc_unit) * 8
336 the _multi version doesn't return the shifted bits, but does support multiple
337 word shifts */
338CC_NONNULL((2, 3))
339cc_unit ccn_shift_left(cc_size n, cc_unit *r, const cc_unit *s, size_t k);
340CC_NONNULL((2, 3))
341void ccn_shift_left_multi(cc_size n, cc_unit *r, const cc_unit *s, size_t k);
342
343/* s == 0 -> return 0 | s > 0 -> return index (starting at 1) of most
344 significant bit that is 1.
345 { N bit } N = n * sizeof(cc_unit) * 8 */
346CC_NONNULL2
347size_t ccn_bitlen(cc_size n, const cc_unit *s);
348
349/* Returns the number of bits which are zero before the first one bit
350   counting from least to most significant bit. */
351CC_NONNULL2
352size_t ccn_trailing_zeros(cc_size n, const cc_unit *s);
353
354/* s == 0 -> return true | s != 0 -> return false
355 { N bit } N = n * sizeof(cc_unit) * 8 */
356#define ccn_is_zero(_n_, _s_) (!ccn_n(_n_, _s_))
357
358/* s == 1 -> return true | s != 1 -> return false
359 { N bit } N = n * sizeof(cc_unit) * 8 */
360#define ccn_is_one(_n_, _s_) (ccn_n(_n_, _s_) == 1 && _s_[0] == 1)
361
362#define ccn_is_zero_or_one(_n_, _s_) (((_n_)==0) || ((ccn_n(_n_, _s_) <= 1) && (_s_[0] <= 1)))
363
364#if CCN_CMP_INLINE
365CC_INLINE CC_PURE CC_NONNULL((2, 3))
366int ccn_cmp(cc_size n, const cc_unit *s, const cc_unit *t) {
367	while (n) {
368        n--;
369        cc_unit si = s[n];
370        cc_unit ti = t[n];
371        if (si != ti)
372            return si > ti ? 1 : -1;
373	}
374	return n;
375}
376#else
377/* s < t -> return - 1 | s == t -> return 0 | s > t -> return 1
378 { N bit, N bit -> int } N = n * sizeof(cc_unit) * 8 */
379CC_PURE CC_NONNULL((2, 3))
380int ccn_cmp(cc_size n, const cc_unit *s, const cc_unit *t);
381#endif
382
383/* s < t -> return - 1 | s == t -> return 0 | s > t -> return 1
384 { N bit, M bit -> int } N = ns * sizeof(cc_unit) * 8  M = nt * sizeof(cc_unit) * 8 */
385CC_INLINE CC_NONNULL((2, 4))
386int ccn_cmpn(cc_size ns, const cc_unit *s,
387             cc_size nt, const cc_unit *t) {
388    if (ns > nt) {
389        return 1;
390    } else if (ns < nt) {
391        return -1;
392    }
393    return ccn_cmp(ns, s, t);
394}
395
396/* s - t -> r return 1 iff t > s
397 { N bit, N bit -> N bit } N = n * sizeof(cc_unit) * 8 */
398CC_NONNULL((2, 3, 4))
399cc_unit ccn_sub(cc_size n, cc_unit *r, const cc_unit *s, const cc_unit *t);
400
401/* s - v -> r return 1 iff v > s return 0 otherwise.
402 { N bit, sizeof(cc_unit) * 8 bit -> N bit } N = n * sizeof(cc_unit) * 8 */
403CC_NONNULL((2, 3))
404cc_unit ccn_sub1(cc_size n, cc_unit *r, const cc_unit *s, cc_unit v);
405
406/* s - t -> r return 1 iff t > s
407 { N bit, NT bit -> N bit  NT <= N} N = n * sizeof(cc_unit) * 8 */
408CC_INLINE
409CC_NONNULL((2, 3, 5))
410cc_unit ccn_subn(cc_size n, cc_unit *r, const cc_unit *s,
411             cc_size nt, const cc_unit *t) {
412    assert(n >= nt);
413    return ccn_sub1(n - nt, r + nt, s + nt, ccn_sub(nt, r, s, t));
414}
415
416
417/* s + t -> r return carry if result doesn't fit in n bits.
418 { N bit, N bit -> N bit } N = n * sizeof(cc_unit) * 8 */
419CC_NONNULL((2, 3, 4))
420cc_unit ccn_add(cc_size n, cc_unit *r, const cc_unit *s, const cc_unit *t);
421
422/* s + v -> r return carry if result doesn't fit in n bits.
423 { N bit, sizeof(cc_unit) * 8 bit -> N bit } N = n * sizeof(cc_unit) * 8 */
424CC_NONNULL((2, 3))
425cc_unit ccn_add1(cc_size n, cc_unit *r, const cc_unit *s, cc_unit v);
426
427/* s + t -> r return carry if result doesn't fit in n bits
428 { N bit, NT bit -> N bit  NT <= N} N = n * sizeof(cc_unit) * 8 */
429CC_INLINE
430CC_NONNULL((2, 3, 5))
431cc_unit ccn_addn(cc_size n, cc_unit *r, const cc_unit *s,
432                 cc_size nt, const cc_unit *t) {
433    assert(n >= nt);
434    return ccn_add1(n - nt, r + nt, s + nt, ccn_add(nt, r, s, t));
435}
436
437CC_NONNULL((4, 5))
438void ccn_divmod(cc_size n, cc_unit *q, cc_unit *r, const cc_unit *s, const cc_unit *t);
439
440
441CC_NONNULL((2, 3, 4))
442void ccn_lcm(cc_size n, cc_unit *r2n, const cc_unit *s, const cc_unit *t);
443
444
445/* s * t -> r_2n                   r_2n must not overlap with s nor t
446 { n bit, n bit -> 2 * n bit } n = count * sizeof(cc_unit) * 8
447 { N bit, N bit -> 2N bit } N = ccn_bitsof(n) */
448CC_NONNULL((2, 3, 4))
449void ccn_mul(cc_size n, cc_unit *r_2n, const cc_unit *s, const cc_unit *t);
450
451/* s[0..n) * v -> r[0..n)+return value
452 { N bit, sizeof(cc_unit) * 8 bit -> N + sizeof(cc_unit) * 8 bit } N = n * sizeof(cc_unit) * 8 */
453CC_NONNULL((2, 3))
454cc_unit ccn_mul1(cc_size n, cc_unit *r, const cc_unit *s, const cc_unit v);
455
456/* s[0..n) * v + r[0..n) -> r[0..n)+return value
457 { N bit, sizeof(cc_unit) * 8 bit -> N + sizeof(cc_unit) * 8 bit } N = n * sizeof(cc_unit) * 8 */
458CC_NONNULL((2, 3))
459cc_unit ccn_addmul1(cc_size n, cc_unit *r, const cc_unit *s, const cc_unit v);
460
461#if 0
462/* a % d -> n
463   {2 * n bit, n bit -> n bit } n = count * sizeof(cc_unit) * 8 */
464CC_NONNULL((2, 3, 4))
465void ccn_mod(cc_size n, cc_unit *r, const cc_unit *a_2n, const cc_unit *d);
466#endif
467
468/* r = gcd(s, t).
469   N bit, N bit -> N bit */
470CC_NONNULL((2, 3, 4))
471void ccn_gcd(cc_size n, cc_unit *r, const cc_unit *s, const cc_unit *t);
472
473/* r = gcd(s, t).
474 N bit, N bit -> O bit */
475CC_NONNULL((2, 4, 6))
476void ccn_gcdn(cc_size rn, cc_unit *r, cc_size sn, const cc_unit *s, cc_size tn, const cc_unit *t);
477
478/* r = (data, len) treated as a big endian byte array, return -1 if data
479 doesn't fit in r, return 0 otherwise. */
480CC_NONNULL((2, 4))
481int ccn_read_uint(cc_size n, cc_unit *r, size_t data_size, const uint8_t *data);
482
483/* r = (data, len) treated as a big endian byte array, return -1 if data
484 doesn't fit in r, return 0 otherwise.
485 ccn_read_uint strips leading zeroes and doesn't care about sign. */
486#define ccn_read_int(n, r, data_size, data) ccn_read_uint(n, r, data_size, data)
487
488/* Return actual size in bytes needed to serialize s. */
489CC_PURE CC_NONNULL2
490size_t ccn_write_uint_size(cc_size n, const cc_unit *s);
491
492/* Serialize s, to out.
493   First byte of byte stream is the m.s. byte of s,
494   regardless of the size of cc_unit.
495
496   No assumption is made about the alignment of out.
497
498   The out_size argument should be the value returned from ccn_write_uint_size,
499   and is also the exact number of bytes this function will write to out.
500   If out_size if less than the value returned by ccn_write_uint_size, only the
501   first out_size non-zero most significant octets of s will be written. */
502CC_NONNULL((2, 4))
503void ccn_write_uint(cc_size n, const cc_unit *s, size_t out_size, void *out);
504
505
506CC_INLINE CC_NONNULL((2, 4))
507cc_size ccn_write_uint_padded(cc_size n, const cc_unit* s, size_t out_size, uint8_t* to)
508{
509    size_t bytesInKey = ccn_write_uint_size(n, s);
510    cc_size offset = (out_size > bytesInKey) ? out_size - bytesInKey : 0;
511
512    cc_zero(offset, to);
513    ccn_write_uint(n, s, out_size - offset, to + offset);
514
515    return offset;
516}
517
518
519/*  Return actual size in bytes needed to serialize s as int
520    (adding leading zero if high bit is set). */
521CC_PURE CC_NONNULL2
522size_t ccn_write_int_size(cc_size n, const cc_unit *s);
523
524/*  Serialize s, to out.
525    First byte of byte stream is the m.s. byte of s,
526    regardless of the size of cc_unit.
527
528    No assumption is made about the alignment of out.
529
530    The out_size argument should be the value returned from ccn_write_int_size,
531    and is also the exact number of bytes this function will write to out.
532    If out_size if less than the value returned by ccn_write_int_size, only the
533    first out_size non-zero most significant octets of s will be written. */
534CC_NONNULL((2, 4))
535void ccn_write_int(cc_size n, const cc_unit *s, size_t out_size, void *out);
536
537
538/* s^2 -> r
539 { n bit -> 2 * n bit } */
540CC_INLINE CC_NONNULL((2, 3))
541void ccn_sqr(cc_size n, cc_unit *r, const cc_unit *s) {
542    ccn_mul(n, r, s, s);
543}
544
545/* s -> r
546 { n bit -> n bit } */
547CC_NONNULL((2, 3))
548void ccn_set(cc_size n, cc_unit *r, const cc_unit *s);
549
550CC_INLINE CC_NONNULL2
551void ccn_zero(cc_size n, cc_unit *r) {
552    CC_BZERO(r, ccn_sizeof_n(n));
553}
554
555CC_NONNULL2
556void ccn_zero_multi(cc_size n, cc_unit *r, ...);
557
558/* Burn (zero fill or otherwise overwrite) n cc_units of stack space. */
559void ccn_burn_stack(cc_size n);
560
561CC_INLINE CC_NONNULL2
562void ccn_seti(cc_size n, cc_unit *r, cc_unit v) {
563    /* assert(n > 0); */
564    r[0] = v;
565    ccn_zero(n - 1, r + 1);
566}
567
568CC_INLINE CC_NONNULL((2, 4))
569void ccn_setn(cc_size n, cc_unit *r, const cc_size s_size, const cc_unit *s) {
570    /* FIXME: assert not available in kernel.
571    assert(n > 0);
572    assert(s_size > 0);
573    assert(s_size <= n);
574    */
575    ccn_set(s_size, r, s);
576    ccn_zero(n - s_size, r + s_size);
577}
578
579#define CC_SWAP_HOST_BIG_64(x) \
580    ((uint64_t)((((uint64_t)(x) & 0xff00000000000000ULL) >> 56) | \
581    (((uint64_t)(x) & 0x00ff000000000000ULL) >> 40) | \
582    (((uint64_t)(x) & 0x0000ff0000000000ULL) >> 24) | \
583    (((uint64_t)(x) & 0x000000ff00000000ULL) >>  8) | \
584    (((uint64_t)(x) & 0x00000000ff000000ULL) <<  8) | \
585    (((uint64_t)(x) & 0x0000000000ff0000ULL) << 24) | \
586    (((uint64_t)(x) & 0x000000000000ff00ULL) << 40) | \
587    (((uint64_t)(x) & 0x00000000000000ffULL) << 56)))
588#define CC_SWAP_HOST_BIG_32(x) \
589    ((((x) & 0xff000000) >> 24) | \
590    (((x) & 0x00ff0000) >>  8) | \
591    (((x) & 0x0000ff00) <<  8) | \
592    (((x) & 0x000000ff) <<  24))
593#define CC_SWAP_HOST_BIG_16(x) \
594    ((((x) & 0xff00) >>  8) | \
595    (((x) & 0x00ff) <<  8))
596
597/* This should probably move if we move ccn_swap out of line. */
598#if CCN_UNIT_SIZE == 8
599#define CC_UNIT_TO_BIG(x) CC_SWAP_HOST_BIG_64(x)
600#elif CCN_UNIT_SIZE == 4
601#define CC_UNIT_TO_BIG(x) CC_SWAP_HOST_BIG_32(x)
602#elif CCN_UNIT_SIZE == 2
603#define CC_UNIT_TO_BIG(x) CC_SWAP_HOST_BIG_16(x)
604#elif CCN_UNIT_SIZE == 1
605#define CC_UNIT_TO_BIG(x) (x)
606#else
607#error unsupported CCN_UNIT_SIZE
608#endif
609
610/* Swap units in r in place from cc_unit vector byte order to big endian byte order (or back). */
611CC_INLINE CC_NONNULL2
612void ccn_swap(cc_size n, cc_unit *r) {
613    cc_unit *e;
614    for (e = r + n - 1; r < e; ++r, --e) {
615        cc_unit t = CC_UNIT_TO_BIG(*r);
616        *r = CC_UNIT_TO_BIG(*e);
617        *e = t;
618    }
619    if (n & 1)
620        *r = CC_UNIT_TO_BIG(*r);
621}
622
623CC_INLINE CC_NONNULL((2, 3, 4))
624void ccn_xor(cc_size n, cc_unit *r, const cc_unit *s, const cc_unit *t) {
625    while (n--) {
626        r[n] = s[n] ^ t[n];
627    }
628}
629
630/* Debugging */
631CC_NONNULL2
632void ccn_print(cc_size n, const cc_unit *s);
633CC_NONNULL3
634void ccn_lprint(cc_size n, const char *label, const cc_unit *s);
635
636/* Forward declaration so we don't depend on ccrng.h. */
637struct ccrng_state;
638
639#if 0
640CC_INLINE CC_NONNULL((2, 3))
641int ccn_random(cc_size n, cc_unit *r, struct ccrng_state *rng) {
642    return (RNG)->generate((RNG), ccn_sizeof_n(n), (unsigned char *)r);
643}
644#else
645#define ccn_random(_n_,_r_,_ccrng_ctx_) \
646    ccrng_generate(_ccrng_ctx_, ccn_sizeof_n(_n_), (unsigned char *)_r_)
647#endif
648
649/* Make a ccn of size ccn_nof(nbits) units with up to nbits sized random value. */
650CC_NONNULL((2, 3))
651int ccn_random_bits(cc_size nbits, cc_unit *r, struct ccrng_state *rng);
652
653#endif /* _CORECRYPTO_CCN_H_ */
654