单片机
返回首页

ESP32高分辨率计时器笔记

2025-09-10 来源:cnblogs

尽管FreeRTOS提供了软件计时器,但这些计时器有一些限制:


最大分辨率等于RTOS滴答周期


计时器回调从低优先级任务分派


硬件计时器不受这两个限制,但是通常它们使用起来不太方便。例如,应用组件可能需要定时器事件在将来的特定时间触发,但是硬件定时器仅包含一个用于中断产生的“比较”值。这意味着需要在硬件计时器之上构建一些功能来管理挂起事件列表,以便在发生相应的硬件中断时可以调度这些事件的回调。


esp_timer 一组API提供了一次性的计时器和定期的计时器,微秒级的时间分辨率以及64位范围。


基于ESP-IDF4.1


 1 #include

 2 #include

 3 #include

 4 #include 'esp_timer.h'

 5 #include 'esp_log.h'

 6 #include 'esp_sleep.h'

 7 #include 'sdkconfig.h'

 8 

 9 static void periodic_timer_callback(void* arg);

10 static void oneshot_timer_callback(void* arg);

11 

12 static const char* TAG = 'example';

13 

14 void app_main(void)

15 {

16     /* 

17      * 创建两个计时器:

18      * 1.每0.5秒运行的一个周期性计时器,并且打印消息

19      * 2.五秒后执行的一次性计时器,并且每1秒重启计时器

20      */

21 

22     //创建周期性计时器

23     const esp_timer_create_args_t periodic_timer_args = {

24             .callback = &periodic_timer_callback,

25             //自定义名称

26             .name = 'periodic'

27     };

28 

29     esp_timer_handle_t periodic_timer;

30     ESP_ERROR_CHECK(esp_timer_create(&periodic_timer_args, &periodic_timer));

31 

32     //创建一次性计时器

33     const esp_timer_create_args_t oneshot_timer_args = {

34             .callback = &oneshot_timer_callback,

35             //指定的参数将会传给计时器回调函数

36             .arg = (void*) periodic_timer,

37             .name = 'one-shot'

38     };

39     esp_timer_handle_t oneshot_timer;

40     ESP_ERROR_CHECK(esp_timer_create(&oneshot_timer_args, &oneshot_timer));

41 

42     //启动计时器

43     ESP_ERROR_CHECK(esp_timer_start_periodic(periodic_timer, 500000));

44     ESP_ERROR_CHECK(esp_timer_start_once(oneshot_timer, 5000000));

45     ESP_LOGI(TAG, 'Started timers, time since boot: %lld us', esp_timer_get_time());

46 

47     // 每2秒打印计时器调试信息到控制台

48     for (int i = 0; i < 5; ++i) {

49         ESP_ERROR_CHECK(esp_timer_dump(stdout));

50         usleep(2000000);

51     }

52 

53 

54     //轻度睡眠中,时间继续保持。轻度睡眠后计时器正确执行

55     ESP_LOGI(TAG, 'Entering light sleep for 0.5s, time since boot: %lld us',esp_timer_get_time());

56     ESP_ERROR_CHECK(esp_sleep_enable_timer_wakeup(500000));

57     esp_light_sleep_start();

58     ESP_LOGI(TAG, 'Woke up from light sleep, time since boot: %lld us', esp_timer_get_time());

59 

60     //让计时器再运行一会

61     usleep(2000000);

62 

63     //停止和清除计时器

64     ESP_ERROR_CHECK(esp_timer_stop(periodic_timer));

65     ESP_ERROR_CHECK(esp_timer_delete(periodic_timer));

66     ESP_ERROR_CHECK(esp_timer_delete(oneshot_timer));

67     ESP_LOGI(TAG, 'Stopped and deleted timers');

68 }

69 

70 //周期性计时器回调函数

71 static void periodic_timer_callback(void* arg)

72 {

73     int64_t time_since_boot = esp_timer_get_time();

74     ESP_LOGI(TAG, 'Periodic timer called, time since boot: %lld us', time_since_boot);

75 }

76 

77 //一次性计时器回调函数

78 static void oneshot_timer_callback(void* arg)

79 {

80     int64_t time_since_boot = esp_timer_get_time();

81     ESP_LOGI(TAG, 'One-shot timer called, time since boot: %lld us', time_since_boot);

82     esp_timer_handle_t periodic_timer_handle = (esp_timer_handle_t) arg;

83     //启动运行的计时器,首先需要先停止它

84     ESP_ERROR_CHECK(esp_timer_stop(periodic_timer_handle));

85     ESP_ERROR_CHECK(esp_timer_start_periodic(periodic_timer_handle, 1000000));

86     time_since_boot = esp_timer_get_time();

87     ESP_LOGI(TAG, 'Restarted periodic timer with 1s period, time since boot: %lld us',time_since_boot);

88 }


进入单片机查看更多内容>>
相关视频
  • 【TI MSPM0 应用实战】智能小车+工业角度编码器+血氧仪+烟雾探测器!硬核参考设计详解!

  • 2022 Digi-Key KOL 系列: 你见过1GHz主频的单片机吗?Teensy 4.1开发板介绍

  • TI 新一代 C2000™ 微控制器:全方位助力伺服及马达驱动应用

  • MSP430电容触摸技术 - 防水Demo演示

  • 直播回放: Microchip Timberwolf™ 音频处理器在线研讨会

  • 基于灵动MM32W0系列MCU的指夹血氧仪控制及OTA升级应用方案分享

精选电路图
  • 锂离子/锂聚合物USB电池充电器

  • 6晶体管H桥

  • AVR LCD温度计—LM35

  • AVR PC步进电机驱动器

  • AVR温度计TCN75

  • JDM2 PIC 18F 编程器

    相关电子头条文章