基于链表重写APP_TIMER

在nodic-SDK的library中提供了一个好用的app_timer,通过创建timer并在定时时间到执行回调函数的方式简化了在裸机状态下的编程模型。

后参考了nordic官方和同事改版的app_timer随即想把它写的在使用过程中更简化一些。比如有些时候创建的timer只需要启动一次,我就可以省去创建ID并再start的步骤,并且能实现内存的动态管理,让只运行一次的timer不再占ram空间而可以启动更多的timer。

涉及到内存的动态管理,那就要用到链表。所以整体的思路就是当创建一个新的app timer的时候就分配一块儿内存加入链表中,当要把这个timer移除的时候就从列表里面删除。整体的思路就通过下面的图来大概分析一下:

通过宏定义,来配置最多可以创建的APP_TIMER数量,也就是内存区分配多大的空间,如下图所示,假如最多可以创建6-1个:(第一个作为链表的入口)

假如创建了一个timer应用,被分配到了2号的内存空间,整个的链表结构如下,entry指向2号,2号又指回了entry,这时候链表里面共有两个元素。

假设现在又创建一个app timer,被分配在了3号的内存中,链表结构如下:entry连接到2号,2号连接到3号,3号连接回entry,还是一个环状的结构。

再添加一个app timer

既然是动态管理,那么除了有添加就可能还存在删除,这个时候3号的定时器执行了一次就不再需要了,要删除它了。整个结构又变了,entyr->2->4->entry。可以看到3号内存空间被从链表里面踢出了。

整体思路清晰了,看代码就很轻松了,这个是头文件:

具体的实现可以看下面的c文件,可以解释下头文件的接口:

  • 宏定义MAX_TIMER 定了了最大可以创建多少个APP_TIMER
  • app_timer_init 用来初始化app_timer
  • app_timer_start\ app_timer_stop 这两个接口函数用来启动和关闭app_timerde 运行,同时关闭所有的timer
  • app_timer_oneshot 用来创建一个一次触发的timer,当timer的时间到回调函数执行完以后就会自动从管理链表里面删除,is_rt参数代表是否实时,实时的会在app_timer_process中执行,非实时的会被放在app_timer_exec执行
  • app_timer_repeat和 app_timer_oneshot 功能类似,只是用来创建可以重复一直周期执行的timer
  • app_timer_delete 删除一个timer,删除以后将从管理链表中移除
  • app_timer_process 放在硬件定时器中断服务函数中,1ms周期性的调用
  • app_timer_exec 放在main函数的while循环中周期性的调用

您可能还喜欢...