qlock.c
来自「著名操作系统Plan 9的第三版的部分核心源代码。现在很难找到了。Plan 9是」· C语言 代码 · 共 217 行
C
217 行
#include "u.h"#include "../port/lib.h"#include "mem.h"#include "dat.h"#include "fns.h"struct { ulong rlock; ulong rlockq; ulong wlock; ulong wlockq; ulong qlock; ulong qlockq;} rwstats;voidqlock(QLock *q){ Proc *p, *mp; lock(&q->use);rwstats.qlock++; if(!q->locked) { q->locked = 1; unlock(&q->use); return; }rwstats.qlockq++; p = q->tail; mp = up; if(mp == nil) panic("qlock"); if(p == 0) q->head = mp; else p->qnext = mp; q->tail = mp; mp->qnext = 0; mp->state = Queueing; up->qpc = getcallerpc(&q); unlock(&q->use); sched();}intcanqlock(QLock *q){ if(!canlock(&q->use)) return 0; if(q->locked){ unlock(&q->use); return 0; } q->locked = 1; unlock(&q->use); return 1;}voidqunlock(QLock *q){ Proc *p; lock(&q->use); p = q->head; if(p) { q->head = p->qnext; if(q->head == 0) q->tail = 0; unlock(&q->use); ready(p); return; } q->locked = 0; unlock(&q->use);}voidrlock(RWlock *q){ Proc *p, *mp; lock(&q->use);rwstats.rlock++; if(q->writer == 0 && q->head == nil){ /* no writer, go for it */ q->readers++; unlock(&q->use); return; }rwstats.rlockq++; p = q->tail; mp = up; if(mp == nil) panic("rlock"); if(p == 0) q->head = mp; else p->qnext = mp; q->tail = mp; mp->qnext = 0; mp->state = QueueingR; unlock(&q->use); sched();}voidrunlock(RWlock *q){ Proc *p; lock(&q->use); p = q->head; if(--(q->readers) > 0 || p == nil){ unlock(&q->use); return; } /* start waiting writer */ if(p->state != QueueingW) panic("runlock"); q->head = p->qnext; if(q->head == 0) q->tail = 0; q->writer = 1; unlock(&q->use); ready(p);}voidwlock(RWlock *q){ Proc *p, *mp; lock(&q->use);rwstats.wlock++; if(q->readers == 0 && q->writer == 0){ /* noone waiting, go for it */ q->wpc = getcallerpc(&q); q->wproc = up; q->writer = 1; unlock(&q->use); return; } /* wait */rwstats.wlockq++; p = q->tail; mp = up; if(mp == nil) panic("wlock"); if(p == nil) q->head = mp; else p->qnext = mp; q->tail = mp; mp->qnext = 0; mp->state = QueueingW; unlock(&q->use); sched();}voidwunlock(RWlock *q){ Proc *p; lock(&q->use); p = q->head; if(p == nil){ q->writer = 0; unlock(&q->use); return; } if(p->state == QueueingW){ /* start waiting writer */ q->head = p->qnext; if(q->head == nil) q->tail = nil; unlock(&q->use); ready(p); return; } if(p->state != QueueingR) panic("wunlock"); /* waken waiting readers */ while(q->head != nil && q->head->state == QueueingR){ p = q->head; q->head = p->qnext; q->readers++; ready(p); } if(q->head == nil) q->tail = nil; q->writer = 0; unlock(&q->use);}/* same as rlock but punts if there are any readers waiting */intcanrlock(RWlock *q){ lock(&q->use);rwstats.rlock++; if(q->writer == 0 && q->head == nil){ /* no writer, go for it */ q->readers++; unlock(&q->use); return 1; } unlock(&q->use); return 0;}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?