2009年10月9日 星期五
DDK 字串處理
ANSI字元 char *str1 = "abc";
UNICODE wchar_t *str2 = L"abc";
DDK自訂字串
typedef struct _STRING {
USHORT Length;
USHORT MaximumLength;
PCHAR Buffer;
} STRING;
typedef STRING *PSTRING;
typedef STRING ANSI_STRING;
typedef PSTRING PANSI_STRING;
typedef STRING OEM_STRING;
typedef PSTRING POEM_STRING;
//初始字串
RtlInitAnsiString(PANSI_STRING DestinationString, PCSZ SourceString);
RtlInitUnicodeString(PUNICODE_STRING DestinationString, PCWSTR SourceString);
//拷貝字串
RtlCopyString(PSTRING DestinationString, PSTRING SourceString);
RtlCopyUnicodeString(PUNICODE_STRING DestinationString, PUNICODE_STRING SourceString );
範例:
//初始化UnicodeString1
#define BUFFER_SIZE 1024
UNICODE_STRING UnicodeString1;
RtlInitUnicodeString(&UnicodeString1,L"Hello World");
//初始化UnicodeString2,因為有分配記憶體空間,最後要記得free
UNICODE_STRING UnicodeString2={0};
UnicodeString2.Buffer = (PWSTR)ExAllocatePool(PagedPool,BUFFER_SIZE);
UnicodeString2.MaximumLength = BUFFER_SIZE;
//將初始化UnicodeString2拷貝到UnicodeString1
RtlCopyUnicodeString(&UnicodeString2,&UnicodeString1);
//銷毀UnicodeString2
RtlFreeUnicodeString(&UnicodeString2);
==========================================================================
//字串比較
RtlCompareString(PSTRING String1, PSTRING String2, BOOLEAN CaseInSensitive);
RtlCompareUnicodeString(PUNICODE_STRING String1, PUNICODE_STRING String2, BOOLEAN CaseInSensitive);
//轉成大寫 , AllocateDestinationString 是否為DestinationString分配記憶體
RtlUpperString(PSTRING DestinationString, PSTRING SourceString);
RtlUpcaseUnicodeString(PUNICODE_STRING DestinationString, PCUNICODE_STRING SourceString, BOOLEAN AllocateDestinationString);
//ANSI_STRING UNICODE_STRING 字串互轉
RtlAnsiStringToUnicodeString(PUNICODE_STRING DestinationString,
PANSI_STRING SourceString,
BOOLEAN AllocateDestinationString
);
RtlUnicodeStringToAnsiString(PANSI_STRING DestinationString,
PUNICODE_STRING SourceString,
BOOLEAN AllocateDestinationString
);
2009年10月7日 星期三
DDk 記憶體複製、填充、比較
但為了保證程式碼可攜,要儘量使用標準的function
//記憶體比較
RtlEqualMemory(Destination,Source,Length);
//記憶體複製,可重疊
RtlMoveMemory(Destination,Source,Length);
//記憶體複製,不可重疊
RtlCopyMemory(Destination,Source,Length);
//記憶體填充
RtlFillMemory(Destination,Length,Fill);
//將記憶體清成0
RtlZeroMemory(Destination,Length);
範例
VOID RtlTest()
{
PUCHAR pBuffer = (PUCHAR)ExAllocatePool(PagedPool,BUFFER_SIZE);
//用零填充記憶體
RtlZeroMemory(pBuffer,BUFFER_SIZE);
PUCHAR pBuffer2 = (PUCHAR)ExAllocatePool(PagedPool,BUFFER_SIZE);
//用固定位元組填充記憶體
RtlFillMemory(pBuffer2,BUFFER_SIZE,0xAA);
//記憶體拷貝
RtlCopyMemory(pBuffer,pBuffer2,BUFFER_SIZE);
//判斷記憶體是否一致
ULONG ulRet = RtlCompareMemory(pBuffer,pBuffer2,BUFFER_SIZE);
if (ulRet==BUFFER_SIZE)
{
KdPrint(("The two blocks are same.\n"));
}
}
DDK 記憶體配置及Linked-list處理
分配Kernal記憶體
PVOID ExAllocatePool(IN POOL_TYPE PoolType, IN SIZE_T NumberOfBytes);
PVOID ExAllocatePoolWithTag(IN POOL_TYPE PoolType, IN SIZE_T NumberOfBytes, IN ULONG Tag);
PVOID ExAllocatePoolWithQuota(IN POOL_TYPE, IN SIZE_T);
PVOID ExAllocatePoolWithQuataTag(IN POOL_TYPE, IN SIZE_T, IN UNLONG);
釋放Kernal記憶體
VOID ExFreePool(IN PVOID P);
NTKERNELAPI VOID ExFreePoolWithTag(IN PVOID P, ULONG tag);
2.
Kernal使用link-list:
typedef struct _LIST_ENTRY {
struct _LIST_ENTRY* Flink;
struct _LIST_ENTRY* Blink;
} LIST_ENTRY, *PLIST_ENTRY;
判斷 linked-list是否為空
IsListEmpty(PLIST_ENTRY);
插入element至 linked-list
InsertHeadList(PLIST_ENTRY head, PLIST_ENTRY entry);
InsertTailList(PLIST_ENTRY tail, PLIST_ENTRY entry);
從linked-list刪除element
RemoveHeadList(PLIST_ENTRY)
RemoveTailList(PLIST_ENTRY)
將element轉換成自訂資料結構
CONTAINING_RECORD(address, type, field) ;
address:自訂資料結構的位址
type:自訂的資料結構
filed:自訂資料結構中的pEntry
範例:
typedef struct _MYDATASTRUCT
{
ULONG number;
LIST_ENTRY ListEntry;
} MYDATASTRUCT, *PMYDATASTRUCT;
#pragma INITCODE
VOID LinkListTest()
{
LIST_ENTRY linkListHead;
//初始化鏈表
InitializeListHead(&linkListHead);
MYDATASTRUCT *pData;
ULONG i = 0;
//在鏈表中插入10個元素
KdPrint(("Begin insert to link list"));
for (i=0 ; i<5 ; i++)
{
pData = (MYDATASTRUCT *)ExAllocatePool(PagedPool,sizeof(MYDATASTRUCT));
pData->number = i;
InsertTailList(&linkListHead,&pData->ListEntry);
}
KdPrint(("Begin remove from link list\n"));
while(!IsListEmpty(&linkListHead))
{
PLIST_ENTRY pEntry = RemoveTailList(&linkListHead);
pData = CONTAINING_RECORD(pEntry,
MYDATASTRUCT,
ListEntry);
KdPrint(("%d\n",pData->number));
ExFreePool(pData);
}
}
3.
Lookaside結構:
避免頻繁配置及釋放記憶體,產生記憶體破碎的情況
使用前先要初始化,非分頁及分頁兩種方式
ExInitializeNPagedLookasideList (
IN PNPAGED_LOOKASIDE_LIST Lookaside,
IN PALLOCATE_FUNCTION Allocate,
IN PFREE_FUNCTION Free,
IN ULONG Flags,
IN SIZE_T Size,
IN ULONG Tag,
IN USHORT Depth
);
ExInitializePagedLookasideList (
IN PPAGED_LOOKASIDE_LIST Lookaside,
IN PALLOCATE_FUNCTION Allocate,
IN PFREE_FUNCTION Free,
IN ULONG Flags,
IN SIZE_T Size,
IN ULONG Tag,
IN USHORT Depth
);
配置記憶體
PVOID ExAllocateFromNPagedLookasideList(IN PNPAGED_LOOKASIDE_LIST);
PVOIDExAllocateFromPagedLookasideList(IN PPAGED_LOOKASIDE_LIST);
釋放記憶體
VOID ExFreeToNPagedLookasideList(IN PNPAGED_LOOKASIDE, IN PVOID);
VOID ExFreeToPagedLookasideList(IN PPAGED_LOOKASIDE, IN PVOID);
使用完需要刪除Lookaside物件
VOID ExDeleteNPagedLookasideList(IN PNPAGED_LOOKASIDE_LIST);
VOID ExDeletePagedLookasideList(IN PPAGED_LOOKASIDE_LIST);
範例:
typedef struct _MYDATASTRUCT
{
CHAR buffer[64];
} MYDATASTRUCT, *PMYDATASTRUCT;
#pragma INITCODE
VOID LookasideTest()
{
PAGED_LOOKASIDE_LIST pageList;
ExInitializePagedLookasideList(&pageList,NULL,NULL,0,sizeof(MYDATASTRUCT),'1234',0);
#define ARRAY_NUMBER 50
PMYDATASTRUCT MyObjectArray[ARRAY_NUMBER];
for (int i=0;i
MyObjectArray[i] = (PMYDATASTRUCT)ExAllocateFromPagedLookasideList(&pageList);
KdPrint(("Alloc MyObjectArray[%d]\n",i));
}
//模擬頻繁回收記憶體
for (i=0;i
KdPrint(("Free MyObjectArray[%d]\n",i));
ExFreeToPagedLookasideList(&pageList,MyObjectArray[i]);
MyObjectArray[i] = NULL;
}
ExDeletePagedLookasideList(&pageList);
//刪除Lookaside物件
}
DDK 使用VC6開發
專案名稱是 MyDriver
步驟
1.File->New->Project->Win32 Application->輸入專案名稱->An Empty project
2.將.c與.h加入到專案
3.Build->Configuration 去掉Debug,Release,增加Driver Check Edition
4.project->Setting->General中,Intermediate files與Output Files改成MyDriver_Check
5.project->Setting->C/C++->Project Options,全部刪除,改成
/nologo /Gz /MLd /W3 /WX /Z7 /Od /D WIN32=100 /D _X86_=1 /D WINVER=0x500 /D DBG=1 /Fo"MyDriver_Check/" /Fd"MyDriver_Check/" /FD /c
6.project->Setting->Link->Project Options,全部刪除,改成
ntoskrnl.lib /nologo /base:"0x10000" /stack:0x400000,0x1000 /entry:"DriverEntry" /subsystem:console /incremental:no /pdb:"DriverDev___Win32_Driver_Release_Edtion/HelloDDK.pdb" /map:"DriverDev___Win32_Driver_Release_Edtion/HelloDDK.map" /debug /machine:I386 /nodefaultlib /out:"MyDriver_Check/HelloDDK.sys" /pdbtype:sept /subsystem:native /driver /SECTION:INIT,D /RELEASE /IGNORE:4078
7.修改VC lib及Include目錄,Tool->Option->Directoies->Show Directories for:
->Include Files加入DDK路徑\INC\W2K 以及INC\DDK\W2K
->Library Files加入DDK路徑\LIB\W2K\I386
2009年10月6日 星期二
PDO與FDO
PDO如何得知上層FDO
->透過AttachedDevice 子欄位
ex:
PDEVICE_OBJECT pDevice = pDriverObject->DeviceObject;
pDevice->AttachedDevice
FDO如何得知下層的裝置
->透過裝置擴充紀錄
ex:
typedef struct _DEVICE_EXTENSION
{
PDEVICE_OBJECT fdo;
PDEVICE_OBJECT NextStackDevice;
UNICODE_STRING ustrDeviceName; // 裝置名
UNICODE_STRING ustrSymLinkName; // 符號連結名
} DEVICE_EXTENSION, *PDEVICE_EXTENSION;
PDEVICE_EXTENSION pdx = (PDEVICE_EXTENSION)fdo->DeviceExtension;
pdx->NextStackDevice = IoAttachDeviceToDeviceStack(fdo, PhysicalDeviceObject);
2009年8月13日 星期四
c#練習 - int,字串互轉
int num = 5;
string str = num.ToString();
string to int
string str= "5";
int num = int.parse(str);
2009年8月8日 星期六
希臘蜜月 - Day 6 - Imerovigli
原本導遊安排在Kamari之後,要先回去飯店休息,因為趙伯伯他們年紀比較大,
而且今天會在Oia看夕陽,怕他們體力不支,不過趙伯伯在Kamari那裡打瞌睡後,
精神就好多啦!於是乎,我們就提早前往Oia,途中會在Imerovigli拍拍照,
在途上,我也不小心瞇了一下下…醒來,已經到了Imerovigli了~
希臘的車型,跟台灣的有點不太一樣,像台灣跟泰國一大堆的Altis,
在希臘好像沒看到耶~而希臘有些車型,在台灣也是沒看到…
向下面這台Toyota的車,比Yaris還可愛耶~
附近的籃球場,
附帶一提的是希臘人很愛籃球,晚上的時候他們都在看籃球轉播,前陣子還有個新聞,
說希臘的球隊想要簽Iverson耶,可見他們對籃球的熱愛,
一口廢棄的井,小丸子很愛演… = =
附帶一提的是,Santorini的水,都是抽取地下水來淡化的,旅館的老闆都需要叫水車來加水,
光是加滿游泳池的水就要花上好幾萬塊台幣,我們洗澡的水,嘗起來確實有嫌鹹的味道
在Imerovigli主要是來看看洞穴屋,這裡有一些民宅,也有飯店,
在Santorini住洞穴屋可不便宜,可以說是高級旅館,有錢想住的話,還不簡單耶…
在旺季的時候,需要一年前就訂位,而且需要連續住上好幾個晚上,老闆才肯讓你入住…
這時候剛好是下午時刻,希臘人通常都在睡午覺,導遊要我們小聲一點,
由於地勢的關係,這一戶的陽台,可能是下一戶的屋頂,可能走著走著,就會走到別人家的屋頂,
走到上面去,映入眼簾的就是這張經典的景象,以地中海為背景,屋子以白色為基調,襯托著藍頂教堂與鐘樓…
不管是月曆或明信片,常常都會有這張照片的出沒…哈
美景當前,當然也要來個甜蜜的合照囉…當然,情侶裝也是必備的!!
一整排的建在懸崖邊的洞穴屋,形成一副特殊的景觀
這裡真的是很漂亮,找間咖啡店,跟心愛的人在這裡靜靜地坐上一個下午,
忘卻所有的煩惱、憂愁,細細品味這裡的景色,咀嚼屬於Santorini的味道,人生夫復何求呢?
近一點,再來一張~
我也要來solo一下~
眺望遠方的愛之船…
濃濃的希臘小島fu
再來這張更厲害啦…
本人犧牲色相,露出修長的美腿,歐耶~~
在這裡泡泡水,看著地中海的景色,真是一大享受阿!
另一個角度再來一張!
這是從下面往上拍的藍頂教堂&鐘樓
鐘樓
下面那張圖的海岬是可以走過去的,可是導遊說路況不好,再加上風滿大的,
所以我們就沒去了,也是明信片級的風景!
陽光灑落在十字架上,感覺滿聖潔的,好像有神蹟發生…哈哈
在這裡發生了一件小插曲…就是從Kamari到這裡路程還滿長的,
結果,到了之後一直想來個山洪爆發,可是導遊說…他之前常跟這裡的餐廳借廁所,
可是團員都沒有消費,久而久之,店家就不願意讓我們借廁所了…
慘了,大家已知道憋尿對身體不好阿,那…乾脆就回歸大自然吧!!!
找個廢墟的又隱密的地方,快樂的舒暢一下…讚啦!!!
雖然心沒有遺留在愛情海,但至少還是留下些東西在愛情海呢!
什麼東西都可以遺留在愛情海…可是把」夢遺留在愛情海」就不好啦…
(有點A,滿18歲的才可以反白看喔!科科~)
好啦,再休息一下下…下篇介紹最迷人的Oia…
敬請期待~~~
winsock2.h redefined問題
解法: #define _WINSOCKAPI_ // stops windows.h including winsock.h #include #include
-
昨天要回新竹的路上,差點A到一臺摩托車, 可以清楚看到路口是綠燈,可是這位老兄,竟然從左方過來要待轉, 旁邊的女騎士也差點A到他,尖叫了一聲... 緊急煞車的同時,第一次感受到ABS做動,還好平安無事... 奉勸大家車子一定要裝行車記錄器阿~
-
對了,要跟大家推薦一下新竹的家具行, 當初要添購家具的時候,跟小丸子很努力的找遍新竹的家具行, 新竹市的家具行其實很多,大部分集中在新竹市的經國路, 還有中華路五段這兩個部分,竹北也有不少家具行, 不過我們主要還是找新竹市的, 找來找去,發現其實家具很多都是一模一樣的,應該都...
-
一早的雅典,有點像黃昏的感覺~ 今天的早餐,在飯店裡享用,大概是這幾天來,早餐吃最好的一餐~ 由於太好吃了,我吃了好幾盤耶~還吃了一大份的提拉米蘇,讚啦!!! 先介紹一下今天的景點,主要是過去伯羅奔尼撒半島玩, 附上地圖讓大家有個概念,依序是 ...