ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/cvsroot/spritz/spritz.c
Revision: 1.1
Committed: Fri Jan 9 09:11:16 2015 UTC (9 years, 6 months ago) by root
Content type: text/plain
Branch: MAIN
Log Message:
*** empty log message ***

File Contents

# User Rev Content
1 root 1.1 #include "spritz.h"
2    
3     #include <assert.h>
4     #include <stdint.h>
5     #include <sys/types.h>
6    
7     void
8     spritz_init (spritz_state *s)
9     {
10     s->a =
11     s->i =
12     s->j =
13     s->k =
14     s->z = 0;
15     s->w = 1;
16    
17     uint_fast8_t v = spritz_N - 1;
18     do
19     s->S[v] = v;
20     while (v--);
21     }
22    
23     void
24     spritz_update (spritz_state *s)
25     {
26     s->i += s->w;
27     s->j = s->k + s->S[s->j + s->S[s->i]];
28     s->k = s->k + s->i + s->S[s->j];
29     SPRITZ_SWAP (s->S[s->i], s->S[s->j]);
30     }
31    
32     void
33     spritz_whip (spritz_state *s, uint_fast16_t r)
34     {
35     while (r--)
36     spritz_update (s);
37    
38     s->w += 2;
39     }
40    
41     #define SPRITZ_SWAP(a,b) { uint8_t ss_c = (a); (a) = (b); (b) = ss_c; }
42    
43     void
44     spritz_crush (spritz_state *s)
45     {
46     uint_fast16_t v;
47    
48     for (v = 0; v < (spritz_N >> 1); ++v)
49     if (s->S[v] > s->S[spritz_N - 1 - v])
50     SPRITZ_SWAP (s->S[v], s->S[spritz_N - 1 - v]);
51     }
52    
53     void
54     spritz_shuffle (spritz_state *s)
55     {
56     spritz_whip (s, 2 * spritz_N); spritz_crush (s);
57     spritz_whip (s, 2 * spritz_N); spritz_crush (s);
58     spritz_whip (s, 2 * spritz_N);
59    
60     s->a = 0;
61     }
62    
63     static void
64     spritz_shuffle_absorb (spritz_state *s)
65     {
66     if (s->a == (spritz_N >> 1))
67     spritz_shuffle (s);
68     }
69    
70     void
71     spritz_absorb_nibble (spritz_state *s, uint8_t x)
72     {
73     spritz_shuffle_absorb (s);
74    
75     SPRITZ_SWAP (s->S[s->a], s->S[(spritz_N >> 1) + x]);
76     ++s->a;
77     }
78    
79     static void
80     spritz_absorb_byte (spritz_state *s, uint8_t b)
81     {
82     spritz_absorb_nibble (s, b & 15);
83     spritz_absorb_nibble (s, b >> 4);
84     }
85    
86     void
87     spritz_absorb (spritz_state *s, const void *I, size_t I_len)
88     {
89     uint8_t *i = (uint8_t *)I;
90    
91     while (I_len--)
92     spritz_absorb_byte (s, *i++);
93     }
94    
95     void
96     spritz_absorb_stop (spritz_state *s)
97     {
98     spritz_shuffle_absorb (s);
99    
100     ++s->a;
101     }
102    
103     // commonly used helper function
104     void
105     spritz_absorb_and_stop (spritz_state *s, const void *I, size_t I_len)
106     {
107     spritz_absorb (s, I, I_len);
108     spritz_absorb_stop (s);
109     }
110    
111     static void
112     spritz_shuffle_squeeze (spritz_state *s)
113     {
114     if (s->a)
115     spritz_shuffle (s);
116     }
117    
118     uint8_t
119     spritz_output (spritz_state *s)
120     {
121     return s->S[s->j + s->S[s->i + s->S[s->z + s->k]]];
122     }
123    
124     // slightly faster internal helper, drip without squeeze preparation
125     static uint8_t
126     spritz_drip_nosqueeze (spritz_state *s)
127     {
128     spritz_update (s);
129     return spritz_output (s);
130     }
131    
132     void
133     spritz_squeeze (spritz_state *s, void *P, size_t P_len)
134     {
135     spritz_shuffle_squeeze (s);
136    
137     uint8_t *p = (uint8_t *)P;
138    
139     while (P_len--)
140     *p++ = spritz_drip_nosqueeze (s);
141     }
142    
143     uint8_t
144     spritz_drip (spritz_state *s)
145     {
146     spritz_shuffle_squeeze (s);
147    
148     return spritz_drip_nosqueeze (s);
149     }
150    
151     void
152     spritz_xor_init (spritz_state *s, const void *K, size_t K_len, const void *IV, size_t IV_len)
153     {
154     spritz_init (s);
155    
156     spritz_absorb (s, K, K_len);
157    
158     if (IV)
159     {
160     spritz_absorb_stop (s);
161     spritz_absorb (s, IV, IV_len);
162     }
163    
164     spritz_shuffle_squeeze (s);
165     }
166    
167     void
168     spritz_xor_crypt (spritz_state *s, const void *I, void *O, size_t len)
169     {
170     const uint8_t *i = (const uint8_t *)I;
171     uint8_t *o = ( uint8_t *)O;
172    
173     while (len--)
174     *o++ = *i++ ^ spritz_drip_nosqueeze (s);
175     }
176    
177     void
178     spritz_hash_finish (spritz_state *s, void *H, size_t H_len)
179     {
180     spritz_absorb_stop (s);
181     assert (H_len <= 0xff);
182     spritz_absorb_byte (s, H_len);
183    
184     spritz_squeeze (s, H, H_len);
185     }
186    
187     void
188     spritz_mac_init (spritz_state *s, const void *K, size_t K_len)
189     {
190     spritz_init (s);
191     spritz_absorb_and_stop (s, K, K_len);
192     }
193    
194     void
195     spritz_aead_init (spritz_state *s, const void *K, size_t K_len)
196     {
197     spritz_mac_init (s, K, K_len);
198     }
199    
200     void
201     spritz_aead_crypt (spritz_state *s, const void *I, void *O, size_t len)
202     {
203     const uint8_t *i = (const uint8_t *)I;
204     uint8_t *o = ( uint8_t *)O;
205    
206     uint8_t x[spritz_N >> 2];
207    
208     while (len)
209     {
210     uint_fast8_t j;
211     uint8_t l = len > sizeof (x) ? sizeof (x) : len;
212     len -= l;
213    
214     spritz_squeeze (s, x, l);
215    
216     for (j = 0; j < l; ++j)
217     spritz_absorb_byte (s, *o++ = *i++ ^ x[j]);
218     }
219     }
220    
221     void
222     spritz_prng_init (spritz_state *s, const void *S, size_t S_len)
223     {
224     spritz_init (s);
225     spritz_absorb (s, S, S_len);
226     }
227