diff --git a/devices/ioctrl/maciobase.cpp b/devices/ioctrl/maciobase.cpp index b2bca143b8..c2f74b53fb 100644 --- a/devices/ioctrl/maciobase.cpp +++ b/devices/ioctrl/maciobase.cpp @@ -145,9 +145,9 @@ void MacIoBase::ack_int_common(uint64_t irq_id, uint8_t irq_line_state) { if ((this->int_mask & MACIO_INT_MODE) || (irq_line_state && !(this->int_levels & irq_id))) { this->int_events |= irq_id; - } else { - this->int_events &= ~irq_id; } + // Events remain latched until software writes InterruptClear. + // update IRQ line state if (irq_line_state) { this->int_levels |= irq_id; diff --git a/devices/ioctrl/maciotwo.cpp b/devices/ioctrl/maciotwo.cpp index ce9ba17366..40ced99a8d 100644 --- a/devices/ioctrl/maciotwo.cpp +++ b/devices/ioctrl/maciotwo.cpp @@ -366,7 +366,10 @@ void MacIoTwo::mio_ctrl_write(uint32_t offset, uint32_t value, int size) { switch (offset & ~3) { case MIO_INT_MASK2: - this->int_mask |= uint64_t(value & ~MACIO_INT_MODE) << 32; + // Preserve the first bank and the read-only IntMode bit. + this->int_mask = (this->int_mask & 0x80000000FFFFFFFFULL) | + (uint64_t(value & ~MACIO_INT_MODE) << 32); + this->clear_cpu_int(); this->signal_cpu_int(); break; case MIO_INT_CLEAR2: @@ -377,6 +380,7 @@ void MacIoTwo::mio_ctrl_write(uint32_t offset, uint32_t value, int size) { this->int_mask = (this->int_mask & 0x7FFFFFFF00000000ULL) | value; // copy IntMode bit to InterruptMask2 register this->int_mask |= uint64_t(this->int_mask & MACIO_INT_MODE) << 32; + this->clear_cpu_int(); this->signal_cpu_int(); break; case MIO_INT_CLEAR1: