Skip to content

Commit 2134146

Browse files
committed
Clean up mmu.rs
1 parent 1280d38 commit 2134146

File tree

7 files changed

+107
-155
lines changed

7 files changed

+107
-155
lines changed

11_virtual_memory/README.md

+33-49
Original file line numberDiff line numberDiff line change
@@ -265,7 +265,7 @@ make chainbot
265265
diff -uNr 10_privilege_level/src/arch/aarch64/mmu.rs 11_virtual_memory/src/arch/aarch64/mmu.rs
266266
--- 10_privilege_level/src/arch/aarch64/mmu.rs
267267
+++ 11_virtual_memory/src/arch/aarch64/mmu.rs
268-
@@ -0,0 +1,316 @@
268+
@@ -0,0 +1,300 @@
269269
+// SPDX-License-Identifier: MIT
270270
+//
271271
+// Copyright (c) 2018-2019 Andre Richter <[email protected]>
@@ -347,28 +347,32 @@ diff -uNr 10_privilege_level/src/arch/aarch64/mmu.rs 11_virtual_memory/src/arch/
347347
+ ]
348348
+}
349349
+
350-
+// Two newtypes for added type safety, so that you cannot accidentally place a TableDescriptor into
351-
+// a PageDescriptor slot in `struct PageTables`, and vice versa.
350+
+const SIXTYFOUR_KIB_SHIFT: usize = 16; // log2(64 * 1024)
351+
+const FIVETWELVE_MIB_SHIFT: usize = 29; // log2(512 * 1024 * 1024)
352+
+
353+
+/// A table descriptor for 64 KiB aperture.
354+
+///
355+
+/// The output points to the next table.
352356
+#[derive(Copy, Clone)]
353357
+#[repr(transparent)]
354-
+struct RawTableDescriptor(u64);
358+
+struct TableDescriptor(u64);
355359
+
360+
+/// A page descriptor with 64 KiB aperture.
361+
+///
362+
+/// The output points to physical memory.
356363
+#[derive(Copy, Clone)]
357364
+#[repr(transparent)]
358-
+struct RawPageDescriptor(u64);
359-
+
360-
+const SIXTYFOUR_KIB_SHIFT: usize = 16; // log2(64 * 1024)
361-
+const FIVETWELVE_MIB_SHIFT: usize = 29; // log2(512 * 1024 * 1024)
365+
+struct PageDescriptor(u64);
362366
+
363367
+/// Big monolithic struct for storing the page tables. Individual levels must be 64 KiB aligned,
364368
+/// hence the "reverse" order of appearance.
365369
+#[repr(C)]
366370
+#[repr(align(65536))]
367371
+struct PageTables<const N: usize> {
368372
+ // Page descriptors, covering 64 KiB windows per entry.
369-
+ lvl3: [[RawPageDescriptor; 8192]; N],
373+
+ lvl3: [[PageDescriptor; 8192]; N],
370374
+ // Table descriptors, covering 512 MiB windows.
371-
+ lvl2: [RawTableDescriptor; N],
375+
+ lvl2: [TableDescriptor; N],
372376
+}
373377
+
374378
+/// Usually evaluates to 1 GiB for RPi3 and 4 GiB for RPi 4.
@@ -378,8 +382,8 @@ diff -uNr 10_privilege_level/src/arch/aarch64/mmu.rs 11_virtual_memory/src/arch/
378382
+///
379383
+/// Supposed to land in `.bss`. Therefore, ensure that they boil down to all "0" entries.
380384
+static mut TABLES: PageTables<{ ENTRIES_512_MIB }> = PageTables {
381-
+ lvl3: [[RawPageDescriptor(0); 8192]; ENTRIES_512_MIB],
382-
+ lvl2: [RawTableDescriptor(0); ENTRIES_512_MIB],
385+
+ lvl3: [[PageDescriptor(0); 8192]; ENTRIES_512_MIB],
386+
+ lvl2: [TableDescriptor(0); ENTRIES_512_MIB],
383387
+};
384388
+
385389
+trait BaseAddr {
@@ -397,24 +401,15 @@ diff -uNr 10_privilege_level/src/arch/aarch64/mmu.rs 11_virtual_memory/src/arch/
397401
+ }
398402
+}
399403
+
400-
+/// A descriptor pointing to the next page table.
401-
+struct TableDescriptor(register::FieldValue<u64, STAGE1_TABLE_DESCRIPTOR::Register>);
402-
+
403-
+impl TableDescriptor {
404-
+ fn new(next_lvl_table_addr: usize) -> TableDescriptor {
404+
+impl convert::From<usize> for TableDescriptor {
405+
+ fn from(next_lvl_table_addr: usize) -> Self {
405406
+ let shifted = next_lvl_table_addr >> SIXTYFOUR_KIB_SHIFT;
407+
+ let val = (STAGE1_TABLE_DESCRIPTOR::VALID::True
408+
+ + STAGE1_TABLE_DESCRIPTOR::TYPE::Table
409+
+ + STAGE1_TABLE_DESCRIPTOR::NEXT_LEVEL_TABLE_ADDR_64KiB.val(shifted as u64))
410+
+ .value;
406411
+
407-
+ TableDescriptor(
408-
+ STAGE1_TABLE_DESCRIPTOR::VALID::True
409-
+ + STAGE1_TABLE_DESCRIPTOR::TYPE::Table
410-
+ + STAGE1_TABLE_DESCRIPTOR::NEXT_LEVEL_TABLE_ADDR_64KiB.val(shifted as u64),
411-
+ )
412-
+ }
413-
+}
414-
+
415-
+impl convert::From<TableDescriptor> for RawTableDescriptor {
416-
+ fn from(desc: TableDescriptor) -> Self {
417-
+ RawTableDescriptor(desc.0.value)
412+
+ TableDescriptor(val)
418413
+ }
419414
+}
420415
+
@@ -452,28 +447,17 @@ diff -uNr 10_privilege_level/src/arch/aarch64/mmu.rs 11_virtual_memory/src/arch/
452447
+ }
453448
+}
454449
+
455-
+/// A page descriptor with 64 KiB aperture.
456-
+///
457-
+/// The output points to physical memory.
458-
+struct PageDescriptor(register::FieldValue<u64, STAGE1_PAGE_DESCRIPTOR::Register>);
459-
+
460450
+impl PageDescriptor {
461451
+ fn new(output_addr: usize, attribute_fields: AttributeFields) -> PageDescriptor {
462452
+ let shifted = output_addr >> SIXTYFOUR_KIB_SHIFT;
463-
+
464-
+ PageDescriptor(
465-
+ STAGE1_PAGE_DESCRIPTOR::VALID::True
466-
+ + STAGE1_PAGE_DESCRIPTOR::AF::True
467-
+ + attribute_fields.into()
468-
+ + STAGE1_PAGE_DESCRIPTOR::TYPE::Table
469-
+ + STAGE1_PAGE_DESCRIPTOR::OUTPUT_ADDR_64KiB.val(shifted as u64),
470-
+ )
471-
+ }
472-
+}
473-
+
474-
+impl convert::From<PageDescriptor> for RawPageDescriptor {
475-
+ fn from(desc: PageDescriptor) -> Self {
476-
+ RawPageDescriptor(desc.0.value)
453+
+ let val = (STAGE1_PAGE_DESCRIPTOR::VALID::True
454+
+ + STAGE1_PAGE_DESCRIPTOR::AF::True
455+
+ + attribute_fields.into()
456+
+ + STAGE1_PAGE_DESCRIPTOR::TYPE::Table
457+
+ + STAGE1_PAGE_DESCRIPTOR::OUTPUT_ADDR_64KiB.val(shifted as u64))
458+
+ .value;
459+
+
460+
+ PageDescriptor(val)
477461
+ }
478462
+}
479463
+
@@ -505,15 +489,15 @@ diff -uNr 10_privilege_level/src/arch/aarch64/mmu.rs 11_virtual_memory/src/arch/
505489
+/// - Modifies a `static mut`. Ensure it only happens from here.
506490
+unsafe fn populate_pt_entries() -> Result<(), &'static str> {
507491
+ for (l2_nr, l2_entry) in TABLES.lvl2.iter_mut().enumerate() {
508-
+ *l2_entry = TableDescriptor::new(TABLES.lvl3[l2_nr].base_addr_usize()).into();
492+
+ *l2_entry = TABLES.lvl3[l2_nr].base_addr_usize().into();
509493
+
510494
+ for (l3_nr, l3_entry) in TABLES.lvl3[l2_nr].iter_mut().enumerate() {
511495
+ let virt_addr = (l2_nr << FIVETWELVE_MIB_SHIFT) + (l3_nr << SIXTYFOUR_KIB_SHIFT);
512496
+
513497
+ let (output_addr, attribute_fields) =
514498
+ bsp::virt_mem_layout().get_virt_addr_properties(virt_addr)?;
515499
+
516-
+ *l3_entry = PageDescriptor::new(output_addr, attribute_fields).into();
500+
+ *l3_entry = PageDescriptor::new(output_addr, attribute_fields);
517501
+ }
518502
+ }
519503
+

