Skip to content

Commit

Permalink
Cleanup const_fn!
Browse files Browse the repository at this point in the history
Fixes #222

The following methods can be made `const` on stable:
  - `GlobalDescriptorTable::from_raw_slice`
  - `MappedFrame::{start_address, size}`
  - `Page<Size4KiB>::p1_index`

The remaining functions still need `const_fn` because:
  - Some GDT methods use `&mut self`
  - The IDT uses function pointers as a type argument
  - The PageSize marker trait is used all over

Comments were updated where appropriate.

Signed-off-by: Joe Richey <[email protected]>
  • Loading branch information
josephlr committed May 14, 2021
1 parent f232228 commit 8dd7bf4
Show file tree
Hide file tree
Showing 6 changed files with 25 additions and 39 deletions.
8 changes: 4 additions & 4 deletions src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,10 +2,10 @@
//! and access to various system registers.
#![cfg_attr(not(test), no_std)]
#![cfg_attr(feature = "const_fn", feature(const_panic))]
#![cfg_attr(feature = "const_fn", feature(const_mut_refs))]
#![cfg_attr(feature = "const_fn", feature(const_fn_fn_ptr_basics))]
#![cfg_attr(feature = "const_fn", feature(const_fn_trait_bound))]
#![cfg_attr(feature = "const_fn", feature(const_panic))] // Better panic messages
#![cfg_attr(feature = "const_fn", feature(const_mut_refs))] // GDT add_entry()
#![cfg_attr(feature = "const_fn", feature(const_fn_fn_ptr_basics))] // IDT new()
#![cfg_attr(feature = "const_fn", feature(const_fn_trait_bound))] // PageSize marker trait
#![cfg_attr(feature = "inline_asm", feature(asm))]
#![cfg_attr(feature = "abi_x86_interrupt", feature(abi_x86_interrupt))]
#![cfg_attr(docsrs, feature(doc_cfg))]
Expand Down
5 changes: 4 additions & 1 deletion src/structures/gdt.rs
Original file line number Diff line number Diff line change
Expand Up @@ -112,12 +112,15 @@ impl GlobalDescriptorTable {
/// * The user must make sure that the entries are well formed
/// * The provided slice **must not be larger than 8 items** (only up to the first 8 will be observed.)
#[inline]
#[cfg(feature = "const_fn")]
pub const unsafe fn from_raw_slice(slice: &[u64]) -> GlobalDescriptorTable {
#[cfg(feature = "const_fn")]
assert!(
slice.len() <= 8,
"initializing a GDT from a slice requires it to be **at most** 8 elements."
);
#[cfg(not(feature = "const_fn"))]
slice[7]; // Will fail if len > 8

let next_free = slice.len();

let mut table = [0; 8];
Expand Down
2 changes: 1 addition & 1 deletion src/structures/paging/frame.rs
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ use core::ops::{Add, AddAssign, Sub, SubAssign};
#[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord)]
#[repr(C)]
pub struct PhysFrame<S: PageSize = Size4KiB> {
start_address: PhysAddr,
pub(crate) start_address: PhysAddr, // TODO: remove when start_address() is const
size: PhantomData<S>,
}

Expand Down
28 changes: 12 additions & 16 deletions src/structures/paging/mapper/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -85,25 +85,21 @@ pub enum MappedFrame {
}

impl MappedFrame {
const_fn! {
/// Returns the start address of the frame.
pub fn start_address(&self) -> PhysAddr {
match self {
MappedFrame::Size4KiB(frame) => frame.start_address(),
MappedFrame::Size2MiB(frame) => frame.start_address(),
MappedFrame::Size1GiB(frame) => frame.start_address(),
}
/// Returns the start address of the frame.
pub const fn start_address(&self) -> PhysAddr {
match self {
MappedFrame::Size4KiB(frame) => frame.start_address,
MappedFrame::Size2MiB(frame) => frame.start_address,
MappedFrame::Size1GiB(frame) => frame.start_address,
}
}

const_fn! {
/// Returns the size the frame (4KB, 2MB or 1GB).
pub fn size(&self) -> u64 {
match self {
MappedFrame::Size4KiB(frame) => frame.size(),
MappedFrame::Size2MiB(frame) => frame.size(),
MappedFrame::Size1GiB(frame) => frame.size(),
}
/// Returns the size the frame (4KB, 2MB or 1GB).
pub const fn size(&self) -> u64 {
match self {
MappedFrame::Size4KiB(_) => Size4KiB::SIZE,
MappedFrame::Size2MiB(_) => Size2MiB::SIZE,
MappedFrame::Size1GiB(_) => Size1GiB::SIZE,
}
}
}
Expand Down
10 changes: 4 additions & 6 deletions src/structures/paging/page.rs
Original file line number Diff line number Diff line change
Expand Up @@ -210,12 +210,10 @@ impl Page<Size4KiB> {
Page::containing_address(VirtAddr::new(addr))
}

const_fn! {
/// Returns the level 1 page table index of this page.
#[inline]
pub fn p1_index(self) -> PageTableIndex {
self.start_address().p1_index()
}
/// Returns the level 1 page table index of this page.
#[inline]
pub const fn p1_index(self) -> PageTableIndex {
self.start_address.p1_index()
}
}

Expand Down
11 changes: 0 additions & 11 deletions src/structures/paging/page_table.rs
Original file line number Diff line number Diff line change
Expand Up @@ -189,7 +189,6 @@ pub struct PageTable {

impl PageTable {
/// Creates an empty page table.
#[cfg(feature = "const_fn")]
#[inline]
pub const fn new() -> Self {
const EMPTY: PageTableEntry = PageTableEntry::new();
Expand All @@ -198,16 +197,6 @@ impl PageTable {
}
}

/// Creates an empty page table.
#[cfg(not(feature = "const_fn"))]
#[inline]
pub fn new() -> Self {
const EMPTY: PageTableEntry = PageTableEntry::new();
PageTable {
entries: [EMPTY; ENTRY_COUNT],
}
}

/// Clears all entries.
#[inline]
pub fn zero(&mut self) {
Expand Down

0 comments on commit 8dd7bf4

Please sign in to comment.