reduce the size of ppage by 8 bytes using signly linked list nov/revmap
authorLunaixsky <lunaixsky@qq.com>
Sat, 8 Feb 2025 05:14:38 +0000 (05:14 +0000)
committerLunaixsky <lunaixsky@qq.com>
Sat, 8 Feb 2025 05:14:38 +0000 (05:14 +0000)
lunaix-os/includes/lunaix/ds/list.h
lunaix-os/includes/lunaix/mm/physical.h
lunaix-os/includes/lunaix/mm/pmm.h
lunaix-os/kernel/mm/pmalloc_simple.c

index 288ee66c2ba79efa4b8655a3c31f1362f77d9696..e4ab34475032719892af92e8ff21d7e9000bfc23 100644 (file)
@@ -33,7 +33,7 @@ list_head_init(struct list_head *list)
 static inline void 
 list_node_init(struct list_node *node)
 {
 static inline void 
 list_node_init(struct list_node *node)
 {
-       node->next = node;
+       node->next = NULL;
 }
 
 #define slist_entry(ptr, type, member)         \
 }
 
 #define slist_entry(ptr, type, member)         \
@@ -58,10 +58,31 @@ __llist_add_batch(struct list_node *new_first,
        return new_last->next == NULL;
 }
 
        return new_last->next == NULL;
 }
 
+static inline bool
+list_empty(struct list_head* head)
+{
+       return !head->first;
+}
+
 static inline void
 list_add(struct list_head* head, struct list_node* node)
 {
        __llist_add_batch(node, node, head);
 }
 
 static inline void
 list_add(struct list_head* head, struct list_node* node)
 {
        __llist_add_batch(node, node, head);
 }
 
+static inline struct list_node*
+list_pop_head(struct list_head* head) {
+       struct list_node* node;
+
+       if (list_empty(head)) {
+               return NULL;
+       }
+
+       node = head->first;
+       head->first = node->next;
+
+       list_node_init(node);
+       return node;
+}
+
 #endif /* __LUNAIX_LIST_H */
 #endif /* __LUNAIX_LIST_H */
index e1710bf691e45a67b8ec7a55b579cad9c866779d..bb15e6cf5008cea076810cccf437aef8cc533daf 100644 (file)
@@ -3,6 +3,7 @@
 
 #include <lunaix/compiler.h>
 #include <asm/physical.h>
 
 #include <lunaix/compiler.h>
 #include <asm/physical.h>
