]> git.sur5r.net Git - u-boot/blob - lib/sha256.c
Merge git://git.denx.de/u-boot-fsl-qoriq
[u-boot] / lib / sha256.c
1 /*
2  * FIPS-180-2 compliant SHA-256 implementation
3  *
4  * Copyright (C) 2001-2003  Christophe Devine
5  *
6  * SPDX-License-Identifier:     GPL-2.0+
7  */
8
9 #ifndef USE_HOSTCC
10 #include <common.h>
11 #include <linux/string.h>
12 #else
13 #include <string.h>
14 #endif /* USE_HOSTCC */
15 #include <watchdog.h>
16 #include <u-boot/sha256.h>
17
18 const uint8_t sha256_der_prefix[SHA256_DER_LEN] = {
19         0x30, 0x31, 0x30, 0x0d, 0x06, 0x09, 0x60, 0x86,
20         0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x01, 0x05,
21         0x00, 0x04, 0x20
22 };
23
24 /*
25  * 32-bit integer manipulation macros (big endian)
26  */
27 #ifndef GET_UINT32_BE
28 #define GET_UINT32_BE(n,b,i) {                          \
29         (n) = ( (unsigned long) (b)[(i)    ] << 24 )    \
30             | ( (unsigned long) (b)[(i) + 1] << 16 )    \
31             | ( (unsigned long) (b)[(i) + 2] <<  8 )    \
32             | ( (unsigned long) (b)[(i) + 3]       );   \
33 }
34 #endif
35 #ifndef PUT_UINT32_BE
36 #define PUT_UINT32_BE(n,b,i) {                          \
37         (b)[(i)    ] = (unsigned char) ( (n) >> 24 );   \
38         (b)[(i) + 1] = (unsigned char) ( (n) >> 16 );   \
39         (b)[(i) + 2] = (unsigned char) ( (n) >>  8 );   \
40         (b)[(i) + 3] = (unsigned char) ( (n)       );   \
41 }
42 #endif
43
44 void sha256_starts(sha256_context * ctx)
45 {
46         ctx->total[0] = 0;
47         ctx->total[1] = 0;
48
49         ctx->state[0] = 0x6A09E667;
50         ctx->state[1] = 0xBB67AE85;
51         ctx->state[2] = 0x3C6EF372;
52         ctx->state[3] = 0xA54FF53A;
53         ctx->state[4] = 0x510E527F;
54         ctx->state[5] = 0x9B05688C;
55         ctx->state[6] = 0x1F83D9AB;
56         ctx->state[7] = 0x5BE0CD19;
57 }
58
59 static void sha256_process(sha256_context *ctx, const uint8_t data[64])
60 {
61         uint32_t temp1, temp2;
62         uint32_t W[64];
63         uint32_t A, B, C, D, E, F, G, H;
64
65         GET_UINT32_BE(W[0], data, 0);
66         GET_UINT32_BE(W[1], data, 4);
67         GET_UINT32_BE(W[2], data, 8);
68         GET_UINT32_BE(W[3], data, 12);
69         GET_UINT32_BE(W[4], data, 16);
70         GET_UINT32_BE(W[5], data, 20);
71         GET_UINT32_BE(W[6], data, 24);
72         GET_UINT32_BE(W[7], data, 28);
73         GET_UINT32_BE(W[8], data, 32);
74         GET_UINT32_BE(W[9], data, 36);
75         GET_UINT32_BE(W[10], data, 40);
76         GET_UINT32_BE(W[11], data, 44);
77         GET_UINT32_BE(W[12], data, 48);
78         GET_UINT32_BE(W[13], data, 52);
79         GET_UINT32_BE(W[14], data, 56);
80         GET_UINT32_BE(W[15], data, 60);
81
82 #define SHR(x,n) ((x & 0xFFFFFFFF) >> n)
83 #define ROTR(x,n) (SHR(x,n) | (x << (32 - n)))
84
85 #define S0(x) (ROTR(x, 7) ^ ROTR(x,18) ^ SHR(x, 3))
86 #define S1(x) (ROTR(x,17) ^ ROTR(x,19) ^ SHR(x,10))
87
88 #define S2(x) (ROTR(x, 2) ^ ROTR(x,13) ^ ROTR(x,22))
89 #define S3(x) (ROTR(x, 6) ^ ROTR(x,11) ^ ROTR(x,25))
90
91 #define F0(x,y,z) ((x & y) | (z & (x | y)))
92 #define F1(x,y,z) (z ^ (x & (y ^ z)))
93
94 #define R(t)                                    \
95 (                                               \
96         W[t] = S1(W[t - 2]) + W[t - 7] +        \
97                 S0(W[t - 15]) + W[t - 16]       \
98 )
99
100 #define P(a,b,c,d,e,f,g,h,x,K) {                \
101         temp1 = h + S3(e) + F1(e,f,g) + K + x;  \
102         temp2 = S2(a) + F0(a,b,c);              \
103         d += temp1; h = temp1 + temp2;          \
104 }
105
106         A = ctx->state[0];
107         B = ctx->state[1];
108         C = ctx->state[2];
109         D = ctx->state[3];
110         E = ctx->state[4];
111         F = ctx->state[5];
112         G = ctx->state[6];
113         H = ctx->state[7];
114
115         P(A, B, C, D, E, F, G, H, W[0], 0x428A2F98);
116         P(H, A, B, C, D, E, F, G, W[1], 0x71374491);
117         P(G, H, A, B, C, D, E, F, W[2], 0xB5C0FBCF);
118         P(F, G, H, A, B, C, D, E, W[3], 0xE9B5DBA5);
119         P(E, F, G, H, A, B, C, D, W[4], 0x3956C25B);
120         P(D, E, F, G, H, A, B, C, W[5], 0x59F111F1);
121         P(C, D, E, F, G, H, A, B, W[6], 0x923F82A4);
122         P(B, C, D, E, F, G, H, A, W[7], 0xAB1C5ED5);
123         P(A, B, C, D, E, F, G, H, W[8], 0xD807AA98);
124         P(H, A, B, C, D, E, F, G, W[9], 0x12835B01);
125         P(G, H, A, B, C, D, E, F, W[10], 0x243185BE);
126         P(F, G, H, A, B, C, D, E, W[11], 0x550C7DC3);
127         P(E, F, G, H, A, B, C, D, W[12], 0x72BE5D74);
128         P(D, E, F, G, H, A, B, C, W[13], 0x80DEB1FE);
129         P(C, D, E, F, G, H, A, B, W[14], 0x9BDC06A7);
130         P(B, C, D, E, F, G, H, A, W[15], 0xC19BF174);
131         P(A, B, C, D, E, F, G, H, R(16), 0xE49B69C1);
132         P(H, A, B, C, D, E, F, G, R(17), 0xEFBE4786);
133         P(G, H, A, B, C, D, E, F, R(18), 0x0FC19DC6);
134         P(F, G, H, A, B, C, D, E, R(19), 0x240CA1CC);
135         P(E, F, G, H, A, B, C, D, R(20), 0x2DE92C6F);
136         P(D, E, F, G, H, A, B, C, R(21), 0x4A7484AA);
137         P(C, D, E, F, G, H, A, B, R(22), 0x5CB0A9DC);
138         P(B, C, D, E, F, G, H, A, R(23), 0x76F988DA);
139         P(A, B, C, D, E, F, G, H, R(24), 0x983E5152);
140         P(H, A, B, C, D, E, F, G, R(25), 0xA831C66D);
141         P(G, H, A, B, C, D, E, F, R(26), 0xB00327C8);
142         P(F, G, H, A, B, C, D, E, R(27), 0xBF597FC7);
143         P(E, F, G, H, A, B, C, D, R(28), 0xC6E00BF3);
144         P(D, E, F, G, H, A, B, C, R(29), 0xD5A79147);
145         P(C, D, E, F, G, H, A, B, R(30), 0x06CA6351);
146         P(B, C, D, E, F, G, H, A, R(31), 0x14292967);
147         P(A, B, C, D, E, F, G, H, R(32), 0x27B70A85);
148         P(H, A, B, C, D, E, F, G, R(33), 0x2E1B2138);
149         P(G, H, A, B, C, D, E, F, R(34), 0x4D2C6DFC);
150         P(F, G, H, A, B, C, D, E, R(35), 0x53380D13);
151         P(E, F, G, H, A, B, C, D, R(36), 0x650A7354);
152         P(D, E, F, G, H, A, B, C, R(37), 0x766A0ABB);
153         P(C, D, E, F, G, H, A, B, R(38), 0x81C2C92E);
154         P(B, C, D, E, F, G, H, A, R(39), 0x92722C85);
155         P(A, B, C, D, E, F, G, H, R(40), 0xA2BFE8A1);
156         P(H, A, B, C, D, E, F, G, R(41), 0xA81A664B);
157         P(G, H, A, B, C, D, E, F, R(42), 0xC24B8B70);
158         P(F, G, H, A, B, C, D, E, R(43), 0xC76C51A3);
159         P(E, F, G, H, A, B, C, D, R(44), 0xD192E819);
160         P(D, E, F, G, H, A, B, C, R(45), 0xD6990624);
161         P(C, D, E, F, G, H, A, B, R(46), 0xF40E3585);
162         P(B, C, D, E, F, G, H, A, R(47), 0x106AA070);
163         P(A, B, C, D, E, F, G, H, R(48), 0x19A4C116);
164         P(H, A, B, C, D, E, F, G, R(49), 0x1E376C08);
165         P(G, H, A, B, C, D, E, F, R(50), 0x2748774C);
166         P(F, G, H, A, B, C, D, E, R(51), 0x34B0BCB5);
167         P(E, F, G, H, A, B, C, D, R(52), 0x391C0CB3);
168         P(D, E, F, G, H, A, B, C, R(53), 0x4ED8AA4A);
169         P(C, D, E, F, G, H, A, B, R(54), 0x5B9CCA4F);
170         P(B, C, D, E, F, G, H, A, R(55), 0x682E6FF3);
171         P(A, B, C, D, E, F, G, H, R(56), 0x748F82EE);
172         P(H, A, B, C, D, E, F, G, R(57), 0x78A5636F);
173         P(G, H, A, B, C, D, E, F, R(58), 0x84C87814);
174         P(F, G, H, A, B, C, D, E, R(59), 0x8CC70208);
175         P(E, F, G, H, A, B, C, D, R(60), 0x90BEFFFA);
176         P(D, E, F, G, H, A, B, C, R(61), 0xA4506CEB);
177         P(C, D, E, F, G, H, A, B, R(62), 0xBEF9A3F7);
178         P(B, C, D, E, F, G, H, A, R(63), 0xC67178F2);
179
180         ctx->state[0] += A;
181         ctx->state[1] += B;
182         ctx->state[2] += C;
183         ctx->state[3] += D;
184         ctx->state[4] += E;
185         ctx->state[5] += F;
186         ctx->state[6] += G;
187         ctx->state[7] += H;
188 }
189
190 void sha256_update(sha256_context *ctx, const uint8_t *input, uint32_t length)
191 {
192         uint32_t left, fill;
193
194         if (!length)
195                 return;
196
197         left = ctx->total[0] & 0x3F;
198         fill = 64 - left;
199
200         ctx->total[0] += length;
201         ctx->total[0] &= 0xFFFFFFFF;
202
203         if (ctx->total[0] < length)
204                 ctx->total[1]++;
205
206         if (left && length >= fill) {
207                 memcpy((void *) (ctx->buffer + left), (void *) input, fill);
208                 sha256_process(ctx, ctx->buffer);
209                 length -= fill;
210                 input += fill;
211                 left = 0;
212         }
213
214         while (length >= 64) {
215                 sha256_process(ctx, input);
216                 length -= 64;
217                 input += 64;
218         }
219
220         if (length)
221                 memcpy((void *) (ctx->buffer + left), (void *) input, length);
222 }
223
224 static uint8_t sha256_padding[64] = {
225         0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
226            0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
227            0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
228            0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
229 };
230
231 void sha256_finish(sha256_context * ctx, uint8_t digest[32])
232 {
233         uint32_t last, padn;
234         uint32_t high, low;
235         uint8_t msglen[8];
236
237         high = ((ctx->total[0] >> 29)
238                 | (ctx->total[1] << 3));
239         low = (ctx->total[0] << 3);
240
241         PUT_UINT32_BE(high, msglen, 0);
242         PUT_UINT32_BE(low, msglen, 4);
243
244         last = ctx->total[0] & 0x3F;
245         padn = (last < 56) ? (56 - last) : (120 - last);
246
247         sha256_update(ctx, sha256_padding, padn);
248         sha256_update(ctx, msglen, 8);
249
250         PUT_UINT32_BE(ctx->state[0], digest, 0);
251         PUT_UINT32_BE(ctx->state[1], digest, 4);
252         PUT_UINT32_BE(ctx->state[2], digest, 8);
253         PUT_UINT32_BE(ctx->state[3], digest, 12);
254         PUT_UINT32_BE(ctx->state[4], digest, 16);
255         PUT_UINT32_BE(ctx->state[5], digest, 20);
256         PUT_UINT32_BE(ctx->state[6], digest, 24);
257         PUT_UINT32_BE(ctx->state[7], digest, 28);
258 }
259
260 /*
261  * Output = SHA-256( input buffer ). Trigger the watchdog every 'chunk_sz'
262  * bytes of input processed.
263  */
264 void sha256_csum_wd(const unsigned char *input, unsigned int ilen,
265                 unsigned char *output, unsigned int chunk_sz)
266 {
267         sha256_context ctx;
268 #if defined(CONFIG_HW_WATCHDOG) || defined(CONFIG_WATCHDOG)
269         const unsigned char *end;
270         unsigned char *curr;
271         int chunk;
272 #endif
273
274         sha256_starts(&ctx);
275
276 #if defined(CONFIG_HW_WATCHDOG) || defined(CONFIG_WATCHDOG)
277         curr = (unsigned char *)input;
278         end = input + ilen;
279         while (curr < end) {
280                 chunk = end - curr;
281                 if (chunk > chunk_sz)
282                         chunk = chunk_sz;
283                 sha256_update(&ctx, curr, chunk);
284                 curr += chunk;
285                 WATCHDOG_RESET();
286         }
287 #else
288         sha256_update(&ctx, input, ilen);
289 #endif
290
291         sha256_finish(&ctx, output);
292 }