复现此题学习一下AES算法、DFA攻击和Frida的食用方法
0x00 AES算法 参考:https://zhuanlan.zhihu.com/p/397940508
0x01 DFA攻击 参考:https://blog.csdn.net/fenfei331/article/details/126385120
关键:在倒数第一轮列混合和倒数第二轮列混合之间(在AES-128中也就是第8轮和第9轮之间,因为最后第10轮不做列混合),修改此时中间结果的一个字节,会导致最终密文和正确密文有4个字节的不同。通过多次的修改,得到多组错误的密文,然后通过正确密文和这些错误密文能够推算出第10轮的密钥(加密模式下),继而能推算出原始密钥。
实际应用中,需要先找准列混合的函数位置 ,然后在他之前去插入缺陷数据。
0x02 Frida 参考:https://www.52pojie.cn/thread-1128884-1-1.html
就是用来HOOK的(
0x03 题目分析 先上Findcrypt,可以找到AES的S盒,但是没有调用的地方
函数不多,一个个找可以找到类似AES的函数
函数结尾有AES-128的特征,16B参与运算
找不到密钥和具体调用S盒的地方,但是根据已存在的AES的S盒和函数结构推测使用的就是AES算法,考虑使用DFA获取密钥
上Frida写脚本
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 import fridaimport ossession = frida.attach("m1_read.exe" ) currentDir = os.getcwd() def getJsScript (fileName="getKey.js" , fileDir=currentDir ) -> str : with open (fileDir + "\\" + fileName, encoding='utf-8' ) as jsScript: return jsScript.read().rstrip() script = session.create_script(getJsScript()) script.load()
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 var baseAddr = Module .findBaseAddress ("m1_read.exe" )var whiteAES = new NativeFunction (baseAddr.add (0x4BF0 ), 'pointer' , ['pointer' ,'pointer' ])var count = 9 Interceptor .attach (baseAddr.add (0x4C2C ),{ onEnter : function (args ){ count++; if (count == 9 ){ var p = ptr (this .context .rdi ) p.add (Math .floor (Math .random ()*16 )).writeU8 (Math .floor (Math .random ()*256 )) } }, onLeave :(retval ) => { } }) for (let index = 0 ; index < 33 ; index++){ var l = Memory .allocAnsiString ("0123456789abcdef" ); var b = Memory .alloc (16 ); whiteAES (l, b); console .log (hexdump (b.readByteArray (16 ),{header :false })); count = 0 ; }
运行脚本的结果如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 00000000 72 93 98 12 0f 00 94 f4 03 7a 44 ee dd 99 20 6f r........zD... o 00000000 72 93 98 5a 0f 00 aa f4 03 2d 44 ee 16 99 20 6f r..Z.....-D... o 00000000 72 56 98 12 b6 00 94 f4 03 7a 44 30 dd 99 b9 6f rV.......zD0...o 00000000 1c 93 98 12 0f 00 94 89 03 7a ce ee dd c8 20 6f .........z.... o 00000000 72 93 98 c4 0f 00 d4 f4 03 d4 44 ee ac 99 20 6f r.........D... o 00000000 72 17 98 12 c1 00 94 f4 03 7a 44 7a dd 99 02 6f r........zDz...o 00000000 72 93 98 e5 0f 00 ad f4 03 0a 44 ee 08 99 20 6f r.........D... o 00000000 72 84 98 12 6a 00 94 f4 03 7a 44 68 dd 99 a6 6f r...j....zDh...o 00000000 d2 93 98 12 0f 00 94 57 03 7a 31 ee dd 36 20 6f .......W.z1..6 o 00000000 72 93 65 12 0f 7c 94 f4 90 7a 44 ee dd 99 20 0f r.e..|...zD... . 00000000 72 93 98 3a 0f 00 e8 f4 03 aa 44 ee 98 99 20 6f r..:......D... o 00000000 72 93 98 44 0f 00 49 f4 03 b2 44 ee 24 99 20 6f r..D..I...D.$. o 00000000 73 93 98 12 0f 00 94 1f 03 7a 76 ee dd 6b 20 6f s........zv..k o 00000000 72 7d 98 12 7e 00 94 f4 03 7a 44 bf dd 99 23 6f r}..~....zD...#o 00000000 72 20 98 12 8a 00 94 f4 03 7a 44 c4 dd 99 35 6f r .......zD...5o 00000000 5e 93 98 12 0f 00 94 35 03 7a 1a ee dd 20 20 6f ^......5.z... o 00000000 72 93 98 a5 0f 00 1e f4 03 77 44 ee 15 99 20 6f r........wD... o 00000000 72 93 98 5c 0f 00 07 f4 03 a5 44 ee 06 99 20 6f r..\......D... o 00000000 72 93 eb 12 0f e0 94 f4 13 7a 44 ee dd 99 20 2a r........zD... * 00000000 72 93 98 97 0f 00 f8 f4 03 c5 44 ee 2a 99 20 6f r.........D.*. o 00000000 72 93 98 ab 0f 00 99 f4 03 d0 44 ee 5b 99 20 6f r.........D.[. o 00000000 72 93 98 cb 0f 00 bd f4 03 9d 44 ee 58 99 20 6f r.........D.X. o 00000000 72 73 98 12 05 00 94 f4 03 7a 44 c5 dd 99 3d 6f rs.......zD...=o 00000000 72 dd 98 12 bf 00 94 f4 03 7a 44 b9 dd 99 45 6f r........zD...Eo 00000000 72 93 67 12 0f 5c 94 f4 d6 7a 44 ee dd 99 20 bb r.g..\...zD... . 00000000 72 84 98 12 42 00 94 f4 03 7a 44 da dd 99 f3 6f r...B....zD....o 00000000 72 68 98 12 b2 00 94 f4 03 7a 44 5c dd 99 b1 6f rh.......zD\...o 00000000 72 e5 98 12 66 00 94 f4 03 7a 44 27 dd 99 42 6f r...f....zD'..Bo 00000000 72 fb 98 12 6e 00 94 f4 03 7a 44 7c dd 99 cc 6f r...n....zD|...o 00000000 72 93 98 86 0f 00 27 f4 03 18 44 ee e0 99 20 6f r.....'...D... o 00000000 72 93 63 12 0f 29 94 f4 8a 7a 44 ee dd 99 20 b0 r.c..)...zD... . 00000000 72 93 98 10 0f 00 cc f4 03 01 44 ee cd 99 20 6f r.........D... o 00000000 72 e0 98 12 77 00 94 f4 03 7a 44 ba dd 99 9a 6f r...w....zD....o
程序最后有一步异或0x66,因此上面的数据需要进行异或后才能使用
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 data = """ 00000000 72 93 98 12 0f 00 94 f4 03 7a 44 ee dd 99 20 6f r........zD... o 00000000 72 93 98 5a 0f 00 aa f4 03 2d 44 ee 16 99 20 6f r..Z.....-D... o 00000000 72 56 98 12 b6 00 94 f4 03 7a 44 30 dd 99 b9 6f rV.......zD0...o 00000000 1c 93 98 12 0f 00 94 89 03 7a ce ee dd c8 20 6f .........z.... o 00000000 72 93 98 c4 0f 00 d4 f4 03 d4 44 ee ac 99 20 6f r.........D... o 00000000 72 17 98 12 c1 00 94 f4 03 7a 44 7a dd 99 02 6f r........zDz...o 00000000 72 93 98 e5 0f 00 ad f4 03 0a 44 ee 08 99 20 6f r.........D... o 00000000 72 84 98 12 6a 00 94 f4 03 7a 44 68 dd 99 a6 6f r...j....zDh...o 00000000 d2 93 98 12 0f 00 94 57 03 7a 31 ee dd 36 20 6f .......W.z1..6 o 00000000 72 93 65 12 0f 7c 94 f4 90 7a 44 ee dd 99 20 0f r.e..|...zD... . 00000000 72 93 98 3a 0f 00 e8 f4 03 aa 44 ee 98 99 20 6f r..:......D... o 00000000 72 93 98 44 0f 00 49 f4 03 b2 44 ee 24 99 20 6f r..D..I...D.$. o 00000000 73 93 98 12 0f 00 94 1f 03 7a 76 ee dd 6b 20 6f s........zv..k o 00000000 72 7d 98 12 7e 00 94 f4 03 7a 44 bf dd 99 23 6f r}..~....zD...#o 00000000 72 20 98 12 8a 00 94 f4 03 7a 44 c4 dd 99 35 6f r .......zD...5o 00000000 5e 93 98 12 0f 00 94 35 03 7a 1a ee dd 20 20 6f ^......5.z... o 00000000 72 93 98 a5 0f 00 1e f4 03 77 44 ee 15 99 20 6f r........wD... o 00000000 72 93 98 5c 0f 00 07 f4 03 a5 44 ee 06 99 20 6f r..\......D... o 00000000 72 93 eb 12 0f e0 94 f4 13 7a 44 ee dd 99 20 2a r........zD... * 00000000 72 93 98 97 0f 00 f8 f4 03 c5 44 ee 2a 99 20 6f r.........D.*. o 00000000 72 93 98 ab 0f 00 99 f4 03 d0 44 ee 5b 99 20 6f r.........D.[. o 00000000 72 93 98 cb 0f 00 bd f4 03 9d 44 ee 58 99 20 6f r.........D.X. o 00000000 72 73 98 12 05 00 94 f4 03 7a 44 c5 dd 99 3d 6f rs.......zD...=o 00000000 72 dd 98 12 bf 00 94 f4 03 7a 44 b9 dd 99 45 6f r........zD...Eo 00000000 72 93 67 12 0f 5c 94 f4 d6 7a 44 ee dd 99 20 bb r.g..\...zD... . 00000000 72 84 98 12 42 00 94 f4 03 7a 44 da dd 99 f3 6f r...B....zD....o 00000000 72 68 98 12 b2 00 94 f4 03 7a 44 5c dd 99 b1 6f rh.......zD\...o 00000000 72 e5 98 12 66 00 94 f4 03 7a 44 27 dd 99 42 6f r...f....zD'..Bo 00000000 72 fb 98 12 6e 00 94 f4 03 7a 44 7c dd 99 cc 6f r...n....zD|...o 00000000 72 93 98 86 0f 00 27 f4 03 18 44 ee e0 99 20 6f r.....'...D... o 00000000 72 93 63 12 0f 29 94 f4 8a 7a 44 ee dd 99 20 b0 r.c..)...zD... . 00000000 72 93 98 10 0f 00 cc f4 03 01 44 ee cd 99 20 6f r.........D... o 00000000 72 e0 98 12 77 00 94 f4 03 7a 44 ba dd 99 9a 6f r...w....zD....o """ def cut (obj, sec ): return [obj[i:i+sec] for i in range (0 , len (obj), sec)] data = cut(data, 76 ) data = data[:-1 ] for i in range (len (data)): data[i] = data[i][11 :-18 ] for i in data: tmp = i.split(' ' ) res = '' for j in tmp: res += '{:02x}' .format (int (j, 16 ) ^ int ("66" , 16 )) print (res)
异或结果
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 14f5fe746966f292651c2288bbff4609 14f5fe3c6966cc92654b228870ff4609 1430fe74d066f292651c2256bbffdf09 7af5fe746966f2ef651ca888bbae4609 14f5fea26966b29265b22288caff4609 1471fe74a766f292651c221cbbff6409 14f5fe836966cb92656c22886eff4609 14e2fe740c66f292651c220ebbffc009 b4f5fe746966f231651c5788bb504609 14f50374691af292f61c2288bbff4669 14f5fe5c69668e9265cc2288feff4609 14f5fe2269662f9265d4228842ff4609 15f5fe746966f279651c1088bb0d4609 141bfe741866f292651c22d9bbff4509 1446fe74ec66f292651c22a2bbff5309 38f5fe746966f253651c7c88bb464609 14f5fec3696678926511228873ff4609 14f5fe3a6966619265c3228860ff4609 14f58d746986f292751c2288bbff464c 14f5fef169669e9265a322884cff4609 14f5fecd6966ff9265b622883dff4609 14f5fead6966db9265fb22883eff4609 1415fe746366f292651c22a3bbff5b09 14bbfe74d966f292651c22dfbbff2309 14f50174693af292b01c2288bbff46dd 14e2fe742466f292651c22bcbbff9509 140efe74d466f292651c223abbffd709 1483fe740066f292651c2241bbff2409 149dfe740866f292651c221abbffaa09 14f5fee069664192657e228886ff4609 14f50574694ff292ec1c2288bbff46d6 14f5fe766966aa9265672288abff4609 1486fe741166f292651c22dcbbfffc09
利用phoenixAES实现DFA
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 # s1是前文中的33轮数据,以字符串形式存储(包含换行,否则无法识别) import phoenixAES s1 = """ 14f5fe746966f292651c2288bbff4609 14f5fe3c6966cc92654b228870ff4609 1430fe74d066f292651c2256bbffdf09 7af5fe746966f2ef651ca888bbae4609 14f5fea26966b29265b22288caff4609 1471fe74a766f292651c221cbbff6409 14f5fe836966cb92656c22886eff4609 14e2fe740c66f292651c220ebbffc009 b4f5fe746966f231651c5788bb504609 14f50374691af292f61c2288bbff4669 14f5fe5c69668e9265cc2288feff4609 14f5fe2269662f9265d4228842ff4609 15f5fe746966f279651c1088bb0d4609 141bfe741866f292651c22d9bbff4509 1446fe74ec66f292651c22a2bbff5309 38f5fe746966f253651c7c88bb464609 14f5fec3696678926511228873ff4609 14f5fe3a6966619265c3228860ff4609 14f58d746986f292751c2288bbff464c 14f5fef169669e9265a322884cff4609 14f5fecd6966ff9265b622883dff4609 14f5fead6966db9265fb22883eff4609 1415fe746366f292651c22a3bbff5b09 14bbfe74d966f292651c22dfbbff2309 14f50174693af292b01c2288bbff46dd 14e2fe742466f292651c22bcbbff9509 140efe74d466f292651c223abbffd709 1483fe740066f292651c2241bbff2409 149dfe740866f292651c221abbffaa09 14f5fee069664192657e228886ff4609 14f50574694ff292ec1c2288bbff46d6 14f5fe766966aa9265672288abff4609 1486fe741166f292651c22dcbbfffc09 """ with open("testfile", "wb") as t: t.write(s1.encode()) phoenixAES.crack_file("testfile") # 自动打印出来第10轮的密钥 # 结果如下 # B4EF5BCB3E92E21123E951CF6F8F188E
参考:https://github.com/SideChannelMarvels/Stark
使用Stark(自行编译)提供一轮密钥暴力破解AES-128
设定好轮数即可
使用010editor查看提供的out.bin
根据M1卡的存储格式,第一行中,4B为卡号,1B为校验位,剩下为厂商信息 ,因此需要解密的部分为第三行
解密脚本如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 from Crypto.Cipher import AESs = "0B987EF5D94DD679592C4D2FADD4EB89" key = bytes .fromhex("00000000000000000000000000000000" ) enc = bytearray (bytes .fromhex(s)) cipher = AES.new(key, AES.MODE_ECB) for i in range (16 ): enc[i] ^= 0x66 flag = cipher.decrypt(enc) print (flag)
flag{cddc8d28dabb4ea9}
复现过程很是痛苦(