11_virtual_memory/kernel

-8 Bytes
Binary file not shown.

11_virtual_memory/src/arch/aarch64/mmu.rs

+32-48
Original file line numberDiff line numberDiff line change
@@ -79,28 +79,32 @@ register_bitfields! {u64,
7979
]
8080
}
8181

82-
// Two newtypes for added type safety, so that you cannot accidentally place a TableDescriptor into
83-
// a PageDescriptor slot in `struct PageTables`, and vice versa.
82+
const SIXTYFOUR_KIB_SHIFT: usize = 16; // log2(64 * 1024)
83+
const FIVETWELVE_MIB_SHIFT: usize = 29; // log2(512 * 1024 * 1024)
84+
85+
/// A table descriptor for 64 KiB aperture.
86+
///
87+
/// The output points to the next table.
8488
#[derive(Copy, Clone)]
8589
#[repr(transparent)]
86-
struct RawTableDescriptor(u64);
90+
struct TableDescriptor(u64);
8791

92+
/// A page descriptor with 64 KiB aperture.
93+
///
94+
/// The output points to physical memory.
8895
#[derive(Copy, Clone)]
8996
#[repr(transparent)]
90-
struct RawPageDescriptor(u64);
91-
92-
const SIXTYFOUR_KIB_SHIFT: usize = 16; // log2(64 * 1024)
93-
const FIVETWELVE_MIB_SHIFT: usize = 29; // log2(512 * 1024 * 1024)
97+
struct PageDescriptor(u64);
9498

