跳转到了这里
然后计算得到第一个自解密的首地址
第一个自解密代码
#include<idc.idc> static main() { auto i = 0; for(i=0;i<=0x151;i++) { PatchByte(0x004051FC + i,Byte(0x004051FC + i) ^ 0x72); } }
解密后创建函数,F5 写脚本得到第一部分
a = [101,108,99,111,109,101] b = [51,64,49,98,59,98] s1 = '' k = 0 for i in range(6): j = (a[i] ^ b[i]) + 35 k ^= j s1 += chr(j) print s1
这六个字符(char)异或值(0x20)作为第二个自解密异或值
第二个自解密脚本
#include<idc.idc> static main() { auto i = 0; for(i = 256; i < 496;i++) { PatchByte(0x00405018 + i,Byte(0x00405018 + i) ^ 32); } }
这里的跳转是 jmp 寄存器 无法被解析 我们直接修改为jmp 地址(注意从add那条指令开始修改 不然要修改到下面的地址)
因为这里吧add覆盖了 我们到跳转点写一个相同的add
之后后面的跳转类似 且不会修改到重要汇编代码 这里我把两处重命名为 tototo和fofofo 方便写汇编
然后F5 得到清晰的伪代码
可以看到第三部分是明文比较 我们现在只需要第二部分了
但是我还是没有看懂这博客里面的代码 自己也写不出来就用他的吧。。。还是太菜了
https://www.cnblogs.com/harmonica11/p/13073221.html
最后的代码如下
a = [101,108,99,111,109,101] b = [51,64,49,98,59,98] flag = 'ACTF{' k = 0 for i in range(6): j = (a[i] ^ b[i]) + 35 k ^= j flag += chr(j) flag += '_' b=[0x30,0x4,0x4,0x3,0x30,0x63] a="F6 A3 5B 9D E0 95 98 68 8C 65 BB 76 89 D4 09 FD F3 5C 3C 4C 36 8E 4D C4 80 44 D6 A9 01 32 77 29 90 BC C0 A8 D8 F9 E1 1D E4 67 7D 2A 2C 59 9E 3D 7A 34 11 43 74 D1 62 60 02 4B AE 99 57 C6 73 B0 33 18 2B FE B9 85 B6 D9 DE 7B CF 4F B3 D5 08 7C 0A 71 12 06 37 FF 7F B7 46 42 25 C9 D0 50 52 CE BD 6C E5 6F A5 15 ED 64 F0 23 35 E7 0C 61 A4 D7 51 75 9A F2 1E EB 58 F1 94 C3 2F 56 F7 E6 86 47 FB 83 5E CC 21 4A 24 07 1C 8A 5A 17 1B DA EC 38 0E 7E B4 48 88 F4 B8 27 91 00 13 97 BE 53 C2 E8 EA 1A E9 2D 14 0B BF B5 40 79 D2 3E 19 5D F8 69 39 5F DB FA B2 8B 6E A2 DF 16 E2 63 B1 20 CB BA EE 8D AA C8 C7 C5 05 66 6D 3A 45 72 0D CA 84 4E F5 31 6B 92 DC DD 9C 3F 55 96 A1 9F CD 9B E3 A0 A7 FC C1 78 10 2E 82 8F 30 54 04 AC 41 93 D3 3B EF 03 81 70 A6 1F 22 26 28 6A AB 87 AD 49 0F AF" a=a.split() for i in range(len(a)): a[i]=eval("0x"+a[i]) for i in range(6): flag += chr((0x83+i)^a.index(b[i])) flag += '_5mcsM<}' print flag