baichunlin2005
驱动牛犊
驱动牛犊
  • 注册日期2009-04-26
  • 最后登录2012-08-20
  • 粉丝0
  • 关注0
  • 积分11分
  • 威望91点
  • 贡献值0点
  • 好评度0点
  • 原创分0分
  • 专家分0分
阅读:2592回复:2

发放内核函数库【第二篇】: 实现类似 HASHMAP / HASHTABLE / List 的效果

楼主#
更多 发布于:2010-08-06 18:09
由于程序中常常要用到 HashMap / List,我们编写了下述 KList 函数库:

#ifndef __KFunction_List__
#define __KFunction_List__
#include <fltKernel.h>

/****************************************** List 操作函数 ***************************************************/
#define KASS_LIST_TAG      'KLst'
typedef struct _KListEntry{
    PVOID Data;
    PVOID Next;
}KListEntry, *PKListEntry;
typedef struct _KList{
    NPAGED_LOOKASIDE_LIST LookasideList;
 PKListEntry First;
}KList, *PKList;


//初始化一个 KList 对象
VOID KList_Init(IN PKList list){
 ExInitializeNPagedLookasideList( &list->LookasideList, NULL, NULL, 0, sizeof(KListEntry), KASS_LIST_TAG, 0 );
 list->First = NULL;
}
//释放一个 KList 对象(自动删除其中的所有KListEntry元素) (每个KListEntry内部的资源,需要自己手动释放)
VOID KList_Free(IN PKList list){
 PKListEntry current = NULL;
 PKListEntry next = NULL;
 current = list->First;
 while(current!=NULL){  
  next = current->Next;
  current->Next = NULL;
  current->Data = NULL;
  ExFreeToNPagedLookasideList( &list->LookasideList, current );
  current = next;
 }
 ExDeleteNPagedLookasideList( &list->LookasideList );
 list->First = NULL;
}
//插入一个元素到 KList 中去 (该元素所占用的相关内存资源要是非分页内存)
VOID KList_Add(IN PKList list, IN PVOID object){
 PKListEntry entry;
 PKListEntry last;
 entry = ExAllocateFromNPagedLookasideList( &list->LookasideList );
 entry->Data = object;
 entry->Next = NULL;
 if(list->First==NULL){
  list->First = entry;
 }else{
  last = list->First;
  while(last->Next!=NULL){
   last = last->Next;
  }
  last->Next = entry;
 }
}
//得到 KList 的元素个数
int KList_Size(IN PKList list){
 int count = 0;
 PKListEntry tmp;
 
 tmp = list->First;
 while(tmp!=NULL){
  tmp = tmp->Next;
  count ++;
 }
 return count;
}
//得到 KList 中的第index个元素值
PVOID KList_Get(IN PKList list, int index){
 int i = 0;
 PKListEntry entry = NULL;
 PVOID data = NULL;
 
 if(index==0){
  entry = list->First;
 }else if(index<0){
  entry = NULL;
 }else{
  entry = list->First;
  while(entry!=NULL){
   if(i==index){
    break;
   }
   entry = entry->Next;
   i++;
  }
  if(i!=index){
   entry = NULL;
  }
 }
 if(entry!=NULL){
  data = entry->Data;
 }
 return data;
}
//从 KList 中移除一个元素
VOID KList_Remove(IN PKList list, IN int index){
 int i = 0;
 PKListEntry previous = NULL;
 PKListEntry current = NULL;
 int size;
 
 size = KList_Size(list);
 if(index<0 || index>=size){
  return;
 }else if(index==0){
  current = list->First;
  previous = NULL;
 }else{
  current = list->First;
  while(current!=NULL){
   if(i==index){
    break;
   }
   previous = current;
   current = current->Next;
   i++;
  }
 }
 if(index==0){
  list->First = current->Next;
 }else{
  previous->Next = current->Next;
 }
 current->Next = NULL;
 current->Data = NULL;
 ExFreeToNPagedLookasideList( &list->LookasideList, current );
}

#endif


----------------------------------------------------------------------------------------------------------
使用方法:

typedef struct _GlobalList_Entry{    //List 结构体
    UNICODE_STRING  FilePath;        
    int ProcessId;            
    BOOLEAN Flag;    
}GlobalList_Entry, *PGlobalList_Entry;
KList GlobalList;            //List 全局变量


//沙盘相关全局变量的初始化
VOID test(){
    int size = 0;
    int i;
    PGlobalList_Entry  pEentry;
    
    //初始化 List
    KList_Init(&GlobalList);

    //插入一个元素到 List 中:
    pEentry = (PGlobalList_Entry)ExAllocate(NonPagedPool, sizeof(GlobalList_Entry));
    pEentry->ProcessId = 0;
    pEentry->Flag = TRUE;
    KStr_Init(&pEentry->FilePath, 100);
    //TODO 给 pEentry->FilePath 赋值
    KList_Add(&GlobalList, pEentry);

    //遍历 List:
    size = KList_Size(&GlobalList);
    if( size>0 ){
        for(i=0; i<size; i++){
            pEentry- = (PGlobalList_Entry)KList_Get(&GlobalList, i);
            if(pEentry-!=NULL){
                DbgPrint("ProcessId=%d\n", pEentry->ProcessId);
            }
        }
    }

    //释放资源:
    size = KList_Size(&GlobalList);
    if( size>0 ){
        for(i=0; i<size; i++){
            pEentry- = (PGlobalList_Entry)KList_Get(&GlobalList, i);
            if(pEentry-!=NULL){
                KStr_Free(pEentry->FilePath);
                ExFreePool(pEentry);
            }
        }
    }
    KList_Free(&GlobalList);
}
wanghui219
禁止发言
禁止发言
  • 注册日期2007-08-28
  • 最后登录2019-07-29
  • 粉丝4
  • 关注3
  • 积分101166分
  • 威望505351点
  • 贡献值0点
  • 好评度137点
  • 原创分0分
  • 专家分4分
  • 社区居民
沙发#
发布于:2010-08-07 08:35
用户被禁言,该主题自动屏蔽!
wzqqwz
驱动牛犊
驱动牛犊
  • 注册日期2009-12-15
  • 最后登录2012-08-02
  • 粉丝0
  • 关注0
  • 积分2分
  • 威望21点
  • 贡献值0点
  • 好评度0点
  • 原创分0分
  • 专家分0分
板凳#
发布于:2012-04-14 22:47
好东东啊.正找这个呢
游客

返回顶部