commit 2e20a5ac9f7945a79961df7807f2dbc12fef7f99
parent 0b3d92b799ddfac0f39c30ce208ae70025e3ea4a
Author: Kris Maglione <jg@suckless.org>
Date: Wed, 28 Nov 2007 18:19:53 -0500
Apparantly, there is a lot of uncommitted cleanup. I've added a
simple file server by Ron Minnich to the examples dir.
Diffstat:
28 files changed, 932 insertions(+), 429 deletions(-)
diff --git a/cmd/Makefile b/cmd/Makefile
@@ -2,8 +2,9 @@ ROOT=..
include ${ROOT}/mk/hdr.mk
include ${ROOT}/mk/ixp.mk
+LDFLAGS += -L${ROOT}/lib -lixp
TARG = ixpc
-OBJ = ixpc
LIB = ${ROOT}/lib/libixp.a
-include ${ROOT}/mk/one.mk
+include ${ROOT}/mk/many.mk
+
diff --git a/cmd/ixpc.c b/cmd/ixpc.c
@@ -8,28 +8,11 @@
#include <string.h>
#include <time.h>
#include <unistd.h>
-#include "ixp.h"
+#include <ixp_local.h>
/* Temporary */
#define fatal(...) ixp_eprint("ixpc: fatal: " __VA_ARGS__); \
-char *argv0;
-#define ARGBEGIN int _argi, _argtmp, _inargv=0; char *_argv; \
- if(!argv0)argv0=ARGF(); _inargv=1; \
- while(argc && argv[0][0] == '-') { \
- _argi=1; _argv=*argv++; argc--; \
- while(_argv[_argi]) switch(_argv[_argi++])
-#define ARGEND }_inargv=0;USED(_argtmp);USED(_argv);USED(_argi)
-#define ARGF() ((_inargv && _argv[_argi]) ? \
- (_argtmp=_argi, _argi=strlen(_argv), _argv+_argtmp) \
- : ((argc > 0) ? (argc--, *argv++) : ((char*)0)))
-#define EARGF(f) ((_inargv && _argv[_argi]) ? \
- (_argtmp=_argi, _argi=strlen(_argv), _argv+_argtmp) \
- : ((argc > 0) ? (argc--, *argv++) : ((f), (char*)0)))
-#define USED(x) if(x){}else
-#define SET(x) ((x)=0)
-#define nil ((void*)0)
-
static IxpClient *client;
static void
@@ -47,7 +30,7 @@ write_data(IxpCFid *fid, char *name) {
void *buf;
uint len;
- buf = ixp_emalloc(fid->iounit);;
+ buf = emalloc(fid->iounit);;
do {
len = read(0, buf, fid->iounit);
if(len >= 0 && ixp_write(fid, buf, len) != len)
@@ -151,7 +134,7 @@ xawrite(int argc, char *argv[]) {
nbuf = 0;
mbuf = 128;
- buf = ixp_emalloc(mbuf);
+ buf = emalloc(mbuf);
while(argc) {
arg = ARGF();
len = strlen(arg);
@@ -222,7 +205,7 @@ xread(int argc, char *argv[]) {
if(fid == nil)
fatal("Can't open file '%s': %s\n", file, ixp_errbuf());
- buf = ixp_emalloc(fid->iounit);
+ buf = emalloc(fid->iounit);
while((count = ixp_read(fid, buf, fid->iounit)) > 0)
write(1, buf, count);
@@ -272,8 +255,8 @@ xls(int argc, char *argv[]) {
nstat = 0;
mstat = 16;
- stat = ixp_emalloc(sizeof(*stat) * mstat);
- buf = ixp_emalloc(fid->iounit);
+ stat = emalloc(sizeof(*stat) * mstat);
+ buf = emalloc(fid->iounit);
while((count = ixp_read(fid, buf, fid->iounit)) > 0) {
m = ixp_message(buf, count, MsgUnpack);
while(m.pos < m.end) {
diff --git a/config.mk b/config.mk
@@ -21,10 +21,11 @@ INCLUDE = ${PREFIX}/include
# Includes and libs
INCPATH = .:${ROOT}/include:${INCLUDE}:/usr/include
LIBS = -L/usr/lib -lc
+MKDEP = cpp -M
# Flags
include ${ROOT}/mk/gcc.mk
-CFLAGS = -g -Wall ${INCS} -DVERSION=\"${VERSION}\"
+CFLAGS = -g ${INCS} -DIXPlint -DVERSION=\"${VERSION}\"
LDFLAGS = -g ${LIBS}
# Compiler
@@ -40,5 +41,4 @@ AR = ar crs
#LDFLAGS = ${LIBS} -R${PREFIX}/lib
#LDFLAGS += -lsocket -lnsl
#CFLAGS += -xtarget=ultra
-FCALL_H_VERSION=.nounion
diff --git a/examples/Makefile b/examples/Makefile
@@ -0,0 +1,10 @@
+ROOT=..
+include ${ROOT}/mk/hdr.mk
+include ${ROOT}/mk/ixp.mk
+
+LDFLAGS += -L${ROOT}/lib -lixp
+TARG = ixpsrv
+LIB = ${ROOT}/lib/libixp.a
+
+include ${ROOT}/mk/many.mk
+
diff --git a/examples/ixpsrv.c b/examples/ixpsrv.c
@@ -0,0 +1,539 @@
+/* Copyright ©2007 Ron Minnich <rminnich at gmail dot com>
+/* Copyright ©2007 Kris Maglione <maglione.k@gmail.com>
+ * See LICENSE file for license details.
+ */
+
+/* This is a simple 9P file server which serves a normal filesystem
+ * hierarchy. While some of the code is from wmii, the server is by
+ * Ron.
+ *
+ * Note: I added an ifdef for Linux vs. BSD for the mount call, so
+ * this compiles on BSD, but it won't actually run. It should,
+ * ideally, have the option of not mounting the FS.
+ * --Kris
+ */
+#include <assert.h>
+#include <dirent.h>
+#include <err.h>
+#include <errno.h>
+#include <fcntl.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <sys/param.h>
+#include <sys/mount.h>
+#include <sys/socket.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <time.h>
+#include <unistd.h>
+
+#include <ixp_local.h>
+
+/* Temporary */
+#define fatal(...) ixp_eprint("ixpsrv: fatal: " __VA_ARGS__)
+#define debug(...) if(debuglevel) fprintf(stderr, "ixpsrv: " __VA_ARGS__)
+
+/* Datatypes: */
+typedef struct FidAux FidAux;
+struct FidAux {
+ DIR *dir;
+ int fd;
+ char name[]; /* c99 */
+};
+
+/* Error messages */
+static char
+ Enoperm[] = "permission denied",
+ Enofile[] = "file not found",
+ Ebadvalue[] = "bad value";
+/* Macros */
+#define QID(t, i) ((vlong)(t))
+
+/* Global Vars */
+static IxpServer server;
+static char *user;
+static int debuglevel = 0;
+
+static void fs_open(Ixp9Req *r);
+static void fs_walk(Ixp9Req *r);
+static void fs_read(Ixp9Req *r);
+static void fs_stat(Ixp9Req *r);
+static void fs_write(Ixp9Req *r);
+static void fs_clunk(Ixp9Req *r);
+static void fs_flush(Ixp9Req *r);
+static void fs_attach(Ixp9Req *r);
+static void fs_create(Ixp9Req *r);
+static void fs_remove(Ixp9Req *r);
+static void fs_freefid(IxpFid *f);
+
+Ixp9Srv p9srv = {
+ .open= fs_open,
+ .walk= fs_walk,
+ .read= fs_read,
+ .stat= fs_stat,
+ .write= fs_write,
+ .clunk= fs_clunk,
+ .flush= fs_flush,
+ .attach=fs_attach,
+ .create=fs_create,
+ .remove=fs_remove,
+ .freefid=fs_freefid
+};
+
+static void
+usage() {
+ fprintf(stderr,
+ "usage: %1$s [-a <address>] {create | read | ls [-ld] | remove | write} <file>\n"
+ " %1$s [-a <address>] xwrite <file> <data>\n"
+ " %1$s -v\n", argv0);
+ exit(1);
+}
+
+
+/* Utility Functions */
+
+static FidAux*
+newfidaux(char *name) {
+ FidAux *f;
+
+ f = ixp_emallocz(sizeof(*f) + strlen(name) + 1);
+ f->fd = -1;
+ strcpy(f->name, name);
+ return f;
+}
+/* is this a dir? */
+/* -1 means it ain't anything .. */
+static int
+isdir(char *path) {
+ struct stat buf;
+
+ if (stat(path, &buf) < 0)
+ return -1;
+
+ return S_ISDIR(buf.st_mode);
+}
+
+/* This should be moved to libixp */
+static void
+write_buf(Ixp9Req *r, char *buf, uint len) {
+
+ if(r->ifcall.offset >= len)
+ return;
+
+ len -= r->ifcall.offset;
+ if(len > r->ifcall.count)
+ len = r->ifcall.count;
+ r->ofcall.data = ixp_emalloc(len);
+ memcpy(r->ofcall.data, buf + r->ifcall.offset, len);
+ r->ofcall.count = len;
+}
+
+
+/* This should be moved to libixp */
+static void
+write_to_buf(Ixp9Req *r, void *buf, uint *len, uint max) {
+ uint offset, count;
+
+// offset = (r->fid->omode&OAPPEND) ? *len : r->ifcall.offset;
+ offset = r->ifcall.offset;
+ if(offset > *len || r->ifcall.count == 0) {
+ r->ofcall.count = 0;
+ return;
+ }
+
+ count = r->ifcall.count;
+ if(max && (count > max - offset))
+ count = max - offset;
+
+ *len = offset + count;
+
+ if(max == 0) {
+ *(void **)buf = ixp_erealloc(*(void **)buf, *len + 1);
+ buf = *(void **)buf;
+ }
+
+ memcpy((uchar*)buf + offset, r->ifcall.data, count);
+ r->ofcall.count = count;
+ ((char *)buf)[offset+count] = '\0';
+}
+
+static void
+dostat(Stat *s, char *name, struct stat *buf) {
+
+ s->type = 0;
+ s->dev = 0;
+ s->qid.type = buf->st_mode&S_IFMT;
+ s->qid.path = buf->st_ino;
+ s->qid.version = 0;
+ s->mode = buf->st_mode & 0777;
+ if (S_ISDIR(buf->st_mode)) {
+ s->mode |= P9_DMDIR;
+ s->qid.type |= QTDIR;
+ }
+ s->atime = buf->st_atime;
+ s->mtime = buf->st_mtime;
+ s->length = buf->st_size;
+ s->name =name;
+ s->uid = user;
+ s->gid = user;
+ s->muid = user;
+}
+
+/* the gnu/linux guys have made a real mess of errno ... don't ask --ron */
+/* I agree. --Kris */
+void
+rerrno(Ixp9Req *r, char *m) {
+/*
+ char errbuf[128];
+ respond(r, strerror_r(errno, errbuf, sizeof(errbuf)));
+ */
+ respond(r, m);
+}
+
+void
+fs_attach(Ixp9Req *r) {
+
+ debug("fs_attach(%p)\n", r);
+
+ r->fid->qid.type = QTDIR;
+ r->fid->qid.path = (uintptr_t)r->fid;
+ r->fid->aux = newfidaux("/");
+ r->ofcall.qid = r->fid->qid;
+ respond(r, nil);
+}
+
+void
+fs_walk(Ixp9Req *r) {
+ struct stat buf;
+ char *name;
+ FidAux *f;
+ int i;
+
+ debug("fs_walk(%p)\n", r);
+
+ f = r->fid->aux;
+ name = malloc(PATH_MAX);
+ strcpy(name, f->name);
+ if (stat(name, &buf) < 0){
+ respond(r, Enofile);
+ return;
+ }
+
+ /* build full path. Stat full path. Done */
+ for(i=0; i < r->ifcall.nwname; i++) {
+ strcat(name, "/");
+ strcat(name, r->ifcall.wname[i]);
+ if (stat(name, &buf) < 0){
+ respond(r, Enofile);
+ free(name);
+ return;
+ }
+ r->ofcall.wqid[i].type = buf.st_mode&S_IFMT;
+ r->ofcall.wqid[i].path = buf.st_ino;
+ }
+
+ r->newfid->aux = newfidaux(name);
+ r->ofcall.nwqid = i;
+ free(name);
+ respond(r, nil);
+}
+
+void
+fs_stat(Ixp9Req *r) {
+ struct stat st;
+ Stat s;
+ IxpMsg m;
+ char *name;
+ uchar *buf;
+ FidAux *f;
+ int size;
+
+ debug("fs_stat(%p)\n", r);
+ debug("fs_stat %s\n", f->name);
+
+ f = r->fid->aux;
+
+ name = f->name;
+ if (stat(name, &st) < 0){
+ respond(r, Enofile);
+ return;
+ }
+
+ dostat(&s, name, &st);
+ r->fid->qid = s.qid;
+ r->ofcall.nstat = size = ixp_sizeof_stat(&s);
+
+ buf = ixp_emallocz(size);
+
+ m = ixp_message(buf, size, MsgPack);
+ ixp_pstat(&m, &s);
+
+ r->ofcall.stat = m.data;
+ respond(r, nil);
+}
+
+void
+fs_read(Ixp9Req *r) {
+ FidAux *f;
+ char *buf;
+ int n, offset;
+ int size;
+
+ debug("fs_read(%p)\n", r);
+
+ f = r->fid->aux;
+
+ if (f->dir) {
+ Stat s;
+ IxpMsg m;
+
+ offset = 0;
+ size = r->ifcall.count;
+ buf = ixp_emallocz(size);
+ m = ixp_message((uchar*)buf, size, MsgPack);
+
+ /* note: we don't really handle lots of things well, so do one thing
+ * at a time
+ */
+ /*for(f=f->next; f; f=f->next) */{
+ struct dirent *d;
+ struct stat st;
+ d = readdir(f->dir);
+ if (d) {
+ stat(d->d_name, &st);
+ dostat(&s, d->d_name, &st);
+ n = ixp_sizeof_stat(&s);
+ ixp_pstat(&m, &s);
+ offset += n;
+ } else n = 0;
+ }
+ r->ofcall.count = n;
+ r->ofcall.data = (char*)m.data;
+ respond(r, nil);
+ return;
+ } else {
+ r->ofcall.data = ixp_emallocz(r->ifcall.count);
+ if (! r->ofcall.data) {
+ respond(r, nil);
+ return;
+ }
+ r->ofcall.count = pread(f->fd, r->ofcall.data, r->ifcall.count, r->ifcall.offset);
+ if (r->ofcall.count < 0)
+ rerrno(r, Enoperm);
+ else
+ respond(r, nil);
+ return;
+ }
+
+ /*
+ * This is an assert because this should this should not be called if
+ * the file is not open for reading.
+ */
+ assert(!"Read called on an unreadable file");
+}
+
+void
+fs_write(Ixp9Req *r) {
+ FidAux *f;
+
+ debug("fs_write(%p)\n", r);
+
+ if(r->ifcall.count == 0) {
+ respond(r, nil);
+ return;
+ }
+ f = r->fid->aux;
+ /*
+ * This is an assert because this function should not be called if
+ * the file is not open for writing.
+ */
+ assert(!"Write called on an unwritable file");
+}
+
+void
+fs_open(Ixp9Req *r) {
+ int dir;
+ FidAux *f;
+
+ debug("fs_open(%p)\n", r);
+
+ f = r->fid->aux;
+ dir = isdir(f->name);
+ /* fucking stupid linux -- open dir is a DIR */
+
+ if (dir) {
+ f->dir = opendir(f->name);
+ if (! f->dir){
+ rerrno(r, Enoperm);
+ return;
+ }
+ } else {
+ f->fd = open(f->name, O_RDONLY);
+ if (f->fd < 0){
+ rerrno(r, Enoperm);
+ return;
+ }
+ }
+ respond(r, nil);
+}
+
+
+void
+fs_create(Ixp9Req *r) {
+ debug("fs_create(%p)\n", r);
+ respond(r, Enoperm);
+}
+
+void
+fs_remove(Ixp9Req *r) {
+ debug("fs_remove(%p)\n", r);
+ respond(r, Enoperm);
+
+}
+
+void
+fs_clunk(Ixp9Req *r) {
+ int dir;
+ FidAux *f;
+
+ debug("fs_clunk(%p)\n", f);
+
+ f = r->fid->aux;
+ dir = isdir(f->name);
+ if (dir) {
+ (void) closedir(f->dir);
+ f->dir = NULL;
+ } else {
+ (void) close(f->fd);
+ f->fd = -1;
+ }
+
+ respond(r, nil);
+}
+
+void
+fs_flush(Ixp9Req *r) {
+ debug("fs_flush(%p)\n", r);
+ respond(r, nil);
+}
+
+void
+fs_freefid(Fid *f) {
+ debug("fs_freefid(%p)\n", f);
+ free(f->aux);
+}
+
+// mount -t 9p 127.1 /tmp/cache -o port=20006,noextend
+/* Yuck. */
+#if defined(__linux__)
+# define MF(n) MS_##n
+# define mymount(src, dest, flags, opts) mount(src, dest, "9p", flags, opts)
+#elif defined(__FreeBSD__) || defined(__OpenBSD__)
+# define MF(n) MNT_##n
+# define mymount(src, dest, flags, opts) mount("9p", dest, flags, src)
+#endif
+
+static ulong mountflags =
+ MF(NOATIME)
+ | MF(NODEV)
+ /* | MF(NODIRATIME) */
+ | MF(NOEXEC)
+ | MF(NOSUID)
+ | MF(RDONLY);
+
+int
+getaddr(char *mountaddr, char **ip, char **port) {
+ char *cp;
+
+ if (!mountaddr)
+ mountaddr = getenv("XCPU_PARENT");
+ if (!mountaddr)
+ return -1;
+
+ cp = mountaddr;
+ if (strcmp(cp, "tcp!"))
+ cp += 4;
+
+ *ip = cp;
+
+ cp = strstr(cp, "!");
+ if (cp)
+ *port = cp + 1;
+ return strtoul(*port, 0, 0);
+}
+
+int
+main(int argc, char *argv[]) {
+ int fd;
+ int ret;
+ int domount, mountonly;
+ char *mountaddr;
+ char *address;
+ char *msg;
+ IxpConn *acceptor;
+
+ domount = 0;
+ mountonly = 0;
+ address = getenv("IXP_ADDRESS");
+ mountaddr = nil;
+
+ ARGBEGIN{
+ case 'v':
+ printf("%s-" VERSION ", ©2007 Ron Minnich\n", argv0);
+ exit(0);
+ case 'a':
+ address = EARGF(usage());
+ break;
+ case 'd':
+ debuglevel++;
+ break;
+ case 'm':
+ domount++;
+ break;
+ case 'M':
+ mountonly++;
+ break;
+ default:
+ usage();
+ }ARGEND;
+
+ if(!address)
+ fatal("$IXP_ADDRESS not set\n");
+
+ fd = ixp_announce(address);
+ if(fd < 0)
+ fatal("%s\n", errstr);
+
+ /* set up a fake client so we can grap connects. */
+ acceptor = ixp_listen(&server, fd, &p9srv, serve_9pcon, NULL);
+
+ /* we might need to mount ourselves. The bit of complexity is the need to fork so
+ * we can serve ourselves. We've done the listen so that's ok.
+ */
+ if (domount){
+ int f = fork();
+ if (f < 0)
+ errx(1, "fork!");
+ if (!f){
+ char *addr, *aport;
+ int port;
+ char options[128];
+
+ port = getaddr(mountaddr, &addr, &aport);
+ sprintf(options, "port=%d,noextend", port);
+ if (mymount(addr, "/tmp/cache", mountflags, options) < 0)
+ errx(1, "Mount failed");
+ }
+
+ }
+
+ if (mountonly)
+ exit(0);
+
+ ixp_serverloop(&server);
+ printf("msg %s\n", ixp_errbuf());
+ return ret;
+}
+
diff --git a/include/Makefile b/include/Makefile
@@ -1,5 +1,6 @@
ROOT= ..
include ${ROOT}/mk/hdr.mk
+include ${ROOT}/mk/ixp.mk
HFILES = ixp.h ixp_fcall.h
diff --git a/include/ixp.h b/include/ixp.h
@@ -7,25 +7,40 @@
#include <sys/types.h>
#include <sys/select.h>
+/* Gunk */
#undef uchar
-#define uchar _ixpuchar
#undef ushort
-#define ushort _ixpushort
#undef uint
-#define uint _ixpuint
#undef ulong
-#define ulong _ixpulong
#undef vlong
-#define vlong _ixpvlong
#undef uvlong
+#define uchar _ixpuchar
+#define ushort _ixpushort
+#define uint _ixpuint
+#define ulong _ixpulong
+#define vlong _ixpvlong
#define uvlong _ixpuvlong
+
+#ifdef KENCC
+# define STRUCT(x) struct {x};
+# define UNION(x) union {x};
+#elif defined(__GNUC__) && !defined(IXPlint)
+# define STRUCT(x) __extension__ struct {x};
+# define UNION(x) __extension__ union {x};
+#else
+# define STRUCT(x) x
+# define UNION(x) x
+#endif
+/* End Gunk */
+
typedef unsigned char uchar;
typedef unsigned short ushort;
typedef unsigned int uint;
typedef unsigned long ulong;
-typedef long long vlong;
typedef unsigned long long uvlong;
+typedef long long vlong;
+
#define IXP_VERSION "9P2000"
#define IXP_NOTAG ((ushort)~0) /* Dummy tag */
#define IXP_NOFID (~0U)
@@ -147,6 +162,7 @@ enum {
# define RStat P9_RStat
# define TWStat P9_TWStat
# define RWStat P9_RWStat
+#
# define OREAD P9_OREAD
# define OWRITE P9_OWRITE
# define ORDWR P9_ORDWR
@@ -159,6 +175,7 @@ enum {
# define OEXCL P9_OEXCL
# define OLOCK P9_OLOCK
# define OAPPEND P9_OAPPEND
+#
# define QTDIR P9_QTDIR
# define QTAPPEND P9_QTAPPEND
# define QTEXCL P9_QTEXCL
@@ -173,6 +190,7 @@ enum {
# define DMMOUNT P9_DMMOUNT
# define DMAUTH P9_DMAUTH
# define DMTMP P9_DMTMP
+#
# define DMSYMLINK P9_DMSYMLINK
# define DMDEVICE P9_DMDEVICE
# define DMNAMEDPIPE P9_DMNAMEDPIPE
@@ -228,36 +246,89 @@ struct IxpRendez {
enum { MsgPack, MsgUnpack, };
struct IxpMsg {
- uchar *data;
- uchar *pos;
- uchar *end;
- uint size;
- uint mode;
+ char *data;
+ char *pos;
+ char *end;
+ uint size;
+ uint mode;
};
struct IxpQid {
- uchar type;
- uint version;
- uvlong path;
+ uchar type;
+ ulong version;
+ uvlong path;
/* internal use only */
- uchar dir_type;
+ uchar dir_type;
};
-#include <ixp_fcall.h>
+/* from fcall(3) in plan9port */
+struct IxpFcall {
+ uchar type;
+ ushort tag;
+ ulong fid;
+
+ UNION (
+ STRUCT ( /* Tversion, Rversion */
+ ulong msize;
+ char *version;
+ )
+ STRUCT ( /* Tflush */
+ ushort oldtag;
+ )
+ STRUCT ( /* Rerror */
+ char *ename;
+ )
+ STRUCT ( /* Ropen, Rcreate */
+ IxpQid qid; /* +Rattach */
+ ulong iounit;
+ )
+ STRUCT ( /* Rauth */
+ IxpQid aqid;
+ )
+ STRUCT ( /* Tauth, Tattach */
+ ulong afid;
+ char *uname;
+ char *aname;
+ )
+ STRUCT ( /* Tcreate */
+ ulong perm;
+ char *name;
+ uchar mode; /* +Topen */
+ )
+ STRUCT ( /* Twalk */
+ ulong newfid;
+ ushort nwname;
+ char *wname[IXP_MAX_WELEM];
+ )
+ STRUCT ( /* Rwalk */
+ ushort nwqid;
+ IxpQid wqid[IXP_MAX_WELEM];
+ )
+ STRUCT (
+ uvlong offset; /* Tread, Twrite */
+ ulong count; /* Tread, Twrite, Rread */
+ char *data; /* Twrite, Rread */
+ )
+ STRUCT ( /* Twstat, Rstat */
+ ushort nstat;
+ uchar *stat;
+ )
+ )
+};
/* stat structure */
struct IxpStat {
- ushort type;
- uint dev;
- IxpQid qid;
- uint mode;
- uint atime;
- uint mtime;
- uvlong length;
- char *name;
- char *uid;
- char *gid;
- char *muid;
+ ushort type;
+ ulong dev;
+ IxpQid qid;
+ ulong mode;
+ ulong atime;
+ ulong mtime;
+ uvlong length;
+ char *name;
+ char *uid;
+ char *gid;
+ char *muid;
};
struct IxpConn {
@@ -273,23 +344,23 @@ struct IxpConn {
};
struct IxpServer {
- IxpConn *conn;
- void (*preselect)(IxpServer*);
- void *aux;
- int running;
- int maxfd;
- fd_set rd;
+ IxpConn *conn;
+ void (*preselect)(IxpServer*);
+ void *aux;
+ int running;
+ int maxfd;
+ fd_set rd;
};
struct IxpRpc {
- IxpClient *mux;
- IxpRpc *next;
- IxpRpc *prev;
- IxpRendez r;
- uint tag;
- IxpFcall *p;
- int waiting;
- int async;
+ IxpClient *mux;
+ IxpRpc *next;
+ IxpRpc *prev;
+ IxpRendez r;
+ uint tag;
+ IxpFcall *p;
+ int waiting;
+ int async;
};
struct IxpClient {
@@ -298,21 +369,21 @@ struct IxpClient {
uint lastfid;
/* Implementation details */
- uint nwait;
- uint mwait;
- uint freetag;
- IxpCFid *freefid;
- IxpMsg rmsg;
- IxpMsg wmsg;
- IxpMutex lk;
- IxpMutex rlock;
- IxpMutex wlock;
- IxpRendez tagrend;
- IxpRpc **wait;
- IxpRpc *muxer;
- IxpRpc sleep;
- int mintag;
- int maxtag;
+ uint nwait;
+ uint mwait;
+ uint freetag;
+ IxpCFid *freefid;
+ IxpMsg rmsg;
+ IxpMsg wmsg;
+ IxpMutex lk;
+ IxpMutex rlock;
+ IxpMutex wlock;
+ IxpRendez tagrend;
+ IxpRpc **wait;
+ IxpRpc *muxer;
+ IxpRpc sleep;
+ int mintag;
+ int maxtag;
};
struct IxpCFid {
@@ -370,36 +441,36 @@ struct Ixp9Srv {
struct IxpThread {
/* RWLock */
- int (*initrwlock)(IxpRWLock*);
- void (*rlock)(IxpRWLock*);
- int (*canrlock)(IxpRWLock*);
- void (*runlock)(IxpRWLock*);
- void (*wlock)(IxpRWLock*);
- int (*canwlock)(IxpRWLock*);
- void (*wunlock)(IxpRWLock*);
- void (*rwdestroy)(IxpRWLock*);
+ int (*initrwlock)(IxpRWLock*);
+ void (*rlock)(IxpRWLock*);
+ int (*canrlock)(IxpRWLock*);
+ void (*runlock)(IxpRWLock*);
+ void (*wlock)(IxpRWLock*);
+ int (*canwlock)(IxpRWLock*);
+ void (*wunlock)(IxpRWLock*);
+ void (*rwdestroy)(IxpRWLock*);
/* Mutex */
- int (*initmutex)(IxpMutex*);
- void (*lock)(IxpMutex*);
- int (*canlock)(IxpMutex*);
- void (*unlock)(IxpMutex*);
- void (*mdestroy)(IxpMutex*);
+ int (*initmutex)(IxpMutex*);
+ void (*lock)(IxpMutex*);
+ int (*canlock)(IxpMutex*);
+ void (*unlock)(IxpMutex*);
+ void (*mdestroy)(IxpMutex*);
/* Rendez */
- int (*initrendez)(IxpRendez*);
- void (*sleep)(IxpRendez*);
- int (*wake)(IxpRendez*);
- int (*wakeall)(IxpRendez*);
- void (*rdestroy)(IxpRendez*);
+ int (*initrendez)(IxpRendez*);
+ void (*sleep)(IxpRendez*);
+ int (*wake)(IxpRendez*);
+ int (*wakeall)(IxpRendez*);
+ void (*rdestroy)(IxpRendez*);
/* Other */
- char *(*errbuf)(void);
- ssize_t (*read)(int, void*, size_t);
- ssize_t (*write)(int, const void*, size_t);
- int (*select)(int, fd_set*, fd_set*, fd_set*, struct timeval*);
+ char *(*errbuf)(void);
+ ssize_t (*read)(int, void*, size_t);
+ ssize_t (*write)(int, const void*, size_t);
+ int (*select)(int, fd_set*, fd_set*, fd_set*, struct timeval*);
};
extern IxpThread *ixp_thread;
-extern int (*ixp_vsnprint)(char*, int, char*, va_list);
-extern char* (*ixp_vsmprint)(char*, va_list);
+extern int (*ixp_vsnprint)(char*, int, const char*, va_list);
+extern char* (*ixp_vsmprint)(const char*, va_list);
/* thread_*.c */
int ixp_taskinit(void);
@@ -407,79 +478,79 @@ int ixp_rubyinit(void);
int ixp_pthread_init(void);
#ifdef VARARGCK
-# pragma varargck argpos ixp_print 2
-# pragma varargck argpos ixp_werrstr 1
-# pragma varargck argpos ixp_eprint 1
+# pragma varargck argpos ixp_print 2
+# pragma varargck argpos ixp_werrstr 1
+# pragma varargck argpos ixp_eprint 1
#endif
/* client.c */
-IxpClient *ixp_mount(char *address);
-IxpClient *ixp_mountfd(int fd);
-void ixp_unmount(IxpClient *c);
-IxpCFid *ixp_create(IxpClient *c, char *name, uint perm, uchar mode);
-IxpCFid *ixp_open(IxpClient *c, char *name, uchar mode);
-int ixp_remove(IxpClient *c, char *path);
-IxpStat *ixp_stat(IxpClient *c, char *path);
-long ixp_read(IxpCFid *f, void *buf, long count);
-long ixp_write(IxpCFid *f, void *buf, long count);
-long ixp_pread(IxpCFid *f, void *buf, long count, vlong offset);
-long ixp_pwrite(IxpCFid *f, void *buf, long count, vlong offset);
-int ixp_close(IxpCFid *f);
-int ixp_print(IxpCFid *f, char *fmt, ...);
-int ixp_vprint(IxpCFid *f, char *fmt, va_list ap);
+IxpClient* ixp_mount(char*);
+IxpClient* ixp_mountfd(int);
+void ixp_unmount(IxpClient*);
+IxpCFid* ixp_create(IxpClient*, char*, uint perm, uchar mode);
+IxpCFid* ixp_open(IxpClient*, char*, uchar);
+int ixp_remove(IxpClient*, char*);
+IxpStat* ixp_stat(IxpClient*, char*);
+long ixp_read(IxpCFid*, void*, long);
+long ixp_write(IxpCFid*, const void*, long);
+long ixp_pread(IxpCFid*, void*, long, vlong);
+long ixp_pwrite(IxpCFid*, const void*, long, vlong);
+int ixp_close(IxpCFid*);
+int ixp_print(IxpCFid*, const char*, ...);
+int ixp_vprint(IxpCFid*, const char*, va_list);
/* convert.c */
-void ixp_pu8(IxpMsg *msg, uchar *val);
-void ixp_pu16(IxpMsg *msg, ushort *val);
-void ixp_pu32(IxpMsg *msg, uint *val);
-void ixp_pu64(IxpMsg *msg, uvlong *val);
-void ixp_pdata(IxpMsg *msg, char **data, uint len);
-void ixp_pstring(IxpMsg *msg, char **s);
-void ixp_pstrings(IxpMsg *msg, ushort *num, char *strings[]);
-void ixp_pqid(IxpMsg *msg, IxpQid *qid);
-void ixp_pqids(IxpMsg *msg, ushort *num, IxpQid qid[]);
-void ixp_pstat(IxpMsg *msg, IxpStat *stat);
+void ixp_pu8(IxpMsg*, uchar*);
+void ixp_pu16(IxpMsg*, ushort*);
+void ixp_pu32(IxpMsg*, ulong*);
+void ixp_pu64(IxpMsg*, uvlong*);
+void ixp_pdata(IxpMsg*, char**, uint);
+void ixp_pstring(IxpMsg*, char**);
+void ixp_pstrings(IxpMsg*, ushort*, char**);
+void ixp_pqid(IxpMsg*, IxpQid*);
+void ixp_pqids(IxpMsg*, ushort*, IxpQid*);
+void ixp_pstat(IxpMsg*, IxpStat*);
/* error.h */
char *ixp_errbuf(void);
void ixp_errstr(char*, int);
void ixp_rerrstr(char*, int);
-void ixp_werrstr(char*, ...);
+void ixp_werrstr(const char*, ...);
/* request.c */
-void respond(Ixp9Req *r, char *error);
-void serve_9pcon(IxpConn *c);
+void respond(Ixp9Req*, const char *err);
+void serve_9pcon(IxpConn*);
/* message.c */
-ushort ixp_sizeof_stat(IxpStat *stat);
-IxpMsg ixp_message(uchar *data, uint length, uint mode);
-void ixp_freestat(IxpStat *s);
-void ixp_freefcall(IxpFcall *fcall);
-uint ixp_msg2fcall(IxpMsg *msg, IxpFcall *fcall);
-uint ixp_fcall2msg(IxpMsg *msg, IxpFcall *fcall);
+ushort ixp_sizeof_stat(IxpStat*);
+IxpMsg ixp_message(uchar*, uint len, uint mode);
+void ixp_freestat(IxpStat*);
+void ixp_freefcall(IxpFcall*);
+uint ixp_msg2fcall(IxpMsg*, IxpFcall*);
+uint ixp_fcall2msg(IxpMsg*, IxpFcall*);
/* server.c */
-IxpConn *ixp_listen(IxpServer *s, int fd, void *aux,
- void (*read)(IxpConn *c),
- void (*close)(IxpConn *c));
-void ixp_hangup(IxpConn *c);
-int ixp_serverloop(IxpServer *s);
-void ixp_server_close(IxpServer *s);
+IxpConn* ixp_listen(IxpServer*, int, void*,
+ void (*read)(IxpConn*),
+ void (*close)(IxpConn*));
+void ixp_hangup(IxpConn*);
+int ixp_serverloop(IxpServer*);
+void ixp_server_close(IxpServer*);
/* socket.c */
-int ixp_dial(char *address);
-int ixp_announce(char *address);
+int ixp_dial(char*);
+int ixp_announce(char*);
/* transport.c */
-uint ixp_sendmsg(int fd, IxpMsg *msg);
-uint ixp_recvmsg(int fd, IxpMsg *msg);
+uint ixp_sendmsg(int, IxpMsg*);
+uint ixp_recvmsg(int, IxpMsg*);
/* util.c */
-void *ixp_emalloc(uint size);
-void *ixp_emallocz(uint size);
-void *ixp_erealloc(void *ptr, uint size);
-char *ixp_estrdup(const char *str);
-void ixp_eprint(const char *fmt, ...);
-uint ixp_tokenize(char **result, uint reslen, char *str, char delim);
-uint ixp_strlcat(char *dst, const char *src, uint siz);
+void* ixp_emalloc(uint);
+void* ixp_emallocz(uint);
+void* ixp_erealloc(void*, uint);
+char* ixp_estrdup(const char*);
+void ixp_eprint(const char*, ...);
+uint ixp_tokenize(char**, uint len, char*, char);
+uint ixp_strlcat(char*, const char*, uint);
diff --git a/include/ixp_local.h b/include/ixp_local.h
@@ -2,6 +2,22 @@
#define IXP_P9_STRUCTS
#include <ixp.h>
+char *argv0;
+#define ARGBEGIN int _argi, _argtmp, _inargv=0; char *_argv; \
+ if(!argv0)argv0=ARGF(); _inargv=1; \
+ while(argc && argv[0][0] == '-') { \
+ _argi=1; _argv=*argv++; argc--; \
+ while(_argv[_argi]) switch(_argv[_argi++])
+#define ARGEND }_inargv=0;USED(_argtmp);USED(_argv);USED(_argi)
+#define ARGF() ((_inargv && _argv[_argi]) ? \
+ (_argtmp=_argi, _argi=strlen(_argv), _argv+_argtmp) \
+ : ((argc > 0) ? (argc--, *argv++) : ((char*)0)))
+#define EARGF(f) ((_inargv && _argv[_argi]) ? \
+ (_argtmp=_argi, _argi=strlen(_argv), _argv+_argtmp) \
+ : ((argc > 0) ? (argc--, *argv++) : ((f), (char*)0)))
+#define USED(x) if(x){}else
+#define SET(x) ((x)=0)
+
#define thread ixp_thread
#define eprint ixp_eprint
@@ -42,17 +58,16 @@ struct Intmap {
#define caninsertkey ixp_caninsertkey
/* intmap.c */
-void initmap(Intmap *m, ulong nhash, void *hash);
-void incref_map(Intmap *m);
-void decref_map(Intmap *m);
-void freemap(Intmap *map, void (*destroy)(void*));
-void execmap(Intmap *map, void (*destroy)(void*));
-void *lookupkey(Intmap *map, ulong id);
-void *insertkey(Intmap *map, ulong id, void *v);
-void *deletekey(Intmap *map, ulong id);
-int caninsertkey(Intmap *map, ulong id, void *v);
+void initmap(Intmap*, ulong, void*);
+void incref_map(Intmap*);
+void decref_map(Intmap*);
+void freemap(Intmap*, void (*destroy)(void*));
+void execmap(Intmap*, void (*destroy)(void*));
+void *lookupkey(Intmap*, ulong);
+void *insertkey(Intmap*, ulong, void*);
+void *deletekey(Intmap*, ulong);
+int caninsertkey(Intmap*, ulong, void*);
#undef nil
#define nil ((void*)0)
-#define USED(v) if(v){}else{}
diff --git a/libixp/Makefile b/libixp/Makefile
@@ -3,8 +3,6 @@ include ${ROOT}/mk/hdr.mk
include ${ROOT}/mk/ixp.mk
TARG = libixp
-FCALL_H = $(ROOT)/include/ixp_fcall.h
-HFILES = $(FCALL_H)
OBJ = client \
convert \
@@ -21,7 +19,3 @@ OBJ = client \
include ${ROOT}/mk/lib.mk
-$(FCALL_H): fcall.h${FCALL_H_VERSION} ${ROOT}/config.mk
- echo HEADER $$($(CLEANNAME) $(BASE)/$(FCALL_H)) from fcall.h${FCALL_H_VERSION}
- cp fcall.h${FCALL_H_VERSION} $(FCALL_H)
-
diff --git a/libixp/client.c b/libixp/client.c
@@ -415,7 +415,7 @@ ixp_pread(IxpCFid *f, void *buf, long count, vlong offset) {
}
static long
-_pwrite(IxpCFid *f, void *buf, long count, vlong offset) {
+_pwrite(IxpCFid *f, const void *buf, long count, vlong offset) {
Fcall fcall;
int n, len;
@@ -425,7 +425,7 @@ _pwrite(IxpCFid *f, void *buf, long count, vlong offset) {
fcall.type = TWrite;
fcall.fid = f->fid;
fcall.offset = f->offset;
- fcall.data = buf + len;
+ fcall.data = (char*)buf + len;
fcall.count = n;
if(dofcall(f->client, &fcall) == 0)
return -1;
@@ -441,7 +441,7 @@ _pwrite(IxpCFid *f, void *buf, long count, vlong offset) {
}
long
-ixp_write(IxpCFid *f, void *buf, long count) {
+ixp_write(IxpCFid *f, const void *buf, long count) {
int n;
thread->lock(&f->iolock);
@@ -453,7 +453,7 @@ ixp_write(IxpCFid *f, void *buf, long count) {
}
long
-ixp_pwrite(IxpCFid *f, void *buf, long count, vlong offset) {
+ixp_pwrite(IxpCFid *f, const void *buf, long count, vlong offset) {
int n;
thread->lock(&f->iolock);
@@ -463,7 +463,7 @@ ixp_pwrite(IxpCFid *f, void *buf, long count, vlong offset) {
}
int
-ixp_vprint(IxpCFid *f, char *fmt, va_list ap) {
+ixp_vprint(IxpCFid *f, const char *fmt, va_list ap) {
char *buf;
int n;
@@ -477,7 +477,7 @@ ixp_vprint(IxpCFid *f, char *fmt, va_list ap) {
}
int
-ixp_print(IxpCFid *f, char *fmt, ...) {
+ixp_print(IxpCFid *f, const char *fmt, ...) {
va_list ap;
int n;
diff --git a/libixp/convert.c b/libixp/convert.c
@@ -14,33 +14,35 @@ enum {
};
void
-ixp_puint(IxpMsg *msg, uint size, uint *val) {
+ixp_puint(IxpMsg *msg, uint size, ulong *val) {
+ uchar *pos;
int v;
if(msg->pos + size <= msg->end) {
+ pos = msg->pos;
switch(msg->mode) {
case MsgPack:
v = *val;
switch(size) {
case SDWord:
- msg->pos[3] = v>>24;
- msg->pos[2] = v>>16;
+ pos[3] = v>>24;
+ pos[2] = v>>16;
case SWord:
- msg->pos[1] = v>>8;
+ pos[1] = v>>8;
case SByte:
- msg->pos[0] = v;
+ pos[0] = v;
break;
}
case MsgUnpack:
v = 0;
switch(size) {
case SDWord:
- v |= msg->pos[3]<<24;
- v |= msg->pos[2]<<16;
+ v |= pos[3]<<24;
+ v |= pos[2]<<16;
case SWord:
- v |= msg->pos[1]<<8;
+ v |= pos[1]<<8;
case SByte:
- v |= msg->pos[0];
+ v |= pos[0];
break;
}
*val = v;
@@ -50,12 +52,12 @@ ixp_puint(IxpMsg *msg, uint size, uint *val) {
}
void
-ixp_pu32(IxpMsg *msg, uint *val) {
+ixp_pu32(IxpMsg *msg, ulong *val) {
ixp_puint(msg, SDWord, val);
}
void
ixp_pu8(IxpMsg *msg, uchar *val) {
- uint v;
+ ulong v;
v = *val;
ixp_puint(msg, SByte, &v);
@@ -63,7 +65,7 @@ ixp_pu8(IxpMsg *msg, uchar *val) {
}
void
ixp_pu16(IxpMsg *msg, ushort *val) {
- uint v;
+ ulong v;
v = *val;
ixp_puint(msg, SWord, &v);
@@ -71,7 +73,7 @@ ixp_pu16(IxpMsg *msg, ushort *val) {
}
void
ixp_pu64(IxpMsg *msg, uvlong *val) {
- uint vl, vb;
+ ulong vl, vb;
vl = (uint)*val;
vb = (uint)(*val>>32);
@@ -101,7 +103,7 @@ ixp_pstring(IxpMsg *msg, char **s) {
void
ixp_pstrings(IxpMsg *msg, ushort *num, char *strings[]) {
- uchar *s;
+ char *s;
uint i, size;
ushort len;
diff --git a/libixp/error.c b/libixp/error.c
@@ -6,12 +6,12 @@
#include "ixp_local.h"
static int
-_vsnprint(char *buf, int n, char *fmt, va_list ap) {
+_vsnprint(char *buf, int n, const char *fmt, va_list ap) {
return vsnprintf(buf, n, fmt, ap);
}
static char*
-_vsmprint(char *fmt, va_list ap) {
+_vsmprint(const char *fmt, va_list ap) {
va_list al;
char *buf = "";
int n;
@@ -26,8 +26,8 @@ _vsmprint(char *fmt, va_list ap) {
return buf;
}
-int (*ixp_vsnprint)(char*, int, char*, va_list) = _vsnprint;
-char* (*ixp_vsmprint)(char*, va_list) = _vsmprint;
+int (*ixp_vsnprint)(char*, int, const char*, va_list) = _vsnprint;
+char* (*ixp_vsmprint)(const char*, va_list) = _vsmprint;
/* Approach to errno handling taken from Plan 9 Port. */
enum {
@@ -62,7 +62,7 @@ rerrstr(char *buf, int n) {
}
void
-werrstr(char *fmt, ...) {
+werrstr(const char *fmt, ...) {
char tmp[IXP_ERRMAX];
va_list ap;
diff --git a/libixp/fcall.h b/libixp/fcall.h
@@ -1,54 +0,0 @@
-/* from fcall(3) in plan9port */
-struct IxpFcall {
- uchar type;
- ushort tag;
- uint fid;
- union {
- struct { /* Tversion, Rversion */
- uint msize;
- char *version;
- };
- struct { /* Tflush */
- ushort oldtag;
- };
- struct { /* Rerror */
- char *ename;
- };
- struct { /* Ropen, Rcreate */
- IxpQid qid; /* +Rattach */
- uint iounit;
- };
- struct { /* Rauth */
- IxpQid aqid;
- };
- struct { /* Tauth, Tattach */
- uint afid;
- char *uname;
- char *aname;
- };
- struct { /* Tcreate */
- uint perm;
- char *name;
- uchar mode; /* +Topen */
- };
- struct { /* Twalk */
- uint newfid;
- ushort nwname;
- char *wname[IXP_MAX_WELEM];
- };
- struct { /* Rwalk */
- ushort nwqid;
- IxpQid wqid[IXP_MAX_WELEM];
- };
- struct { /* Twrite */
- uvlong offset; /* +Tread */
- /* +Rread */
- uint count; /* +Tread */
- char *data;
- };
- struct { /* Twstat, Rstat */
- ushort nstat;
- uchar *stat;
- };
- };
-};
diff --git a/libixp/fcall.h.nounion b/libixp/fcall.h.nounion
@@ -1,53 +0,0 @@
-/* from fcall(3) in plan9port */
-struct IxpFcall {
- uchar type;
- ushort tag;
- uint fid;
-
- /* Tversion, Rversion */
- uint msize;
- char *version;
-
- /* Tflush */
- ushort oldtag;
-
- /* Rerror */
- char *ename;
-
- /* Ropen, Rcreate */
- IxpQid qid; /* +Rattach */
- uint iounit;
-
- /* Rauth */
- IxpQid aqid;
-
- /* Tauth, Tattach */
- uint afid;
- char *uname;
- char *aname;
-
- /* Tcreate */
- uint perm;
- char *name;
- uchar mode; /* +Topen */
-
- /* Twalk */
- uint newfid;
- ushort nwname;
- char *wname[IXP_MAX_WELEM];
-
- /* Rwalk */
- ushort nwqid;
- IxpQid wqid[IXP_MAX_WELEM];
-
- /* Twrite */
- uvlong offset; /* +Tread */
-
- /* +Rread */
- uint count; /* +Tread */
- char *data;
-
- /* Twstat, Rstat */
- ushort nstat;
- uchar *stat;
-};
diff --git a/libixp/ixp_fcall.h b/libixp/ixp_fcall.h
@@ -1,53 +0,0 @@
-/* from fcall(3) in plan9port */
-struct IxpFcall {
- uchar type;
- ushort tag;
- uint fid;
-
- /* Tversion, Rversion */
- uint msize;
- char *version;
-
- /* Tflush */
- ushort oldtag;
-
- /* Rerror */
- char *ename;
-
- /* Ropen, Rcreate */
- IxpQid qid; /* +Rattach */
- uint iounit;
-
- /* Rauth */
- IxpQid aqid;
-
- /* Tauth, Tattach */
- uint afid;
- char *uname;
- char *aname;
-
- /* Tcreate */
- uint perm;
- char *name;
- uchar mode; /* +Topen */
-
- /* Twalk */
- uint newfid;
- ushort nwname;
- char *wname[IXP_MAX_WELEM];
-
- /* Rwalk */
- ushort nwqid;
- IxpQid wqid[IXP_MAX_WELEM];
-
- /* Twrite */
- uvlong offset; /* +Tread */
-
- /* +Rread */
- uint count; /* +Tread */
- char *data;
-
- /* Twstat, Rstat */
- ushort nstat;
- uchar *stat;
-};
diff --git a/libixp/message.c b/libixp/message.c
@@ -169,7 +169,7 @@ ixp_pfcall(IxpMsg *msg, Fcall *fcall) {
uint
ixp_fcall2msg(IxpMsg *msg, Fcall *fcall) {
- uint size;
+ ulong size;
msg->end = msg->data + msg->size;
msg->pos = msg->data + SDWord;
diff --git a/libixp/request.c b/libixp/request.c
@@ -307,7 +307,7 @@ handlereq(Ixp9Req *r) {
}
void
-respond(Ixp9Req *r, char *error) {
+respond(Ixp9Req *r, const char *error) {
Ixp9Conn *pc;
int msize;
@@ -389,7 +389,7 @@ respond(Ixp9Req *r, char *error) {
r->ofcall.type = r->ifcall.type + 1;
else {
r->ofcall.type = RError;
- r->ofcall.ename = error;
+ r->ofcall.ename = (char*)error;
}
deletekey(&pc->tagmap, r->ifcall.tag);;
diff --git a/libixp/socket.c b/libixp/socket.c
@@ -1,5 +1,5 @@
-/* (C)opyright MMIV-MMVI Anselm R. Garbe <garbeam at gmail dot com>
- * Copyright ©2007 Kris Maglione <fbsdaemon@gmail.com>
+/* Copyright ©2007 Kris Maglione <fbsdaemon@gmail.com>
+ * Copyright ©2004-2006 Anselm R. Garbe <garbeam at gmail dot com>
* See LICENSE file for license details.
*/
#include <errno.h>
@@ -47,7 +47,7 @@ static int
sock_unix(char *address, sockaddr_un *sa, socklen_t *salen) {
int fd;
- memset(sa, 0, sizeof(sa));
+ memset(sa, 0, sizeof(*sa));
sa->sun_family = AF_UNIX;
strncpy(sa->sun_path, address, sizeof(sa->sun_path));
diff --git a/libixp/transport.c b/libixp/transport.c
@@ -70,7 +70,7 @@ ixp_sendmsg(int fd, IxpMsg *msg) {
uint
ixp_recvmsg(int fd, IxpMsg *msg) {
enum { SSize = 4 };
- uint msize, size;
+ ulong msize, size;
msg->mode = MsgUnpack;
msg->pos = msg->data;
diff --git a/man/Makefile b/man/Makefile
@@ -1,5 +1,6 @@
ROOT=..
include ${ROOT}/mk/hdr.mk
+include ${ROOT}/mk/ixp.mk
TARG = ixpc.1
diff --git a/mk/gcc.mk b/mk/gcc.mk
@@ -7,7 +7,6 @@ CFLAGS += \
-Wno-switch \
-Wno-comment \
-Wno-sign-compare \
- -Wno-uninitialized \
-Wno-unused-parameter \
-Wimplicit \
-Wreturn-type \
diff --git a/mk/hdr.mk b/mk/hdr.mk
@@ -13,8 +13,8 @@ all:
${LINK} $@ $<
.c.O:
- ${COMPILE} $@ $<
- ${LINK} $@ $<
+ ${COMPILE} ${<:.c=.o} $<
+ ${LINK} $@ ${<:.c=.o}
.awk.O:
echo FILTER ${BASE}$<
diff --git a/mk/ixp.mk b/mk/ixp.mk
@@ -1 +1,4 @@
VERSION = 0.3
+
+${ROOT}/include/ixp.h: ${ROOT}/config.mk
+
diff --git a/test/client.c b/test/client.c
@@ -3,11 +3,18 @@
#include <bio.h>
#include <thread.h>
#include <ixp.h>
-#include <ixp_pthread.h>
extern char *(*_syserrstr)(void);
char *path;
+enum {
+ DATA = 1,
+ THREAD = 2,
+ TRACE = 4,
+ READ = 8,
+};
+int chatty = READ;
+
typedef struct arg arg;
typedef struct arg2 arg2;
struct arg {
@@ -24,126 +31,161 @@ struct arg2 {
int j;
};
+Channel *chan;
+int nproc;
+
+void
+spawn(void(*f)(void*), void *v, int s) {
+ nproc++;
+ proccreate(f, v, s);
+}
+
+void
+_print(Biobuf *b, char *p, char *end, int j, int k) {
+ for(; p < end; p++) {
+ Bputc(b, *p);
+ if(*p == '\n') {
+ Bflush(b);
+ Bprint(b, ":: %d %d: ", j, k);
+ }
+ }
+}
+
void
readfile(IxpCFid *f, int j, int k) {
Biobuf *b;
- char *buf, *p, *end;
+ char *buf;
int n;
- fprint(2, "readfile(%p, %d, %d) iounit: %d\n", f, j, k, f->iounit);
+ if(chatty&TRACE)
+ fprint(2, "readfile(%p, %d, %d) iounit: %d\n", f, j, k, f->iounit);
- b = Bfdopen(1, OWRITE);
- Bprint(b, ":: %d %d: ", j, k);
+ b = Bfdopen(dup(1, -1), OWRITE);
+ if(chatty&DATA)
+ Bprint(b, ":: %d %d: ", j, k);
buf = ixp_emalloc(f->iounit);
while((n = ixp_read(f, buf, f->iounit)) > 0) {
- fprint(2, "+readfile(%p, %d, %d) n=%d\n", f, j, k, n);
- end = buf+n;
- p = buf;
- for(p = buf; p < end; p++) {
- Bputc(b, *p);
- if(*p == '\n') {
- Bflush(b);
- Bprint(b, ":: %d %d: ", j, k);
- }
- }
+ if(chatty&READ)
+ fprint(2, "+readfile(%p, %d, %d) n=%d\n", f, j, k, n);
+ if(chatty&DATA)
+ _print(b, buf, buf+n, j, k);
+ sleep(0);
}
- fprint(2, "-readfile(%p, %d, %d) iounit: %d\n", f, j, k, f->iounit);
- Bputc(b, '\n');
+ if(chatty&TRACE)
+ fprint(2, "-readfile(%p, %d, %d) iounit: %d\n", f, j, k, f->iounit);
+ if(chatty&DATA)
+ Bputc(b, '\n');
Bterm(b);
}
static void
_read(void *p) {
arg *a;
- int i, k;
+ int k;
a = p;
k = a->k;
- print("Start _read: %d\n", a->j, k);
+ if(chatty&THREAD)
+ print("Start _read: %d\n", a->j, k);
qlock(a->r.l);
sendul(a->ch, 0);
rsleep(&a->r);
- print("Wake _read: %d\n", a->j, k);
+ if(chatty&THREAD)
+ print("Wake _read: %d\n", a->j, k);
qunlock(a->r.l);
- for(i = 0; i < 15; i++)
- readfile(a->f, a->j, k);
+ readfile(a->f, a->j, k);
+ sendul(chan, 0);
}
static void
_open(void *p) {
arg2 *a2;
- arg a;
+ arg *a;
+
+ a = malloc(sizeof *a);
a2 = p;
- a.j = a2->j;
- memset(&a.r, 0, sizeof(a.r));
- a.r.l = mallocz(sizeof(QLock), 1);
- a.ch = chancreate(sizeof(ulong), 0);
- print("Start _open: %d\n", a2->j);
+ a->j = a2->j;
+ memset(&a->r, 0, sizeof(a->r));
+ a->r.l = mallocz(sizeof(QLock), 1);
+ a->ch = chancreate(sizeof(ulong), 0);
+
+ if(chatty&THREAD)
+ print("Start _open: %d\n", a2->j);
qlock(a2->r.l);
sendul(a2->ch, 0);
rsleep(&a2->r);
- print("Wake _open: %d\n", a2->j);
+ if(chatty&THREAD)
+ print("Wake _open: %d\n", a2->j);
qunlock(a2->r.l);
- a.f = ixp_open(a2->c, path, OREAD);
- if(a.f == nil)
+ a->f = ixp_open(a2->c, path, OREAD);
+ if(a->f == nil)
sysfatal("can't open %q: %r\n", path);
+ sleep(0);
- for(a.k = 0; a.k < 5; a.k++) {
- proccreate(_read, &a, mainstacksize);
- recvul(a.ch);
+ for(a->k = 0; a->k < 5; a->k++) {
+ spawn(_read, a, mainstacksize);
+ recvul(a->ch);
}
- qlock(a.r.l);
- rwakeupall(&a.r);
- qunlock(a.r.l);
- recvul(chancreate(sizeof(ulong),0));
+ qlock(a->r.l);
+ rwakeupall(&a->r);
+ qunlock(a->r.l);
+
+ sendul(chan, 0);
}
const char *_malloc_options = "A";
void
threadmain(int argc, char *argv[]) {
- arg2 a;
+ arg2 *a;
char *address;
- USED(argc);
- USED(argv);
+ USED(argc, argv);
address = "unix!/tmp/ns.kris.:0/wmii";
address = "tcp!localhost!6663";
path = "/n/local/var/log/messages";
+ a = malloc(sizeof *a);
+ chan = chancreate(sizeof(ulong), 0);
+
quotefmtinstall();
_syserrstr = ixp_errbuf;
if(ixp_pthread_init())
sysfatal("can't init pthread: %r\n");
- a.c = ixp_mount(address);
- if(a.c == nil)
+ a->c = ixp_mount(address);
+ if(a->c == nil)
sysfatal("can't mount: %r\n");
- memset(&a.r, 0, sizeof(a.r));
- a.r.l = mallocz(sizeof(QLock), 1);
- a.ch = chancreate(sizeof(ulong), 0);
- for(a.j = 0; a.j < 5; a.j++) {
- proccreate(_open, &a, mainstacksize);
- recvul(a.ch);
+ memset(&a->r, 0, sizeof(a->r));
+ a->r.l = mallocz(sizeof(QLock), 1);
+ a->ch = chancreate(sizeof(ulong), 0);
+ for(a->j = 0; a->j < 5; a->j++) {
+ spawn(_open, a, mainstacksize);
+ recvul(a->ch);
}
- qlock(a.r.l);
- fprint(2, "qlock()\n");
- rwakeupall(&a.r);
- fprint(2, "wokeup\n");
- qunlock(a.r.l);
- fprint(2, "unlocked\n");
- recvul(chancreate(sizeof(ulong),0));
+ qlock(a->r.l);
+ if(chatty&THREAD)
+ fprint(2, "qlock()\n");
+ rwakeupall(&a->r);
+ if(chatty&THREAD)
+ fprint(2, "wokeup\n");
+ qunlock(a->r.l);
+ if(chatty&THREAD)
+ fprint(2, "unlocked\n");
+
+ while(nproc--)
+ recvul(chan);
}
diff --git a/test/mkfile b/test/mkfile
@@ -2,8 +2,8 @@
default:V: all
-CFLAGS=-I../include -O0
-LDFLAGS=-L../libixp -L../libixp_pthread -lixp -lixp_pthread
+CFLAGS=-I../include
+LDFLAGS=-L../lib -lixp -lixp_pthread
TARG=\
client\
diff --git a/test/o.client b/test/o.client
Binary files differ.
diff --git a/util/compile b/util/compile
@@ -8,6 +8,7 @@ bin="$(echo $0 | sed 's,/[^/]*$,,')"
xtmp=/tmp/cc.$$.$USER.out
echo CC $($bin/cleanname ${BASE}$outfile)
+[ -n "$noisycc" ] && echo $CC -o $outfile $CFLAGS $@
$CC -o $outfile $CFLAGS $@ 2>$xtmp
status=$?
diff --git a/util/link b/util/link
@@ -21,6 +21,7 @@ done
xtmp=/tmp/ld.$$.$USER.out
echo LD "$($bin/cleanname ${BASE}$outfile)"
+[ -n "$noisycc" ] && echo $LD -o $outfile $ofiles $LDFLAGS $args
$LD -o $outfile $ofiles $LDFLAGS $args >$xtmp 2>&1
status=$?