我们有一个嵌入式产品,自 5 年前以来,我们一直在进行多次硬件迭代。我们拥有所有源代码,其中大部分都有很好的文档记录。由于该产品正在积极销售并需要升级,因此我的任务是设计下一代改进版本。
虽然我们拥有所有源代码,并且其中大部分都有详细记录,但安全部分不是,尤其是其最慢的部分,不是一个 72 轮的 128 位哈希函数。我可以在我们的调试器中逐步调试它,执行它,并且代码运行良好,但它很慢。如果我知道它是哪种密码学标准,我可以尝试升级它以在硬件中执行,这将大大加快它的速度。(原来写这个功能的顾问不在我们公司,我找不到她)。
有什么合乎逻辑的方法可以找出我们正在执行哪种加密?我不需要帮助来完成我的工作,如果有任何如何查看代码的策略(“未优化的混乱”),我正在寻求建议;学习它的原理(像这个有 72 轮和 128 位散列);然后寻找候选标准做同样的事情。
我认为在找到记录的标准后,我应该能够通过使用我们的哈希和标准哈希来对各种数字进行哈希处理,然后简单地查看结果是否匹配?
我在网上查找有关使用 72 轮的已知函数的信息,例如Skein 算法,但找不到任何类似的信息。
是否有已知标准的任何已知散列值,例如散列 0 的结果?此散列将 0 转换为这 16 个十六进制字节:
ae c5 40 44 df 2d 91 1c 87 ab 1a ff 59 09 aa b7
函数开始和结束在下面,正如你们中的一些人所要求的,完整的函数在: full_function_code
看起来以前的程序员让旧的 C 编译器对其进行转换,然后以“汇编”样式使用它。也许是为了避免编译器优化,只是我的猜测。
有 72 轮,每轮都以调用 function 结束TricoreDextr()
;这是英飞凌 TriCore DEXTR 指令的 C 等效项。将 dextr 视为将 64 位数字分成两部分(在选定的位位置)并交换它们。
任何概念解释都是一个很大的帮助,谢谢!
/*
* @param in_arr 16 byte long array, input data (128 bits)
* @param out_arr 16 byte long array, output data (128 bits)
*/
void Hash16bytes(unsigned char *in_arr, unsigned char *out_arr)
{
long d0, d1, d2, d3, d4, d5, d6, d7, d8, d9, d10, d11, d12, d13, d15;
long IN[16];
d4 = 0xB12E8FB5;
int i;
for (i = 0; i < 16; i++)
{
IN[i] = (long) (*(in_arr + i));
}
d11 = (IN[3] << 24) | (IN[2] << 16) | (IN[1] << 8) | IN[0];
d10 = (IN[7] << 24) | (IN[6] << 16) | (IN[5] << 8) | IN[4];
d12 = (IN[0xB] << 24) | (IN[0xA] << 16) | (IN[9] << 8) | IN[8];
d13 = (IN[0xF] << 24) | (IN[0xE] << 16) | (IN[0xD] << 8) | IN[0xC];
/* block like this below repeats 72 times... */
d3 = 0x7025BD47;
d8 = 0xCCEE4EFE;
d8 += d13;
d8 += d3;
d8 = TricoreDextr(d8, 6);
/*
etc., TricoreDextr is called total of 72 times
*/
d0 += d15;
d0 += 0x5C4E0000;
d0 -= 0x2EDC;
d0 = TricoreDextr(d0, 5);
*(out_arr + 3) = (unsigned char) ((d5 >> 24) & 0xFF);
*(out_arr + 2) = (unsigned char) ((d5 >> 16) & 0xFF);
*(out_arr + 1) = (unsigned char) ((d5 >> 8) & 0xFF);
*(out_arr + 0) = (unsigned char) ((d5) & 0xFF);
*(out_arr + 7) = (unsigned char) ((d6 >> 24) & 0xFF);
*(out_arr + 6) = (unsigned char) ((d6 >> 16) & 0xFF);
*(out_arr + 5) = (unsigned char) ((d6 >> 8) & 0xFF);
*(out_arr + 4) = (unsigned char) ((d6) & 0xFF);
d8 += d0;
d8 += 0x10320000;
d8 += 0x5476;
*(out_arr + 0xB) = (unsigned char) ((d8 >> 24) & 0xFF);
*(out_arr + 0xA) = (unsigned char) ((d8 >> 16) & 0xFF);
*(out_arr + 9) = (unsigned char) ((d8 >> 8) & 0xFF);
*(out_arr + 8) = (unsigned char) ((d8) & 0xFF);
*(out_arr + 0xF) = (unsigned char) ((d7 >> 24) & 0xFF);
*(out_arr + 0xE) = (unsigned char) ((d7 >> 16) & 0xFF);
*(out_arr + 0xD) = (unsigned char) ((d7 >> 8) & 0xFF);
*(out_arr + 0xC) = (unsigned char) ((d7) & 0xFF);
}