Merge branch 'master' into prog-loader
[lunaix-os.git] / lunaix-os / kernel / mm / region.c
1 #include <lunaix/mm/region.h>
2 #include <lunaix/mm/valloc.h>
3
4 struct mm_region*
5 region_add(struct llist_header* lead,
6            unsigned long start,
7            unsigned long end,
8            unsigned int attr)
9 {
10     struct mm_region* region = valloc(sizeof(struct mm_region));
11
12     *region = (struct mm_region){ .attr = attr, .end = end, .start = start };
13
14     if (llist_empty(lead)) {
15         llist_append(lead, &region->head);
16         return region;
17     }
18
19     struct mm_region *pos, *n;
20     llist_for_each(pos, n, lead, head)
21     {
22         if (start >= pos->end && end <= n->start) {
23             break;
24         }
25     }
26
27     llist_insert_after(&pos->head, &region->head);
28     return region;
29 }
30
31 void
32 region_release_all(struct llist_header* lead)
33 {
34     struct mm_region *pos, *n;
35
36     llist_for_each(pos, n, lead, head)
37     {
38         vfree(pos);
39     }
40 }
41
42 void
43 region_copy(struct llist_header* src, struct llist_header* dest)
44 {
45     if (!src) {
46         return;
47     }
48
49     struct mm_region *pos, *n;
50
51     llist_for_each(pos, n, src, head)
52     {
53         region_add(dest, pos->start, pos->end, pos->attr);
54     }
55 }
56
57 struct mm_region*
58 region_get(struct llist_header* lead, unsigned long vaddr)
59 {
60     if (llist_empty(lead)) {
61         return NULL;
62     }
63
64     struct mm_region *pos, *n;
65
66     llist_for_each(pos, n, lead, head)
67     {
68         if (pos->start <= vaddr && vaddr < pos->end) {
69             return pos;
70         }
71     }
72     return NULL;
73 }