get_hash_entry

来源:互联网 发布:金融数据挖掘python 编辑:程序博客网 时间:2024/06/03 23:48

函数意思是返回一个HASHELEMENT指针,HASHBUCKET是一个Element指针的宏定义。

  1. 首先判断现有的freelist中是否有可用的Element,如果有,进入4,否则进入2
  2. 如果现有的freelist中没有,就试图扩展freelist,如果无法扩展就进入3
  3. 循环查找现有的freelist(32取模),如果找到了就返回该Element,如果找不到就返回NULL
  4. 如果有可用的就找到并返回该Element,nentries加1。
typedef HASHELEMENT* HASHBUCKET;
/* create a new entry if possible */static HASHBUCKET get_hash_entry(HTAB *hashp, int freelist_idx){    HASHHDR *hctl = hashp->hctl;    HASHBUCKET newElement;    int borrow_from_idx;    for (;;)    {        ……        /* 试图获取Element */        newElement = hctl->freeList[freelist_idx].freeList;        //判断,如果newElement指向的链表不为空,则跳出循环,获取需要的值        if (newElement != NULL)            break;        /* 如果没有链表就尝试创建一个链表,element_alloc是创建链表的函数*/        if (!element_alloc(hashp, hctl->nelem_alloc, freelist_idx))        {        /*如果创建失败后进入函数内部,再已有的freelist中循环查找*/            if (!IS_PARTITIONED(hctl))                return NULL;    /* out of memory */            borrow_from_idx = freelist_idx;            for (;;)            {                /*进行循环查找,每次borrow增加1*/                borrow_from_idx = (borrow_from_idx + 1) % NUM_FREELISTS;                /* 如果找了一圈还没有找到就跳出循环 */                if (borrow_from_idx == freelist_idx)                    break;                SpinLockAcquire(&(hctl->freeList[borrow_from_idx].mutex));                newElement = hctl->freeList[borrow_from_idx].freeList;            /*如果能够找到就获取跳出循环*/                if (newElement != NULL)                {                    hctl->freeList[borrow_from_idx].freeList = newElement->link;                    SpinLockRelease(&(hctl->freeList[borrow_from_idx].mutex));                    SpinLockAcquire(&hctl->freeList[freelist_idx].mutex);                    hctl->freeList[freelist_idx].nentries++;                    SpinLockRelease(&hctl->freeList[freelist_idx].mutex);                    break;                }                SpinLockRelease(&(hctl->freeList[borrow_from_idx].mutex));            }            /*返回得到的Element*/            return newElement;        }    }    /* remove entry from freelist, bump nentries */    hctl->freeList[freelist_idx].freeList = newElement->link;    hctl->freeList[freelist_idx].nentries++;    if (IS_PARTITIONED(hctl))        SpinLockRelease(&hctl->freeList[freelist_idx].mutex);    return newElement;}

这里写图片描述

1 0
原创粉丝点击