UnicodeString基本操作(Ring3)
// 纯粹做个记录,微软源码
1 // Unicode_String_Ring3.cpp : 定义控制台应用程序的入口点。
// #include "stdafx.h"
#include "Unicode_String_Ring3.h" /*
所有带Ums_前缀的函数都是自己根据windows2000源码实现的 因为Ring3不能直接定义UnicodeString
所以根据微软的源代码来实现 */ int main()
{
Test();
return ;
} void Test()
{
//初始化
//StringInitTest(); //拷贝操作
//StringCopyTest(); //字符串比较
//StringCompareTest(); //字符串变大写***
StringToUpperTest(); //字符串与整型相互转化
//StringToIntegerTest(); //ANSI_STRING字符串与UNICODE_STRING字符串相互转换
//StringConverTest();
//最后未释放内存,bug printf("Input AnyKey To Exit\r\n");
getchar();
} //初始化
void StringInitTest()
{
Sub_1();
//Sub_2();
//Sub_3();
} void Sub_1()
{
UNICODE_STRING v1; Ums_RtlInitUnicodeString(&v1, L"HelloWorld"); printf("%Z\r\n", &v1); }
VOID
Ums_RtlInitUnicodeString(
OUT PUNICODE_STRING DestinationString,
IN PCWSTR SourceString OPTIONAL
)
{
USHORT Length = ;
DestinationString->Length = ;
DestinationString->Buffer = (PWSTR)SourceString;
if (SourceString != NULL)
{
while (*SourceString++)
{
Length += sizeof(*SourceString);
} DestinationString->Length = Length; DestinationString->MaximumLength = Length+(USHORT)sizeof(UNICODE_NULL);
}
else
{
DestinationString->MaximumLength = ;
}
}
void Sub_2()
{
UNICODE_STRING v1;
WCHAR BufferData[] = L"HelloWorld";
v1.Buffer = BufferData;
v1.Length = wcslen(BufferData) * sizeof(WCHAR);
v1.MaximumLength = (wcslen(BufferData) + ) * sizeof(WCHAR);
printf("%Z\r\n", &v1);
} void Sub_3()
{
UNICODE_STRING v1;
WCHAR BufferData[] = L"HelloWorld"; v1.Length = wcslen(BufferData) * sizeof(WCHAR);
v1.MaximumLength = (wcslen(BufferData) + ) * sizeof(WCHAR);
v1.Buffer = (WCHAR*)malloc(v1.MaximumLength);
RtlZeroMemory(v1.Buffer, v1.MaximumLength);
RtlCopyMemory(v1.Buffer, BufferData, v1.Length); printf("%Z\r\n", &v1);
if (v1.Buffer != NULL)
{
free(v1.Buffer);
v1.Buffer = NULL;
v1.Length = v1.MaximumLength = ;
}
} //拷贝操作
void StringCopyTest()
{
UNICODE_STRING SourceString;
Ums_RtlInitUnicodeString(&SourceString, L"HelloWorld"); UNICODE_STRING DestinationString = { };
DestinationString.Buffer = (PWSTR)malloc(BUFFER_SIZE);
DestinationString.MaximumLength = BUFFER_SIZE; Ums_RtlCopyUnicodeString(&DestinationString, &SourceString); printf("SourceString:%wZ\r\n", &SourceString);
printf("DestinationString:%wZ\n", &DestinationString); Ums_RtlFreeUnicodeString(&DestinationString);
} VOID
Ums_RtlCopyUnicodeString(
OUT PUNICODE_STRING DestinationString,
IN PUNICODE_STRING SourceString OPTIONAL
)
{
UNALIGNED WCHAR *Source, *Dest;
ULONG n; if (SourceString!=NULL)
{
Dest = DestinationString->Buffer;
Source = SourceString->Buffer;
n = SourceString->Length;
if ((USHORT)n > DestinationString->MaximumLength)
{
n = DestinationString->MaximumLength;
} DestinationString->Length = (USHORT)n;
RtlCopyMemory(Dest, Source, n);
if (DestinationString->Length < DestinationString->MaximumLength)
{
Dest[n / sizeof(WCHAR)] = UNICODE_NULL;
} }
else
{
DestinationString->Length = ;
} return;
}
VOID
Ums_RtlFreeUnicodeString(
IN OUT PUNICODE_STRING UnicodeString
)
{
if (UnicodeString->Buffer)
{
//free(UnicodeString->Buffer); memset( UnicodeString, , sizeof( *UnicodeString ) );
}
} //字符串比较
void StringCompareTest()
{
//初始化UnicodeString1
UNICODE_STRING UnicodeString1;
Ums_RtlInitUnicodeString(&UnicodeString1,L"HELLOWORLD"); //初始化UnicodeString2
UNICODE_STRING UnicodeString2;
//Ums_RtlInitUnicodeString(&UnicodeString2, L"Hello");
//Ums_RtlInitUnicodeString(&UnicodeString2, L"HELLOWORLD");
Ums_RtlInitUnicodeString(&UnicodeString2, L"helloworld"); if (Ums_RtlEqualUnicodeString(
&UnicodeString1,
&UnicodeString2,
TRUE
//If TRUE,
//case should be ignored when doing the comparison.
)
)
{
printf("UnicodeString1 and UnicodeString2 are equal\n");
}
else
{
printf("UnicodeString1 and UnicodeString2 are NOT equal\n");
}
}
BOOLEAN
Ums_RtlEqualUnicodeString(
IN const PUNICODE_STRING String1,
IN const PUNICODE_STRING String2,
IN BOOLEAN CaseInSensitive
)
{
UNALIGNED WCHAR *s1, *s2;
USHORT n1, n2;
WCHAR c1, c2; s1 = String1->Buffer;
s2 = String2->Buffer;
n1 = (USHORT )(String1->Length / sizeof(WCHAR));
n2 = (USHORT )(String2->Length / sizeof(WCHAR)); if ( n1 != n2 )
{
return FALSE;
} if (CaseInSensitive)
{
while ( n1 )
{
if ( *s1++ != *s2++ )
{
c1 = upcase(*(s1-));
c2 = upcase(*(s2-));
if (c1 != c2)
{
return( FALSE );
}
}
n1--;
}
}
else
{
while ( n1 )
{ if (*s1++ != *s2++)
{
return( FALSE );
} n1--;
}
}
return TRUE;
} //字符串变大写
void StringToUpperTest()
{
UNICODE_STRING SourceString;
Ums_RtlInitUnicodeString(&SourceString, L"Hello World"); UNICODE_STRING DestinationString;
DestinationString.Buffer = (PWSTR)malloc(BUFFER_SIZE);
DestinationString.MaximumLength = BUFFER_SIZE; //变化前
printf("变化前:%wZ\n", &SourceString);
//变大写
Ums_RtlUpcaseUnicodeString(
&DestinationString, //DestinationString
&SourceString, //SourceString
FALSE//Specifies if RtlUpcaseUnicodeString is to allocate the buffer space for the DestinationString.
//If it does, the buffer must be deallocated by calling RtlFreeUnicodeString.
); //变化后
printf("变化后:%wZ\n", &DestinationString); Ums_RtlFreeUnicodeString(&DestinationString);
} BOOL
Ums_RtlUpcaseUnicodeString(
OUT PUNICODE_STRING DestinationString,
IN PCUNICODE_STRING SourceString,
IN BOOLEAN AllocateDestinationString
)
{
ULONG Index;
ULONG StopIndex; if ( AllocateDestinationString )
{
DestinationString->MaximumLength = SourceString->Length;
//DestinationString->Buffer = (Ums_RtlAllocateStringRoutine)((ULONG)DestinationString->MaximumLength); DestinationString->Buffer = (PWSTR)malloc((ULONG)DestinationString->MaximumLength); if ( !DestinationString->Buffer )
{
return FALSE;
}
}
else
{
if ( SourceString->Length > DestinationString->MaximumLength )
{
return FALSE;
}
} StopIndex = ((ULONG)SourceString->Length) / sizeof( WCHAR ); for (Index = ; Index < StopIndex; Index++)
{
DestinationString->Buffer[Index] = (WCHAR)NLS_UPCASE(SourceString->Buffer[Index]);
} DestinationString->Length = SourceString->Length; return TRUE;
} //字符串与整型相互转化
void StringToIntegerTest()
{
//(1)字符串转换成数字
UNICODE_STRING UnicodeString1;
Ums_RtlInitUnicodeString(&UnicodeString1, L"-100"); ULONG lNumber;
NTSTATUS Status =
Ums_RtlUnicodeStringToInteger(//第二个参数Base
&UnicodeString1,
//10,//-100是10进制 //输出-100
//16,//-100是16进制 //输出-256
, //-100是8进制 //输出-64
&lNumber
); if (NT_SUCCESS(Status))
{
printf("Conver to integer succussfully!\n");
printf("Result:%d\n", lNumber);
}
else
{
printf("Conver to integer unsuccessfully!\n");
}
//(2)数字转换成字符串
UNICODE_STRING UnicodeString2 = { };
UnicodeString2.Buffer = (PWSTR)malloc(BUFFER_SIZE);
UnicodeString2.MaximumLength = BUFFER_SIZE; Status = Ums_RtlIntegerToUnicodeString(//同上 第二参数是Base
,
//10, //输出200
//8, //输出310
, //输出 C8
&UnicodeString2
); /*
HEX C8
DEC 200
OCT 310 */
if (NT_SUCCESS(Status))
{
printf("Conver to string succussfully!\n");
printf("Result:%wZ\n", &UnicodeString2);
}
else
{
printf("Conver to string unsuccessfully!\n");
} //销毁UnicodeString2
//注意!!UnicodeString1不用销毁
Ums_RtlFreeUnicodeString(&UnicodeString2); }
BOOL
Ums_RtlUnicodeStringToInteger(
IN PUNICODE_STRING String,
IN ULONG Base OPTIONAL,
OUT PULONG Value
)
{
PCWSTR s;
WCHAR c, Sign;
ULONG nChars, Result, Digit, Shift; s = String->Buffer;
nChars = String->Length / sizeof(WCHAR);
while (nChars-- && (Sign = *s++) <= ' ') {
if (!nChars) {
Sign = UNICODE_NULL;
break;
}
} c = Sign;
if (c == L'-' || c == L'+') {
if (nChars) {
nChars--;
c = *s++;
}
else {
c = UNICODE_NULL;
}
} if (((ULONG_PTR)Base)!=NULL) {
Base = ;
Shift = ;
if (c == L'') {
if (nChars) {
nChars--;
c = *s++;
if (c == L'x') {
Base = ;
Shift = ;
}
else
if (c == L'o') {
Base = ;
Shift = ;
}
else
if (c == L'b') {
Base = ;
Shift = ;
}
else {
nChars++;
s--;
}
} if (nChars) {
nChars--;
c = *s++;
}
else {
c = UNICODE_NULL;
}
}
}
else {
switch (Base) {
case : Shift = ; break;
case : Shift = ; break;
case : Shift = ; break;
case : Shift = ; break;
default: return(FALSE);
}
} Result = ;
while (c != UNICODE_NULL) {
if (c >= L'' && c <= L'') {
Digit = c - L'';
}
else
if (c >= L'A' && c <= L'F') {
Digit = c - L'A' + ;
}
else
if (c >= L'a' && c <= L'f') {
Digit = c - L'a' + ;
}
else {
break;
} if (Digit >= Base) {
break;
} if (Shift == ) {
Result = (Base * Result) + Digit;
}
else {
Result = (Result << Shift) | Digit;
} if (!nChars) {
break;
}
nChars--;
c = *s++;
} if (Sign == L'-') {
Result = (ULONG)(-(LONG)Result);
} __try
{
*Value = Result;
}
__except(EXCEPTION_EXECUTE_HANDLER) {
return(GetExceptionCode());
} return(TRUE);
} BOOL
Ums_RtlIntegerToUnicodeString(
IN ULONG Value,
IN ULONG Base OPTIONAL,
IN OUT PUNICODE_STRING String
)
{
BOOL IsOk;
char ResultBuffer[];
ANSI_STRING AnsiString; IsOk = Ums_RtlIntegerToChar(Value, Base, sizeof(ResultBuffer), ResultBuffer);
if (IsOk)
{
AnsiString.Buffer = ResultBuffer;
AnsiString.MaximumLength = sizeof(ResultBuffer);
AnsiString.Length = (USHORT)strlen(ResultBuffer);
IsOk = Ums_RtlAnsiStringToUnicodeString(String, &AnsiString, FALSE);
} return(IsOk);
} BOOL
Ums_RtlAnsiStringToUnicodeString(
OUT PUNICODE_STRING DestinationString,
IN PANSI_STRING SourceString,
IN BOOLEAN AllocateDestinationString
)
{
ULONG UnicodeLength;
ULONG Index;
NTSTATUS st; UnicodeLength = (SourceString->Length << ) + sizeof(UNICODE_NULL); if (UnicodeLength > MAXUSHORT) {
return FALSE;
} DestinationString->Length = (USHORT)(UnicodeLength - sizeof(UNICODE_NULL)); /*
if (AllocateDestinationString) {
return FALSE;
}
else {
if (DestinationString->Length >= DestinationString->MaximumLength) {
return FALSE;
}
}
*/
//DestinationString->buffer没有申请内存 所以 我们这里仿造上一个函数的申请
DestinationString->Buffer = (PWCHAR)malloc(UnicodeLength); Index = ;
while (Index < DestinationString->Length)
{
DestinationString->Buffer[Index] = (WCHAR)SourceString->Buffer[Index];
Index++;
}
DestinationString->Buffer[Index] = UNICODE_NULL; return TRUE;
} BOOL
Ums_RtlIntegerToChar(
IN ULONG Value,
IN ULONG Base OPTIONAL,
IN LONG OutputLength,
OUT char* String
)
{
CHAR Result[], *s;
ULONG Shift, Mask, Digit, Length; Shift = ;
switch (Base) {
case : Shift = ; break;
case : Shift = ; break;
case : Shift = ; break; case : Base = ;
case : Shift = ; break;
default: return(FALSE);
} if (Shift != ) {
Mask = 0xF >> ( - Shift);
} s = &Result[];
*s = '\0';
do {
if (Shift != ) {
Digit = Value & Mask;
Value >>= Shift;
}
else {
Digit = Value % Base;
Value = Value / Base;
} *--s = RtlpIntegerChars[Digit];
} while (Value != ); Length = (ULONG)(&Result[] - s);
if (OutputLength < ) {
OutputLength = -OutputLength;
while ((LONG)Length < OutputLength) {
*--s = '';
Length++;
}
} if ((LONG)Length > OutputLength)
{
return(FALSE);
}
else {
__try {
RtlMoveMemory(String, s, Length); if ((LONG)Length < OutputLength) {
String[Length] = '\0';
}
} __except(EXCEPTION_EXECUTE_HANDLER)
{
return(GetExceptionCode());
} return(TRUE);
}
} //ANSI_STRING字符串与UNICODE_STRING字符串相互
void StringConverTest()
{
//(1)将UNICODE_STRING字符串转换成ANSI_STRING字符串
//初始化UnicodeString1
UNICODE_STRING UnicodeString1;
Ums_RtlInitUnicodeString(&UnicodeString1, L"HelloWorld"); ANSI_STRING AnsiString1;
NTSTATUS Status = Ums_RtlUnicodeStringToAnsiString(
&AnsiString1,
&UnicodeString1,
TRUE
//TRUE if this routine is to allocate the buffer space for the DestinationString.
//If it does, the buffer must be deallocated by calling RtlFreeAnsiString.
); if (NT_SUCCESS(Status))
{
printf("Conver succussfully!\n");
//printf("Result:%Z\n", &AnsiString1);
//printf("Result:%Z\n", AnsiString1.Buffer);
printf("Result:%s\n", AnsiString1.Buffer);
}
else
{
printf("Conver unsuccessfully!\n");
} //销毁AnsiString1
Ums_RtlFreeAnsiString(&AnsiString1); /******************************************/ //(2)将ANSI_STRING字符串转换成UNICODE_STRING字符串 ANSI_STRING AnsiString2;
Ums_RtlInitString(&AnsiString2, "HelloWorld"); UNICODE_STRING UnicodeString2;
Status = Ums_RtlAnsiStringToUnicodeString(
&UnicodeString2,
&AnsiString2,
TRUE
//Specifies if this routine should allocate the buffer space for the destination string.
//If it does, the caller must deallocate the buffer by calling RtlFreeUnicodeString. ); if (NT_SUCCESS(Status))
{
printf("Conver succussfully!\n");
//printf("Result:%wZ\n", &UnicodeString2);
//printf("Result:%wZ\n", UnicodeString2.Buffer);
printf("Result:%S\n", UnicodeString2.Buffer);
}
else
{
printf("Conver unsuccessfully!\n");
} //销毁UnicodeString2
Ums_RtlFreeUnicodeString(&UnicodeString2);
} VOID
Ums_RtlFreeAnsiString(
IN OUT PANSI_STRING AnsiString
)
{
if (AnsiString->Buffer) {
free(AnsiString->Buffer);
memset(AnsiString, , sizeof(*AnsiString));
}
}
VOID
Ums_RtlInitString(
OUT PSTRING DestinationString,
IN char* SourceString OPTIONAL
)
{
DestinationString->Length = ;
DestinationString->Buffer = (PCHAR)SourceString;
if ( SourceString !=NULL ) {
while (*SourceString++) {
DestinationString->Length++;
} DestinationString->MaximumLength = (SHORT)(DestinationString->Length+);
}
else {
DestinationString->MaximumLength = ;
}
} BOOL
Ums_RtlUnicodeStringToAnsiString(
OUT PANSI_STRING DestinationString,
IN PUNICODE_STRING SourceString,
IN BOOLEAN AllocateDestinationString
)
{
ULONG AnsiLength;
ULONG Index;
NTSTATUS st;
BOOL ReturnStatus = TRUE; AnsiLength = Ums_RtlxUnicodeStringToAnsiSize(SourceString);
if ( AnsiLength > MAXUSHORT ) {
return FALSE;
} DestinationString->Length = (USHORT)(AnsiLength - );
if ( AllocateDestinationString )
{
DestinationString->MaximumLength = (USHORT)AnsiLength;
//DestinationString->Buffer = (RtlAllocateStringRoutine)(AnsiLength);
DestinationString->Buffer = (PCHAR)malloc(AnsiLength); if ( !DestinationString->Buffer ) {
return FALSE;
}
}
else {
if ( DestinationString->Length >= DestinationString->MaximumLength ) {
/*
* Return STATUS_BUFFER_OVERFLOW, but translate as much as
* will fit into the buffer first. This is the expected
* behavior for routines such as GetProfileStringA.
* Set the length of the buffer to one less than the maximum
* (so that the trail byte of a double byte char is not
* overwritten by doing DestinationString->Buffer[Index] = '\0').
* RtlUnicodeToMultiByteN is careful not to truncate a
* multibyte character.
*/
if (!DestinationString->MaximumLength) {
return FALSE;
}
ReturnStatus = FALSE;
DestinationString->Length = DestinationString->MaximumLength - ;
}
} st = Ums_RtlUnicodeToMultiByteN(
DestinationString->Buffer,
DestinationString->Length,
&Index,
SourceString->Buffer,
SourceString->Length
); if (!NT_SUCCESS(st)) {
if ( AllocateDestinationString ) {
free(DestinationString->Buffer);
DestinationString->Buffer = NULL;
} return st;
} DestinationString->Buffer[Index] = '\0'; return ReturnStatus;
} BOOL
Ums_RtlUnicodeToMultiByteN(
OUT PCH MultiByteString,
IN ULONG MaxBytesInMultiByteString,
OUT PULONG BytesInMultiByteString OPTIONAL,
IN PWCH UnicodeString,
IN ULONG BytesInUnicodeString
)
{
ULONG TmpCount;
ULONG LoopCount;
ULONG CharsInUnicodeString;
UCHAR SbChar;
WCHAR UnicodeChar;
ULONG i; //
// Convert Unicode byte count to character count. Byte count of
// multibyte string is equivalent to character count.
//
CharsInUnicodeString = BytesInUnicodeString / sizeof(WCHAR); LoopCount = (CharsInUnicodeString < MaxBytesInMultiByteString) ?
CharsInUnicodeString : MaxBytesInMultiByteString; if ((BytesInMultiByteString) != NULL)
*BytesInMultiByteString = LoopCount; for (i = ; i < LoopCount; i++) {
MultiByteString[i] = (CHAR)UnicodeString[i];
} return TRUE; }
ULONG
Ums_RtlxUnicodeStringToAnsiSize(
IN PUNICODE_STRING UnicodeString
)
{
ULONG cbMultiByteString; //
// Get the size of the string - this call handles DBCS.
//
Ums_RtlUnicodeToMultiByteSize( &cbMultiByteString,
UnicodeString->Buffer,
UnicodeString->Length ); //
// Return the size in bytes.
//
return (cbMultiByteString + );
}
BOOL
Ums_RtlUnicodeToMultiByteSize(
OUT PULONG BytesInMultiByteString,
IN PWCH UnicodeString,
IN ULONG BytesInUnicodeString)
{
ULONG cbMultiByte = ;
ULONG CharsInUnicodeString; /*
* convert from bytes to chars for easier loop handling.
*/
CharsInUnicodeString = BytesInUnicodeString / sizeof(WCHAR); if (NlsMbCodePageTag) {
USHORT MbChar; while (CharsInUnicodeString--) {
MbChar = NlsUnicodeToMbAnsiData[ *UnicodeString++ ];
if (HIBYTE(MbChar) == ) {
cbMultiByte++ ;
} else {
cbMultiByte += ;
}
}
*BytesInMultiByteString = cbMultiByte;
}
else {
*BytesInMultiByteString = CharsInUnicodeString;
} return TRUE;
} ULONG
Ums_RtlxAnsiStringToUnicodeSize(
IN PANSI_STRING AnsiString
) {
ULONG cbConverted; //
// Get the size of the string - this call handles DBCS.
//
Ums_RtlMultiByteToUnicodeSize( &cbConverted ,
AnsiString->Buffer,
AnsiString->Length ); //
// Return the size in bytes.
//
return ( cbConverted + sizeof(UNICODE_NULL) );
}
BOOL
Ums_RtlMultiByteToUnicodeSize(
OUT PULONG BytesInUnicodeString,
IN PCH MultiByteString,
IN ULONG BytesInMultiByteString
)
{
ULONG cbUnicode = ;
if (NlsMbCodePageTag) {
//
// The ACP is a multibyte code page. Check each character
// to see if it is a lead byte before doing the translation.
//
while (BytesInMultiByteString--) {
if (NlsLeadByteInfo[*(PUCHAR)MultiByteString++]) {
//
// Lead byte - translate the trail byte using the table
// that corresponds to this lead byte. NOTE: make sure
// we have a trail byte to convert.
//
if (BytesInMultiByteString == ) {
//
// RtlMultibyteToUnicodeN() uses the unicode
// default character if the last multibyte
// character is a lead byte.
//
cbUnicode += sizeof(WCHAR);
break;
} else {
BytesInMultiByteString--;
MultiByteString++;
}
}
cbUnicode += sizeof(WCHAR);
}
*BytesInUnicodeString = cbUnicode;
} else {
//
// The ACP is a single byte code page.
//
*BytesInUnicodeString = BytesInMultiByteString * sizeof(WCHAR);
} return TRUE;
}
#pragma once
#include <windows.h>
#include <iostream> using namespace std; #define BUFFER_SIZE 0x400
#define DBCS_TABLE_SIZE 256
#define NT_SUCCESS(Status) (((NTSTATUS)(Status)) >= 0) //拷贝
#define upcase(C) \
(WCHAR )(((C) >= 'a' && (C) <= 'z' ? (C) - ('a' - 'A') : (C))) //字符串变大写
#define LOBYTE(w) ((UCHAR)((w)))
#define HIBYTE(w) ((UCHAR)(((USHORT)((w)) >> 8) & 0xFF))
#define GET8(w) ((ULONG)(((w) >> 8) & 0xff))
#define GETHI4(w) ((ULONG)(((w) >> 4) & 0xf))
#define GETLO4(w) ((ULONG)((w) & 0xf))
#define TRAVERSE844W(pTable, wch) \
( (pTable)[(pTable)[(pTable)[GET8((wch))] + GETHI4((wch))] + GETLO4((wch))] ) PUSHORT Nls844UnicodeUpcaseTable;
extern PUSHORT Nls844UnicodeUpcaseTable; #define NLS_UPCASE(wch) ( \
((wch) < 'a' ? \
(wch) \
: \
((wch) <= 'z' ? \
(wch) - ('a'-'A') \
: \
((WCHAR)((wch) + TRAVERSE844W(Nls844UnicodeUpcaseTable,(wch)))) \
) \
) \
)
#define MAXUSHORT USHRT_MAX typedef char *PSZ; typedef struct _UNICODE_STRING
{
USHORT Length;
USHORT MaximumLength;
PWCHAR Buffer;
}UNICODE_STRING, *PUNICODE_STRING; typedef const UNICODE_STRING *PCUNICODE_STRING; typedef struct _STRING {
USHORT Length;
USHORT MaximumLength;
#ifdef MIDL_PASS
[size_is(MaximumLength), length_is(Length)]
#endif // MIDL_PASS
_Field_size_bytes_part_opt_(MaximumLength, Length) PCHAR Buffer;
} STRING;
typedef STRING *PSTRING;
typedef STRING ANSI_STRING;
typedef PSTRING PANSI_STRING; CHAR RtlpIntegerChars[] = { '', '', '', '', '', '', '', '',
'', '', 'A', 'B', 'C', 'D', 'E', 'F' }; BOOLEAN NlsMbCodePageTag = FALSE; // TRUE -> Multibyte ACP, FALSE -> Singlebyte ACP
USHORT NlsLeadByteInfoTable[DBCS_TABLE_SIZE]; // Lead byte info. for ACP
PUSHORT NlsLeadByteInfo = NlsLeadByteInfoTable;
PUSHORT NlsUnicodeToMbAnsiData; // Unicode to Multibyte Ansi CP translation table void Test(); //初始化
void StringInitTest(); void Sub_1();
VOID
Ums_RtlInitUnicodeString(
OUT PUNICODE_STRING DestinationString,
IN PCWSTR SourceString OPTIONAL
); void Sub_2();
void Sub_3(); //拷贝操作
void StringCopyTest();
VOID
Ums_RtlCopyUnicodeString(
OUT PUNICODE_STRING DestinationString,
IN PUNICODE_STRING SourceString OPTIONAL
);
VOID
Ums_RtlFreeUnicodeString(
IN OUT PUNICODE_STRING UnicodeString
); //字符串比较
void StringCompareTest();
BOOLEAN
Ums_RtlEqualUnicodeString(
IN const PUNICODE_STRING String1,
IN const PUNICODE_STRING String2,
IN BOOLEAN CaseInSensitive
); //字符串变大写
void StringToUpperTest();
BOOL
Ums_RtlUpcaseUnicodeString(
OUT PUNICODE_STRING DestinationString,
IN PCUNICODE_STRING SourceString,
IN BOOLEAN AllocateDestinationString
); //字符串与整型相互转化
void StringToIntegerTest(); BOOL
Ums_RtlUnicodeStringToInteger(
IN PUNICODE_STRING String,
IN ULONG Base OPTIONAL,
OUT PULONG Value
);
BOOL
Ums_RtlIntegerToUnicodeString(
IN ULONG Value,
IN ULONG Base OPTIONAL,
IN OUT PUNICODE_STRING String
);
BOOL
Ums_RtlIntegerToChar(
IN ULONG Value,
IN ULONG Base OPTIONAL,
IN LONG OutputLength,
OUT PSZ String
);
BOOL
Ums_RtlAnsiStringToUnicodeString(
OUT PUNICODE_STRING DestinationString,
IN PANSI_STRING SourceString,
IN BOOLEAN AllocateDestinationString
); //ANSI_STRING字符串与UNICODE_STRING字符串相互
void StringConverTest(); VOID
Ums_RtlFreeAnsiString(
IN OUT PANSI_STRING AnsiString
); VOID
Ums_RtlInitString(
OUT PSTRING DestinationString,
IN char* SourceString OPTIONAL
);
BOOL
Ums_RtlUnicodeStringToAnsiString(
OUT PANSI_STRING DestinationString,
IN PUNICODE_STRING SourceString,
IN BOOLEAN AllocateDestinationString
);
ULONG
Ums_RtlxAnsiStringToUnicodeSize(
IN PANSI_STRING AnsiString
);
BOOL
Ums_RtlMultiByteToUnicodeSize(
OUT PULONG BytesInUnicodeString,
IN PCH MultiByteString,
IN ULONG BytesInMultiByteString
);
ULONG
Ums_RtlxUnicodeStringToAnsiSize(
IN PUNICODE_STRING UnicodeString
);
BOOL
Ums_RtlUnicodeToMultiByteSize(
OUT PULONG BytesInMultiByteString,
IN PWCH UnicodeString,
IN ULONG BytesInUnicodeString
);
BOOL
Ums_RtlUnicodeToMultiByteN(
OUT PCH MultiByteString,
IN ULONG MaxBytesInMultiByteString,
OUT PULONG BytesInMultiByteString OPTIONAL,
IN PWCH UnicodeString,
IN ULONG BytesInUnicodeString
);
UnicodeString基本操作(Ring3)的更多相关文章
- UnicodeString基本操作(Ring0)
#include "Unicode_String_Ring0.h" //bp Unicode_String_Ring0!DriverEntry NTSTATUS DriverEnt ...
- Ring3层 UNICODE_STRING
今天写驱动用到UNICODE_STRING,就在Ring3层抠了一些源代码,学习一下,不多说了上代码了 #pragma once #include <windows.h> #include ...
- Key/Value之王Memcached初探:二、Memcached在.Net中的基本操作
一.Memcached ClientLib For .Net 首先,不得不说,许多语言都实现了连接Memcached的客户端,其中以Perl.PHP为主. 仅仅memcached网站上列出的语言就有: ...
- Android Notification 详解(一)——基本操作
Android Notification 详解(一)--基本操作 版权声明:本文为博主原创文章,未经博主允许不得转载. 微博:厉圣杰 源码:AndroidDemo/Notification 文中如有纰 ...
- Android Notification 详解——基本操作
Android Notification 详解 版权声明:本文为博主原创文章,未经博主允许不得转载. 前几天项目中有用到 Android 通知相关的内容,索性把 Android Notificatio ...
- 三、Redis基本操作——List
小喵的唠叨话:前面我们介绍了Redis的string的数据结构的原理和操作.当时我们提到Redis的键值对不仅仅是字符串.而这次我们就要介绍Redis的第二个数据结构了,List(链表).由于List ...
- 二、Redis基本操作——String(实战篇)
小喵万万没想到,上一篇博客,居然已经被阅读600次了!!!让小喵感觉压力颇大.万一有写错的地方,岂不是会误导很多筒子们.所以,恳请大家,如果看到小喵的博客有什么不对的地方,请尽快指正!谢谢! 小喵的唠 ...
- 一、Redis基本操作——String(原理篇)
小喵的唠叨话:最近京东图书大减价,小喵手痒了就买了本<Redis设计与实现>[1]来看看.这里权当小喵看书的笔记啦.这一系列的模式,主要是先介绍Redis的实现原理(可能很大一部分会直接照 ...
- Linq查询基本操作
摘要:本文介绍Linq查询基本操作(查询关键字) - from 子句 - where 子句 - select子句 - group 子句 - into 子句 - orderby 子句 - join 子句 ...
随机推荐
- jenkins安装教程
首先部署java环境 然后部署tomacat(部署之后无需开启tomcat服务) sudo wget -O /etc/yum.repos.d/jenkins.repo https://pkg.jenk ...
- encrypt and decrypt data
https://www.cyberciti.biz/tips/linux-how-to-encrypt-and-decrypt-files-with-a-password.html Encryptin ...
- Python的itertools模块
本章将介绍Python自建模块itertools,更多内容请参考:Python参考指南 python的自建模块itertools提供了非常有用的用于操作迭代对象的函数. 首先,我们看看itertool ...
- Hi3518EV200音频相关
1.sample程序可以录音,音频格式为G711A.G711U.G726.ADPCM: 2.ADPCM找不到音频播放器 3.G711格式海思添加了4字节头0x00 0x01 0x0a 0x00,普通播 ...
- http1.1 和 http2 的协议对比测试
http1.1 和 http2 的协议对比测试 http 协议发展了很多年,目前最为流行的是 http 2. 发现有些网站很流行的网站用的 http1.1, 询问后原来是因为有特殊用途. https: ...
- ES9新特性
这篇文章主要介绍ES2018(ES9)的新特性, 以及使用方法 JS是一门跨平台的语言, ES6也就是ECMAScript 2015 花费了5年的时间敲定, 是一次非常大的改版, 之后每年都有一个小版 ...
- Spring Cloud 与 Dubbo、Spring Cloud 与 Docker、Spring Cloud 与 Kubernetes 比较
出处:http://dockone.io/article/4142
- Kubernetes 知识点
自己总结的 Kubernetes 的各模块(待补充) 各模块包含关系: namespace => node => pod => container table th:first-of ...
- create-react-app 搭建的项目中,使用 CSS Modules
create-react-app 搭建的项目中,使用 CSS Modules: 修改config目录下 webpack.config.dev.js 和 webpack.config.prod.js 文 ...
- Jenkins 安装启动提示“iJob for jenkins.service failed because the control process exited with error code. See "systemctl status jenkins.service" and "journalctl -xe" for details.”
通过RPM安装Jenkins简单方便,不太需要复杂的过程,但是在安装完成以后启动Jenkins的时候提示“Starting jenkins (via systemctl): Job for jenki ...