吾爱破解 - 52pojie.cn

 找回密码
 注册[Register]

QQ登录

只需一步,快速开始

查看: 6899|回复: 21
收起左侧

[Packers] [VC] 64位壳子编写

  [复制链接]
舒默哦 发表于 2020-6-27 01:12
本帖最后由 舒默哦 于 2020-7-4 01:19 编辑




更新:
x64壳子的编写源码放到github上了,地址https://github.com/shumo-e/64-github。
源码兼容x32编译,支持x32加壳。实现了IAT加密,添加了一些反调试,实现了反虚拟机的功能。



0x01
感谢《加密与解密》第四版的作者。
我编写的64位壳子就是借助这本书,还不完善,只实现了对代码段的简单加密,等项目完成后,我会把源码和流程发布到github上,到时第一时间通知吾爱的兄弟们。




0x02
加密与解密上的64位壳子的源码有些问题,我会把源码传上来,下面我贴哪些地方需要更改的:
[C++] 纯文本查看 复制代码
01
02
03
04
05
06
07
08
09
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
void __declspec(naked) Start()
{
        _asm {
                pushfq
                call Start1()
                popfq
                jmp rax
                ret
        }
}
 
ULONG_PTR  Start1()
{
         
        //获取kernel32基址       
        ULONGLONG dwBase = GetKernel32Addr();
 
        fnGetProcAddress pfnGetProcAddress = (fnGetProcAddress)MyGetProcessAddress();
        //获取API地址
        fnLoadLibraryA pfnLoadLibraryA = (fnLoadLibraryA)pfnGetProcAddress((HMODULE)dwBase, "LoadLibraryW");
        fnGetModuleHandleA pfnGetModuleHandle = (fnGetModuleHandleA)pfnGetProcAddress((HMODULE)dwBase, "GetModuleHandleW");
        fnVirtualProtect pfnVirtualProtect = (fnVirtualProtect)pfnGetProcAddress((HMODULE)dwBase, "VirtualProtect");
        HMODULE hUser32 = (HMODULE)pfnLoadLibraryA(L"user32.dll");
        HMODULE hKernel32 = (HMODULE)pfnGetModuleHandle(L"kernel32.dll");
 
        fnExitProcess pfnExitProcess = (fnExitProcess)pfnGetProcAddress(hKernel32, "ExitProcess");
 
 
        fnMessageBox pfnMessageBox = (fnMessageBox)pfnGetProcAddress(hUser32, "MessageBoxW");
        ////弹出信息框                       
        int nRet = pfnMessageBox(NULL, L"欢迎使用免费64位加壳程序,是否运行主程序?", L"Hello PEDIY", MB_YESNO);
 
        if (nRet == IDYES)
        {
                //修改代码段属性
                ULONGLONG dwCodeBase = g_stcParam.dwImageBase + (DWORD)g_stcParam.lpStartVA;
                DWORD dwOldProtect = 0;
                pfnVirtualProtect((LPVOID)dwCodeBase, g_stcParam.dwCodeSize, PAGE_EXECUTE_READWRITE, &dwOldProtect);
                XorCode();//解密代码
                pfnVirtualProtect((LPVOID)dwCodeBase, g_stcParam.dwCodeSize, dwOldProtect, &dwOldProtect);
 
                g_oep = (FUN)(g_stcParam.dwImageBase + g_stcParam.dwOEP);
                //跳回原始OEP
                return (ULONG_PTR)g_oep;
        }
        //退出程序
        pfnExitProcess(0);
}

上面这段代码在Stub的工程目录里。
我用的是intel编译器,可以支持x64内联汇编,没有intel编译器也没关系,,可以直接写shellcode,Start()函数字节不多,shellcode就那几十个字节。



0x03
项目中要多次申请内存,为了防止内存泄漏,可以使用智能指针,但我感觉用起来别扭,所有写了一个自动释放内存的类:
[C++] 纯文本查看 复制代码
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
#pragma once
#include <vector>
using namespace std;
 
class AllocMemory
{
        vector<char*>p;
         
public:
        virtual ~AllocMemory()
        {
                for (int i = 0; i < p.size(); i++)
                {
                        free(p[i]);
                }
                p.clear();
        }
 
public:
        template<typename T>
        T auto_malloc( ULONG_PTR MAXSIZE)
        {
                T tmp = (T)malloc(MAXSIZE);
                memset((char*)tmp, 0, MAXSIZE);
                p.push_back((char*)tmp);
                return tmp;
        }
 
 
};

