interrupt.c 2.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129
  1. /*
  2. * File : interrupt.c
  3. * This file is part of RT-Thread RTOS
  4. * COPYRIGHT (C) 2006 - 2010, RT-Thread Development Team
  5. *
  6. * The license and distribution terms for this file may be
  7. * found in the file LICENSE in this distribution or at
  8. * http://www.rt-thread.org/license/LICENSE
  9. *
  10. * Change Logs:
  11. * Date Author Notes
  12. * 2010-10-15 Bernard first version
  13. */
  14. #include <rtthread.h>
  15. #include "soc3210.h"
  16. #define MAX_INTR 32
  17. extern rt_uint32_t rt_interrupt_nest;
  18. rt_uint32_t rt_interrupt_from_thread, rt_interrupt_to_thread;
  19. rt_uint32_t rt_thread_switch_interrput_flag;
  20. static rt_isr_handler_t irq_handle_table[MAX_INTR];
  21. void rt_interrupt_dispatch(void *ptreg);
  22. void rt_hw_timer_handler();
  23. /**
  24. * @addtogroup Loogonson SoC3210
  25. */
  26. /*@{*/
  27. void rt_hw_interrupt_handler(int vector)
  28. {
  29. rt_kprintf("Unhandled interrupt %d occured!!!\n", vector);
  30. }
  31. /**
  32. * This function will initialize hardware interrupt
  33. */
  34. void rt_hw_interrupt_init()
  35. {
  36. rt_int32_t index;
  37. for (index = 0; index < MAX_INTR; index ++)
  38. {
  39. irq_handle_table[index] = (rt_isr_handler_t)rt_hw_interrupt_handler;
  40. }
  41. /* init interrupt nest, and context in thread sp */
  42. rt_interrupt_nest = 0;
  43. rt_interrupt_from_thread = 0;
  44. rt_interrupt_to_thread = 0;
  45. rt_thread_switch_interrput_flag = 0;
  46. }
  47. /**
  48. * This function will mask a interrupt.
  49. * @param vector the interrupt number
  50. */
  51. void rt_hw_interrupt_mask(int vector)
  52. {
  53. /* mask interrupt */
  54. INT_EN &= ~(1 << vector);
  55. }
  56. /**
  57. * This function will un-mask a interrupt.
  58. * @param vector the interrupt number
  59. */
  60. void rt_hw_interrupt_umask(int vector)
  61. {
  62. INT_EN |= (1 << vector);
  63. }
  64. /**
  65. * This function will install a interrupt service routine to a interrupt.
  66. * @param vector the interrupt number
  67. * @param new_handler the interrupt service routine to be installed
  68. * @param old_handler the old interrupt service routine
  69. */
  70. void rt_hw_interrupt_install(int vector, rt_isr_handler_t new_handler, rt_isr_handler_t *old_handler)
  71. {
  72. if (vector >= 0 && vector < MAX_INTR)
  73. {
  74. if (old_handler != RT_NULL)
  75. *old_handler = irq_handle_table[vector];
  76. if (new_handler != RT_NULL)
  77. irq_handle_table[vector] = (rt_isr_handler_t)new_handler;
  78. }
  79. }
  80. void rt_interrupt_dispatch(void *ptreg)
  81. {
  82. int i;
  83. rt_isr_handler_t irq_func;
  84. static rt_uint32_t status = 0;
  85. rt_uint32_t c0_status;
  86. /* check os timer */
  87. c0_status = read_c0_status();
  88. if (c0_status & 0x8000)
  89. {
  90. rt_hw_timer_handler();
  91. }
  92. if (c0_status & 0x0400)
  93. {
  94. /* the hardware interrupt */
  95. status |= INT_ISR;
  96. if (!status) return;
  97. for (i = MAX_INTR; i > 0; --i)
  98. {
  99. if ((status & (1<<i)))
  100. {
  101. status &= ~(1<<i);
  102. irq_func = irq_handle_table[i];
  103. /* do interrupt */
  104. (*irq_func)(i);
  105. /* ack interrupt */
  106. INT_CLR = (1 << i);
  107. }
  108. }
  109. }
  110. }
  111. /*@}*/