提交 5515a5e3 创建 作者: Silas Boyd-Wickizer's avatar Silas Boyd-Wickizer

Merge.

......@@ -32,6 +32,7 @@ OBJS = \
cga.o \
condvar.o \
console.o \
crange.o \
e1000.o \
exec.o \
file.o \
......@@ -53,6 +54,7 @@ OBJS = \
proc.o \
prof.o \
gc.o \
rnd.o \
sampler.o \
sched.o \
spinlock.o \
......
差异被折叠。
......@@ -31,7 +31,7 @@ struct gc {
};
int type;
} __mpalign__;
struct gc gc_epoch[NEPOCH] __mpalign__;
struct gc gc_epoch[NEPOCH][NCPU] __mpalign__;
u64 global_epoch __mpalign__;
int ndelayed __mpalign__;
......@@ -73,6 +73,9 @@ gc_free_elem(struct gc *r)
static void
gc_free_epoch(u64 epoch)
{
cprintf("free epoch %d\n", epoch);
for (int j = 0; j < NCPU; j++) {
if (__sync_bool_compare_and_swap(&global_epoch, epoch, epoch+1)) {
// only one core succeeds; that core in charge of freeing epoch
struct gc *head;
......@@ -80,13 +83,13 @@ gc_free_epoch(u64 epoch)
uint32 fe = (epoch - (NEPOCH-2)) % NEPOCH;
int cas;
if (gc_epoch[fe].epoch != epoch - (NEPOCH-2))
if (gc_epoch[fe][j].epoch != epoch - (NEPOCH-2))
panic("gc_free_epoch");
// unhook list for fe epoch atomically
head = gc_epoch[fe].next;
head = gc_epoch[fe][j].next;
// this shouldn't fail, because no core is modifying it.
cas = __sync_bool_compare_and_swap(&gc_epoch[fe].next, head, 0);
cas = __sync_bool_compare_and_swap(&gc_epoch[fe][j].next, head, 0);
if (!cas) panic("gc_free_epoch");
// free list items on the delayed list
for (r = head; r != NULL; r = nr) {
......@@ -99,9 +102,10 @@ gc_free_epoch(u64 epoch)
int x = __sync_fetch_and_sub(&ndelayed, 1);
if (x < 0) panic("gc_free_epoch");
}
if (gc_epoch[fe].next != 0)
if (gc_epoch[fe][j].next != 0)
panic("gc_free_epoch");
gc_epoch[fe].epoch = gc_epoch[fe].epoch + NEPOCH;
gc_epoch[fe][j].epoch = gc_epoch[fe][j].epoch + NEPOCH;
}
}
}
......@@ -148,7 +152,7 @@ gc_delayed_int(struct gc *r)
{
pushcli();
u64 myepoch = myproc()->epoch;
u64 minepoch = gc_epoch[myepoch % NEPOCH].epoch;
u64 minepoch = gc_epoch[myepoch % NEPOCH][mycpu()->id].epoch;
// cprintf("%d: gc_delayed: %lu ndelayed %d\n", myproc()->pid, global_epoch, ndelayed);
if (myepoch != minepoch) {
cprintf("%d: myepoch %lu minepoch %lu\n", myproc()->pid, myepoch, minepoch);
......@@ -156,8 +160,8 @@ gc_delayed_int(struct gc *r)
}
r->epoch = myepoch;
do {
r->next = gc_epoch[myepoch % NEPOCH].next;
} while (!__sync_bool_compare_and_swap(&(gc_epoch[myepoch % NEPOCH].next), r->next, r));
r->next = gc_epoch[myepoch % NEPOCH][mycpu()->id].next;
} while (!__sync_bool_compare_and_swap(&(gc_epoch[myepoch % NEPOCH][mycpu()->id].next), r->next, r));
popcli();
}
......@@ -210,5 +214,6 @@ initgc(void)
}
global_epoch = NEPOCH-2;
for (int i = 0; i < NEPOCH; i++)
gc_epoch[i].epoch = i;
for (int j = 0; j < NEPOCH; j++)
gc_epoch[i][j].epoch = i;
}
......@@ -102,6 +102,15 @@ int dirlink(struct inode*, char*, u32);
void dir_init(struct inode *dp);
void dir_flush(struct inode *dp);
// gc.c
void initgc(void);
void gc_begin_epoch();
void gc_end_epoch();
void gc_delayed(void*, void (*dofree)(void*));
void gc_delayed2(int, u64, void (*dofree)(int, u64));
void gc_start(void);
void gc_worker(void);
// hwvm.c
void freevm(pml4e_t*);
pml4e_t* setupkvm(void);
......@@ -225,14 +234,9 @@ extern int profenable;
void profreset(void);
void profdump(void);
// rcu.c
void initgc(void);
void gc_begin_epoch();
void gc_end_epoch();
void gc_delayed(void*, void (*dofree)(void*));
void gc_delayed2(int, u64, void (*dofree)(int, u64));
void gc_start(void);
void gc_worker(void);
// rnd.c
u64 rnd();
// sampler.c
void sampstart(void);
......
#include "param.h"
#include "types.h"
#include "kernel.h"
#include "cpu.h"
struct seed {
u64 v;
} __mapalign__;
static struct seed seeds[NCPU] __mpalign__;
u64
rnd(void)
{
if (seeds[mycpu()->id].v == 0) {
seeds[mycpu()->id].v = ticks;
}
seeds[mycpu()->id].v =
seeds[mycpu()->id].v * 6364136223846793005 + 1442695040888963407;
return seeds[mycpu()->id].v;
}
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论