Browse Source

pic: correct level triggered interrupts

Fabian 4 months ago
parent
commit
f3b34eae0a
1 changed files with 12 additions and 4 deletions
  1. 12 4
      src/rust/cpu/pic.rs

+ 12 - 4
src/rust/cpu/pic.rs

@@ -225,7 +225,7 @@ pub unsafe fn pic_set_irq(i: u8) {
 
     if i < 8 {
         let mask = 1 << i;
-        if master.irq_value & mask == 0 {
+        if master.irq_value & mask == 0 || master.elcr & mask != 0 {
             master.irr |= mask;
             master.irq_value |= mask;
             check_irqs(&mut master);
@@ -233,7 +233,7 @@ pub unsafe fn pic_set_irq(i: u8) {
     }
     else {
         let mask = 1 << (i - 8);
-        if slave.irq_value & mask == 0 {
+        if slave.irq_value & mask == 0 || slave.elcr & mask != 0 {
             slave.irr |= mask;
             slave.irq_value |= mask;
             check_irqs(&mut slave);
@@ -252,18 +252,26 @@ pub unsafe fn pic_clear_irq(i: u8) {
 
     if i < 8 {
         let mask = 1 << i;
-        if master.irq_value & mask != 0 {
+        if master.elcr & mask != 0 {
             master.irq_value &= !mask;
             master.irr &= !mask;
             check_irqs(&mut master);
         }
+        else if master.irq_value & mask != 0 {
+            master.irq_value &= !mask;
+            check_irqs(&mut master);
+        }
     } else {
         let mask = 1 << (i - 8);
-        if slave.irq_value & mask != 0 {
+        if slave.elcr & mask != 0 {
             slave.irq_value &= !mask;
             slave.irr &= !mask;
             check_irqs(&mut slave);
         }
+        else if slave.irq_value & mask != 0 {
+            slave.irq_value &= !mask;
+            check_irqs(&mut slave);
+        }
     }
 }