本文为看雪论坛优秀文章
看雪论坛作者ID:一夜酒狂
如果你完全明白 nCanMapSize 的大小是怎么来的,那么你可以跳过。
根据图片可以 ntdll.dll的代码段的最大只能是 0x0117000。
那么 nCanMapSize = 0x0117000,可以吗?答案是肯定不行的。
坑了我很长时间,其实他的是意思就是:当你BaseAddress指定了值,那么他必须是0x10000的倍数而不是0x1000(其实我也不知道为什么),因此nCanMapSize必须是 0x120000(当你出现了程序崩溃失败的时候,异常的时候,一般都是这个值的问题),自此我们完成了 关键的步骤。顺带看一下某pubg他是怎么重新映射ntdll的。

需要注意一点:当你映射ntdll的时候,这个时候你已经卸载他 ZwMapViewOfSection已经不存在,你需要做点额外工作,自己去中断进内核。


如果喜欢,请给我一键三连。
方便你们C+V测试
{
PIMAGE_NT_HEADERS pNtHeaders = NULL;
PIMAGE_DOS_HEADER pDosHdr = (PIMAGE_DOS_HEADER)pInfo->lpBaseOfDll;
pNtHeaders = (PIMAGE_NT_HEADERS64)((PUCHAR)pInfo->lpBaseOfDll + pDosHdr->e_lfanew);
sectionData dwSection;
DWORD nSize = 0;
PIMAGE_SECTION_HEADER pFirstSection = (PIMAGE_SECTION_HEADER)(pNtHeaders + 1);
if (IMAGE32(pNtHeaders))
pFirstSection = (PIMAGE_SECTION_HEADER)((PIMAGE_NT_HEADERS32)pNtHeaders + 1);
for (PIMAGE_SECTION_HEADER pSection = pFirstSection;
pSection < pFirstSection + pNtHeaders->FileHeader.NumberOfSections;
pSection++)
{
if (IMAGE_SCN_MEM_EXECUTE & pSection->Characteristics)
{
nSize += pSection->Misc.VirtualSize;
}
else
{
dwSection.VirtualAddress = pSection->VirtualAddress;
dwSection.VirtualSize = pSection->Misc.VirtualSize;
dwSection.nProtection = BBCastSectionProtection(pSection->Characteristics, FALSE);
pSectionData.emplace_back(dwSection);
}
}
if (nSize > 0x10000)
{
nSize = nSize & (~0xffff);
nSize += 0x10000;
if ((pSectionData.at(0).VirtualAddress+pSectionData.at(0).VirtualSize) >= nSize)
{
pSectionData.at(0).VirtualAddress = nSize;
pSectionData.at(0).VirtualSize = pSectionData.at(1).VirtualAddress - pSectionData.at(0).VirtualAddress ;
}
else
{
pSectionData.~vector();
}
}
else
{
nSize = 0;
}
return nSize;
{
BOOL bRet = FALSE;
if (!pInfo) return bRet;
HANDLE hSection = 0;
LARGE_INTEGER cbSectionOffset = {};
PVOID pViewBase = NULL;
SIZE_T cbViewSize = 0;
NTSTATUS ntstatus = 0;
dwSectionData;
ULONG nCanMapSize = 0;
nCanMapSize = calcTextSize(pInfo,dwSectionData);
if (nCanMapSize < 0x10000) {
return bRet;
}
ULONG64 nNextMapAddress = nCanMapSize + (ULONG64)pInfo->lpBaseOfDll;
ULONG nNextMapSize = pInfo->SizeOfImage - nCanMapSize;
LARGE_INTEGER cbSectionSize = { 0 };
pInfo->SizeOfImage; =
ntstatus = ZwCreateSection(
&hSection,
SECTION_ALL_ACCESS,
NULL,
&cbSectionSize,
PAGE_EXECUTE_READWRITE,
SEC_COMMIT,
NULL);
pViewBase = 0;
0; =
cbViewSize = 0;
ntstatus = ZwMapViewOfSection(
hSection,
NtCurrentProcess(),
&pViewBase,
0,
0,
&cbSectionOffset,
&cbViewSize,
ViewUnmap,
0,
PAGE_EXECUTE_READWRITE);
if (NT_SUCCESS(ntstatus))
{
pInfo->lpBaseOfDll, pInfo->SizeOfImage);
地址 卸载
ntstatus = ZwUnmapViewOfSection(NtCurrentProcess(), pViewBase);
ntstatus = ZwUnmapViewOfSection(NtCurrentProcess(), pInfo->lpBaseOfDll);
if (NT_SUCCESS(ntstatus))
{
代码节区 全给他 PAGE_EXECUTE_READ并且加上 SEC_NO_CHANGE
pViewBase = pInfo->lpBaseOfDll;
0; =
cbViewSize = nCanMapSize;
ntstatus = ZwMapViewOfSection(
hSection,
NtCurrentProcess(),
&pViewBase,
0,
0,
&cbSectionOffset,
&cbViewSize,
ViewUnmap,
SEC_NO_CHANGE,
PAGE_EXECUTE_READ);
if (NT_SUCCESS(ntstatus))
{
给PAGE_READWRITE
pViewBase = (PVOID)nNextMapAddress;
nCanMapSize; =
cbViewSize = nNextMapSize;
ntstatus = ZwMapViewOfSection(
hSection,
NtCurrentProcess(),
&pViewBase,
0,
0,
&cbSectionOffset,
&cbViewSize,
ViewUnmap,
0,
PAGE_READWRITE);
if (NT_SUCCESS(ntstatus) && !dwSectionData.empty())
{
还原数据段 的内存属性 你不喜欢可以不执行
:iterator it = dwSectionData.begin(); :
SIZE_T tmpSize = 0;
DWORD OldAccessProtection = 0;
ULONG prot = 0;
PVOID pAddr = NULL;
for (it; it != dwSectionData.end(); ++it)
{
if (it->nProtection == PAGE_READONLY)
{
prot = it->nProtection;
pAddr = (PVOID)((ULONG64)pInfo->lpBaseOfDll + it->VirtualAddress);
tmpSize = it->VirtualSize;
&pAddr, &tmpSize, prot, &OldAccessProtection);
}
}
}
}
}
}
if (hSection) {
CloseHandle(hSection);
}
return bRet;
{
ULONG dwResult = PAGE_NOACCESS;
if (characteristics & IMAGE_SCN_MEM_DISCARDABLE)
{
dwResult = PAGE_NOACCESS;
}
else if (characteristics & IMAGE_SCN_MEM_EXECUTE)
{
if (characteristics & IMAGE_SCN_MEM_WRITE)
dwResult = noDEP ? PAGE_READWRITE : PAGE_EXECUTE_READWRITE;
else if (characteristics & IMAGE_SCN_MEM_READ)
dwResult = noDEP ? PAGE_READONLY : PAGE_EXECUTE_READ;
else
dwResult = noDEP ? PAGE_READONLY : PAGE_EXECUTE;
}
else
{
if (characteristics & IMAGE_SCN_MEM_WRITE)
dwResult = PAGE_READWRITE;
else if (characteristics & IMAGE_SCN_MEM_READ)
dwResult = PAGE_READONLY;
else
dwResult = PAGE_NOACCESS;
}
return dwResult;
看雪ID:一夜酒狂
https://bbs.pediy.com/user-home-877765.htm
2.5折门票限时抢购
峰会官网:https://meet.kanxue.com/kxmeet-6.htm
# 往期推荐
球分享
球点赞
球在看
点击“阅读原文”,了解更多!
原文始发于微信公众号(看雪学苑):如何保护自己的代码?给自己的代码添加NoChange属性
免责声明:文章中涉及的程序(方法)可能带有攻击性,仅供安全研究与教学之用,读者将其信息做其他用途,由读者承担全部法律及连带责任,本站不承担任何法律及连带责任;如有问题可邮件联系(建议使用企业邮箱或有效邮箱,避免邮件被拦截,联系方式见首页),望知悉。
- 左青龙
- 微信扫一扫
-
- 右白虎
- 微信扫一扫
-
评论