修复重定位表代码没用书里作者提供的,下面贴出代码:
[C++] 纯文本查看 复制代码
01
02
03
04
05
06
07
08
09
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
53
54
55
56
57
58
59
60
61
62
63
64
65
/*////////////////////////////////////////////////////////////////
*※※*  FullName:         PerformBaseRelocation
*※※*  功能        :         修复重定位表
*※※*  Returns:            无
*※※*  Parameter:        char* buff,PE文件首地址
*※※*  Parameter:        POINTER_TYPE Value,buff的基址与贴在内存中的地址的差值
*※※*  Parameter:
*※※*  Parameter:
*※※*  Parameter:
*※※*         Author:                    LCH
*/////////////////////////////////////////////////////////////////;
void PE::PerformBaseRelocation(ULONG_PTR buff, ULONG_PTR Value)
{
        PIMAGE_DOS_HEADER pDosHeader = (PIMAGE_DOS_HEADER)buff;
        PIMAGE_NT_HEADERS pNtHeader = (PIMAGE_NT_HEADERS)(buff + pDosHeader->e_lfanew);
 
        //获取目录表头指针
        PIMAGE_DATA_DIRECTORY pDataDirectory = pNtHeader->OptionalHeader.DataDirectory;
        if (pDataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].Size > 0)
        {
                PIMAGE_BASE_RELOCATION relocation = (PIMAGE_BASE_RELOCATION)((ULONG_PTR buff + pDataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress);
                while (relocation->VirtualAddress > 0)
                {
                        BYTE* dest = (PBYTE)((ULONG_PTR )buff + relocation->VirtualAddress);
                        WORD* relInfo = (PWORD)((ULONG_PTR )relocation + sizeof(IMAGE_BASE_RELOCATION));
                        for (DWORD i = 0; i < ((relocation->SizeOfBlock - sizeof(IMAGE_BASE_RELOCATION)) / 2); ++i, ++relInfo)
                        {
                                DWORD *patchAddrHL;
#ifdef _WIN64
                                ULONGLONG *patchAddr64;//change comlete 64 bit address
#endif
                 
                                ULONG_PTR type, offset;
 
                                //the upper 4 bits define the type of relocation
                                type = *relInfo >> 12;
                                //the lower 12 bits define the offset
                                offset = (*relInfo) & 0xFFF;
 
                                switch (type)
                                {
                                case IMAGE_REL_BASED_ABSOLUTE:
                                        //skip relocation
                                        break;
#ifdef _WIN64
                                case IMAGE_REL_BASED_DIR64://change comlete 64 bit address
                                         patchAddr64 = (ULONGLONG*)(dest + offset);
                                         *patchAddr64 += Value;
                                         break;
#endif                               
                                case IMAGE_REL_BASED_HIGHLOW://change comlete 32 bit address                                       
                                        patchAddrHL = (DWORD*)(dest + offset);
                                        *patchAddrHL += Value;
                                        break;                                                               
                                default:
                                        break;
                                }
                        }
 
                        //advance to next relocation block
                        relocation = PIMAGE_BASE_RELOCATION((char*)relocation + relocation->SizeOfBlock);
                }
        }
 
}





0x04
结语:
x64加壳框架外观,程序我会上传。
加密与解密第四版配套源码链接:
链接:https://pan.baidu.com/s/1hjAxUCsF6wiQl0TlKvCwvA 提取码:rfq6
clipboard1.png
clipboard.png

64位壳子.7z

135.29 KB, 下载次数: 138, 下载积分: 吾爱币 -1 CB

免费评分

参与人数 3吾爱币 +3 热心值 +2 收起 理由
cpj1203 + 1 + 1 谢谢@Thanks!
oepoep + 1 我很赞同!
Rodriguezs + 1 + 1 谢谢@Thanks!

查看全部评分

发帖前要善用论坛搜索功能,那里可能会有你要找的答案或者已经有人发布过相同内容了,请勿重复发帖。

风之暇想 发表于 2020-6-30 20:05
舒默哦 发表于 2020-6-30 10:49
我写的兼容32位和64位的哦,版主大人

兼容性有待提高
cpj1203 发表于 2020-6-28 11:12
netspirit 发表于 2020-6-27 01:36
王兰花秀丽 发表于 2020-6-27 01:40
虽然没怎么看懂,但是不妨碍我夸你厉害
拉玛西亚 发表于 2020-6-27 04:02
书我存了,谢谢分享了
Rodriguezs 发表于 2020-6-27 07:34
厉害了我的哥
yiting8 发表于 2020-6-27 11:37
大佬,书可以共享一下吗?
gh0st_ 发表于 2020-6-27 15:47
感谢分享
htpidk 发表于 2020-6-27 15:52
可以的,我也在准备写壳
 楼主| 舒默哦 发表于 2020-6-28 14:16
yiting8 发表于 2020-6-27 11:37
大佬,书可以共享一下吗?

链接:https://pan.baidu.com/s/1BG8Foq5ComqNbkFbAJ2DCQ
提取码:khqa
您需要登录后才可以回帖 登录 | 注册[Register]

本版积分规则

返回列表

RSS订阅|小黑屋|处罚记录|联系我们|吾爱破解 - LCG - LSG ( 京ICP备16042023号 | 京公网安备 11010502030087号 )

GMT+8, 2025-5-23 07:08

Powered by Discuz!

Copyright © 2001-2020, Tencent Cloud.

快速回复 返回顶部 返回列表