Commit Diff


commit - 0c7c441e9033e523b96b474cdbee6b63410805f9
commit + 00d75e0eaefc3d52a6bb631e4747da2b88e7c393
blob - 9bf483c233d04a093edc3075a4a7aae31214c917
blob + c601ac196cc9f4eafb03376b03e5937a9f1cc8ea
--- src/cmd/acme/mail/dat.h
+++ src/cmd/acme/mail/dat.h
@@ -153,8 +153,8 @@ extern	Window	*wbox;
 extern	Message	mbox;
 extern	Message	replies;
 extern	char		*fsname;
-extern	int		plumbsendfd;
-extern	int		plumbseemailfd;
+extern	CFid		*plumbsendfd;
+extern	CFid		*plumbseemailfd;
 extern	char		*home;
 extern	char		*outgoing;
 extern	char		*mailboxdir;
blob - 0ce7ac972c105798ba7d78abd5583cf7f95a2e7c
blob + 832385980173936dc5ee76170dca0a091e2b9cfc
--- src/cmd/acme/mail/mail.c
+++ src/cmd/acme/mail/mail.c
@@ -2,13 +2,13 @@
 #include <libc.h>
 #include <bio.h>
 #include <thread.h>
+#include <9pclient.h>
 #include <plumb.h>
 #include <ctype.h>
-#include <9pclient.h>
 #include "dat.h"
 
-char	*maildir = "/mail/";			/* mountpoint of mail file system */
-char *mboxname = "INBOX";			/* mailboxdir/mboxname is mail spool file */
+char	*maildir = "Mail/";			/* mountpoint of mail file system */
+char *mboxname = "mbox";			/* mailboxdir/mboxname is mail spool file */
 char	*mailboxdir = nil;				/* nil == /mail/box/$user */
 char *fsname;						/* filesystem for mailboxdir/mboxname is at maildir/fsname */
 char	*user;
@@ -18,10 +18,10 @@ Window	*wbox;
 Message	mbox;
 Message	replies;
 char		*home;
-int		plumbsendfd;
-int		plumbseemailfd;
-int		plumbshowmailfd;
-int		plumbsendmailfd;
+CFid		*plumbsendfd;
+CFid		*plumbseemailfd;
+CFid		*plumbshowmailfd;
+CFid		*plumbsendmailfd;
 Channel	*cplumb;
 Channel	*cplumbshow;
 Channel	*cplumbsend;
@@ -85,9 +85,9 @@ threadmain(int argc, char *argv[])
 	quotefmtinstall();
 
 	/* open these early so we won't miss notification of new mail messages while we read mbox */
