mpfs_hal/
lib.rs

1#![no_std]
2
3#[cfg(feature = "alloc")]
4mod alloc;
5#[cfg(feature = "alloc")]
6use alloc::init_heap;
7
8mod critical_section_impl;
9critical_section::set_impl!(critical_section_impl::MPFSCriticalSection);
10
11pub use mpfs_hal_procmacros::{hart1_main, hart2_main, hart3_main, hart4_main, init_once};
12
13mod mutex;
14pub use mutex::Mutex;
15
16pub use mpfs_pac as pac;
17pub use pac::hart_id;
18
19mod peripheral;
20pub use peripheral::*;
21
22#[cfg(feature = "print")]
23mod print;
24#[cfg(feature = "print")]
25pub use print::*;
26
27#[cfg(feature = "log")]
28mod logger;
29#[cfg(feature = "log")]
30pub use logger::init_logger;
31
32pub mod ethernet;
33pub mod gpio;
34pub mod qspi;
35pub mod uart;
36pub mod usb;
37
38//----------------------------------------------------------
39// Entry points
40
41extern "C" {
42    fn __init_once();
43    fn __init_once_embassy();
44    fn __hart1_entry();
45    fn __hart2_entry();
46    fn __hart3_entry();
47    fn __hart4_entry();
48}
49
50fn init_once() {
51    unsafe {
52        pac::mss_config_clk_rst(
53            pac::mss_peripherals__MSS_PERIPH_CFM,
54            pac::MPFS_HAL_FIRST_HART as u8,
55            pac::PERIPH_RESET_STATE__PERIPHERAL_ON,
56        );
57
58        #[cfg(feature = "alloc")]
59        init_heap();
60        #[cfg(feature = "print")]
61        init_print();
62
63        __init_once_embassy();
64        __init_once();
65    }
66}
67
68#[no_mangle]
69extern "C" fn u54_1() {
70    unsafe {
71        // Rest of hardware initialization
72        pac::clear_soft_interrupt();
73        core::arch::asm!("csrs mie, {}", const pac::MIP_MSIP, options(nomem, nostack));
74
75        pac::PLIC_init();
76        pac::__enable_irq();
77        // All other harts are put into wfi when they boot, so we can init_once from here
78        init_once();
79
80        // Now we wake up the other harts
81        pac::raise_soft_interrupt(2);
82        pac::raise_soft_interrupt(3);
83        pac::raise_soft_interrupt(4);
84
85        __hart1_entry();
86    }
87}
88
89#[no_mangle]
90extern "C" fn u54_2() {
91    unsafe {
92        // Rest of hardware initialization
93        pac::clear_soft_interrupt();
94        core::arch::asm!("csrs mie, {}", const pac::MIP_MSIP, options(nomem, nostack));
95        pac::PLIC_init();
96        pac::__enable_irq();
97
98        // Wait for the software interrupt
99        core::arch::asm!("wfi", options(nomem, nostack));
100        __hart2_entry();
101    }
102}
103
104#[no_mangle]
105extern "C" fn u54_3() {
106    unsafe {
107        // Rest of hardware initialization
108        pac::clear_soft_interrupt();
109        core::arch::asm!("csrs mie, {}", const pac::MIP_MSIP, options(nomem, nostack));
110        pac::PLIC_init();
111        pac::__enable_irq();
112
113        // Wait for the software interrupt
114        core::arch::asm!("wfi", options(nomem, nostack));
115        __hart3_entry();
116    }
117}
118
119#[no_mangle]
120extern "C" fn u54_4() {
121    unsafe {
122        // Rest of hardware initialization
123        pac::clear_soft_interrupt();
124        core::arch::asm!("csrs mie, {}", const pac::MIP_MSIP, options(nomem, nostack));
125        pac::PLIC_init();
126        pac::__enable_irq();
127
128        // Wait for the software interrupt
129        core::arch::asm!("wfi", options(nomem, nostack));
130
131        __hart4_entry();
132    }
133}