RPC(Remote Procedure Call Protocol)——远程过程调用协议,它是一种通过网络从远程计算机程序上请求服务,而不需要了解底层网络技术的协议。RPC协议假定某些传输协议的存在,如TCP或UDP,为通信程序之间携带信息数据。在OSI网络通信模型中,RPC跨越了传输层和应用层。RPC使得开发包括网络分布式多程序在内的应用程序更加容易。
只有样本没有源码,应该是挂接\RPC Control\DNDResolver接管系统所有DNS解析的消息 然后修改的 禁止DNSCache是禁止DNS缓存,让所有解析都到他那里去 已经搞定了,只要\RPC Control\DNDResolver这个对象,关闭所有打开的句柄就行了
void __cdecl wmain()
{
HANDLE v0; // edi@3
int Dst; // [sp+8h] [bp-80h]@1
int v2; // [sp+Ch] [bp-7Ch]@1
int v3; // [sp+10h] [bp-78h]@2
int v4; // [sp+88h] [bp+0h]@1
unsigned int v5; // [sp+124h] [bp+9Ch]@1
v5 = (unsigned int)&v4 ^ __security_cookie;
memset(&Dst, 0, 0x11Cu);
Dst = 284;
GetVersionExW((LPOSVERSIONINFOW)&Dst);
if ( v2 == 5 )
{
if ( v3 == 1 )
{
dword_40A540 = (int)CreateEventW(0, 0, 0, 0);
hEvent = CreateEventW(0, 0, 1, 0);
dword_40A544 = (int)CreateEventW(0, 0, 0, 0);
v0 = CreateThread(0, 0, (LPTHREAD_START_ROUTINE)sub_401965, 0, 0, 0);// 开始劫持
sub_40168A();
WaitForSingleObject(v0, 0xFFFFFFFFu);
RpcMgmtStopServerListening(0);
RpcServerUnregisterIf(0, 0, 0);
}
}
ExitProcess(0);
}int __cdecl sub_401965()
{
DWORD i; // eax@1
signed int v1; // esi@6
signed int v2; // ecx@17
int v3; // edx@17
unsigned int v4; // ebx@17
int v5; // eax@18
int v6; // eax@19
unsigned int v7; // esi@22
int v8; // eax@22
const wchar_t *v10; // [sp+0h] [bp-38h]@4
HANDLE Handles; // [sp+1Ch] [bp-1Ch]@1
HANDLE v12; // [sp+20h] [bp-18h]@1
int v13; // [sp+24h] [bp-14h]@1
int v14; // [sp+34h] [bp-4h]@6
Handles = (HANDLE)dword_40A544;
v12 = hEvent;
v13 = dword_40A540;
for ( i = WaitForMultipleObjects(3u, &Handles, 0, 0x1388u); i; i = WaitForMultipleObjects(3u, &Handles, 0, 0x1388u) )
{
if ( i == 1 )
{
wprintf(L"start DNSRedir...\n");
wprintf(L">Download ip-name pair...\n");
if ( sub_4034C3((int)&dword_40A558) ) // 网络读取需要劫持的域名
v10 = L">Download ip-name pair successfully.\n";
else
v10 = L">Download ip-name pair failed.\n";
wprintf(v10);
v14 = 0;
sub_4044C3(); // 应该是禁止Dnscache服务
wprintf(L">try to start dns redirector...\n");
Sleep(0xBB8u);
v1 = 0;
do
{
if ( hObject )
CloseHandle(hObject);
hObject = CreateThread(0, 0, (LPTHREAD_START_ROUTINE)StartAddress, &off_40A06C, 0, 0);// 注册RPC并监听
if ( dword_40A074 )
CloseHandle(dword_40A074);
dword_40A074 = CreateEventW(0, 1, 0, 0);
WaitForSingleObject(dword_40A074, 0xBB8u);
WaitForSingleObject(dword_40A074, 0x7D0u);
++v1;
wprintf(L">try start dns redirector %d time.\n", v1);
}
while ( dword_40A07C == 1740 && v1 < 50 );
if ( dword_40A07C )
{
wprintf(L">DNSRedir start failed, error code: %d!\n", dword_40A07C);
}
else
{
wprintf(L">DNSRedir start successfully!\n");
sub_401201();
}
v14 = -1;
}
else
{
Sleep(0x1D4C0u);
wprintf(L">update ip-name pair...\n");
sub_4034C3((int)&dword_40A558);
v2 = 28;
v3 = (dword_40A598 - dword_40A594) % 28;
v4 = 0;
if ( (dword_40A598 - dword_40A594) / 28 )
{
do
{
v5 = sub_401C88(v4);
if ( *(_DWORD *)(v5 + 24) < 0x10u )
v6 = v5 + 4;
else
v6 = *(_DWORD *)(v5 + 4);
printf(">name %d: %s\n", v4, v6);
v2 = 28;
v3 = (dword_40A598 - dword_40A594) % 28;
++v4;
}
while ( v4 < (dword_40A598 - dword_40A594) / 28 );
}
v7 = 0;
v8 = (dword_40A580 - dword_40A57C) >> 2;
if ( v8 )
{
if ( (unsigned int)v8 <= 0 )
invalid_parameter_noinfo(v2, v3);
do
{
wprintf(
L">ip %d: %d.%d.%d.%d\n",
v7,
(unsigned __int8)*(_DWORD *)(dword_40A57C + 4 * v7),
(unsigned __int16)*(_DWORD *)(dword_40A57C + 4 * v7) >> 8,
(*(_DWORD *)(dword_40A57C + 4 * v7) >> 16) & 0xFF,
*(_DWORD *)(dword_40A57C + 4 * v7) >> 24);
++v7;
}
while ( v7 < (dword_40A580 - dword_40A57C) >> 2 );
}
}
}
return 0;
}只有样本没有源码,应该是挂接\RPC Control\DNDResolver接管系统所有DNS解析的消息 然后修改的 禁止DNSCache是禁止DNS缓存,让所有解析都到他那里去 已经搞定了,只要\RPC Control\DNDResolver这个对象,关闭所有打开的句柄就行了
NTSTATUS status;
UNICODE_STRING ustrDns;
PFILE_OBJECT fileObj;
PVOID pLpcObject;
PLPCP_PORT_OBJECT pLpcObj = NULL;
RtlInitUnicodeString(&ustrDns, L"\\RPC Control\\DNSResolver");
UNICODE_STRING ustrLPC;
RtlInitUnicodeString(&ustrLPC, L"LpcPortObjectType");
PVOID pLpcPortObjectType = MmGetSystemRoutineAddress(&ustrLPC);
if ( pLpcPortObjectType != NULL )
{
status = ObReferenceObjectByName(&ustrDns,
OBJ_CASE_INSENSITIVE,
NULL,
FILE_ALL_ACCESS,
(POBJECT_TYPE)pLpcPortObjectType,
KernelMode,
NULL,
&pLpcObject);
pLpcObj = (PLPCP_PORT_OBJECT)pLpcObject;
if ( MmIsAddressValid(pLpcObj) )
{
//获取宿主进程ID
HANDLE hProcId = PsGetProcessId(pLpcObj->ServerProcess);
//获取进程句柄
HANDLE hProcess = NULL;
status = ObOpenObjectByPointer((PVOID)pLpcObj->ServerProcess,
0,
NULL,
PROCESS_ALL_ACCESS,
*PsProcessType,
KernelMode,
&hProcess);
//枚举系统所有句柄
ULONG uRetLength = 0;
PVOID pBuffer = kmalloc(0x100);
PSYSTEM_HANDLE_INFORMATION pHandleInfo = NULL;
ULONG HandleCount = 0;
status = ZwQuerySystemInformation(SystemHandleInformation, pBuffer, 0x100, &uRetLength);
if ( !NT_SUCCESS(status) )
{
kfree(pBuffer);
pBuffer = kmalloc(uRetLength);
if ( pBuffer )
{
RtlZeroMemory(pBuffer, uRetLength);
status = ZwQuerySystemInformation(SystemHandleInformation, pBuffer, uRetLength, &uRetLength);
if ( NT_SUCCESS(status) )
{
//句柄数量
HandleCount = *((ULONG *)pBuffer);
pHandleInfo = (PSYSTEM_HANDLE_INFORMATION)((ULONG)pBuffer + sizeof(ULONG));
}
}
}
POBJECT_TYPE_INFORMATION ObjTypeInfo = (POBJECT_TYPE_INFORMATION)kmalloc(MAX_PATH * 10);
PVOID ObjName = (PVOID)kmalloc(MAX_PATH * 10);
if ( ObjTypeInfo && ObjName )
{
RtlZeroMemory(ObjTypeInfo, MAX_PATH * 10);
RtlZeroMemory(ObjName, MAX_PATH * 10);
}
if ( HandleCount >0 && pHandleInfo != NULL )
{
ULONG i;
for ( i = 0; i < HandleCount; i ++ )
{
if ( pHandleInfo[i].ProcessId == (ULONG)hProcId )
{
HANDLE hObject;
status = ZwDuplicateObject(hProcess,
(HANDLE)pHandleInfo[i].Handle,
NtCurrentProcess(),
&hObject,
0,
0,
DUPLICATE_SAME_ACCESS);
if (!NT_SUCCESS(status))
continue;
//Query the object type
status = ZwQueryObject(hObject,
ObjectTypeInformation,
ObjTypeInfo,
MAX_PATH * 10,
&uRetLength);
if (!NT_SUCCESS(status))
{
ZwClose(hObject);
continue;
}
status = ZwQueryObject(hObject,
(OBJECT_INFORMATION_CLASS)1,
ObjName,
MAX_PATH * 10,
&uRetLength);
if (!NT_SUCCESS(status))
{
ZwClose(hObject);
continue;
}
UNICODE_STRING ustrType;
UNICODE_STRING win7_ALPC_PORT;
RtlInitUnicodeString(&ustrType, L"Port");
RtlInitUnicodeString(&win7_ALPC_PORT, L"ALPC Port");
if ( 0 == RtlCompareUnicodeString(&ustrType, &ObjTypeInfo->Name, TRUE) ||
0 == RtlCompareUnicodeString(&win7_ALPC_PORT, &ObjTypeInfo->Name, TRUE) )
{
if ( 0 == RtlCompareUnicodeString(&ustrDns,(PUNICODE_STRING)ObjName, TRUE) )
{
KAPC_STATE k_apc;
KeStackAttachProcess(pLpcObj->ServerProcess, &k_apc);
ZwClose((HANDLE)pHandleInfo[i].Handle);//草泥马
KeUnstackDetachProcess(&k_apc);
ZwClose(hObject);//必须关闭自己复制来的句柄 不然无法上网了
ZwTerminateProcess(hProcess, 0);
}
}
}
}
}
if ( pBuffer )
{
kfree(pBuffer);
pBuffer = NULL;
}
if ( ObjTypeInfo )
{
kfree(ObjTypeInfo);
ObjTypeInfo = NULL;
}
if ( ObjName )
{
kfree(ObjName);
ObjName = NULL;
}
if ( hProcess )
{
ZwClose(hProcess);
}
}
}
if ( pLpcObject )
{
ObDereferenceObject(pLpcObject);
}
if ( MmIsAddressValid(pLpcObj) )
{
ObDereferenceObject(pLpcObj->ServerProcess);
} 收藏的用户(0) X
正在加载信息~
推荐阅读
最新回复 (0)
站点信息
- 文章2314
- 用户1336
- 访客11813325
每日一句
Let's seek joy in the simple, quiet moments.
让我们在简单宁静的时刻中寻找快乐。
让我们在简单宁静的时刻中寻找快乐。