-	plumbsendfd = plumbopen("send", OWRITE|OCEXEC);
-	plumbseemailfd = plumbopen("seemail", OREAD|OCEXEC);
-	plumbshowmailfd = plumbopen("showmail", OREAD|OCEXEC);
+	plumbsendfd = plumbopenfid("send", OWRITE|OCEXEC);
+	plumbseemailfd = plumbopenfid("seemail", OREAD|OCEXEC);
+	plumbshowmailfd = plumbopenfid("showmail", OREAD|OCEXEC);
 
 	shortmenu = 0;
 	ARGBEGIN{
@@ -114,7 +114,7 @@ threadmain(int argc, char *argv[])
 	if(mailfs == nil)
 		error("cannot mount mail: %r");
 
-	name = "INBOX";
+	name = "mbox";
 
 	newdir = 1;
 	if(argc > 0){
@@ -159,9 +159,9 @@ threadmain(int argc, char *argv[])
 	if(outgoing == nil)
 		outgoing = estrstrdup(mailboxdir, "/outgoing");
 
-	mbox.ctlfd = fsopen(mailfs, "INBOX/ctl", OWRITE);
+	mbox.ctlfd = fsopen(mailfs, "mbox/ctl", OWRITE);
 	if(mbox.ctlfd == nil)
-		error("can't open %s: %r", "INBOX/ctl");
+		error("can't open %s: %r", "mbox/ctl");
 
 	fsname = estrdup(name);
 	if(newdir && argc > 0){
@@ -216,12 +216,12 @@ threadmain(int argc, char *argv[])
 	wctlfd = -1;
 	cplumb = chancreate(sizeof(Plumbmsg*), 0);
 	cplumbshow = chancreate(sizeof(Plumbmsg*), 0);
-	if(strcmp(name, "INBOX") == 0){
+	if(strcmp(name, "mbox") == 0){
 		/*
 		 * Avoid creating multiple windows to send mail by only accepting
 		 * sendmail plumb messages if we're reading the main mailbox.
 		 */
-		plumbsendmailfd = plumbopen("sendmail", OREAD|OCEXEC);
+		plumbsendmailfd = plumbopenfid("sendmail", OREAD|OCEXEC);
 		cplumbsend = chancreate(sizeof(Plumbmsg*), 0);
 		proccreate(plumbsendproc, nil, STACK);
 		threadcreate(plumbsendthread, nil, STACK);
@@ -241,7 +241,7 @@ plumbproc(void* v)
 
 	threadsetname("plumbproc");
 	for(;;){
-		m = plumbrecv(plumbseemailfd);
+		m = plumbrecvfid(plumbseemailfd);
 		sendp(cplumb, m);
 		if(m == nil)
 			threadexits(nil);
@@ -255,7 +255,7 @@ plumbshowproc(void* v)
 
 	threadsetname("plumbshowproc");
 	for(;;){
-		m = plumbrecv(plumbshowmailfd);
+		m = plumbrecvfid(plumbshowmailfd);
 		sendp(cplumbshow, m);
 		if(m == nil)
 			threadexits(nil);
@@ -269,7 +269,7 @@ plumbsendproc(void* v)
 
 	threadsetname("plumbsendproc");
 	for(;;){
-		m = plumbrecv(plumbsendmailfd);
+		m = plumbrecvfid(plumbsendmailfd);
 		sendp(cplumbsend, m);
 		if(m == nil)
 			threadexits(nil);
@@ -285,8 +285,8 @@ newmesg(char *name, char *digest)
 		return;	/* message is about another mailbox */
 	if(mesglookupfile(&mbox, name, digest) != nil)
 		return;
-	if(strncmp(name, "/mail/", 6) == 0)
-		name += 6;
+	if(strncmp(name, "Mail/", 5) == 0)
+		name += 5;
 	d = fsdirstat(mailfs, name);
 	if(d == nil)
 		return;
@@ -300,10 +300,8 @@ showmesg(char *name, char *digest)
 {
 	char *n;
 	char *mb;
-	
+
 	mb = mbox.name;
-	if(strncmp(mb, "/mail/", 6) == 0)
-		mb += 6;
 	if(strncmp(name, mb, strlen(mb)) != 0)
 		return;	/* message is about another mailbox */
 	n = estrdup(name+strlen(mb));
blob - 29f6bb59773f33d145e7079b63506c2722a57999
blob + d54b7fb296bb9affb4037939b2a7485d3882997b
--- src/cmd/acme/mail/mesg.c
+++ src/cmd/acme/mail/mesg.c
@@ -3,8 +3,8 @@
 #include <bio.h>
 #include <thread.h>
 #include <ctype.h>
-#include <plumb.h>
 #include <9pclient.h>
+#include <plumb.h>
 #include "dat.h"
 
 enum
@@ -200,9 +200,9 @@ isnumeric(char *s)
 CFid*
 mailopen(char *name, int mode)
 {
-	if(strncmp(name, "/mail/", 6) != 0)
+	if(strncmp(name, "Mail/", 5) != 0)
 		return nil;
-	return fsopen(mailfs, name+6, mode);
+	return fsopen(mailfs, name+5, mode);
 }
 
 Dir*
@@ -624,7 +624,7 @@ mesgsave(Message *m, char *s, int save)
 	char *t, *raw, *unixheader, *all;
 
 	if(save){
-		if(fsprint(mbox.ctlfd, "save %q %q", m->name, s) < 0){
+		if(fsprint(mbox.ctlfd, "save %q %q", s, m->name) < 0){
 			fprint(2, "Mail: can't save %s to %s: %r\n", m->name, s);
 			return 0;
 		}
@@ -865,7 +865,7 @@ replytoaddr(Window *w, Message *m, Event *e, char *s)
 				pm->attr->value = estrdup(m->subject);
 			pm->attr->next = nil;
 		}
-		if(plumbsend(plumbsendfd, pm) < 0)
+		if(plumbsendtofid(plumbsendfd, pm) < 0)
 			fprint(2, "error writing plumb message: %r\n");
 		plumbfree(pm);
 	}
@@ -1253,7 +1253,7 @@ plumb(Message *m, char *dir)
 		pm->ndata = -1;
 		pm->data = estrstrdup(dir, "body");
 		pm->data = eappend(pm->data, "", ports[i].suffix);
-		if(plumbsend(plumbsendfd, pm) < 0)
+		if(plumbsendtofid(plumbsendfd, pm) < 0)
 			fprint(2, "error writing plumb message: %r\n");
 		plumbfree(pm);
 	}
blob - 0a7fe0e0aac572924fdc20cbeed018c62147fb1c
blob + d95e1b2195a2bfcdc96ec33597571e90af1e17f4
--- src/cmd/acme/mail/mkfile
+++ src/cmd/acme/mail/mkfile
@@ -1,7 +1,5 @@
 <$PLAN9/src/mkhdr
 
-CC=9c
-
 TARG=Mail
 OFILES=\
 		html.$O\
@@ -12,21 +10,6 @@ OFILES=\
 		win.$O
 
 HFILES=dat.h
-LIB=
 
-BIN=/acme/bin/$objtype
-
-UPDATE=\
-	mkfile\
-	$HFILES\
-	${OFILES:%.$O=%.c}\
-
 <$PLAN9/src/mkone
 
-$O.out: $OFILES
-	$LD -o $target  $LDFLAGS $OFILES
-
-syms:V:
-	8c -a mail.c	>syms
-	8c -aa mesg.c reply.c util.c win.c 	>>syms
-
blob - eecaf26d20168f792e2bd51b1f5328820d81df54
blob + b52dcbbb56458c63591c2aa9ede3920dc3477134
--- src/cmd/faces/facedb.c
+++ src/cmd/faces/facedb.c
@@ -15,6 +15,9 @@ enum	/* number of deleted faces to cache */
 static Facefile	*facefiles;
 static int		nsaved;
 static char	*facedom;
+static char	*libface;
+static char	*homeface;
+static char	*machinelist;
 
 /*
  * Loading the files is slow enough on a dial-up line to be worth this trouble
@@ -148,9 +151,8 @@ readfile(char *s)
 	return strdup(r->data);
 }
 
-
 static char*
-translatedomain(char *dom)
+translatedomain(char *dom, char *list)
 {
 	static char buf[200];
 	char *p, *ep, *q, *nextp, *file;
@@ -160,7 +162,7 @@ translatedomain(char *dom)
 	if(dom == nil || *dom == 0)
 		return nil;
 
-	if((file = readfile(unsharp("#9/face/.machinelist"))) == nil)
+	if(list == nil || (file = readfile(list)) == nil)
 		return dom;
 
 	for(p=file; p; p=nextp) {
@@ -210,26 +212,17 @@ translatedomain(char *dom)
 }
 
 static char*
-tryfindpicture_user(char *dom, char *user, int depth)
+tryfindpicture(char *dom, char *user, char *dir, char *dict)
 {
-	static char buf[200];
-	char *p, *q, *nextp, *file;
-	static char *home;
-
-	if(home == nil)
-		home = getenv("home");
-	if(home == nil)
-		home = getenv("HOME");
-	if(home == nil)
+	static char buf[1024];
+	char *file, *p, *nextp, *q;
+	
+	if((file = readfile(dict)) == nil)
 		return nil;
 
-	sprint(buf, "%s/lib/face/48x48x%d/.dict", home, depth);
-	if((file = readfile(buf)) == nil)
-		return nil;
-
 	snprint(buf, sizeof buf, "%s/%s", dom, user);
 
-	for(p=file; p; p=nextp) {
+	for(p=file; p; p=nextp){
 		if(nextp = strchr(p, '\n'))
 			*nextp++ = '\0';
 
@@ -237,75 +230,114 @@ tryfindpicture_user(char *dom, char *user, int depth)
 			continue;
 		*q++ = 0;
 
-		if(strcmp(buf, p) == 0) {
+		if(strcmp(buf, p) == 0){
 			q += strspn(q, " \t");
-			q = buf+snprint(buf, sizeof buf, "%s/lib/face/48x48x%d/%s", home, depth, q);
+			snprint(buf, sizeof buf, "%s/%s", dir, q);
+			q = buf+strlen(buf);
 			while(q > buf && (q[-1] == ' ' || q[-1] == '\t'))
 				*--q = 0;
 			free(file);
-			return buf;
+			return estrdup(buf);
 		}
 	}
 	free(file);
-	return nil;			
+	return nil;
 }
 
 static char*
-tryfindpicture_global(char *dom, char *user, int depth)
+estrstrdup(char *a, char *b)
 {
-	static char buf[200];
-	char *p, *q, *nextp, *file;
-
-	sprint(buf, "#9/face/48x48x%d/.dict", depth);
-	if((file = readfile(unsharp(buf))) == nil)
-		return nil;
-
-	snprint(buf, sizeof buf, "%s/%s", dom, user);
-
-	for(p=file; p; p=nextp) {
-		if(nextp = strchr(p, '\n'))
-			*nextp++ = '\0';
-
-		if(*p == '#' || (q = strpbrk(p, " \t")) == nil)
-			continue;
-		*q++ = 0;
-
-		if(strcmp(buf, p) == 0) {
-			q += strspn(q, " \t");
-			q = buf+snprint(buf, sizeof buf, "#9/face/48x48x%d/%s", depth, q);
-			while(q > buf && (q[-1] == ' ' || q[-1] == '\t'))
-				*--q = 0;
-			free(file);
-			return unsharp(buf);
-		}
-	}
-	free(file);
-	return nil;			
+	char *t;
+	
+	t = emalloc(strlen(a)+strlen(b)+1);
+	strcpy(t, a);
+	strcat(t, b);
+	return t;
 }
 
 static char*
-tryfindpicture(char *dom, char *user, int depth)
+tryfindfiledir(char *dom, char *user, char *dir)
 {
-	char* result;
+	char *dict, *ndir, *x;
+	int fd;
+	int i, n;
+	Dir *d;
+	
+	/*
+	 * If this directory has a .machinelist, use it.
+	 */
+	x = estrstrdup(dir, "/.machinelist");
+	dom = estrdup(translatedomain(dom, x));
+	free(x);
 
-	if((result = tryfindpicture_user(dom, user, depth)) != nil)
-		return result;
-
-	return tryfindpicture_global(dom, user, depth);
+	/*
+	 * If this directory has a .dict, use it.
+	 */
+	dict = estrstrdup(dir, "/.dict");
+	if(access(dict, AEXIST) >= 0){
+		x = tryfindpicture(dom, user, dir, dict);
+		free(dict);
+		free(dom);
+		return x;
+	}
+	free(dict);
+	
+	/*
+	 * If not, recurse into subdirectories.
+	 * Ignore 48x48xN directories for now.
+	 */
+	if((fd = open(dir, OREAD)) < 0)
+		return nil;
+	while((n = dirread(fd, &d)) > 0){
+		for(i=0; i<n; i++){
+			if((d[i].mode&DMDIR)&& strncmp(d[i].name, "48x48x", 6) != 0){
+				ndir = emalloc(strlen(dir)+1+strlen(d[i].name)+1);
+				strcpy(ndir, dir);
+				strcat(ndir, "/");
+				strcat(ndir, d[i].name);
+				if((x = tryfindfiledir(dom, user, ndir)) != nil){
+					free(ndir);
+					free(d);
+					close(fd);
+					free(dom);
+					return x;
+				}
+			}
+		}
+		free(d);
+	}
+	close(fd);
+	
+	/*
+	 * Handle 48x48xN directories in the right order.
+	 */
+	ndir = estrstrdup(dir, "/48x48x8");
+	for(i=8; i>0; i>>=1){
+		ndir[strlen(ndir)-1] = i+'0';
+		if(access(ndir, AEXIST) >= 0 && (x = tryfindfiledir(dom, user, ndir)) != nil){
+			free(ndir);
+			free(dom);
+			return x;
+		}
+	}
+	free(ndir);
+	free(dom);
+	return nil;
 }
 
 static char*
-tryfindfile(char *dom, char *user, int depth)
+tryfindfile(char *dom, char *user)
 {
-	char *p, *q;
+	char *p;
 
-	for(;;){
-		for(p=dom; p; (p=strchr(p, '.')) && p++)
-			if(q = tryfindpicture(p, user, depth))
-				return q;
-		depth >>= 1;
-		if(depth == 0)
+	while(dom && *dom){
+		if(homeface && (p = tryfindfiledir(dom, user, homeface)) != nil)
+			return p;
+		if((p = tryfindfiledir(dom, user, libface)) != nil)
+			return p;
+		if((dom = strchr(dom, '.')) == nil)
 			break;
+		dom++;
 	}
 	return nil;
 }
@@ -314,34 +346,31 @@ char*
 findfile(Face *f, char *dom, char *user)
 {
 	char *p;
-	int depth;
 
 	if(facedom == nil){
 		facedom = getenv("facedom");
 		if(facedom == nil)
 			facedom = DEFAULT;
 	}
+	if(libface == nil)
+		libface = unsharp("#9/face");
+	if(machinelist == nil)
+		machinelist = estrstrdup(libface, "/.machinelist");
+	if(homeface == nil)
+		homeface = smprint("%s/lib/face", getenv("HOME"));
 
-	dom = translatedomain(dom);
+	dom = translatedomain(dom, machinelist);
 	if(dom == nil)
 		dom = facedom;
 
-	if(screen == nil)
-		depth = 8;
-	else
-		depth = screen->depth;
-
-	if(depth > 8)
-		depth = 8;
-
 	f->unknown = 0;
-	if(p = tryfindfile(dom, user, depth))
+	if((p = tryfindfile(dom, user)) != nil)
 		return p;
 	f->unknown = 1;
-	p = tryfindfile(dom, "unknown", depth);
-	if(p != nil || strcmp(dom, facedom)==0)
+	p = tryfindfile(dom, "unknown");
+	if(p != nil || strcmp(dom, facedom) == 0)
 		return p;
-	return tryfindfile("unknown", "unknown", depth);
+	return tryfindfile("unknown", "unknown");
 }
 
 static
blob - 862188490c00e539bfed5363236d2e6f75979802
blob + c1fbecf57c1c5e180da63bc6d8beeb2f419653fe
--- src/cmd/faces/main.c
+++ src/cmd/faces/main.c
@@ -77,7 +77,7 @@ int	ndown;
 
 char	date[64];
 Face	**faces;
-char	*maildir = "INBOX";
+char	*maildir = "mbox";
 ulong	now;
 
 Point	datep = { 8, 6 };
@@ -108,7 +108,7 @@ init(void)
 	initplumb();
 
 	/* make background color */
-	bgrnd = allocimagemix(display, DPalebluegreen, DWhite);
+	bgrnd = allocimage(display, Rect(0,0,1,1), screen->chan, 1, DWhite);
 	blue = allocimage(display, Rect(0,0,1,1), screen->chan, 1, 0x008888FF);	/* blue-green */
 	left = allocimage(display, leftright, GREY1, 0, DWhite);
 	right = allocimage(display, leftright, GREY1, 0, DWhite);
blob - 58cc4d253fcaad12564b85bfd3bb3bb306f4963e
blob + d7dc5ab72136061b494027723fb947938ac099ab
--- src/cmd/faces/mkfile
+++ src/cmd/faces/mkfile
@@ -22,5 +22,5 @@ UPDATE=\
 <$PLAN9/src/mkone
 CFLAGS=$CFLAGS '-DDEFAULT='$DEFAULT
 
-$O.dblook: dblook.$O facedb.$O util.$O
+dblook: dblook.$O facedb.$O util.$O
 	$LD -o $target $prereq
blob - 1807fd3878f89163797cb52babe0addd2c69c4be
blob + 4d246b5c20f3c9ed2198f0588ff4dd8b169df7f0
--- src/cmd/faces/plumb.c
+++ src/cmd/faces/plumb.c
@@ -45,24 +45,23 @@ attr(Face *f)
 void
 showmail(Face *f)
 {
+	char buf[256];
 	Plumbmsg pm;
 	Plumbattr a;
-	char *s;
 
 	if(showfd<0 || f->str[Sshow]==nil || f->str[Sshow][0]=='\0')
 		return;
-	s = emalloc(strlen("/mail/fs")+1+strlen(f->str[Sshow]));
-	sprint(s,"/mail/fs/%s",f->str[Sshow]);
+	snprint(buf, sizeof buf, "Mail/%s", f->str[Sshow]);
 	pm.src = "faces";
 	pm.dst = "showmail";
-	pm.wdir = "/mail/fs";
+	pm.wdir = "/";
 	pm.type = "text";
 	a.name = "digest";
 	a.value = f->str[Sdigest];
 	a.next = nil;
 	pm.attr = &a;
-	pm.ndata = strlen(s);
-	pm.data = s;
+	pm.ndata = strlen(buf);
+	pm.data = buf;
 	plumbsendtofid(showfd, &pm);
 }
 
@@ -203,12 +202,9 @@ nextface(void)
 			delete(m->data, value(m->attr, "digest", nil));
 		else if(strcmp(t, "new") != 0)
 			fprint(2, "faces: unknown plumb message type %s\n", t);
-		else for(i=0; i<nmaildirs; i++) {	/* XXX */
-			if(strncmp(m->data,"/mail/fs/",strlen("/mail/fs/")) == 0)
-				m->data += strlen("/mail/fs/");
+		else for(i=0; i<nmaildirs; i++)
 			if(strncmp(m->data, maildirs[i], strlen(maildirs[i])) == 0)
 				goto Found;
-		}
 		plumbfree(m);
 		continue;