X-Git-Url: https://scm.lunaixsky.com/lunaix-os.git/blobdiff_plain/cd09c4b222e4ddf45a42522563ae2471a829d1c8..69777bdcab284335651a8002e2896f3862fa423d:/lunaix-os/includes/lunaix/mm/pmm.h diff --git a/lunaix-os/includes/lunaix/mm/pmm.h b/lunaix-os/includes/lunaix/mm/pmm.h index 36396df..fa22f7b 100644 --- a/lunaix-os/includes/lunaix/mm/pmm.h +++ b/lunaix-os/includes/lunaix/mm/pmm.h @@ -2,64 +2,136 @@ #define __LUNAIX_PMM_H // Physical memory manager -#include +#include #include +#include + +#define PM_PAGE_SIZE 4096 +#define PM_BMP_MAX_SIZE (1024 * 1024) + +/** + * @brief 长久页:不会被缓存,但允许释放 + * + */ +#define PP_FGPERSIST 0b00001 + +/** + * @brief 锁定页:不会被缓存,不能被释放 + * + */ +#define PP_FGLOCKED 0b00011 -#define PM_PAGE_SIZE 4096 -#define PM_BMP_MAX_SIZE (128 * 1024) +typedef u32_t pp_attr_t; + +struct pp_struct +{ + u32_t ref_counts; + pp_attr_t attr; +}; /** * @brief 标注物理页为可使用 - * + * * @param ppn page number */ -void pmm_mark_page_free(uintptr_t ppn); +void +pmm_mark_page_free(ptr_t ppn); /** * @brief 标注物理页为已占用 - * - * @param ppn + * + * @param ppn */ -void pmm_mark_page_occupied(uintptr_t ppn); +void +pmm_mark_page_occupied(ptr_t ppn, pp_attr_t attr); /** * @brief 标注多个连续的物理页为可用 - * + * * @param start_ppn 起始PPN * @param page_count 数量 */ -void pmm_mark_chunk_free(uintptr_t start_ppn, size_t page_count); +void +pmm_mark_chunk_free(ptr_t start_ppn, size_t page_count); /** * @brief 标注多个连续的物理页为已占用 - * + * * @param start_ppn 起始PPN * @param page_count 数量 */ -void pmm_mark_chunk_occupied(uintptr_t start_ppn, size_t page_count); +void +pmm_mark_chunk_occupied(u32_t start_ppn, + size_t page_count, + pp_attr_t attr); /** * @brief 分配一个可用的物理页 - * + * * @return void* 可用的页地址,否则为 NULL */ -void* pmm_alloc_page(); +ptr_t +pmm_alloc_page(pp_attr_t attr); + +/** + * @brief 分配一个连续的物理内存区域 + * + * @param owner + * @param num_pages 区域大小,单位为页 + * @param attr + * @return ptr_t + */ +ptr_t +pmm_alloc_cpage(size_t num_pages, pp_attr_t attr); /** * @brief 初始化物理内存管理器 - * + * * @param mem_upper_lim 最大可用内存地址 */ -void pmm_init(uintptr_t mem_upper_lim); +void +pmm_init(ptr_t mem_upper_lim); +struct pp_struct* +pmm_query(ptr_t pa); /** - * @brief 释放一个已分配的物理页,假若页地址不存在,则无操作。 + * @brief Free physical page with given attributes * + * @param page + * @return int + */ +int +pmm_free_one(ptr_t page, pp_attr_t attr_mask); + +/** + * @brief Free a normal physical page + * * @param page 页地址 * @return 是否成功 */ -int pmm_free_page(void* page); +static inline int +pmm_free_page(ptr_t page) +{ + return pmm_free_one(page, 0); +} + +/** + * @brief Free physical page regardless of it's attribute + * + * @param page + * @return int + */ +static inline int +pmm_free_any(ptr_t page) +{ + return pmm_free_one(page, -1); +} + +int +pmm_ref_page(ptr_t page); +void +pmm_set_attr(ptr_t page, pp_attr_t attr); #endif /* __LUNAIX_PMM_H */