More wq rejigger..

上级 6ba1797d
$(O)/bin/%.o: CFLAGS:=$(CFLAGS) $(O)/bin/%.o: CFLAGS:=$(CFLAGS) -DXV6_USER
$(O)/bin/%.o: CXXFLAGS:=$(CXXFLAGS) $(O)/bin/%.o: CXXFLAGS:=$(CXXFLAGS) -DXV6_USER
UPROGS= \ UPROGS= \
bench \ bench \
......
...@@ -12,6 +12,7 @@ typedef uint64_t u64; ...@@ -12,6 +12,7 @@ typedef uint64_t u64;
#include "wq.hh" #include "wq.hh"
#include "reducer.hh" #include "reducer.hh"
#include "user/dirit.hh" #include "user/dirit.hh"
#include "user/util.h"
#define ST_SIZE(st) (st).st_size #define ST_SIZE(st) (st).st_size
#define ST_ISDIR(st) S_ISDIR((st).st_mode) #define ST_ISDIR(st) S_ISDIR((st).st_mode)
#define BSIZ 256 #define BSIZ 256
......
...@@ -5,7 +5,9 @@ ...@@ -5,7 +5,9 @@
#include <string.h> #include <string.h>
#include <fcntl.h> #include <fcntl.h>
#include <unistd.h> #include <unistd.h>
#include "types.h"
#include "user/dirit.hh" #include "user/dirit.hh"
#include "user/util.h"
#include "wq.hh" #include "wq.hh"
#define ST_SIZE(st) (st).st_size #define ST_SIZE(st) (st).st_size
#define ST_TYPE(st) (ST_ISDIR(st) ? 1 : ST_ISREG(st) ? 2 : 3) #define ST_TYPE(st) (ST_ISDIR(st) ? 1 : ST_ISREG(st) ? 2 : 3)
......
...@@ -3,6 +3,7 @@ ...@@ -3,6 +3,7 @@
#include "wqtypes.hh" #include "wqtypes.hh"
#include "percpu.hh" #include "percpu.hh"
struct uwq_ipcbuf;
class work; class work;
int wq_trywork(void); int wq_trywork(void);
...@@ -80,20 +81,17 @@ private: ...@@ -80,20 +81,17 @@ private:
#endif #endif
}; };
void* xallocwork(unsigned long nbytes);
void xfreework(void* ptr, unsigned long nbytes);
#if defined(XV6_USER)
void* wqalloc(unsigned long nbytes);
void wqfree(void *ptr);
extern u64 wq_maxworkers;
#endif
#if defined(LINUX) #if defined(LINUX)
#include <stdlib.h>
#include <assert.h> #include <assert.h>
#include <atomic>
#define xallocwork(n) malloc(n)
#define xfreework(p, sz) free(p)
#elif defined(XV6_KERNEL)
#define xallocwork(n) kmalloc(n, "xallocwork")
#define xfreework(p, sz) kmfree(p, sz)
#else // xv6 user
extern void* wqalloc(unsigned long nbytes);
extern void wqfree(void *ptr);
#define xallocwork(n) wqalloc(n)
#define xfreework(n, sz) wqfree(n)
extern u64 wq_maxworkers; extern u64 wq_maxworkers;
#endif #endif
......
...@@ -2,14 +2,9 @@ ...@@ -2,14 +2,9 @@
#include "uspinlock.h" #include "uspinlock.h"
#include "amd64.h" #include "amd64.h"
#include "user.h" #include "user.h"
#include "pthread.h"
#include "memlayout.h" #include "memlayout.h"
#include "uwq.hh" #include "uwq.hh"
#include "atomic.hh" #include "wqtypes.hh"
#include "lib.h"
#include "elf.hh"
typedef struct uspinlock wqlock_t;
int mycpuid(void); int mycpuid(void);
...@@ -56,7 +51,3 @@ wqlock_init(wqlock_t *lock) ...@@ -56,7 +51,3 @@ wqlock_init(wqlock_t *lock)
} }
#define xprintf printf #define xprintf printf
#define pushcli()
#define popcli()
u64 wq_maxworkers = NWORKERS;
...@@ -8,6 +8,18 @@ ...@@ -8,6 +8,18 @@
static wq *wq_; static wq *wq_;
void*
xallocwork(unsigned long nbytes)
{
return kmalloc(nbytes, "xallocwork");
}
void
xfreework(void* ptr, unsigned long nbytes)
{
kmfree(ptr, nbytes);
}
size_t size_t
wq_size(void) wq_size(void)
{ {
......
...@@ -9,48 +9,6 @@ ...@@ -9,48 +9,6 @@
enum { wq_steal_others = 1 }; enum { wq_steal_others = 1 };
#if 0
static wq *wq_;
size_t
wq_size(void)
{
return sizeof(wq);
}
int
wq_push(work *w)
{
return wq_->push(w, mycpuid());
}
int
wq_pushto(work *w, int tcpuid)
{
return wq_->push(w, tcpuid);
}
int
wq_trywork(void)
{
return wq_->trywork();
}
void
wq_dump(void)
{
return wq_->dump();
}
void
initwq(void)
{
wq_ = new wq();
wqarch_init();
}
#endif
// //
// wq // wq
// //
...@@ -106,11 +64,11 @@ wq::push(work *w, int tcpuid) ...@@ -106,11 +64,11 @@ wq::push(work *w, int tcpuid)
{ {
int i; int i;
acquire(&q_[tcpuid].lock); wqlock_acquire(&q_[tcpuid].lock);
i = q_[tcpuid].head; i = q_[tcpuid].head;
if ((i - q_[tcpuid].tail) == NSLOTS) { if ((i - q_[tcpuid].tail) == NSLOTS) {
stat_[tcpuid].full++; stat_[tcpuid].full++;
release(&q_[tcpuid].lock); wqlock_release(&q_[tcpuid].lock);
return -1; return -1;
} }
i = i & (NSLOTS-1); i = i & (NSLOTS-1);
...@@ -119,7 +77,7 @@ wq::push(work *w, int tcpuid) ...@@ -119,7 +77,7 @@ wq::push(work *w, int tcpuid)
q_[tcpuid].head++; q_[tcpuid].head++;
inclen(tcpuid); inclen(tcpuid);
stat_[tcpuid].push++; stat_[tcpuid].push++;
release(&q_[tcpuid].lock); wqlock_release(&q_[tcpuid].lock);
return 0; return 0;
} }
......
#include "types.h" #include "types.h"
#include "user.h" #include "user.h"
#include "uwq.hh" #include "uwq.hh"
#include "wqtypes.hh"
#include "wq.hh" #include "wq.hh"
#include "atomic.hh" #include "atomic.hh"
#include "pthread.h" #include "pthread.h"
#include "elf.hh" #include "elf.hh"
u64 wq_maxworkers = NWORKERS;
static pthread_key_t idkey; static pthread_key_t idkey;
static std::atomic<int> nextid; static std::atomic<int> nextid;
...@@ -29,16 +32,6 @@ initworker(void) ...@@ -29,16 +32,6 @@ initworker(void)
} }
DEFINE_XV6_ADDRNOTE(xnote, XV6_ADDR_ID_WQ, &initworker); DEFINE_XV6_ADDRNOTE(xnote, XV6_ADDR_ID_WQ, &initworker);
static inline void
wqarch_init(void)
{
if (pthread_key_create(&idkey, 0))
die("wqarch_init: pthread_key_create");
int id = nextid++;
pthread_setspecific(idkey, (void*)(u64)id);
}
int int
mycpuid(void) mycpuid(void)
{ {
...@@ -75,9 +68,28 @@ wq_dump(void) ...@@ -75,9 +68,28 @@ wq_dump(void)
return wq_->dump(); return wq_->dump();
} }
void*
xallocwork(unsigned long nbytes)
{
return wqalloc(nbytes);
}
void
xfreework(void* ptr, unsigned long nbytes)
{
wqfree(ptr);
}
void void
initwq(void) initwq(void)
{ {
if (pthread_key_create(&idkey, 0))
die("wqarch_init: pthread_key_create");
int id = nextid++;
pthread_setspecific(idkey, (void*)(u64)id);
wq_ = new wq(); wq_ = new wq();
wqarch_init(); if (wq_ == nullptr)
die("initwq");
} }
...@@ -5,6 +5,11 @@ NCXXFLAGS = -static -g -MD -m64 -O3 -Wall -Werror -DHW_$(HW) \ ...@@ -5,6 +5,11 @@ NCXXFLAGS = -static -g -MD -m64 -O3 -Wall -Werror -DHW_$(HW) \
-iquote . -iquote include \ -iquote . -iquote include \
-include param.h -include include/compiler.h -include param.h -include include/compiler.h
$(O)/user/%.o: user/%.cc
@echo " CXX $@"
$(Q)mkdir -p $(@D)
$(Q)$(CXX) -DLINUX $(NCXXFLAGS) -c -o $@ $<
$(O)/user/%.o: lib/%.cc $(O)/user/%.o: lib/%.cc
@echo " CXX $@" @echo " CXX $@"
$(Q)mkdir -p $(@D) $(Q)mkdir -p $(@D)
...@@ -15,7 +20,7 @@ $(O)/user/%.o: bin/%.cc ...@@ -15,7 +20,7 @@ $(O)/user/%.o: bin/%.cc
$(Q)mkdir -p $(@D) $(Q)mkdir -p $(@D)
$(Q)$(CXX) -DLINUX $(NCXXFLAGS) -c -o $@ $< $(Q)$(CXX) -DLINUX $(NCXXFLAGS) -c -o $@ $<
$(O)/%: $(O)/user/%.o $(O)/user/wq.o $(O)/%: $(O)/user/%.o $(O)/user/wqlib.o $(O)/user/wqlinux.o
@echo " LD $@" @echo " LD $@"
$(Q)mkdir -p $(@D) $(Q)mkdir -p $(@D)
$(Q)$(CXX) -o $@ $^ -lpthread $(Q)$(CXX) -o $@ $^ -lpthread
......
...@@ -19,20 +19,15 @@ public: ...@@ -19,20 +19,15 @@ public:
return *this; return *this;
} }
const char * copy_value() {
char *buf = (char*)malloc(256);
return name(buf, 256);
}
bool end() const { return end_; }
private:
char *name(char *buf, size_t n) const { char *name(char *buf, size_t n) const {
strncpy(buf, ent_->d_name, n-1); strncpy(buf, ent_->d_name, n-1);
buf[n-1] = 0; buf[n-1] = 0;
return buf; return buf;
} }
bool end() const { return end_; }
private:
void refill(void) { void refill(void) {
struct dirent *result; struct dirent *result;
int r = readdir_r(d_, ent_, &result); int r = readdir_r(d_, ent_, &result);
...@@ -46,3 +41,16 @@ private: ...@@ -46,3 +41,16 @@ private:
struct dirent *ent_; struct dirent *ent_;
DIR *d_; DIR *d_;
}; };
static inline const char*
copy_value(dirit &it)
{
char *buf = (char*)malloc(256);
return it.name(buf, 256);
}
static inline void
free_value(dirit &it, const char *name)
{
free((void*)name);
}
#include <stdlib.h>
#include <stdio.h>
#include <pthread.h>
#include "types.h"
#include "wq.hh"
#include "user/util.h"
static __thread int myid_;
static wq *wq_;
u64 wq_maxworkers = NCPU-1;
int
mycpuid(void)
{
return myid_;
}
size_t
wq_size(void)
{
return sizeof(wq);
}
int
wq_push(work *w)
{
return wq_->push(w, mycpuid());
}
int
wq_pushto(work *w, int tcpuid)
{
return wq_->push(w, tcpuid);
}
int
wq_trywork(void)
{
return wq_->trywork();
}
void
wq_dump(void)
{
return wq_->dump();
}
static void*
workerth(void *x)
{
u64 c = (u64)x;
myid_ = c;
setaffinity(c);
while (1)
wq_trywork();
return NULL;
}
void*
xallocwork(unsigned long nbytes)
{
return malloc(nbytes);
}
void
xfreework(void* ptr, unsigned long nbytes)
{
free(ptr);
}
void
initwq(void)
{
wq_ = new wq();
if (wq_ == nullptr)
die("initwq");
pthread_t th;
int r;
myid_ = 0;
setaffinity(0);
for (int i = 1; i < wq_maxworkers+1; i++) {
r = pthread_create(&th, NULL, workerth, (void*)(u64)i);
if (r < 0)
edie("pthread_create");
}
}
#include <pthread.h>
#include <stdlib.h> #include <stdlib.h>
#include <stdio.h> #include <stdio.h>
#include <assert.h>
#include <pthread.h>
#include "user/util.h" #include "types.h"
#include "include/types.h" #include "wqtypes.hh"
#include "include/wq.hh"
static __thread int myid_; int mycpuid(void);
int
mycpuid(void)
{
return myid_;
}
static inline void* static inline void*
allocwq(unsigned long nbytes) allocwq(unsigned long nbytes)
...@@ -53,34 +45,4 @@ rdtsc(void) ...@@ -53,34 +45,4 @@ rdtsc(void)
return ((u64)lo)|(((u64)hi)<<32); return ((u64)lo)|(((u64)hi)<<32);
} }
static void*
workerth(void *x)
{
u64 c = (u64)x;
myid_ = c;
setaffinity(c);
while (1)
wq_trywork();
return NULL;
}
static inline void
wqarch_init(void)
{
pthread_t th;
int r;
myid_ = 0;
setaffinity(0);
for (int i = 1; i < NCPU; i++) {
r = pthread_create(&th, NULL, workerth, (void*)(u64)i);
if (r < 0)
edie("pthread_create");
}
}
#define xprintf printf #define xprintf printf
#define pushcli()
#define popcli()
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论