1+ /*-------------------------------------------------------------
2+
3+ sha.c -- SHA Engine
4+
5+ Copyright (C) 2023
6+ Joris 'DacoTaco' Vermeylen info@dacotaco.com
7+
8+ This software is provided 'as-is', without any express or implied
9+ warranty. In no event will the authors be held liable for any
10+ damages arising from the use of this software.
11+
12+ Permission is granted to anyone to use this software for any
13+ purpose, including commercial applications, and to alter it and
14+ redistribute it freely, subject to the following restrictions:
15+
16+ 1. The origin of this software must not be misrepresented; you
17+ must not claim that you wrote the original software. If you use
18+ this software in a product, an acknowledgment in the product
19+ documentation would be appreciated but is not required.
20+
21+ 2. Altered source versions must be plainly marked as such, and
22+ must not be misrepresented as being the original software.
23+
24+ 3. This notice may not be removed or altered from any source
25+ distribution.
26+
27+ -------------------------------------------------------------*/
28+ #if defined(HW_RVL )
29+
30+ #include <string.h>
31+ #include "gctypes.h"
32+ #include "gcutil.h"
33+ #include "ipc.h"
34+ #include "sha.h"
35+
36+ static s32 __sha_fd = -1 ;
37+ static s32 __sha_hid = -1 ;
38+
39+ #define SHA_HEAPSIZE 0x50
40+ typedef enum
41+ {
42+ ResetContext = 0x00 ,
43+ AddData = 0x01 ,
44+ FinalizeHash = 0x02 ,
45+ } ShaCommand ;
46+
47+ static s32 SHA_ExecuteCommand (const ShaCommand command , sha_context * context , const void * in_data , const u32 data_size , void * out_data )
48+ {
49+ ioctlv * params = (ioctlv * )iosAlloc (__sha_hid , sizeof (ioctlv ) * 3 );
50+ s32 ret = -1 ;
51+
52+ if (params == NULL )
53+ return -4 ;
54+
55+ for (u32 i = 0 ; i < data_size ; i += SHA_BLOCK_SIZE ) {
56+ u32 size = SHA_BLOCK_SIZE ;
57+ ShaCommand block_cmd = command ;
58+
59+ //if it's the final block, set size correctly.
60+ //if it's not the final block, and we got a finalize, we will first send the add command
61+ if (i + SHA_BLOCK_SIZE >= data_size )
62+ size = data_size - i ;
63+ else if (command == FinalizeHash )
64+ block_cmd = AddData ;
65+
66+ params [0 ].data = (void * )((u32 )in_data + i );
67+ params [0 ].len = size ;
68+ params [1 ].data = (void * ) context ;
69+ params [1 ].len = sizeof (sha_context );
70+ params [2 ].data = (void * )((u32 )out_data );
71+ params [2 ].len = 0x14 ;
72+
73+ ret = IOS_Ioctlv (__sha_fd , block_cmd , 1 , 2 , params );
74+ if (ret < 0 )
75+ break ;
76+ }
77+
78+ iosFree (__sha_hid , params );
79+ return ret ;
80+ }
81+
82+ s32 SHA_Init (void )
83+ {
84+ if (__sha_fd >= 0 )
85+ return -1 ;
86+
87+ __sha_fd = IOS_Open ("/dev/sha" , 0 );
88+ if (__sha_fd < 0 )
89+ return __sha_fd ;
90+
91+ //only create heap if it wasn't created yet.
92+ //its never disposed, so only create once.
93+ if (__sha_hid < 0 )
94+ __sha_hid = iosCreateHeap (SHA_HEAPSIZE );
95+
96+ if (__sha_hid < 0 ) {
97+ SHA_Close ();
98+ return __sha_hid ;
99+ }
100+
101+ return 0 ;
102+ }
103+
104+ s32 SHA_Close (void )
105+ {
106+ if (__sha_fd < 0 )
107+ return -1 ;
108+
109+ IOS_Close (__sha_fd );
110+ __sha_fd = -1 ;
111+
112+ return 0 ;
113+ }
114+
115+ s32 SHA_InitializeContext (sha_context * context )
116+ {
117+ if (context == NULL )
118+ return -1 ;
119+
120+ if (((u32 )context ) & 0x1F )
121+ return -4 ;
122+
123+ ioctlv * params = (ioctlv * )iosAlloc (__sha_hid , sizeof (ioctlv ) * 4 );
124+ if (params == NULL )
125+ return -4 ;
126+
127+ memset (params , 0 , sizeof (ioctlv ) * 4 );
128+ params [1 ].data = (void * ) context ;
129+ params [1 ].len = sizeof (sha_context );
130+ s32 ret = IOS_Ioctlv (__sha_fd , ResetContext , 1 , 2 , params );
131+
132+ iosFree (__sha_hid , params );
133+ return ret ;
134+ }
135+ s32 SHA_Calculate (sha_context * context , const void * data , const u32 data_size , void * message_digest )
136+ {
137+ if (context == NULL || message_digest == NULL || data_size == 0 || data == NULL )
138+ return -1 ;
139+
140+ if (((u32 )context & 0x1F ) != 0 || ((u32 )message_digest & 0x1F ) != 0 )
141+ return -4 ;
142+
143+ if ( data != NULL && ((u32 )data & 0x3F ) != 0 )
144+ return -4 ;
145+
146+ return SHA_ExecuteCommand (FinalizeHash , context , data , data_size , message_digest );
147+ }
148+
149+ s32 SHA_Input (sha_context * context , const void * data , const u32 data_size )
150+ {
151+ if (context == NULL || data == NULL || data_size == 0 )
152+ return -1 ;
153+
154+ if ((((u32 )context ) & 0x1F ) || (((u32 )data ) & 0x3F ) || (data_size & ~(SHA_BLOCK_SIZE - 1 )) != 0 )
155+ return -4 ;
156+
157+ return SHA_ExecuteCommand (AddData , context , data , data_size , NULL );
158+ }
159+
160+ #endif
0 commit comments