浏览代码

Inter-core interrupt

luojia65 4 年之前
父节点
当前提交
a2c60ef6db
共有 1 个文件被更改,包括 45 次插入16 次删除
  1. 45 16
      platform/k210/src/main.rs

+ 45 - 16
platform/k210/src/main.rs

@@ -31,11 +31,32 @@ fn oom(_layout: Layout) -> ! {
 }
 
 fn mp_hook() -> bool {
-    match mhartid::read() {
-        0 => true,
-        _ => loop {
-            unsafe { riscv::asm::wfi() }
-        },
+    use riscv::asm::wfi;
+    use k210_hal::clint::msip;
+
+    let hartid = mhartid::read();
+    if hartid == 0 {
+        true
+    } else {
+        unsafe {
+            // Clear IPI
+            msip::set_value(hartid, false);
+            // Start listening for software interrupts
+            mie::set_msoft();
+
+            loop {
+                wfi();
+                if mip::read().msoft() {
+                    break;
+                }
+            }
+
+            // Stop listening for software interrupts
+            mie::clear_msoft();
+            // Clear IPI
+            msip::set_value(hartid, false);
+        }
+        false
     }
 }
 
@@ -119,6 +140,25 @@ fn main() -> ! {
         let (tx, rx) = serial.split();
         use rustsbi::legacy_stdio::init_legacy_stdio_embedded_hal_fuse;
         init_legacy_stdio_embedded_hal_fuse(tx, rx);
+
+        struct Ipi;
+
+        impl rustsbi::Ipi for Ipi {
+            fn max_hart_id(&self) -> usize {
+                1
+            }
+            fn send_ipi_many(&mut self, hart_mask: rustsbi::HartMask) {
+                use k210_hal::clint::msip;
+                for i in 0..=1 {
+                    if hart_mask.has_bit(i) {
+                        msip::set_value(i, true);
+                        msip::set_value(i, false);
+                    }
+                }
+            }
+        }
+        use rustsbi::init_ipi;
+        init_ipi(Ipi);
     }
     
     unsafe {
@@ -243,17 +283,6 @@ _start_trap:
 "
 );
 
-// #[doc(hidden)]
-// #[export_name = "_mp_hook"]
-// pub extern "Rust" fn _mp_hook() -> bool {
-//     match mhartid::read() {
-//         0 => true,
-//         _ => loop {
-//             unsafe { riscv::asm::wfi() }
-//         },
-//     }
-// }
-
 #[allow(unused)]
 struct TrapFrame {
     ra: usize,