驱动中常见的字符串操作
Windows内核分析索引目录:https://www.cnblogs.com/onetrainee/p/11675224.html
驱动中常见的字符串操作
驱动中的字符串初始化有三种常见的方法:
1. RTL_UNICODE_STRING:
UNICODE_STRING us = RTL_CONSTANT_STRING(L"RTL_CONSTANT_STRING UnicodeString");
这种定义出来的是常量,无法被修改。
2. RtlInitUnicodeString
UNICODE_STRING us;
RtlInitUnicodeString(&us, L"abcd");
该方法与第一种方法一样,同样是常量无法被修改。
3. RtlInitEmptyUnicodeString
UNICODE_STRING usDest;
WCHAR wcstr[128] = { 0 };
RtlInitEmptyUnicodeString(&usDest, wcstr, sizeof(wcstr));
这种有自己独立的缓冲区,可以被修改,但该缓冲区在栈中,内核中栈非常小,这样会造成栈溢出,应该使用ExAllocatePool来从堆中分配内存。
#include <ntddk.h> #include <intrin.h> #include <ntstrsafe.h> // 内存操作 void MemoryOperation() { PCHAR pcstr; DbgPrint("1.内存操作:\n"); // 1)申请内存 pcstr = (PCHAR)ExAllocatePoolWithTag(NonPagedPool, 1024, 'abcd'); if (pcstr == NULL) { DbgPrint("内存分配失败\n"); return; } // 2)清空内存 RtlZeroMemory(pcstr, 1024); // 3)赋值内存 strcpy(pcstr, "这是一次内存测试"); DbgPrint("%s\n", pcstr); // 4)释放内存 ExFreePoolWithTag(pcstr, 'abcd'); DbgPrint("**************\n"); } // 使用宏来进行字符串初始化操作 void InitStringByRtl() { DbgPrint("2.通过宏来进行字符串初始化操作:\n"); UNICODE_STRING us = RTL_CONSTANT_STRING(L"RTL_CONSTANT_STRING UnicodeString"); ANSI_STRING as = RTL_CONSTANT_STRING("RTL_CONSTANT_STRING AnsiString"); DbgPrint("%wZ\n", &us); DbgPrint("%Z\n", &as); DbgPrint("**************\n"); } // 字符串赋值操作 void StringCopy() { DbgPrint("3.字符串复制操作:\n"); // 1)声明目标字符串 UNICODE_STRING usDest; ANSI_STRING asDest; WCHAR wcstr[128] = { 0 }; // UnicodeString的缓冲区 CHAR asstr[128] = { 0 }; // AnsiString的缓冲区 // 2)初始化原字符串 UNICODE_STRING us = RTL_CONSTANT_STRING(L"UnicodeString"); ANSI_STRING as = RTL_CONSTANT_STRING("AnsiString"); // 3)初始化目标字符串(自定义缓冲区) RtlInitEmptyUnicodeString(&usDest, wcstr, sizeof(wcstr)); RtlInitEmptyAnsiString(&asDest, asstr, sizeof(asstr)); // 4)复制目标字符串 RtlCopyUnicodeString(&usDest, &us); RtlCopyString(&asDest, &as); // 5)输出字符串 DbgPrint("%wZ\n", &usDest); DbgPrint("%Z\n", &asDest); DbgPrint("**************\n"); } // 字符串比较操作 VOID CompareString() { DbgPrint("4.字符串比较操作:\n"); // 1)初始化字符串 UNICODE_STRING s1 = RTL_CONSTANT_STRING(L"Hello world!"); UNICODE_STRING s2 = RTL_CONSTANT_STRING(L"Hello world!"); // 2)字符串比较 int ret = RtlCompareUnicodeString(&s1, &s2, TRUE); // 3)输出字符串比较结果 if (ret == 0) { KdPrint(("s1=s2\n")); } else if (ret < 0) { KdPrint(("s1<s2\n")); } else { KdPrint(("s1>s2\n")); } DbgPrint("**************\n"); } // 字符串转换为写操作 void UpperString() { DbgPrint("5.将字符串转换为大写:\n"); // 1)声明并初始化字符串 UNICODE_STRING us, usDest; RtlInitUnicodeString(&us, L"abcd"); WCHAR wcstr[128] = { 0 }; RtlInitEmptyUnicodeString(&usDest, wcstr, sizeof(wcstr)); // 2)将字符串转换为大写 RtlUpcaseUnicodeString(&usDest, &us, FALSE); DbgPrint("转换为大写:%wZ\n", &usDest); DbgPrint("**************\n"); } // 字符串与数字的转换 void StringToInteger() { DbgPrint("6.字符串与数字的转换:\n"); UNICODE_STRING us,usDest; int Value; WCHAR wcstr[128] = { 0 }; RtlInitEmptyUnicodeString(&usDest, wcstr, sizeof(wcstr)); // 1)字符串转换为数字 RtlInitUnicodeString(&us, L"-123"); RtlUnicodeStringToInteger(&us, 10, &Value); KdPrint(("%d\n", Value)); // 2)数字转换为字符串 RtlIntegerToUnicodeString(123, 10, &usDest); KdPrint(("%wZ\n", &us)); DbgPrint("**************\n"); } // 格式化输出 void FormatPrint() { DbgPrint("7.标准化输出:\n"); // 1)初始化字符串 UNICODE_STRING str1 = RTL_CONSTANT_STRING(L"abc"); UNICODE_STRING us; WCHAR wcstr[128] = { 0 }; RtlInitEmptyUnicodeString(&us, wcstr, sizeof(wcstr)); // 2)标准化格式输出 ntstrsafe.h RtlUnicodeStringPrintf(&us, L"%d%wZ\n",10,&str1); // 3)输出 DbgPrint("%wZ", &us); DbgPrint("**************\n"); } // ANSI与UnicodeString之间的转换 void AnsiToUnicode() { DbgPrint("8.ANSI与UnicodeString之间的转换:\n"); // 1)初始化Unicode字符串 UNICODE_STRING us; WCHAR wcstr[128] = { 0 }; RtlInitEmptyUnicodeString(&us, wcstr, sizeof(wcstr)); // 2)初始化ANSI字符串 ANSI_STRING as = RTL_CONSTANT_STRING("Hello World!"); // 3)ANSI转换为Unicode RtlAnsiStringToUnicodeString(&us, &as, FALSE); DbgPrint("%wZ\n", &us); DbgPrint("**************\n"); } VOID DriverUnload(_In_ struct _DRIVER_OBJECT* DriverObject) { DbgPrint("%s\r\n", "驱动卸载成功"); } NTSTATUS DriverEntry(PDRIVER_OBJECT pDriver, PUNICODE_STRING pRegPath) { pDriver->DriverUnload = DriverUnload; MemoryOperation(); // 内存操作 InitStringByRtl(); // 字符串初始化操作 StringCopy(); // 字符串复制操作 CompareString(); // 字符串比较操作 UpperString(); // 字符串大写操作 StringToInteger(); // 字符串与数字的转换 FormatPrint(); // 标准化格式输出 AnsiToUnicode(); // Ansi与Unicode字符串之间的转换 return STATUS_SUCCESS; }