Skip to content
Open
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
115 changes: 115 additions & 0 deletions cortex-m/src/asm.rs
Original file line number Diff line number Diff line change
Expand Up @@ -388,3 +388,118 @@ pub unsafe fn bootload(vector_table: *const u32) -> ! {
bootstrap(msp as *const u32, rv as *const u32);
}
}

/// This instruction moves one Register to a Coprocessor Register.
/// This function generates inline assembly and needs the instruction configuration
/// during compilation time (i.e. as `const`).
/// The values of the constants required by this function should be defined by
/// the coprocessor's reference manual.
/// - CP: The coprocessor's index.
/// - OP1: First optional operation for the coprocessor.
/// - CRN: Coprocessor register N.
/// - CRM: Coprocessor register M.
/// - OP2: Second optional operation for the coprocessor.
#[inline(always)]
#[asm_cfg(any(armv7m, armv8m))]
pub unsafe 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)
)
};
}

/// This instruction moves one Coprocessor Register to a Register.
/// This function generates inline assembly and needs the instruction configuration
/// during compilation time (i.e. as `const`).
/// The values of the constants required by this function should be defined by
/// the coprocessor's reference manual.
/// - CP: The coprocessor's index.
/// - OP1: First optional operation for the coprocessor.
/// - CRN: Coprocessor register N.
/// - CRM: Coprocessor register M.
/// - OP2: Second optional operation for the coprocessor.
#[inline(always)]
#[asm_cfg(any(armv7m, armv8m))]
pub unsafe fn mrc<const CP: u32, const OP1: u32, const CRN: u32, const CRM: u32, const OP2: u32>()
-> u32 {
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
}

/// This instruction moves two Registers to Coprocessor Registers.
/// This function generates inline assembly and needs the instruction configuration
/// during compilation time (i.e. as `const`).
/// The values of the constants required by this function should be defined by
/// the coprocessor's reference manual.
/// - CP: The coprocessor's index.
/// - OP1: First optional operation for the coprocessor.
/// - CRM: Coprocessor register M.
#[inline(always)]
#[asm_cfg(any(armv7m, armv8m))]
pub unsafe 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)
)
};
}

/// This instruction moves two Coprocessor Registers to Registers.
/// This function generates inline assembly and needs the instruction configuration
/// during compilation time (i.e. as `const`).
/// The values of the constants required by this function should be defined by
/// the coprocessor's reference manual.
/// - CP: The coprocessor's index.
/// - OP1: First optional operation for the coprocessor.
/// - CRM: Coprocessor register M.
#[inline(always)]
#[asm_cfg(any(armv7m, armv8m))]
pub unsafe 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)
}
Loading