linux互斥与同步 之 顺序锁

来源:互联网 发布:pc蛋蛋牛人10×0算法 编辑:程序博客网 时间:2024/05/21 05:07

1、顺序锁seqlock的思想

对某一共享数据在读取的时候不加锁,写的时候加锁。

引入一顺序值sequence,读取者在开始读取前读取该变量的值,在读取后再次读取该值,如果两次读取的值不一致,说明在读取期间数据发生变化,读取无效。

写入者通过自旋锁做写入者之间的互斥。

每次写入前,将sequence值加1,写入之后,再次将sequence值加1。在学如过程中spinlock对其他写入者互斥。


2、seqlock的定义

typedef struct {

             unsigned sequence;

             spinlock_t lock;

} seqlock_t;

sequence 是顺序值,用来作读取数据有效无效的判断。

lock 是自旋锁,用来做写入者之间的互斥。


3、初始化

DEFINE_SEQLOCK(X)  : 定义并初始化一个顺序锁

seqlock_init(x) :动态初始化一个顺序锁


4、写入者的操作

static inline void write_seqlock (seqlockt_t * sl)

获得顺序锁里的自旋锁

将sequence值加1

static inline void write_sequnlock(seqlock_t * sl)

将sequence值加1

解锁

static inline int write_trylock(seqlock_t * sl)

成功获得自旋锁返回 1 ,否则返回 0


5、读取者的操作

static __always_inline unsigned read_seqbegin(const seqlock_t *sl)

主要是获取seqence的值。如果遇到写操作正在进行,则不断循环等待写结束。

返回的是seqence的值。

static __always_inline int read_seqretry(const seqlock_t *sl, unsigned start)

start是用read_seqbegin获得的sequence的值。

如果本次读取无效,则返回 1 ,有效返回 0 。


读取者的代码实例:

unsigned start;

do {

      start = read_seqbegin(&demo_seqlock);

     do_read();

} while(read_seqretry(&demo_seqlock ,start ))


6、其他版本

write_seqlock_irq(lock)

write_seqlock_irqsave(lock,flags)

write_seqlock_bh(lock)


write_sequnlock_irq(lock)

write_sequnlock_irqrestore(lock,flags)

write_sequnlock_bh(lock)


read_seqbegin_irqsave(lock , flags)

read_seqretry_irqrestore(lock,iv,flags)



顺序锁seqlock与自旋读写锁rwlock的区别:

rwlock在写的时候与读取者和写入者都互斥

seqlock在写的时候只与写入者互斥

当要保护的资源很小,会很频繁被访问并且写入操作很少发生且快速时,可用seqlock


原创粉丝点击