我正试图从shellcode中取出128位密钥。我已经将shellcode编译为数组中的C代码,就像
一样#include <stdio.h>
#include <stdlib.h>
/*shellcode.c*/
char code[] = "\x31\xC0\x50\x68\x75\x70\x25\x75\x68\x23\x78\x27\x78\x68\x25\x74\x72\x20\x68\x79\x24\x73\x77\x68\x71\x72\x77\x76\x68\x20\x25\x22\x70\x68\x23\x78\x75\x27\x68\x75\x20\x23\x75\x68\x76\x72\x79\x79\x68\x20\x70\x72\x73\x68\x71\x71\x24\x25\x68\x79\x27\x76\x77\x68\x24\x77\x71\x72\x68\x27\x79\x70\x70\x68\x74\x24\x24\x75\x68\x79\x73\x23\x23\x68\x74\x22\x75\x79\x68\x23\x74\x70\x27\x68\x20\x74\x24\x79\x68\x74\x77\x24\x78\x68\x25\x27\x70\x75\x68\x74\x77\x74\x78\x68\x23\x23\x71\x76\x68\x77\x70\x73\x71\x68\x27\x20\x77\x24\x68\x22\x72\x78\x75\x68\x25\x72\x79\x77\x68\x23\x75\x79\x76\x68\x72\x71\x72\x24\x68\x71\x23\x23\x79\x68\x79\x23\x79\x70\x68\x20\x20\x76\x77\x54\x5E\x8B\xFE\x8B\xD7\xFC\xB9\x80\x00\x00\x00\xBB\x41\x00\x00\x00\x31\xC0\x50\xAC\x33\xC3\xAA\xE2\xFA\x54\x5E\xCC";
int main(int argc, char **argv)
{
int (*func)();
func = (int (*)()) code;
(int)(*func)();
}
当我在linux下使用GCC编译它时。在使用GDB进行反汇编之后,将shellcode放在代码数组中;
(gdb) disas &code
Dump of assembler code for function code:
0x0000000000600840 <+0>: xor %eax,%eax
0x0000000000600842 <+2>: push %rax
0x0000000000600843 <+3>: pushq $0x75257075
0x0000000000600848 <+8>: pushq $0x78277823
0x000000000060084d <+13>: pushq $0x20727425
0x0000000000600852 <+18>: pushq $0x77732479
0x0000000000600857 <+23>: pushq $0x76777271
0x000000000060085c <+28>: pushq $0x70222520
0x0000000000600861 <+33>: pushq $0x27757823
0x0000000000600866 <+38>: pushq $0x75232075
0x000000000060086b <+43>: pushq $0x79797276
0x0000000000600870 <+48>: pushq $0x73727020
0x0000000000600875 <+53>: pushq $0x25247171
0x000000000060087a <+58>: pushq $0x77762779
0x000000000060087f <+63>: pushq $0x72717724
0x0000000000600884 <+68>: pushq $0x70707927
0x0000000000600889 <+73>: pushq $0x75242474
0x000000000060088e <+78>: pushq $0x23237379
0x0000000000600893 <+83>: pushq $0x79752274
0x0000000000600898 <+88>: pushq $0x27707423
0x000000000060089d <+93>: pushq $0x79247420
0x00000000006008a2 <+98>: pushq $0x78247774
0x00000000006008a7 <+103>: pushq $0x75702725
0x00000000006008ac <+108>: pushq $0x78747774
0x00000000006008b1 <+113>: pushq $0x76712323
0x00000000006008b6 <+118>: pushq $0x71737077
0x00000000006008bb <+123>: pushq $0x24772027
0x00000000006008c0 <+128>: pushq $0x75787222
0x00000000006008c5 <+133>: pushq $0x77797225
0x00000000006008ca <+138>: pushq $0x76797523
0x00000000006008cf <+143>: pushq $0x24727172
0x00000000006008d4 <+148>: pushq $0x79232371
0x00000000006008d9 <+153>: pushq $0x70792379
0x00000000006008de <+158>: pushq $0x77762020
0x00000000006008e3 <+163>: push %rsp
0x00000000006008e4 <+164>: pop %rsi
0x00000000006008e5 <+165>: mov %esi,%edi
0x00000000006008e7 <+167>: mov %edi,%edx
0x00000000006008e9 <+169>: cld
0x00000000006008ea <+170>: mov $0x80,%ecx
0x00000000006008ef <+175>: mov $0x41,%ebx
0x00000000006008f4 <+180>: xor %eax,%eax
0x00000000006008f6 <+182>: push %rax
0x00000000006008f7 <+183>: lods %ds:(%rsi),%al
0x00000000006008f8 <+184>: xor %ebx,%eax
0x00000000006008fa <+186>: stos %al,%es:(%rdi)
0x00000000006008fb <+187>: loop 0x6008f7 <code+183>
0x00000000006008fd <+189>: push %rsp
0x00000000006008fe <+190>: pop %rsi
0x00000000006008ff <+191>: int3
0x0000000000600900 <+192>: add %al,(%rax)
End of assembler dump.
查看反汇编128位密钥将在6008fb的循环指令后计算。我对GDB不太满意。如何从这个shellcode中获取128位密钥我怀疑我需要在循环后立即放置一个指针并查看内容?但我不知道该怎么做。 非常感谢你提前...
答案 0 :(得分:0)
如果您可以成功运行此代码,它将在最后的int3
指令处停止。此时,您将在rsp+8
开始在内存中使用解密后的字符串(与rsi+8
相同)。例如,您可以gdb
从x/s $rsp+8
打印出来。 +8
来自push %rax
的{{1}}。
请注意,此代码似乎错误地移植了32位代码。所有0x6008f6
指令将存储指令中给出的立即数,后跟4个零字节。解密将导致每4个字母出现pushq
(并且仅获得密钥的一半)。位于AAAA
的{{1}}将使mov %esi,%edi
的顶部位为零,因此代码仅在堆栈位于地址空间的前4GB(通常不在64位系统)。
此外,代码假定它在堆栈上,但是你的C包装器将它放在数据部分中。无论如何,您也需要执行权限。
或者,由于此代码除了通过0x6008e5
对值进行异或操作之外什么都不做,您可以轻松地手动执行此操作,记住x86是小端,因此反汇编中打印的常量必须进行字节交换。