⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 wdmstub.cpp

📁 Programming the Microsoft Windows driver model.2nd 随书光盘。内有很多作者送的实用工具和随书源码。WDM编程
💻 CPP
📖 第 1 页 / 共 2 页
字号:
	#undef Get_VMM_Version

	USHORT version;

	ULONG dbgver;

	VMMCall(Get_VMM_Version);

	_asm mov version, ax

	_asm mov dbgver, ecx



	if (MajorVersion)

		*MajorVersion = version >> 8;

	if (MinorVersion)

		*MinorVersion = version & 255;

	if (BuildNumber)

		*BuildNumber = buildnum;

	if (spnum)

		spnum->Length = 0;



	return dbgver != 0;

	}							// PsGetVersion



NTSTATUS IoAcquireRemoveLockEx(PIO_REMOVE_LOCK p, PVOID tag, PCSTR file, ULONG line, ULONG size)

	{							// IoAcquireRemoveLockEx

	ASSERT(KeGetCurrentIrql() <= DISPATCH_LEVEL);

	return AcquireRemoveLock(p, tag, file, line, size);

	}							// IoAcquireRemoveLockEx



VOID IoReleaseRemoveLockEx(PIO_REMOVE_LOCK p, PVOID tag, ULONG size)

	{							// IoReleaseRemoveLockEx

	ASSERT(KeGetCurrentIrql() <= DISPATCH_LEVEL);

	ReleaseRemoveLock(p, tag, size);

	}							// IoReleaseRemoveLockEx



VOID IoReleaseRemoveLockAndWaitEx(PIO_REMOVE_LOCK p, PVOID tag, ULONG size)

	{							// IoReleaseRemoveLockAndWaitEx

	ASSERT(KeGetCurrentIrql() == PASSIVE_LEVEL);

	ReleaseRemoveLockAndWait(p, tag, size);

	}							// IoReleaseRemoveLockAndWaitEx



VOID IoInitializeRemoveLockEx(PIO_REMOVE_LOCK p, ULONG tag, ULONG maxminutes, ULONG hwm, ULONG size)

	{							// IoInitializeRemoveLockEx

	ASSERT(KeGetCurrentIrql() == PASSIVE_LEVEL);

	InitializeRemoveLock(p, tag, maxminutes, hwm, size);

	}							// IoInitializeRemoveLockEx



#pragma warning(disable:4035)



USHORT FASTCALL RtlUshortByteSwap(USHORT source)

	{							// RtlUshortByteSwap

	_asm movzx eax, cx

	_asm xchg ah, al

	}							// RtlUshortByteSwap



ULONG FASTCALL RtlUlongByteSwap(ULONG source)

	{							// RtlUlongByteSwap

	_asm mov eax, ecx

	_asm bswap eax

	}							// RtlUlongByteSwap



ULONGLONG FASTCALL RtlUlonglongByteSwap(ULONGLONG source)

	{							// RtlUlonglongByteSwap

	_asm mov eax, ecx

	_asm xchg eax, edx

	_asm bswap eax

	_asm bswap edx

	}							// RtlUlonglongByteSwap



#pragma warning(default:4035)



NTSTATUS RtlInt64ToUnicodeString(ULONGLONG value, ULONG base, PUNICODE_STRING string)

	{							// RtlInt64ToUnicodeString

	return STATUS_NOT_IMPLEMENTED;

	}							// RtlInt64ToUnicodeString



VOID KeEnterCriticalRegion()

	{							// KeEnterCriticalRegion

	ASSERT(KeGetCurrentIrql() == PASSIVE_LEVEL);

	}							// KeEnterCriticalRegion



VOID KeLeaveCriticalRegion()

	{							// KeLeaveCriticalRegion

	ASSERT(KeGetCurrentIrql() == PASSIVE_LEVEL);

	}							// KeLeaveCriticalRegion



VOID KeSetTargetProcessorDpc(PRKDPC dpc, CCHAR number)

	{							// KeSetTargetProcessorDpc

	}							// KeSetTargetProcessorDpc



