自我介紹

Text

暱稱: Hohshen

目前擔任: 肝苦碼農

Lock鎖

By Hohshen

目錄

1. 那樣的夜色太美你太溫柔-都是xx惹的禍

2. 命中注定鎖定你-共享資源

3. 解鎖還需上鎖人-鎖的方式

4. 綑綁與羈絆-分散的鎖
5. 多共享變數

隱藏黑暗力量的鑰匙啊,

在我面前顯示真正的力量吧!

跟擬定下約定的BESG命令你,封印解除!

那樣的夜色太美你太溫柔-

都是xx惹的禍

這是一個解鎖匠的故事,  在很久很久以前......

單用戶系統

輸入完磁帶,才開始跑,
每run一次就要重新把磁帶在讀入

批次處理系統

資料和程式可以在運行之中透過I/O輸入,

每次的執行,都會包裝成一個job,

cpu會一個一個job的處理

多道程序系統

開始有process和schedule的概念,

基本上每個process執行中不會做切換,

但是當process正在等待i/o時,可以先把cpu使用權交給其他process

分時系統

為了解決有其中一個process跑得特別久
有time Interrupt了,不管正在執行的process執行到哪裡了

分時系統

該如何在容易被中途插入的過程中,

順利的完成理想的結果呢?

通通都是分時惹的禍!

命中注定鎖定你-
共享資源

這是一個青澀的愛情的故事...

Text

 那些年,

我們一起追的共享變數......

介紹共享變數的互斥性

process

process

process

Text

共享變數

故事的背景是這樣的...

但因多個process間共享資源,執行過程中有需多不確定性,也難以重現,錯誤也可能間歇性的發生

多個process同時併發,有需多好處
1. 共享資源: e.g.帳戶餘額可以在多台atm上做操作

2. 分工加速: e.g. 把功能切成數塊,分工運作

3. 模組化: e.g. 大程式切成小程式

問題演示

getter=getter+1

LOAD mem reg1
STORE reg1 getter
INC reg1
STORE reg1 mem

生活應用

買麵包問題

try1 買麵包前留下一張便利貼

if(no_bread){
    if(no_note){
        leave_note
        buy_bread
        remove_note
    }
}

try2 先貼便利貼,
再確認冰箱有沒有麵包

 
leave_note
if(no_bread){
    if(no_note){
        buy_bread
    }
}
remove_note
try3
A一直檢查是否有便利貼,沒有貼就馬上去買,
B先貼便利貼,在確認冰箱有沒有麵包,並且在便利貼上寫名字
//A
leave_note_A
while(no_note_B){}
if(no_bread){
    buy_bread
}
remove_note_A
//B
leave_note_B
if(no_note_A){
    if(no_bread){
        buy_bread
    }
}
remove_note_B

try4 Peterson Alg

// 以下是A的code,B記得換成對方的變數
do{
    note_A=true
    turn=P_B //表示自己可以去,不過對方想去可以先給對方=>增加公平性
    while(note_B===true&&turn=P_B){} //忙等待,對方想去,且對方真的有權要去
    //c.s. start
    buy_bread
    //c.s. end
    note_A=false
}while(true)

try5 Dekker Alg更多thread

環形演算法,類似Peterson的衍生

臨界區間需要原子性的操作

有一個操作,不存在任何

中斷(就算中斷也不引響該共享變數)或失敗

1. 成功就全部完成

2. 失敗就全部退回

3. 不會有部份成功發生

臨界區間Critical section

在訪問c.s.時,必須是互斥的,當有人在裡面時,其他人不可以進來

1. 空閒則入 2. 忙則阻塞等待 

3. 有限阻塞 4. 讓權阻塞(option)

Process/thread的共享變數

解鎖還需上鎖人-
鎖的方式

除了剛剛軟體法外

硬體法

 

禁用中斷

spin lock(mutex lock)

  • atomic ts,exchage
    硬體保證該function內 atomic
boolean TestAndSet(boolean * target){
    boolean rv= *target
    *target=true
    return rv
}

Implement

class Lock{
boolean value=0;
    acquire(){
        while(TestAndSet(value)){};//忙等待
    }
    release(){
        value=0
    }
}

OS法

 

Semaphore

三個成員
sem:共享變數
P(): if(sem>0){ sem-- }else{ waitQueue.enqueue(threadA)}
V(): if(sem<=0){ sem++; waitQueue.dequeue(); }
使用點:

1. c.s.

2. 條件等待

class BoundBuf{
    const mutex=Semphore(1)
    const fullBuf=Semphore(0)
    const eptBuf=Semphore(n)
    const q=queue()
    public productor(c){
        eptBuf.P()
        mutex.P()
        q.enqueue(c)
        mutex.V()
        fullBuf.V()
    }
    
    public consumer(){
        fullBuf.P()
        mutex.P()
        q.dequeue(c)
        mutex.V()
        eptBuf.V()
    }
}

Monitor

一個鎖,n個條件,兩個操作

class BoundBuf{
    const entryLock=lock()
    const count=0
    const notFull=Condition()
    const notEmpt=Condition()
    const q=queue()
    public productor(c){
        entryLock.acquire()
        //滿時不能進
        while(count==n){
            notFull.wait(&entryLock)
        }
        
        q.enqueue(c)
        count++
        
        //告知非空
        notEmpt.signal()
        entryLock.release()
    }
    
    public consumer(){
        entryLock.acquire()
        //空時不能進
        while(count==0){
            notEmpt.wait(&entryLock)
        }
        
        q.dequeue(c)
        count--
        
        //告知非滿
        notFull.signal()
        entryLock.release()
    }
}

但......令人失望的是

綑綁與羈絆-
分散的鎖

分散式鎖

放大一點

其實還是同一台

介紹分散式鎖與原理

demo1

多共享變數

介紹共享變數在多個地方性

這是一個有關於影分身之術的故事...

共享變數Cluster

 那些年,

我們一起追的共享變數......

process

process

process

Redis Cluster

R/W split

Sentinel(R/W split)

Cluster

進入點都是一樣在master上的

RedLock

 

Subtitle

​成功條件:只要過半 N/2+1

根本沒有一個叢集長這樣阿QAQ

 

RedLock 方法就是根除普通基於 Redis 分佈式鎖而生的(無論是主從模式、sentinel 模式還是 cluster 模式)
我們假設有 N 個 Redis Master。
這些節點完全互相獨立,
不存在主從複製或者其他集羣協調機制(重點!!

但他的同步機制呢?

Gossip protocol

DEMO:
 

Subtitle

謝謝大家

Q&A+工商時間

Lock

By Shen Hoh

Lock

  • 131