Skip to content

Commit f0524f8

Browse files
authored
Aligen definitions with corter-3 (#78)
* Rename Cursor fields * More rename * Align with asterinas definition of PagingConstsTrait * fmt * fmt
1 parent 6772140 commit f0524f8

3 files changed

Lines changed: 163 additions & 70 deletions

File tree

lock-protocol/src/exec/rw/common.rs

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -13,15 +13,10 @@ use crate::helpers::extern_const::*;
1313
use crate::spec::{common::*, utils::*};
1414

1515
pub use super::configs::*;
16+
pub use crate::mm::{Paddr, Vaddr, PagingLevel};
1617

1718
verus! {
1819

19-
pub type Paddr = usize;
20-
21-
pub type Vaddr = usize;
22-
23-
pub type PagingLevel = usize;
24-
2520
// pub const MAX_FRAME_NUM: u64 = 256;
2621
pub const INVALID_PADDR: Paddr = 0xffff_ffff_ffff_ffff;
2722

lock-protocol/src/exec/rw/cursor.rs

Lines changed: 49 additions & 47 deletions
Original file line numberDiff line numberDiff line change
@@ -24,19 +24,20 @@ use crate::mm::page_table::cursor::MAX_NR_LEVELS;
2424
verus! {
2525

2626
pub enum GuardInPath {
27-
ReadLocked(PageTableReadLock),
28-
WriteLocked(PageTableWriteLock),
29-
None,
27+
Read(PageTableReadLock),
28+
Write(PageTableWriteLock),
29+
ImplicitWrite(PageTableWriteLock),
30+
Unlocked,
3031
}
3132

3233
impl GuardInPath {
3334
#[verifier::external_body] // Verus does not support replace.
3435
pub fn take(&mut self) -> (res: Self)
3536
ensures
3637
res =~= *old(self),
37-
*self is None,
38+
*self is Unlocked,
3839
{
39-
core::mem::replace(self, Self::None)
40+
core::mem::replace(self, Self::Unlocked)
4041
}
4142
}
4243

@@ -58,15 +59,15 @@ impl Cursor {
5859
#![trigger self.path[level - 1]]
5960
1 <= level <= 4 ==> {
6061
if level < self.guard_level {
61-
self.path[level - 1] is None
62+
self.path[level - 1] is Unlocked
6263
} else if level == self.guard_level {
63-
&&& self.path[level - 1] is WriteLocked
64-
&&& self.path[level - 1]->WriteLocked_0.wf()
65-
&&& self.path[level - 1]->WriteLocked_0.inst_id() == self.inst@.id()
64+
&&& self.path[level - 1] is Write
65+
&&& self.path[level - 1]->Write_0.wf()
66+
&&& self.path[level - 1]->Write_0.inst_id() == self.inst@.id()
6667
} else {
67-
&&& self.path[level - 1] is ReadLocked
68-
&&& self.path[level - 1]->ReadLocked_0.wf()
69-
&&& self.path[level - 1]->ReadLocked_0.inst_id() == self.inst@.id()
68+
&&& self.path[level - 1] is Read
69+
&&& self.path[level - 1]->Read_0.wf()
70+
&&& self.path[level - 1]->Read_0.inst_id() == self.inst@.id()
7071
}
7172
}
7273
// &&& valid_vaddr(self.va)
@@ -88,7 +89,7 @@ impl Cursor {
8889
&&& self.unlock_level@ == 5
8990
&&& forall|level: int|
9091
#![trigger self.path@[level - 1]]
91-
1 <= level <= 4 ==> self.path@[level - 1] is None
92+
1 <= level <= 4 ==> self.path@[level - 1] is Unlocked
9293
}
9394

9495
pub open spec fn wf_with_lock_protocol_model(&self, m: LockProtocolModel) -> bool {
@@ -97,11 +98,12 @@ impl Cursor {
9798
&&& forall|level: int|
9899
#![trigger self.path[level - 1]]
99100
self.unlock_level@ <= level <= 4 ==> {
100-
&&& !(self.path[level - 1] is None)
101+
&&& !(self.path[level - 1] is Unlocked)
101102
&&& match self.path[level - 1] {
102-
GuardInPath::ReadLocked(rguard) => m.path()[4 - level] == rguard.nid(),
103-
GuardInPath::WriteLocked(wguard) => m.path()[4 - level] == wguard.nid(),
104-
GuardInPath::None => true,
103+
GuardInPath::Read(rguard) => m.path()[4 - level] == rguard.nid(),
104+
GuardInPath::Write(wguard) => m.path()[4 - level] == wguard.nid(),
105+
GuardInPath::ImplicitWrite(wguard) => m.path()[4 - level] == wguard.nid(),
106+
GuardInPath::Unlocked => true,
105107
}
106108
}
107109
}
@@ -112,7 +114,7 @@ impl Cursor {
112114
0 <= idx < old(self).path@.len(),
113115
ensures
114116
res =~= old(self).path@[idx as int],
115-
self.path@ =~= old(self).path@.update(idx as int, GuardInPath::None),
117+
self.path@ =~= old(self).path@.update(idx as int, GuardInPath::Unlocked),
116118
self.level == old(self).level,
117119
self.guard_level == old(self).guard_level,
118120
self.va =~= old(self).va,
@@ -254,10 +256,10 @@ pub fn lock_range(
254256
res.0.wf_with_lock_protocol_model(res.1@),
255257
{
256258
let mut path: [GuardInPath; MAX_NR_LEVELS] = [
257-
GuardInPath::None,
258-
GuardInPath::None,
259-
GuardInPath::None,
260-
GuardInPath::None,
259+
GuardInPath::Unlocked,
260+
GuardInPath::Unlocked,
261+
GuardInPath::Unlocked,
262+
GuardInPath::Unlocked,
261263
];
262264

263265
let ghost mut cur_nid: NodeId = 0;
@@ -303,12 +305,12 @@ pub fn lock_range(
303305
forall|i: int|
304306
#![trigger path@[i - 1]]
305307
level < i <= 4 ==> {
306-
&&& path@[i - 1] is ReadLocked
307-
&&& path@[i - 1]->ReadLocked_0.wf()
308-
&&& path@[i - 1]->ReadLocked_0.inst_id() == pt.inst@.id()
309-
&&& m.path()[4 - i] == path@[i - 1]->ReadLocked_0.nid()
308+
&&& path@[i - 1] is Read
309+
&&& path@[i - 1]->Read_0.wf()
310+
&&& path@[i - 1]->Read_0.inst_id() == pt.inst@.id()
311+
&&& m.path()[4 - i] == path@[i - 1]->Read_0.nid()
310312
},
311-
forall|i: int| #![trigger path@[i - 1]] 1 <= i <= level ==> path@[i - 1] is None,
313+
forall|i: int| #![trigger path@[i - 1]] 1 <= i <= level ==> path@[i - 1] is Unlocked,
312314
m.path().len() == 4 - level,
313315
m.path().is_prefix_of(va_range_get_tree_path(*va)),
314316
m.state() is ReadLocking,
@@ -327,12 +329,12 @@ pub fn lock_range(
327329
forall|i: int|
328330
#![trigger path@[i - 1]]
329331
level < i <= 4 ==> {
330-
&&& path@[i - 1] is ReadLocked
331-
&&& path@[i - 1]->ReadLocked_0.wf()
332-
&&& path@[i - 1]->ReadLocked_0.inst_id() == pt.inst@.id()
333-
&&& m.path()[4 - i] == path@[i - 1]->ReadLocked_0.nid()
332+
&&& path@[i - 1] is Read
333+
&&& path@[i - 1]->Read_0.wf()
334+
&&& path@[i - 1]->Read_0.inst_id() == pt.inst@.id()
335+
&&& m.path()[4 - i] == path@[i - 1]->Read_0.nid()
334336
},
335-
forall|i: int| #![trigger path@[i - 1]] 1 <= i <= level ==> path@[i - 1] is None,
337+
forall|i: int| #![trigger path@[i - 1]] 1 <= i <= level ==> path@[i - 1] is Unlocked,
336338
m.path().len() == 4 - level,
337339
m.path().is_prefix_of(va_range_get_tree_path(*va)),
338340
m.state() is ReadLocking,
@@ -393,7 +395,7 @@ pub fn lock_range(
393395
match child {
394396
Child::PageTable(_, _, _) => unreached(),
395397
Child::PageTableRef(pt, _, _) => {
396-
path[level as usize - 1] = GuardInPath::ReadLocked(cur_pt_rlockguard);
398+
path[level as usize - 1] = GuardInPath::Read(cur_pt_rlockguard);
397399
cur_pt_paddr = pt;
398400
level -= 1;
399401
proof {
@@ -433,7 +435,7 @@ pub fn lock_range(
433435
m = res.1.get();
434436
}
435437

436-
path[level as usize - 1] = GuardInPath::ReadLocked(cur_pt_rlockguard);
438+
path[level as usize - 1] = GuardInPath::Read(cur_pt_rlockguard);
437439
cur_pt_paddr = pt;
438440
level -= 1;
439441
proof {
@@ -470,7 +472,7 @@ pub fn lock_range(
470472
proof {
471473
m = res.1.get();
472474
}
473-
path[level as usize - 1] = GuardInPath::ReadLocked(cur_pt_rlockguard);
475+
path[level as usize - 1] = GuardInPath::Read(cur_pt_rlockguard);
474476
level -= 1;
475477
proof {
476478
cur_nid = NodeHelper::get_child(cur_nid, start_idx as nat);
@@ -517,7 +519,7 @@ pub fn lock_range(
517519
res.0
518520
};
519521

520-
path[level as usize - 1] = GuardInPath::WriteLocked(cur_pt_wlockguard);
522+
path[level as usize - 1] = GuardInPath::Write(cur_pt_wlockguard);
521523

522524
let tracked inst = pt.inst.borrow().clone();
523525
let cursor = Cursor {
@@ -548,9 +550,9 @@ pub fn unlock_range(cursor: &mut Cursor, m: Tracked<LockProtocolModel>) -> (res:
548550
let tracked mut m = m.get();
549551

550552
let guard_level = cursor.guard_level;
551-
let GuardInPath::WriteLocked(mut guard_node) = cursor.take_guard(
552-
guard_level as usize - 1,
553-
) else { unreached() };
553+
let GuardInPath::Write(mut guard_node) = cursor.take_guard(guard_level as usize - 1) else {
554+
unreached()
555+
};
554556
let res = guard_node.unlock(Tracked(m));
555557
let pt = res.0;
556558
proof {
@@ -568,22 +570,22 @@ pub fn unlock_range(cursor: &mut Cursor, m: Tracked<LockProtocolModel>) -> (res:
568570
forall|level: int|
569571
#![trigger cursor.path@[level - 1]]
570572
i <= level <= 4 ==> {
571-
&&& cursor.path@[level - 1] is ReadLocked
572-
&&& cursor.path@[level - 1]->ReadLocked_0.wf()
573-
&&& cursor.path@[level - 1]->ReadLocked_0.inst_id() == cursor.inst@.id()
573+
&&& cursor.path@[level - 1] is Read
574+
&&& cursor.path@[level - 1]->Read_0.wf()
575+
&&& cursor.path@[level - 1]->Read_0.inst_id() == cursor.inst@.id()
574576
},
575577
forall|level: int|
576578
#![trigger cursor.path@[level - 1]]
577-
1 <= level < i ==> cursor.path@[level - 1] is None,
579+
1 <= level < i ==> cursor.path@[level - 1] is Unlocked,
578580
cursor.wf_with_lock_protocol_model(m),
579581
m.inv(),
580582
m.state() is ReadLocking,
581583
cursor.inst@.cpu_num() == GLOBAL_CPU_NUM,
582584
decreases 5 - i,
583585
{
584586
match cursor.take_guard(i as usize - 1) {
585-
GuardInPath::None => unreached(),
586-
GuardInPath::ReadLocked(mut rguard) => {
587+
GuardInPath::Unlocked => unreached(),
588+
GuardInPath::Read(mut rguard) => {
587589
assert(m.path()[4 - i] == rguard.nid());
588590
let res = rguard.unlock(Tracked(m));
589591
let pt = res.0;
@@ -593,8 +595,8 @@ pub fn unlock_range(cursor: &mut Cursor, m: Tracked<LockProtocolModel>) -> (res:
593595
pt.into_raw();
594596
cursor.unlock_level = Ghost((cursor.unlock_level@ + 1) as PagingLevel);
595597
},
596-
GuardInPath::WriteLocked(_) => unreached(),
597-
// GuardInPath::ImplicitlyLocked(_) => unreached(),
598+
GuardInPath::Write(_) => unreached(),
599+
GuardInPath::ImplicitWrite(_) => unreached(),
598600
}
599601
i += 1;
600602
}

lock-protocol/src/mm/page_table/mod.rs

Lines changed: 113 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -139,6 +139,38 @@ impl<C: PageTableConfig> PagingConstsTrait for C {
139139
fn NR_LEVELS() -> (res: PagingLevel) {
140140
C::C::NR_LEVELS()
141141
}
142+
143+
open spec fn HIGHEST_TRANSLATION_LEVEL_SPEC() -> PagingLevel {
144+
C::C::HIGHEST_TRANSLATION_LEVEL_SPEC()
145+
}
146+
147+
fn HIGHEST_TRANSLATION_LEVEL() -> PagingLevel {
148+
C::C::HIGHEST_TRANSLATION_LEVEL()
149+
}
150+
151+
open spec fn PTE_SIZE_SPEC() -> usize {
152+
C::C::PTE_SIZE_SPEC()
153+
}
154+
155+
fn PTE_SIZE() -> usize {
156+
C::C::PTE_SIZE()
157+
}
158+
159+
open spec fn ADDRESS_WIDTH_SPEC() -> usize {
160+
C::C::ADDRESS_WIDTH_SPEC()
161+
}
162+
163+
fn ADDRESS_WIDTH() -> usize {
164+
C::C::ADDRESS_WIDTH()
165+
}
166+
167+
open spec fn VA_SIGN_EXT_SPEC() -> bool {
168+
C::C::VA_SIGN_EXT_SPEC()
169+
}
170+
171+
fn VA_SIGN_EXT() -> bool {
172+
C::C::VA_SIGN_EXT()
173+
}
142174
}
143175

144176
pub trait PageTableEntryTrait:
@@ -278,25 +310,61 @@ Sized {
278310

279311
spec fn NR_LEVELS_SPEC() -> PagingLevel;
280312

281-
// /// The number of levels in the page table.
282-
// /// The numbering of levels goes from deepest node to the root node. For example,
283-
// /// the level 1 to 5 on AMD64 corresponds to Page Tables, Page Directory Tables,
284-
// /// Page Directory Pointer Tables, Page-Map Level-4 Table, and Page-Map Level-5
285-
// /// Table, respectively.
313+
/// The number of levels in the page table.
314+
/// The numbering of levels goes from deepest node to the root node. For example,
315+
/// the level 1 to 5 on AMD64 corresponds to Page Tables, Page Directory Tables,
316+
/// Page Directory Pointer Tables, Page-Map Level-4 Table, and Page-Map Level-5
317+
/// Table, respectively.
286318
#[verifier::when_used_as_spec(NR_LEVELS_SPEC)]
287319
fn NR_LEVELS() -> PagingLevel
288320
returns
289321
Self::NR_LEVELS_SPEC(),
290-
; // /
291-
// The highest level that a PTE can be directly used to translate a VA.
292-
// /// This affects the the largest page size supported by the page table.
293-
// const HIGHEST_TRANSLATION_LEVEL: PagingLevel;
294-
// /// The size of a PTE.
295-
// const PTE_SIZE: usize;
296-
// /// The address width may be BASE_PAGE_SIZE.ilog2() + NR_LEVELS * IN_FRAME_INDEX_BITS.
297-
// /// If it is shorter than that, the higher bits in the highest level are ignored.
298-
// const ADDRESS_WIDTH: usize;
322+
;
323+
324+
spec fn HIGHEST_TRANSLATION_LEVEL_SPEC() -> PagingLevel;
325+
326+
/// The highest level that a PTE can be directly used to translate a VA.
327+
/// This affects the the largest page size supported by the page table.
328+
#[verifier::when_used_as_spec(HIGHEST_TRANSLATION_LEVEL_SPEC)]
329+
fn HIGHEST_TRANSLATION_LEVEL() -> PagingLevel
330+
returns
331+
Self::HIGHEST_TRANSLATION_LEVEL_SPEC(),
332+
;
333+
334+
spec fn PTE_SIZE_SPEC() -> usize;
335+
336+
/// The size of a PTE.
337+
fn PTE_SIZE() -> usize
338+
returns
339+
Self::PTE_SIZE_SPEC(),
340+
;
299341

342+
spec fn ADDRESS_WIDTH_SPEC() -> usize;
343+
344+
/// The address width may be BASE_PAGE_SIZE.ilog2() + NR_LEVELS * IN_FRAME_INDEX_BITS.
345+
/// If it is shorter than that, the higher bits in the highest level are ignored.
346+
fn ADDRESS_WIDTH() -> usize
347+
returns
348+
Self::ADDRESS_WIDTH_SPEC(),
349+
;
350+
351+
spec fn VA_SIGN_EXT_SPEC() -> bool;
352+
353+
/// Whether virtual addresses are sign-extended.
354+
///
355+
/// The sign bit of a [`Vaddr`] is the bit at index [`PagingConstsTrait::ADDRESS_WIDTH`] - 1.
356+
/// If this constant is `true`, bits in [`Vaddr`] that are higher than the sign bit must be
357+
/// equal to the sign bit. If an address violates this rule, both the hardware and OSTD
358+
/// should reject it.
359+
///
360+
/// Otherwise, if this constant is `false`, higher bits must be zero.
361+
///
362+
/// Regardless of sign extension, [`Vaddr`] is always not signed upon calculation.
363+
/// That means, `0xffff_ffff_ffff_0000 < 0xffff_ffff_ffff_0001` is `true`.
364+
fn VA_SIGN_EXT() -> bool
365+
returns
366+
Self::VA_SIGN_EXT_SPEC(),
367+
;
300368
}
301369

302370
// TODO: This is for x86, create the arch directory and move this to x86/mod.rs
@@ -323,10 +391,38 @@ impl PagingConstsTrait for PagingConsts {
323391
fn NR_LEVELS() -> (res: PagingLevel) {
324392
4
325393
}
326-
// const ADDRESS_WIDTH: usize = 48;
327-
// const HIGHEST_TRANSLATION_LEVEL: PagingLevel = 2;
328-
// const PTE_SIZE: usize = core::mem::size_of::<PageTableEntry>();
329394

395+
open spec fn HIGHEST_TRANSLATION_LEVEL_SPEC() -> PagingLevel {
396+
2
397+
}
398+
399+
fn HIGHEST_TRANSLATION_LEVEL() -> PagingLevel {
400+
2
401+
}
402+
403+
open spec fn PTE_SIZE_SPEC() -> usize {
404+
core::mem::size_of::<exec::SimplePageTableEntry>()
405+
}
406+
407+
fn PTE_SIZE() -> usize {
408+
core::mem::size_of::<exec::SimplePageTableEntry>()
409+
}
410+
411+
open spec fn ADDRESS_WIDTH_SPEC() -> usize {
412+
48
413+
}
414+
415+
fn ADDRESS_WIDTH() -> usize {
416+
48
417+
}
418+
419+
open spec fn VA_SIGN_EXT_SPEC() -> bool {
420+
true
421+
}
422+
423+
fn VA_SIGN_EXT() -> bool {
424+
true
425+
}
330426
}
331427

332428
// Copied from aster_common

0 commit comments

Comments
 (0)