Chinaunix首页 | 论坛 | 博客
  • 博客访问: 9413557
  • 博文数量: 1748
  • 博客积分: 12961
  • 博客等级: 上将
  • 技术积分: 20070
  • 用 户 组: 普通用户
  • 注册时间: 2009-01-09 11:25
个人简介

偷得浮生半桶水(半日闲), 好记性不如抄下来(烂笔头). 信息爆炸的时代, 学习是一项持续的工作.

文章分类

全部博文(1748)

文章存档

2024年(24)

2023年(26)

2022年(112)

2021年(217)

2020年(157)

2019年(192)

2018年(81)

2017年(78)

2016年(70)

2015年(52)

2014年(40)

2013年(51)

2012年(85)

2011年(45)

2010年(231)

2009年(287)

分类: LINUX

2010-11-08 17:26:24

  1. 原子变量   atomic_t
    1. 对int值上的原子操作。避免对整数的操作都要进行加锁的繁琐。
    2. void atomic_set(atomic_t *v, int i);
      atomic_t v = ATOMIC_INIT(0);
    3. int atomic_read(atomic_t *v);
      void atomic_add(int i, atomic_t *v);
      void atomic_sub(int i , atomic_t *v);
      void atomic_inc(atomic_t *v);
      void atomic_dec(atomic_t *v);
    4. int atomic_inc_and_test(atomic_t *v);
      int atomic_dec_and_test(atomic_t *v);
      int atomic_sub_and_test(int i, atomic_t *v);
      先进行操作,然后返回操作结果, 若原子值为0,返回真。
    5. int atomic_add_negative(int i, atomic_t *v);
      先进行加操作,若结果为负数(negative),则返回值为真。
    6. void atomic_add_return(int i, atomic_t *v);
      void atomic_sub_return(int i , atomic_t *v);
      void atomic_inc_return(atomic_t *v);
      void atomic_dec_return(atomic_t *v);
  2. 位操作 使得位操作原子化
    1. 参数 int nr, 要操作的位。
      参数 void *addr, 要修改的地址。
    2. void set_bit(nr, void *addr); //设置addr对应的数据项的第nr位为1
      void clear_bit(nr, void *addr); //设置addr对应的数据项的第nr位为0
      void change_bit(nr, void *addr); //翻转addr对应的数据项的第nr位的值
    3. 设置值,,并返回设置之前的值 (0, 1)
      int test_set_bit(nr, void *addr);
      int test_clear_bit(nr, void *addr);
      int test_change_bit(nr, void *addr); 
  3. seqlock 锁
    1. 保护的资源简单且经常被存取。写操作较少并且速度较快,读操作与写操作冲突时可以重试读取。
    2. 一般不用于对含有指针的数据结构进行锁机制保护。
    3. seqlock_t lock1 = SEQLOCK_UNLOCKED;
      seqlock_t lock2; seqlock_init(&lock2);
    4. 读操作的流程为:进入临界区获得一个无序整数序列工作,读取完成后于当前值比较,若不匹配说明度的数据已经失效(有并发写执行过)需要重新读取(丢弃原有数据)
      unsigned int seq;

      do {
      seq = read_seqbegin(&the_lock);
      /* Do what you need to do */
      } while read_seqretry(&the_lock, seq);
    5. 当用于中断子程序中,可以使用IRQ的安全调用
      uint read_seqbegin_irqsave(seqlock_t *lock, ulong flags);
      int read_seqbegin_irqrestor(seqlock_t *lock, ulong flags);
    6. 写操作的内部实现为自旋锁。
      void write_seqlock(seqlock_t *lock);
      void write_seqlock_irqsave(seqlock_t *lock, ulong flags);
      void write_seqlock_irq(seqlock_t *lock);
      void write_seqlock_bh(seqlock_t *lock);

      void write_sequnlock(seqlock_t *lock);
      void write_sequnlock_irqrestore(seqlock_t *lock, ulong flags);
      void write_sequnlock_irq(seqlock_t *lock);
      void write_sequnlock_bh(seqlock_t *lock);

      int write_tryseqlock(seqlock_t *lock);
  4. RCU  读 - 拷贝 - 更新
    1. 适用于经常读而极少写的情况。
    2. 保护的资源硬通过指针来存取。
    3. 对资源的引用必须由源自代码持有。
    4. 当数据结构要进行修改,写线程作一个拷贝,改变拷贝,接着使相关的指针对准新拷贝。内核当确认没有对旧版本存在引用时会自动调用用户定义的释放函数。
    5. 读操作
      struct my_stuff *stuff; 
      rcu_read_lock();  //禁用内核抢占并没有任何等待的延迟,直接进入原子操作。
      stuff = find_the_stuff(args...);//下面两行为原子操作。
      do_something_with(stuff);
      rcu_read_unlock();
    6. 写操作
      分配新结构,如有需要拷贝旧数据,然后替换读代码要看到的指针。资源改变完成后调用
      void call_rcu(struct rcu_head *head, void(*func)(void *arg), void *arg);
      func为释放旧资源的调用,arg为func执行的arg





阅读(1672) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~