VOID KeSetImportanceDpc(PRKDPC dpc, KDPC_IMPORTANCE importance)

	{							// KeSetImportanceDpc

	}							// KeSetImportanceDpc



VOID IoReuseIrp(PIRP Irp, NTSTATUS status)

	{							// IoReuseIrp

	ReuseIrp(Irp, status);

	}							// IoReuseIrp



void __cdecl MessageCallback(char* msg);



BOOLEAN IoRaiseInformationalHardError(NTSTATUS status, PUNICODE_STRING string, PKTHREAD thread)

	{							// IoRaiseInformationalHardError

	char* msg = (char*) _HeapAllocate(1024, 0);

	if (!msg)

		return FALSE;

	if (string)

		{						// convert string data

		UINT unilen = string->Length;

		UINT ansilen = unilen / 2;

		char* ansistring = (char*) _HeapAllocate(ansilen + 1, 0);

		if (!ansistring)

			{

			_HeapFree(msg, 0);

			return FALSE;

			}



		#define BCS_OEM 1

		ansistring[UniToBCS((PBYTE) ansistring, string->Buffer, unilen, ansilen, BCS_OEM)] = 0;

		_Sprintf(msg, "An operation failed with status %8.8lX. The operation relates to '%s'", status, ansistring);

		_HeapFree(ansistring, 0);

		}						// convert string data

	else

		_Sprintf(msg, "An operation failed with status %8.8lX", status);



	BOOL okay;

	okay = _SHELL_CallAtAppyTime((APPY_CALLBACK) MessageCallback, (DWORD) msg, 0) != 0;

	if (!okay)

		{						// can't queue regular message box

		SHELL_SYSMODAL_Message(Get_Sys_VM_Handle(), MB_OK | MB_ICONHAND | MB_SYSTEMMODAL, msg, "Windows - Operation Failed");

		_HeapFree(msg, 0);

		okay = TRUE;

		}						// can't queue regular message box



	return (BOOLEAN) okay;

	}							// IoRaiseInformationalHardError



BOOLEAN HalTranslateBusAddress(INTERFACE_TYPE InterfaceType, ULONG BusNumber, PHYSICAL_ADDRESS BusAddress,

	PULONG AddressSpace, PPHYSICAL_ADDRESS TranslatedAddress)

	{							// HalTranslateBusAddress

	ASSERT(KeGetCurrentIrql() <= DISPATCH_LEVEL);

	*TranslatedAddress = BusAddress;

	return TRUE;

	}							// HalTranslateBusAddress



BOOLEAN ExIsProcessorFeaturePresent(ULONG feature)

	{							// ExIsProcessorFeaturePresent

	BOOLEAN result = FALSE;



	switch (feature)

		{						// determine if feature present

	case PF_FLOATING_POINT_PRECISION_ERRATA:

		result = PrecisionErrata;

		break;



	case PF_FLOATING_POINT_EMULATED:

		result = (features & FEATURE_FPU) == 0;

		break;



	case PF_COMPARE_EXCHANGE_DOUBLE:

		result = (features & FEATURE_CMPXCHG8B) != 0;

		break;



	case PF_MMX_INSTRUCTIONS_AVAILABLE:

		result = (features & FEATURE_MMX) != 0;



	case PF_PPC_MOVEMEM_64BIT_OK:

	case PF_ALPHA_BYTE_INSTRUCTIONS:

		break;					// non-x86 features



	case PF_XMMI_INSTRUCTIONS_AVAILABLE:

		result = (features & FEATURE_XMMI) != 0;

		break;



	case PF_3DNOW_INSTRUCTIONS_AVAILABLE:

		break;					// assume false until somebody needs it to work...



	case PF_RDTSC_INSTRUCTION_AVAILABLE:

		result = (features & FEATURE_RDTSC) != 0;

		break;



	case PF_PAE_ENABLED:

		break;					// Win98 doesn't run on phys addr extension machines

		}						// determine if feature present



	return result;

	}							// ExIsProcessorFeaturePresent



