irq.c 3.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133
  1. /*
  2. * Copyright (c) 2006-2021, RT-Thread Development Team
  3. *
  4. * SPDX-License-Identifier: Apache-2.0
  5. *
  6. * Change Logs:
  7. * Date Author Notes
  8. * 2006-02-24 Bernard first version
  9. * 2006-05-03 Bernard add IRQ_DEBUG
  10. * 2016-08-09 ArdaFu add interrupt enter and leave hook.
  11. * 2018-11-22 Jesven rt_interrupt_get_nest function add disable irq
  12. * 2021-08-15 Supperthomas fix the comment
  13. */
  14. #include <rthw.h>
  15. #include <rtthread.h>
  16. #ifdef RT_USING_HOOK
  17. static void (*rt_interrupt_enter_hook)(void);
  18. static void (*rt_interrupt_leave_hook)(void);
  19. /**
  20. * @ingroup Hook
  21. *
  22. * @brief This function set a hook function when the system enter a interrupt
  23. *
  24. * @note The hook function must be simple and never be blocked or suspend.
  25. *
  26. * @param hook the function point to be called
  27. */
  28. void rt_interrupt_enter_sethook(void (*hook)(void))
  29. {
  30. rt_interrupt_enter_hook = hook;
  31. }
  32. /**
  33. * @ingroup Hook
  34. *
  35. * @brief This function set a hook function when the system exit a interrupt.
  36. *
  37. * @note The hook function must be simple and never be blocked or suspend.
  38. *
  39. * @param hook the function point to be called
  40. */
  41. void rt_interrupt_leave_sethook(void (*hook)(void))
  42. {
  43. rt_interrupt_leave_hook = hook;
  44. }
  45. #endif /* RT_USING_HOOK */
  46. /**
  47. * @addtogroup Kernel
  48. */
  49. /**@{*/
  50. #ifdef RT_USING_SMP
  51. #define rt_interrupt_nest rt_cpu_self()->irq_nest
  52. #else
  53. volatile rt_uint8_t rt_interrupt_nest = 0;
  54. #endif /* RT_USING_SMP */
  55. /**
  56. * @brief This function will be invoked by BSP, when enter interrupt service routine
  57. *
  58. * @note Please don't invoke this routine in application
  59. *
  60. * @see rt_interrupt_leave
  61. */
  62. void rt_interrupt_enter(void)
  63. {
  64. rt_base_t level;
  65. level = rt_hw_interrupt_disable();
  66. rt_interrupt_nest ++;
  67. RT_OBJECT_HOOK_CALL(rt_interrupt_enter_hook,());
  68. rt_hw_interrupt_enable(level);
  69. RT_DEBUG_LOG(RT_DEBUG_IRQ, ("irq has come..., irq current nest:%d\n",
  70. rt_interrupt_nest));
  71. }
  72. RTM_EXPORT(rt_interrupt_enter);
  73. /**
  74. * @brief This function will be invoked by BSP, when leave interrupt service routine
  75. *
  76. * @note Please don't invoke this routine in application
  77. *
  78. * @see rt_interrupt_enter
  79. */
  80. void rt_interrupt_leave(void)
  81. {
  82. rt_base_t level;
  83. RT_DEBUG_LOG(RT_DEBUG_IRQ, ("irq is going to leave, irq current nest:%d\n",
  84. rt_interrupt_nest));
  85. level = rt_hw_interrupt_disable();
  86. RT_OBJECT_HOOK_CALL(rt_interrupt_leave_hook,());
  87. rt_interrupt_nest --;
  88. rt_hw_interrupt_enable(level);
  89. }
  90. RTM_EXPORT(rt_interrupt_leave);
  91. /**
  92. * @brief This function will return the nest of interrupt.
  93. *
  94. * User application can invoke this function to get whether current
  95. * context is interrupt context.
  96. *
  97. * @return the number of nested interrupts.
  98. */
  99. RT_WEAK rt_uint8_t rt_interrupt_get_nest(void)
  100. {
  101. rt_uint8_t ret;
  102. rt_base_t level;
  103. level = rt_hw_interrupt_disable();
  104. ret = rt_interrupt_nest;
  105. rt_hw_interrupt_enable(level);
  106. return ret;
  107. }
  108. RTM_EXPORT(rt_interrupt_get_nest);
  109. RTM_EXPORT(rt_hw_interrupt_disable);
  110. RTM_EXPORT(rt_hw_interrupt_enable);
  111. /**@}*/