]> git.cryptolib.org Git - avr-crypto-lib.git/blob - scal/scal-nessie.c
trivium fixed; further migrating to SCAL
[avr-crypto-lib.git] / scal / scal-nessie.c
1 /* scal-nessie.c */
2 /*
3     This file is part of the AVR-Crypto-Lib.
4     Copyright (C) 2006-2011 Daniel Otte (daniel.otte@rub.de)
5
6     This program is free software: you can redistribute it and/or modify
7     it under the terms of the GNU General Public License as published by
8     the Free Software Foundation, either version 3 of the License, or
9     (at your option) any later version.
10
11     This program is distributed in the hope that it will be useful,
12     but WITHOUT ANY WARRANTY; without even the implied warranty of
13     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14     GNU General Public License for more details.
15
16     You should have received a copy of the GNU General Public License
17     along with this program.  If not, see <http://www.gnu.org/licenses/>.
18 */
19
20 #include <stdint.h>
21 #include <string.h>
22 #include "streamcipher_descriptor.h"
23 #include "scal-basic.h"
24 #include "nessie_common.h"
25 #include "memxor.h"
26 #include <avr/pgmspace.h>
27
28 static const uint8_t normal_hooks[] PROGMEM = {
29                 0, 192/64, 256/64, 448/64
30 };
31
32 static const uint16_t long_hooks[] PROGMEM = {
33                 0, 65472/64, 65536/64, 131008/64
34 };
35
36 static const char stream0_n[] PROGMEM = "stream[0..63]";
37 static const char stream1_n[] PROGMEM = "stream[192..255]";
38 static const char stream2_n[] PROGMEM = "stream[256..319]";
39 static const char stream3_n[] PROGMEM = "stream[448..511]";
40 static const char streamX_n[] PROGMEM = "stream[0..511]xored";
41
42 static const char* stream_n_str[] PROGMEM = {
43                 stream0_n,
44                 stream1_n,
45                 stream2_n,
46                 stream3_n,
47                 streamX_n
48 };
49
50 static const char stream1_l[] PROGMEM = "stream[65472..65535]";
51 static const char stream2_l[] PROGMEM = "stream[65536..65599]";
52 static const char stream3_l[] PROGMEM = "stream[131008..131071]";
53 static const char streamX_l[] PROGMEM = "stream[0..131071]xored";
54
55 static const char* stream_l_str[] PROGMEM = {
56                 stream0_n,
57                 stream1_l,
58                 stream2_l,
59                 stream3_l,
60                 streamX_l
61 };
62
63 static const uint8_t list_of_keys[][20] PROGMEM = {
64         { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
65           0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
66         { 0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef, 0xfe, 0xdc,
67           0xba, 0x98, 0x76, 0x54, 0x32, 0x10, 0x00, 0x00, 0x00, 0x00 },
68         { 0x67, 0x45, 0x23, 0x01, 0xef, 0xcd, 0xab, 0x89, 0x98, 0xba,
69           0xdc, 0xfe, 0x10, 0x32, 0x54, 0x76, 0xc3, 0xd2, 0xe1, 0xf0 }
70 };
71
72 static const uint8_t list_of_ivs[][4] PROGMEM = {
73         { 0x00, 0x00, 0x00, 0x00 },
74         { 0x01, 0x01, 0x01, 0x01 },
75         { 0x01, 0x35, 0x77, 0xaf }
76 };
77
78 static
79 void normal_block(scgen_ctx_t *ctx){
80         uint8_t xor_block[64];
81         uint8_t block[64];
82         PGM_VOID_P hook_ptr = normal_hooks;
83         PGM_VOID_P hook_str_ptr = stream_n_str;
84         char str[21];
85         uint8_t i;
86
87         memset(xor_block, 0, 64);
88         for(i=0; i<=448/64; ++i){
89                 scal_cipher_gen_fillblock(block, 64, ctx);
90                 memxor(xor_block, block, 64);
91                 if(i==pgm_read_byte(hook_ptr)){
92                         hook_ptr = (uint8_t*)hook_ptr + 1;
93                         strcpy_P(str, (PGM_VOID_P)pgm_read_word(hook_str_ptr));
94                         hook_str_ptr = (uint8_t*)hook_str_ptr + 2;
95                         nessie_print_item(str, block, 64);
96                 }
97         }
98         strcpy_P(str, (PGM_VOID_P)pgm_read_word(hook_str_ptr));
99         nessie_print_item(str, xor_block, 64);
100 }
101
102 static
103 void long_block(scgen_ctx_t *ctx){
104         uint8_t xor_block[64];
105         uint8_t block[64];
106         PGM_VOID_P hook_ptr = long_hooks;
107         PGM_VOID_P hook_str_ptr = stream_l_str;
108         char str[24];
109         uint16_t i;
110
111         memset(xor_block, 0, 64);
112         for(i=0; i<=131008/64; ++i){
113                 scal_cipher_gen_fillblock(block, 64, ctx);
114                 memxor(xor_block, block, 64);
115                 if(i==pgm_read_word(hook_ptr)){
116                         hook_ptr = (uint8_t*)hook_ptr + 2;
117                         strcpy_P(str, (PGM_VOID_P)pgm_read_word(hook_str_ptr));
118                         hook_str_ptr =  (uint8_t*)hook_str_ptr + 2;
119                         nessie_print_item(str, block, 64);
120                 }
121                 if(i%64==0){
122                         NESSIE_SEND_ALIVE;
123                 }
124         }
125         strcpy_P(str, (PGM_VOID_P)pgm_read_word(hook_str_ptr));
126         nessie_print_item(str, xor_block, 64);
127 }
128
129 void scal_nessie_stream_run(const scdesc_t *desc, uint16_t keysize_b, uint16_t ivsize_b){
130         uint8_t name_length = strlen_P((PGM_VOID_P)pgm_read_word(&(desc->name)));
131         char name[name_length+1];
132         memcpy_P(name, (PGM_VOID_P)pgm_read_word(&(desc->name)), name_length+1);
133
134         uint8_t key[(keysize_b+7)/8];
135         uint8_t iv[(ivsize_b+7)/8];
136         uint16_t v;
137         scgen_ctx_t ctx;
138         nessie_print_header(name, keysize_b, 0, 0, 0, ivsize_b?ivsize_b:((uint16_t)-1));
139
140         memset(iv, 0, (ivsize_b+7)/8);
141         memset(key, 0, (keysize_b+7)/8);
142         /***  Test SET 1 ***/
143         nessie_print_setheader(1);
144         for(v=0;v<keysize_b; ++v){
145                 nessie_print_set_vector(1,v);
146                 key[v/8] |= 0x80>>(v&7);
147                 nessie_print_item("key", key, (keysize_b+7)/8);
148                 if(ivsize_b){
149                         nessie_print_item("IV", iv, (ivsize_b+7)/8);
150                 }
151                 scal_cipher_init(desc, key, keysize_b, iv, ivsize_b, &ctx);
152                 normal_block(&ctx);
153                 key[v/8] = 0;
154                 scal_cipher_free(&ctx);
155         }
156         /***  Test SET 2 ***/
157         nessie_print_setheader(2);
158         for(v=0;v<256; ++v){
159                 nessie_print_set_vector(2,v);
160                 memset(key, v&0xff, (keysize_b+7)/8);
161                 nessie_print_item("key", key, (keysize_b+7)/8);
162                 if(ivsize_b){
163                         nessie_print_item("IV", iv, (ivsize_b+7)/8);
164                 }
165                 scal_cipher_init(desc, key, keysize_b, iv, ivsize_b, &ctx);
166                 normal_block(&ctx);
167                 scal_cipher_free(&ctx);
168         }
169         /***  Test SET 3 ***/
170         nessie_print_setheader(3);
171         for(v=0;v<256; ++v){
172                 uint8_t i;
173                 nessie_print_set_vector(3,v);
174                 for(i=0; i<((keysize_b+7)/8); ++i){
175                         key[i]=(i+v)&0xff;
176                 }
177                 nessie_print_item("key", key, (keysize_b+7)/8);
178                 if(ivsize_b){
179                         nessie_print_item("IV", iv, (ivsize_b+7)/8);
180                 }
181                 scal_cipher_init(desc, key, keysize_b, iv, ivsize_b, &ctx);
182                 normal_block(&ctx);
183                 scal_cipher_free(&ctx);
184         }
185         /***  Test SET 4 ***/
186         nessie_print_setheader(4);
187         for(v=0;v<4; ++v){
188                 uint8_t i;
189                 nessie_print_set_vector(4,v);
190                 for(i=0; i<((keysize_b+7)/8); ++i){
191                         key[i]=(i*0x53+v*5)&0xff;
192                 }
193                 nessie_print_item("key", key, (keysize_b+7)/8);
194                 if(ivsize_b){
195                         nessie_print_item("IV", iv, (ivsize_b+7)/8);
196                 }
197                 scal_cipher_init(desc, key, keysize_b, iv, ivsize_b, &ctx);
198                 long_block(&ctx);
199                 scal_cipher_free(&ctx);
200         }
201         if(ivsize_b==0){ /* exit if there is no IV */
202                 nessie_print_footer();
203                 return;
204         }
205         /***  Test SET 5 ***/
206         nessie_print_setheader(5);
207         memset(key, 0, (keysize_b+7)/8);
208         for(v=0;v<ivsize_b; ++v){
209                 nessie_print_set_vector(5,v);
210                 iv[v/8] |= 0x80>>(v&7);
211                 nessie_print_item("key", key, (keysize_b+7)/8);
212                 nessie_print_item("IV", iv, (ivsize_b+7)/8);
213                 scal_cipher_init(desc, key, keysize_b, iv, ivsize_b, &ctx);
214                 normal_block(&ctx);
215                 scal_cipher_free(&ctx);
216                 iv[v/8] = 0;
217         }
218         /***  Test SET 6 ***/
219         nessie_print_setheader(6);
220         for(v=0;v<4; ++v){
221                 uint8_t i;
222                 nessie_print_set_vector(6,v);
223                 for(i=0; i<((keysize_b+7)/8); ++i){
224                         key[i]=(i*0x53+v*5)&0xff;
225                 }
226                 for(i=0; i<((ivsize_b+7)/8); ++i){
227                         iv[i]=(i*0x67+v*9+13)&0xff;
228                 }
229                 nessie_print_item("key", key, (keysize_b+7)/8);
230                 nessie_print_item("IV", iv, (ivsize_b+7)/8);
231                 scal_cipher_init(desc, key, keysize_b, iv, ivsize_b, &ctx);
232                 long_block(&ctx);
233                 scal_cipher_free(&ctx);
234         }
235         /***  Test SET 7 ***/
236         nessie_print_setheader(7);
237         uint8_t u;
238         for(v=0;v<3; ++v){
239                 for(u=0; u<3; ++u){
240                         uint8_t i;
241                         nessie_print_set_vector(7,v*3+u);
242                         for(i=0; i<((keysize_b+7)/8); ++i){
243                                 key[i]=pgm_read_byte(list_of_keys+20*v+(i%20));
244                         }
245                         for(i=0; i<((ivsize_b+7)/8); ++i){
246                                 key[i]=pgm_read_byte(list_of_keys+4*u+(i%4));
247                         }
248                 }
249                 nessie_print_item("key", key, (keysize_b+7)/8);
250                 nessie_print_item("IV", iv, (ivsize_b+7)/8);
251                 scal_cipher_init(desc, key, keysize_b, iv, ivsize_b, &ctx);
252                 long_block(&ctx);
253                 scal_cipher_free(&ctx);
254         }
255         nessie_print_footer();
256 }
257
258 void scal_nessie_run(const scdesc_t* desc){
259         uint16_t keysizes_count, ivsizes_count,i,j;
260         uint16_t *keysizes=NULL, *ivsizes=NULL;
261         keysizes_count = get_keysizes((PGM_VOID_P)pgm_read_word(&(desc->valid_keysize_desc)), &keysizes);
262         ivsizes_count = get_keysizes((PGM_VOID_P)pgm_read_word(&(desc->valid_ivsize_desc)), &ivsizes);
263         for(i=0; i<keysizes_count; ++i){
264                 for(j=0; j<ivsizes_count; ++j){
265                         scal_nessie_stream_run(desc, keysizes[i], ivsizes[j]);
266                 }
267         }
268 }