xref: /OK3568_Linux_fs/u-boot/lib/avb/libavb/avb_sha512.c (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1 /* SHA-256 and SHA-512 implementation based on code by Oliver Gay
2  * <olivier.gay@a3.epfl.ch> under a BSD-style license. See below.
3  */
4 
5 /*
6  * FIPS 180-2 SHA-224/256/384/512 implementation
7  * Last update: 02/02/2007
8  * Issue date:  04/30/2005
9  *
10  * Copyright (C) 2005, 2007 Olivier Gay <olivier.gay@a3.epfl.ch>
11  * All rights reserved.
12  *
13  * Redistribution and use in source and binary forms, with or without
14  * modification, are permitted provided that the following conditions
15  * are met:
16  * 1. Redistributions of source code must retain the above copyright
17  *    notice, this list of conditions and the following disclaimer.
18  * 2. Redistributions in binary form must reproduce the above copyright
19  *    notice, this list of conditions and the following disclaimer in the
20  *    documentation and/or other materials provided with the distribution.
21  * 3. Neither the name of the project nor the names of its contributors
22  *    may be used to endorse or promote products derived from this software
23  *    without specific prior written permission.
24  *
25  * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
26  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
27  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
28  * ARE DISCLAIMED.  IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
29  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
30  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
31  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
32  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
33  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
34  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
35  * SUCH DAMAGE.
36  */
37 
38 #include <android_avb/avb_sha.h>
39 #include <android_avb/avb_util.h>
40 
41 #define SHFR(x, n) (x >> n)
42 #define ROTR(x, n) ((x >> n) | (x << ((sizeof(x) << 3) - n)))
43 #define ROTL(x, n) ((x << n) | (x >> ((sizeof(x) << 3) - n)))
44 #define CH(x, y, z) ((x & y) ^ (~x & z))
45 #define MAJ(x, y, z) ((x & y) ^ (x & z) ^ (y & z))
46 
47 #define SHA512_F1(x) (ROTR(x, 28) ^ ROTR(x, 34) ^ ROTR(x, 39))
48 #define SHA512_F2(x) (ROTR(x, 14) ^ ROTR(x, 18) ^ ROTR(x, 41))
49 #define SHA512_F3(x) (ROTR(x, 1) ^ ROTR(x, 8) ^ SHFR(x, 7))
50 #define SHA512_F4(x) (ROTR(x, 19) ^ ROTR(x, 61) ^ SHFR(x, 6))
51 
52 #define UNPACK32(x, str)                 \
53   {                                      \
54     *((str) + 3) = (uint8_t)((x));       \
55     *((str) + 2) = (uint8_t)((x) >> 8);  \
56     *((str) + 1) = (uint8_t)((x) >> 16); \
57     *((str) + 0) = (uint8_t)((x) >> 24); \
58   }
59 
60 #define UNPACK64(x, str)                         \
61   {                                              \
62     *((str) + 7) = (uint8_t)x;                   \
63     *((str) + 6) = (uint8_t)((uint64_t)x >> 8);  \
64     *((str) + 5) = (uint8_t)((uint64_t)x >> 16); \
65     *((str) + 4) = (uint8_t)((uint64_t)x >> 24); \
66     *((str) + 3) = (uint8_t)((uint64_t)x >> 32); \
67     *((str) + 2) = (uint8_t)((uint64_t)x >> 40); \
68     *((str) + 1) = (uint8_t)((uint64_t)x >> 48); \
69     *((str) + 0) = (uint8_t)((uint64_t)x >> 56); \
70   }
71 
72 #define PACK64(str, x)                                                        \
73   {                                                                           \
74     *(x) =                                                                    \
75         ((uint64_t) * ((str) + 7)) | ((uint64_t) * ((str) + 6) << 8) |        \
76         ((uint64_t) * ((str) + 5) << 16) | ((uint64_t) * ((str) + 4) << 24) | \
77         ((uint64_t) * ((str) + 3) << 32) | ((uint64_t) * ((str) + 2) << 40) | \
78         ((uint64_t) * ((str) + 1) << 48) | ((uint64_t) * ((str) + 0) << 56);  \
79   }
80 
81 /* Macros used for loops unrolling */
82 
83 #define SHA512_SCR(i) \
84   { w[i] = SHA512_F4(w[i - 2]) + w[i - 7] + SHA512_F3(w[i - 15]) + w[i - 16]; }
85 
86 #define SHA512_EXP(a, b, c, d, e, f, g, h, j)                               \
87   {                                                                         \
88     t1 = wv[h] + SHA512_F2(wv[e]) + CH(wv[e], wv[f], wv[g]) + sha512_k[j] + \
89          w[j];                                                              \
90     t2 = SHA512_F1(wv[a]) + MAJ(wv[a], wv[b], wv[c]);                       \
91     wv[d] += t1;                                                            \
92     wv[h] = t1 + t2;                                                        \
93   }
94 
95 static const uint64_t sha512_h0[8] = {0x6a09e667f3bcc908ULL,
96                                       0xbb67ae8584caa73bULL,
97                                       0x3c6ef372fe94f82bULL,
98                                       0xa54ff53a5f1d36f1ULL,
99                                       0x510e527fade682d1ULL,
100                                       0x9b05688c2b3e6c1fULL,
101                                       0x1f83d9abfb41bd6bULL,
102                                       0x5be0cd19137e2179ULL};
103 
104 static const uint64_t sha512_k[80] = {
105     0x428a2f98d728ae22ULL, 0x7137449123ef65cdULL, 0xb5c0fbcfec4d3b2fULL,
106     0xe9b5dba58189dbbcULL, 0x3956c25bf348b538ULL, 0x59f111f1b605d019ULL,
107     0x923f82a4af194f9bULL, 0xab1c5ed5da6d8118ULL, 0xd807aa98a3030242ULL,
108     0x12835b0145706fbeULL, 0x243185be4ee4b28cULL, 0x550c7dc3d5ffb4e2ULL,
109     0x72be5d74f27b896fULL, 0x80deb1fe3b1696b1ULL, 0x9bdc06a725c71235ULL,
110     0xc19bf174cf692694ULL, 0xe49b69c19ef14ad2ULL, 0xefbe4786384f25e3ULL,
111     0x0fc19dc68b8cd5b5ULL, 0x240ca1cc77ac9c65ULL, 0x2de92c6f592b0275ULL,
112     0x4a7484aa6ea6e483ULL, 0x5cb0a9dcbd41fbd4ULL, 0x76f988da831153b5ULL,
113     0x983e5152ee66dfabULL, 0xa831c66d2db43210ULL, 0xb00327c898fb213fULL,
114     0xbf597fc7beef0ee4ULL, 0xc6e00bf33da88fc2ULL, 0xd5a79147930aa725ULL,
115     0x06ca6351e003826fULL, 0x142929670a0e6e70ULL, 0x27b70a8546d22ffcULL,
116     0x2e1b21385c26c926ULL, 0x4d2c6dfc5ac42aedULL, 0x53380d139d95b3dfULL,
117     0x650a73548baf63deULL, 0x766a0abb3c77b2a8ULL, 0x81c2c92e47edaee6ULL,
118     0x92722c851482353bULL, 0xa2bfe8a14cf10364ULL, 0xa81a664bbc423001ULL,
119     0xc24b8b70d0f89791ULL, 0xc76c51a30654be30ULL, 0xd192e819d6ef5218ULL,
120     0xd69906245565a910ULL, 0xf40e35855771202aULL, 0x106aa07032bbd1b8ULL,
121     0x19a4c116b8d2d0c8ULL, 0x1e376c085141ab53ULL, 0x2748774cdf8eeb99ULL,
122     0x34b0bcb5e19b48a8ULL, 0x391c0cb3c5c95a63ULL, 0x4ed8aa4ae3418acbULL,
123     0x5b9cca4f7763e373ULL, 0x682e6ff3d6b2b8a3ULL, 0x748f82ee5defb2fcULL,
124     0x78a5636f43172f60ULL, 0x84c87814a1f0ab72ULL, 0x8cc702081a6439ecULL,
125     0x90befffa23631e28ULL, 0xa4506cebde82bde9ULL, 0xbef9a3f7b2c67915ULL,
126     0xc67178f2e372532bULL, 0xca273eceea26619cULL, 0xd186b8c721c0c207ULL,
127     0xeada7dd6cde0eb1eULL, 0xf57d4f7fee6ed178ULL, 0x06f067aa72176fbaULL,
128     0x0a637dc5a2c898a6ULL, 0x113f9804bef90daeULL, 0x1b710b35131c471bULL,
129     0x28db77f523047d84ULL, 0x32caab7b40c72493ULL, 0x3c9ebe0a15c9bebcULL,
130     0x431d67c49c100d4cULL, 0x4cc5d4becb3e42b6ULL, 0x597f299cfc657e2aULL,
131     0x5fcb6fab3ad6faecULL, 0x6c44198c4a475817ULL};
132 
133 /* SHA-512 implementation */
134 
avb_sha512_init(AvbSHA512Ctx * ctx)135 void avb_sha512_init(AvbSHA512Ctx* ctx) {
136 /* Crypto-v1 is not support sha512 */
137 #ifdef CONFIG_ROCKCHIP_CRYPTO_V2
138   ctx->crypto_ctx.algo = CRYPTO_SHA512;
139   ctx->crypto_ctx.length = ctx->tot_len;
140   memset(ctx->buf, 0, sizeof(ctx->buf));
141 
142   ctx->crypto_dev = crypto_get_device(ctx->crypto_ctx.algo);
143   /* If there is no available crypto device, calculate in software instead. */
144   if (ctx->crypto_dev) {
145     crypto_sha_init(ctx->crypto_dev, &ctx->crypto_ctx);
146     return;
147   }
148 #endif
149 #ifdef UNROLL_LOOPS_SHA512
150   ctx->h[0] = sha512_h0[0];
151   ctx->h[1] = sha512_h0[1];
152   ctx->h[2] = sha512_h0[2];
153   ctx->h[3] = sha512_h0[3];
154   ctx->h[4] = sha512_h0[4];
155   ctx->h[5] = sha512_h0[5];
156   ctx->h[6] = sha512_h0[6];
157   ctx->h[7] = sha512_h0[7];
158 #else
159   int i;
160 
161   for (i = 0; i < 8; i++)
162     ctx->h[i] = sha512_h0[i];
163 #endif /* UNROLL_LOOPS_SHA512 */
164 
165   ctx->len = 0;
166   ctx->tot_len = 0;
167 }
168 
SHA512_transform(AvbSHA512Ctx * ctx,const uint8_t * message,size_t block_nb)169 static void SHA512_transform(AvbSHA512Ctx* ctx,
170                              const uint8_t* message,
171                              size_t block_nb) {
172   uint64_t w[80];
173   uint64_t wv[8];
174   uint64_t t1, t2;
175   const uint8_t* sub_block;
176   size_t i, j;
177 
178   for (i = 0; i < block_nb; i++) {
179     sub_block = message + (i << 7);
180 
181 #ifdef UNROLL_LOOPS_SHA512
182     PACK64(&sub_block[0], &w[0]);
183     PACK64(&sub_block[8], &w[1]);
184     PACK64(&sub_block[16], &w[2]);
185     PACK64(&sub_block[24], &w[3]);
186     PACK64(&sub_block[32], &w[4]);
187     PACK64(&sub_block[40], &w[5]);
188     PACK64(&sub_block[48], &w[6]);
189     PACK64(&sub_block[56], &w[7]);
190     PACK64(&sub_block[64], &w[8]);
191     PACK64(&sub_block[72], &w[9]);
192     PACK64(&sub_block[80], &w[10]);
193     PACK64(&sub_block[88], &w[11]);
194     PACK64(&sub_block[96], &w[12]);
195     PACK64(&sub_block[104], &w[13]);
196     PACK64(&sub_block[112], &w[14]);
197     PACK64(&sub_block[120], &w[15]);
198 
199     SHA512_SCR(16);
200     SHA512_SCR(17);
201     SHA512_SCR(18);
202     SHA512_SCR(19);
203     SHA512_SCR(20);
204     SHA512_SCR(21);
205     SHA512_SCR(22);
206     SHA512_SCR(23);
207     SHA512_SCR(24);
208     SHA512_SCR(25);
209     SHA512_SCR(26);
210     SHA512_SCR(27);
211     SHA512_SCR(28);
212     SHA512_SCR(29);
213     SHA512_SCR(30);
214     SHA512_SCR(31);
215     SHA512_SCR(32);
216     SHA512_SCR(33);
217     SHA512_SCR(34);
218     SHA512_SCR(35);
219     SHA512_SCR(36);
220     SHA512_SCR(37);
221     SHA512_SCR(38);
222     SHA512_SCR(39);
223     SHA512_SCR(40);
224     SHA512_SCR(41);
225     SHA512_SCR(42);
226     SHA512_SCR(43);
227     SHA512_SCR(44);
228     SHA512_SCR(45);
229     SHA512_SCR(46);
230     SHA512_SCR(47);
231     SHA512_SCR(48);
232     SHA512_SCR(49);
233     SHA512_SCR(50);
234     SHA512_SCR(51);
235     SHA512_SCR(52);
236     SHA512_SCR(53);
237     SHA512_SCR(54);
238     SHA512_SCR(55);
239     SHA512_SCR(56);
240     SHA512_SCR(57);
241     SHA512_SCR(58);
242     SHA512_SCR(59);
243     SHA512_SCR(60);
244     SHA512_SCR(61);
245     SHA512_SCR(62);
246     SHA512_SCR(63);
247     SHA512_SCR(64);
248     SHA512_SCR(65);
249     SHA512_SCR(66);
250     SHA512_SCR(67);
251     SHA512_SCR(68);
252     SHA512_SCR(69);
253     SHA512_SCR(70);
254     SHA512_SCR(71);
255     SHA512_SCR(72);
256     SHA512_SCR(73);
257     SHA512_SCR(74);
258     SHA512_SCR(75);
259     SHA512_SCR(76);
260     SHA512_SCR(77);
261     SHA512_SCR(78);
262     SHA512_SCR(79);
263 
264     wv[0] = ctx->h[0];
265     wv[1] = ctx->h[1];
266     wv[2] = ctx->h[2];
267     wv[3] = ctx->h[3];
268     wv[4] = ctx->h[4];
269     wv[5] = ctx->h[5];
270     wv[6] = ctx->h[6];
271     wv[7] = ctx->h[7];
272 
273     j = 0;
274 
275     do {
276       SHA512_EXP(0, 1, 2, 3, 4, 5, 6, 7, j);
277       j++;
278       SHA512_EXP(7, 0, 1, 2, 3, 4, 5, 6, j);
279       j++;
280       SHA512_EXP(6, 7, 0, 1, 2, 3, 4, 5, j);
281       j++;
282       SHA512_EXP(5, 6, 7, 0, 1, 2, 3, 4, j);
283       j++;
284       SHA512_EXP(4, 5, 6, 7, 0, 1, 2, 3, j);
285       j++;
286       SHA512_EXP(3, 4, 5, 6, 7, 0, 1, 2, j);
287       j++;
288       SHA512_EXP(2, 3, 4, 5, 6, 7, 0, 1, j);
289       j++;
290       SHA512_EXP(1, 2, 3, 4, 5, 6, 7, 0, j);
291       j++;
292     } while (j < 80);
293 
294     ctx->h[0] += wv[0];
295     ctx->h[1] += wv[1];
296     ctx->h[2] += wv[2];
297     ctx->h[3] += wv[3];
298     ctx->h[4] += wv[4];
299     ctx->h[5] += wv[5];
300     ctx->h[6] += wv[6];
301     ctx->h[7] += wv[7];
302 #else
303     for (j = 0; j < 16; j++) {
304       PACK64(&sub_block[j << 3], &w[j]);
305     }
306 
307     for (j = 16; j < 80; j++) {
308       SHA512_SCR(j);
309     }
310 
311     for (j = 0; j < 8; j++) {
312       wv[j] = ctx->h[j];
313     }
314 
315     for (j = 0; j < 80; j++) {
316       t1 = wv[7] + SHA512_F2(wv[4]) + CH(wv[4], wv[5], wv[6]) + sha512_k[j] +
317            w[j];
318       t2 = SHA512_F1(wv[0]) + MAJ(wv[0], wv[1], wv[2]);
319       wv[7] = wv[6];
320       wv[6] = wv[5];
321       wv[5] = wv[4];
322       wv[4] = wv[3] + t1;
323       wv[3] = wv[2];
324       wv[2] = wv[1];
325       wv[1] = wv[0];
326       wv[0] = t1 + t2;
327     }
328 
329     for (j = 0; j < 8; j++)
330       ctx->h[j] += wv[j];
331 #endif /* UNROLL_LOOPS_SHA512 */
332   }
333 }
334 
avb_sha512_update(AvbSHA512Ctx * ctx,const uint8_t * data,size_t len)335 void avb_sha512_update(AvbSHA512Ctx* ctx, const uint8_t* data, size_t len) {
336 /* Crypto-v1 is not support sha512 */
337 #ifdef CONFIG_ROCKCHIP_CRYPTO_V2
338   /* If there is no available crypto device, calculate in software instead. */
339   if (ctx->crypto_dev) {
340     crypto_sha_update(ctx->crypto_dev, (u32 *)data, len);
341     return;
342   }
343 #endif
344 
345   size_t block_nb;
346   size_t new_len, rem_len, tmp_len;
347   const uint8_t* shifted_data;
348 
349   tmp_len = AVB_SHA512_BLOCK_SIZE - ctx->len;
350   rem_len = len < tmp_len ? len : tmp_len;
351 
352   avb_memcpy(&ctx->block[ctx->len], data, rem_len);
353 
354   if (ctx->len + len < AVB_SHA512_BLOCK_SIZE) {
355     ctx->len += len;
356     return;
357   }
358 
359   new_len = len - rem_len;
360   block_nb = new_len / AVB_SHA512_BLOCK_SIZE;
361 
362   shifted_data = data + rem_len;
363 
364   SHA512_transform(ctx, ctx->block, 1);
365   SHA512_transform(ctx, shifted_data, block_nb);
366 
367   rem_len = new_len % AVB_SHA512_BLOCK_SIZE;
368 
369   avb_memcpy(ctx->block, &shifted_data[block_nb << 7], rem_len);
370 
371   ctx->len = rem_len;
372   ctx->tot_len += (block_nb + 1) << 7;
373 }
374 
avb_sha512_final(AvbSHA512Ctx * ctx)375 uint8_t* avb_sha512_final(AvbSHA512Ctx* ctx) {
376 /* Crypto-v1 is not support sha512 */
377 #ifdef CONFIG_ROCKCHIP_CRYPTO_V2
378   /* If there is no available crypto device, calculate in software instead. */
379   if (ctx->crypto_dev) {
380     crypto_sha_final(ctx->crypto_dev, &ctx->crypto_ctx, ctx->buf);
381     return ctx->buf;
382   }
383 #endif
384 
385   size_t block_nb;
386   size_t pm_len;
387   uint64_t len_b;
388 
389 #ifndef UNROLL_LOOPS_SHA512
390   size_t i;
391 #endif
392 
393   block_nb =
394       1 + ((AVB_SHA512_BLOCK_SIZE - 17) < (ctx->len % AVB_SHA512_BLOCK_SIZE));
395 
396   len_b = (ctx->tot_len + ctx->len) << 3;
397   pm_len = block_nb << 7;
398 
399   avb_memset(ctx->block + ctx->len, 0, pm_len - ctx->len);
400   ctx->block[ctx->len] = 0x80;
401   UNPACK64(len_b, ctx->block + pm_len - 8);
402 
403   SHA512_transform(ctx, ctx->block, block_nb);
404 
405 #ifdef UNROLL_LOOPS_SHA512
406   UNPACK64(ctx->h[0], &ctx->buf[0]);
407   UNPACK64(ctx->h[1], &ctx->buf[8]);
408   UNPACK64(ctx->h[2], &ctx->buf[16]);
409   UNPACK64(ctx->h[3], &ctx->buf[24]);
410   UNPACK64(ctx->h[4], &ctx->buf[32]);
411   UNPACK64(ctx->h[5], &ctx->buf[40]);
412   UNPACK64(ctx->h[6], &ctx->buf[48]);
413   UNPACK64(ctx->h[7], &ctx->buf[56]);
414 #else
415   for (i = 0; i < 8; i++)
416     UNPACK64(ctx->h[i], &ctx->buf[i << 3]);
417 #endif /* UNROLL_LOOPS_SHA512 */
418 
419   return ctx->buf;
420 }
421