1// SPDX-License-Identifier: GPL-2.0+
2/*
3 * Copyright (c) 2022 Nuvoton Technology Corp.
4 */
5
6#include <common.h>
7#include <dm.h>
8#include <hash.h>
9#include <malloc.h>
10#include <uboot_aes.h>
11#include <asm/io.h>
12
13#define HASH_DIG_H_NUM			8
14
15#define HASH_CTR_STS_SHA_EN             BIT(0)
16#define HASH_CTR_STS_SHA_BUSY           BIT(1)
17#define HASH_CTR_STS_SHA_RST            BIT(2)
18#define HASH_CFG_SHA1_SHA2              BIT(0)
19
20/* SHA type */
21enum npcm_sha_type {
22	npcm_sha_type_sha2 = 0,
23	npcm_sha_type_sha1,
24	npcm_sha_type_num
25};
26
27struct npcm_sha_regs {
28	unsigned int hash_data_in;
29	unsigned char hash_ctr_sts;
30	unsigned char reserved_0[0x03];
31	unsigned char hash_cfg;
32	unsigned char reserved_1[0x03];
33	unsigned char hash_ver;
34	unsigned char reserved_2[0x13];
35	unsigned int hash_dig[HASH_DIG_H_NUM];
36};
37
38struct npcm_sha_priv {
39	struct npcm_sha_regs *regs;
40};
41
42static struct npcm_sha_priv *sha_priv;
43
44#ifdef SHA_DEBUG_MODULE
45#define sha_print(fmt, args...)  printf(fmt, ##args)
46#else
47#define sha_print(fmt, args...)  (void)0
48#endif
49
50#define SHA_BLOCK_LENGTH        (512 / 8)
51#define SHA_2_HASH_LENGTH       (256 / 8)
52#define SHA_1_HASH_LENGTH       (160 / 8)
53#define SHA_HASH_LENGTH(type)   ((type == npcm_sha_type_sha2) ? \
54							(SHA_2_HASH_LENGTH) : (SHA_1_HASH_LENGTH))
55
56#define SHA_SECRUN_BUFF_SIZE    64
57#define SHA_TIMEOUT             100
58#define SHA_DATA_LAST_BYTE      0x80
59
60#define SHA2_NUM_OF_SELF_TESTS  3
61#define SHA1_NUM_OF_SELF_TESTS  4
62
63#define NUVOTON_ALIGNMENT       4
64
65/*-----------------------------------------------------------------------------*/
66/* SHA instance struct handler                                                 */
67/*-----------------------------------------------------------------------------*/
68struct SHA_HANDLE_T {
69	u32                 hv[SHA_2_HASH_LENGTH / sizeof(u32)];
70	u32                 length0;
71	u32                 length1;
72	u32					block[SHA_BLOCK_LENGTH / sizeof(u32)];
73	u8					type;
74	bool                active;
75};
76
77// The # of bytes currently in the sha  block buffer
78#define SHA_BUFF_POS(length)        ((length) & (SHA_BLOCK_LENGTH - 1))
79
80// The # of free bytes in the sha block buffer
81#define SHA_BUFF_FREE(length)       (SHA_BLOCK_LENGTH - SHA_BUFF_POS(length))
82
83static void SHA_FlushLocalBuffer_l(const u32 *buff);
84static int  SHA_BusyWait_l(void);
85static void SHA_GetShaDigest_l(u8 *hashdigest, u8 type);
86static void SHA_SetShaDigest_l(const u32 *hashdigest, u8 type);
87static void SHA_SetBlock_l(const u8 *data, u32 len, u16 position, u32 *block);
88static void SHA_ClearBlock_l(u16 len, u16 position, u32 *block);
89static void SHA_SetLength32_l(struct SHA_HANDLE_T *handleptr, u32 *block);
90
91static int SHA_Init(struct SHA_HANDLE_T *handleptr);
92static int SHA_Start(struct SHA_HANDLE_T *handleptr, u8 type);
93static int SHA_Update(struct SHA_HANDLE_T *handleptr, const u8 *buffer, u32 len);
94static int SHA_Finish(struct SHA_HANDLE_T *handleptr, u8 *hashdigest);
95static int SHA_Reset(void);
96static int SHA_Power(bool on);
97#ifdef SHA_PRINT
98static void SHA_PrintRegs(void);
99static void SHA_PrintVersion(void);
100#endif
101
102static struct SHA_HANDLE_T sha_handle;
103
104/*----------------------------------------------------------------------------*/
105/* Checks if give function returns int error, and returns the error           */
106/* immediately after SHA disabling                                            */
107/*----------------------------------------------------------------------------*/
108int npcm_sha_check(int status)
109{
110	if (status != 0) {
111		SHA_Power(false);
112		return status;
113	}
114	return 0;
115}
116
117/*----------------------------------------------------------------------------*/
118/* Function:        npcm_sha_calc                                          */
119/*                                                                            */
120/* Parameters:      type - SHA module type                                    */
121/*                  inBuff  - Pointer to a buffer containing the data to      */
122/*                            be hashed                                       */
123/*                  len     - Length of the data to hash                      */
124/*                  hashDigest - Pointer to a buffer where the reseulting     */
125/*                               digest will be copied to                     */
126/*                                                                            */
127/* Returns:         0 on success or other int error code on error             */
128/* Side effects:                                                              */
129/* Description:                                                               */
130/*                  This routine performs complete SHA calculation in one     */
131/*                  step                                                      */
132/*----------------------------------------------------------------------------*/
133int npcm_sha_calc(u8 type, const u8 *inbuff, u32 len, u8 *hashdigest)
134{
135	int status;
136	struct SHA_HANDLE_T handle;
137
138	SHA_Init(&handle);
139	SHA_Power(true);
140	SHA_Reset();
141	SHA_Start(&handle, type);
142	status = SHA_Update(&handle, inbuff, len);
143	npcm_sha_check(status);
144	status = SHA_Finish(&handle, hashdigest);
145	npcm_sha_check(status);
146	SHA_Power(false);
147
148	return 0;
149}
150
151/*
152 * Computes hash value of input pbuf using h/w acceleration
153 *
154 * @param in_addr    A pointer to the input buffer
155 * @param bufleni    Byte length of input buffer
156 * @param out_addr   A pointer to the output buffer. When complete
157 *           32 bytes are copied to pout[0]...pout[31]. Thus, a user
158 *           should allocate at least 32 bytes at pOut in advance.
159 * @param chunk_size chunk size for sha256
160 */
161void hw_sha256(const uchar *in_addr, uint buflen, uchar *out_addr, uint chunk_size)
162{
163	puts("\nhw_sha256 using BMC HW accelerator\t");
164	npcm_sha_calc(npcm_sha_type_sha2, (u8 *)in_addr, buflen, (u8 *)out_addr);
165}
166
167/*
168 * Computes hash value of input pbuf using h/w acceleration
169 *
170 * @param in_addr    A pointer to the input buffer
171 * @param bufleni    Byte length of input buffer
172 * @param out_addr   A pointer to the output buffer. When complete
173 *           32 bytes are copied to pout[0]...pout[31]. Thus, a user
174 *           should allocate at least 32 bytes at pOut in advance.
175 * @param chunk_size chunk_size for sha1
176 */
177void hw_sha1(const uchar *in_addr, uint buflen, uchar *out_addr, uint chunk_size)
178{
179	puts("\nhw_sha1 using BMC HW accelerator\t");
180	npcm_sha_calc(npcm_sha_type_sha1, (u8 *)in_addr, buflen, (u8 *)out_addr);
181}
182
183/*
184 * Create the context for sha progressive hashing using h/w acceleration
185 *
186 * @algo: Pointer to the hash_algo struct
187 * @ctxp: Pointer to the pointer of the context for hashing
188 * @return 0 if ok, -ve on error
189 */
190int hw_sha_init(struct hash_algo *algo, void **ctxp)
191{
192	const char *algo_name1 = "sha1";
193	const char *algo_name2 = "sha256";
194
195	SHA_Init(&sha_handle);
196	SHA_Power(true);
197	SHA_Reset();
198	if (!strcmp(algo_name1, algo->name))
199		return SHA_Start(&sha_handle, npcm_sha_type_sha1);
200	else if (!strcmp(algo_name2, algo->name))
201		return SHA_Start(&sha_handle, npcm_sha_type_sha2);
202	else
203		return -EPROTO;
204}
205
206/*
207 * Update buffer for sha progressive hashing using h/w acceleration
208 *
209 * The context is freed by this function if an error occurs.
210 *
211 * @algo: Pointer to the hash_algo struct
212 * @ctx: Pointer to the context for hashing
213 * @buf: Pointer to the buffer being hashed
214 * @size: Size of the buffer being hashed
215 * @is_last: 1 if this is the last update; 0 otherwise
216 * @return 0 if ok, -ve on error
217 */
218int hw_sha_update(struct hash_algo *algo, void *ctx, const void *buf,
219		  unsigned int size, int is_last)
220{
221	return SHA_Update(&sha_handle, buf, size);
222}
223
224/*
225 * Copy sha hash result at destination location
226 *
227 * The context is freed after completion of hash operation or after an error.
228 *
229 * @algo: Pointer to the hash_algo struct
230 * @ctx: Pointer to the context for hashing
231 * @dest_buf: Pointer to the destination buffer where hash is to be copied
232 * @size: Size of the buffer being hashed
233 * @return 0 if ok, -ve on error
234 */
235int hw_sha_finish(struct hash_algo *algo, void *ctx, void *dest_buf, int size)
236{
237	int status;
238
239	status = SHA_Finish(&sha_handle, dest_buf);
240	npcm_sha_check(status);
241	return SHA_Power(false);
242}
243
244/*----------------------------------------------------------------------------*/
245/* Function:        SHA_Init                                                  */
246/*                                                                            */
247/* Parameters:      handlePtr - SHA processing handle pointer                 */
248/* Returns:         0 on success or other int error code on error.            */
249/* Side effects:                                                              */
250/* Description:                                                               */
251/*                  This routine initialize the SHA module                    */
252/*----------------------------------------------------------------------------*/
253static int SHA_Init(struct SHA_HANDLE_T *handleptr)
254{
255	handleptr->active = false;
256
257	return 0;
258}
259
260/*----------------------------------------------------------------------------*/
261/* Function:        SHA_Start                                                 */
262/*                                                                            */
263/* Parameters:      handlePtr   - SHA processing handle pointer               */
264/*                  type        - SHA module type                             */
265/*                                                                            */
266/* Returns:         0 on success or other int error code on error.            */
267/* Side effects:                                                              */
268/* Description:                                                               */
269/*                  This routine start a single SHA process                   */
270/*----------------------------------------------------------------------------*/
271static int SHA_Start(struct SHA_HANDLE_T *handleptr, u8 type)
272{
273	struct npcm_sha_regs *regs = sha_priv->regs;
274
275	// Initialize handle
276	handleptr->length0 = 0;
277	handleptr->length1 = 0;
278	handleptr->type = type;
279	handleptr->active = true;
280
281	// Set SHA type
282	writeb(handleptr->type & HASH_CFG_SHA1_SHA2, &regs->hash_cfg);
283
284	// Reset SHA hardware
285	SHA_Reset();
286
287	/* The handlePtr->hv is initialized with the correct IV as the SHA engine
288	 * automatically fill the HASH_DIG_Hn registers according to SHA spec
289	 * (following SHA_RST assertion)
290	 */
291	SHA_GetShaDigest_l((u8 *)handleptr->hv, type);
292
293	// Init block with zeros
294	memset(handleptr->block, 0, sizeof(handleptr->block));
295
296	return 0;
297}
298
299/*----------------------------------------------------------------------------*/
300/* Function:        SHA_Update                                                */
301/*                                                                            */
302/* Parameters:      handlePtr - SHA processing handle pointer                 */
303/*                  buffer    - Pointer to the data that will be added to     */
304/*                              the hash calculation                          */
305/*                  len -      Length of data to add to SHA calculation       */
306/*                                                                            */
307/*                                                                            */
308/* Returns:         0 on success or other int error code on error             */
309/* Side effects:                                                              */
310/* Description:                                                               */
311/*                  This routine adds data to previously started SHA          */
312/*                  calculation                                               */
313/*----------------------------------------------------------------------------*/
314static int SHA_Update(struct SHA_HANDLE_T *handleptr, const u8 *buffer, u32 len)
315{
316	struct npcm_sha_regs *regs = sha_priv->regs;
317	u32 localbuffer[SHA_SECRUN_BUFF_SIZE / sizeof(u32)];
318	u32 bufferlen = len;
319	u16 pos = 0;
320	u8 *blockptr;
321	int status;
322
323	// Error check
324	if (!handleptr->active)
325		return -EPROTO;
326
327	// Wait till SHA is not busy
328	status = SHA_BusyWait_l();
329	npcm_sha_check(status);
330
331	// Set SHA type
332	writeb(handleptr->type & HASH_CFG_SHA1_SHA2, &regs->hash_cfg);
333
334	// Write SHA latest digest into SHA module
335	SHA_SetShaDigest_l(handleptr->hv, handleptr->type);
336
337	// Set number of unhashed bytes which remained from last update
338	pos = SHA_BUFF_POS(handleptr->length0);
339
340	// Copy unhashed bytes which remained from last update to secrun buffer
341	SHA_SetBlock_l((u8 *)handleptr->block, pos, 0, localbuffer);
342
343	while (len) {
344		// Wait for the hardware to be available (in case we are hashing)
345		status = SHA_BusyWait_l();
346		npcm_sha_check(status);
347
348		// Move as much bytes  as we can into the secrun buffer
349		bufferlen = min(len, SHA_BUFF_FREE(handleptr->length0));
350
351		// Copy current given buffer to the secrun buffer
352		SHA_SetBlock_l((u8 *)buffer, bufferlen, pos, localbuffer);
353
354		// Update size of hashed bytes
355		handleptr->length0 += bufferlen;
356
357		if (handleptr->length0 < bufferlen)
358			handleptr->length1++;
359
360		// Update length of data left to digest
361		len -= bufferlen;
362
363		// Update given buffer pointer
364		buffer += bufferlen;
365
366		// If secrun buffer is full
367		if (SHA_BUFF_POS(handleptr->length0) == 0) {
368			/* We just filled up the buffer perfectly, so let it hash (we'll
369			 * unload the hash only when we are done with all hashing)
370			 */
371			SHA_FlushLocalBuffer_l(localbuffer);
372
373			pos = 0;
374			bufferlen = 0;
375		}
376	}
377
378	// Wait till SHA is not busy
379	status = SHA_BusyWait_l();
380	npcm_sha_check(status);
381
382	/* Copy unhashed bytes from given buffer to handle block for next update/finish */
383	blockptr = (u8 *)handleptr->block;
384	while (bufferlen)
385		blockptr[--bufferlen + pos] = *(--buffer);
386
387	// Save SHA current digest
388	SHA_GetShaDigest_l((u8 *)handleptr->hv, handleptr->type);
389
390	return 0;
391}
392
393/*----------------------------------------------------------------------------*/
394/* Function:        SHA_Finish                                                */
395/*                                                                            */
396/* Parameters:      handlePtr  - SHA processing handle pointer                */
397/*                  hashDigest - Pointer to a buffer where the final digest   */
398/*                               will be copied to                            */
399/*                                                                            */
400/* Returns:         0 on success or other int error code on error             */
401/* Side effects:                                                              */
402/* Description:                                                               */
403/*                  This routine finish SHA calculation and get               */
404/*                  the resulting SHA digest                                  */
405/*----------------------------------------------------------------------------*/
406static int SHA_Finish(struct SHA_HANDLE_T *handleptr, u8 *hashdigest)
407{
408	struct npcm_sha_regs *regs = sha_priv->regs;
409	u32 localbuffer[SHA_SECRUN_BUFF_SIZE / sizeof(u32)];
410	const u8 lastbyte = SHA_DATA_LAST_BYTE;
411	u16 pos;
412	int status;
413
414	// Error check
415	if (!handleptr->active)
416		return -EPROTO;
417
418	// Set SHA type
419	writeb(handleptr->type & HASH_CFG_SHA1_SHA2, &regs->hash_cfg);
420
421	// Wait till SHA is not busy
422	status = SHA_BusyWait_l();
423	npcm_sha_check(status);
424
425	// Finish off the current buffer with the SHA spec'ed padding
426	pos = SHA_BUFF_POS(handleptr->length0);
427
428	// Init SHA digest
429	SHA_SetShaDigest_l(handleptr->hv, handleptr->type);
430
431	// Load data into secrun buffer
432	SHA_SetBlock_l((u8 *)handleptr->block, pos, 0, localbuffer);
433
434	// Set data last byte as in SHA algorithm spec
435	SHA_SetBlock_l(&lastbyte, 1, pos++, localbuffer);
436
437	// If the remainder of data is longer then one block
438	if (pos > (SHA_BLOCK_LENGTH - 8)) {
439		/* The length will be in the next block Pad the rest of the last block with 0's */
440		SHA_ClearBlock_l((SHA_BLOCK_LENGTH - pos), pos, localbuffer);
441
442		// Hash the current block
443		SHA_FlushLocalBuffer_l(localbuffer);
444
445		pos = 0;
446
447		// Wait till SHA is not busy
448		status = SHA_BusyWait_l();
449		npcm_sha_check(status);
450	}
451
452	// Pad the rest of the last block with 0's except for the last 8-3 bytes
453	SHA_ClearBlock_l((SHA_BLOCK_LENGTH - (8 - 3)) - pos, pos, localbuffer);
454
455	/* The last 8-3 bytes are set to the bit-length of the message in big-endian form */
456	SHA_SetLength32_l(handleptr, localbuffer);
457
458	// Hash all that, and save the hash for the caller
459	SHA_FlushLocalBuffer_l(localbuffer);
460
461	// Wait till SHA is not busy
462	status = SHA_BusyWait_l();
463	npcm_sha_check(status);
464
465	// Save SHA final digest into given buffer
466	SHA_GetShaDigest_l(hashdigest, handleptr->type);
467
468	// Free handle
469	handleptr->active = false;
470
471	return 0;
472}
473
474/*----------------------------------------------------------------------------*/
475/* Function:        SHA_Reset                                                 */
476/*                                                                            */
477/* Parameters:      none                                                      */
478/* Returns:         none                                                      */
479/* Side effects:                                                              */
480/* Description:                                                               */
481/*                  This routine reset SHA module                             */
482/*----------------------------------------------------------------------------*/
483static int SHA_Reset(void)
484{
485	struct npcm_sha_regs *regs = sha_priv->regs;
486
487	writel(readl(&regs->hash_ctr_sts) | HASH_CTR_STS_SHA_RST, &regs->hash_ctr_sts);
488
489	return 0;
490}
491
492/*----------------------------------------------------------------------------*/
493/* Function:        SHA_Power                                                 */
494/*                                                                            */
495/* Parameters:      on - true enable the module, false disable the module     */
496/* Returns:         none                                                      */
497/* Side effects:                                                              */
498/* Description:                                                               */
499/*                  This routine set SHA module power on/off                  */
500/*----------------------------------------------------------------------------*/
501static int SHA_Power(bool on)
502{
503	struct npcm_sha_regs *regs = sha_priv->regs;
504	u8 hash_sts;
505
506	hash_sts = readb(&regs->hash_ctr_sts) & ~HASH_CTR_STS_SHA_EN;
507	writeb(hash_sts | (on & HASH_CTR_STS_SHA_EN), &regs->hash_ctr_sts);
508
509	return 0;
510}
511
512#ifdef SHA_PRINT
513/*----------------------------------------------------------------------------*/
514/* Function:        SHA_PrintRegs                                             */
515/*                                                                            */
516/* Parameters:      none                                                      */
517/* Returns:         none                                                      */
518/* Side effects:                                                              */
519/* Description:                                                               */
520/*                  This routine prints the module registers                  */
521/*----------------------------------------------------------------------------*/
522static void SHA_PrintRegs(void)
523{
524#ifdef SHA_DEBUG_MODULE
525	struct npcm_sha_regs *regs = sha_priv->regs;
526#endif
527	unsigned int i;
528
529	sha_print("/*--------------*/\n");
530	sha_print("/*     SHA      */\n");
531	sha_print("/*--------------*/\n\n");
532
533	sha_print("HASH_CTR_STS    = 0x%02X\n", readb(&regs->hash_ctr_sts));
534	sha_print("HASH_CFG        = 0x%02X\n", readb(&regs->hash_cfg));
535
536	for (i = 0; i < HASH_DIG_H_NUM; i++)
537		sha_print("HASH_DIG_H%d     = 0x%08X\n", i, readl(&regs->hash_dig[i]));
538
539	sha_print("HASH_VER         = 0x%08X\n", readb(&regs->hash_ver));
540
541	sha_print("\n");
542}
543
544/*----------------------------------------------------------------------------*/
545/* Function:        SHA_PrintVersion                                          */
546/*                                                                            */
547/* Parameters:      none                                                      */
548/* Returns:         none                                                      */
549/* Side effects:                                                              */
550/* Description:                                                               */
551/*                  This routine prints the module version                    */
552/*----------------------------------------------------------------------------*/
553static void SHA_PrintVersion(void)
554{
555	struct npcm_sha_regs *regs = sha_priv->regs;
556
557	printf("SHA MODULE VER  = %d\n", readb(&regs->hash_ver));
558}
559#endif
560
561/*----------------------------------------------------------------------------*/
562/* Function:        npcm_sha_selftest                                      */
563/*                                                                            */
564/* Parameters:      type - SHA module type                                    */
565/* Returns:         0 on success or other int error code on error             */
566/* Side effects:                                                              */
567/* Description:                                                               */
568/*                  This routine performs various tests on the SHA HW and SW  */
569/*----------------------------------------------------------------------------*/
570int npcm_sha_selftest(u8 type)
571{
572	int status;
573	struct SHA_HANDLE_T handle;
574	u8 hashdigest[max(SHA_1_HASH_LENGTH, SHA_2_HASH_LENGTH)];
575	u16 i, j;
576
577	/*------------------------------------------------------------------------*/
578	/* SHA1 tests info                                                        */
579	/*------------------------------------------------------------------------*/
580
581	static const u8 sha1selftestbuff[SHA1_NUM_OF_SELF_TESTS][94] = {
582		{"abc"},
583		{"abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq"},
584		{"0123456789012345678901234567890123456789012345678901234567890123"},
585		{0x30, 0x5c, 0x30, 0x2c, 0x02, 0x01, 0x00, 0x30, 0x09, 0x06, 0x05, 0x2b,
586		 0x0e, 0x03, 0x02, 0x1a, 0x05, 0x00, 0x30, 0x06, 0x06, 0x04, 0x67, 0x2a,
587		 0x01, 0x0c, 0x04, 0x14, 0xe1, 0xb6, 0x93, 0xfe, 0x33, 0x43, 0xc1, 0x20,
588		 0x5d, 0x4b, 0xaa, 0xb8, 0x63, 0xfb, 0xcf, 0x6c, 0x46, 0x1e, 0x88, 0x04,
589		 0x30, 0x2c, 0x02, 0x01, 0x00, 0x30, 0x09, 0x06, 0x05, 0x2b, 0x0e, 0x03,
590		 0x02, 0x1a, 0x05, 0x00, 0x30, 0x06, 0x06, 0x04, 0x67, 0x2a, 0x01, 0x0c,
591		 0x04, 0x14, 0x13, 0xc1, 0x0c, 0xfc, 0xc8, 0x92, 0xd7, 0xde, 0x07, 0x1c,
592		 0x40, 0xde, 0x4f, 0xcd, 0x07, 0x5b, 0x68, 0x20, 0x5a, 0x6c}
593	};
594
595	static const u8 sha1selftestbufflen[SHA1_NUM_OF_SELF_TESTS] = {
596		3, 56, 64, 94
597	};
598
599	static const u8 sha1selftestexpres[SHA1_NUM_OF_SELF_TESTS][SHA_1_HASH_LENGTH] = {
600		{0xA9, 0x99, 0x3E, 0x36,
601		 0x47, 0x06, 0x81, 0x6A,
602		 0xBA, 0x3E, 0x25, 0x71,
603		 0x78, 0x50, 0xC2, 0x6C,
604		 0x9C, 0xD0, 0xD8, 0x9D},
605		{0x84, 0x98, 0x3E, 0x44,
606		 0x1C, 0x3B, 0xD2, 0x6E,
607		 0xBA, 0xAE, 0x4A, 0xA1,
608		 0xF9, 0x51, 0x29, 0xE5,
609		 0xE5, 0x46, 0x70, 0xF1},
610		{0xCF, 0x08, 0x00, 0xF7,
611		 0x64, 0x4A, 0xCE, 0x3C,
612		 0xB4, 0xC3, 0xFA, 0x33,
613		 0x38, 0x8D, 0x3B, 0xA0,
614		 0xEA, 0x3C, 0x8B, 0x6E},
615		{0xc9, 0x84, 0x45, 0xc8,
616		 0x64, 0x04, 0xb1, 0xe3,
617		 0x3c, 0x6b, 0x0a, 0x8c,
618		 0x8b, 0x80, 0x94, 0xfc,
619		 0xf3, 0xc9, 0x98, 0xab}
620	};
621
622	/*------------------------------------------------------------------------*/
623	/* SHA2 tests info                                                        */
624	/*------------------------------------------------------------------------*/
625
626	static const u8 sha2selftestbuff[SHA2_NUM_OF_SELF_TESTS][100] = {
627		{ "abc" },
628		{ "abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq" },
629		{'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a',
630		 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a',
631		 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a',
632		 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a',
633		 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a',
634		 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a',
635		 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a',
636		 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a',
637		 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a',
638		 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a', 'a'}
639	};
640
641	static const u8 sha2selftestbufflen[SHA2_NUM_OF_SELF_TESTS] = {
642		3, 56, 100
643	};
644
645	static const u8 sha2selftestexpres[SHA2_NUM_OF_SELF_TESTS][SHA_2_HASH_LENGTH] = {
646		/*
647		 * SHA-256 test vectors
648		 */
649		{ 0xBA, 0x78, 0x16, 0xBF, 0x8F, 0x01, 0xCF, 0xEA,
650		  0x41, 0x41, 0x40, 0xDE, 0x5D, 0xAE, 0x22, 0x23,
651		  0xB0, 0x03, 0x61, 0xA3, 0x96, 0x17, 0x7A, 0x9C,
652		  0xB4, 0x10, 0xFF, 0x61, 0xF2, 0x00, 0x15, 0xAD },
653		{ 0x24, 0x8D, 0x6A, 0x61, 0xD2, 0x06, 0x38, 0xB8,
654		  0xE5, 0xC0, 0x26, 0x93, 0x0C, 0x3E, 0x60, 0x39,
655		  0xA3, 0x3C, 0xE4, 0x59, 0x64, 0xFF, 0x21, 0x67,
656		  0xF6, 0xEC, 0xED, 0xD4, 0x19, 0xDB, 0x06, 0xC1 },
657		{ 0xCD, 0xC7, 0x6E, 0x5C, 0x99, 0x14, 0xFB, 0x92,
658		  0x81, 0xA1, 0xC7, 0xE2, 0x84, 0xD7, 0x3E, 0x67,
659		  0xF1, 0x80, 0x9A, 0x48, 0xA4, 0x97, 0x20, 0x0E,
660		  0x04, 0x6D, 0x39, 0xCC, 0xC7, 0x11, 0x2C, 0xD0 },
661	};
662
663	if (type == npcm_sha_type_sha1) {
664		/*--------------------------------------------------------------------*/
665		/* SHA 1 TESTS                                                        */
666		/*--------------------------------------------------------------------*/
667		for (i = 0; i < SHA1_NUM_OF_SELF_TESTS; i++) {
668			if (i != 3) {
669				status = npcm_sha_calc(npcm_sha_type_sha1, sha1selftestbuff[i], sha1selftestbufflen[i], hashdigest);
670				npcm_sha_check(status);
671			} else {
672				SHA_Power(true);
673				SHA_Reset();
674				status = SHA_Start(&handle, npcm_sha_type_sha1);
675				npcm_sha_check(status);
676				status = SHA_Update(&handle, sha1selftestbuff[i], 73);
677				npcm_sha_check(status);
678				status = SHA_Update(&handle, &sha1selftestbuff[i][73], sha1selftestbufflen[i] - 73);
679				npcm_sha_check(status);
680				status = SHA_Finish(&handle, hashdigest);
681				npcm_sha_check(status);
682				SHA_Power(false);
683			}
684
685			if (memcmp(hashdigest, sha1selftestexpres[i], SHA_1_HASH_LENGTH))
686				return -1;
687		}
688
689	} else {
690		/*--------------------------------------------------------------------*/
691		/* SHA 2 TESTS                                                        */
692		/*--------------------------------------------------------------------*/
693		for (i = 0; i < SHA2_NUM_OF_SELF_TESTS; i++) {
694			SHA_Power(true);
695			SHA_Reset();
696			status = SHA_Start(&handle, npcm_sha_type_sha2);
697			npcm_sha_check(status);
698			if (i == 2) {
699				for (j = 0; j < 10000; j++) { //not working
700					status = SHA_Update(&handle, sha2selftestbuff[i], sha2selftestbufflen[i]);
701					npcm_sha_check(status);
702				}
703			} else {
704				status = SHA_Update(&handle, sha2selftestbuff[i], sha2selftestbufflen[i]);
705				npcm_sha_check(status);
706			}
707
708			status = SHA_Finish(&handle, hashdigest);
709			npcm_sha_check(status);
710			SHA_Power(false);
711			if (memcmp(hashdigest, sha2selftestexpres[i], SHA_2_HASH_LENGTH))
712				return -1;
713
714			npcm_sha_calc(npcm_sha_type_sha2, sha2selftestbuff[i], sha2selftestbufflen[i], hashdigest);
715			if (memcmp(hashdigest, sha2selftestexpres[i], SHA_2_HASH_LENGTH))
716				return -1;
717		}
718	}
719
720	return 0;
721}
722
723/*----------------------------------------------------------------------------*/
724/* Function:        SHA_FlushLocalBuffer_l                                    */
725/*                                                                            */
726/* Parameters:                                                                */
727/* Returns:         none                                                      */
728/* Side effects:                                                              */
729/* Description:     This routine flush secrun buffer to SHA module            */
730/*----------------------------------------------------------------------------*/
731static void SHA_FlushLocalBuffer_l(const u32 *buff)
732{
733	struct npcm_sha_regs *regs = sha_priv->regs;
734	u32 i;
735
736	for (i = 0; i < (SHA_BLOCK_LENGTH / sizeof(u32)); i++)
737		writel(buff[i], &regs->hash_data_in);
738}
739
740/*----------------------------------------------------------------------------*/
741/* Function:        SHA_BusyWait_l                                            */
742/*                                                                            */
743/* Parameters:                                                                */
744/* Returns:         0 if no error was found or DEFS_STATUS_ERROR otherwise    */
745/* Side effects:                                                              */
746/* Description:     This routine wait for SHA unit to no longer be busy       */
747/*----------------------------------------------------------------------------*/
748static int SHA_BusyWait_l(void)
749{
750	struct npcm_sha_regs *regs = sha_priv->regs;
751	u32 timeout = SHA_TIMEOUT;
752
753	do {
754		if (timeout-- == 0)
755			return -ETIMEDOUT;
756	} while ((readb(&regs->hash_ctr_sts) & HASH_CTR_STS_SHA_BUSY)
757						== HASH_CTR_STS_SHA_BUSY);
758
759	return 0;
760}
761
762/*----------------------------------------------------------------------------*/
763/* Function:        SHA_GetShaDigest_l                                        */
764/*                                                                            */
765/* Parameters:      hashDigest - buffer for the hash output.                  */
766/*                  type - SHA module type                                    */
767/* Returns:         none                                                      */
768/* Side effects:                                                              */
769/* Description:     This routine copy the hash digest from the hardware       */
770/*                  and into given buffer (in ram)                            */
771/*----------------------------------------------------------------------------*/
772static void SHA_GetShaDigest_l(u8 *hashdigest, u8 type)
773{
774	struct npcm_sha_regs *regs = sha_priv->regs;
775	u16 j;
776	u8 len = SHA_HASH_LENGTH(type) / sizeof(u32);
777
778	// Copy Bytes from SHA module to given buffer
779	for (j = 0; j < len; j++)
780		((u32 *)hashdigest)[j] = readl(&regs->hash_dig[j]);
781}
782
783/*----------------------------------------------------------------------------*/
784/* Function:        SHA_SetShaDigest_l                                        */
785/*                                                                            */
786/* Parameters:      hashDigest - input buffer to set as hash digest           */
787/*                  type - SHA module type                                    */
788/* Returns:         none                                                      */
789/* Side effects:                                                              */
790/* Description:     This routine set the hash digest in the hardware from     */
791/*                  a given buffer (in ram)                                   */
792/*----------------------------------------------------------------------------*/
793static void SHA_SetShaDigest_l(const u32 *hashdigest, u8 type)
794{
795	struct npcm_sha_regs *regs = sha_priv->regs;
796	u16 j;
797	u8 len = SHA_HASH_LENGTH(type) / sizeof(u32);
798
799	// Copy Bytes from given buffer to SHA module
800	for (j = 0; j < len; j++)
801		writel(hashdigest[j], &regs->hash_dig[j]);
802}
803
804/*----------------------------------------------------------------------------*/
805/* Function:        SHA_SetBlock_l                                            */
806/*                                                                            */
807/* Parameters:      data        - data to copy                                */
808/*                  len         - size of data                                */
809/*                  position    - byte offset into the block at which data    */
810/*                                should be placed                            */
811/*                  block       - block buffer                                */
812/* Returns:         none                                                      */
813/* Side effects:                                                              */
814/* Description:     This routine load bytes into block buffer                 */
815/*----------------------------------------------------------------------------*/
816static void SHA_SetBlock_l(const u8 *data, u32 len, u16 position, u32 *block)
817{
818	u8 *dest = (u8 *)block;
819
820	memcpy(dest + position, data, len);
821}
822
823/*----------------------------------------------------------------------------*/
824/* Function:        SHA_SetBlock_l                                            */
825/*                                                                            */
826/* Parameters:                                                                */
827/*                  len - size of data                                        */
828/*                  position - byte offset into the block at which data       */
829/*                             should be placed                               */
830/*                  block - block buffer                                      */
831/* Returns:         none                                                      */
832/* Side effects:                                                              */
833/* Description:     This routine load zero's into the block buffer            */
834/*----------------------------------------------------------------------------*/
835static void SHA_ClearBlock_l(u16 len, u16 position, u32 *block)
836{
837	u8 *dest = (u8 *)block;
838
839	memset(dest + position, 0, len);
840}
841
842/*----------------------------------------------------------------------------*/
843/* Function:        SHA_SetLength32_l                                         */
844/*                                                                            */
845/* Parameters:                                                                */
846/*                  handlePtr  -   SHA processing handle pointer              */
847/*                  block - block buffer                                      */
848/* Returns:         none                                                      */
849/* Side effects:                                                              */
850/* Description:     This routine set the length of the hash's data            */
851/*                  len is the 32-bit byte length of the message              */
852/*lint -efunc(734,SHA_SetLength32_l) Supperess loss of percision lint warning */
853/*----------------------------------------------------------------------------*/
854static void SHA_SetLength32_l(struct SHA_HANDLE_T *handleptr, u32 *block)
855{
856	u16 *secrunbufferswappedptr = (u16 *)(void *)(block);
857
858	secrunbufferswappedptr[(SHA_BLOCK_LENGTH / sizeof(u16)) - 1] = (u16)
859	((handleptr->length0 << 3) << 8) | ((u16)(handleptr->length0 << 3) >> 8);
860	secrunbufferswappedptr[(SHA_BLOCK_LENGTH / sizeof(u16)) - 2] = (u16)
861	((handleptr->length0 >> (16 - 3)) >> 8) | ((u16)(handleptr->length0 >> (16 - 3)) << 8);
862	secrunbufferswappedptr[(SHA_BLOCK_LENGTH / sizeof(u16)) - 3] = (u16)
863	((handleptr->length1 << 3) << 8) | ((u16)(handleptr->length1 << 3) >> 8);
864	secrunbufferswappedptr[(SHA_BLOCK_LENGTH / sizeof(u16)) - 4] = (u16)
865	((handleptr->length1 >> (16 - 3)) >> 8) | ((u16)(handleptr->length1 >> (16 - 3)) << 8);
866}
867
868static int npcm_sha_bind(struct udevice *dev)
869{
870	sha_priv = calloc(1, sizeof(struct npcm_sha_priv));
871	if (!sha_priv)
872		return -ENOMEM;
873
874	sha_priv->regs = dev_remap_addr_index(dev, 0);
875	if (!sha_priv->regs) {
876		printf("Cannot find sha reg address, binding failed\n");
877		return -EINVAL;
878	}
879
880	printf("SHA: NPCM SHA module bind OK\n");
881
882	return 0;
883}
884
885static const struct udevice_id npcm_sha_ids[] = {
886	{ .compatible = "nuvoton,npcm845-sha" },
887	{ .compatible = "nuvoton,npcm750-sha" },
888	{ }
889};
890
891U_BOOT_DRIVER(npcm_sha) = {
892	.name = "npcm_sha",
893	.id = UCLASS_MISC,
894	.of_match = npcm_sha_ids,
895	.priv_auto = sizeof(struct npcm_sha_priv),
896	.bind = npcm_sha_bind,
897};
898