这是一个很难在网上解释的问题,但我不知道发生了什么,我真的需要帮助,所以就这样吧!
基本上,我已经编写了一个安全软件(作为内核驱动程序),它最终将挂钩Windows XP - 32位的SSDT (系统服务描述符表)中的每个方法。每次进行系统调用时,我都会将其记录到一个文件中。
当我挂接ZwOpenFile时,我的问题就出现了,因为这是一个系统调用,我的代码也会执行这个系统调用来打开日志文件并将其写入。所以我得到了一个内核堆栈溢出错误,因为有些东西会调用ZwOpenFile,然后我会尝试记录它,然后我的记录器(它是我的驱动程序的一部分)将调用ZwOpenFile,然后调用ZwOpenFile,依此类推,直到我填满了堆栈,导致蓝屏死亡。
为了解决这个问题,我决定,每次调用记录器函数时,都会为它提供一个指向旧的、未挂钩的ZwOpenFile函数的指针,这样它就可以直接调用它,而不是通过我的挂钩函数来创建递归混乱。但是,当记录器调用作为参数提供的ZwOpenFile函数指针时,它会得到STATUS_INVALID_PARAMETER错误。如果直接调用ZwOpenFile (而不是通过指针),它就能完美地工作!但是,当指向具有相同参数的相同函数的指针被调用时,它会抛出STATUS_INVALID_PARAMETER错误代码!但是,指针必须指向正确的函数,否则不会抛出此Windows错误消息。下面是我的代码中的一小段(希望如此),让它更有意义:
*mydriver.h*
#define UNICODE
#define _UNICODE
#include <ntddk.h>
#include <ntstrsafe.h>
#define OPEN_FILE_INDEX 0x74
NTSTATUS newZwOpenFile(
PHANDLE FileHandle,
ACCESS_MASK DesiredAccess,
POBJECT_ATTRIBUTES ObjectAttributes,
PIO_STATUS_BLOCK IoStatusBlock,
ULONG ShareAccess,
ULONG OpenOptions);
typedef NTSTATUS (*ZwOpenFilePtr)(
PHANDLE FileHandle,
ACCESS_MASK DesiredAccess,
POBJECT_ATTRIBUTES ObjectAttributes,
PIO_STATUS_BLOCK IoStatusBlock,
ULONG ShareAccess,
ULONG OpenOptions);
*mydriver.c*
#include "mydriver.h"
#include "filehandling.c"
//global definition of pointer at top of mydriver.c file
ZwOpenFilePtr oldZwOpenFile;
NTSTATUS DriverEntry(PDRIVER_OBJECT pDriverObject, PUNICODE_STRING pRegistryPath){
...
...
//hooks the SSDT using the index of ZwOpenFile in the SSDT
oldZwOpenFile = (ZwOpenFilePtr)hookSSDTWithIndex(OPEN_FILE_INDEX, (BYTE*)newZwOpenFile, (DWORD*)systemCallTable);
...
...
}
//inside the method body of every hooked function, there is, at some point, the a call to the logger.
//This is shown in the context of newZwOpenFile
NTSTATUS newZwOpenFile(PHANDLE FileHandle, ACCESS_MASK DesiredAccess, POBJECT_ATTRIBUTES ObjectAttributes, PIO_STATUS_BLOCK IoStatusBlock, ULONG ShareAccess, ULONG OpenOptions){
...
driverWriteFile(&uFullString, &uProcess, *oldZwOpenFile);
...
}
*filehandling.c*
#include <ntstrsafe.h>
//the logger file
//the function doing the opening and writing
NTSTATUS driverWriteFile(PUNICODE_STRING stringToLog, PUNICODE_STRING filename, NTSTATUS (*fileOpenFunction)(PHANDLE,ACCESS_MASK,POBJECT_ATTRIBUTES,PIO_STATUS_BLOCK,ULONG,ULONG)) {
...
//the failing call that returns c000000d
ntstatus = fileOpenFunction(&handle, FILE_APPEND_DATA, &objAttr, &ioStatusBlock, FILE_SHARE_READ | FILE_SHARE_WRITE, FILE_SYNCHRONOUS_IO_NONALERT);
...
}更重要的是,所有的钩子函数都抛出了c000000d错误(使用DbgPrint),但是有一两次,它以某种方式成功了……任何帮助或建议都将不胜感激!
发布于 2017-04-29 06:41:23
一开始,您调用的不是ZwOpenFile,而是NtOpenFile。其次,当您从内核调用ZwOpenFile时,PreviousMode是内核模式,IopCreateFile不检查参数(内核对内核的信任)。当你调用NtOpenFile时,PreviousMode可以是用户模式,参数是选中的。并且您在调用NtOpenFile中使用了无效参数-您使用了FILE_SYNCHRONOUS_IO_ALERT选项,但没有在所需的访问中请求SYNCHRONIZE。所以你必须得到STATUS_INVALID_PARAMETER。
https://stackoverflow.com/questions/43502316
复制相似问题