Skip to content

Commit 29ecc45

Browse files
committed
sha: remove need for 64 byte alignment on input
1 parent aa87b60 commit 29ecc45

File tree

1 file changed

+29
-17
lines changed

1 file changed

+29
-17
lines changed

libogc/sha.c

Lines changed: 29 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ distribution.
2727
-------------------------------------------------------------*/
2828
#if defined(HW_RVL)
2929

30+
#include <malloc.h>
3031
#include <string.h>
3132
#include "gctypes.h"
3233
#include "gcutil.h"
@@ -43,36 +44,50 @@ typedef enum
4344
AddData = 0x01,
4445
FinalizeHash = 0x02,
4546
} ShaCommand;
47+
static u8 input_buffer[0x1000] ATTRIBUTE_ALIGN(64);
4648

4749
static s32 SHA_ExecuteCommand(const ShaCommand command, sha_context* context, const void* in_data, const u32 data_size, void* out_data)
4850
{
4951
ioctlv* params = (ioctlv*)iosAlloc(__sha_hid, sizeof(ioctlv) * 3);
50-
s32 ret = -1;
51-
5252
if(params == NULL)
53-
return -4;
53+
return -5;
5454

55-
for (u32 i = 0; i < data_size; i += SHA_MSGBLOCK_SIZE) {
56-
u32 size = SHA_MSGBLOCK_SIZE;
55+
params[1].data = (void*) context;
56+
params[1].len = sizeof(sha_context);
57+
params[2].data = out_data;
58+
params[2].len = 0x14;
59+
60+
//if data is not 64-byte aligned we use the internal input_buffer to contain the data
61+
bool isAlignedInput = ((u32)in_data & 0x3F) == 0;
62+
s32 ret = -1;
63+
64+
for (u32 i = 0; i < data_size;)
65+
{
66+
const void* input = in_data + i;
67+
u32 size = isAlignedInput ? SHA_MSGBLOCK_SIZE : sizeof(input_buffer);
5768
ShaCommand block_cmd = command;
58-
69+
5970
//if it's the final block, set size correctly.
6071
//if it's not the final block, and we got a finalize, we will first send the add command
61-
if(i+SHA_MSGBLOCK_SIZE >= data_size)
72+
if(i+size >= data_size)
6273
size = data_size - i;
6374
else if(command == FinalizeHash)
6475
block_cmd = AddData;
6576

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;
77+
if(!isAlignedInput)
78+
{
79+
input = input_buffer;
80+
memcpy(input_buffer, in_data + i, size);
81+
}
82+
83+
params[0].data = (void*)input;
84+
params[0].len = size;
7285

7386
ret = IOS_Ioctlv(__sha_fd, block_cmd, 1, 2, params);
7487
if (ret < 0)
7588
break;
89+
90+
i += size;
7691
}
7792

7893
iosFree(__sha_hid, params);
@@ -140,9 +155,6 @@ s32 SHA_Calculate(sha_context* context, const void* data, const u32 data_size, v
140155
if(((u32)context & 0x1F) != 0 || ((u32)message_digest & 0x1F) != 0)
141156
return -4;
142157

143-
if( data != NULL && ((u32)data & 0x3F) != 0)
144-
return -4;
145-
146158
return SHA_ExecuteCommand(FinalizeHash, context, data, data_size, message_digest);
147159
}
148160

@@ -151,7 +163,7 @@ s32 SHA_Input(sha_context* context, const void* data, const u32 data_size)
151163
if(context == NULL || data == NULL || data_size == 0)
152164
return -1;
153165

154-
if((((u32)context) & 0x1F) || (((u32)data) & 0x3F))
166+
if(((u32)context) & 0x1F)
155167
return -4;
156168

157169
return SHA_ExecuteCommand(AddData, context, data, data_size, NULL);

0 commit comments

Comments
 (0)