PVOID MmGetSystemRoutineAddress(PUNICODE_STRING name)

	{							// MmGetSystemRoutineAddress

	char ansiname[256];

	ansiname[UniToBCS((PBYTE) ansiname, name->Buffer, name->Length, 255, BCS_WANSI)] = 0;

	return _PELDR_GetProcAddress((HPEMODULE) ntoskrnl, ansiname, NULL);

	}							// MmGetSystemRoutineAddress



NTSTATUS ZwQueryInformationFile(HANDLE h, PIO_STATUS_BLOCK pstatus, PVOID fi,

	ULONG length, FILE_INFORMATION_CLASS c)

	{							// ZwQueryInformationFile

	pstatus->Status = STATUS_NOT_IMPLEMENTED;

	return STATUS_NOT_IMPLEMENTED;

	}							// ZwQueryInformationFile



NTSTATUS ZwSetInformationFile(HANDLE h, PIO_STATUS_BLOCK pstatus, PVOID fi,

	ULONG length, FILE_INFORMATION_CLASS c)		

	{							// ZwSetInformationFile

	pstatus->Status = STATUS_NOT_IMPLEMENTED;

	return STATUS_NOT_IMPLEMENTED;

	}							// ZwSetInformationFile



NTSTATUS ZwQueryDefaultLocale(BOOLEAN thread, LCID* plocale)

	{							// ZwQueryDefaultLocale

	*plocale = locale;

	return STATUS_SUCCESS;

	}							// ZwQueryDefaultLocale



VOID ExFreePoolWithTag(PVOID p, ULONG tag)

	{							// ExFreePoolWithTag

	ExFreePool(p);

	}							// ExFreePoolWithTag



NTSTATUS ZwLoadDriver(PUNICODE_STRING ServiceKey)

	{							// ZwLoadDriver

	return _NtKernLoadDriver(ServiceKey);

	}							// ZwLoadDriver



NTSTATUS ZwUnloadDriver(PUNICODE_STRING ServiceKey)

	{							// ZwUnloadDriver



	// Isolate the service name from the end of the key.

	// This will be the name of the driver object



	for (int i = ServiceKey->Length / sizeof(WCHAR) - 1; i >= 0; --i)

		if (ServiceKey->Buffer[i] == L'\\')

			break;

	++i;						// skip backslash

	int lname = ServiceKey->Length / sizeof(WCHAR) - i;



	WCHAR objname[128];

	wcscpy(objname, L"\\Driver\\");

	memcpy(objname + 8, ServiceKey->Buffer + i, 2 * lname);

	objname[lname + 8] = 0;

	UNICODE_STRING oname;

	RtlInitUnicodeString(&oname, objname);



	// Find the driver object



	PDRIVER_OBJECT DriverObject;

	NTSTATUS status = ObReferenceObjectByName(&oname, 0, 0, 0, *IoDriverObjectType, KernelMode, 0, (PVOID*) &DriverObject);

	if (!NT_SUCCESS(status))

		{

		KdPrint((DRIVERNAME " - Can't locate driver object %ws - %X\n", objname, status));

		return status;

		}

	ObDereferenceObject(DriverObject);	// remove reference from ObReferenceObjectByName



	// Determine the module name by reading the registry key, backscanning

	// to the last backslash, and converting to ANSI



	OBJECT_ATTRIBUTES oa;

	InitializeObjectAttributes(&oa, ServiceKey, OBJ_KERNEL_HANDLE, NULL, NULL);



	HANDLE hkey;

	status = ZwOpenKey(&hkey, KEY_READ, &oa);

	if (!NT_SUCCESS(status))

		{

		KdPrint((DRIVERNAME " - ZwOpenKey(%ws) failed - %X\n", ServiceKey->Buffer, status));

		return status;

		}



	struct foo : public _KEY_VALUE_PARTIAL_INFORMATION

		{

		UCHAR buffer[511];

		} value;

	UNICODE_STRING valname;

	ULONG size;

	RtlInitUnicodeString(&valname, L"ImagePath");

	status = ZwQueryValueKey(hkey, &valname, KeyValuePartialInformation,

		&value, sizeof(value), &size);

	ZwClose(hkey);



	if (!NT_SUCCESS(status))

		{

		KdPrint((DRIVERNAME " - ZwQueryValueKey failed - %X\n", status));

		return status;

		}



	for (i = value.DataLength / sizeof(WCHAR) - 1; i >= 0; --i)

		if (((PWCHAR) (value.Data))[i] == L'\\')

			break;

	++i;

	lname = value.DataLength / sizeof(WCHAR) - i;

	memcpy(objname, value.Data + i * 2, lname * 2);

	objname[lname] = 0;



	BYTE modname[64];

	modname[UniToBCS(modname, objname, lname * 2, sizeof(modname), BCS_WANSI)] = 0;

	HPEMODULE hmod = _PELDR_GetModuleHandle((PSTR) modname);



	if (!hmod)

		{

		KdPrint((DRIVERNAME " - Can't get module handle to %s\n", modname));

		return STATUS_UNSUCCESSFUL;

		}



	// At long last, unload the module and release the extra references to

	// the device object



	if (DriverObject->DriverUnload)

		(*DriverObject->DriverUnload)(DriverObject);

	ObDereferenceObject(DriverObject);

	ObDereferenceObject(DriverObject);

	_PELDR_FreeModule(hmod, NULL);



	return STATUS_SUCCESS;

	}							// ZwUnloadDriver



