Linux kernel 在Beaglebone中,你是否给出了错误的时间

Linux kernel 在Beaglebone中,你是否给出了错误的时间,linux-kernel,arm,interrupt,beagleboard,gpio,Linux Kernel,Arm,Interrupt,Beagleboard,Gpio,我试图测量一个运行埃OS的Beaglebone上的方波的时间周期。我已经编写了一个内核驱动程序来注册一个ISR,我在其中对脉冲进行计时。一切正常,但测量的时间间隔完全错误。我使用do_gettimeofday()函数来测量时间。当我在用户空间程序中使用poll()函数执行同样的操作时,我能够获得正确的值(对于1000us波,它显示大约1007us),但当我使用驱动器测量脉冲时,我得到的间隔为1923us。我不知道为什么内核中的时间间隔高于用户空间中的时间间隔。我在下面附上了我的代码。 如果有人能

我试图测量一个运行埃OS的Beaglebone上的方波的时间周期。我已经编写了一个内核驱动程序来注册一个ISR,我在其中对脉冲进行计时。一切正常,但测量的时间间隔完全错误。我使用do_gettimeofday()函数来测量时间。当我在用户空间程序中使用poll()函数执行同样的操作时,我能够获得正确的值(对于1000us波,它显示大约1007us),但当我使用驱动器测量脉冲时,我得到的间隔为1923us。我不知道为什么内核中的时间间隔高于用户空间中的时间间隔。我在下面附上了我的代码。 如果有人能发现我程序中的错误,我将不胜感激

内核ISR:

static irqreturn_t ISR ( int irq, void *dev_id)
{

prev = c;
do_gettimeofday(&c);

printk(KERN_ALERT "%ld", (c.tv_usec - prev.tv_usec));
return IRQ_HANDLED;
}
用户空间程序:

while(1){
    prev = start;
    gettimeofday(&start, NULL);
    rc = poll(&fdset, 1, 20000);
    if(rc < 0){
        printf("Error in rc\n");
        return -1;
    }

    if(rc == 0){
        printf("Timed out\n");
        return -1;
    }

    if (fdset.revents & POLLPRI) {
        len = read(fdset.fd, buf, 2);
        printf("%ld\n", (start.tv_usec - prev.tv_usec));
    }

}
while(1){
prev=开始;
gettimeofday(&start,NULL);
rc=轮询(&fdset,12000);
if(rc<0){
printf(“rc\n中的错误”);
返回-1;
}
如果(rc==0){
printf(“超时\n”);
返回-1;
}
if(fdset.revents和POLLPRI){
len=读取(fdset.fd,buf,2);
printf(“%ld\n”,(start.tv_usec-prev.tv_usec));
}
}

对于分析中断延迟,我发现懒惰和设置GPIO引脚然后用示波器测量时间非常有用。可能不是您想要的答案,但它可能会帮助您快速跨越障碍。

时间间隔可能不会像您所说的那样“错误”。您的代码正在ISR中尝试获取锁(通过调用
do\u gettimeofday()
),谢谢您的回复。但我不明白获取锁是如何导致这种行为的。你能解释一下吗?如果一个ISR中的锁可能被另一个ISR持有,那么试图获取该锁是危险的。如果不是意外的延迟,可能会出现死锁。嗨。如何设计中断,使其测量脉冲宽度。我必须测量低至250us的脉冲宽度。目前使用这种方法,我可以正确地测量脉冲宽度,如果它更高,大约10毫秒。