| 1 | /* Implements `movealloc`. |
| 2 | * |
| 3 | * this feature allows us to take a given virtual pointer, and copy |
| 4 | * its pages over to pages in the correct domain, and change the |
| 5 | * page tables to point to these correct pages. this is a form |
| 6 | * of "mini page migration" that we use to move over initial |
| 7 | * allocations to the right node. this lives entirely separate |
| 8 | * from our real page migration */ |
| 9 | #pragma once |
| 10 | #include <compiler.h> |
| 11 | #include <container_of.h> |
| 12 | #include <linker/symbols.h> |
| 13 | #include <mem/vmm.h> |
| 14 | #include <structures/list.h> |
| 15 | |
| 16 | /* this will always panic upon alloc failure - only to be used in init code! */ |
| 17 | void movealloc_internal(size_t domain, void *ptr, enum vmm_flags vf); |
| 18 | |
| 19 | /* movealloc(domain, ptr[, vf]) - vf defaults to VMM_FLAG_NONE */ |
| 20 | #define movealloc_2(d, p) movealloc_internal((d), (p), VMM_FLAG_NONE) |
| 21 | #define movealloc_3(d, p, vf) movealloc_internal((d), (p), (vf)) |
| 22 | #define movealloc(...) _DISPATCH(movealloc, PP_NARG(__VA_ARGS__))(__VA_ARGS__) |
| 23 | |
| 24 | typedef void (*movealloc_callback)(void *a, void *b); |
| 25 | |
| 26 | struct movealloc_callback_node { |
| 27 | movealloc_callback callback; |
| 28 | void *a, *b; |
| 29 | struct list_head list; |
| 30 | }; |
| 31 | |
| 32 | struct movealloc_callback_chain { |
| 33 | struct list_head list; |
| 34 | }; |
| 35 | |
| 36 | #define movealloc_callback_node_from_list_node(ln) \ |
| 37 | (container_of(ln, struct movealloc_callback_node, list)) |
| 38 | |
| 39 | #define MOVEALLOC_REGISTER_CALL(name, callback, param1, param2) \ |
| 40 | static LINKER_SECTION_OBJECT(struct movealloc_callback_node, \ |
| 41 | movealloc_callbacks) \ |
| 42 | movealloc_##name = {callback, param1, param2, .list = {0}}; |
| 43 | |
| 44 | void movealloc_exec_all(void); |
| 45 | |