BOOLEAN SeSinglePrivilegeCheck(LUID PrivilegeValue, KPROCESSOR_MODE PreviousMode)

	{							// SeSinglePrivilegeCheck

	ASSERT(KeGetCurrentIrql() == PASSIVE_LEVEL);

	ASSERT(PreviousMode == UserMode || PreviousMode == KernelMode);

	return TRUE;

	}							// SeSinglePrivilegeCheck



NTSTATUS IoSetCompletionRoutineEx(PDEVICE_OBJECT fdo, PIRP Irp, PIO_COMPLETION_ROUTINE CompletionRoutine,

	PVOID Context, BOOLEAN success, BOOLEAN failure, BOOLEAN cancel)		

	{							// IoSetCompletionRoutineEx

	ASSERT(fdo);

	ASSERT(Irp);

	ASSERT(CompletionRoutine);

	ASSERT(success || failure || cancel);



	PCOMPLETION_CONTEXT ctx = (PCOMPLETION_CONTEXT) _HeapAllocate(sizeof(COMPLETION_CONTEXT), 0);

	if (!ctx)

		return STATUS_INSUFFICIENT_RESOURCES;

	ctx->CompletionRoutine = CompletionRoutine;

	ctx->Context = Context;

	ctx->fdo = fdo;



	IoSetCompletionRoutine(Irp, (PIO_COMPLETION_ROUTINE) CompletionRoutineWrapper, (PVOID) ctx,

		success, failure, cancel);



	return STATUS_SUCCESS;

	}							// IoSetCompletionRoutineEx



///////////////////////////////////////////////////////////////////////////////



void __cdecl MessageCallback(char* msg)

	{							// MessageCallback

#pragma pack(2)

	struct {					// MessageBox parameters

		WORD fuStyle;			// style flags

		DWORD lpszTitle;		// title string

		DWORD lpszText;			// message text

		WORD hwndParent;		// parent window handle

		} parms;				// MessageBox parameters

#pragma pack()



	// Construct parameter list for call to MessageBox



	parms.fuStyle = MB_OK | MB_ICONHAND;

	parms.lpszTitle = _SHELL_LocalAllocEx(LMEM_STRING, 0, "Windows - Operation Failed");

	parms.lpszText = _SHELL_LocalAllocEx(LMEM_STRING, 0, msg);

	parms.hwndParent = 0;

	

	// Invoke MessageBox to display the message



	if (parms.lpszTitle && parms.lpszText)

		_SHELL_CallDll("USER", "MESSAGEBOX", sizeof(parms), &parms);



	// Cleanup



	if (parms.lpszText)

		_SHELL_LocalFree(parms.lpszText);

	if (parms.lpszTitle)

		_SHELL_LocalFree(parms.lpszTitle);

	_HeapFree(msg, 0);

	}							// MessageCallback



