Skip to content

Implement coprocessor access instructions #531

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

Open
wants to merge 6 commits into
base: master
Choose a base branch
from
Open
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
90 changes: 90 additions & 0 deletions cortex-m/src/coprocessor.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
//! Coprocessor access assembly instructions.



/// Internal function to create an inlined MCR instruction.
/// This instruction moves one Register to a Coprocessor Register.
#[inline(always)]
pub fn mcr<const CP: u32, const OP1: u32, const CRN: u32, const CRM: u32, const OP2: u32>(value: u32) {
unsafe {
core::arch::asm!(
"MCR p{cp}, #{op1}, {0}, c{crn}, c{crm}, #{op2}",
in(reg) value,
cp = const CP,
op1 = const OP1,
crn = const CRN,
crm = const CRM,
op2 = const OP2,
options(nostack, nomem)
)
}
}



/// Internal function to create an inlined MRC instruction.
/// This instruction moves one Coprocessor Register to a Register.
#[inline(always)]
pub fn mrc<const CP: u32, const OP1: u32, const CRN: u32, const CRM: u32, const OP2: u32>() -> u32 {
// Preallocate the value.
let a: u32;

unsafe {
core::arch::asm!(
"MRC p{cp}, #{op1}, {0}, c{crn}, c{crm}, #{op2}",
out(reg) a,
cp = const CP,
op1 = const OP1,
crn = const CRN,
crm = const CRM,
op2 = const OP2,
options(nostack, nomem)
)
}

a
}



/// Internal function to create an inlined MCRR instruction.
/// This instruction moves two Registers to Coprocessor Registers.
#[inline(always)]
pub fn mcrr<const CP: u32, const OP1: u32, const CRM: u32>(a: u32, b: u32) {
unsafe {
core::arch::asm!(
"MCRR p{cp}, #{op1}, {0}, {1}, c{crm}",
in(reg) a,
in(reg) b,
cp = const CP,
op1 = const OP1,
crm = const CRM,
options(nostack, nomem)
)
}
}



/// Internal function to create an inlined MRRC instruction.
/// This instruction moves two Coprocessor Registers to Registers.
#[inline(always)]
pub fn mrrc<const CP: u32, const OPC: u32, const CRM: u32>() -> (u32, u32) {
// Preallocate the values.
let a: u32;
let b: u32;

unsafe {
core::arch::asm!(
"MRRC p{cp}, #{opc}, {0}, {1}, c{crm}",
out(reg) a,
out(reg) b,
cp = const CP,
opc = const OPC,
crm = const CRM,
options(nostack, nomem)
)
}

(a, b)
}
2 changes: 2 additions & 0 deletions cortex-m/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,8 @@ mod macros;
pub mod asm;
#[cfg(armv8m)]
pub mod cmse;
#[cfg(not(armv6m))]
pub mod coprocessor;
pub mod delay;
pub mod interrupt;
#[cfg(all(not(armv6m), not(armv8m_base)))]
Expand Down