ostd/specs/mm/page_table/
vaddr_range_proofs.rs1use vstd::{
9 arithmetic::power2::{lemma_pow2_adds, lemma_pow2_pos, pow2},
10 prelude::*,
11};
12
13use crate::specs::mm::page_table::pte_index_bit_offset_spec;
14
15use crate::mm::{PagingConstsTrait, Vaddr, page_table::PageTableConfig};
16
17verus! {
18
19pub proof fn lemma_pt_va_range_start_shift_facts<C: PageTableConfig>(
22 idx_start: usize,
23 offset: usize,
24)
25 requires
26 idx_start == C::TOP_LEVEL_INDEX_RANGE().start,
27 offset == pte_index_bit_offset_spec::<C>(C::NR_LEVELS()),
28 ensures
29 offset < usize::BITS,
30 idx_start * pow2(offset as nat) <= usize::MAX,
31 offset == pte_index_bit_offset_spec::<C>(C::NR_LEVELS()),
32{
33 C::lemma_paging_consts_properties();
34 C::lemma_page_table_config_constant_properties();
35 vstd::layout::unsigned_int_max_values();
36
37 let off = pte_index_bit_offset_spec::<C>(C::NR_LEVELS()) as nat;
38 let aw = C::ADDRESS_WIDTH() as nat;
39 let top_w = (aw - off) as nat;
40 lemma_pow2_adds(top_w, off);
41 lemma_pow2_pos(off);
42 lemma_pow2_pos(top_w);
43 lemma_pow2_pos(aw);
44
45 let i_start = C::TOP_LEVEL_INDEX_RANGE().start as int;
46 let p_off = pow2(off) as int;
47 let p_top = pow2(top_w) as int;
48
49 assert(i_start * p_off < p_top * p_off) by (nonlinear_arith)
50 requires
51 i_start < p_top,
52 p_off > 0,
53 ;
54
55 if aw < 64 {
56 vstd::arithmetic::power2::lemma_pow2_strictly_increases(aw, 64);
57 }
58}
59
60pub proof fn lemma_pt_va_range_end_shift_facts<C: PageTableConfig>(idx_end: usize, offset: usize)
63 requires
64 idx_end == C::TOP_LEVEL_INDEX_RANGE().end,
65 offset == pte_index_bit_offset_spec::<C>(C::NR_LEVELS()),
66 ensures
67 offset < usize::BITS,
68 idx_end * pow2(offset as nat) <= usize::MAX,
69 0 < idx_end * pow2(offset as nat),
70 offset == pte_index_bit_offset_spec::<C>(C::NR_LEVELS()),
71{
72 C::lemma_paging_consts_properties();
73 C::lemma_page_table_config_constant_properties();
74 lemma_pow2_pos(offset as nat);
75
76 let i_end = C::TOP_LEVEL_INDEX_RANGE().end as int;
77 let p_off = pow2(offset as nat) as int;
78 assert(i_end * p_off > 0) by (nonlinear_arith)
79 requires
80 i_end > 0,
81 p_off > 0,
82 ;
83}
84
85pub proof fn lemma_pt_va_range_end_wrapping_sub<C: PageTableConfig>(
88 idx_end: usize,
89 offset: usize,
90 shifted: usize,
91 ret: usize,
92)
93 requires
94 idx_end == C::TOP_LEVEL_INDEX_RANGE().end,
95 offset == pte_index_bit_offset_spec::<C>(C::NR_LEVELS()),
96 shifted == idx_end * pow2(offset as nat),
97 ret == vstd::wrapping::usize_specs::wrapping_sub(shifted, 1usize),
98 ensures
99 ret == (C::TOP_LEVEL_INDEX_RANGE().end * pow2(
100 pte_index_bit_offset_spec::<C>(C::NR_LEVELS()) as nat,
101 ) - 1) % 0x1_0000_0000_0000_0000int,
102{
103 lemma_pt_va_range_end_shift_facts::<C>(idx_end, offset);
104 vstd::layout::unsigned_int_max_values();
105}
106
107pub proof fn lemma_idx_times_pow2_bound<C: PageTableConfig>(start: Vaddr, end: Vaddr)
115 requires
116 start == C::TOP_LEVEL_INDEX_RANGE().start * (pow2(
117 pte_index_bit_offset_spec::<C>(C::NR_LEVELS()) as nat,
118 ) as int),
119 end == (C::TOP_LEVEL_INDEX_RANGE().end * (pow2(
120 pte_index_bit_offset_spec::<C>(C::NR_LEVELS()) as nat,
121 ) as int) - 1) % 0x1_0000_0000_0000_0000int,
122 ensures
123 start < pow2(C::ADDRESS_WIDTH() as nat),
124 end < pow2(C::ADDRESS_WIDTH() as nat),
125 end == C::TOP_LEVEL_INDEX_RANGE().end * pow2(
127 pte_index_bit_offset_spec::<C>(C::NR_LEVELS()) as nat,
128 ) - 1,
129{
130 C::lemma_paging_consts_properties();
131 C::lemma_page_table_config_constant_properties();
132 let off = pte_index_bit_offset_spec::<C>(C::NR_LEVELS()) as nat;
133 let aw = C::ADDRESS_WIDTH() as nat;
134 let top_w = (aw - off) as nat;
135 lemma_pow2_adds(top_w, off);
136 lemma_pow2_pos(off);
137 lemma_pow2_pos(top_w);
138 lemma_pow2_pos(aw);
139 let i_start = C::TOP_LEVEL_INDEX_RANGE().start as int;
141 let i_end = C::TOP_LEVEL_INDEX_RANGE().end as int;
142 let p_off = pow2(off) as int;
143 let p_top = pow2(top_w) as int;
144 let p_aw = pow2(aw) as int;
145 assert(start < (p_top * p_off)) by (nonlinear_arith)
147 requires
148 start == i_start * p_off,
149 i_start < p_top,
150 p_off > 0,
151 ;
152 let e_pre = i_end * p_off;
154 assert(e_pre <= p_top * p_off) by (nonlinear_arith)
155 requires
156 e_pre == i_end * p_off,
157 i_end <= p_top,
158 p_off > 0,
159 ;
160 assert(e_pre > 0) by (nonlinear_arith)
163 requires
164 e_pre == i_end * p_off,
165 i_end > 0,
166 p_off > 0,
167 ;
168}
169
170}