1
2
3
4
5
6
7
8
9
10
11#include <linux/string.h>
12#include <linux/export.h>
13#include "skein_base.h"
14#include "skein_iv.h"
15#include "skein_block.h"
16
17
18
19
20
21
22
23int skein_256_init(struct skein_256_ctx *ctx, size_t hash_bit_len)
24{
25 union {
26 u8 b[SKEIN_256_STATE_BYTES];
27 u64 w[SKEIN_256_STATE_WORDS];
28 } cfg;
29
30 skein_assert_ret(hash_bit_len > 0, SKEIN_BAD_HASHLEN);
31 ctx->h.hash_bit_len = hash_bit_len;
32
33 switch (hash_bit_len) {
34 case 256:
35 memcpy(ctx->x, SKEIN_256_IV_256, sizeof(ctx->x));
36 break;
37 case 224:
38 memcpy(ctx->x, SKEIN_256_IV_224, sizeof(ctx->x));
39 break;
40 case 160:
41 memcpy(ctx->x, SKEIN_256_IV_160, sizeof(ctx->x));
42 break;
43 case 128:
44 memcpy(ctx->x, SKEIN_256_IV_128, sizeof(ctx->x));
45 break;
46 default:
47
48
49
50
51
52
53 skein_start_new_type(ctx, CFG_FINAL);
54
55
56 cfg.w[0] = skein_swap64(SKEIN_SCHEMA_VER);
57
58 cfg.w[1] = skein_swap64(hash_bit_len);
59 cfg.w[2] = skein_swap64(SKEIN_CFG_TREE_INFO_SEQUENTIAL);
60
61 memset(&cfg.w[3], 0, sizeof(cfg) - 3*sizeof(cfg.w[0]));
62
63
64
65 memset(ctx->x, 0, sizeof(ctx->x));
66 skein_256_process_block(ctx, cfg.b, 1, SKEIN_CFG_STR_LEN);
67 break;
68 }
69
70
71 skein_start_new_type(ctx, MSG);
72
73 return SKEIN_SUCCESS;
74}
75
76
77
78
79
80int skein_256_init_ext(struct skein_256_ctx *ctx, size_t hash_bit_len,
81 u64 tree_info, const u8 *key, size_t key_bytes)
82{
83 union {
84 u8 b[SKEIN_256_STATE_BYTES];
85 u64 w[SKEIN_256_STATE_WORDS];
86 } cfg;
87
88 skein_assert_ret(hash_bit_len > 0, SKEIN_BAD_HASHLEN);
89 skein_assert_ret(key_bytes == 0 || key != NULL, SKEIN_FAIL);
90
91
92 if (key_bytes == 0) {
93
94 memset(ctx->x, 0, sizeof(ctx->x));
95 } else {
96 skein_assert(sizeof(cfg.b) >= sizeof(ctx->x));
97
98
99 ctx->h.hash_bit_len = 8*sizeof(ctx->x);
100
101 skein_start_new_type(ctx, KEY);
102
103 memset(ctx->x, 0, sizeof(ctx->x));
104
105 skein_256_update(ctx, key, key_bytes);
106
107 skein_256_final_pad(ctx, cfg.b);
108
109 memcpy(ctx->x, cfg.b, sizeof(cfg.b));
110 }
111
112
113
114
115
116 ctx->h.hash_bit_len = hash_bit_len;
117 skein_start_new_type(ctx, CFG_FINAL);
118
119
120 memset(&cfg.w, 0, sizeof(cfg.w));
121 cfg.w[0] = skein_swap64(SKEIN_SCHEMA_VER);
122
123 cfg.w[1] = skein_swap64(hash_bit_len);
124
125 cfg.w[2] = skein_swap64(tree_info);
126
127
128 skein_256_process_block(ctx, cfg.b, 1, SKEIN_CFG_STR_LEN);
129
130
131
132 skein_start_new_type(ctx, MSG);
133
134 return SKEIN_SUCCESS;
135}
136
137
138
139int skein_256_update(struct skein_256_ctx *ctx, const u8 *msg,
140 size_t msg_byte_cnt)
141{
142 size_t n;
143
144
145 skein_assert_ret(ctx->h.b_cnt <= SKEIN_256_BLOCK_BYTES, SKEIN_FAIL);
146
147
148 if (msg_byte_cnt + ctx->h.b_cnt > SKEIN_256_BLOCK_BYTES) {
149
150 if (ctx->h.b_cnt) {
151
152 n = SKEIN_256_BLOCK_BYTES - ctx->h.b_cnt;
153 if (n) {
154
155 skein_assert(n < msg_byte_cnt);
156 memcpy(&ctx->b[ctx->h.b_cnt], msg, n);
157 msg_byte_cnt -= n;
158 msg += n;
159 ctx->h.b_cnt += n;
160 }
161 skein_assert(ctx->h.b_cnt == SKEIN_256_BLOCK_BYTES);
162 skein_256_process_block(ctx, ctx->b, 1,
163 SKEIN_256_BLOCK_BYTES);
164 ctx->h.b_cnt = 0;
165 }
166
167
168
169
170 if (msg_byte_cnt > SKEIN_256_BLOCK_BYTES) {
171
172 n = (msg_byte_cnt-1) / SKEIN_256_BLOCK_BYTES;
173 skein_256_process_block(ctx, msg, n,
174 SKEIN_256_BLOCK_BYTES);
175 msg_byte_cnt -= n * SKEIN_256_BLOCK_BYTES;
176 msg += n * SKEIN_256_BLOCK_BYTES;
177 }
178 skein_assert(ctx->h.b_cnt == 0);
179 }
180
181
182 if (msg_byte_cnt) {
183 skein_assert(msg_byte_cnt + ctx->h.b_cnt <=
184 SKEIN_256_BLOCK_BYTES);
185 memcpy(&ctx->b[ctx->h.b_cnt], msg, msg_byte_cnt);
186 ctx->h.b_cnt += msg_byte_cnt;
187 }
188
189 return SKEIN_SUCCESS;
190}
191
192
193
194int skein_256_final(struct skein_256_ctx *ctx, u8 *hash_val)
195{
196 size_t i, n, byte_cnt;
197 u64 x[SKEIN_256_STATE_WORDS];
198
199 skein_assert_ret(ctx->h.b_cnt <= SKEIN_256_BLOCK_BYTES, SKEIN_FAIL);
200
201
202 ctx->h.tweak[1] |= SKEIN_T1_FLAG_FINAL;
203
204 if (ctx->h.b_cnt < SKEIN_256_BLOCK_BYTES)
205 memset(&ctx->b[ctx->h.b_cnt], 0,
206 SKEIN_256_BLOCK_BYTES - ctx->h.b_cnt);
207
208
209 skein_256_process_block(ctx, ctx->b, 1, ctx->h.b_cnt);
210
211
212
213 byte_cnt = (ctx->h.hash_bit_len + 7) >> 3;
214
215
216
217 memset(ctx->b, 0, sizeof(ctx->b));
218
219 memcpy(x, ctx->x, sizeof(x));
220 for (i = 0; i*SKEIN_256_BLOCK_BYTES < byte_cnt; i++) {
221
222 ((u64 *)ctx->b)[0] = skein_swap64((u64) i);
223 skein_start_new_type(ctx, OUT_FINAL);
224
225 skein_256_process_block(ctx, ctx->b, 1, sizeof(u64));
226
227 n = byte_cnt - i*SKEIN_256_BLOCK_BYTES;
228 if (n >= SKEIN_256_BLOCK_BYTES)
229 n = SKEIN_256_BLOCK_BYTES;
230
231 skein_put64_lsb_first(hash_val+i*SKEIN_256_BLOCK_BYTES, ctx->x,
232 n);
233
234 memcpy(ctx->x, x, sizeof(x));
235 }
236 return SKEIN_SUCCESS;
237}
238
239
240
241
242
243
244
245int skein_512_init(struct skein_512_ctx *ctx, size_t hash_bit_len)
246{
247 union {
248 u8 b[SKEIN_512_STATE_BYTES];
249 u64 w[SKEIN_512_STATE_WORDS];
250 } cfg;
251
252 skein_assert_ret(hash_bit_len > 0, SKEIN_BAD_HASHLEN);
253 ctx->h.hash_bit_len = hash_bit_len;
254
255 switch (hash_bit_len) {
256 case 512:
257 memcpy(ctx->x, SKEIN_512_IV_512, sizeof(ctx->x));
258 break;
259 case 384:
260 memcpy(ctx->x, SKEIN_512_IV_384, sizeof(ctx->x));
261 break;
262 case 256:
263 memcpy(ctx->x, SKEIN_512_IV_256, sizeof(ctx->x));
264 break;
265 case 224:
266 memcpy(ctx->x, SKEIN_512_IV_224, sizeof(ctx->x));
267 break;
268 default:
269
270
271
272
273
274
275 skein_start_new_type(ctx, CFG_FINAL);
276
277
278 cfg.w[0] = skein_swap64(SKEIN_SCHEMA_VER);
279
280 cfg.w[1] = skein_swap64(hash_bit_len);
281 cfg.w[2] = skein_swap64(SKEIN_CFG_TREE_INFO_SEQUENTIAL);
282
283 memset(&cfg.w[3], 0, sizeof(cfg) - 3*sizeof(cfg.w[0]));
284
285
286
287 memset(ctx->x, 0, sizeof(ctx->x));
288 skein_512_process_block(ctx, cfg.b, 1, SKEIN_CFG_STR_LEN);
289 break;
290 }
291
292
293
294
295
296
297 skein_start_new_type(ctx, MSG);
298
299 return SKEIN_SUCCESS;
300}
301
302
303
304
305
306int skein_512_init_ext(struct skein_512_ctx *ctx, size_t hash_bit_len,
307 u64 tree_info, const u8 *key, size_t key_bytes)
308{
309 union {
310 u8 b[SKEIN_512_STATE_BYTES];
311 u64 w[SKEIN_512_STATE_WORDS];
312 } cfg;
313
314 skein_assert_ret(hash_bit_len > 0, SKEIN_BAD_HASHLEN);
315 skein_assert_ret(key_bytes == 0 || key != NULL, SKEIN_FAIL);
316
317
318 if (key_bytes == 0) {
319
320 memset(ctx->x, 0, sizeof(ctx->x));
321 } else {
322 skein_assert(sizeof(cfg.b) >= sizeof(ctx->x));
323
324
325 ctx->h.hash_bit_len = 8*sizeof(ctx->x);
326
327 skein_start_new_type(ctx, KEY);
328
329 memset(ctx->x, 0, sizeof(ctx->x));
330
331 skein_512_update(ctx, key, key_bytes);
332
333 skein_512_final_pad(ctx, cfg.b);
334
335 memcpy(ctx->x, cfg.b, sizeof(cfg.b));
336 }
337
338
339
340
341 ctx->h.hash_bit_len = hash_bit_len;
342 skein_start_new_type(ctx, CFG_FINAL);
343
344
345 memset(&cfg.w, 0, sizeof(cfg.w));
346 cfg.w[0] = skein_swap64(SKEIN_SCHEMA_VER);
347
348 cfg.w[1] = skein_swap64(hash_bit_len);
349
350 cfg.w[2] = skein_swap64(tree_info);
351
352
353 skein_512_process_block(ctx, cfg.b, 1, SKEIN_CFG_STR_LEN);
354
355
356
357 skein_start_new_type(ctx, MSG);
358
359 return SKEIN_SUCCESS;
360}
361
362
363
364int skein_512_update(struct skein_512_ctx *ctx, const u8 *msg,
365 size_t msg_byte_cnt)
366{
367 size_t n;
368
369
370 skein_assert_ret(ctx->h.b_cnt <= SKEIN_512_BLOCK_BYTES, SKEIN_FAIL);
371
372
373 if (msg_byte_cnt + ctx->h.b_cnt > SKEIN_512_BLOCK_BYTES) {
374
375 if (ctx->h.b_cnt) {
376
377 n = SKEIN_512_BLOCK_BYTES - ctx->h.b_cnt;
378 if (n) {
379
380 skein_assert(n < msg_byte_cnt);
381 memcpy(&ctx->b[ctx->h.b_cnt], msg, n);
382 msg_byte_cnt -= n;
383 msg += n;
384 ctx->h.b_cnt += n;
385 }
386 skein_assert(ctx->h.b_cnt == SKEIN_512_BLOCK_BYTES);
387 skein_512_process_block(ctx, ctx->b, 1,
388 SKEIN_512_BLOCK_BYTES);
389 ctx->h.b_cnt = 0;
390 }
391
392
393
394
395 if (msg_byte_cnt > SKEIN_512_BLOCK_BYTES) {
396
397 n = (msg_byte_cnt-1) / SKEIN_512_BLOCK_BYTES;
398 skein_512_process_block(ctx, msg, n,
399 SKEIN_512_BLOCK_BYTES);
400 msg_byte_cnt -= n * SKEIN_512_BLOCK_BYTES;
401 msg += n * SKEIN_512_BLOCK_BYTES;
402 }
403 skein_assert(ctx->h.b_cnt == 0);
404 }
405
406
407 if (msg_byte_cnt) {
408 skein_assert(msg_byte_cnt + ctx->h.b_cnt <=
409 SKEIN_512_BLOCK_BYTES);
410 memcpy(&ctx->b[ctx->h.b_cnt], msg, msg_byte_cnt);
411 ctx->h.b_cnt += msg_byte_cnt;
412 }
413
414 return SKEIN_SUCCESS;
415}
416
417
418
419int skein_512_final(struct skein_512_ctx *ctx, u8 *hash_val)
420{
421 size_t i, n, byte_cnt;
422 u64 x[SKEIN_512_STATE_WORDS];
423
424 skein_assert_ret(ctx->h.b_cnt <= SKEIN_512_BLOCK_BYTES, SKEIN_FAIL);
425
426
427 ctx->h.tweak[1] |= SKEIN_T1_FLAG_FINAL;
428
429 if (ctx->h.b_cnt < SKEIN_512_BLOCK_BYTES)
430 memset(&ctx->b[ctx->h.b_cnt], 0,
431 SKEIN_512_BLOCK_BYTES - ctx->h.b_cnt);
432
433
434 skein_512_process_block(ctx, ctx->b, 1, ctx->h.b_cnt);
435
436
437
438 byte_cnt = (ctx->h.hash_bit_len + 7) >> 3;
439
440
441
442 memset(ctx->b, 0, sizeof(ctx->b));
443
444 memcpy(x, ctx->x, sizeof(x));
445 for (i = 0; i*SKEIN_512_BLOCK_BYTES < byte_cnt; i++) {
446
447 ((u64 *)ctx->b)[0] = skein_swap64((u64) i);
448 skein_start_new_type(ctx, OUT_FINAL);
449
450 skein_512_process_block(ctx, ctx->b, 1, sizeof(u64));
451
452 n = byte_cnt - i*SKEIN_512_BLOCK_BYTES;
453 if (n >= SKEIN_512_BLOCK_BYTES)
454 n = SKEIN_512_BLOCK_BYTES;
455
456 skein_put64_lsb_first(hash_val+i*SKEIN_512_BLOCK_BYTES, ctx->x,
457 n);
458
459 memcpy(ctx->x, x, sizeof(x));
460 }
461 return SKEIN_SUCCESS;
462}
463
464
465
466
467
468
469
470int skein_1024_init(struct skein_1024_ctx *ctx, size_t hash_bit_len)
471{
472 union {
473 u8 b[SKEIN_1024_STATE_BYTES];
474 u64 w[SKEIN_1024_STATE_WORDS];
475 } cfg;
476
477 skein_assert_ret(hash_bit_len > 0, SKEIN_BAD_HASHLEN);
478 ctx->h.hash_bit_len = hash_bit_len;
479
480 switch (hash_bit_len) {
481 case 512:
482 memcpy(ctx->x, SKEIN_1024_IV_512, sizeof(ctx->x));
483 break;
484 case 384:
485 memcpy(ctx->x, SKEIN_1024_IV_384, sizeof(ctx->x));
486 break;
487 case 1024:
488 memcpy(ctx->x, SKEIN_1024_IV_1024, sizeof(ctx->x));
489 break;
490 default:
491
492
493
494
495
496
497 skein_start_new_type(ctx, CFG_FINAL);
498
499
500 cfg.w[0] = skein_swap64(SKEIN_SCHEMA_VER);
501
502 cfg.w[1] = skein_swap64(hash_bit_len);
503 cfg.w[2] = skein_swap64(SKEIN_CFG_TREE_INFO_SEQUENTIAL);
504
505 memset(&cfg.w[3], 0, sizeof(cfg) - 3*sizeof(cfg.w[0]));
506
507
508
509 memset(ctx->x, 0, sizeof(ctx->x));
510 skein_1024_process_block(ctx, cfg.b, 1, SKEIN_CFG_STR_LEN);
511 break;
512 }
513
514
515
516 skein_start_new_type(ctx, MSG);
517
518 return SKEIN_SUCCESS;
519}
520
521
522
523
524
525int skein_1024_init_ext(struct skein_1024_ctx *ctx, size_t hash_bit_len,
526 u64 tree_info, const u8 *key, size_t key_bytes)
527{
528 union {
529 u8 b[SKEIN_1024_STATE_BYTES];
530 u64 w[SKEIN_1024_STATE_WORDS];
531 } cfg;
532
533 skein_assert_ret(hash_bit_len > 0, SKEIN_BAD_HASHLEN);
534 skein_assert_ret(key_bytes == 0 || key != NULL, SKEIN_FAIL);
535
536
537 if (key_bytes == 0) {
538
539 memset(ctx->x, 0, sizeof(ctx->x));
540 } else {
541 skein_assert(sizeof(cfg.b) >= sizeof(ctx->x));
542
543
544 ctx->h.hash_bit_len = 8*sizeof(ctx->x);
545
546 skein_start_new_type(ctx, KEY);
547
548 memset(ctx->x, 0, sizeof(ctx->x));
549
550 skein_1024_update(ctx, key, key_bytes);
551
552 skein_1024_final_pad(ctx, cfg.b);
553
554 memcpy(ctx->x, cfg.b, sizeof(cfg.b));
555 }
556
557
558
559
560
561 ctx->h.hash_bit_len = hash_bit_len;
562 skein_start_new_type(ctx, CFG_FINAL);
563
564
565 memset(&cfg.w, 0, sizeof(cfg.w));
566 cfg.w[0] = skein_swap64(SKEIN_SCHEMA_VER);
567
568 cfg.w[1] = skein_swap64(hash_bit_len);
569
570 cfg.w[2] = skein_swap64(tree_info);
571
572
573 skein_1024_process_block(ctx, cfg.b, 1, SKEIN_CFG_STR_LEN);
574
575
576
577 skein_start_new_type(ctx, MSG);
578
579 return SKEIN_SUCCESS;
580}
581
582
583
584int skein_1024_update(struct skein_1024_ctx *ctx, const u8 *msg,
585 size_t msg_byte_cnt)
586{
587 size_t n;
588
589
590 skein_assert_ret(ctx->h.b_cnt <= SKEIN_1024_BLOCK_BYTES, SKEIN_FAIL);
591
592
593 if (msg_byte_cnt + ctx->h.b_cnt > SKEIN_1024_BLOCK_BYTES) {
594
595 if (ctx->h.b_cnt) {
596
597 n = SKEIN_1024_BLOCK_BYTES - ctx->h.b_cnt;
598 if (n) {
599
600 skein_assert(n < msg_byte_cnt);
601 memcpy(&ctx->b[ctx->h.b_cnt], msg, n);
602 msg_byte_cnt -= n;
603 msg += n;
604 ctx->h.b_cnt += n;
605 }
606 skein_assert(ctx->h.b_cnt == SKEIN_1024_BLOCK_BYTES);
607 skein_1024_process_block(ctx, ctx->b, 1,
608 SKEIN_1024_BLOCK_BYTES);
609 ctx->h.b_cnt = 0;
610 }
611
612
613
614
615 if (msg_byte_cnt > SKEIN_1024_BLOCK_BYTES) {
616
617 n = (msg_byte_cnt-1) / SKEIN_1024_BLOCK_BYTES;
618 skein_1024_process_block(ctx, msg, n,
619 SKEIN_1024_BLOCK_BYTES);
620 msg_byte_cnt -= n * SKEIN_1024_BLOCK_BYTES;
621 msg += n * SKEIN_1024_BLOCK_BYTES;
622 }
623 skein_assert(ctx->h.b_cnt == 0);
624 }
625
626
627 if (msg_byte_cnt) {
628 skein_assert(msg_byte_cnt + ctx->h.b_cnt <=
629 SKEIN_1024_BLOCK_BYTES);
630 memcpy(&ctx->b[ctx->h.b_cnt], msg, msg_byte_cnt);
631 ctx->h.b_cnt += msg_byte_cnt;
632 }
633
634 return SKEIN_SUCCESS;
635}
636
637
638
639int skein_1024_final(struct skein_1024_ctx *ctx, u8 *hash_val)
640{
641 size_t i, n, byte_cnt;
642 u64 x[SKEIN_1024_STATE_WORDS];
643
644 skein_assert_ret(ctx->h.b_cnt <= SKEIN_1024_BLOCK_BYTES, SKEIN_FAIL);
645
646
647 ctx->h.tweak[1] |= SKEIN_T1_FLAG_FINAL;
648
649 if (ctx->h.b_cnt < SKEIN_1024_BLOCK_BYTES)
650 memset(&ctx->b[ctx->h.b_cnt], 0,
651 SKEIN_1024_BLOCK_BYTES - ctx->h.b_cnt);
652
653
654 skein_1024_process_block(ctx, ctx->b, 1, ctx->h.b_cnt);
655
656
657
658 byte_cnt = (ctx->h.hash_bit_len + 7) >> 3;
659
660
661
662 memset(ctx->b, 0, sizeof(ctx->b));
663
664 memcpy(x, ctx->x, sizeof(x));
665 for (i = 0; i*SKEIN_1024_BLOCK_BYTES < byte_cnt; i++) {
666
667 ((u64 *)ctx->b)[0] = skein_swap64((u64) i);
668 skein_start_new_type(ctx, OUT_FINAL);
669
670 skein_1024_process_block(ctx, ctx->b, 1, sizeof(u64));
671
672 n = byte_cnt - i*SKEIN_1024_BLOCK_BYTES;
673 if (n >= SKEIN_1024_BLOCK_BYTES)
674 n = SKEIN_1024_BLOCK_BYTES;
675
676 skein_put64_lsb_first(hash_val+i*SKEIN_1024_BLOCK_BYTES, ctx->x,
677 n);
678
679 memcpy(ctx->x, x, sizeof(x));
680 }
681 return SKEIN_SUCCESS;
682}
683
684
685
686
687
688
689int skein_256_final_pad(struct skein_256_ctx *ctx, u8 *hash_val)
690{
691
692 skein_assert_ret(ctx->h.b_cnt <= SKEIN_256_BLOCK_BYTES, SKEIN_FAIL);
693
694
695 ctx->h.tweak[1] |= SKEIN_T1_FLAG_FINAL;
696
697 if (ctx->h.b_cnt < SKEIN_256_BLOCK_BYTES)
698 memset(&ctx->b[ctx->h.b_cnt], 0,
699 SKEIN_256_BLOCK_BYTES - ctx->h.b_cnt);
700
701 skein_256_process_block(ctx, ctx->b, 1, ctx->h.b_cnt);
702
703
704 skein_put64_lsb_first(hash_val, ctx->x, SKEIN_256_BLOCK_BYTES);
705
706 return SKEIN_SUCCESS;
707}
708
709
710
711int skein_512_final_pad(struct skein_512_ctx *ctx, u8 *hash_val)
712{
713
714 skein_assert_ret(ctx->h.b_cnt <= SKEIN_512_BLOCK_BYTES, SKEIN_FAIL);
715
716
717 ctx->h.tweak[1] |= SKEIN_T1_FLAG_FINAL;
718
719 if (ctx->h.b_cnt < SKEIN_512_BLOCK_BYTES)
720 memset(&ctx->b[ctx->h.b_cnt], 0,
721 SKEIN_512_BLOCK_BYTES - ctx->h.b_cnt);
722
723 skein_512_process_block(ctx, ctx->b, 1, ctx->h.b_cnt);
724
725
726 skein_put64_lsb_first(hash_val, ctx->x, SKEIN_512_BLOCK_BYTES);
727
728 return SKEIN_SUCCESS;
729}
730
731
732
733int skein_1024_final_pad(struct skein_1024_ctx *ctx, u8 *hash_val)
734{
735
736 skein_assert_ret(ctx->h.b_cnt <= SKEIN_1024_BLOCK_BYTES, SKEIN_FAIL);
737
738
739 ctx->h.tweak[1] |= SKEIN_T1_FLAG_FINAL;
740
741 if (ctx->h.b_cnt < SKEIN_1024_BLOCK_BYTES)
742 memset(&ctx->b[ctx->h.b_cnt], 0,
743 SKEIN_1024_BLOCK_BYTES - ctx->h.b_cnt);
744
745 skein_1024_process_block(ctx, ctx->b, 1, ctx->h.b_cnt);
746
747
748 skein_put64_lsb_first(hash_val, ctx->x, SKEIN_1024_BLOCK_BYTES);
749
750 return SKEIN_SUCCESS;
751}
752
753#if SKEIN_TREE_HASH
754
755
756int skein_256_output(struct skein_256_ctx *ctx, u8 *hash_val)
757{
758 size_t i, n, byte_cnt;
759 u64 x[SKEIN_256_STATE_WORDS];
760
761 skein_assert_ret(ctx->h.b_cnt <= SKEIN_256_BLOCK_BYTES, SKEIN_FAIL);
762
763
764
765 byte_cnt = (ctx->h.hash_bit_len + 7) >> 3;
766
767
768
769 memset(ctx->b, 0, sizeof(ctx->b));
770
771 memcpy(x, ctx->x, sizeof(x));
772 for (i = 0; i*SKEIN_256_BLOCK_BYTES < byte_cnt; i++) {
773
774 ((u64 *)ctx->b)[0] = skein_swap64((u64) i);
775 skein_start_new_type(ctx, OUT_FINAL);
776
777 skein_256_process_block(ctx, ctx->b, 1, sizeof(u64));
778
779 n = byte_cnt - i*SKEIN_256_BLOCK_BYTES;
780 if (n >= SKEIN_256_BLOCK_BYTES)
781 n = SKEIN_256_BLOCK_BYTES;
782
783 skein_put64_lsb_first(hash_val+i*SKEIN_256_BLOCK_BYTES, ctx->x,
784 n);
785
786 memcpy(ctx->x, x, sizeof(x));
787 }
788 return SKEIN_SUCCESS;
789}
790
791
792
793int skein_512_output(struct skein_512_ctx *ctx, u8 *hash_val)
794{
795 size_t i, n, byte_cnt;
796 u64 x[SKEIN_512_STATE_WORDS];
797
798 skein_assert_ret(ctx->h.b_cnt <= SKEIN_512_BLOCK_BYTES, SKEIN_FAIL);
799
800
801
802 byte_cnt = (ctx->h.hash_bit_len + 7) >> 3;
803
804
805
806 memset(ctx->b, 0, sizeof(ctx->b));
807
808 memcpy(x, ctx->x, sizeof(x));
809 for (i = 0; i*SKEIN_512_BLOCK_BYTES < byte_cnt; i++) {
810
811 ((u64 *)ctx->b)[0] = skein_swap64((u64) i);
812 skein_start_new_type(ctx, OUT_FINAL);
813
814 skein_512_process_block(ctx, ctx->b, 1, sizeof(u64));
815
816 n = byte_cnt - i*SKEIN_512_BLOCK_BYTES;
817 if (n >= SKEIN_512_BLOCK_BYTES)
818 n = SKEIN_512_BLOCK_BYTES;
819
820 skein_put64_lsb_first(hash_val+i*SKEIN_512_BLOCK_BYTES, ctx->x,
821 n);
822
823 memcpy(ctx->x, x, sizeof(x));
824 }
825 return SKEIN_SUCCESS;
826}
827
828
829
830int skein_1024_output(struct skein_1024_ctx *ctx, u8 *hash_val)
831{
832 size_t i, n, byte_cnt;
833 u64 x[SKEIN_1024_STATE_WORDS];
834
835 skein_assert_ret(ctx->h.b_cnt <= SKEIN_1024_BLOCK_BYTES, SKEIN_FAIL);
836
837
838
839 byte_cnt = (ctx->h.hash_bit_len + 7) >> 3;
840
841
842
843 memset(ctx->b, 0, sizeof(ctx->b));
844
845 memcpy(x, ctx->x, sizeof(x));
846 for (i = 0; i*SKEIN_1024_BLOCK_BYTES < byte_cnt; i++) {
847
848 ((u64 *)ctx->b)[0] = skein_swap64((u64) i);
849 skein_start_new_type(ctx, OUT_FINAL);
850
851 skein_1024_process_block(ctx, ctx->b, 1, sizeof(u64));
852
853 n = byte_cnt - i*SKEIN_1024_BLOCK_BYTES;
854 if (n >= SKEIN_1024_BLOCK_BYTES)
855 n = SKEIN_1024_BLOCK_BYTES;
856
857 skein_put64_lsb_first(hash_val+i*SKEIN_1024_BLOCK_BYTES, ctx->x,
858 n);
859
860 memcpy(ctx->x, x, sizeof(x));
861 }
862 return SKEIN_SUCCESS;
863}
864#endif
865