9599
/// Big monolithic struct for storing the page tables. Individual levels must be 64 KiB aligned,
96100
/// hence the "reverse" order of appearance.
97101
#[repr(C)]
98102
#[repr(align(65536))]
99103
struct PageTables<const N: usize> {
100104
// Page descriptors, covering 64 KiB windows per entry.
101-
lvl3: [[RawPageDescriptor; 8192]; N],
105+
lvl3: [[PageDescriptor; 8192]; N],
102106
// Table descriptors, covering 512 MiB windows.
103-
lvl2: [RawTableDescriptor; N],
107+
lvl2: [TableDescriptor; N],
104108
}
105109

106110
/// Usually evaluates to 1 GiB for RPi3 and 4 GiB for RPi 4.
@@ -110,8 +114,8 @@ const ENTRIES_512_MIB: usize = bsp::addr_space_size() >> FIVETWELVE_MIB_SHIFT;
110114
///
111115
/// Supposed to land in `.bss`. Therefore, ensure that they boil down to all "0" entries.
112116
static mut TABLES: PageTables<{ ENTRIES_512_MIB }> = PageTables {
113-
lvl3: [[RawPageDescriptor(0); 8192]; ENTRIES_512_MIB],
114-
lvl2: [RawTableDescriptor(0); ENTRIES_512_MIB],
117+
lvl3: [[PageDescriptor(0); 8192]; ENTRIES_512_MIB],
118+
lvl2: [TableDescriptor(0); ENTRIES_512_MIB],
115119
};
116120

117121
trait BaseAddr {
@@ -129,24 +133,15 @@ impl<T, const N: usize> BaseAddr for [T; N] {
129133
}
130134
}
131135

