組み込みLINUX駆動型学習(3)派生スピンロックの8つの競合状態と同時実行関連の問題

組み込みLINUX駆動型学習(3)派生スピンロックの8つの競合状態と同時実行関連の問題

1.ヘッダーファイル、関数、説明

派生スピンロックは、主にスピンロックと割り込みシールドに基づいて実装され、派生スピンロックを使用してコンテンツの操作をスリープさせません

/*
  对要操作的全局变量或寄存器添加衍生自旋锁函数:
      spin_lock_irqsave(lock,flags);
      参数:
         lock : spinlock_t lock;  
         flags: unsigned long flags);
         注:在spin_lock_irqsave函数中做形参使用时;lock应当取地址
             lock:应当都为全局静态变量,
             flags:一般用局部变量即可;
     用法:
         static spinlock_t lock;
         static unsigned long flags;
         static void/int/... xxx_func(..形参 ...){
             spin_lock_irqsave(&lock,flags);  
             ......要操作的全局变量或寄存器...
             spin_unlock_irqrestore(&lock,flags);
源码位置:include/linux/spinlock.h
*/
#define spin_lock_irqsave(lock, flags)                          \
do {                                                            \
        raw_spin_lock_irqsave(spinlock_check(lock), flags);//源码实现见附A.1     \
} while (0)

/*
    释放衍生自旋锁函数:spin_unlock_irqrestore()
*/
static inline void spin_unlock_irqrestore(spinlock_t *lock, unsigned long flags)
{
    
    
        raw_spin_unlock_irqrestore(&lock->rlock, flags);
}

添付資料A.1

/*函数功能,将形参lock转换为raw_spinlock_t结构体类型*/
static inline raw_spinlock_t *spinlock_check(spinlock_t *lock)
{
    
    
        //结构体spinlock_t的成员变量rlock为,结构体struct raw_spinlock类型
        //而结构体类型:raw_spinlock_t为struct raw_spinlock别名
        //详见源代码:include/linux/spinlock_types.h
        return &lock->rlock;
        
}

#define raw_spin_lock_irqsave(lock, flags)                      \
        do {                                            \
                typecheck(unsigned long, flags);        \
                flags = _raw_spin_lock_irqsave(lock);//源码实现见附A.1.1   \
        } while (0)

/*
    函数typecheck(a,b)功能:
        检查形参 b 是否为形参 a 类型
*/

付属A.1.1

//源码位置:linux/spinlock_api_smp.h
#define _raw_spin_lock_irqsave(lock) __raw_spin_lock_irqsave(lock)

static inline unsigned long __raw_spin_lock_irqsave(raw_spinlock_t *lock)
{
    
    
        unsigned long flags;    
        local_irq_save(flags); //使用中断屏蔽
        preempt_disable(); //关闭抢占
        spin_acquire(&lock->dep_map, 0, 0, _RET_IP_);
#ifdef CONFIG_LOCKDEP
        LOCK_CONTENDED(lock, do_raw_spin_trylock, do_raw_spin_lock);//实现方法见附A1.1.1
#else
        do_raw_spin_lock_flags(lock, &flags); //使用中断屏蔽,实现方法见附A1.1.2
#endif
        return flags;
}

添付A1.1.1

#ifdef CONFIG_LOCK_STAT
extern void lock_contended(struct lockdep_map *lock, unsigned long ip);
extern void lock_acquired(struct lockdep_map *lock, unsigned long ip);
#define LOCK_CONTENDED(_lock, try, lock)                        \
do {     
        /*      
               do_raw_spin_trylock(lock)                      
        */        
        if (!try(_lock)) {
    
                                          \
                lock_contended(&(_lock)->dep_map, _RET_IP_);    \
                lock(_lock);                                    \
        }                                                       \
        lock_acquired(&(_lock)->dep_map, _RET_IP_);                     \
} while (0)

/* do_raw_spin_trylock()函数实现*/
//源码位置:include/linux/spinlock.h
static inline int do_raw_spin_trylock(raw_spinlock_t *lock)
{
    
    
        return arch_spin_trylock(&(lock)->raw_lock);
}
//源码位置:include/linux/spinlock_up.h
static inline int arch_spin_trylock(arch_spinlock_t *lock)
{
    
    
        char oldval = lock->slock;
        lock->slock = 0;
        return oldval > 0;
}

付属A1.1.2

/*   do_raw_spin_lock_flags()函数实现
    源码位置:include/linux/spinlock.h
*/
static inline void\
do_raw_spin_lock_flags(raw_spinlock_t *lock, unsigned long *flags) __acquires(lock)
{
    
    
        __acquire(lock);
        arch_spin_lock_flags(&lock->raw_lock, *flags);//实现方式如下:
}

//源码位置:include/linux/spinlock_up.h
static inline void\
arch_spin_lock_flags(arch_spinlock_t *lock, unsigned long flags)
{
    
    
        local_irq_save(flags);
        lock->slock = 0;
}

//arch_spinlock_t结构体原型
typedef struct {
    
    
        volatile unsigned int slock;
} arch_spinlock_t;

おすすめ

転載: blog.csdn.net/weixin_47273317/article/details/108051001