多核心與同步

上方的程式碼使用CAS(&p, 預期值, 新值)將共用變數counter變成2倍。CAS失敗而重做迴圈,是在什麼情況下?

int old, new;
do {
    old = counter;
    new = old * 2;
} while (!CAS(&counter, old, new));
  1. Acounter的值為0時
  2. B從讀取old到執行CAS之間,其他執行緒改寫了counter時
  3. Cnew的值大於old時
查看答案與解析

正確答案:B. 從讀取old到執行CAS之間,其他執行緒改寫了counter時

CAS在counter仍是讀取時的old時,會寫入新值。若這段期間其他執行緒已改變了值,手上的new是依據舊值算出的,所以不會寫入並回傳失敗。迴圈會重新讀取最新的值並重做計算。若只是加法,用取得並相加即可,但像變成2倍這種任意的更新,也能用這種形式不可分割地進行。

  • A. 即使是0,只要沒有被其他執行緒改變就會成功。
  • B. 正確。捨棄依據舊值的計算並重做。
  • C. 值的大小不是失敗的條件。
練習這個領域 前往領域頁面

多核心與同步的其他題目

  1. 在RISC-V的LR/SC(載入保留/條件式儲存)這類指令組中,SC(條件式儲存)會在什麼情況下失敗?
  2. 關於使用CAS的無鎖資料結構中會出現的ABA問題,下列說明何者正確?
  3. 關於RISC-V的amoadd.w指令或x86的lock xadd指令這類取得並相加(fetch-and-add)指令的動作,下列何者正確?
  4. 關於自旋鎖(spinlock),下列說明何者正確?
  5. 下列何者是最不適合使用自旋鎖的情境?

這個領域的比較