以前自己一直在应用层编程级别上混,现在决定了,要向内核和系统底层驱动进军!主要是因为前段时间看论坛上一个朋友写的代码是讲的内枋编程方面的,不禁有情感叹,自己老是在应用层混,永远都不法达到高手的地步,现在狠下心来,决定潜心研究内核驱动编程,可能以后会把我学习中的一点一滴都记下来,为以后复习做好基础,因为我想学习内核不是一两天的事,既然下决了决心,就要把它学好了!
下面是我最近在研究的一个内核工具中的一些源代码,我有一个疑问,这些代码怎么很像是在写服务的程序,开始不知道为什么,最近在网上找到老罗的一本KMD教程,有这方面的介绍,这里也引用一下:
Windows NT使用某种机制来启动进程,并让它们不和某个具体的交互式的用户界面相关联,这些进程就被称为服务(service),服务的一个很好的例子就是Web服务器,这些Web服务都没有用户界面,服务是唯一以这种方式运行的应用程序(注:指没有用户界面,当然,严格地说病毒、木马以及所有不想见光的程序也是这样的~~),服务可以在系统启动的时候自动启动,也可以被手工启动,从这一点来看,设备驱动程序和服务是类似的 下面有一些很经典的代码,可以作为以后写驱动程序作为参考:
驱动程序模板:
驱动控制程序模板
注册驱动:
RegisterDriver proc uses esi edi ebx pszDriverName:LPSTR, pszDriverPath:LPSTR
xor ebx, ebx ; assume error
mov edi, offset g_szFail
invoke OpenSCManager, NULL, NULL, SC_MANAGER_CREATE_SERVICE
.if eax != NULL
mov esi, eax
; Register driver - fill registry directory
invoke CreateService, esi, pszDriverName, pszDriverName, \
0, SERVICE_KERNEL_DRIVER, SERVICE_DEMAND_START, SERVICE_ERROR_IGNORE, \
pszDriverPath, NULL, NULL, NULL, NULL, NULL
invoke LastError
.if eax != NULL
invoke CloseServiceHandle, eax
inc ebx ; success
mov edi, offset g_szSuccess
.endif
invoke CloseServiceHandle, esi
.else
invoke MessageBox, NULL, addr g_szOpenSCManagerError, addr g_szCriticalError, MB_OK + MB_ICONSTOP
.endif
return ebx
RegisterDriver endp 卸载驱动:
UnregisterDriver proc uses esi edi ebx pszDriverName:LPSTR
xor ebx, ebx ; assume error
mov edi, offset g_szFail
invoke OpenSCManager, NULL, NULL, SC_MANAGER_CONNECT
.if eax != NULL
mov esi, eax
; Unregister driver - remove registry directory
invoke OpenService, esi, pszDriverName, DELETE
invoke LastError
.if eax != NULL
push eax
invoke DeleteService, eax
invoke LastError
.if eax != 0
inc ebx ; success
mov edi, offset g_szSuccess
.endif
call CloseServiceHandle
.endif
invoke CloseServiceHandle, esi
.else
invoke MessageBox, NULL, addr g_szOpenSCManagerError, addr g_szCriticalError, MB_OK + MB_ICONSTOP
.endif
return ebx
UnregisterDriver endp 运行驱动:
RunDriver proc uses esi edi ebx pszDriverName:LPSTR
xor ebx, ebx ; assume error
mov edi, offset g_szFail
invoke OpenSCManager, NULL, NULL, SC_MANAGER_CONNECT
.if eax != NULL
mov esi, eax
; Unregister driver - remove registry directory
invoke OpenService, esi, pszDriverName, SERVICE_START
invoke LastError
.if eax != NULL
push eax
invoke StartService, eax, 0, NULL
invoke LastError
.if eax != 0
inc ebx ; success
mov edi, offset g_szSuccess
.endif
call CloseServiceHandle
mov edi, offset g_szSuccess
.endif
invoke CloseServiceHandle, esi
.else
invoke MessageBox, NULL, addr g_szOpenSCManagerError, addr g_szCriticalError, MB_OK + MB_ICONSTOP
.endif
return ebx
RunDriver endp
停止驱动:
StopDriver proc uses esi ebx pszDriverName:LPSTR
LOCAL sest:SERVICE_STATUS
xor ebx, ebx ; assume error
mov edi, offset g_szFail
invoke OpenSCManager, NULL, NULL, SC_MANAGER_CONNECT
.if eax != NULL
mov esi, eax
; Unregister driver - remove registry directory
invoke OpenService, esi, pszDriverName, SERVICE_STOP
invoke LastError
.if eax != NULL
push eax
mov ecx, eax
invoke ControlService, ecx, SERVICE_CONTROL_STOP, addr sest
invoke LastError
.if eax != 0
inc ebx ; success
mov edi, offset g_szSuccess
.endif
call CloseServiceHandle
.endif
invoke CloseServiceHandle, esi
.else
invoke MessageBox, NULL, addr g_szOpenSCManagerError, addr g_szCriticalError, MB_OK + MB_ICONSTOP
.endif
return ebx
StopDriver endp
控制驱动:
ControlDriver proc uses esi edi ebx pszDriverName:LPSTR, dwCode:DWORD
LOCAL acBuffer[MAX_PATH]:CHAR
LOCAL dwBytesReturned:DWORD
xor ebx, ebx ; assume error
mov edi, offset g_szFail
invoke GetVersion
.if al >= 5
mov eax, $CTA0("\\\\.\\Global\\%s")
.else
mov eax, $CTA0("\\\\.\\%s")
.endif
invoke wsprintf, addr acBuffer, eax, pszDriverName
invoke CreateFile, addr acBuffer, GENERIC_READ + GENERIC_WRITE, 0, \
NULL, OPEN_EXISTING, 0, NULL
invoke LastError
.if eax != INVALID_HANDLE_VALUE
mov esi, eax
invoke DeviceIoControl, esi, dwCode, NULL, 0, NULL, 0, addr dwBytesReturned, NULL
invoke LastError
.if eax != 0
inc ebx ; success
mov edi, offset g_szSuccess
.endif
invoke CloseHandle, esi
.else
invoke MessageBox, NULL, $CTA0("Can't get Driver handle."), addr g_szCriticalError, MB_OK + MB_ICONSTOP
.endif
return ebx
ControlDriver endp
上面几个函数都很好理解,我只想给大家介绍一下最后一个函数是做什么?
当我们启动驱动之后,我们要用这个函数去控制它,首先我们使用CreateFile函数打开驱动,以获得一个文件句柄,当CreateFile函数成功地创建或者打开指定的设备,那么返回值就是设备句柄,否则返回值是INVALID_HANDLE_VALUE。
invoke CreateFile, addr acBuffer, GENERIC_READ + GENERIC_WRITE, 0, \
NULL, OPEN_EXISTING, 0, NULL
如果上面返回有效的设备句柄,现在就可以像写应用程序那个调用ReadFile,WriteFile,以及DeviceIoControl函数来和设备通讯。
invoke DeviceIoControl, esi, dwCode, NULL, 0, NULL, 0, addr dwBytesReturned, NULL
这样一个驱动的控制程序也就完了,也不是很难,这让我想起了一句话:这个社会上没有学不会的知识,只是看你肯不肯花时间去学!
好了,今天就先不学习到这里,至少知道了几个驱动控制函数,呵呵~~每天进步一点点~~相信以后我也可以很自信的去研究内核安全编程!!!加油
[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课