【问题标题】:How locks are implemented on multiple cores如何在多核上实现锁
【发布时间】:2011-08-11 06:09:08
【问题描述】:

对于单处理器,锁定算法非常简单。

Lock(threadID) {
  Disable Interrupts
  If lock is already owned by same thread{
    Restore Interrupts
    return
  }
  if lock is free {
    make lock busy
    set current thread as the owner of the lock
  }
  else {
     add threadID to the lock queue.
  }
  Restore Interrupts
  return
}

但是我们如何在多处理器/多核系统中实现此代码。如果 2 个核心/进程尝试为不同的进程提供相同的锁会怎样。

【问题讨论】:

    标签: operating-system mutex multicore locks multiprocessor


    【解决方案1】:

    我说考虑锁的最简单方法是原子交换指令。下面获取锁X。

    锁: 设置寄存器A = 1 Atomic_Exchange(X, RegisterA) //运行使得没有其他线程可以使用 X 如果寄存器A == 1: 意味着当我进行交换时 X 为 1,因此其他人拥有锁 由于我没有锁,请转到 LOCK 别的: 如果 A 为零,则意味着我是第一个将 X 设置为 1 的人,这意味着我拥有锁 开锁: X = 0

    原子交换存在于大多数计算机中。英特尔的 x86 对此有一个 EXCHG 指令。仅供参考,英特尔的 x86 还具有比较和交换指令,可以为您处理获取和比较。基本上,它不是首先进行交换然后在软件中进行测试,而是使用硬件并且仅在 X==0 开始时才进行交换。这节省了对变量 X 的额外写入,从而减少了 X 的缓存未命中,从而提高了性能。

    【讨论】:

      【解决方案2】:

      互斥锁通常使用atomic operations 在单个内存值上实现。例如,锁可以是一个单词,当0 时是空闲的,1 时是锁定的。为了获得锁,处理器将锁定内存总线(因此没有其他处理器可以读取或写入内存),读取该字的最新值,如果是0,则将其设置为1,然后解锁内存总线。要解锁,可以将单词设置为0

      这是一个简单的例子,没有说明当锁被争用时会发生什么。不同的操作系统使用不同的机制来处理。 Linux 使用称为futexes 的东西。我不确定 Windows 或 Mac 能做什么。

      虽然您发布的算法是正确的,但非内核代码无法禁用 CPU 中断,因此即使在单个内核上,用户空间代码也会倾向于使用原子操作。

      【讨论】:

      • 只能通过原子操作完成,还是还需要系统调用(禁用中断)?
      猜你喜欢
      • 2011-05-13
      • 2021-03-08
      • 2016-07-15
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-04-19
      • 2020-03-15
      相关资源
      最近更新 更多