irq.c 1.1 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950
  1. #include "picorv32.h"
  2. #include "fw.h"
  3. #include "console.h"
  4. /* Invalid interrupt */
  5. static void spurious_irq_handler(unsigned int vector)
  6. {
  7. con_printf("spurious interrupt: %u\n", vector);
  8. mask_irq(vector);
  9. }
  10. /* Valid edge-triggered interrupt just to wake up waitirq */
  11. void null_irq_handler(unsigned int vector)
  12. {
  13. }
  14. /* __irq_handler_table must be in .sdata so it ends up in the zero page */
  15. irq_handler_t __attribute__((section(".sdata")))
  16. __irq_handler_table[IRQ_VECTORS] =
  17. { [0 ... IRQ_VECTORS-1] = spurious_irq_handler };
  18. irq_handler_t register_irq(unsigned int vector, irq_handler_t handler,
  19. bool enable)
  20. {
  21. irq_handler_t old_handler;
  22. if (vector >= IRQ_VECTORS)
  23. return NULL; /* Invalid vector */
  24. mask_irq(vector);
  25. if (!handler) {
  26. enable = false;
  27. handler = spurious_irq_handler;
  28. }
  29. old_handler = __irq_handler_table[vector];
  30. __irq_handler_table[vector] = handler;
  31. if (enable)
  32. unmask_irq(vector);
  33. if (old_handler == spurious_irq_handler)
  34. old_handler = NULL;
  35. con_printf("irq: register vector %u, handler = %p, mask = %08x\n",
  36. vector, handler, irqmask());
  37. return old_handler;
  38. }