Commit Diff


commit - f1ea0d2916f842454306bde2e9cdec47f0af9ee4
commit + e84044be84489b6f4f9ce69d0d6eba6cac66a9b6
blob - e1a77773f747ff0102b3c0ff83c904b0e6f69655
blob + 0a93b6b5904154535abc5f804b7c2a92e2232ad6
--- src/cmd/upas/nfs/imap.c
+++ src/cmd/upas/nfs/imap.c
@@ -17,6 +17,7 @@ struct Imap
 	int		autoreconnect;
 	int		ticks;	/* until boom! */
 	char*	server;
+	char*	root;
 	int		mode;
 	int		fd;
 	Biobuf	b;
@@ -90,7 +91,7 @@ static Sx*		zBrdsx(Imap*);
  */
 
 Imap*
-imapconnect(char *server, int mode)
+imapconnect(char *server, int mode, char *root)
 {
 	Imap *z;
 
@@ -100,6 +101,13 @@ imapconnect(char *server, int mode)
 	z = emalloc(sizeof *z);
 	z->server = estrdup(server);
 	z->mode = mode;
+	if(root)
+		if(root[0] != 0 && root[strlen(root)-1] != '/')
+			z->root = smprint("%s/", root);
+		else
+			z->root = root;
+	else
+		z->root = "";
 	z->fd = -1;
 	z->autoreconnect = 0;
 	z->io = ioproc();
@@ -220,7 +228,9 @@ getboxes(Imap *z)
 		boxes[i]->exists = 0;
 		boxes[i]->maxseen = 0;
 	}
-	if(imapcmd(z, nil, "LIST %Z *", "") < 0)
+	if(imapcmd(z, nil, "LIST %Z *", z->root) < 0)
+		return -1;
+	if(z->root != nil && imapcmd(z, nil, "LIST %Z INBOX", "") < 0)
 		return -1;
 	if(z->nextbox && z->nextbox->mark)
 		z->nextbox = nil;
@@ -739,7 +749,8 @@ imapdial(char *server, int mode)
 		fd[1] = dup(p[0], -1);
 		fd[2] = dup(2, -1);
 		tmp = esmprint("%s:993", server);
-		if(threadspawnl(fd, "/usr/sbin/stunnel", "stunnel", "-c", "-r", tmp, nil) < 0){
+		if(threadspawnl(fd, "/usr/sbin/stunnel", "stunnel", "-c", "-r", tmp, nil) < 0
+		    && threadspawnl(fd, "/usr/bin/stunnel", "stunnel", "-c", "-r", tmp, nil) < 0){
 			free(tmp);
 			close(p[0]);
 			close(p[1]);
@@ -1222,22 +1233,32 @@ xlist(Imap *z, Sx *sx)
 		s = gsub(s, "/", "_");
 		s = gsub(s, sx->sx[3]->data, "/");
 	}
+
+	/*
+	 * INBOX is the special imap name for the main mailbox.
+	 * All other mailbox names have the root prefix removed, if applicable.
+	 */
+	inbox = 0;
+	if(cistrcmp(s, "INBOX") == 0){
+		inbox = 1;
+		free(s);
+		s = estrdup("mbox");
+	} else if(z->root && strstr(s, z->root) == s) {
+		t = estrdup(s+strlen(z->root));
+		free(s);
+		s = t;
+	}
 	
 	/* 
 	 * Plan 9 calls the main mailbox mbox.  
 	 * Rename any existing mbox by appending a $.
 	 */
-	inbox = 0;
-	if(strncmp(s, "mbox", 4) == 0 && alldollars(s+4)){
+	if(!inbox && strncmp(s, "mbox", 4) == 0 && alldollars(s+4)){
 		t = emalloc(strlen(s)+2);
 		strcpy(t, s);
 		strcat(t, "$");
 		free(s);
 		s = t;
-	}else if(cistrcmp(s, "INBOX") == 0){
-		inbox = 1;
-		free(s);
-		s = estrdup("mbox");
 	}
 
 	box = boxcreate(s);
blob - c4677a97f8f38990238f8c3160e6a758785c848c
blob + 3f3d2aa63fe749dc891de7df33ed88ae1a051bb8
--- src/cmd/upas/nfs/imap.h
+++ src/cmd/upas/nfs/imap.h
@@ -1,7 +1,7 @@
 typedef struct Imap Imap;
 
 void		imapcheckbox(Imap *z, Box *b);
-Imap*		imapconnect(char *server, int mode);
+Imap*		imapconnect(char *server, int mode, char *root);
 int		imapcopylist(Imap *z, char *nbox, Msg **m, uint nm);
 void		imapfetchraw(Imap *z, Part *p);
 void		imapfetchrawbody(Imap *z, Part *p);
blob - cd644db827bd7065e3294d0932c42697b4d57c3a
blob + 121d97461fdbdc4372473f36e4768a089b5d1840
--- src/cmd/upas/nfs/main.c
+++ src/cmd/upas/nfs/main.c
@@ -22,17 +22,18 @@ Imap *imap;
 void
 usage(void)
 {
-	fprint(2, "usage: mailfs [-DVtx] [-s srvname] server\n");
+	fprint(2, "usage: mailfs [-DVtx] [-s srvname] [-r root] server\n");
 	threadexitsall("usage");
 }
 
 void
 threadmain(int argc, char **argv)
 {
-	char *server, *srvname;
+	char *server, *srvname, *root;
 	int mode;
 
 	srvname = "mail";
+	root = "";
 	mode = Unencrypted;
 	ARGBEGIN{
 	default:
@@ -52,6 +53,9 @@ threadmain(int argc, char **argv)
 	case 'x':
 		mode = Cmd;
 		break;
+	case 'r':
+		root = EARGF(usage());
+		break;
 	}ARGEND
 
 	quotefmtinstall();	
@@ -65,7 +69,7 @@ threadmain(int argc, char **argv)
 	boxinit();
 	fsinit0();
 
-	if((imap = imapconnect(server, mode)) == nil)
+	if((imap = imapconnect(server, mode, root)) == nil)
 		sysfatal("imapconnect: %r");
 	threadpostmountsrv(&fs, srvname, nil, 0);
 }