1 /* TomsFastMath, a fast ISO C bignum library.
2 *
3 * This project is meant to fill in where LibTomMath
4 * falls short. That is speed ;-)
5 *
6 * This project is public domain and free for all purposes.
7 *
8 * Tom St Denis, tomstdenis@gmail.com
9 */
10 #include <tfm_private.h>
11
fp_read_unsigned_bin(fp_int * a,const unsigned char * b,int c)12 void fp_read_unsigned_bin(fp_int *a, const unsigned char *b, int c)
13 {
14 /* zero the int */
15 fp_zero (a);
16
17 /* If we know the endianness of this architecture, and we're using
18 32-bit fp_digits, we can optimize this */
19 #if (defined(ENDIAN_LITTLE) || defined(ENDIAN_BIG)) && !defined(FP_64BIT)
20 /* But not for both simultaneously */
21 #if defined(ENDIAN_LITTLE) && defined(ENDIAN_BIG)
22 #error Both ENDIAN_LITTLE and ENDIAN_BIG defined.
23 #endif
24 {
25 unsigned char *pd = (unsigned char *)a->dp;
26
27 if ((unsigned)c > (FP_SIZE * sizeof(fp_digit))) {
28 int excess = c - (FP_SIZE * sizeof(fp_digit));
29 c -= excess;
30 b += excess;
31 }
32 a->used = (c + sizeof(fp_digit) - 1)/sizeof(fp_digit);
33 /* read the bytes in */
34 #ifdef ENDIAN_BIG
35 {
36 /* Use Duff's device to unroll the loop. */
37 int idx = (c - 1) & ~3;
38 switch (c % 4) {
39 case 0: do { pd[idx+0] = *b++;
40 case 3: pd[idx+1] = *b++;
41 case 2: pd[idx+2] = *b++;
42 case 1: pd[idx+3] = *b++;
43 idx -= 4;
44 } while ((c -= 4) > 0);
45 }
46 }
47 #else
48 for (c -= 1; c >= 0; c -= 1) {
49 pd[c] = *b++;
50 }
51 #endif
52 }
53 #else
54 /* read the bytes in */
55 for (; c > 0; c--) {
56 fp_mul_2d (a, 8, a);
57 a->dp[0] |= *b++;
58 a->used += 1;
59 }
60 #endif
61 fp_clamp (a);
62 }
63
64 /* $Source$ */
65 /* $Revision$ */
66 /* $Date$ */
67