Skip to content
项目
群组
代码片段
帮助
当前项目
正在载入...
登录 / 注册
切换导航面板
X
xv6-public
项目
项目
详情
活动
周期分析
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
统计图
问题
0
问题
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
CI / CD
CI / CD
流水线
作业
日程
统计图
Wiki
Wiki
代码片段
代码片段
成员
成员
折叠边栏
关闭边栏
活动
图像
聊天
创建新问题
作业
提交
问题看板
Open sidebar
银宸时代
OS Lab Group
奖励实验
xv6-public
提交
c132eade
提交
c132eade
3月 01, 2012
创建
作者:
Nickolai Zeldovich
浏览文件
操作
浏览文件
下载
差异文件
Merge branch 'scale-amd64' of
git+ssh://pdos.csail.mit.edu/home/am0/6.828/xv6
into scale-amd64
上级
b002deab
a0943975
显示空白字符变更
内嵌
并排
正在显示
8 个修改的文件
包含
214 行增加
和
129 行删除
+214
-129
pls.cc
bin/pls.cc
+107
-0
kernel.hh
include/kernel.hh
+8
-35
mmu.h
include/mmu.h
+1
-0
proc.hh
include/proc.hh
+1
-0
cilk.cc
kernel/cilk.cc
+28
-50
exec.cc
kernel/exec.cc
+21
-18
main.cc
kernel/main.cc
+28
-5
wq.cc
kernel/wq.cc
+20
-21
没有找到文件。
bin/pls.cc
0 → 100644
浏览文件 @
c132eade
#include "types.h"
#include "stat.h"
#include "user.h"
#include "fs.h"
const
char
*
fmtname
(
const
char
*
path
)
{
static
char
buf
[
DIRSIZ
+
1
];
const
char
*
p
;
// Find first character after last slash.
for
(
p
=
path
+
strlen
(
path
);
p
>=
path
&&
*
p
!=
'/'
;
p
--
)
;
p
++
;
// Return blank-padded name.
if
(
strlen
(
p
)
>=
DIRSIZ
)
return
p
;
memmove
(
buf
,
p
,
strlen
(
p
));
memset
(
buf
+
strlen
(
p
),
' '
,
DIRSIZ
-
strlen
(
p
));
return
buf
;
}
void
ls
(
const
char
*
path
)
{
char
buf
[
512
],
*
p
;
int
fd
;
struct
dirent
de
;
struct
stat
st
;
if
((
fd
=
open
(
path
,
0
))
<
0
){
fprintf
(
2
,
"ls: cannot open %s
\n
"
,
path
);
return
;
}
if
(
fstat
(
fd
,
&
st
)
<
0
){
fprintf
(
2
,
"ls: cannot stat %s
\n
"
,
path
);
close
(
fd
);
return
;
}
switch
(
st
.
type
){
case
T_FILE
:
fprintf
(
1
,
"%s %d %d %d
\n
"
,
fmtname
(
path
),
st
.
type
,
st
.
ino
,
st
.
size
);
break
;
case
T_DIR
:
if
(
strlen
(
path
)
+
1
+
DIRSIZ
+
1
>
sizeof
buf
){
fprintf
(
1
,
"ls: path too long
\n
"
);
break
;
}
strcpy
(
buf
,
path
);
p
=
buf
+
strlen
(
buf
);
*
p
++
=
'/'
;
while
(
read
(
fd
,
&
de
,
sizeof
(
de
))
==
sizeof
(
de
)){
if
(
de
.
inum
==
0
)
continue
;
memmove
(
p
,
de
.
name
,
DIRSIZ
);
p
[
DIRSIZ
]
=
0
;
if
(
stat
(
buf
,
&
st
)
<
0
){
fprintf
(
1
,
"ls: cannot stat %s
\n
"
,
buf
);
continue
;
}
fprintf
(
1
,
"%s %d %d %d
\n
"
,
fmtname
(
buf
),
st
.
type
,
st
.
ino
,
st
.
size
);
}
break
;
}
close
(
fd
);
}
void
work
(
void
*
arg
)
{
u64
tid
=
(
u64
)
arg
;
// grab and push work (may divide into blocks? and call ls on a block)?
// maybe implement getdirent sys call that gives you some unread dir entry
}
int
main
(
int
argc
,
char
*
argv
[])
{
int
i
;
int
nthread
=
4
;
for
(
int
i
=
0
;
i
<
nthread
;
i
++
)
{
sbrk
(
8192
);
void
*
tstack
=
sbrk
(
0
);
// fprintf(1, "tstack %lx\n", tstack);
int
tid
=
forkt
(
tstack
,
(
void
*
)
thr
,
(
void
*
)(
u64
)
i
);
if
(
0
)
fprintf
(
1
,
"pls[%d]: child %d
\n
"
,
getpid
(),
tid
);
}
// push work wq.cc
if
(
argc
<
2
){
ls
(
"."
);
exit
();
}
for
(
i
=
1
;
i
<
argc
;
i
++
)
ls
(
argv
[
i
]);
for
(
int
i
=
0
;
i
<
nthread
;
i
++
)
wait
();
exit
();
}
include/kernel.hh
浏览文件 @
c132eade
...
@@ -263,54 +263,27 @@ struct work * allocwork(void);
...
@@ -263,54 +263,27 @@ struct work * allocwork(void);
void
freework
(
struct
work
*
w
);
void
freework
(
struct
work
*
w
);
// cilk.c
// cilk.c
void
initcilkframe
(
struct
cilkframe
*
);
#if CILKENABLE
#if CILKENABLE
void
cilk_push
(
void
(
*
fn
)(
uptr
,
uptr
),
u64
arg0
,
u64
arg1
);
void
cilk_push
(
void
(
*
fn
)(
uptr
,
uptr
),
u64
arg0
,
u64
arg1
);
void
cilk_start
(
void
);
void
cilk_start
(
void
);
void
cilk_end
(
void
);
u64
cilk_end
(
void
);
void
cilk_dump
(
void
);
void
cilk_dump
(
void
);
int
cilk_trywork
(
void
);
void
cilk_abort
(
u64
val
);
void
initcilkframe
(
struct
cilkframe
*
wq
);
#else
#else
#define cilk_push(rip, arg0, arg1) do { \
#define cilk_push(rip, arg0, arg1) do { \
void (*fn)(uptr, uptr) = rip; \
void (*fn)(uptr, uptr) = rip; \
fn(arg0, arg1); \
fn(arg0, arg1); \
} while(0)
} while(0)
#define cilk_start() do { } while(0)
#define cilk_start() do { } while(0)
#define cilk_end() do { } while(0)
#define cilk_end() (myproc()->cilkframe.abort)
#define cilk_dump() do { } while(0)
#define cilk_dump() do { } while(0)
#define cilk_trywork() 0
#define cilk_abort(val) do { \
#define initcilkframe(x) do { } while (0)
cmpxch(&myproc()->cilkframe.abort, (u64)0, (u64)val); \
} while (0)
#endif
#endif
// various init functions
void
initpic
(
void
);
void
initioapic
(
void
);
void
inituart
(
void
);
void
initcga
(
void
);
void
initconsole
(
void
);
void
initpg
(
void
);
void
initmp
(
void
);
void
initlapic
(
void
);
void
inittls
(
void
);
void
initnmi
(
void
);
void
inittrap
(
void
);
void
initseg
(
void
);
void
initkalloc
(
u64
mbaddr
);
void
initrcu
(
void
);
void
initproc
(
void
);
void
initbio
(
void
);
void
initinode
(
void
);
void
initdisk
(
void
);
void
inituser
(
void
);
void
initcilk
(
void
);
void
initsamp
(
void
);
void
initpci
(
void
);
void
initnet
(
void
);
void
initsched
(
void
);
void
initlockstat
(
void
);
void
initwq
(
void
);
void
initsperf
(
void
);
// other exported/imported functions
// other exported/imported functions
void
cmain
(
u64
mbmagic
,
u64
mbaddr
);
void
cmain
(
u64
mbmagic
,
u64
mbaddr
);
void
mpboot
(
void
);
void
mpboot
(
void
);
...
...
include/mmu.h
浏览文件 @
c132eade
...
@@ -24,6 +24,7 @@
...
@@ -24,6 +24,7 @@
#define PGROUNDUP(sz) (((sz)+PGSIZE-1) & ~(PGSIZE-1))
#define PGROUNDUP(sz) (((sz)+PGSIZE-1) & ~(PGSIZE-1))
#define PGROUNDDOWN(a) ((__typeof__(a))((((uptr)(a)) & ~(PGSIZE-1))))
#define PGROUNDDOWN(a) ((__typeof__(a))((((uptr)(a)) & ~(PGSIZE-1))))
#define PGOFFSET(a) ((a) & ((1<<PGSHIFT)-1))
// Address in page table or page directory entry
// Address in page table or page directory entry
#define PTE_ADDR(pte) ((uptr)(pte) & ~0xFFF)
#define PTE_ADDR(pte) ((uptr)(pte) & ~0xFFF)
...
...
include/proc.hh
浏览文件 @
c132eade
...
@@ -19,6 +19,7 @@ struct context {
...
@@ -19,6 +19,7 @@ struct context {
// Work queue frame
// Work queue frame
struct
cilkframe
{
struct
cilkframe
{
volatile
std
::
atomic
<
u64
>
ref
;
volatile
std
::
atomic
<
u64
>
ref
;
volatile
std
::
atomic
<
u64
>
abort
;
};
};
// Per-process, per-stack meta data for mtrace
// Per-process, per-stack meta data for mtrace
...
...
kernel/cilk.cc
浏览文件 @
c132eade
// cilk style run queue
// cilk style run queue built on wq.cc:
// A work queue is built from NCPU per-core wqueues.
// A core pushes work to the head of its per-core wq.
// A core pushes work to the head of its per-core wqueue.
// A core pops work from the head of its per-core wq.
// A core pops work from the head of its per-core wqueue.
// A core pops work from the tail of another core's per-core wqueue.
// A core pops work from the tail of another core's per-core wqueue.
//
//
// Usage:
// Usage:
...
@@ -25,7 +24,6 @@
...
@@ -25,7 +24,6 @@
// cprintf("%c %c\n", arg[0], arg[1]);
// cprintf("%c %c\n", arg[0], arg[1]);
// }
// }
#if CILKENABLE
#include "types.h"
#include "types.h"
#include "kernel.hh"
#include "kernel.hh"
#include "amd64.h"
#include "amd64.h"
...
@@ -35,37 +33,18 @@
...
@@ -35,37 +33,18 @@
#include "condvar.h"
#include "condvar.h"
#include "queue.h"
#include "queue.h"
#include "proc.hh"
#include "proc.hh"
#if CILKENABLE
#include "mtrace.h"
#include "mtrace.h"
#include "wq.hh"
#include "wq.hh"
#include "percpu.hh"
#define NSLOTS (1 << CILKSHIFT)
struct
cilkqueue
{
struct
cilkthread
*
thread
[
NSLOTS
];
volatile
int
head
__mpalign__
;
struct
spinlock
lock
;
volatile
int
tail
;
__padout__
;
}
__mpalign__
;
struct
cilkthread
{
u64
rip
;
u64
arg0
;
u64
arg1
;
struct
cilkframe
*
frame
;
// parent cilkframe
__padout__
;
}
__mpalign__
;
struct
cilkstat
{
struct
cilkstat
{
u64
push
;
u64
push
;
u64
full
;
u64
full
;
u64
steal
;
u64
steal
;
__padout__
;
};
}
__mpalign__
;
static
percpu
<
cilkstat
>
stat
;
static
struct
cilkqueue
queue
[
NCPU
]
__mpalign__
;
static
struct
cilkstat
stat
[
NCPU
]
__mpalign__
;
static
struct
cilkframe
*
static
struct
cilkframe
*
cilk_frame
(
void
)
cilk_frame
(
void
)
...
@@ -73,12 +52,6 @@ cilk_frame(void)
...
@@ -73,12 +52,6 @@ cilk_frame(void)
return
mycpu
()
->
cilkframe
;
return
mycpu
()
->
cilkframe
;
}
}
static
struct
cilkstat
*
cilk_stat
(
void
)
{
return
&
stat
[
mycpu
()
->
id
];
}
static
void
static
void
__cilk_run
(
struct
work
*
w
,
void
*
xfn
,
void
*
arg0
,
void
*
arg1
,
void
*
xframe
)
__cilk_run
(
struct
work
*
w
,
void
*
xfn
,
void
*
arg0
,
void
*
arg1
,
void
*
xframe
)
{
{
...
@@ -87,9 +60,10 @@ __cilk_run(struct work *w, void *xfn, void *arg0, void *arg1, void *xframe)
...
@@ -87,9 +60,10 @@ __cilk_run(struct work *w, void *xfn, void *arg0, void *arg1, void *xframe)
struct
cilkframe
*
old
=
mycpu
()
->
cilkframe
;
struct
cilkframe
*
old
=
mycpu
()
->
cilkframe
;
if
(
old
!=
frame
)
if
(
old
!=
frame
)
cilk_stat
()
->
steal
++
;
stat
->
steal
++
;
mycpu
()
->
cilkframe
=
frame
;
mycpu
()
->
cilkframe
=
frame
;
if
(
frame
->
abort
==
0
)
fn
((
uptr
)
arg0
,
(
uptr
)
arg1
);
fn
((
uptr
)
arg0
,
(
uptr
)
arg1
);
mycpu
()
->
cilkframe
=
old
;
mycpu
()
->
cilkframe
=
old
;
frame
->
ref
--
;
frame
->
ref
--
;
...
@@ -117,10 +91,10 @@ cilk_push(void (*fn)(uptr, uptr), u64 arg0, u64 arg1)
...
@@ -117,10 +91,10 @@ cilk_push(void (*fn)(uptr, uptr), u64 arg0, u64 arg1)
if
(
wq_push
(
w
))
{
if
(
wq_push
(
w
))
{
freework
(
w
);
freework
(
w
);
fn
(
arg0
,
arg1
);
fn
(
arg0
,
arg1
);
cilk_stat
()
->
full
++
;
stat
->
full
++
;
}
else
{
}
else
{
cilk_frame
()
->
ref
++
;
cilk_frame
()
->
ref
++
;
cilk_stat
()
->
push
++
;
stat
->
push
++
;
}
}
}
}
...
@@ -138,14 +112,26 @@ cilk_start(void)
...
@@ -138,14 +112,26 @@ cilk_start(void)
// End of the current work queue frame.
// End of the current work queue frame.
// The core works while the reference count of the current
// The core works while the reference count of the current
// work queue frame is not 0.
// work queue frame is not 0.
void
u64
cilk_end
(
void
)
cilk_end
(
void
)
{
{
u64
r
;
while
(
cilk_frame
()
->
ref
!=
0
)
while
(
cilk_frame
()
->
ref
!=
0
)
wq_trywork
();
wq_trywork
();
r
=
cilk_frame
()
->
abort
;
mycpu
()
->
cilkframe
=
0
;
mycpu
()
->
cilkframe
=
0
;
popcli
();
popcli
();
return
r
;
}
void
cilk_abort
(
u64
val
)
{
cmpxch
(
&
cilk_frame
()
->
abort
,
(
u64
)
0
,
val
);
}
}
void
void
...
@@ -189,19 +175,11 @@ testcilk(void)
...
@@ -189,19 +175,11 @@ testcilk(void)
}
}
popcli
();
popcli
();
}
}
#endif // CILKENABLE
void
void
initcilkframe
(
struct
cilkframe
*
cilk
)
initcilkframe
(
struct
cilkframe
*
cilk
)
{
{
memset
(
cilk
,
0
,
sizeof
(
*
cilk
));
cilk
->
ref
=
0
;
}
cilk
->
abort
=
0
;
void
initcilk
(
void
)
{
int
i
;
for
(
i
=
0
;
i
<
NCPU
;
i
++
)
initlock
(
&
queue
[
i
].
lock
,
"queue lock"
,
LOCKSTAT_CILK
);
}
}
#endif // CILKENABLE
kernel/exec.cc
浏览文件 @
c132eade
...
@@ -34,6 +34,10 @@ dosegment(uptr a0, u64 a1)
...
@@ -34,6 +34,10 @@ dosegment(uptr a0, u64 a1)
u64
off
=
a1
;
u64
off
=
a1
;
struct
vmnode
*
vmn
=
nullptr
;
struct
vmnode
*
vmn
=
nullptr
;
struct
proghdr
ph
;
struct
proghdr
ph
;
uptr
va_start
,
va_end
;
uptr
in_off
;
uptr
in_sz
;
int
npg
;
prof_start
(
dosegment_prof
);
prof_start
(
dosegment_prof
);
if
(
readi
(
args
->
ip
,
(
char
*
)
&
ph
,
off
,
sizeof
(
ph
))
!=
sizeof
(
ph
))
if
(
readi
(
args
->
ip
,
(
char
*
)
&
ph
,
off
,
sizeof
(
ph
))
!=
sizeof
(
ph
))
...
@@ -42,33 +46,30 @@ dosegment(uptr a0, u64 a1)
...
@@ -42,33 +46,30 @@ dosegment(uptr a0, u64 a1)
goto
bad
;
goto
bad
;
if
(
ph
.
memsz
<
ph
.
filesz
)
if
(
ph
.
memsz
<
ph
.
filesz
)
goto
bad
;
goto
bad
;
// XXX(sbw) vaddr doesn't have to be page aligned..
if
(
ph
.
offset
<
PGOFFSET
(
ph
.
vaddr
))
if
(
ph
.
vaddr
%
PGSIZE
)
{
cprintf
(
"unaligned ph.va
\n
"
);
goto
bad
;
goto
bad
;
}
{
va_start
=
PGROUNDDOWN
(
ph
.
vaddr
);
uptr
va_start
=
PGROUNDDOWN
(
ph
.
vaddr
);
va_end
=
PGROUNDUP
(
ph
.
vaddr
+
ph
.
memsz
);
uptr
va_end
=
PGROUNDUP
(
ph
.
vaddr
+
ph
.
memsz
);
in_off
=
ph
.
offset
-
PGOFFSET
(
ph
.
vaddr
);
in_sz
=
ph
.
filesz
+
PGOFFSET
(
ph
.
vaddr
);
int
npg
=
(
va_end
-
va_start
)
/
PGSIZE
;
npg
=
(
va_end
-
va_start
)
/
PGSIZE
;
if
((
vmn
=
new
vmnode
(
npg
,
odp
?
ONDEMAND
:
EAGER
,
if
((
vmn
=
new
vmnode
(
npg
,
odp
?
ONDEMAND
:
EAGER
,
args
->
ip
,
ph
.
offset
,
ph
.
file
sz
))
==
0
)
args
->
ip
,
in_off
,
in_
sz
))
==
0
)
goto
bad
;
goto
bad
;
if
(
args
->
vmap
->
insert
(
vmn
,
ph
.
vaddr
,
1
)
<
0
)
if
(
args
->
vmap
->
insert
(
vmn
,
va_start
,
1
)
<
0
)
goto
bad
;
goto
bad
;
prof_end
(
dosegment_prof
);
prof_end
(
dosegment_prof
);
return
;
return
;
}
bad:
bad:
panic
(
"dosegment: Oops"
);
cilk_abort
(
-
1
);
}
}
static
void
dostack
(
uptr
a0
,
u64
a1
)
static
void
__attribute__
((
unused
))
dostack
(
uptr
a0
,
u64
a1
)
{
{
struct
vmnode
*
vmn
=
nullptr
;
struct
vmnode
*
vmn
=
nullptr
;
struct
eargs
*
args
=
(
eargs
*
)
a0
;
struct
eargs
*
args
=
(
eargs
*
)
a0
;
...
@@ -110,18 +111,19 @@ static void dostack(uptr a0, u64 a1)
...
@@ -110,18 +111,19 @@ static void dostack(uptr a0, u64 a1)
for
(
last
=
s
=
args
->
path
;
*
s
;
s
++
)
for
(
last
=
s
=
args
->
path
;
*
s
;
s
++
)
if
(
*
s
==
'/'
)
if
(
*
s
==
'/'
)
last
=
s
+
1
;
last
=
s
+
1
;
safestrcpy
(
args
->
proc
->
name
,
last
,
sizeof
(
args
->
proc
->
name
));
// XXX(sbw) Oops, don't want to do this, unless we have abort
safestrcpy
(
args
->
proc
->
name
,
last
,
sizeof
(
args
->
proc
->
name
));
args
->
proc
->
tf
->
rsp
=
sp
;
args
->
proc
->
tf
->
rsp
=
sp
;
prof_end
(
dostack_prof
);
prof_end
(
dostack_prof
);
return
;
return
;
bad:
bad:
panic
(
"dostack: Oops"
);
cilk_abort
(
-
1
);
}
}
static
void
doheap
(
uptr
a0
,
u64
a1
)
static
void
__attribute__
((
unused
))
doheap
(
uptr
a0
,
u64
a1
)
{
{
struct
vmnode
*
vmn
=
nullptr
;
struct
vmnode
*
vmn
=
nullptr
;
struct
eargs
*
args
=
(
eargs
*
)
a0
;
struct
eargs
*
args
=
(
eargs
*
)
a0
;
...
@@ -138,7 +140,7 @@ static void doheap(uptr a0, u64 a1)
...
@@ -138,7 +140,7 @@ static void doheap(uptr a0, u64 a1)
return
;
return
;
bad:
bad:
panic
(
"doheap: Oops"
);
cilk_abort
(
-
1
);
}
}
int
int
...
@@ -204,7 +206,8 @@ exec(const char *path, char **argv)
...
@@ -204,7 +206,8 @@ exec(const char *path, char **argv)
//cilk_push(dostack, (uptr)&args, (uptr)0);
//cilk_push(dostack, (uptr)&args, (uptr)0);
dostack
((
uptr
)
&
args
,
(
uptr
)
0
);
dostack
((
uptr
)
&
args
,
(
uptr
)
0
);
cilk_end
();
if
(
cilk_end
())
goto
bad
;
// Commit to the user image.
// Commit to the user image.
oldvmap
=
myproc
()
->
vmap
;
oldvmap
=
myproc
()
->
vmap
;
...
...
kernel/main.cc
浏览文件 @
c132eade
...
@@ -9,8 +9,34 @@
...
@@ -9,8 +9,34 @@
#include "condvar.h"
#include "condvar.h"
#include "proc.hh"
#include "proc.hh"
extern
void
initidle
(
void
);
void
initpic
(
void
);
extern
void
idleloop
(
void
);
void
initioapic
(
void
);
void
inituart
(
void
);
void
initcga
(
void
);
void
initconsole
(
void
);
void
initpg
(
void
);
void
initmp
(
void
);
void
initlapic
(
void
);
void
inittls
(
void
);
void
initnmi
(
void
);
void
inittrap
(
void
);
void
initseg
(
void
);
void
initkalloc
(
u64
mbaddr
);
void
initrcu
(
void
);
void
initproc
(
void
);
void
initbio
(
void
);
void
initinode
(
void
);
void
initdisk
(
void
);
void
inituser
(
void
);
void
initsamp
(
void
);
void
initpci
(
void
);
void
initnet
(
void
);
void
initsched
(
void
);
void
initlockstat
(
void
);
void
initwq
(
void
);
void
initsperf
(
void
);
void
initidle
(
void
);
void
idleloop
(
void
);
static
volatile
int
bstate
;
static
volatile
int
bstate
;
...
@@ -89,9 +115,6 @@ cmain(u64 mbmagic, u64 mbaddr)
...
@@ -89,9 +115,6 @@ cmain(u64 mbmagic, u64 mbaddr)
initinode
();
// inode cache
initinode
();
// inode cache
initdisk
();
// disk
initdisk
();
// disk
initwq
();
initwq
();
#if CILKENABLE
initcilk
();
#endif
initsamp
();
initsamp
();
initlockstat
();
initlockstat
();
initpci
();
initpci
();
...
...
kernel/wq.cc
浏览文件 @
c132eade
...
@@ -109,10 +109,18 @@ wq_push2(void (*fn)(struct work*, void*, void*), void *a0, void *a1)
...
@@ -109,10 +109,18 @@ wq_push2(void (*fn)(struct work*, void*, void*), void *a0, void *a1)
return
0
;
return
0
;
}
}
static
struct
work
*
static
void
__wq_run
(
struct
work
*
w
)
{
void
(
*
fn
)(
struct
work
*
,
void
*
,
void
*
,
void
*
,
void
*
,
void
*
)
=
(
void
(
*
)(
work
*
,
void
*
,
void
*
,
void
*
,
void
*
,
void
*
))
w
->
rip
;
fn
(
w
,
w
->
arg0
,
w
->
arg1
,
w
->
arg2
,
w
->
arg3
,
w
->
arg4
);
freework
(
w
);
}
static
inline
struct
work
*
__wq_pop
(
int
c
)
__wq_pop
(
int
c
)
{
{
// Called with cli
struct
wqueue
*
wq
=
&
queue
[
c
];
struct
wqueue
*
wq
=
&
queue
[
c
];
struct
work
*
w
;
struct
work
*
w
;
int
i
;
int
i
;
...
@@ -136,10 +144,9 @@ __wq_pop(int c)
...
@@ -136,10 +144,9 @@ __wq_pop(int c)
return
w
;
return
w
;
}
}
static
struct
work
*
static
inline
struct
work
*
__wq_steal
(
int
c
)
__wq_steal
(
int
c
)
{
{
// Called with cli
struct
wqueue
*
wq
=
&
queue
[
c
];
struct
wqueue
*
wq
=
&
queue
[
c
];
struct
work
*
w
;
struct
work
*
w
;
int
i
;
int
i
;
...
@@ -160,42 +167,34 @@ __wq_steal(int c)
...
@@ -160,42 +167,34 @@ __wq_steal(int c)
return
w
;
return
w
;
}
}
static
void
__wq_run
(
struct
work
*
w
)
{
void
(
*
fn
)(
struct
work
*
,
void
*
,
void
*
,
void
*
,
void
*
,
void
*
)
=
(
void
(
*
)(
work
*
,
void
*
,
void
*
,
void
*
,
void
*
,
void
*
))
w
->
rip
;
fn
(
w
,
w
->
arg0
,
w
->
arg1
,
w
->
arg2
,
w
->
arg3
,
w
->
arg4
);
freework
(
w
);
}
int
int
wq_trywork
(
void
)
wq_trywork
(
void
)
{
{
struct
work
*
w
;
struct
work
*
w
;
int
i
;
int
i
,
k
;
// A "random" victim CPU
k
=
rdtsc
();
//pushcli();
w
=
__wq_pop
(
mycpu
()
->
id
);
w
=
__wq_pop
(
mycpu
()
->
id
);
if
(
w
!=
nullptr
)
{
if
(
w
!=
nullptr
)
{
__wq_run
(
w
);
__wq_run
(
w
);
//popcli();
return
1
;
return
1
;
}
}
// XXX(sbw) should be random
for
(
i
=
0
;
i
<
NCPU
;
i
++
)
{
for
(
i
=
0
;
i
<
NCPU
;
i
++
)
{
if
(
i
==
mycpu
()
->
id
)
int
j
=
(
i
+
k
)
%
NCPU
;
if
(
j
==
mycpu
()
->
id
)
continue
;
continue
;
w
=
__wq_steal
(
i
);
w
=
__wq_steal
(
j
);
if
(
w
!=
nullptr
)
{
if
(
w
!=
nullptr
)
{
__wq_run
(
w
);
__wq_run
(
w
);
//popcli();
return
1
;
return
1
;
}
}
}
}
//popcli();
return
0
;
return
0
;
}
}
...
...
编写
预览
您添加了
0
人
到此讨论。请谨慎行事。
请先完成此评论的编辑!
取消
请
注册
或者
登录
后发表评论