LIST_ENTRY
HASH表
TREE树
LookAside结构
1.LIST_ENTRY
typedef _struct _MYDATA_LIST
{
LIST_ENTRY Entry;
WCHAR NameBuffer[MAX_PATH];
} MYDATA_LIST_ENTRY,
*PMYDATA_LIST_ENTRY;
PLIST_ENTRY pListHead;//头指针
typedef struct _LIST_ENTRY
{
struct _LIST_ENTRY *Flink;
struct _LIST_ENTRY *Blink;
} LIST_ENTRY,*PLIST_ENTRY;
PMYDATA_LIST_ENTRY dataEntry = CONTAINING_RECORD(pList, MYDATA_LIST_ENTRY, Entry);
dataEntry->wszFileName
#define CONTAINING_RECORD(address, type, field) ((type *)( \
(PCHAR)(address) - \
(ULONG_PTR)(&((type *)0)->field)))
LIST_ENTRY使用方法
LIST_ENTRY listHead;//头指针
PMYDATA_LIST_ENTRY tmpEntry;//结点,须自己初始化值
InitializeListHead(&listHead);//初始化
InsertHeadList(&listHead, &tmpEntry->Entry); //结点头插入
InsertTailList(&listHead, &tmpEntry->Entry); //结点尾插入
IsListEmpty(&listHead);//判断是否为空链表
PLIST_ENTRY listEntry = RemoveHeadList(&listHead);//移除
PLIST_ENTRY listEntry = RemoveTailList(&listHead);//移除
//枚举
PLIST_ENTRY plistHead = &listHead;
PLIST_ENTRY pList = NULL;
PMYDATA_LIST_ENTRY dataEntry = NULL;
For(pList = plistHead ->Flink; pList != plistHead; pList = pList->Flink)
{
dataEntry = CONTAINING_RECORD(pList,
MYDATA_LIST_ENTRY, Entry);
DbgPrint(“%S\n”, dataEntry->NameBuffer);
}
RemoveEntryList(&dataEntry->Entry);
while(!IsListEmpty(&listHead))
{
listEntry = RemoveHeadList(&listHead);
dataEntry = CONTAINING_RECORD(
listEntry,
SBPROCESS_ENTRY,
Entry
);
DbgPrint(“%ws\n”, dataEntry->NameBuffer);
RemoveEntryList(listEntry);//删除接点
ExFreePool(dataEntry);
}
2.HASH表
typedef struct _ELEMENT
{
int x;
} ELEMENT, *PELEMENT;
typedef struct _HNODE
{
DWORD key;
ELEMENT data;
LIST_ENTRY linkfield;
} HNODE, *PHNODE;
typedef struct _HASHTABLE
{
unsigned int tableSize;
PLIST_ENTRY *pListHeads;
} HASHTABLE, *PHASHTABLE;
PHASHTABLE InitializeTable(unsigned int tableSize);
PTWOWAY Find(DWORD key,
PHASHTABLE pHashTable)
void Insert(DWORD key, PELEMENT pData,
PHASHTABLE pHashTable);
void Remove(DWORD key,
PHASHTABLE pHashTable);
void DestroyTable(PHASHTABLE pHashTable);
ULONG DumpTable(PHASHTABLE pHashTable);
3.平衡树
如果HASH还是无法满足需要,怎么办?
WRK里面的:AvlTable.c
RTL_AVL_TABLE g_FileNameTable;
RtlInitializeGenericTableAvl(
&g_FileNameTable,
CompareNameFunc,
AllocateFunc,
FreeFunc,
NULL);
ExAcquireFastMutex(&g_FileNameTableMutex);
RtlInsertElementGenericTableAvl(&g_FileNameTable, &Key, sizeof(FILE_NAME_ENTRY), NULL);
ExReleaseFastMutex(&g_FileNameTableMutex);
LookAside结构
频繁的内存分配产生空洞和碎片
频繁分配固定大小内存
LookAside类别
PAGED_LOOKASIDE_LIST
NPAGED_LOOKASIDE_LIST
PAGED_LOOKASIDE_LIST g_pageList;
ExInitializePagedLookasideList(
&g_pageList,
NULL,
NULL,
0,
sizeof(MYDATA),
‘HSAH',
0);
MYDATA * pMyData = (MYDATA*)
ExAllocateFromPagedLookasideList(
&g_pageList);
ExFreeToPagedLookasideList(
&g_pageList,
pMyData);
ExDeletePagedLookasideList(&g_pageList);