Marco Gerards wrote: > If I knew a better way, I would have used it. I think the > alternatives will all end up in either code duplication or a loss of > type safety that now is at least present through warnings. But please > understand that you only have to use the macros, not change them :-) > > Suggestions are welcome.
Hi, Well... How about something like this? It only requires one cast and no macros at all. Thanks, Vesa Jääskeläinen
#include <stdio.h> #include <stdlib.h> #include <string.h> typedef struct grub_list { struct grub_list *next; } grub_list_t; typedef struct { /* Has to be first */ grub_list_t entry; /* Just some data */ char name[32]; } grub_fs_t; void grub_list_add(grub_list_t **list, grub_list_t *item) { item->next = *list; *list = item; } void grub_list_remove(grub_list_t **list, grub_list_t *item) { grub_list_t *prev = 0; grub_list_t *tmp = *list; while (tmp) { if (tmp == item) { if (! prev) { *list = tmp->next; tmp->next = 0; return; } else { prev->next = tmp->next; tmp->next = 0; return; } } prev = tmp; tmp = tmp->next; } } int grub_list_iterate(grub_list_t *list, int (*hook) (const grub_list_t *item)) { while (list) { if (hook(list)) return 1; list = list->next; } return 0; } int grub_fs_print (const grub_list_t *list_item) { grub_fs_t *item = (grub_fs_t *)list_item; printf("'%s'\n", item->name); return 0; } int main() { grub_fs_t item1; grub_fs_t item2; grub_fs_t item3; grub_list_t *fs_list = 0; memset(&item1, 0, sizeof(item1)); memset(&item2, 0, sizeof(item2)); memset(&item3, 0, sizeof(item3)); strcpy(item1.name, "item 1"); strcpy(item2.name, "item 2"); strcpy(item3.name, "item 3"); grub_list_add(&fs_list, &item1.entry); grub_list_add(&fs_list, &item2.entry); grub_list_add(&fs_list, &item3.entry); printf("---\n"); grub_list_iterate(fs_list, grub_fs_print); printf("---\n"); grub_list_remove(&fs_list, &item2.entry); grub_list_iterate(fs_list, grub_fs_print); printf("---\n"); grub_list_remove(&fs_list, &item2.entry); grub_list_iterate(fs_list, grub_fs_print); printf("---\n"); grub_list_remove(&fs_list, &item1.entry); grub_list_iterate(fs_list, grub_fs_print); printf("---\n"); grub_list_remove(&fs_list, &item3.entry); grub_list_iterate(fs_list, grub_fs_print); printf("---\n"); grub_list_remove(&fs_list, &item3.entry); grub_list_iterate(fs_list, grub_fs_print); printf("---\n"); return 0; }
_______________________________________________ Grub-devel mailing list Grub-devel@gnu.org http://lists.gnu.org/mailman/listinfo/grub-devel