132-
/// A descriptor pointing to the next page table.
133-
struct TableDescriptor(register::FieldValue<u64, STAGE1_TABLE_DESCRIPTOR::Register>);
134-
135-
impl TableDescriptor {
136-
fn new(next_lvl_table_addr: usize) -> TableDescriptor {
136+
impl convert::From<usize> for TableDescriptor {
137+
fn from(next_lvl_table_addr: usize) -> Self {
137138
let shifted = next_lvl_table_addr >> SIXTYFOUR_KIB_SHIFT;
139+
let val = (STAGE1_TABLE_DESCRIPTOR::VALID::True
140+
+ STAGE1_TABLE_DESCRIPTOR::TYPE::Table
141+
+ STAGE1_TABLE_DESCRIPTOR::NEXT_LEVEL_TABLE_ADDR_64KiB.val(shifted as u64))
142+
.value;
138143

139-
TableDescriptor(
140-
STAGE1_TABLE_DESCRIPTOR::VALID::True
141-
+ STAGE1_TABLE_DESCRIPTOR::TYPE::Table
142-
+ STAGE1_TABLE_DESCRIPTOR::NEXT_LEVEL_TABLE_ADDR_64KiB.val(shifted as u64),
143-
)
144-
}
145-
}
146-
147-
impl convert::From<TableDescriptor> for RawTableDescriptor {
148-
fn from(desc: TableDescriptor) -> Self {
149-
RawTableDescriptor(desc.0.value)
144+
TableDescriptor(val)
150145
}
151146
}
152147

@@ -184,28 +179,17 @@ impl convert::From<AttributeFields>
184179
}
185180
}
186181

187-
/// A page descriptor with 64 KiB aperture.
188-
///
189-
/// The output points to physical memory.
190-
struct PageDescriptor(register::FieldValue<u64, STAGE1_PAGE_DESCRIPTOR::Register>);
191-
192182
impl PageDescriptor {
193183
fn new(output_addr: usize, attribute_fields: AttributeFields) -> PageDescriptor {
194184
let shifted = output_addr >> SIXTYFOUR_KIB_SHIFT;
195-
196-
PageDescriptor(
197-
STAGE1_PAGE_DESCRIPTOR::VALID::True
198-
+ STAGE1_PAGE_DESCRIPTOR::AF::True
199-
+ attribute_fields.into()
200-
+ STAGE1_PAGE_DESCRIPTOR::TYPE::Table
201-
+ STAGE1_PAGE_DESCRIPTOR::OUTPUT_ADDR_64KiB.val(shifted as u64),
202-
)
203-
}
204-
}
205-
206-
impl convert::From<PageDescriptor> for RawPageDescriptor {
207-
fn from(desc: PageDescriptor) -> Self {
208-
RawPageDescriptor(desc.0.value)
185+
let val = (STAGE1_PAGE_DESCRIPTOR::VALID::True
186+
+ STAGE1_PAGE_DESCRIPTOR::AF::True
187+
+ attribute_fields.into()
188+
+ STAGE1_PAGE_DESCRIPTOR::TYPE::Table
189+
+ STAGE1_PAGE_DESCRIPTOR::OUTPUT_ADDR_64KiB.val(shifted as u64))
190+
.value;
191+
192+
PageDescriptor(val)
209193
}
210194
}
211195

