|
16 | 16 | #define _PAGE_BIT_PSE 7 /* 4 MB (or 2MB) page */ |
17 | 17 | #define _PAGE_BIT_PAT 7 /* on 4KB pages */ |
18 | 18 | #define _PAGE_BIT_GLOBAL 8 /* Global TLB entry PPro+ */ |
19 | | -#define _PAGE_BIT_UNUSED1 9 /* available for programmer */ |
20 | | -#define _PAGE_BIT_IOMAP 10 /* flag used to indicate IO mapping */ |
21 | | -#define _PAGE_BIT_HIDDEN 11 /* hidden by kmemcheck */ |
| 19 | +#define _PAGE_BIT_SOFTW1 9 /* available for programmer */ |
| 20 | +#define _PAGE_BIT_SOFTW2 10 /* " */ |
| 21 | +#define _PAGE_BIT_SOFTW3 11 /* " */ |
22 | 22 | #define _PAGE_BIT_PAT_LARGE 12 /* On 2MB or 1GB pages */ |
23 | | -#define _PAGE_BIT_SPECIAL _PAGE_BIT_UNUSED1 |
24 | | -#define _PAGE_BIT_CPA_TEST _PAGE_BIT_UNUSED1 |
25 | | -#define _PAGE_BIT_SPLITTING _PAGE_BIT_UNUSED1 /* only valid on a PSE pmd */ |
| 23 | +#define _PAGE_BIT_SPECIAL _PAGE_BIT_SOFTW1 |
| 24 | +#define _PAGE_BIT_CPA_TEST _PAGE_BIT_SOFTW1 |
| 25 | +#define _PAGE_BIT_SPLITTING _PAGE_BIT_SOFTW2 /* only valid on a PSE pmd */ |
| 26 | +#define _PAGE_BIT_IOMAP _PAGE_BIT_SOFTW2 /* flag used to indicate IO mapping */ |
| 27 | +#define _PAGE_BIT_HIDDEN _PAGE_BIT_SOFTW3 /* hidden by kmemcheck */ |
| 28 | +#define _PAGE_BIT_SOFT_DIRTY _PAGE_BIT_SOFTW3 /* software dirty tracking */ |
26 | 29 | #define _PAGE_BIT_NX 63 /* No execute: only valid after cpuid check */ |
27 | 30 |
|
| 31 | +/* |
| 32 | + * Swap offsets on configurations that allow automatic NUMA balancing use the |
| 33 | + * bits after _PAGE_BIT_GLOBAL. To uniquely distinguish NUMA hinting PTEs from |
| 34 | + * swap entries, we use the first bit after _PAGE_BIT_GLOBAL and shrink the |
| 35 | + * maximum possible swap space from 16TB to 8TB. |
| 36 | + */ |
| 37 | +#define _PAGE_BIT_NUMA (_PAGE_BIT_GLOBAL+1) |
| 38 | + |
28 | 39 | /* If _PAGE_BIT_PRESENT is clear, we use these: */ |
29 | 40 | /* - if the user mapped it with PROT_NONE; pte_present gives true */ |
30 | 41 | #define _PAGE_BIT_PROTNONE _PAGE_BIT_GLOBAL |
|
40 | 51 | #define _PAGE_DIRTY (_AT(pteval_t, 1) << _PAGE_BIT_DIRTY) |
41 | 52 | #define _PAGE_PSE (_AT(pteval_t, 1) << _PAGE_BIT_PSE) |
42 | 53 | #define _PAGE_GLOBAL (_AT(pteval_t, 1) << _PAGE_BIT_GLOBAL) |
43 | | -#define _PAGE_UNUSED1 (_AT(pteval_t, 1) << _PAGE_BIT_UNUSED1) |
| 54 | +#define _PAGE_SOFTW1 (_AT(pteval_t, 1) << _PAGE_BIT_SOFTW1) |
44 | 55 | #define _PAGE_IOMAP (_AT(pteval_t, 1) << _PAGE_BIT_IOMAP) |
45 | 56 | #define _PAGE_PAT (_AT(pteval_t, 1) << _PAGE_BIT_PAT) |
46 | 57 | #define _PAGE_PAT_LARGE (_AT(pteval_t, 1) << _PAGE_BIT_PAT_LARGE) |
|
61 | 72 | * they do not conflict with each other. |
62 | 73 | */ |
63 | 74 |
|
64 | | -#define _PAGE_BIT_SOFT_DIRTY _PAGE_BIT_HIDDEN |
65 | | - |
66 | 75 | #ifdef CONFIG_MEM_SOFT_DIRTY |
67 | 76 | #define _PAGE_SOFT_DIRTY (_AT(pteval_t, 1) << _PAGE_BIT_SOFT_DIRTY) |
68 | 77 | #else |
69 | 78 | #define _PAGE_SOFT_DIRTY (_AT(pteval_t, 0)) |
70 | 79 | #endif |
71 | 80 |
|
| 81 | +/* |
| 82 | + * _PAGE_NUMA distinguishes between a numa hinting minor fault and a page |
| 83 | + * that is not present. The hinting fault gathers numa placement statistics |
| 84 | + * (see pte_numa()). The bit is always zero when the PTE is not present. |
| 85 | + * |
| 86 | + * The bit picked must be always zero when the pmd is present and not |
| 87 | + * present, so that we don't lose information when we set it while |
| 88 | + * atomically clearing the present bit. |
| 89 | + */ |
| 90 | +#ifdef CONFIG_NUMA_BALANCING |
| 91 | +#define _PAGE_NUMA (_AT(pteval_t, 1) << _PAGE_BIT_NUMA) |
| 92 | +#else |
| 93 | +#define _PAGE_NUMA (_AT(pteval_t, 0)) |
| 94 | +#endif |
| 95 | + |
72 | 96 | /* |
73 | 97 | * Tracking soft dirty bit when a page goes to a swap is tricky. |
74 | 98 | * We need a bit which can be stored in pte _and_ not conflict |
|
94 | 118 | #define _PAGE_FILE (_AT(pteval_t, 1) << _PAGE_BIT_FILE) |
95 | 119 | #define _PAGE_PROTNONE (_AT(pteval_t, 1) << _PAGE_BIT_PROTNONE) |
96 | 120 |
|
97 | | -/* |
98 | | - * _PAGE_NUMA indicates that this page will trigger a numa hinting |
99 | | - * minor page fault to gather numa placement statistics (see |
100 | | - * pte_numa()). The bit picked (8) is within the range between |
101 | | - * _PAGE_FILE (6) and _PAGE_PROTNONE (8) bits. Therefore, it doesn't |
102 | | - * require changes to the swp entry format because that bit is always |
103 | | - * zero when the pte is not present. |
104 | | - * |
105 | | - * The bit picked must be always zero when the pmd is present and not |
106 | | - * present, so that we don't lose information when we set it while |
107 | | - * atomically clearing the present bit. |
108 | | - * |
109 | | - * Because we shared the same bit (8) with _PAGE_PROTNONE this can be |
110 | | - * interpreted as _PAGE_NUMA only in places that _PAGE_PROTNONE |
111 | | - * couldn't reach, like handle_mm_fault() (see access_error in |
112 | | - * arch/x86/mm/fault.c, the vma protection must not be PROT_NONE for |
113 | | - * handle_mm_fault() to be invoked). |
114 | | - */ |
115 | | -#define _PAGE_NUMA _PAGE_PROTNONE |
116 | | - |
117 | 121 | #define _PAGE_TABLE (_PAGE_PRESENT | _PAGE_RW | _PAGE_USER | \ |
118 | 122 | _PAGE_ACCESSED | _PAGE_DIRTY) |
119 | 123 | #define _KERNPG_TABLE (_PAGE_PRESENT | _PAGE_RW | _PAGE_ACCESSED | \ |
|
122 | 126 | /* Set of bits not changed in pte_modify */ |
123 | 127 | #define _PAGE_CHG_MASK (PTE_PFN_MASK | _PAGE_PCD | _PAGE_PWT | \ |
124 | 128 | _PAGE_SPECIAL | _PAGE_ACCESSED | _PAGE_DIRTY | \ |
125 | | - _PAGE_SOFT_DIRTY) |
126 | | -#define _HPAGE_CHG_MASK (_PAGE_CHG_MASK | _PAGE_PSE) |
| 129 | + _PAGE_SOFT_DIRTY | _PAGE_NUMA) |
| 130 | +#define _HPAGE_CHG_MASK (_PAGE_CHG_MASK | _PAGE_PSE | _PAGE_NUMA) |
127 | 131 |
|
128 | 132 | #define _PAGE_CACHE_MASK (_PAGE_PCD | _PAGE_PWT) |
129 | 133 | #define _PAGE_CACHE_WB (0) |
|
0 commit comments