提交 eddb2693 创建 作者: Nickolai Zeldovich's avatar Nickolai Zeldovich

one less pushcli/popcli

上级 83ec933a
...@@ -57,9 +57,9 @@ struct proc : public rcu_freed { ...@@ -57,9 +57,9 @@ struct proc : public rcu_freed {
SLIST_HEAD(childlist, proc) childq; SLIST_HEAD(childlist, proc) childq;
SLIST_ENTRY(proc) child_next; SLIST_ENTRY(proc) child_next;
struct condvar cv; struct condvar cv;
u64 epoch; std::atomic<u64> epoch;
struct spinlock gc_epoch_lock; struct spinlock gc_epoch_lock;
u64 epoch_depth; std::atomic<u64> epoch_depth;
char lockname[16]; char lockname[16];
int on_runq; int on_runq;
int cpu_pin; int cpu_pin;
......
...@@ -138,7 +138,7 @@ gc_delayfreelist(void) ...@@ -138,7 +138,7 @@ gc_delayfreelist(void)
// p->epoch, so gc_thread does it for them. XXX get rid off lock? // p->epoch, so gc_thread does it for them. XXX get rid off lock?
acquire(&p->gc_epoch_lock); acquire(&p->gc_epoch_lock);
if (p->epoch_depth == 0) if (p->epoch_depth == 0)
p->epoch = global_epoch; p->epoch = global_epoch.load();
release(&p->gc_epoch_lock); release(&p->gc_epoch_lock);
// cprintf("gc_min %d(%s): %lu %ld\n", p->pid, p->name, p->epoch, p->epoch_depth); // cprintf("gc_min %d(%s): %lu %ld\n", p->pid, p->name, p->epoch, p->epoch_depth);
if (min > p->epoch) if (min > p->epoch)
...@@ -155,9 +155,9 @@ gc_delayfreelist(void) ...@@ -155,9 +155,9 @@ gc_delayfreelist(void)
void void
gc_delayed(rcu_freed *e) gc_delayed(rcu_freed *e)
{ {
gc_state[mycpu()->id].ndelayed++;
pushcli();
int c = mycpu()->id; int c = mycpu()->id;
gc_state[c].ndelayed++;
u64 myepoch = myproc()->epoch; u64 myepoch = myproc()->epoch;
u64 minepoch = gc_state[c].delayed[myepoch % NEPOCH].epoch; u64 minepoch = gc_state[c].delayed[myepoch % NEPOCH].epoch;
if (gc_debug) if (gc_debug)
...@@ -170,7 +170,6 @@ gc_delayed(rcu_freed *e) ...@@ -170,7 +170,6 @@ gc_delayed(rcu_freed *e)
e->_rcu_epoch = myepoch; e->_rcu_epoch = myepoch;
e->_rcu_next = gc_state[c].delayed[myepoch % NEPOCH].head; e->_rcu_next = gc_state[c].delayed[myepoch % NEPOCH].head;
while (!cmpxch_update(&gc_state[c].delayed[myepoch % NEPOCH].head, &e->_rcu_next, e)) {} while (!cmpxch_update(&gc_state[c].delayed[myepoch % NEPOCH].head, &e->_rcu_next, e)) {}
popcli();
} }
void void
...@@ -180,9 +179,10 @@ gc_begin_epoch(void) ...@@ -180,9 +179,10 @@ gc_begin_epoch(void)
acquire(&myproc()->gc_epoch_lock); acquire(&myproc()->gc_epoch_lock);
if (myproc()->epoch_depth++ > 0) if (myproc()->epoch_depth++ > 0)
goto done; goto done;
myproc()->epoch = global_epoch; // not atomic, but it never goes backwards myproc()->epoch = global_epoch.load(); // not atomic, but it never goes backwards
// __sync_synchronize(); // __sync_synchronize();
done: done:
(void) 0;
release(&myproc()->gc_epoch_lock); release(&myproc()->gc_epoch_lock);
} }
...@@ -221,7 +221,7 @@ gc_worker(void *x) ...@@ -221,7 +221,7 @@ gc_worker(void *x)
release(&wl); release(&wl);
gc_state[mycpu()->id].nrun++; gc_state[mycpu()->id].nrun++;
u64 global = global_epoch; u64 global = global_epoch;
myproc()->epoch = global_epoch; // move the gc thread to next epoch myproc()->epoch = global_epoch.load(); // move the gc thread to next epoch
for (i = gc_state[mycpu()->id].min_epoch; i < global-2; i++) { for (i = gc_state[mycpu()->id].min_epoch; i < global-2; i++) {
int nfree = gc_free_tofreelist(&gc_state[mycpu()->id].tofree[i%NEPOCH].head, i); int nfree = gc_free_tofreelist(&gc_state[mycpu()->id].tofree[i%NEPOCH].head, i);
gc_state[mycpu()->id].tofree[i%NEPOCH].epoch += NEPOCH; gc_state[mycpu()->id].tofree[i%NEPOCH].epoch += NEPOCH;
...@@ -239,7 +239,7 @@ gc_worker(void *x) ...@@ -239,7 +239,7 @@ gc_worker(void *x)
void void
initprocgc(struct proc *p) initprocgc(struct proc *p)
{ {
p->epoch = global_epoch; p->epoch = global_epoch.load();
p->epoch_depth = 0; p->epoch_depth = 0;
initlock(&p->gc_epoch_lock, "per process gc_lock", 0); initlock(&p->gc_epoch_lock, "per process gc_lock", 0);
} }
......
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论