2013-04-02 37 views
3

我很難從Linux內核使用list.h爲我的代碼提供鏈表功能。我懷疑我幾乎有功能代碼,但我在某處混合了指針。如何正確使用list.h中的list_for_each宏(來自Linux內核)?

如何正確使用list_for_each宏?在我的代碼中,它陷入了一個無限循環,並沒有退出列表。下面是我的代碼片段,其中問題在於(在add_kv函數查找):

dict_entry *alloc_dict(void) 
{ 
    //allocates the linked list head node 
    dict_entry *d = malloc(sizeof(dict_entry)); 
    INIT_LIST_HEAD(&d->list); 
    return d; 
} 

void free_dict(dict_entry *d) 
{ 
    //TODO: free each dict_entry struct and their keys and values. 
    free(d); 
} 

int add_kv(dict_entry *d, char *key, char *value) 
{ 
    if(!key || !d) return 0; //if key or d is null, return 0 

    struct list_head *p; //serves as the cursor 
    dict_entry *entry; //empty dict_entry 
    entry = alloc_dict(); //allocate memory for it 

    list_for_each(p, &d->list){ 
     d = list_entry(p, dict_entry, list); //CHANGED TO d FROM entry 
     printf("gothere, p = %p\n",p); // something in here is creating an infinite loop. p is moving back and forth. this is the big problem in this code 
     if(strcmp(entry->key, key) == 0){ 
      free(entry->value); 
      entry->value = 0; 
      entry->value = malloc(strlen(value)); 
      strcpy(entry->value, value); 
      return 1; //how do i get rid of entry? 
     } 
    } 
    //If you haven't returned by now, continue on to add a new entry at the end of the list 
    entry->key = malloc(strlen(key)); //allocate memory for the key 
    strcpy(entry->key, key); //copy the key value to the key in the entry 
    entry->value = malloc(strlen(value)); //allocate memory for value 
    strcpy(entry->value, value); //copy value value to the value in the entry 

    list_add(&entry->list,&d->list); //tacks the list of the new entry onto the existing list (provided as d) 
    return 1; 
} 

下面是從list.h的list_for_each宏,以供參考:

/** 
* list_for_each - iterate over a list 
* @pos: the &struct list_head to use as a loop cursor. 
* @head: the head for your list. 
*/ 
#define list_for_each(pos, head) \ 
    for (pos = (head)->next; pos != (head); pos = pos->next) 

,這裏是從list.h的LIST_ENTRY宏,也供參考:

/** 
* list_entry - get the struct for this entry 
* @ptr: the &struct list_head pointer. 
* @type: the type of the struct this is embedded in. 
* @member: the name of the list_struct within the struct. 
*/ 
#define list_entry(ptr, type, member) \ 
    container_of(ptr, type, member) 

...和我使用的dict_entry結構:

6 typedef struct { 
    7 char *key; 
    8 char *value; 
    9 struct list_head list; 
10 }dict_entry; 

...並運行時,出現這種情況:

gothere, p = 0x1178050 
gothere, p = 0x1178020 
gothere, p = 0x1178050 
gothere, p = 0x1178020 

一遍又一遍。

關於如何用list.h實現列表的一個很好的解釋可以參見here

+0

如何定義'dict_entry'? –

回答

4

由於某種原因,您正在重新分配變量d,並且這會中斷list_for_each宏。

你有這樣的代碼:

list_for_each(p, &d->list){ 
    d = list_entry(p, dict_entry, list); 

宏在每次迭代重新評估&d->list看到到達列表結束的時候。由於d被重新分配,所以此檢查失敗並且永久循環。

+0

之前,該代碼是更sane-它使用的是: 'list_for_each(P,D->列表){ 條目= LIST_ENTRY(P,dict_entry,列表)' 但是我改變了它在恐慌到重新分配d,因爲它只是反覆打印一個地址 - 無限循環仍然會發生。所以,我編輯了代碼來不再重新分配d,並且我仍然對循環宏有問題。 – DEED

+0

我想在這裏你應該使用'list_for_each_entry()' – SaveTheRbtz