renamed 'hf mfdes readdata, writedata' to 'read/write'
[RRG-proxmark3.git] / client / deps / hardnested / hardnested_tables.c
blob1ab600275568462df48380de108cf01a05ce3ba2
1 //-----------------------------------------------------------------------------
2 // Copyright (C) 2015, 2016 by piwi
3 //
4 // This code is licensed to you under the terms of the GNU GPL, version 2 or,
5 // at your option, any later version. See the LICENSE.txt file for the text of
6 // the license.
7 //-----------------------------------------------------------------------------
8 // Implements a card only attack based on crypto text (encrypted nonces
9 // received during a nested authentication) only. Unlike other card only
10 // attacks this doesn't rely on implementation errors but only on the
11 // inherent weaknesses of the crypto1 cypher. Described in
12 // Carlo Meijer, Roel Verdult, "Ciphertext-only Cryptanalysis on Hardened
13 // Mifare Classic Cards" in Proceedings of the 22nd ACM SIGSAC Conference on
14 // Computer and Communications Security, 2015
15 //-----------------------------------------------------------------------------
17 // This program calculates tables with possible states for a given
18 // bitflip property.
20 //-----------------------------------------------------------------------------
22 // To compile it:
23 // gcc -I../../../common -I../../../include -o hardnested_tables hardnested_tables.c
25 #include <inttypes.h>
26 #include <stdbool.h>
27 #include <stdlib.h>
28 #ifndef __APPLE__
29 #include <malloc.h>
30 #endif
31 #include <string.h>
32 #include <stdio.h>
33 #include <time.h>
34 #include "crapto1/crapto1.h"
35 #include "parity.h"
38 #define NUM_PART_SUMS 9
39 #define BITFLIP_2ND_BYTE 0x0200
41 typedef enum {
42 EVEN_STATE = 0,
43 ODD_STATE = 1
44 } odd_even_t;
47 static uint16_t PartialSumProperty(uint32_t state, odd_even_t odd_even) {
48 uint16_t sum = 0;
49 for (uint16_t j = 0; j < 16; j++) {
50 uint32_t st = state;
51 uint16_t part_sum = 0;
52 if (odd_even == ODD_STATE) {
53 part_sum ^= filter(st);
54 for (uint16_t i = 0; i < 4; i++) {
55 st = (st << 1) | ((j >> (3 - i)) & 0x01) ;
56 part_sum ^= filter(st);
58 part_sum ^= 1; // XOR 1 cancelled out for the other 8 bits
59 } else {
60 for (uint16_t i = 0; i < 4; i++) {
61 st = (st << 1) | ((j >> (3 - i)) & 0x01) ;
62 part_sum ^= filter(st);
65 sum += part_sum;
67 return sum;
71 //////////////////////////////////////////////////////////////////////////////////////////////////////////////////
72 // bitarray functions
74 #if defined (_WIN32)
75 #define malloc_bitarray(x) __builtin_assume_aligned(_aligned_malloc((x), __BIGGEST_ALIGNMENT__), __BIGGEST_ALIGNMENT__)
76 #define free_bitarray(x) _aligned_free(x)
77 #elif defined (__APPLE__)
78 static void *malloc_bitarray(size_t x) {
79 char *allocated_memory;
80 if (posix_memalign((void **)&allocated_memory, __BIGGEST_ALIGNMENT__, x)) {
81 return NULL;
82 } else {
83 return __builtin_assume_aligned(allocated_memory, __BIGGEST_ALIGNMENT__);
86 #define free_bitarray(x) free(x)
87 #else
88 #define malloc_bitarray(x) memalign(__BIGGEST_ALIGNMENT__, (x))
89 #define free_bitarray(x) free(x)
90 #endif
92 static inline void clear_bitarray24(uint32_t *bitarray) {
93 memset(bitarray, 0x00, sizeof(uint32_t) * (1 << 19));
97 static inline uint32_t test_bit24(uint32_t *bitarray, uint32_t index) {
98 return bitarray[index >> 5] & (0x80000000 >> (index & 0x0000001f));
102 static inline void set_bit24(uint32_t *bitarray, uint32_t index) {
103 bitarray[index >> 5] |= 0x80000000 >> (index & 0x0000001f);
107 static inline uint32_t next_state(uint32_t *bitset, uint32_t state) {
108 if (++state == 1 << 24) return 1 << 24;
109 uint32_t index = state >> 5;
110 uint_fast8_t bit = state & 0x1f;
111 uint32_t line = bitset[index] << bit;
112 while (bit <= 0x1f) {
113 if (line & 0x80000000) return state;
114 state++;
115 bit++;
116 line <<= 1;
118 index++;
119 while (bitset[index] == 0x00000000 && state < 1 << 24) {
120 index++;
121 state += 0x20;
123 if (state >= 1 << 24) return 1 << 24;
124 #if defined __GNUC__
125 return state + __builtin_clz(bitset[index]);
126 #else
127 bit = 0x00;
128 line = bitset[index];
129 while (bit <= 0x1f) {
130 if (line & 0x80000000) return state;
131 state++;
132 bit++;
133 line <<= 1;
135 return 1 << 24;
136 #endif
140 static inline uint32_t next_not_state(uint32_t *bitset, uint32_t state) {
141 if (++state == 1 << 24) return 1 << 24;
142 uint32_t index = state >> 5;
143 uint_fast8_t bit = state & 0x1f;
144 uint32_t line = bitset[index] << bit;
145 while (bit <= 0x1f) {
146 if ((line & 0x80000000) == 0) return state;
147 state++;
148 bit++;
149 line <<= 1;
151 index++;
152 while (bitset[index] == 0xffffffff && state < 1 << 24) {
153 index++;
154 state += 0x20;
156 if (state >= 1 << 24) return 1 << 24;
157 #if defined __GNUC__
158 return state + __builtin_clz(~bitset[index]);
159 #else
160 bit = 0x00;
161 line = bitset[index];
162 while (bit <= 0x1f) {
163 if ((line & 0x80000000) == 0) return state;
164 state++;
165 bit++;
166 line <<= 1;
168 return 1 << 24;
169 #endif
173 static inline uint32_t bitcount(uint32_t a) {
174 #if defined __GNUC__
175 return __builtin_popcountl(a);
176 #else
177 a = a - ((a >> 1) & 0x55555555);
178 a = (a & 0x33333333) + ((a >> 2) & 0x33333333);
179 return (((a + (a >> 4)) & 0x0f0f0f0f) * 0x01010101) >> 24;
180 #endif
184 static inline uint32_t count_states(uint32_t *bitset) {
185 uint32_t count = 0;
186 for (uint32_t i = 0; i < (1 << 19); i++) {
187 count += bitcount(bitset[i]);
189 return count;
193 static void write_bitflips_file(odd_even_t odd_even, uint16_t bitflip, int sum_a0, uint32_t *bitset, uint32_t count) {
194 char filename[80];
195 sprintf(filename, "bitflip_%d_%03" PRIx16 "_sum%d_states.bin", odd_even, bitflip, sum_a0);
196 FILE *outfile = fopen(filename, "wb");
197 fwrite(&count, 1, sizeof(count), outfile);
198 fwrite(bitset, 1, sizeof(uint32_t) * (1 << 19), outfile);
199 fclose(outfile);
203 uint32_t *restrict part_sum_a0_bitarrays[2][NUM_PART_SUMS];
205 static void init_part_sum_bitarrays(void) {
206 printf("init_part_sum_bitarrays()...");
207 for (odd_even_t odd_even = EVEN_STATE; odd_even <= ODD_STATE; odd_even++) {
208 for (uint16_t part_sum_a0 = 0; part_sum_a0 < NUM_PART_SUMS; part_sum_a0++) {
209 part_sum_a0_bitarrays[odd_even][part_sum_a0] = (uint32_t *)malloc_bitarray(sizeof(uint32_t) * (1 << 19));
210 if (part_sum_a0_bitarrays[odd_even][part_sum_a0] == NULL) {
211 printf("Out of memory error in init_part_suma0_statelists(). Aborting...\n");
212 exit(4);
214 clear_bitarray24(part_sum_a0_bitarrays[odd_even][part_sum_a0]);
217 for (odd_even_t odd_even = EVEN_STATE; odd_even <= ODD_STATE; odd_even++) {
218 //printf("(%d, %" PRIu16 ")...", odd_even, part_sum_a0);
219 for (uint32_t state = 0; state < (1 << 20); state++) {
220 uint16_t part_sum_a0 = PartialSumProperty(state, odd_even) / 2;
221 for (uint16_t low_bits = 0; low_bits < 1 << 4; low_bits++) {
222 set_bit24(part_sum_a0_bitarrays[odd_even][part_sum_a0], state << 4 | low_bits);
226 printf("done.\n");
230 static void free_part_sum_bitarrays(void) {
231 printf("free_part_sum_bitarrays()...");
232 for (int16_t part_sum_a0 = (NUM_PART_SUMS - 1); part_sum_a0 >= 0; part_sum_a0--) {
233 free_bitarray(part_sum_a0_bitarrays[ODD_STATE][part_sum_a0]);
235 for (int16_t part_sum_a0 = (NUM_PART_SUMS - 1); part_sum_a0 >= 0; part_sum_a0--) {
236 free_bitarray(part_sum_a0_bitarrays[EVEN_STATE][part_sum_a0]);
238 printf("done.\n");
241 uint32_t *restrict sum_a0_bitarray[2];
243 void init_sum_bitarray(uint16_t sum_a0) {
244 printf("init_sum_bitarray()...\n");
245 for (odd_even_t odd_even = EVEN_STATE; odd_even <= ODD_STATE; odd_even++) {
246 sum_a0_bitarray[odd_even] = (uint32_t *)malloc_bitarray(sizeof(uint32_t) * (1 << 19));
247 if (sum_a0_bitarray[odd_even] == NULL) {
248 printf("Out of memory error in init_sum_bitarrays(). Aborting...\n");
249 exit(4);
251 clear_bitarray24(sum_a0_bitarray[odd_even]);
253 for (uint8_t p = 0; p < NUM_PART_SUMS; p++) {
254 for (uint8_t q = 0; q < NUM_PART_SUMS; q++) {
255 if (sum_a0 == 2 * p * (16 - 2 * q) + (16 - 2 * p) * 2 * q) {
256 for (uint32_t i = 0; i < (1 << 19); i++) {
257 sum_a0_bitarray[EVEN_STATE][i] |= part_sum_a0_bitarrays[EVEN_STATE][q][i];
258 sum_a0_bitarray[ODD_STATE][i] |= part_sum_a0_bitarrays[ODD_STATE][p][i];
263 for (odd_even_t odd_even = EVEN_STATE; odd_even <= ODD_STATE; odd_even++) {
264 uint32_t count = count_states(sum_a0_bitarray[odd_even]);
265 printf("sum_a0_bitarray[%s] has %u states (%5.2f%%)\n", odd_even == EVEN_STATE ? "even" : "odd ", count, (float)count / (1 << 24) * 100.0);
267 printf("done.\n");
271 static void free_sum_bitarray(void) {
272 printf("free_sum_bitarray()...");
273 free_bitarray(sum_a0_bitarray[ODD_STATE]);
274 free_bitarray(sum_a0_bitarray[EVEN_STATE]);
275 printf("done.\n");
279 static void precalculate_bit0_bitflip_bitarrays(uint8_t const bitflip, uint16_t const sum_a0) {
280 // #define TEST_RUN
281 #ifdef TEST_RUN
282 #define NUM_TEST_STATES (1<<10)
283 #else
284 #define NUM_TEST_STATES (1<<23)
285 #endif
287 time_t start_time = time(NULL);
288 time_t last_check_time = start_time;
290 uint32_t *restrict test_bitarray[2];
291 uint32_t *restrict test_not_bitarray[2];
293 test_bitarray[EVEN_STATE] = malloc_bitarray(sizeof(uint32_t) * (1 << 19));
294 clear_bitarray24(test_bitarray[EVEN_STATE]);
295 test_bitarray[ODD_STATE] = malloc_bitarray(sizeof(uint32_t) * (1 << 19));
296 clear_bitarray24(test_bitarray[ODD_STATE]);
298 test_not_bitarray[EVEN_STATE] = malloc_bitarray(sizeof(uint32_t) * (1 << 19));
299 clear_bitarray24(test_not_bitarray[EVEN_STATE]);
300 test_not_bitarray[ODD_STATE] = malloc_bitarray(sizeof(uint32_t) * (1 << 19));
301 clear_bitarray24(test_not_bitarray[ODD_STATE]);
303 uint32_t count[2];
304 bool all_odd_states_are_possible_for_notbitflip = false;
306 printf("\n\nStarting search for crypto1 states resulting in bitflip property 0x%03x...\n", bitflip);
307 for (uint32_t even_state = next_state(sum_a0_bitarray[EVEN_STATE], -1); even_state < NUM_TEST_STATES; even_state = next_state(sum_a0_bitarray[EVEN_STATE], even_state)) {
308 bool even_state_is_possible = false;
309 time_t time_now = time(NULL);
310 if (difftime(time_now, last_check_time) > 5 * 60) { // print status every 5 minutes
311 float runtime = difftime(time_now, start_time);
312 float remaining_time = runtime * ((1 << 23) - even_state) / even_state;
313 printf("\n%1.1f hours elapsed, expected completion in %1.1f hours (%1.1f days)", runtime / 3600, remaining_time / 3600, remaining_time / 3600 / 24);
314 last_check_time = time_now;
316 for (uint32_t odd_state = next_state(sum_a0_bitarray[ODD_STATE], -1); odd_state < (1 << 24); odd_state = next_state(test_bitarray[ODD_STATE], odd_state)) {
317 if (even_state_is_possible && test_bit24(test_bitarray[ODD_STATE], odd_state)) continue;
318 // load crypto1 state
319 struct Crypto1State cs;
320 cs.odd = odd_state >> 4;
321 cs.even = even_state >> 4;
323 // track flipping bits in state
324 struct Crypto1DeltaState {
325 uint_fast8_t odd;
326 uint_fast8_t even;
327 } cs_delta;
328 cs_delta.odd = 0;
329 cs_delta.even = 0;
331 uint_fast16_t keystream = 0;
333 // decrypt 9 bits
334 for (int i = 0; i < 9; i++) {
335 uint_fast8_t keystream_bit = filter(cs.odd & 0x000fffff) ^ filter((cs.odd & 0x000fffff) ^ cs_delta.odd);
336 keystream = keystream << 1 | keystream_bit;
337 uint_fast8_t nt_bit = BIT(bitflip, i) ^ keystream_bit;
338 uint_fast8_t LSFR_feedback = BIT(cs_delta.odd, 2) ^ BIT(cs_delta.even, 2) ^ BIT(cs_delta.odd, 3);
340 cs_delta.even = cs_delta.even << 1 | (LSFR_feedback ^ nt_bit);
341 uint_fast8_t tmp = cs_delta.odd;
342 cs_delta.odd = cs_delta.even;
343 cs_delta.even = tmp;
345 cs.even = cs.odd;
346 if (i & 1) {
347 cs.odd = odd_state >> (7 - i) / 2;
348 } else {
349 cs.odd = even_state >> (7 - i) / 2;
353 if (evenparity32(keystream) == evenparity32(bitflip)) {
354 // found valid bitflip state
355 even_state_is_possible = true;
356 set_bit24(test_bitarray[EVEN_STATE], even_state);
357 set_bit24(test_bitarray[EVEN_STATE], 1 << 23 | even_state);
358 set_bit24(test_bitarray[ODD_STATE], odd_state);
359 } else {
360 // found valid !bitflip state
361 set_bit24(test_not_bitarray[EVEN_STATE], even_state);
362 set_bit24(test_not_bitarray[EVEN_STATE], 1 << 23 | even_state);
363 set_bit24(test_not_bitarray[ODD_STATE], odd_state);
366 if (!even_state_is_possible) {
367 all_odd_states_are_possible_for_notbitflip = true;
371 printf("\nAnalysis completed. Checking for effective bitflip properties...\n");
372 for (odd_even_t odd_even = EVEN_STATE; odd_even <= ODD_STATE; odd_even++) {
373 count[odd_even] = count_states(test_bitarray[odd_even]);
374 if (count[odd_even] != 1 << 24) {
375 printf("Writing %u possible %s states for bitflip property %03x (%u (%1.2f%%) states eliminated)\n",
376 count[odd_even],
377 odd_even == EVEN_STATE ? "even" : "odd",
378 bitflip,
379 (1 << 24) - count[odd_even],
380 (float)((1 << 24) - count[odd_even]) / (1 << 24) * 100.0);
381 #ifndef TEST_RUN
382 write_bitflips_file(odd_even, bitflip, sum_a0, test_bitarray[odd_even], count[odd_even]);
383 #endif
384 } else {
385 printf("All %s states for bitflip property %03x are possible. No file written.\n", odd_even == EVEN_STATE ? "even" : "odd", bitflip);
388 uint32_t *restrict test_bitarray_2nd = malloc_bitarray(sizeof(uint32_t) * (1 << 19));
389 clear_bitarray24(test_bitarray_2nd);
390 for (odd_even_t odd_even = EVEN_STATE; odd_even <= ODD_STATE; odd_even++) {
391 if (count[odd_even] != 1 << 24) {
392 for (uint32_t state = 0; state < (1 << 24); state += 1 << 4) {
393 uint32_t line = test_bitarray[odd_even][state >> 5];
394 uint16_t half_line = (state & 0x000000010) ? line & 0x0000ffff : line >> 16;
395 if (half_line != 0) {
396 for (uint32_t low_bits = 0; low_bits < (1 << 4); low_bits++) {
397 set_bit24(test_bitarray_2nd, low_bits << 20 | state >> 4);
401 count[odd_even] = count_states(test_bitarray_2nd);
402 if (count[odd_even] != 1 << 24) {
403 printf("Writing %u possible %s states for bitflip property %03x (%u (%1.2f%%) states eliminated)\n",
404 count[odd_even],
405 odd_even == EVEN_STATE ? "even" : "odd",
406 bitflip | BITFLIP_2ND_BYTE,
407 (1 << 24) - count[odd_even],
408 (float)((1 << 24) - count[odd_even]) / (1 << 24) * 100.0);
409 #ifndef TEST_RUN
410 write_bitflips_file(odd_even, bitflip | BITFLIP_2ND_BYTE, sum_a0, test_bitarray_2nd, count[odd_even]);
411 #endif
412 } else {
413 printf("All %s states for bitflip property %03x are possible. No file written.\n", odd_even == EVEN_STATE ? "even" : "odd", bitflip | BITFLIP_2ND_BYTE);
415 } else {
416 printf("All %s states for bitflip property %03x are possible. No file written.\n", odd_even == EVEN_STATE ? "even" : "odd", bitflip | BITFLIP_2ND_BYTE);
420 ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
421 // second run for the remaining "not bitflip" states
422 printf("\n\nStarting search for crypto1 states resulting in bitflip property 0x%03x...", bitflip | 0x100);
423 start_time = time(NULL);
424 last_check_time = start_time;
425 for (uint32_t even_state = next_state(sum_a0_bitarray[EVEN_STATE], -1); even_state < NUM_TEST_STATES; even_state = next_state(sum_a0_bitarray[EVEN_STATE], even_state)) {
426 bool even_state_is_possible = test_bit24(test_not_bitarray[EVEN_STATE], even_state);
427 time_t time_now = time(NULL);
428 if (difftime(time_now, last_check_time) > 5 * 60) { // print status every 5 minutes
429 float runtime = difftime(time_now, start_time);
430 float remaining_time = runtime * ((1 << 23) - even_state) / even_state;
431 printf("\n%1.1f hours elapsed, expected completion in %1.1f hours (%1.1f days)", runtime / 3600, remaining_time / 3600, remaining_time / 3600 / 24);
432 last_check_time = time_now;
434 for (uint32_t odd_state = next_state(sum_a0_bitarray[ODD_STATE], -1); odd_state < (1 << 24); odd_state = next_state(sum_a0_bitarray[ODD_STATE], odd_state)) {
435 if (even_state_is_possible) {
436 if (all_odd_states_are_possible_for_notbitflip) break;
437 if (test_bit24(test_not_bitarray[ODD_STATE], odd_state)) continue;
439 // load crypto1 state
440 struct Crypto1State cs;
441 cs.odd = odd_state >> 4;
442 cs.even = even_state >> 4;
444 // track flipping bits in state
445 struct Crypto1DeltaState {
446 uint_fast8_t odd;
447 uint_fast8_t even;
448 } cs_delta;
449 cs_delta.odd = 0;
450 cs_delta.even = 0;
452 uint_fast16_t keystream = 0;
453 // uint_fast16_t nt = 0;
455 // decrypt 9 bits
456 for (int i = 0; i < 9; i++) {
457 uint_fast8_t keystream_bit = filter(cs.odd & 0x000fffff) ^ filter((cs.odd & 0x000fffff) ^ cs_delta.odd);
458 keystream = keystream << 1 | keystream_bit;
459 uint_fast8_t nt_bit = BIT(bitflip | 0x100, i) ^ keystream_bit;
460 uint_fast8_t LSFR_feedback = BIT(cs_delta.odd, 2) ^ BIT(cs_delta.even, 2) ^ BIT(cs_delta.odd, 3);
462 cs_delta.even = cs_delta.even << 1 | (LSFR_feedback ^ nt_bit);
463 uint_fast8_t tmp = cs_delta.odd;
464 cs_delta.odd = cs_delta.even;
465 cs_delta.even = tmp;
467 cs.even = cs.odd;
468 if (i & 1) {
469 cs.odd = odd_state >> (7 - i) / 2;
470 } else {
471 cs.odd = even_state >> (7 - i) / 2;
475 if (evenparity32(keystream) != evenparity32(bitflip)) {
476 // found valid !bitflip state
477 even_state_is_possible = true;
478 set_bit24(test_not_bitarray[EVEN_STATE], even_state);
479 set_bit24(test_not_bitarray[EVEN_STATE], 1 << 23 | even_state);
480 set_bit24(test_not_bitarray[ODD_STATE], odd_state);
485 printf("\nAnalysis completed. Checking for effective !bitflip properties...\n");
486 for (odd_even_t odd_even = EVEN_STATE; odd_even <= ODD_STATE; odd_even++) {
487 count[odd_even] = count_states(test_not_bitarray[odd_even]);
488 if (count[odd_even] != 1 << 24) {
489 printf("Writing %u possible %s states for bitflip property %03x (%u (%1.2f%%) states eliminated)\n",
490 count[odd_even],
491 odd_even == EVEN_STATE ? "even" : "odd",
492 bitflip | 0x100,
493 (1 << 24) - count[odd_even],
494 (float)((1 << 24) - count[odd_even]) / (1 << 24) * 100.0);
495 #ifndef TEST_RUN
496 write_bitflips_file(odd_even, bitflip | 0x100, sum_a0, test_not_bitarray[odd_even], count[odd_even]);
497 #endif
498 } else {
499 printf("All %s states for bitflip property %03x are possible. No file written.\n", odd_even == EVEN_STATE ? "even" : "odd", bitflip | 0x100);
503 clear_bitarray24(test_bitarray_2nd);
504 for (odd_even_t odd_even = EVEN_STATE; odd_even <= ODD_STATE; odd_even++) {
505 if (count[odd_even] != 1 << 24) {
506 for (uint32_t state = 0; state < (1 << 24); state += 1 << 4) {
507 uint32_t line = test_not_bitarray[odd_even][state >> 5];
508 uint16_t half_line = (state & 0x000000010) ? line & 0x0000ffff : line >> 16;
509 if (half_line != 0) {
510 for (uint32_t low_bits = 0; low_bits < (1 << 4); low_bits++) {
511 set_bit24(test_bitarray_2nd, low_bits << 20 | state >> 4);
515 count[odd_even] = count_states(test_bitarray_2nd);
516 if (count[odd_even] != 1 << 24) {
517 printf("Writing %u possible %s states for bitflip property %03x (%u (%1.2f%%) states eliminated)\n",
518 count[odd_even],
519 odd_even == EVEN_STATE ? "even" : "odd",
520 bitflip | 0x100 | BITFLIP_2ND_BYTE,
521 (1 << 24) - count[odd_even],
522 (float)((1 << 24) - count[odd_even]) / (1 << 24) * 100.0);
523 #ifndef TEST_RUN
524 write_bitflips_file(odd_even, bitflip | 0x100 | BITFLIP_2ND_BYTE, sum_a0, test_bitarray_2nd, count[odd_even]);
525 #endif
526 } else {
527 printf("All %s states for bitflip property %03x are possible. No file written.\n", odd_even == EVEN_STATE ? "even" : "odd", bitflip | 0x100 | BITFLIP_2ND_BYTE);
529 } else {
530 printf("All %s states for bitflip property %03x are possible. No file written.\n", odd_even == EVEN_STATE ? "even" : "odd", bitflip | 0x100 | BITFLIP_2ND_BYTE);
534 free_bitarray(test_bitarray_2nd);
535 free_bitarray(test_not_bitarray[ODD_STATE]);
536 free_bitarray(test_not_bitarray[EVEN_STATE]);
537 free_bitarray(test_bitarray[ODD_STATE]);
538 free_bitarray(test_bitarray[EVEN_STATE]);
539 exit(0);
543 int main(int argc, char *argv[]) {
545 unsigned int bitflip_in;
546 int sum_a0 = 0;
548 printf("Create tables required by hardnested attack.\n");
549 printf("Expect a runtime in the range of days or weeks.\n");
550 printf("Single thread only. If you want to use several threads, start it multiple times :-)\n\n");
552 if (argc != 2 && argc != 3) {
553 printf(" syntax: %s <bitflip property> [<Sum_a0>]\n\n", argv[0]);
554 printf(" example: %s 1f\n", argv[0]);
555 return 1;
558 sscanf(argv[1], "%x", &bitflip_in);
560 if (bitflip_in > 255) {
561 printf("Bitflip property must be less than or equal to 0xff\n\n");
562 return 1;
565 if (argc == 3) {
566 sscanf(argv[2], "%d", &sum_a0);
569 switch (sum_a0) {
570 case 0:
571 case 32:
572 case 56:
573 case 64:
574 case 80:
575 case 96:
576 case 104:
577 case 112:
578 case 120:
579 case 128:
580 case 136:
581 case 144:
582 case 152:
583 case 160:
584 case 176:
585 case 192:
586 case 200:
587 case 224:
588 case 256:
589 break;
590 default:
591 sum_a0 = -1;
594 printf("Calculating for bitflip = %02x, sum_a0 = %d\n", bitflip_in, sum_a0);
596 init_part_sum_bitarrays();
597 init_sum_bitarray(sum_a0);
599 precalculate_bit0_bitflip_bitarrays(bitflip_in, sum_a0);
601 free_sum_bitarray();
602 free_part_sum_bitarrays();
604 return 0;