Skip to content

[WIP] use modular_bitfield crate #282

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ links = "cortex-m" # prevent multiple versions of this crate to be linked toget
[dependencies]
bare-metal = { version = "0.2.0", features = ["const-fn"] }
volatile-register = "0.2.0"
bitfield = "0.13.2"
modular-bitfield = "0.11.2"
embedded-hal = "0.2.4"

[features]
Expand Down
48 changes: 24 additions & 24 deletions src/cmse.rs
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@
//! ```

use crate::asm::{tt, tta, ttat, ttt};
use bitfield::bitfield;
use modular_bitfield::bitfield;

/// Memory access behaviour: determine which privilege execution mode is used and which Memory
/// Protection Unit (MPU) is used.
Expand All @@ -60,35 +60,35 @@ pub struct TestTarget {
access_type: AccessType,
}

bitfield! {
/// Test Target Response Payload
///
/// Provides the response payload from a TT, TTA, TTT or TTAT instruction.
#[derive(PartialEq, Copy, Clone)]
struct TtResp(u32);
impl Debug;
mregion, _: 7, 0;
sregion, _: 15, 8;
mrvalid, _: 16;
srvalid, _: 17;
r, _: 18;
rw, _: 19;
nsr, _: 20;
nsrw, _: 21;
s, _: 22;
irvalid, _: 23;
iregion, _: 31, 24;
/// Test Target Response Payload
///
/// Provides the response payload from a TT, TTA, TTT or TTAT instruction.
#[bitfield]
#[repr(u32)]
#[derive(Debug, Copy, Clone, PartialEq)]
pub struct TtResp {
pub mregion: u8,
pub sregion: u8,
pub mrvalid: bool,
pub srvalid: bool,
pub r: bool,
pub rw: bool,
pub nsr: bool,
pub nsrw: bool,
pub s: bool,
pub irvalid: bool,
pub iregion: u8,
}

impl TestTarget {
/// Creates a Test Target Response Payload by testing addr using access_type.
#[inline]
pub fn check(addr: *mut u32, access_type: AccessType) -> Self {
let tt_resp = match access_type {
AccessType::Current => TtResp(tt(addr)),
AccessType::Unprivileged => TtResp(ttt(addr)),
AccessType::NonSecure => TtResp(tta(addr)),
AccessType::NonSecureUnprivileged => TtResp(ttat(addr)),
AccessType::Current => TtResp::from(tt(addr)),
AccessType::Unprivileged => TtResp::from(ttt(addr)),
AccessType::NonSecure => TtResp::from(tta(addr)),
AccessType::NonSecureUnprivileged => TtResp::from(ttat(addr)),
};

TestTarget {
Expand Down Expand Up @@ -138,7 +138,7 @@ impl TestTarget {
/// Get the raw u32 value returned by the TT instruction used.
#[inline]
pub fn as_u32(self) -> u32 {
self.tt_resp.0
u32::from(self.tt_resp)
}

/// Read accessibility of the target address. Only returns the MPU settings without checking
Expand Down
147 changes: 82 additions & 65 deletions src/peripheral/sau.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@

use crate::interrupt;
use crate::peripheral::SAU;
use bitfield::bitfield;
use modular_bitfield::prelude::*;
use volatile_register::{RO, RW};

/// Register block
Expand All @@ -31,75 +31,92 @@ pub struct RegisterBlock {
pub sfar: RO<Sfar>,
}

bitfield! {
/// Control Register description
#[repr(C)]
#[derive(Copy, Clone)]
pub struct Ctrl(u32);
get_enable, set_enable: 0;
get_allns, set_allns: 1;
#[bitfield(bits = 32)]
#[derive(Copy, Clone)]
#[repr(u32)]
/// Control Register description.
pub struct Ctrl {
pub enable: bool,
pub allns: bool,
#[skip]
__: B30,
}

bitfield! {
/// Type Register description
#[repr(C)]
#[derive(Copy, Clone)]
pub struct Type(u32);
u8;
sregion, _: 7, 0;
#[bitfield(bits = 32)]
#[derive(Copy, Clone)]
#[repr(C, u32)]
/// Type Register description.
pub struct Type {
#[skip(setters)]
pub sregion: u8,
#[skip]
__: B24,
}

bitfield! {
/// Region Number Register description
#[repr(C)]
#[derive(Copy, Clone)]
pub struct Rnr(u32);
u8;
get_region, set_region: 7, 0;
#[bitfield(bits = 32)]
#[derive(Copy, Clone)]
#[repr(C, u32)]
/// Region Number Register description.
pub struct Rnr {
pub region: u8,
#[skip]
__: B24,
}

bitfield! {
/// Region Base Address Register description
#[repr(C)]
#[derive(Copy, Clone)]
pub struct Rbar(u32);
u32;
get_baddr, set_baddr: 31, 5;
#[bitfield(bits = 32)]
#[derive(Copy, Clone)]
#[repr(C, u32)]
/// Region Base Address Register description.
pub struct Rbar {
#[skip]
__: B5,
pub baddr: B27,
}

bitfield! {
/// Region Limit Address Register description
#[repr(C)]
#[derive(Copy, Clone)]
pub struct Rlar(u32);
u32;
get_laddr, set_laddr: 31, 5;
get_nsc, set_nsc: 1;
get_enable, set_enable: 0;
#[bitfield(bits = 32)]
#[derive(Copy, Clone)]
#[repr(C, u32)]
/// Region Limit Address Register description.
pub struct Rlar {
pub enable: bool,
pub nsc: bool,
#[skip]
__: B3,
pub laddr: B27,
}

bitfield! {
/// Secure Fault Status Register description
#[repr(C)]
#[derive(Copy, Clone)]
pub struct Sfsr(u32);
invep, _: 0;
invis, _: 1;
inver, _: 2;
auviol, _: 3;
invtran, _: 4;
lsperr, _: 5;
sfarvalid, _: 6;
lserr, _: 7;
#[bitfield(bits = 32)]
#[derive(Copy, Clone)]
#[repr(C, u32)]
/// Secure Fault Status Register description.
pub struct Sfsr {
#[skip(setters)]
pub invep: bool,
#[skip(setters)]
pub invis: bool,
#[skip(setters)]
pub inver: bool,
#[skip(setters)]
pub auviol: bool,
#[skip(setters)]
pub invtran: bool,
#[skip(setters)]
pub lsperr: bool,
#[skip(setters)]
pub sfarvalid: bool,
#[skip(setters)]
pub lserr: bool,
#[skip]
__: B24,
}

bitfield! {
/// Secure Fault Address Register description
#[repr(C)]
#[derive(Copy, Clone)]
pub struct Sfar(u32);
u32;
address, _: 31, 0;
#[bitfield(bits = 32)]
#[derive(Copy, Clone)]
#[repr(C, u32)]
/// Secure Fault Address Register description.
pub struct Sfar {
#[skip(setters)]
pub address: u32,
}

/// Possible attribute of a SAU region.
Expand Down Expand Up @@ -176,9 +193,9 @@ impl SAU {
} else {
// All fields of these registers are going to be modified so we don't need to read them
// before.
let mut rnr = Rnr(0);
let mut rbar = Rbar(0);
let mut rlar = Rlar(0);
let mut rnr = Rnr::from(0u32);
let mut rbar = Rbar::from(0u32);
let mut rlar = Rlar::from(0u32);

rnr.set_region(region_number);
rbar.set_baddr(base_address >> 5);
Expand Down Expand Up @@ -220,21 +237,21 @@ impl SAU {
Err(SauError::RegionNumberTooBig)
} else {
unsafe {
self.rnr.write(Rnr(region_number.into()));
self.rnr.write(Rnr::from(region_number as u32));
}

let rbar = self.rbar.read();
let rlar = self.rlar.read();

let attribute = match (rlar.get_enable(), rlar.get_nsc()) {
let attribute = match (rlar.enable(), rlar.nsc()) {
(false, _) => SauRegionAttribute::Secure,
(true, false) => SauRegionAttribute::NonSecure,
(true, true) => SauRegionAttribute::NonSecureCallable,
};

Ok(SauRegion {
base_address: rbar.get_baddr() << 5,
limit_address: (rlar.get_laddr() << 5) | 0x1F,
base_address: rbar.baddr() << 5,
limit_address: (rlar.laddr() << 5) | 0x1F,
attribute,
})
}
Expand Down