aes 算法识别与对抗

0x00 前言

在对称加密中,遇到最多的就是DES,AES,其次国内也经常能够看到SM4算法。今天主要对AES进行一个简单分析, 以及一种称之为白盒AES的算法。本文部分内容是从别的博客摘抄。

0x01 AES算法介绍

识别

AES128为例,算法如下图:

整个流程分为以下几部分:

  1. 密钥初始化(key init)
  2. 10轮加密:
    1. 字节替换(SubBytes)
    2. 行位移(Shift Rows)
    3. 列混合(Mix Column)
    4. 轮密钥加密(Add Round Key)

其中最后一轮的加密是不需要经过列混合的。 在我们逆向分析中,只要能够想办法识别出这几个过程的特征,基本就能够知道这个算法是不是aes了。

Key Init 过程中,根据算法可以知道这个扩展后的密钥是一个 16 * 11 的大小,根据这个特征基本可以判定这个算法是AES算法, 另外扩展后的密钥,第一个16个字节其实是包含了原始密钥的,只不过这个时候,密钥是每4个字节翻转的。 比如ABCDABCDABCDABCD 是密钥, 那么扩展之后的密钥,前16个字节就是 DCBADCBADCBADCBA

SubBytes 过程中,需要注意的是, 这个时候会有一个Sbox 参与进来, 在二进制中,通常这就是一个全局变量,可以查看Sbox中的内容来确定是不是AES。 比如,正常 AES 的 Sbox 为

ShiftRows中,需要知道这个位移的关系

MixColumn 中,会存在一个 4 * 4 的数组, 你可以当作是第一行的4个字节,每次都右移一个字节得到下一行。通过这个特征就能够发现是AES.

1
2
3
4
0x02, 0x03, 0x01, 0x01,
0x01, 0x02, 0x03, 0x01,
0x01, 0x01, 0x02, 0x03,
0x03, 0x01, 0x01, 0x02

最后是AddRoundkey, 这个就是输入和最开始的扩展密钥进行抑或的过程,比较简单。

另外在AES中还又一个称之为GaloisMultiplication的乘法运算, 这个也是一个特征。

上面主要讲到了如何识别 AES 算法,你可以发现,其实 AES 的特征非常多,只要识别出一个点,基本上剩下的工作就是去找key,或者是加密模式(ecb, cbc),从我的经验看,业内基本都是清一色的使用cbc模式,所以需要额外在找一个 iv,不过这个基本就是小菜一碟。 那么如何对AES进行防御呢?

防御

对于一个比较有经验的逆向工程师来说, 混淆已经不能够对识别算法造成太大的影响了,比如可以通过模拟执行,直接不管内部算法,或者通过hook,观察输入输出,大致确定算法属于哪一类。本文不讨论如何对抗模拟执行,只要是一个纯算法,基本都没办法对抗。

对于一个攻击者来说,最重要的是识别出一个算法的类型,一个算法的 key,iv,其他完全不需要 care。

那么如何把一个AES算法改成不是AES算法呢? 这就需要魔改 AES 了,比如密钥扩展阶段,你可以再增加一点别的操作,让前16个字节变异,或者故意更改密钥扩展的长度来迷惑攻击者。再比如,把 Sbox 里的内容随机改动一下,确保生成的结果和标准结果不一致。这种魔改的方式,有一定的效果,但是配套起来就比较麻烦,比如需要给SDK写一套,给后台写一套。

另外对于 key 的保护, 通常就是把 key 用另一个算法保护起来, 需要用到的时候再解密。 见过很多把 key 藏在图片里的,然后不断用key 解密key, 虽然一顿操作猛如虎,但是关键点hook一下, 关键数据全部出来了。

接下里谈谈 一种AES的变种,白盒AES。

0x02 白盒AES算法

这个算法其实接触过好几次,但是以前一直不知道还能这么玩。

白盒AES的核心是直接把 key 融入到一个表中,这样,AES 算法就变成了一个查表的过程, 攻击者很难拿到原始的key,自然也就无法攻破AES。

在白盒算法中 AddRoundKeySubBytes 可以 和原始的 Sbox 进行合并,构成一个新的Tbox, 每一轮16个表,10轮就会生成160个表。

最终算法就变成了

1
2
3
4
5
6
7
8
state <- plaintext
for r = 1 to 9:
ShiftRows
TBoxesTyiTables
XORTables
ShiftRows
Tboxes
ciphertext <- state

从安全性上考虑, 这个算法是优于AES的,因为某种程度上,他都可以不算是一个AES了,只不过他的结果刚好和 AES 一致。 攻击者能够想办法拿到160个表,但是无法拿到原始的密钥(实际有办法拿到:)),这就是一种保护。

从性能上来说,白盒AES将运算转变成了查表,性能上确比原来的 AES要 慢不少了。

总结

从我目前的观察来看,目前大部分应用都是在用普通的 AES 算法,基本上密钥都会使用固定字符串或者是通过 RSA + 随机密钥的方式。 白盒 AES 变种可以很多,但需要对算法本身比较了解,能做白盒的人比较少,所以整体上,更加安全些。