Embedded LINUX driver learning 7 interrupt related (5) delay processing function


In the linux system, there are two types of task delays:
one is busy delay, which is mainly used in interrupt-related functions. The implementation method is idling in place, similar to while(n), which does not release resources. , But always handle the waiting state; the
other: sleep delay, this method is mainly used for the process, once the sleep delay is used, the process will release the resource, and the resource will be reacquired after the delay time expires and continue to run

1. Header file and description of busy delay method (mainly used in interrupt processing function)

//源码位置:arch/arm/include/asm/delay.h
//udelay(n)函数功能:延迟n微秒后继续向下执行
#define udelay(n)                                                       \
        (__builtin_constant_p(n) ?                                      \
          ((n) > (MAX_UDELAY_MS * 1000) ? __bad_udelay() :              \
                        __const_udelay((n) * ((2199023U*HZ)>>11))) :    \ 
          __udelay(n))
          //__const_udelay函数和__udelay函数源码位置:arch/arm/lib/delay.S
          
//源码位置:include/linux/delay.h
//ndelay函数功能:延迟x纳秒后继续向下执行
static inline void ndelay(unsigned long x)
{
    
    
        udelay(DIV_ROUND_UP(x, 1000));
        /*
           DIV_ROUND_UP函数位置:linux/kernel.h
           #define DIV_ROUND_UP(n,d) (((n) + (d) - 1) / (d))
        */
}

//源码位置:include/linux/delay.h
//mdelay函数功能:延迟n毫秒后继续向下执行
#ifndef MAX_UDELAY_MS
#define MAX_UDELAY_MS   5
#endif
#ifndef mdelay
#define mdelay(n) (\
        (__builtin_constant_p(n) && (n)<=MAX_UDELAY_MS) ? udelay((n)*1000) : \
        ({unsigned long __ms=(n); while (__ms--) udelay(1000);}))
#endif

2. Sleep delay method header file, function and description (used in process)

/*  msleep(n) : 
    功能 : 休眠n毫秒后继续向下执行
    源码头文件位置:include/linux/delay.h
    源码实现位置:kernel/delay.c
*/
void msleep(unsigned int msecs)
{
    
    
        unsigned long timeout = msecs_to_jiffies(msecs) + 1;
        while (timeout)
                timeout = schedule_timeout_uninterruptible(timeout);
}
EXPORT_SYMBOL(msleep);

/* ssleep(n):
    功能 : 休眠n秒后,继续向下执行
    源码位置:include/linux/delay.h
*/
static inline void ssleep(unsigned int seconds)
{
    
    
        msleep(seconds * 1000);
}

schedule() 
/*
    功能:永久休眠,但可以被中断打断
    头文件位置:include/linux/sched.h
               asmlinkage void schedule(void);
*/

schedule_timeout(signed long timeout)
/*
    功能:休眠timeout(一般有HZ。如:1*HZ表示1秒),但可以被中断打断
          当timeout 为: MAX_SCHEDULE_TIMEOUT时,表示永久休眠,等同于schedule() 函数
    头文件位置:include/linux/sched.h
               signed long __sched schedule_timeout(signed long timeout)

*/

Guess you like

Origin blog.csdn.net/weixin_47273317/article/details/107984530