常见加解密算法07 - 分组密码实战

160 阅读3分钟

各位as handsome as Pan An, national beauty and heavenly fragrance的读者们好啊,今天我们来实战一下AES算法的逆向。

样本已上传到 github.com/aprz512/And…

Java层的比较简单就略过了,直接看C层的。

反汇编观察

bool __fastcall Java_com_kanxue_cipher7test_MainActivity_test3(__int64 a1, __int64 a2, __int64 a3)
{
  int i; // [xsp+24h] [xbp-7Ch]
  __int64 v5; // [xsp+28h] [xbp-78h]
  __int64 v6; // [xsp+38h] [xbp-68h]
  __int128 v7[2]; // [xsp+60h] [xbp-40h]
  __int128 v8; // [xsp+80h] [xbp-20h] BYREF
  __int64 v9; // [xsp+98h] [xbp-8h]

  v9 = *(_QWORD *)(_ReadStatusReg(ARM64_SYSREG(331302)) + 40);
  v6 = GetStringUTFChars(a1, a3, 0LL);
  v8 = xmmword_2CB77;
  v5 = sub_11210(v6, "i am encrypt key", &v8);
  v7[1] = xmmword_2CB97;
  v7[0] = xmmword_2CB87;
  for ( i = 0; i <= 32 && *(unsigned __int8 *)(v5 + i) == *((unsigned __int8 *)v7 + i); ++i )
    ;
  _ReadStatusReg(ARM64_SYSREG(3, 3, 13, 0, 2));
  return i == 32;
}

使用 findcrypt 跑一下:

sub_11210 是一个AES加密函数。

继续分析可知:

  • i am encrypt key 是密钥,v8 是初始化向量,为:
.rodata:000000000002CB77 00 01 02 03 04 05 06 07 08 09+xmmword_2CB77 DCB 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0xA, 0xB, 0xC, 0xD, 0xE, 0xF
.rodata:000000000002CB77 0A 0B 0C 0D 0E 0F

接下来就是使用重放来确定其工作模式。

使用 frida hook这个函数:

function hook_libnativelib() {
    var nativelibmodule = Process.getModuleByName("libnative-lib.so");
    var sub11210 = nativelibmodule.base.add(0x11210);

    Interceptor.attach(sub11210, {
        onEnterfunction (args) {
            console.log("content: "hexdump(args[0]));
            console.log("key: "hexdump(args[1]));
            console.log("iv: "hexdump(args[2]));
        }, onLeavefunction (result) {
            console.log("result: "hexdump(result));
        }
    });

}

function aes_main() {
    if (Java.available) {
        Java.perform(function () {
            console.log("go into main");
            var RuntimeClass = Java.use('java.lang.Runtime');
            RuntimeClass.loadLibrary0.overload('java.lang.Class''java.lang.String').implementation = function (arg0: object, arg1: string) {
                var result = this.loadLibrary0(arg0, arg1);
                console.log("Runtime.loadLibrary0:", arg1);
                if (arg1.indexOf('native-lib') != -1) {
                    hook_libnativelib();
                }

                return result;
            }
        })
    }
}

setImmediate(aes_main);

随便输入一个 q

content:               0  1  2  3  4  5  6  7  8  9  A  B  C  D  E  F  0123456789ABCDEF
74e30d78c8  71 00 00 c2 78 67 3c ad db 52a c5 e0 18 d3 52  q...xg<..]*....R

key:               0  1  2  3  4  5  6  7  8  9  A  B  C  D  E  F  0123456789ABCDEF
74e2e30b22  69 20 61 620 65 663 72 79 70 74 20 665 79  i am encrypt key

iv:               0  1  2  3  4  5  6  7  8  9  A  B  C  D  E  F  0123456789ABCDEF
7ffd669b30  00 01 02 03 04 05 06 07 08 09 000c 000f  ................

result:               0  1  2  3  4  5  6  7  8  9  A  B  C  D  E  F  0123456789ABCDEF
753e6dcc90  19 4e e9 8f a6 c6 39 44 b4 af 70 aa d6 763 e9  .N....9D..p..{c.

查看输出为16位,可知,工作模式要么是 ECB 要么是 CBC。再写个32位的重复输入就观察输出就知道是哪中模式了。直接说结论,就是 CBC 模式,可以自行尝试。

当然也可以在 CyberChef里面尝试各种组合,看哪种工作模式匹配: