public int kirk_CMD10(byte *inbuff, int insize)
{
if (!is_kirk_initialized)
{
return(KIRK_NOT_INITIALIZED);
}
AES128CMACHeader *header = (AES128CMACHeader *)inbuff;
if (!(header->Mode == KIRK_MODE_CMD1 || header->Mode == KIRK_MODE_CMD2 || header->Mode == KIRK_MODE_CMD3))
{
return(KIRK_INVALID_MODE);
}
if (header->DataSize == 0)
{
return(KIRK_DATA_SIZE_ZERO);
}
if (header->Mode == KIRK_MODE_CMD1)
{
header_keys keys; //0-15 AES key, 16-31 CMAC key
Crypto.AES_cbc_decrypt(aes_kirk1_ptr, inbuff, (byte *)&keys, 32); //decrypt AES & CMAC key to temp buffer
Crypto.AES_ctx cmac_key;
Crypto.AES_set_key(&cmac_key, keys.CMAC, 128);
var _cmac_header_hash = new byte[16];
var _cmac_data_hash = new byte[16];
fixed(byte *cmac_header_hash = _cmac_header_hash)
fixed(byte *cmac_data_hash = _cmac_data_hash)
{
Crypto.AES_CMAC(&cmac_key, inbuff + 0x60, 0x30, cmac_header_hash);
//Make sure data is 16 aligned
int chk_size = header->DataSize;
if ((chk_size % 16) != 0)
{
chk_size += 16 - (chk_size % 16);
}
Crypto.AES_CMAC(&cmac_key, inbuff + 0x60, 0x30 + chk_size + header->DataOffset, cmac_data_hash);
if (Crypto.memcmp(cmac_header_hash, header->CMAC_header_hash, 16) != 0)
{
Console.WriteLine("header hash invalid");
return(KIRK_HEADER_HASH_INVALID);
}
if (Crypto.memcmp(cmac_data_hash, header->CMAC_data_hash, 16) != 0)
{
Console.WriteLine("data hash invalid");
return(KIRK_DATA_HASH_INVALID);
}
return(KIRK_OPERATION_SUCCESS);
}
}
return(KIRK_SIG_CHECK_INVALID); //Checks for cmd 2 & 3 not included right now
}