]> git.buserror.net Git - polintos/scott/priv.git/blob - kernel/include/kern/generic-pagetable.h
Lots of stuff.
[polintos/scott/priv.git] / kernel / include / kern / generic-pagetable.h
1 // This is a generic pagetable implementation that most architectures
2 // should be able to use as is, though architectures with weird paging
3 // hardware can provide their own implementation.  It corresponds to
4 // mem/pagetable.cc.
5
6 #ifndef _KERN_GENERIC_PAGETABLE_H
7 #define _KERN_GENERIC_PAGETABLE_H
8
9 #include <kern/mem.h>
10 #include <util/lock.h>
11 #include <arch/pagetable.h>
12 #include <kern/pagetable.h>
13
14 namespace Mem {
15         template<typename PTE>
16         class PageTableImpl : public PageTable {
17         public:
18                 typedef Mem::PTEFlags Flags;
19                 typedef System::Mem::Region Region;
20                 typedef System::Mem::RegionWithOffset RegionWithOffset;
21                 typedef typename PTE::VirtAddr VirtAddr;
22                 typedef typename PTE::DirPTE DirPTE;
23
24         private:
25                 // The lock of any page table may nest in the lock of any
26                 // aspace.
27                 
28                 Lock::Lock lock;
29                 
30                 // For non-process aspaces, the number of levels may be more or
31                 // less than what the hardware provides (in particular, large file
32                 // mappings on 32-bit targets will need more levels).  For process
33                 // aspaces, num_levels must equal PTE::num_levels.  Levels for
34                 // non-process address spaces can be added dynamically as needed. 
35                 // Non-proc aspaces may also use a different PTE format.
36                 
37                 int num_levels;
38                 int toplevel_shift, lastlevel_shift;
39
40                 static uint pages_per_table()
41                 {
42                         return 1 << PTE::shift_per_level;
43                 }
44                 
45                 static uint pages_per_dtable()
46                 {
47                         return 1 << DirPTE::shift_per_level;
48                 }
49                 
50                 void end_map(RegionWithOffset region, PTE flags, void *table);
51                 
52                 void end_unmap(Region region, void *table);
53
54                 void end_set_flags(Region region, PTE flags, PTE mask, void *table);
55
56                 void rec_map(RegionWithOffset region, PTE flags,
57                              void *table, int shift);
58                 
59                 void rec_unmap(Region region, void *table, int shift);
60
61                 void rec_set_flags(Region region, PTE flags,
62                                    PTE mask, void *table, int shift);
63
64         public:
65                 PageTableImpl(bool process);
66                 PageTableImpl(void *table);
67                 
68                 virtual ~PageTableImpl();
69
70                 virtual void map(RegionWithOffset region, Flags flags);
71                 virtual void unmap(Region region);
72                 virtual void set_flags(Region region, Flags flags, Flags mask);
73                 virtual void get_mapping(u64 addr, u64 *phys, Flags *flags);
74
75                 virtual void get_size(u64 *size)
76                 {
77                         if (is_process)
78                                 *size = 1ULL << (PTE::num_levels * PTE::shift_per_level);
79                         else
80                                 *size = 1ULL << (64 - PTE::page_shift);
81                 }
82         };
83 }
84
85 #endif