调用Zw函数 —> 检查参数,检查发起 *** 作的模式 --> nt函数
驱动程序源代码:
#include#include #include #include #define DEVICE_NAME L"\Device\MyFirstDevice" #define SYM_NAME L"\??\MyFirstDevice" #define IOCTL_MUL CTL_CODE(FILE_DEVICE_UNKNOWN, 0x9888, METHOD_BUFFERED, FILE_ANY_ACCESS) VOID nothing(HANDLE ppid, HANDLE mypid, BOOLEAN bcreate) { DbgPrint("ProcessNotifyn"); } VOID DrvUnload(PDRIVER_OBJECT pdriver) { DbgPrint("Unloadn"); if (pdriver->DeviceObject) { IoDeleteDevice(pdriver->DeviceObject); UNICODE_STRING symname = { 0 }; RtlInitUnicodeString(&symname, SYM_NAME); IoDeleteSymboliclink(&symname); } PsSetCreateProcessNotifyRoutine(nothing, TRUE); } NTSTATUS MyCreate(PDEVICE_OBJECT pdevice, PIRP pirp) //PDEVICE_OBJECT { NTSTATUS status = STATUS_SUCCESS; DbgPrint("My Device has be openedn"); pirp->IoStatus.Status = status; pirp->IoStatus.Information = 0; IoCompleteRequest(pirp, IO_NO_INCREMENT); return 0; } NTSTATUS MyClose(PDEVICE_OBJECT pdevice, PIRP pirp) //PDEVICE_OBJECT { NTSTATUS status = STATUS_SUCCESS; DbgPrint("My Device has be MyClosen"); pirp->IoStatus.Status = status; pirp->IoStatus.Information = 0; IoCompleteRequest(pirp, IO_NO_INCREMENT); return 0; } NTSTATUS MyCleanUp(PDEVICE_OBJECT pdevice, PIRP pirp) //PDEVICE_OBJECT { NTSTATUS status = STATUS_SUCCESS; DbgPrint("My Device has be MyCleanUpn"); pirp->IoStatus.Status = status; pirp->IoStatus.Information = 0; IoCompleteRequest(pirp, IO_NO_INCREMENT); return 0; } NTSTATUS MyRead(PDEVICE_OBJECT pdevice, PIRP pirp) { NTSTATUS status = STATUS_SUCCESS; DbgPrint("My Device has be MyReadn"); PIO_STACK_LOCATION pstack = IoGetCurrentIrpStackLocation(pirp); ULONG readsize = pstack->Parameters.Read.Length; PCHAR readbuffer = pirp->AssociatedIrp.SystemBuffer; RtlCopyMemory(readbuffer, "This Message Come From Kernel.", strlen("This Message Come From Kernel.")); pirp->IoStatus.Status = status; pirp->IoStatus.Information = strlen("This Message Come From Kernel."); DbgPrint("Really Read Info Len is %dn", strlen("This Message Come From Kernel.")); IoCompleteRequest(pirp, IO_NO_INCREMENT); return STATUS_SUCCESS; } NTSTATUS MyWrite(PDEVICE_OBJECT pdevice, PIRP pirp) { NTSTATUS status = STATUS_SUCCESS; DbgPrint("My Device has be MyWriten"); PIO_STACK_LOCATION pstack = IoGetCurrentIrpStackLocation(pirp); ULONG writesize = pstack->Parameters.Write.Length; PCHAR writebuffer = pirp->AssociatedIrp.SystemBuffer; RtlZeroMemory(pdevice->DeviceExtension, 200); RtlCopyMemory(pdevice->DeviceExtension, writebuffer, writesize); DbgPrint("--%p--%sn", writebuffer, (PCHAR)pdevice->DeviceExtension); pirp->IoStatus.Status = status; pirp->IoStatus.Information = 13; DbgPrint("Really Read Info Len is %dn", strlen("This Message Come From Kernel.")); IoCompleteRequest(pirp, IO_NO_INCREMENT); return STATUS_SUCCESS; } NTSTATUS MyControl(PDEVICE_OBJECT pdevice, PIRP pirp) { NTSTATUS status = STATUS_SUCCESS; PIO_STACK_LOCATION pstack = IoGetCurrentIrpStackLocation(pirp); ULONG iocode = pstack->Parameters.DeviceIoControl.IoControlCode; ULONG inlen = pstack->Parameters.DeviceIoControl.InputBufferLength; ULONG outlen = pstack->Parameters.DeviceIoControl.OutputBufferLength; ULONG ioinfo = 0; DbgPrint("---------Device IO---------n"); switch (iocode) { case IOCTL_MUL: { DWORD indata = *(PDWORD)pirp->AssociatedIrp.SystemBuffer; DbgPrint("--Kernel Indata %d--n", indata); indata = indata * 5; *(PDWORD)pirp->AssociatedIrp.SystemBuffer = indata; ioinfo = 888; break; } default: status = STATUS_UNSUCCESSFUL; ioinfo = 0; break; } DbgPrint("My Device has be MyCleanUpn"); pirp->IoStatus.Status = status; pirp->IoStatus.Information = 0; IoCompleteRequest(pirp, IO_NO_INCREMENT); return 0; } //5.1 KernelDeleteFile() 局限性:只可删除未被占用的程序 NTSTATUS KernelDeleteFile(PWCHAR file_path) { UNICODE_STRING filepath = { 0 }; NTSTATUS status = STATUS_SUCCESS; OBJECT_ATTRIBUTES obja = { 0 }; RtlInitUnicodeString(&filepath, file_path); InitializeObjectAttributes(&obja, &filepath, OBJ_CASE_INSENSITIVE, NULL, NULL); status = ZwDeleteFile(&obja); if (!NT_SUCCESS(status)) { DbgPrint("Delete File Failed: %xn", status); } return status; } //5.2 KernelCopyFile() NTSTATUS KernelCopyFile(PWCHAR defile_path, PWCHAR sourcefile_path) { NTSTATUS status = STATUS_SUCCESS; HANDLE hfile1 = NULL; UNICODE_STRING sourcefilepath = { 0 }; IO_STATUS_BLOCK iostack1 = { 0 }; OBJECT_ATTRIBUTES obja1 = { 0 }; RtlInitUnicodeString(&sourcefilepath, sourcefile_path); InitializeObjectAttributes(&obja1, &sourcefilepath, OBJ_CASE_INSENSITIVE | OBJ_KERNEL_HANDLE, NULL, NULL); status = ZwOpenFile(&hfile1, GENERIC_ALL, &obja1, &iostack1, FILE_SHARE_READ | FILE_SHARE_WRITE, FILE_SYNCHRONOUS_IO_NONalert); if (!NT_SUCCESS(status)) { DbgPrint("Open SourceFile Failed: %xn", status); return status; } FILE_STANDARD_INFORMATION fbi = { 0 }; status = ZwQueryInformationFile(hfile1, &iostack1, &fbi, sizeof(FILE_STANDARD_INFORMATION), FileStandardInformation); if (!NT_SUCCESS(status)) { DbgPrint("QueryInformation SourceFile Failed: %xn", status); ZwClose(hfile1); return status; } PVOID filebuffer = NULL; filebuffer = ExAllocatePool(NonPagedPool, fbi.EndOfFile.QuadPart); if (!filebuffer) { DbgPrint("AllocateBuffer Failedn"); ZwClose(hfile1); return status; } RtlZeroMemory(filebuffer, fbi.EndOfFile.QuadPart); LARGE_INTEGER readoffset = { 0 }; readoffset.QuadPart = 0; status = ZwReadFile(hfile1, NULL, NULL, NULL, &iostack1, filebuffer, fbi.EndOfFile.QuadPart, &readoffset, NULL); if (!filebuffer) { DbgPrint("ReadFile Failed :%xn", status); ZwClose(hfile1); ExFreePool(filebuffer); return status; } DbgPrint("---IoInfo---%dn", iostack1.Information); ZwClose(hfile1); //create new file HANDLE hfile2 = NULL; UNICODE_STRING defilepath = { 0 }; OBJECT_ATTRIBUTES obja2 = { 0 }; IO_STATUS_BLOCK iostack2 = { 0 }; RtlInitUnicodeString(&defilepath, defile_path); InitializeObjectAttributes(&obja2, &defilepath, OBJ_CASE_INSENSITIVE | OBJ_KERNEL_HANDLE, NULL, NULL); status = ZwCreateFile(&hfile2, GENERIC_ALL, &obja2, &iostack2, NULL, FILE_ATTRIBUTE_NORMAL, FILE_SHARE_WRITE, FILE_SUPERSEDE, FILE_SYNCHRONOUS_IO_NONalert, NULL, 0); if (!NT_SUCCESS(status)) { DbgPrint("Create File Failed : %xn", status); ExFreePool(filebuffer); return status; } LARGE_INTEGER writeoffset = { 0 }; writeoffset.QuadPart = 0; status = ZwWriteFile(hfile2, NULL, NULL, NULL, &iostack2, filebuffer, fbi.EndOfFile.QuadPart, &writeoffset, NULL); if (!NT_SUCCESS(status)) { DbgPrint("Write File Failed : %xn", status); ExFreePool(filebuffer); ZwClose(hfile2); return status; } DbgPrint("---write---%dn", iostack2.Information); ExFreePool(filebuffer); ZwClose(hfile2); return STATUS_SUCCESS; } NTSTATUS DriverEntry(PDRIVER_OBJECT driver, PUNICODE_STRING reg_path) //PDRIVER_OBJECT { NTSTATUS status = STATUS_SUCCESS; UNICODE_STRING devicename = { 0 }; //RTL_CONSTANT_STRING(DEVICE_NAME) UNICODE_STRING targeunicode = { 0 }; PDEVICE_OBJECT pdevice = NULL; driver->DriverUnload = DrvUnload; //test1 //test2 PCHAR tempbuffer = "C:\ABc\fff\dEF\123.txt"; STRING str = { 0 }; RtlInitString(&str, tempbuffer); RtlAnsiStringToUnicodeString(&devicename, &str, TRUE); DbgPrint("--%wZ--n", &devicename); targeunicode.Buffer = ExAllocatePool(NonPagedPool, 0x1000); targeunicode.MaximumLength = 0x1000; RtlCopyUnicodeString(&targeunicode, &devicename); DbgPrint("--%wZ--n", &targeunicode); RtlUpcaseUnicodeString(&devicename, &devicename, FALSE); ExFreePool(targeunicode.Buffer); RtlFreeUnicodeString(&devicename); //test3 PWCHAR tempbuffer2 = ExAllocatePool(NonPagedPool, 0x1000); RtlZeroMemory(tempbuffer2, 0x1000); RtlStringCbCopyW(tempbuffer2, 0x1000, L"\??\"); RtlStringCbCatW(tempbuffer2, 0x1000, L"C:\ABc\fff\dEF\123.txt"); UNICODE_STRING temp1 = { 0 }, temp2 = { 0 }; RtlInitUnicodeString(&temp1, tempbuffer2); RtlInitUnicodeString(&temp2, L"\??\"); if (RtlPrefixUnicodeString(&temp2, &temp1, FALSE)) { DbgPrint("OK , FINEn"); } UNICODE_STRING temp3 = { 0 }, temp4 = { 0 }; RtlInitUnicodeString(&temp3, L"D:\ABc\fcc\ddd\eee.txt"); RtlInitUnicodeString(&temp4, L"D:\ABc\fcc\DDD\eee.txt"); if (RtlEqualUnicodeString(&temp3, &temp4, TRUE)) { DbgPrint("temp3 = temp4n"); } UNICODE_STRING temp5 = { 0 }; RtlInitUnicodeString(&temp5, L"*EEE.TXT"); //EEE.TXT 一定要大写 if (FsRtlIsNameInexpression(&temp5, &temp4, TRUE, NULL)) { DbgPrint("Searchedn"); } DbgPrint("--%ws--n", &tempbuffer2); KernelDeleteFile(L"\??\C:\123.exe"); KernelCopyFile(L"\??\C:\888.exe", L"\??\C:\567.exe"); return 0; }
执行前状态:
执行后(删除123.exe,567.exe赋值到888.exe):
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)