///////////////////////////////////////////////////////////////////////////////



__int64 GetZoneBias()

	{							// GetZoneBias

	DWORD hkey;

	if (_RegOpenKey(HKEY_LOCAL_MACHINE, REGSTR_PATH_TIMEZONE, &hkey) != 0)

		return 0;



	__int64 bias;

	LONG actbias;

	DWORD size = sizeof(actbias);



	if (_RegQueryValueEx(hkey, REGSTR_VAL_TZACTBIAS, NULL, NULL, &actbias, &size) == 0)

		{						// compute 100-ns bias

		actbias *= 60;			// minutes to seconds

		_asm mov eax, actbias

		_asm mov ecx, 10000000	// seconds to 100-ns units

		_asm imul ecx

		_asm mov dword ptr bias, eax

		_asm mov dword ptr bias+4, edx



		}						// compute 100-ns bias

	else

		bias = 0;



	_RegCloseKey(hkey);

	return bias;

	}							// GetZoneBias



///////////////////////////////////////////////////////////////////////////////



DWORD atox(char* s)

	{							// atox

	DWORD result = 0;

	char ch;

	while ((ch = *s++))

		{						// convert hex number

		BYTE hexit;

		if (ch >= '0' && ch <= '9')

			hexit = ch - '0';

		else if (ch >= 'A' && ch <= 'F')

			hexit = ch - ('A' - 10);

		else if ( ch >= 'a' && ch <= 'f')

			hexit = ch - ('a' - 10);

		else

			break;				// invalid hexit -- ignore



		result <<= 4;

		result += hexit;

		}						// convert hex number



	return result;

	}							// atox



///////////////////////////////////////////////////////////////////////////////



LCID GetSystemLocale()

	{							// GetSystemLocale

	LCID lcid = LOCALE_SYSTEM_DEFAULT;	// in case nothing found

	#define REGSTR_PATH_LOCALE TEXT("System\\CurrentControlSet\\Control\\Nls\\Locale")



	// Query the registry to determine the default locale



	DWORD hKey;

	if (_RegOpenKey(HKEY_LOCAL_MACHINE, REGSTR_PATH_LOCALE, &hKey) != 0)

		return lcid;



	char szLocale[9];

	DWORD size = sizeof(szLocale);

	DWORD type;



	if (_RegQueryValueEx(hKey, NULL, NULL, &type, (PBYTE) szLocale, &size) == 0 && type == REG_SZ)

		lcid = atox(szLocale);



	_RegCloseKey(hKey);

	return lcid;

	}							// GetSystemLocale



///////////////////////////////////////////////////////////////////////////////



#pragma warning(disable:4035)



LONG __stdcall Get_System_Time()

	{							// Get_System_Time

	VMMCall(Get_System_Time)

	}							// Get_System_Time



#pragma warning(default:4035)



///////////////////////////////////////////////////////////////////////////////



NTSTATUS CompletionRoutineWrapper(PDEVICE_OBJECT junk, PIRP Irp, PCOMPLETION_CONTEXT ctx)

	{							// CompletionRoutineWrapper

	ObReferenceObject(ctx->fdo);

	NTSTATUS status = (*ctx->CompletionRoutine)(junk, Irp, ctx->Context);

	ObDereferenceObject(ctx->fdo);

	_HeapFree((PVOID) ctx, 0);

	return status;

	}							// CompletionRoutineWrapper

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -