ยปCore Development>Code coverage>Modules/_blake2/impl/blake2b-ref.c

Python code coverage for Modules/_blake2/impl/blake2b-ref.c

#countcontent
1n/a/*
2n/a BLAKE2 reference source code package - reference C implementations
3n/a
4n/a Copyright 2012, Samuel Neves <sneves@dei.uc.pt>. You may use this under the
5n/a terms of the CC0, the OpenSSL Licence, or the Apache Public License 2.0, at
6n/a your option. The terms of these licenses can be found at:
7n/a
8n/a - CC0 1.0 Universal : http://creativecommons.org/publicdomain/zero/1.0
9n/a - OpenSSL license : https://www.openssl.org/source/license.html
10n/a - Apache 2.0 : http://www.apache.org/licenses/LICENSE-2.0
11n/a
12n/a More information about the BLAKE2 hash function can be found at
13n/a https://blake2.net.
14n/a*/
15n/a
16n/a#include <stdint.h>
17n/a#include <string.h>
18n/a#include <stdio.h>
19n/a
20n/a#include "blake2.h"
21n/a#include "blake2-impl.h"
22n/a
23n/astatic const uint64_t blake2b_IV[8] =
24n/a{
25n/a 0x6a09e667f3bcc908ULL, 0xbb67ae8584caa73bULL,
26n/a 0x3c6ef372fe94f82bULL, 0xa54ff53a5f1d36f1ULL,
27n/a 0x510e527fade682d1ULL, 0x9b05688c2b3e6c1fULL,
28n/a 0x1f83d9abfb41bd6bULL, 0x5be0cd19137e2179ULL
29n/a};
30n/a
31n/astatic const uint8_t blake2b_sigma[12][16] =
32n/a{
33n/a { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 } ,
34n/a { 14, 10, 4, 8, 9, 15, 13, 6, 1, 12, 0, 2, 11, 7, 5, 3 } ,
35n/a { 11, 8, 12, 0, 5, 2, 15, 13, 10, 14, 3, 6, 7, 1, 9, 4 } ,
36n/a { 7, 9, 3, 1, 13, 12, 11, 14, 2, 6, 5, 10, 4, 0, 15, 8 } ,
37n/a { 9, 0, 5, 7, 2, 4, 10, 15, 14, 1, 11, 12, 6, 8, 3, 13 } ,
38n/a { 2, 12, 6, 10, 0, 11, 8, 3, 4, 13, 7, 5, 15, 14, 1, 9 } ,
39n/a { 12, 5, 1, 15, 14, 13, 4, 10, 0, 7, 6, 3, 9, 2, 8, 11 } ,
40n/a { 13, 11, 7, 14, 12, 1, 3, 9, 5, 0, 15, 4, 8, 6, 2, 10 } ,
41n/a { 6, 15, 14, 9, 11, 3, 0, 8, 12, 2, 13, 7, 1, 4, 10, 5 } ,
42n/a { 10, 2, 8, 4, 7, 6, 1, 5, 15, 11, 9, 14, 3, 12, 13 , 0 } ,
43n/a { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 } ,
44n/a { 14, 10, 4, 8, 9, 15, 13, 6, 1, 12, 0, 2, 11, 7, 5, 3 }
45n/a};
46n/a
47n/a
48n/aBLAKE2_LOCAL_INLINE(int) blake2b_set_lastnode( blake2b_state *S )
49n/a{
50n/a S->f[1] = -1;
51n/a return 0;
52n/a}
53n/a
54n/aBLAKE2_LOCAL_INLINE(int) blake2b_clear_lastnode( blake2b_state *S )
55n/a{
56n/a S->f[1] = 0;
57n/a return 0;
58n/a}
59n/a
60n/a/* Some helper functions, not necessarily useful */
61n/aBLAKE2_LOCAL_INLINE(int) blake2b_is_lastblock( const blake2b_state *S )
62n/a{
63n/a return S->f[0] != 0;
64n/a}
65n/a
66n/aBLAKE2_LOCAL_INLINE(int) blake2b_set_lastblock( blake2b_state *S )
67n/a{
68n/a if( S->last_node ) blake2b_set_lastnode( S );
69n/a
70n/a S->f[0] = -1;
71n/a return 0;
72n/a}
73n/a
74n/aBLAKE2_LOCAL_INLINE(int) blake2b_clear_lastblock( blake2b_state *S )
75n/a{
76n/a if( S->last_node ) blake2b_clear_lastnode( S );
77n/a
78n/a S->f[0] = 0;
79n/a return 0;
80n/a}
81n/a
82n/aBLAKE2_LOCAL_INLINE(int) blake2b_increment_counter( blake2b_state *S, const uint64_t inc )
83n/a{
84n/a S->t[0] += inc;
85n/a S->t[1] += ( S->t[0] < inc );
86n/a return 0;
87n/a}
88n/a
89n/a
90n/a
91n/a/* Parameter-related functions */
92n/aBLAKE2_LOCAL_INLINE(int) blake2b_param_set_digest_length( blake2b_param *P, const uint8_t digest_length )
93n/a{
94n/a P->digest_length = digest_length;
95n/a return 0;
96n/a}
97n/a
98n/aBLAKE2_LOCAL_INLINE(int) blake2b_param_set_fanout( blake2b_param *P, const uint8_t fanout )
99n/a{
100n/a P->fanout = fanout;
101n/a return 0;
102n/a}
103n/a
104n/aBLAKE2_LOCAL_INLINE(int) blake2b_param_set_max_depth( blake2b_param *P, const uint8_t depth )
105n/a{
106n/a P->depth = depth;
107n/a return 0;
108n/a}
109n/a
110n/aBLAKE2_LOCAL_INLINE(int) blake2b_param_set_leaf_length( blake2b_param *P, const uint32_t leaf_length )
111n/a{
112n/a store32( &P->leaf_length, leaf_length );
113n/a return 0;
114n/a}
115n/a
116n/aBLAKE2_LOCAL_INLINE(int) blake2b_param_set_node_offset( blake2b_param *P, const uint64_t node_offset )
117n/a{
118n/a store64( &P->node_offset, node_offset );
119n/a return 0;
120n/a}
121n/a
122n/aBLAKE2_LOCAL_INLINE(int) blake2b_param_set_node_depth( blake2b_param *P, const uint8_t node_depth )
123n/a{
124n/a P->node_depth = node_depth;
125n/a return 0;
126n/a}
127n/a
128n/aBLAKE2_LOCAL_INLINE(int) blake2b_param_set_inner_length( blake2b_param *P, const uint8_t inner_length )
129n/a{
130n/a P->inner_length = inner_length;
131n/a return 0;
132n/a}
133n/a
134n/aBLAKE2_LOCAL_INLINE(int) blake2b_param_set_salt( blake2b_param *P, const uint8_t salt[BLAKE2B_SALTBYTES] )
135n/a{
136n/a memcpy( P->salt, salt, BLAKE2B_SALTBYTES );
137n/a return 0;
138n/a}
139n/a
140n/aBLAKE2_LOCAL_INLINE(int) blake2b_param_set_personal( blake2b_param *P, const uint8_t personal[BLAKE2B_PERSONALBYTES] )
141n/a{
142n/a memcpy( P->personal, personal, BLAKE2B_PERSONALBYTES );
143n/a return 0;
144n/a}
145n/a
146n/aBLAKE2_LOCAL_INLINE(int) blake2b_init0( blake2b_state *S )
147n/a{
148n/a int i;
149n/a memset( S, 0, sizeof( blake2b_state ) );
150n/a
151n/a for( i = 0; i < 8; ++i ) S->h[i] = blake2b_IV[i];
152n/a
153n/a return 0;
154n/a}
155n/a
156n/a/* init xors IV with input parameter block */
157n/aint blake2b_init_param( blake2b_state *S, const blake2b_param *P )
158n/a{
159n/a const uint8_t *p = ( const uint8_t * )( P );
160n/a size_t i;
161n/a
162n/a blake2b_init0( S );
163n/a
164n/a /* IV XOR ParamBlock */
165n/a for( i = 0; i < 8; ++i )
166n/a S->h[i] ^= load64( p + sizeof( S->h[i] ) * i );
167n/a
168n/a return 0;
169n/a}
170n/a
171n/a
172n/a
173n/aint blake2b_init( blake2b_state *S, const uint8_t outlen )
174n/a{
175n/a blake2b_param P[1];
176n/a
177n/a if ( ( !outlen ) || ( outlen > BLAKE2B_OUTBYTES ) ) return -1;
178n/a
179n/a P->digest_length = outlen;
180n/a P->key_length = 0;
181n/a P->fanout = 1;
182n/a P->depth = 1;
183n/a store32( &P->leaf_length, 0 );
184n/a store64( &P->node_offset, 0 );
185n/a P->node_depth = 0;
186n/a P->inner_length = 0;
187n/a memset( P->reserved, 0, sizeof( P->reserved ) );
188n/a memset( P->salt, 0, sizeof( P->salt ) );
189n/a memset( P->personal, 0, sizeof( P->personal ) );
190n/a return blake2b_init_param( S, P );
191n/a}
192n/a
193n/a
194n/aint blake2b_init_key( blake2b_state *S, const uint8_t outlen, const void *key, const uint8_t keylen )
195n/a{
196n/a blake2b_param P[1];
197n/a
198n/a if ( ( !outlen ) || ( outlen > BLAKE2B_OUTBYTES ) ) return -1;
199n/a
200n/a if ( !key || !keylen || keylen > BLAKE2B_KEYBYTES ) return -1;
201n/a
202n/a P->digest_length = outlen;
203n/a P->key_length = keylen;
204n/a P->fanout = 1;
205n/a P->depth = 1;
206n/a store32( &P->leaf_length, 0 );
207n/a store64( &P->node_offset, 0 );
208n/a P->node_depth = 0;
209n/a P->inner_length = 0;
210n/a memset( P->reserved, 0, sizeof( P->reserved ) );
211n/a memset( P->salt, 0, sizeof( P->salt ) );
212n/a memset( P->personal, 0, sizeof( P->personal ) );
213n/a
214n/a if( blake2b_init_param( S, P ) < 0 ) return -1;
215n/a
216n/a {
217n/a uint8_t block[BLAKE2B_BLOCKBYTES];
218n/a memset( block, 0, BLAKE2B_BLOCKBYTES );
219n/a memcpy( block, key, keylen );
220n/a blake2b_update( S, block, BLAKE2B_BLOCKBYTES );
221n/a secure_zero_memory( block, BLAKE2B_BLOCKBYTES ); /* Burn the key from stack */
222n/a }
223n/a return 0;
224n/a}
225n/a
226n/astatic int blake2b_compress( blake2b_state *S, const uint8_t block[BLAKE2B_BLOCKBYTES] )
227n/a{
228n/a uint64_t m[16];
229n/a uint64_t v[16];
230n/a int i;
231n/a
232n/a for( i = 0; i < 16; ++i )
233n/a m[i] = load64( block + i * sizeof( m[i] ) );
234n/a
235n/a for( i = 0; i < 8; ++i )
236n/a v[i] = S->h[i];
237n/a
238n/a v[ 8] = blake2b_IV[0];
239n/a v[ 9] = blake2b_IV[1];
240n/a v[10] = blake2b_IV[2];
241n/a v[11] = blake2b_IV[3];
242n/a v[12] = S->t[0] ^ blake2b_IV[4];
243n/a v[13] = S->t[1] ^ blake2b_IV[5];
244n/a v[14] = S->f[0] ^ blake2b_IV[6];
245n/a v[15] = S->f[1] ^ blake2b_IV[7];
246n/a#define G(r,i,a,b,c,d) \
247n/a do { \
248n/a a = a + b + m[blake2b_sigma[r][2*i+0]]; \
249n/a d = rotr64(d ^ a, 32); \
250n/a c = c + d; \
251n/a b = rotr64(b ^ c, 24); \
252n/a a = a + b + m[blake2b_sigma[r][2*i+1]]; \
253n/a d = rotr64(d ^ a, 16); \
254n/a c = c + d; \
255n/a b = rotr64(b ^ c, 63); \
256n/a } while(0)
257n/a#define ROUND(r) \
258n/a do { \
259n/a G(r,0,v[ 0],v[ 4],v[ 8],v[12]); \
260n/a G(r,1,v[ 1],v[ 5],v[ 9],v[13]); \
261n/a G(r,2,v[ 2],v[ 6],v[10],v[14]); \
262n/a G(r,3,v[ 3],v[ 7],v[11],v[15]); \
263n/a G(r,4,v[ 0],v[ 5],v[10],v[15]); \
264n/a G(r,5,v[ 1],v[ 6],v[11],v[12]); \
265n/a G(r,6,v[ 2],v[ 7],v[ 8],v[13]); \
266n/a G(r,7,v[ 3],v[ 4],v[ 9],v[14]); \
267n/a } while(0)
268n/a ROUND( 0 );
269n/a ROUND( 1 );
270n/a ROUND( 2 );
271n/a ROUND( 3 );
272n/a ROUND( 4 );
273n/a ROUND( 5 );
274n/a ROUND( 6 );
275n/a ROUND( 7 );
276n/a ROUND( 8 );
277n/a ROUND( 9 );
278n/a ROUND( 10 );
279n/a ROUND( 11 );
280n/a
281n/a for( i = 0; i < 8; ++i )
282n/a S->h[i] = S->h[i] ^ v[i] ^ v[i + 8];
283n/a
284n/a#undef G
285n/a#undef ROUND
286n/a return 0;
287n/a}
288n/a
289n/a/* inlen now in bytes */
290n/aint blake2b_update( blake2b_state *S, const uint8_t *in, uint64_t inlen )
291n/a{
292n/a while( inlen > 0 )
293n/a {
294n/a size_t left = S->buflen;
295n/a size_t fill = 2 * BLAKE2B_BLOCKBYTES - left;
296n/a
297n/a if( inlen > fill )
298n/a {
299n/a memcpy( S->buf + left, in, fill ); /* Fill buffer */
300n/a S->buflen += fill;
301n/a blake2b_increment_counter( S, BLAKE2B_BLOCKBYTES );
302n/a blake2b_compress( S, S->buf ); /* Compress */
303n/a memcpy( S->buf, S->buf + BLAKE2B_BLOCKBYTES, BLAKE2B_BLOCKBYTES ); /* Shift buffer left */
304n/a S->buflen -= BLAKE2B_BLOCKBYTES;
305n/a in += fill;
306n/a inlen -= fill;
307n/a }
308n/a else /* inlen <= fill */
309n/a {
310n/a memcpy( S->buf + left, in, (size_t)inlen );
311n/a S->buflen += (size_t)inlen; /* Be lazy, do not compress */
312n/a in += inlen;
313n/a inlen -= inlen;
314n/a }
315n/a }
316n/a
317n/a return 0;
318n/a}
319n/a
320n/a/* Is this correct? */
321n/aint blake2b_final( blake2b_state *S, uint8_t *out, uint8_t outlen )
322n/a{
323n/a uint8_t buffer[BLAKE2B_OUTBYTES] = {0};
324n/a int i;
325n/a
326n/a if( out == NULL || outlen == 0 || outlen > BLAKE2B_OUTBYTES )
327n/a return -1;
328n/a
329n/a if( blake2b_is_lastblock( S ) )
330n/a return -1;
331n/a
332n/a if( S->buflen > BLAKE2B_BLOCKBYTES )
333n/a {
334n/a blake2b_increment_counter( S, BLAKE2B_BLOCKBYTES );
335n/a blake2b_compress( S, S->buf );
336n/a S->buflen -= BLAKE2B_BLOCKBYTES;
337n/a memmove( S->buf, S->buf + BLAKE2B_BLOCKBYTES, S->buflen );
338n/a }
339n/a
340n/a blake2b_increment_counter( S, S->buflen );
341n/a blake2b_set_lastblock( S );
342n/a memset( S->buf + S->buflen, 0, 2 * BLAKE2B_BLOCKBYTES - S->buflen ); /* Padding */
343n/a blake2b_compress( S, S->buf );
344n/a
345n/a for( i = 0; i < 8; ++i ) /* Output full hash to temp buffer */
346n/a store64( buffer + sizeof( S->h[i] ) * i, S->h[i] );
347n/a
348n/a memcpy( out, buffer, outlen );
349n/a return 0;
350n/a}
351n/a
352n/a/* inlen, at least, should be uint64_t. Others can be size_t. */
353n/aint blake2b( uint8_t *out, const void *in, const void *key, const uint8_t outlen, const uint64_t inlen, uint8_t keylen )
354n/a{
355n/a blake2b_state S[1];
356n/a
357n/a /* Verify parameters */
358n/a if ( NULL == in && inlen > 0 ) return -1;
359n/a
360n/a if ( NULL == out ) return -1;
361n/a
362n/a if( NULL == key && keylen > 0 ) return -1;
363n/a
364n/a if( !outlen || outlen > BLAKE2B_OUTBYTES ) return -1;
365n/a
366n/a if( keylen > BLAKE2B_KEYBYTES ) return -1;
367n/a
368n/a if( keylen > 0 )
369n/a {
370n/a if( blake2b_init_key( S, outlen, key, keylen ) < 0 ) return -1;
371n/a }
372n/a else
373n/a {
374n/a if( blake2b_init( S, outlen ) < 0 ) return -1;
375n/a }
376n/a
377n/a blake2b_update( S, ( const uint8_t * )in, inlen );
378n/a blake2b_final( S, out, outlen );
379n/a return 0;
380n/a}
381n/a
382n/a#if defined(SUPERCOP)
383n/aint crypto_hash( unsigned char *out, unsigned char *in, unsigned long long inlen )
384n/a{
385n/a return blake2b( out, in, NULL, BLAKE2B_OUTBYTES, inlen, 0 );
386n/a}
387n/a#endif
388n/a
389n/a#if defined(BLAKE2B_SELFTEST)
390n/a#include <string.h>
391n/a#include "blake2-kat.h"
392n/aint main( int argc, char **argv )
393n/a{
394n/a uint8_t key[BLAKE2B_KEYBYTES];
395n/a uint8_t buf[KAT_LENGTH];
396n/a size_t i;
397n/a
398n/a for( i = 0; i < BLAKE2B_KEYBYTES; ++i )
399n/a key[i] = ( uint8_t )i;
400n/a
401n/a for( i = 0; i < KAT_LENGTH; ++i )
402n/a buf[i] = ( uint8_t )i;
403n/a
404n/a for( i = 0; i < KAT_LENGTH; ++i )
405n/a {
406n/a uint8_t hash[BLAKE2B_OUTBYTES];
407n/a blake2b( hash, buf, key, BLAKE2B_OUTBYTES, i, BLAKE2B_KEYBYTES );
408n/a
409n/a if( 0 != memcmp( hash, blake2b_keyed_kat[i], BLAKE2B_OUTBYTES ) )
410n/a {
411n/a puts( "error" );
412n/a return -1;
413n/a }
414n/a }
415n/a
416n/a puts( "ok" );
417n/a return 0;
418n/a}
419n/a#endif
420n/a