1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
|
#pragma once
#include <stdint.h>
//in the lower half, memory is only ever mapped below 0x0080.0000.0000. this is
//one p3's worth. the p4 and p3 in app_memory are always real, but p3 may have
//zero entries indicating p2's that aren't needed. similarly, the p2's may have
//zero entries indicating p1's that aren't needed.
namespace hilbert::kernel {
class app_memory {
typedef uint64_t *v_page_table;
v_page_table p4;
v_page_table p3;
v_page_table p2s[512];
v_page_table *p1s[512];
bool **pram_pages_to_free_on_exit[512];
public:
uint64_t p4_paddr;
app_memory();
~app_memory();
//vaddr and paddr must be page aligned.
//vaddr must be < 0x0080.0000.0000.
void map_page(
uint64_t vaddr, uint64_t paddr, bool write,
bool execute, bool free_pram_on_exit);
//also frees the pram if marked in pram_pages_to_free_on_exit
void unmap_page(uint64_t vaddr);
bool valid_to_read(
uint64_t vaddr_start, uint64_t vaddr_end, bool and_write) const;
inline bool valid_to_read(
const void *vaddr_start, const void *vaddr_end, bool and_write) const {
return valid_to_read(
(uint64_t)vaddr_start, (uint64_t)vaddr_end, and_write);
}
//pages are together; returns start of first page.
//only looks in range [0x0000.0000.1000, 0x0040.0000.0000)
uint64_t get_free_vaddr_pages(uint64_t count);
//returns top of stack
uint64_t map_new_stack();
//also frees pram pages
void unmap_stack(uint64_t top);
//in lower half
uint64_t count_mapped_vram_pages() const;
};
}
|