+#include <lunaix/ds/list.h>
 
 /**
  * @brief 长久页:不会被缓存,但允许释放
 
 /**
  * @brief 长久页:不会被缓存,但允许释放
@@ -45,7 +46,7 @@ struct ppage
     };
     unsigned short companion;
     
     };
     unsigned short companion;
     
-    struct llist_header sibs;
+    struct list_node sibs;
 
     struct ppage_arch arch;
 } align(16);
 
     struct ppage_arch arch;
 } align(16);
index bd55eb1e46435d4140a03318d496696b75a06cbf..c0e08b28ab16467adddb198e4f521be833537b04 100644 (file)
@@ -36,7 +36,7 @@ struct pmem_pool
     
 #elif defined(CONFIG_PMALLOC_METHOD_SIMPLE)
 
     
 #elif defined(CONFIG_PMALLOC_METHOD_SIMPLE)
 
-    struct llist_header idle_order[MAX_PAGE_ORDERS];
+    struct list_head idle_order[MAX_PAGE_ORDERS];
     int count[MAX_PAGE_ORDERS];
 
 #endif
     int count[MAX_PAGE_ORDERS];
 
 #endif
index 93fae04fb55945a401ddb20924bda961854757ea..2cfcde361da782b8ed3f0f3be0f19a1d1faf3f8a 100644 (file)
@@ -27,13 +27,13 @@ __uninitialized_page(struct ppage* page)
 }
 
 static inline void
 }
 
 static inline void
-__set_page_initialized(struct ppage* page)
+__init_page(struct ppage* page)
 {
     page->flags |= INIT_FLAG;
 }
 
 static inline void
 {
     page->flags |= INIT_FLAG;
 }
 
 static inline void
-__set_pages_uninitialized(struct ppage* lead)
+__deinit_page(struct ppage* lead)
 {
     for (size_t i = 0; i < (1UL << lead->order); i++)
     {
 {
     for (size_t i = 0; i < (1UL << lead->order); i++)
     {
@@ -51,7 +51,7 @@ void
 pmm_allocator_init_pool(struct pmem_pool* pool)
 {
     for (int i = 0; i < MAX_PAGE_ORDERS; i++) {
 pmm_allocator_init_pool(struct pmem_pool* pool)
 {
     for (int i = 0; i < MAX_PAGE_ORDERS; i++) {
-        llist_init_head(&pool->idle_order[i]);
+        list_head_init(&pool->idle_order[i]);
         pool->count[i] = 0;
     }
 
         pool->count[i] = 0;
     }
 
@@ -78,15 +78,15 @@ pmm_free_one(struct ppage* page, int type_mask)
     assert(order <= MAX_PAGE_ORDERS);
 
     struct pmem_pool* pool = pmm_pool_lookup(page);
     assert(order <= MAX_PAGE_ORDERS);
 
     struct pmem_pool* pool = pmm_pool_lookup(page);
-    struct llist_header* bucket = &pool->idle_order[order];
+    struct list_head* bucket = &pool->idle_order[order];
 
     if (pool->count[order] < po_limit[order]) {
 
     if (pool->count[order] < po_limit[order]) {
-        llist_append(bucket, &page->sibs);
-        pool->count[order]++;
+        list_add(bucket, &page->sibs);
+        pool->count[order] += 1;
         return;
     }
 
         return;
     }
 
-    __set_pages_uninitialized(page);
+    __deinit_page(page);
 }
 
 static pfn_t index = 0;
 }
 
 static pfn_t index = 0;
@@ -128,28 +128,42 @@ pmm_looknext(struct pmem_pool* pool, size_t order)
         page->companion = i;
         page->pool = pool->type;
         page->refs = 0;
         page->companion = i;
         page->pool = pool->type;
         page->refs = 0;
-        llist_init_head(&page->sibs);
-        __set_page_initialized(page);
+        list_node_init(&page->sibs);
+        __init_page(page);
     }
 
     return lead;
 }
 
     }
 
     return lead;
 }
 
+static struct ppage*
+__select_free_page_from(struct list_head* bucket)
+{
+    struct list_node* sib;
+    struct ppage* page;
+
+    do {
+        sib = list_pop_head(bucket);
+        page = sib ? slist_entry(sib, struct ppage, sibs) : NULL;
+    } while (page && __uninitialized_page(page));
+
+    return page;
+}
+
 struct ppage*
 pmm_alloc_napot_type(int pool, size_t order, ppage_type_t type)
 {
     assert(order <= MAX_PAGE_ORDERS);
 
     struct pmem_pool* _pool = pmm_pool_get(pool);
 struct ppage*
 pmm_alloc_napot_type(int pool, size_t order, ppage_type_t type)
 {
     assert(order <= MAX_PAGE_ORDERS);
 
     struct pmem_pool* _pool = pmm_pool_get(pool);
-    struct llist_header* bucket = &_pool->idle_order[order];
-
+    struct list_head* bucket = &_pool->idle_order[order];
     struct ppage* good_page = NULL;
     struct ppage* good_page = NULL;
-    if (!llist_empty(bucket)) {
-        (_pool->count[order])--;
-        good_page = list_entry(bucket->next, struct ppage, sibs);
-        llist_delete(&good_page->sibs);
+
+    if (!list_empty(bucket)) {
+        _pool->count[order] -= 1;
+        good_page = __select_free_page_from(bucket);
     }
     }
-    else {
+    
+    if (!good_page) {
         good_page = pmm_looknext(_pool, order);
     }
 
         good_page = pmm_looknext(_pool, order);
     }
 
@@ -169,14 +183,10 @@ pmm_allocator_trymark_onhold(struct pmem_pool* pool,
     while (start <= end) {
         if (__uninitialized_page(start)) {
             set_reserved(start);
     while (start <= end) {
         if (__uninitialized_page(start)) {
             set_reserved(start);
-            __set_page_initialized(start);
+            __init_page(start);
         }
         else if (!start->refs) {
         }
         else if (!start->refs) {
-            struct ppage* lead = leading_page(start);
-            llist_delete(&lead->sibs);
-
-            __set_pages_uninitialized(lead);
-            
+            __deinit_page(leading_page(start));
             continue;
         }
         else if (!reserved_page(start)) {
             continue;
         }
         else if (!reserved_page(start)) {
@@ -195,7 +205,7 @@ pmm_allocator_trymark_unhold(struct pmem_pool* pool,
 {
     while (start <= end) {
         if (!__uninitialized_page(start) && reserved_page(start)) {
 {
     while (start <= end) {
         if (!__uninitialized_page(start) && reserved_page(start)) {
-            __set_pages_uninitialized(start);
+            __deinit_page(start);
         }
 
         start++;
         }
 
         start++;