我的使用步骤具体如下:
首先kernel中已经打开了high resolution Timer support
驱动程序中hrtimer的初始化如下:
hrtimer_init(&m_timer, CLOCK_MONOTONIC, HRTIMER_MODE_REL_PINNED);
m_timer.function = vibrator_timer_func;
hrtimer_start(&m_timer,ktime_set(0, 62500),HRTIMER_MODE_REL_PINNED);
定时函数vibrator_timer_func如下:
static enum hrtimer_restart vibrator_timer_func(struct hrtimer *timer)
{
gpio_set_value(gpio_test, 1);
gpio_set_value(gpio_test, 0);
hrtimer_forward_now(&m_timer,ktime_set(0, 62500));
return HRTIMER_RESTART;
}
其中gpio_test为输出引脚,为了方便输出查看。
但是用示波器查看引脚波形时,发现虽然设定的周期为62.5us,但是输出总是为72us左右,而且偶尔会有两个波形靠的很近(也就是说周期突然变为10us以下)。我将周期设到40us的话,就会出现72us和10us经常交替出现,无法实现精确的40us的波形,如果设置到100us时,则波形就是100us了,而且貌似没有看到有10us以下的周期出现。
上面就是目前我使用下来的现象,不知道大神们有什么建议,是不是我哪些地方不对?
(注:我用rt_task(current)查看驱动是否是实时任务时返回的是false,不知道这个会不会有影响?如果有的话,怎么设置成实时任务?)
1 个解决方案
#1
没有人回复,自己研究了两天内核里的hrTimer软件架构,终于搞定了。
我用的是dm365,因此在arch/arm/mach-davinci/time.c文件中有下列函数
该函数中有一行
而hrTimer在设定下一次定时中断时,会跟该值进行对比
(在clockevents_program_event函数中)
默认该值是50us,所以我定时小于50us的都被改为了50us,将该值改为5us后,问题解决,出来了完美的40us周期波形。
写在这里希望对后面遇到同样问题的人有帮助。
我用的是dm365,因此在arch/arm/mach-davinci/time.c文件中有下列函数
static void __init davinci_timer_init(void)
该函数中有一行
clockevent_davinci.min_delta_ns = 50000; /* 50 usec */
而hrTimer在设定下一次定时中断时,会跟该值进行对比
if (delta < dev->min_delta_ns)
delta = dev->min_delta_ns;
(在clockevents_program_event函数中)
默认该值是50us,所以我定时小于50us的都被改为了50us,将该值改为5us后,问题解决,出来了完美的40us周期波形。
写在这里希望对后面遇到同样问题的人有帮助。
#1
没有人回复,自己研究了两天内核里的hrTimer软件架构,终于搞定了。
我用的是dm365,因此在arch/arm/mach-davinci/time.c文件中有下列函数
该函数中有一行
而hrTimer在设定下一次定时中断时,会跟该值进行对比
(在clockevents_program_event函数中)
默认该值是50us,所以我定时小于50us的都被改为了50us,将该值改为5us后,问题解决,出来了完美的40us周期波形。
写在这里希望对后面遇到同样问题的人有帮助。
我用的是dm365,因此在arch/arm/mach-davinci/time.c文件中有下列函数
static void __init davinci_timer_init(void)
该函数中有一行
clockevent_davinci.min_delta_ns = 50000; /* 50 usec */
而hrTimer在设定下一次定时中断时,会跟该值进行对比
if (delta < dev->min_delta_ns)
delta = dev->min_delta_ns;
(在clockevents_program_event函数中)
默认该值是50us,所以我定时小于50us的都被改为了50us,将该值改为5us后,问题解决,出来了完美的40us周期波形。
写在这里希望对后面遇到同样问题的人有帮助。