dbc23b8ff590619266c1afb3cf0c3b0148140358
[barrelfish] / include / barrelfish / slot_alloc.h
1 /**
2  * \file
3  * \brief Slot allocator
4  */
5
6 /*
7  * Copyright (c) 2010, ETH Zurich.
8  * All rights reserved.
9  *
10  * This file is distributed under the terms in the attached LICENSE file.
11  * If you do not find this file, copies can be found by writing to:
12  * ETH Zurich D-INFK, Haldeneggsteig 4, CH-8092 Zurich. Attn: Systems Group.
13  */
14
15 #ifndef SLOT_ALLOC_H
16 #define SLOT_ALLOC_H
17
18 #include <sys/cdefs.h>
19
20 #include <barrelfish/threads.h>
21 #include <barrelfish/slab.h>
22 #include <barrelfish/vspace_common.h>
23
24 __BEGIN_DECLS
25
26 struct slot_allocator {
27     errval_t (*alloc)(struct slot_allocator *ca, struct capref *cap);
28     errval_t (*free)(struct slot_allocator *ca, struct capref cap);
29     struct thread_mutex mutex;     ///< Mutex for thread safety
30     cslot_t nslots;                ///< Slots to grow allocator by
31     cslot_t space;                 ///< Space left in the allocator
32 };
33
34 /// Meta data for single_slot_allocator
35 struct cnode_meta {
36     cslot_t slot;
37     cslot_t space;
38     struct cnode_meta *next;
39 };
40
41 struct single_slot_allocator {
42     struct slot_allocator a;    ///< Public data
43     struct capref cap;          ///< Cap of the cnode the allocator is tracking
44     struct cnoderef cnode;      ///< Cnode the allocator is tracking
45     struct cnode_meta *head;    ///< Linked list of free slots
46     struct slab_allocator slab;     ///< Slab for backing the list
47 };
48
49 struct slot_allocator_list {
50     struct single_slot_allocator a;
51     struct slot_allocator_list *next;
52 };
53
54 struct multi_slot_allocator {
55     struct slot_allocator a;      ///< Public data
56
57     struct slot_allocator *top;   ///< Top level of the two level allocator
58     struct slot_allocator_list *head; ///< List of single slot allocators
59     struct slot_allocator_list *reserve; ///< One single allocator in reserve
60
61     struct slab_allocator slab;      ///< Slab backing the slot_allocator_list
62
63     struct vspace_mmu_aware mmu_state;
64 };
65
66 struct range_slot_allocator {
67     struct capref cnode_cap;     ///< capref for the L1 cnode
68     cslot_t rootcn_slot;         ///< L1 slot of L2 cnode in this allocator
69     struct cnoderef cnode;       ///< cnoderef for the cnode to allocate from
70     struct cnode_meta *meta;     ///< Linked list of meta data
71     struct slab_allocator slab;      ///< Slab allocation
72     struct thread_mutex mutex;   ///< Mutex for thread safety (used when is_head == true)
73     struct range_slot_allocator *next; ///< Next slot allocator
74     bool is_head; ///< Is this instance head of a chain
75 };
76
77 // single_slot_alloc_init_raw() requires a specific buflen
78 #define SINGLE_SLOT_ALLOC_BUFLEN(nslots) \
79     (SLAB_STATIC_SIZE(nslots / 2, sizeof(struct cnode_meta)))
80
81 errval_t single_slot_alloc_init(struct single_slot_allocator *ret,
82                                 cslot_t nslots, cslot_t *retslots);
83 errval_t single_slot_alloc_init_raw(struct single_slot_allocator *ret,
84                                     struct capref cap, struct cnoderef cnode,
85                                     cslot_t nslots, void *buf, size_t buflen);
86
87 errval_t multi_slot_alloc_init(struct multi_slot_allocator *ret,
88                                cslot_t nslots, cslot_t *retslots);
89 errval_t multi_slot_alloc_init_raw(struct multi_slot_allocator *ret,
90                                    cslot_t nslots, struct capref top_cap,
91                                    struct cnoderef top_cnode,
92                                    void *top_buf, void *head_buf,
93                                    void *reserve_buf, size_t bufsize);
94
95 errval_t two_level_slot_alloc_init(struct multi_slot_allocator *ret,
96                                    cslot_t nslots, cslot_t *retslots);
97 errval_t two_level_slot_alloc_init_raw(struct multi_slot_allocator *ret,
98                                        cslot_t nslots, struct capref top_cap,
99                                        struct cnoderef top_cnode,
100                                        void *top_buf, void *head_buf,
101                                        void *reserve_buf, size_t bufsize);
102
103 errval_t slot_alloc_init(void);
104 errval_t slot_alloc_init_2(void);
105 struct slot_allocator *get_default_slot_allocator(void);
106 errval_t slot_alloc(struct capref *ret);
107 errval_t slot_alloc_root(struct capref *ret);
108 errval_t slot_free(struct capref ret);
109
110 errval_t range_slot_alloc(struct range_slot_allocator *alloc, cslot_t nslots,
111                           struct capref *ret);
112 errval_t range_slot_free(struct range_slot_allocator *alloc, struct capref cap,
113                          cslot_t nslots);
114 errval_t range_slot_alloc_init(struct range_slot_allocator *ret,
115                                cslot_t nslots, cslot_t *retslots);
116 size_t range_slot_alloc_freecount(struct range_slot_allocator *alloc);
117 errval_t range_slot_alloc_refill(struct range_slot_allocator *alloc, cslot_t slots);
118
119 __END_DECLS
120
121 #endif // SLOT_ALLOC_H