历史上的今天
返回首页

历史上的今天

今天是:2024年12月30日(星期一)

正在发生

2021年12月30日 | 4412 Linux定时器

2021-12-30 来源:eefocus

一、Linux定时器基础知识

1.1 定时器的使用范围

延后执行某个操作,定时查询某个状态;前提是对时间要求不高的地方


1.2 内核时间概念

  • Hz:(系统时钟通过CONFIG_HZ来设置,范围是100-1000;HZ决定使用中断发生的频率)


    • 1/200 = 5ms,说明4412中是5ms产生一次时钟中断。如果就没有定义的话,默认是100

  • 内核的全局变量jiffies:(记录内核自启动来的节拍数,内核之启动以来,产生的中断数)时钟中断,每产生一个中断,jiffies就加1。

  • jiffies/HZ:jiffies除以Hz得到内核自启动以来的秒数


2.1 内核定时器的例程

结构体timer_list,函数setup_timer,add_timer,del_timer,mod_timer

 timer_list

struct timer_list {

    /*

     * All fields that change during normal runtime grouped to the

     * same cacheline

     */

    struct list_head entry;

    unsigned long expires;

    struct tvec_base *base;


    void (*function)(unsigned long);

    unsigned long data;


    int slack;


#ifdef CONFIG_TIMER_STATS

    int start_pid;

    void *start_site;

    char start_comm[16];

#endif

#ifdef CONFIG_LOCKDEP

    struct lockdep_map lockdep_map;

#endif

};




timer_list参数

  • struct list_head entry双向链表

  • unsigned long expires:超时时间,记录什么时候产生时钟中断

  • struct tvec_base *base:管理时钟的结构体

  • void *(function)(unsigned long):时钟中断产生之后的动作

  • unsigned long data:传递的参数


