提交 d678eac0 创建 作者: Robert Morris's avatar Robert Morris

hack to farm mmap()s out to wq

上级 22ed1efb
......@@ -18,6 +18,7 @@ UPROGS= \
usertests \
lockstat \
preadtest \
scripttest \
ftest \
perf
......
#include "types.h"
#include "stat.h"
#include "fcntl.h"
#include "user.h"
#include "lib.h"
#include "amd64.h"
#include "ipc.hh"
#include "mmu.h"
int
main(int ac, char **av)
{
char *p = (char*) PGROUNDUP((u64)(sbrk(0) + 0x80000));
u64 len = 1000*4096;
u64 chunk = 128*4096; // max vmnode size
#if 0
char *q = p;
while(q < p + len){
u64 x = len - (q - p);
if(x > chunk)
x = chunk;
if(map(q, x) < 0){
fprintf(1, "map failed\n");
exit();
}
q += x;
}
#else
script(p, len, chunk);
#endif
memset(p, 1, len);
exit();
}
......@@ -47,6 +47,7 @@ long sys_listen(int, int);
long sys_accept(int, void*, void*);
long sys_pread(int fd, void *ubuf, size_t count, off_t offset);
long sys_async(int, size_t, off_t, u32, u32);
long sys_script(void *addr, u64 len, u64 chunk);
extern long (*syscalls[])(u64, u64, u64, u64, u64, u64);
// other exported/imported functions
......
......@@ -29,4 +29,5 @@
#define SYS_accept 28
#define SYS_pread 29
#define SYS_async 30
#define SYS_ncount 31 /* total number of system calls */
#define SYS_script 31
#define SYS_ncount 32 /* total number of system calls */
......@@ -29,6 +29,7 @@ int unmap(void *addr, int len);
void halt(void);
ssize_t pread(int, void*, size_t, off_t);
int async(int, size_t, off_t, u32, u32);
int script(void *addr, u64 len, u64 chunk);
// ulib.c
int stat(char*, struct stat*);
......
......@@ -60,7 +60,7 @@ struct vmap {
void decref();
vmap* copy(int share);
vma* lookup(uptr start, uptr len);
int insert(vmnode *n, uptr va_start);
int insert(vmnode *n, uptr va_start, int dotlb);
int remove(uptr start, uptr len);
int pagefault(uptr va, u32 err);
......
......@@ -44,6 +44,7 @@ OBJS = \
trap.o \
trapasm.o \
wq.o \
script.o \
incbin.o
OBJS := $(addprefix $(O)/kernel/, $(OBJS))
......
......@@ -78,5 +78,6 @@ long (*syscalls[])(u64, u64, u64, u64, u64, u64) = {
SYSCALL(accept),
SYSCALL(pread),
SYSCALL(async),
SYSCALL(script),
};
......@@ -58,7 +58,7 @@ dosegment(uptr a0, u64 a1)
args->ip, ph.offset, ph.filesz)) == 0)
goto bad;
if(args->vmap->insert(vmn, ph.vaddr) < 0)
if(args->vmap->insert(vmn, ph.vaddr, 1) < 0)
goto bad;
prof_end(dosegment_prof);
......@@ -82,7 +82,7 @@ static void dostack(uptr a0, u64 a1)
// Allocate a one-page stack at the top of the (user) address space
if((vmn = new vmnode(USTACKPAGES)) == 0)
goto bad;
if(args->vmap->insert(vmn, USERTOP-(USTACKPAGES*PGSIZE)) < 0)
if(args->vmap->insert(vmn, USERTOP-(USTACKPAGES*PGSIZE), 1) < 0)
goto bad;
vmn = 0;
......@@ -133,7 +133,7 @@ static void doheap(uptr a0, u64 a1)
// XXX pre-allocate 32 pages..
if((vmn = new vmnode(32)) == 0)
goto bad;
if(args->vmap->insert(vmn, BRK) < 0)
if(args->vmap->insert(vmn, BRK, 1) < 0)
goto bad;
vmn = 0;
prof_end(doheap_prof);
......
......@@ -277,7 +277,7 @@ inituser(void)
vmnode *vmn = new vmnode(PGROUNDUP(_initcode_size) / PGSIZE);
if(vmn == 0)
panic("userinit: vmn_allocpg");
if(p->vmap->insert(vmn, 0) < 0)
if(p->vmap->insert(vmn, 0, 1) < 0)
panic("userinit: vmap_insert");
if(p->vmap->copyout(0, _initcode_start, _initcode_size) < 0)
panic("userinit: copyout");
......@@ -391,6 +391,7 @@ scheduler(void)
if (idle[mycpu()->id]) {
int worked;
do {
assert(mycpu()->ncli == 0);
worked = wq_trywork();
} while(worked);
sti();
......
......@@ -9,7 +9,7 @@
#include "cpu.hh"
#include "bits.hh"
#include "kmtrace.hh"
#include "sched.h"
#include "sched.hh"
#include "vm.hh"
#include <stddef.h>
......
#include "types.h"
#include "kernel.hh"
#include "spinlock.h"
#include "condvar.h"
#include "cpu.hh"
#include "proc.hh"
#include "fs.h"
#include "wq.hh"
#include "ipc.hh"
#include "vm.hh"
#include "file.hh"
void
script_mmap_work(struct work *w, void *a0, void *a1, void *a2, void *a3)
{
void *addr = (void *) a0;
u64 len = (u64) a1;
atomic<int> *donep = (atomic<int> *) a2;
struct proc *p = (struct proc *) a3;
vmnode *vmn = new vmnode(PGROUNDUP(len) / PGSIZE);
if(vmn == 0)
panic("sys_script: new vmnode");
if(p->vmap->insert(vmn, PGROUNDDOWN((u64)addr), 0) < 0)
panic("sys_script: insert");
*donep += 1;
}
long
sys_script(void *addr, u64 len, u64 chunk)
{
atomic<int> done;
done = 0;
int queued = 0;
char *q = (char*) addr;
while(q < (char*)addr + len){
u64 x = len - (q - (char*)addr);
if(x > chunk)
x = chunk;
struct work *w = allocwork();
if(w == 0)
panic("sys_script allocwork");
w->rip = (void*) script_mmap_work;
w->arg0 = (void *) q;
w->arg1 = (void *) x;
w->arg2 = (void *) &done;
w->arg3 = (void *) myproc();
if(wq_push(w) < 0)
panic("sys_script wq_push");
queued++;
q += chunk;
}
while(done < queued){
// yield();
wq_trywork();
}
tlbflush();
return 0;
}
......@@ -111,7 +111,7 @@ sys_map(void)
if (vmn == 0)
return -1;
if (myproc()->vmap->insert(vmn, PGROUNDDOWN(addr)) < 0) {
if (myproc()->vmap->insert(vmn, PGROUNDDOWN(addr), 1) < 0) {
delete vmn;
return -1;
}
......
......@@ -275,7 +275,7 @@ vmap::lookup(uptr start, uptr len)
}
int
vmap::insert(vmnode *n, uptr vma_start)
vmap::insert(vmnode *n, uptr vma_start, int dotlb)
{
vma *e;
......@@ -309,7 +309,8 @@ vmap::insert(vmnode *n, uptr vma_start)
break;
}
});
tlbflush();
if(dotlb)
tlbflush();
return 0;
}
......
......@@ -38,3 +38,4 @@ SYSCALL(listen)
SYSCALL(accept)
SYSCALL(pread)
SYSCALL(async)
SYSCALL(script)
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论