luat_timer_freertos.c 3.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120
  1. #include "luat_base.h"
  2. #include "luat_mem.h"
  3. #include "luat_timer.h"
  4. #include "luat_msgbus.h"
  5. #ifdef LUAT_FREERTOS_FULL_INCLUDE
  6. #include "freertos/FreeRTOS.h"
  7. #include "freertos/task.h"
  8. #include "freertos/timers.h"
  9. #else
  10. #include "FreeRTOS.h"
  11. #include "task.h"
  12. #include "timers.h"
  13. #endif
  14. #define LUAT_LOG_TAG "timer"
  15. #include "luat_log.h"
  16. #define FREERTOS_TIMER_COUNT 64
  17. static luat_timer_t* timers[FREERTOS_TIMER_COUNT] = {0};
  18. static inline int MS2T(int ms) {
  19. if (ms <= 0)
  20. return 0;
  21. if ((configTICK_RATE_HZ) == 1000)
  22. return ms;
  23. if ((configTICK_RATE_HZ) == 500)
  24. return (ms + 1) / 2;
  25. return ms;
  26. }
  27. static void luat_timer_callback(TimerHandle_t xTimer) {
  28. //LLOGD("timer callback");
  29. rtos_msg_t msg;
  30. size_t timer_id = (size_t)pvTimerGetTimerID(xTimer);
  31. luat_timer_t *timer = luat_timer_get(timer_id);
  32. if (timer == NULL)
  33. return;
  34. msg.handler = timer->func;
  35. msg.ptr = timer;
  36. msg.arg1 = timer_id;
  37. msg.arg2 = 0;
  38. luat_msgbus_put(&msg, 0);
  39. // int re = luat_msgbus_put(&msg, 0);
  40. //LLOGD("timer msgbus re=%ld", re);
  41. }
  42. static int nextTimerSlot() {
  43. for (size_t i = 0; i < FREERTOS_TIMER_COUNT; i++)
  44. {
  45. if (timers[i] == NULL) {
  46. return i;
  47. }
  48. }
  49. return -1;
  50. }
  51. int luat_timer_start(luat_timer_t* timer) {
  52. TimerHandle_t os_timer;
  53. int timerIndex;
  54. // LLOGD(">>luat_timer_start timeout=%ld xTimerPeriodInTicks=%d repeat=%d", timer->timeout,MS2T(timer->timeout),timer->repeat);
  55. timerIndex = nextTimerSlot();
  56. if (timerIndex < 0) {
  57. LLOGE("too many timers");
  58. return 1; // too many timer!!
  59. }
  60. os_timer = xTimerCreate("luat_timer", MS2T(timer->timeout), timer->repeat==0?pdFALSE:pdTRUE, (void*)(timer->id), luat_timer_callback);
  61. //LLOGD("timer id=%ld, osTimerNew=%p", timerIndex, os_timer);
  62. if (!os_timer) {
  63. LLOGE("xTimerCreate FAIL");
  64. return -1;
  65. }
  66. timers[timerIndex] = timer;
  67. timer->os_timer = os_timer;
  68. int re = xTimerStart(os_timer, 5);
  69. //LLOGD("timer id=%ld timeout=%ld start=%ld", timerIndex, timer->timeout, re);
  70. if (re != pdPASS) {
  71. LLOGE("xTimerStart FAIL");
  72. xTimerDelete(os_timer, 5);
  73. timers[timerIndex] = NULL;
  74. }
  75. return re == pdPASS ? 0 : -1;
  76. }
  77. int luat_timer_stop(luat_timer_t* timer) {
  78. if (timer == NULL || timer->os_timer == NULL)
  79. return 1;
  80. for (size_t i = 0; i < FREERTOS_TIMER_COUNT; i++)
  81. {
  82. if (timers[i] == timer) {
  83. timers[i] = NULL;
  84. break;
  85. }
  86. }
  87. xTimerStop((TimerHandle_t)timer->os_timer, 1);
  88. xTimerDelete((TimerHandle_t)timer->os_timer, 1);
  89. timer->os_timer = NULL;
  90. return 0;
  91. };
  92. luat_timer_t* luat_timer_get(size_t timer_id) {
  93. for (size_t i = 0; i < FREERTOS_TIMER_COUNT; i++)
  94. {
  95. if (timers[i] && timers[i]->id == timer_id) {
  96. return timers[i];
  97. }
  98. }
  99. return NULL;
  100. }
  101. int luat_timer_mdelay(size_t ms) {
  102. if (ms > 0) {
  103. vTaskDelay(MS2T(ms));
  104. }
  105. return 0;
  106. }