AES: implement CCM extra shit. fixes freeze when DSi home menu has a picture to show.

This commit is contained in:
Arisotura
2021-08-16 23:49:05 +02:00
parent 2d8749a7f2
commit 6062b5e1ff

View File

@ -31,6 +31,7 @@ namespace DSi_AES
u32 Cnt; u32 Cnt;
u32 BlkCnt; u32 BlkCnt;
u32 RemExtra;
u32 RemBlocks; u32 RemBlocks;
bool OutputFlush; bool OutputFlush;
@ -106,6 +107,7 @@ void Reset()
Cnt = 0; Cnt = 0;
BlkCnt = 0; BlkCnt = 0;
RemExtra = 0;
RemBlocks = 0; RemBlocks = 0;
OutputFlush = false; OutputFlush = false;
@ -154,6 +156,22 @@ void Reset()
} }
void ProcessBlock_CCM_Extra()
{
u8 data[16];
u8 data_rev[16];
*(u32*)&data[0] = InputFIFO.Read();
*(u32*)&data[4] = InputFIFO.Read();
*(u32*)&data[8] = InputFIFO.Read();
*(u32*)&data[12] = InputFIFO.Read();
Swap16(data_rev, data);
for (int i = 0; i < 16; i++) CurMAC[i] ^= data_rev[i];
AES_ECB_encrypt(&Ctx, CurMAC);
}
void ProcessBlock_CCM_Decrypt() void ProcessBlock_CCM_Decrypt()
{ {
u8 data[16]; u8 data[16];
@ -272,13 +290,14 @@ void WriteCnt(u32 val)
if (!(oldcnt & (1<<31)) && (val & (1<<31))) if (!(oldcnt & (1<<31)) && (val & (1<<31)))
{ {
// transfer start (checkme) // transfer start (checkme)
RemExtra = (AESMode < 2) ? (BlkCnt & 0xFFFF) : 0;
RemBlocks = BlkCnt >> 16; RemBlocks = BlkCnt >> 16;
OutputMACDue = false; OutputMACDue = false;
if (AESMode == 0 && (!(val & (1<<20)))) printf("AES: CCM-DECRYPT MAC FROM WRFIFO, TODO\n"); if (AESMode == 0 && (!(val & (1<<20)))) printf("AES: CCM-DECRYPT MAC FROM WRFIFO, TODO\n");
if (RemBlocks > 0) if ((RemBlocks > 0) || (RemExtra > 0))
{ {
u8 key[16]; u8 key[16];
u8 iv[16]; u8 iv[16];
@ -288,8 +307,6 @@ void WriteCnt(u32 val)
if (AESMode < 2) if (AESMode < 2)
{ {
if (BlkCnt & 0xFFFF) printf("AES: CCM EXTRA LEN TODO\n");
u32 maclen = (val >> 16) & 0x7; u32 maclen = (val >> 16) & 0x7;
if (maclen < 1) maclen = 1; if (maclen < 1) maclen = 1;
@ -325,8 +342,8 @@ void WriteCnt(u32 val)
} }
} }
//printf("AES CNT: %08X / mode=%d key=%d inDMA=%d outDMA=%d blocks=%d\n", //printf("AES CNT: %08X / mode=%d key=%d inDMA=%d outDMA=%d blocks=%d (BLKCNT=%08X)\n",
// val, AESMode, (val >> 26) & 0x3, InputDMASize, OutputDMASize, RemBlocks); // val, AESMode, (val >> 26) & 0x3, InputDMASize, OutputDMASize, RemBlocks, BlkCnt);
} }
void WriteBlkCnt(u32 val) void WriteBlkCnt(u32 val)
@ -380,7 +397,7 @@ void WriteInputFIFO(u32 val)
void CheckInputDMA() void CheckInputDMA()
{ {
if (RemBlocks == 0) return; if (RemBlocks == 0 && RemExtra == 0) return;
if (InputFIFO.Level() <= InputDMASize) if (InputFIFO.Level() <= InputDMASize)
{ {
@ -401,6 +418,17 @@ void CheckOutputDMA()
} }
void Update() void Update()
{
if (RemExtra > 0)
{
while (InputFIFO.Level() >= 4 && RemExtra > 0)
{
ProcessBlock_CCM_Extra();
RemExtra--;
}
}
if (RemExtra == 0)
{ {
while (InputFIFO.Level() >= 4 && OutputFIFO.Level() <= 12 && RemBlocks > 0) while (InputFIFO.Level() >= 4 && OutputFIFO.Level() <= 12 && RemBlocks > 0)
{ {
@ -414,10 +442,11 @@ void Update()
RemBlocks--; RemBlocks--;
} }
}
CheckOutputDMA(); CheckOutputDMA();
if (RemBlocks == 0) if (RemBlocks == 0 && RemExtra == 0)
{ {
if (AESMode == 0) if (AESMode == 0)
{ {
@ -443,6 +472,15 @@ void Update()
AES_CTR_xcrypt_buffer(&Ctx, CurMAC, 16); AES_CTR_xcrypt_buffer(&Ctx, CurMAC, 16);
Swap16(OutputMAC, CurMAC); Swap16(OutputMAC, CurMAC);
if (OutputFIFO.Level() <= 12)
{
OutputFIFO.Write(*(u32*)&OutputMAC[0]);
OutputFIFO.Write(*(u32*)&OutputMAC[4]);
OutputFIFO.Write(*(u32*)&OutputMAC[8]);
OutputFIFO.Write(*(u32*)&OutputMAC[12]);
}
else
OutputMACDue = true; OutputMACDue = true;
// CHECKME // CHECKME