#define setup_timer(timer, fn, data)                   

    do {                               

        static struct lock_class_key __key;         

        setup_timer_key((timer), #timer, &__key, (fn), (data));

    } while (0)


void add_timer(struct timer_list *timer);

int del_timer(struct timer_list * timer);

int mod_timer(struct timer_list *timer, unsigned long expires);


2.2 双向链表

platform_driver_register→driver_register

→bus_add_driver

→struct bus_type *bus

→struct subsys_private *p

→struct kset subsys→struct list_head list;

 

2.3 mod_timer相当于

mod_timer = del_timer(time);timer->expires = expires;add_timer(timer);

 

3 内核定时器实现的分析

从内核定时器初始化到定时器例程

3.1 add_timer如何添加定时器

        add_timer→mod_timer
        →__mod_timer(内核函数有下划线,表示“局部函数”)
        →internal_add_timer

3.2 struct tvec_base *base结构体分析--管理内核时钟的结构体

        struct tvec_base {

            spinlock_t lock;    //自旋锁

            struct timer_list *running_timer;    //内核中正在处理的定时器

            unsigned long timer_jiffies;        //内核目前正在处理的定时器时间

            unsigned long next_timer;    

            struct tvec_root tv1;

            {

                struct list_head vec[TVR_SIZE];//256长度数组

                TVR_SIZE→#define TVR_SIZE (1 << TVR_BITS)

                TVR_BITS=8;

                宏定义CONFIG_BASE_SMALL=0

                TVR_SIZE = 256

            }

            struct tvec tv2;    //64长度数组

            struct tvec tv3;

            struct tvec tv4;

            struct tvec tv5;

        }


per_cpu 与CPU核多少有关    
DEFINE_PER_CPU看到这样的变量,就表明这个变量是和CPU核相关的。

有一些宏定义是在内核目录的config文件配置的 

3.3 internal_add_timer

分析idx参数
如果idx<256,则将time_list添加到TV1
如果idx<256*64,则将time_list添加到TV2
如果idx<256*64*64,则将time_list添加到TV3
如果idx<256*64*64*64,则将time_list添加到TV4
如果idx > 0xffffffffUL,则将time_list添加到TV5

 

3.4 list_add_tail

双向链表操作函数都在include/linux/list.h文件中


上一篇:4412 4路pwm输出

下一篇:4412 SPI驱动

推荐阅读

史海拾趣

Digital Voice Systems Inc公司的发展小趣事

Digital Voice Systems, Inc.(DVSI)于1988年成立,当时正值数字通信技术的兴起阶段。公司创始人凭借对语音编解码技术的深刻理解和前瞻性的市场洞察力,决定投身于这一领域。他们开发出了具有专利保护的基于鲁棒性多带激励模型(MBE Model)的低码率语音压缩算法,如IMBE和AMBE编解码系统。这些算法在当时的市场上独树一帜,为DVSI赢得了第一桶金。

在创立初期,DVSI面临着资金、技术、市场等多方面的挑战。然而,他们凭借着坚定的信念和不懈的努力,逐步克服了这些困难。他们不断投入研发,优化算法,提高产品的性能和稳定性;同时,他们积极开拓市场,与各大通信设备制造商建立合作关系,将产品推向市场。

随着时间的推移,DVSI的产品逐渐在市场上获得了认可。他们的编解码系统被广泛应用于移动通信、卫星通信、军事通信等领域,为客户提供了高效、稳定的语音通信解决方案。DVSI也因此逐渐崭露头角,成为了电子行业中一颗耀眼的明星。

故事二至五框架概述

  1. 技术创新与突破:DVSI在语音编解码技术方面的持续创新,如推出新一代的高效压缩算法,进一步提升了产品的竞争力。
  2. 市场拓展与国际化:随着公司实力的增强,DVSI开始拓展国际市场,与全球多家知名企业建立合作关系,实现了国际化发展。
  3. 合作与竞争:在电子行业中,DVSI与其他企业的合作与竞争并存。他们通过合作共赢的方式,共同推动行业的发展;同时,也面临着来自竞争对手的挑战和竞争压力。
  4. 企业文化与团队建设:DVSI注重企业文化建设,倡导创新、协作、共赢的价值观。他们注重团队建设,吸引了一批优秀人才加入公司,为公司的发展提供了有力的人才保障。

以上故事和框架概述仅供参考,您可以根据这些线索进一步挖掘和编写关于DVSI公司的故事。

艾华集团(AISHI)公司的发展小趣事

1985年,艾立华和王安安怀揣着3700元的全部家当,毅然决然地踏上了创业之路。他们租下了两间不到50平方米的废弃小平房,与几名工人一起,手工制作铝电解电容器。由于资金、技术和市场的限制,艾华集团最初只能接一些其他企业不愿意做的、用量很少但又刚需的项目。然而,即便是在这样的困境中,艾立华和王安安也始终坚持对产品品质的精益求精,他们深知,只有高品质的产品才能在市场上立足。

德欣(COV)公司的发展小趣事

作为一家有社会责任感的企业,德欣公司始终关注环境保护和可持续发展。公司积极推广绿色生产技术和资源循环利用方案,减少生产过程中的能源消耗和废弃物排放。同时,德欣公司还积极参与社会公益活动,为社区和环境贡献自己的力量。这些举措不仅体现了德欣公司的社会责任担当,也为其赢得了更多客户和合作伙伴的信任和支持。

FORYARD公司的发展小趣事

在快速发展的同时,FORYARD始终不忘企业的社会责任和可持续发展目标。公司积极推广绿色生产和环保理念,采用环保材料和节能技术降低生产过程中的碳排放和资源消耗。此外,FORYARD还积极参与社会公益事业和慈善活动,为贫困地区的教育和医疗事业贡献力量。这些举措不仅提升了公司的社会形象和品牌价值,也为实现可持续发展目标做出了积极贡献。

EDAL公司的发展小趣事

随着技术的不断进步和市场的变化,EDAL公司意识到必须不断优化产品以满足客户的需求。公司投入大量研发资源,对EDA工具进行迭代升级,推出了更加智能化、用户友好的产品。同时,EDAL公司积极拓展市场,与全球各大芯片设计公司建立了合作关系,将产品销售到世界各地。

长江微电(cjiang)公司的发展小趣事

为了进一步扩大市场份额和品牌影响力,长江微电积极寻求与业内知名分销商的合作。基于对世强先进O2O技术分销模式的信赖与认可,长江微电与世强先进(深圳)科技股份有限公司签署了授权代理协议。双方将携手合作,共同为用户提供车规级电感、车规级耦合电感等全线产品。这一合作不仅丰富了世强硬创平台电子元器件产品的品类及信息,也为长江微电的市场拓展提供了有力支持。

问答坊 | AI 解惑

在VS2005+PB6.0的编译环境下调试HelloCE程序出错

提示 “WM_HIBERNATE”:未声明的标识符 代码如下: //====================================================================== // HelloCE - A simple application for Windows CE // // Written for the book Programming Windows CE // ...…

查看全部问答>

16f877 sim仿真 现金求助

pic16f877 通过编程仿真 由Sim-Emu 6.01 Configurator v2.1 写入手机号码的相关参数后得到: 一张十合一的可以自动切换imsi的sim卡 这个卡可以用于iphone 这个网址可以提供相应的知识准备 http://www.weiphone.com/viewthread.php?tid=4272& ...…

查看全部问答>

如何在EVC下使用CxImage

在VC6.0下,可以正常使用,然而在EVC4.0下,却总是编译不过...…

查看全部问答>

CE平台上的ISR!!!

那位写过CE平台上的中断服务程序! 请指点一二呀。我对这不懂,谢谢了…

查看全部问答>

发个好用的LCD1602最简程序

本帖最后由 paulhyde 于 2014-9-15 09:20 编辑 我的LCD1602是三个控制线的即:RS,RW,E 在论坛里本来有这个显示例程,但我下进我的LCD1602后不显,后来我从网上找到一个觉得不错特来分享   原地址:…

查看全部问答>

淘宝发现两个好东西,不知道其它地方可以买到吗?

msp430超值系列的单片机 达利尔官方只要6块钱。 然后它有28到32个引脚。资源也丰富 更重要的是,它支持两线仿真     我很想买几块,就是运费要20,舍不得。不知道别的地方有卖的吗?  …

查看全部问答>

防止驱动电源“掉链子”——LED照明测试技术分析

LED照明具有节能、环保、长寿命、易控制、免维护等特点。然而颇具讽刺意味的是,我们常常听闻由于LED驱动电源本身的寿命直接拖累LED照明灯具变得并不“长寿”,极大地增加了维护/使用成本;或者驱动电源的效率不高导致LED照明灯具的能效转换比并不 ...…

查看全部问答>

大家一起学习PIC单片机之二(独立键盘蜂鸣器提示)

 大家好,本人是PIC单片机新手,但是我很勤奋,我买的ND118-877APIC实验开发板,里面有实例,但是没有源代码,本人自己写代码大家一起交流,希望能陆续写下去,本人QQ476857290 希望大家学习指导。本节学习 8位独立按键蜂鸣器提示   ...…

查看全部问答>

cpld产生一定形式方波的问题

cpld时钟50M,怎么产生下图所示的周期性方波?还有采用什么方法产生周期为1s的方波信号占用硬件资源更少? …

查看全部问答>

stm32 串口通信地址唤醒问题

stm32串口通信支持地址唤醒,但是地址位只有4位,也就是说最多连接16个..在很多情况下都不够用。 除此以外还有其他问题,比如,对于1号地址,接收的数据必须以0x81开头,但是如果给2号地址发送: 82 05 05 81 02 02 那么一号机就会收到81 02 02. ...…

查看全部问答>