Linux内核定时器的使用

内核定时器的结构体定义在include/linux/timer.h:
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
};
只需初始化定时器的超时时间expires,超时调用函数function,data成员会作为定时器超时函数的参数传递,驱动可以用data来存储自己的私有数据结构地址。下面是定时器应用的一个实例:
驱动的私有数据结构:
struct msg21xx_ts_data {
	struct input_dev *input;
	struct hrtimer timer;
	struct work_struct work;
	int irq;
	struct dentry *dir;
	char *ts_info;
	u8 addr;
	int fw_major;
	int fw_minor;
#ifdef CONFIG_FB
	struct notifier_block fb_notif;
#endif
	bool suspended;
	struct timer_list tp_timer;
	struct i2c_client *client;
	struct regulator *vdd;
	struct regulator *vcc_i2c;
	struct msg21xx_platform_data *pdata;
	struct workqueue_struct *msg21xx_wq;
	struct mutex msg21xx_mutex;
};
驱动的probe函数:
static int msg21xx_ts_probe(struct i2c_client *client,
            const struct i2c_device_id *id)
{
    struct msg21xx_ts_data *data;
    
    data = kzalloc(sizeof(struct msg21xx_ts_data), GFP_KERNEL);
    if (!data) {
        dev_err(&client->dev, "%s: Alloc mem fail!", __func__);
        err = -ENOMEM;
        goto exit;
    }
    
    init_timer(&data->tp_timer);
    data->tp_timer.function = tp_timer_function;
    data->tp_timer.data = (unsigned long)data;
//    setup_timer(&tp_timer, tp_timer_function, (unsigned long)data);
    add_timer(&data->tp_timer);
    mod_timer(&data->tp_timer, jiffies+HZ * 2);
}
调用init_timer初始化定时器,然后设置定时器的超时调用函数,data成员被初始化为驱动的私有数据结构的地址,最后调用add_timer将定时器加入内核,调用mod_timer后,定时器会在2秒后超时,tp_timer_function函数被调用,data作为函数的参数被传入,在tp_timer_function函数中,就可以操作驱动的硬件。
void tp_timer_function(unsigned long datap)
{
	struct msg21xx_ts_data *data = (struct msg21xx_ts_data *)datap;

	gpio_set_value_cansleep(data->pdata->home_gpio, 0);
	gpio_set_value_cansleep(data->pdata->return_gpio, 0);
	gpio_set_value_cansleep(data->pdata->system_gpio, 0);
}
下面的三条语句可以用一条代替:setup_timer(&tp_timer, tp_timer_function, (unsigned long)data);
init_timer(&data->tp_timer);
data->tp_timer.function = tp_timer_function;
data->tp_timer.data = (unsigned long)data;

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值