1cb213e4bb4c0bf02d0b683f10282deddb868350
[akaros.git] / kern / include / page_alloc.h
1 /* Copyright (c) 2009, 2010 The Regents of the University  of California. 
2  * See the COPYRIGHT files at the top of this source tree for full 
3  * license information.
4  * 
5  * Kevin Klues <klueska@cs.berkeley.edu>    
6  * Barret Rhoden <brho@cs.berkeley.edu> */
7  
8 #ifndef PAGE_ALLOC_H
9 #define PAGE_ALLOC_H
10
11 #include <atomic.h>
12 #include <sys/queue.h>
13 #include <error.h>
14 #include <arch/mmu.h>
15 #include <colored_page_alloc.h>
16 #include <process.h>
17 #include <kref.h>
18 #include <kthread.h>
19
20 struct page_map;                /* preprocessor games */
21
22 /****************** Page Structures *********************/
23 struct page;
24 typedef size_t ppn_t;
25 typedef struct page page_t;
26 typedef LIST_HEAD(PageList, page) page_list_t;
27 typedef LIST_ENTRY(page) page_list_entry_t;
28
29 /* Per-page flag bits related to their state in the page cache */
30 #define PG_LOCKED               0x001   /* involved in an IO op */
31 #define PG_UPTODATE             0x002   /* page map, filled with file data */
32 #define PG_DIRTY                0x004   /* page map, data is dirty */
33 #define PG_BUFFER               0x008   /* is a buffer page, has BHs */
34
35 /* TODO: this struct is not protected from concurrent operations in some
36  * functions.  If you want to lock on it, use the spinlock in the semaphore.
37  * This structure is getting pretty big (and we're wasting RAM).  If it becomes
38  * an issue, we can dynamically allocate some of these things when we're a
39  * buffer page (in a page mapping) */
40 struct page {
41         LIST_ENTRY(page)                        pg_link;        /* membership in various lists */
42         struct kref                                     pg_kref;
43         unsigned int                            pg_flags;
44         struct page_map                         *pg_mapping;
45         unsigned long                           pg_index;
46         void                                            *pg_private;    /* type depends on page usage */
47         struct semaphore                        pg_sem;         /* for blocking on IO */
48 };
49
50 /******** Externally visible global variables ************/
51 extern uint8_t* global_cache_colors_map;
52 extern spinlock_t colored_page_free_list_lock;
53 extern page_list_t LCKD(&colored_page_free_list_lock) * RO CT(llc_num_colors)
54     colored_page_free_list;
55
56 /*************** Functional Interface *******************/
57 void page_alloc_init(void);
58 void colored_page_alloc_init(void);
59
60 error_t upage_alloc(struct proc* p, page_t *SAFE *page, int zero);
61 error_t kpage_alloc(page_t *SAFE *page);
62 error_t upage_alloc_specific(struct proc* p, page_t *SAFE *page, size_t ppn);
63 error_t kpage_alloc_specific(page_t *SAFE *page, size_t ppn);
64
65 void *CT(1 << order) get_cont_pages(size_t order, int flags);
66 void free_cont_pages(void *buf, size_t order);
67
68 void page_incref(page_t *SAFE page);
69 void page_decref(page_t *SAFE page);
70 void page_setref(page_t *SAFE page, size_t val);
71
72 int page_is_free(size_t ppn);
73 void lock_page(struct page *page);
74 void unlock_page(struct page *page);
75 void print_pageinfo(struct page *page);
76
77 #endif //PAGE_ALLOC_H
78