trace_mbox_irq_handle(MAILBOX_NAME, irq);
/* Schedule a rx_work to call the callback functions */
queue_work(mb_chann->work_q, &mb_chann->rx_work);
- /* Clear IOHUB register */
- mailbox_reg_write(mb_chann, mb_chann->iohub_int_addr, 0);
return IRQ_HANDLED;
}
return;
}
+again:
+ mailbox_reg_write(mb_chann, mb_chann->iohub_int_addr, 0);
+
while (1) {
/*
* If return is 0, keep consuming next message, until there is
if (unlikely(ret)) {
MB_ERR(mb_chann, "Unexpected ret %d, disable irq", ret);
WRITE_ONCE(mb_chann->bad_state, true);
- disable_irq(mb_chann->msix_irq);
- break;
+ return;
}
}
+
+ /*
+ * The hardware will not generate interrupt if firmware creates a new
+ * response right after driver clears interrupt register. Check
+ * the interrupt register to make sure there is not any new response
+ * before exiting.
+ */
+ if (mailbox_reg_read(mb_chann, mb_chann->iohub_int_addr))
+ goto again;
}
int xdna_mailbox_send_msg(struct mailbox_channel *mb_chann,