@@ -237,15 +221,15 @@ fn set_up_mair() {
237221
/// - Modifies a `static mut`. Ensure it only happens from here.
238222
unsafe fn populate_pt_entries() -> Result<(), &'static str> {
239223
for (l2_nr, l2_entry) in TABLES.lvl2.iter_mut().enumerate() {
240-
*l2_entry = TableDescriptor::new(TABLES.lvl3[l2_nr].base_addr_usize()).into();
224+
*l2_entry = TABLES.lvl3[l2_nr].base_addr_usize().into();
241225

242226
for (l3_nr, l3_entry) in TABLES.lvl3[l2_nr].iter_mut().enumerate() {
243227
let virt_addr = (l2_nr << FIVETWELVE_MIB_SHIFT) + (l3_nr << SIXTYFOUR_KIB_SHIFT);
244228

245229
let (output_addr, attribute_fields) =
246230
bsp::virt_mem_layout().get_virt_addr_properties(virt_addr)?;
247231

248-
*l3_entry = PageDescriptor::new(output_addr, attribute_fields).into();
232+
*l3_entry = PageDescriptor::new(output_addr, attribute_fields);
249233
}
250234
}
251235

12_cpu_exceptions_part1/README.md

+10-10
Original file line numberDiff line numberDiff line change
@@ -459,9 +459,9 @@ General purpose register:
459459
## Diff to previous
460460
```diff
461461

462-
diff -uNr 11_virtual_memory/src/arch/aarch64/exception.rs 12_exceptions_part1/src/arch/aarch64/exception.rs
462+
diff -uNr 11_virtual_memory/src/arch/aarch64/exception.rs 12_cpu_exceptions_part1/src/arch/aarch64/exception.rs
463463
--- 11_virtual_memory/src/arch/aarch64/exception.rs
464-
+++ 12_exceptions_part1/src/arch/aarch64/exception.rs
464+
+++ 12_cpu_exceptions_part1/src/arch/aarch64/exception.rs
465465
@@ -4,12 +4,248 @@
466466

467467
//! Exception handling.
@@ -713,9 +713,9 @@ diff -uNr 11_virtual_memory/src/arch/aarch64/exception.rs 12_exceptions_part1/sr
713713
fn daif_field() -> register::Field<u32, DAIF::Register>;
714714
}
715715

716-
diff -uNr 11_virtual_memory/src/arch/aarch64/exception.S 12_exceptions_part1/src/arch/aarch64/exception.S
716+
diff -uNr 11_virtual_memory/src/arch/aarch64/exception.S 12_cpu_exceptions_part1/src/arch/aarch64/exception.S
717717
--- 11_virtual_memory/src/arch/aarch64/exception.S
718-
+++ 12_exceptions_part1/src/arch/aarch64/exception.S
718+
+++ 12_cpu_exceptions_part1/src/arch/aarch64/exception.S
719719
@@ -0,0 +1,135 @@
720720
+// SPDX-License-Identifier: MIT
721721
+//
@@ -853,9 +853,9 @@ diff -uNr 11_virtual_memory/src/arch/aarch64/exception.S 12_exceptions_part1/src
853853
+
854854
+ eret
855855

856-
diff -uNr 11_virtual_memory/src/arch/aarch64.rs 12_exceptions_part1/src/arch/aarch64.rs
856+
diff -uNr 11_virtual_memory/src/arch/aarch64.rs 12_cpu_exceptions_part1/src/arch/aarch64.rs
857857
--- 11_virtual_memory/src/arch/aarch64.rs
858-
+++ 12_exceptions_part1/src/arch/aarch64.rs
858+
+++ 12_cpu_exceptions_part1/src/arch/aarch64.rs
859859
@@ -106,6 +106,15 @@
860860
}
861861
}
@@ -873,9 +873,9 @@ diff -uNr 11_virtual_memory/src/arch/aarch64.rs 12_exceptions_part1/src/arch/aar
873873
pub fn mmu() -> &'static impl interface::mm::MMU {
874874
&MMU
875875

876-
diff -uNr 11_virtual_memory/src/bsp.rs 12_exceptions_part1/src/bsp.rs
876+
diff -uNr 11_virtual_memory/src/bsp.rs 12_cpu_exceptions_part1/src/bsp.rs
877877
--- 11_virtual_memory/src/bsp.rs
878-
+++ 12_exceptions_part1/src/bsp.rs
878+
+++ 12_cpu_exceptions_part1/src/bsp.rs
879879
@@ -4,7 +4,7 @@
880880

881881
//! Conditional exporting of Board Support Packages.
@@ -886,9 +886,9 @@ diff -uNr 11_virtual_memory/src/bsp.rs 12_exceptions_part1/src/bsp.rs
886886
#[cfg(any(feature = "bsp_rpi3", feature = "bsp_rpi4"))]
887887
mod rpi;
888888

889-
diff -uNr 11_virtual_memory/src/main.rs 12_exceptions_part1/src/main.rs
889+
diff -uNr 11_virtual_memory/src/main.rs 12_cpu_exceptions_part1/src/main.rs
890890
--- 11_virtual_memory/src/main.rs
891-
+++ 12_exceptions_part1/src/main.rs
891+
+++ 12_cpu_exceptions_part1/src/main.rs
892892
@@ -22,6 +22,7 @@
893893
#![allow(incomplete_features)]
894894
#![feature(const_generics)]

12_cpu_exceptions_part1/kernel

-32 Bytes
Binary file not shown.

12_cpu_exceptions_part1/kernel8.img

0 Bytes
Binary file not shown.

0 commit comments

Comments
 (0)