ShellCode 如下
strstr ShellCode实现
1.函数原型
char* Mystrstr(const char* SrcStrPtr, const char* SubStrPtr)
{
int nCount;
if (*SubStrPtr) //判断寻找的SubStr是否为空.
{
while (*SrcStrPtr) //判断寻找的srcStr是否为空,不为空循环
{
//内部循环判断.每次 str指针++ 判断跟 substr++ 是否相等.
for (nCount = 0; *(SrcStrPtr + nCount) == *(SubStrPtr + nCount); nCount++)
{
//如果substrptr + 1 没有.则返回找到的字符串.
if (!*(SubStrPtr + nCount + 1))
{
return(char*)SrcStrPtr;
}
}
SrcStrPtr++;
}
return NULL;
}
else
return (char*)SrcStrPtr;
}
2.ShellCode提取.
注意是外平栈. 调用者平展. 有两个参数. 所以在调用的时候.你需要 add esp , 8
UCHAR g_StrstrShellCode[] =
{
0X55,
0X8B,0xEC,
0X53,
0X57,
0X8B,0X7D,0X0C,
0X8A,0X1F,
0X84,0XDB,
0X74,0X3E,
0X56,
0X8B,0X75,0X08,
0X8A,0X06,
0X84,0XC0,
0X74,0X26,
0X8B,0XD6,
0X2B,0XD7,
0X0F,0X1F,0X40,0X00,
0X3A,0XC3,
0X75,0X11,
0X8B,0XC7,
0X8A,0X48,0X01,
0X8D,0X40,0X01,
0X84,0XC9,
0X74,0X15,
0X38,0X0C,0X02,
0X74,0XF1,
0X8A,0X46,0X01,
0X46,
0X42,
0X84,0XC0,
0X75,0XE2,
0X5E,
0X5F,
0X33,0XC0,
0X5B,
0X5D,
0XC3,
0x8b,0xc6,
0x5e,
0x5f,
0x5b,
0x5d,
0xc3,
0x8b,0x45,0x08,
0x5f,
0x5b,
0x5d,
0xc3
};
3.汇编代码如下
push ebp
mov ebp, esp
push ebx
push edi
mov edi, dword ptr ss:[ebp + 0xC]
mov bl, byte ptr ds:[edi]
test bl, bl
je 0x7E004C //重定位
push esi
mov esi, dword ptr ss:[ebp + 0x8]
mov al, byte ptr ds:[esi]
test al, al
je 0x7E003E //重定位
mov edx, esi
sub edx, edi
nop dword ptr ds:[eax], eax
cmp al, bl
jne 0x7E0035 //重定位
mov eax, edi
mov cl, byte ptr ds:[eax + 0x1]
lea eax, dword ptr ds:[eax + 0x1]
test cl, cl
je 0x7E0045 //重定位
cmp byte ptr ds:[edx + eax], cl
je 0x7E0026 //重定位
mov al, byte ptr ds:[esi + 0x1]
inc esi
inc edx
test al, al
jne 0x7E0020 //重定位
pop esi
pop edi
xor eax, eax
pop ebx
pop ebp
ret
mov eax, esi
pop esi
pop edi
pop ebx
pop ebp
ret
mov eax, dword ptr ss:[ebp + 0x8]
pop edi
pop ebx
pop ebp
ret
带有重定位说明.是因为我是直接把汇编考出来的. ShellCode 在内存中查看.可以看到其实自己已经重定位好了. 这是是方便直观贴出来的.
想直接在内存看可以用如下代码
LPVOID lpShellCodeMemory = VirtualAlloc(NULL, 0x1000, MEM_COMMIT, PAGE_EXECUTE_READWRITE);
memcpy(lpShellCodeMemory, g_StrstrShellCode, 0x200);
Od附加. 当memcpy执行完毕之后 去 lpShellCodeMemory 内存查看即可.