CBC…

Padding_Oracle_Attack

0x01

Padding Oracle是针对分组加密的CBC模式,Attack针对的Padding模式为PKCS#5/PKCS#7.

What’s CBC?

以上清楚的表达了CBC的工作模式流程.
其中:

1
2
3
4
Plaintext表示被填充后的明文块
IV表示初始向量
Key表示加密密钥
Ciphertext表示加密后的密文块

各种分组加密算法块大小

Cipher Block Size
AES 16 Bytes
ARC2 8 Bytes
Blowfish 8 Bytes
CAST 8 Bytes
DES 8 Bytes
DES3 8 Bytes
IDEA 8 Bytes
RC5 8 Bytes
Why Can Attack?

PKCS#5 填充

填充方式:明文最后一个数据块填充N个字节的数据.(N却决于最后剩余的空字节数)
如下图:


以数据块长度是8个字节为例,可填充的值范围是0x01~0x08,可以看出填充的规则就是填充值是可填充个数.

由于解密的过程中,如果最后的明文数据块不符合填充规则,大部分的解密程序会抛出异常,而这个异常就作为是验证Padding Oracle Attack的基础.

How?

条件

  1. 初始变量IV可控[已知]
  2. 加密后的密文已知并可控

应用程序接受到密文,返回情况:

  1. 密文正确,填充正确,明文正确,返回200
  2. 密文非法,填充错误,返回500
  3. 密文合法,填充正确,返回200

以上返回状况针对不同的解密程序而不同.
第二/三种情况是利用所需要的.


CBC加/解密模式详解:

接下以”BRIAN;12;2”作为明文给出加密以及解密过程图示
其中IV会通过例如?en=7B216A634951170FF851D6CC68FC9537858795A28ED4AAC6给出

填充以及加密


加密

解密

可以从图中看出解密得出最后的数据块是正确的填充序列.
其中的Intermediary Value下面用IVa来表示


Two Ways


1.通过Padding Oracle Attack获取明文的方式.
2.Padding Oracle Attack还可以用来构造指定明文的密文.


1.

由于初始变量的可控,修改初始变量并且对第一块密文进行单独解密.

1.
?en=0000000000000000F851D6CC68FC9537 返回值500


可以看出解密后,填充序列不正确,所以返回500.其中IVa是未知的,也即是要获取的.
接下来只需要不断修改IV最后一个字节,修改范围0x00~0xff

2.
?en=000000000000003CF851D6CC68FC9537 返回值200


此时可以通过IV最后一个字节推算出IVa最后一个字节.
1
2
3
IVa ^ 0x3c == 0x01
IVa == 0x3c ^ 0x01
Iva == 0x3d

这样就可以知道IVa最后的字节为0x3d
由于初始变量IV是已知的,可以计算出明文块的最后一个字节的值.
(P代表明块最后一个字节)

1
2
3
P ^ 0x0f == 0x3d //0x0f是已知初始变量IV中的
P == 0x0f ^ 0x3d
P == 0x32 //2

这样就只有到明文块最后的字符是2.

3.
接下来需要不断向前推算出IVa对应字节.


由于填充序列为0x02,所以要修改IV的最后一个字节,计算方法同推算IVa字节类似.
以此类推

最后得到所有的IVa,就可以计算出明文块所有的值.


2.

不同于获取明文,构造密文最重要的是获取IV,并且还要利用之前获取的IVa.

要求第一个数据块解密为’TEST’,可以从CBC的解密模式中得出,只需要明文字节异或对应的IVa即可得到IV.

当然这是填充一个数据块的方式,如果填充的数据块更多怎么办?
这个时候仔细研究CBC的解密模式,你就会发现一个数据块获得的IV可以当作上个数据块的密文.
这样就能使用之前推算IVa的方式,不同的是这次需要获取的值就是攻击者自己传入的IV.
然后用获取的IV在进行此类的推算,最后获取完整的密文和初始变量IV.


0x02

Eg:
攻击的演示:

1
2
3
4
5
Plain = 'BRIAN;12;2'
iv = '12346578'
Plain = 'S_Dante'
key = 'abcdefgh'
cipher = 'des'


0x03

Padding Oracle Attack 最为巧妙的地方是不用获取密钥而就可以利用程序获取想要的东西.

参考资料1

参考资料2

(ง •_•)ง
2017-07-21 14:49:08 星期五