c / expert
Snippet
Intrusive Linked Lists using offsetof and container_of
Intrusive linked lists embed node pointers directly inside payload structures rather than wrapping payload pointers inside list nodes. The `container_of` macro uses `offsetof` from `<stddef.h>` to perform pointer arithmetic, casting the node address to a byte pointer and subtracting the structure member offset to recover the enclosing parent structure pointer with zero heap memory allocations.
snippet.c
c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
#include <stdio.h>#include <stddef.h>#define container_of(ptr, type, member) \((type *)((char *)(ptr) - offsetof(type, member)))struct list_node {struct list_node *next;};struct task {int priority;const char *name;struct list_node node;};int main(void) {struct task t1 = { .priority = 1, .name = "Cleanup", .node = { NULL } };struct list_node *node_ptr = &t1.node;struct task *recovered_task = container_of(node_ptr, struct task, node);printf("Task Name: %s, Priority: %d\n", recovered_task->name, recovered_task->priority);return 0;}
Breakdown
1
#define container_of(ptr, type, member) \
Defines macro for calculating enclosing parent struct pointer from member address.
2
((type *)((char *)(ptr) - offsetof(type, member)))
Casts member pointer to byte char pointer and subtracts byte offset of member within type.
3
struct task *recovered_task = container_of(node_ptr, struct task, node);
Invokes macro to retrieve containing struct task memory address from embedded node address.