exportfs: fix bugs, error consistency, cleanup
This commit is contained in:
parent
1cd5d74d4d
commit
8f67fae1a0
1 changed files with 66 additions and 70 deletions
|
@ -52,7 +52,7 @@ int encproto = Encnone;
|
||||||
int readonly;
|
int readonly;
|
||||||
|
|
||||||
static void mksecret(char *, uchar *);
|
static void mksecret(char *, uchar *);
|
||||||
static int localread9pmsg(int, void *, uint, ulong *);
|
static int localread9pmsg(int, void *, uint, void *);
|
||||||
static char *anstring = "tcp!*!0";
|
static char *anstring = "tcp!*!0";
|
||||||
|
|
||||||
char *netdir = "", *local = "", *remote = "";
|
char *netdir = "", *local = "", *remote = "";
|
||||||
|
@ -85,12 +85,11 @@ noteconn(int fd)
|
||||||
void
|
void
|
||||||
main(int argc, char **argv)
|
main(int argc, char **argv)
|
||||||
{
|
{
|
||||||
char buf[ERRMAX], ebuf[ERRMAX], *srvfdfile;
|
char buf[ERRMAX], ebuf[ERRMAX], initial[4], *ini, *srvfdfile;
|
||||||
Fsrpc *r;
|
|
||||||
int doauth, n, fd;
|
|
||||||
char *dbfile, *srv, *na, *nsfile, *keyspec;
|
char *dbfile, *srv, *na, *nsfile, *keyspec;
|
||||||
|
int doauth, n, fd;
|
||||||
AuthInfo *ai;
|
AuthInfo *ai;
|
||||||
ulong initial;
|
Fsrpc *r;
|
||||||
|
|
||||||
dbfile = "/tmp/exportdb";
|
dbfile = "/tmp/exportdb";
|
||||||
srv = nil;
|
srv = nil;
|
||||||
|
@ -195,21 +194,21 @@ main(int argc, char **argv)
|
||||||
|
|
||||||
if(srvfdfile){
|
if(srvfdfile){
|
||||||
if((srvfd = open(srvfdfile, ORDWR)) < 0)
|
if((srvfd = open(srvfdfile, ORDWR)) < 0)
|
||||||
sysfatal("open '%s': %r", srvfdfile);
|
fatal("open %s: %r", srvfdfile);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(na){
|
if(na){
|
||||||
if(srv == nil)
|
if(srv == nil)
|
||||||
sysfatal("-B requires -s");
|
fatal("-B requires -s");
|
||||||
|
|
||||||
local = "me";
|
local = "me";
|
||||||
remote = na;
|
remote = na;
|
||||||
if((fd = dial(netmkaddr(na, 0, "importfs"), 0, 0, 0)) < 0)
|
if((fd = dial(netmkaddr(na, 0, "importfs"), 0, 0, 0)) < 0)
|
||||||
sysfatal("can't dial %s: %r", na);
|
fatal("can't dial %s: %r", na);
|
||||||
|
|
||||||
ai = auth_proxy(fd, auth_getkey, "proto=p9any role=client %s", keyspec);
|
ai = auth_proxy(fd, auth_getkey, "proto=p9any role=client %s", keyspec);
|
||||||
if(ai == nil)
|
if(ai == nil)
|
||||||
sysfatal("%r: %s", na);
|
fatal("%r: %s", na);
|
||||||
|
|
||||||
dup(fd, 0);
|
dup(fd, 0);
|
||||||
dup(fd, 1);
|
dup(fd, 1);
|
||||||
|
@ -240,8 +239,6 @@ main(int argc, char **argv)
|
||||||
}
|
}
|
||||||
|
|
||||||
Workq = emallocz(sizeof(Fsrpc)*Nr_workbufs);
|
Workq = emallocz(sizeof(Fsrpc)*Nr_workbufs);
|
||||||
// for(i=0; i<Nr_workbufs; i++)
|
|
||||||
// Workq[i].buf = emallocz(messagesize);
|
|
||||||
fhash = emallocz(sizeof(Fid*)*FHASHSIZE);
|
fhash = emallocz(sizeof(Fid*)*FHASHSIZE);
|
||||||
|
|
||||||
fmtinstall('F', fcallfmt);
|
fmtinstall('F', fcallfmt);
|
||||||
|
@ -285,55 +282,54 @@ main(int argc, char **argv)
|
||||||
if(srv == nil && srvfd == -1 && write(0, "OK", 2) != 2)
|
if(srv == nil && srvfd == -1 && write(0, "OK", 2) != 2)
|
||||||
fatal("open ack write");
|
fatal("open ack write");
|
||||||
|
|
||||||
if (readn(netfd, &initial, sizeof(ulong)) < sizeof(ulong))
|
ini = initial;
|
||||||
fatal("can't read initial string: %r\n");
|
if (readn(netfd, initial, sizeof(initial)) < sizeof(initial))
|
||||||
|
fatal("can't read initial string: %r");
|
||||||
|
|
||||||
if (strncmp((char *)&initial, "impo", sizeof(ulong)) == 0) {
|
if (memcmp(ini, "impo", 4) == 0) {
|
||||||
char buf[128], *p, *args[3];
|
char buf[128], *p, *args[3];
|
||||||
|
|
||||||
/* New import. Read import's parameters... */
|
ini = nil;
|
||||||
initial = 0;
|
|
||||||
|
|
||||||
p = buf;
|
p = buf;
|
||||||
while (p - buf < sizeof buf) {
|
for(;;){
|
||||||
if ((n = read(netfd, p, 1)) < 0)
|
if ((n = read(netfd, p, 1)) < 0)
|
||||||
fatal("can't read impo arguments: %r\n");
|
fatal("can't read impo arguments: %r");
|
||||||
|
|
||||||
if (n == 0)
|
if (n == 0)
|
||||||
fatal("connection closed while reading arguments\n");
|
fatal("connection closed while reading arguments");
|
||||||
|
|
||||||
if (*p == '\n')
|
if (*p == '\n')
|
||||||
*p = '\0';
|
*p = '\0';
|
||||||
if (*p++ == '\0')
|
if (*p++ == '\0')
|
||||||
break;
|
break;
|
||||||
|
if(p >= buf + sizeof(buf))
|
||||||
|
fatal("import parameters too long");
|
||||||
}
|
}
|
||||||
|
|
||||||
if (tokenize(buf, args, nelem(args)) != 2)
|
if (tokenize(buf, args, nelem(args)) != 2)
|
||||||
fatal("impo arguments invalid: impo%s...\n", buf);
|
fatal("impo arguments invalid: impo%s...", buf);
|
||||||
|
|
||||||
if (strcmp(args[0], "aan") == 0)
|
if (strcmp(args[0], "aan") == 0)
|
||||||
filterp = aanfilter;
|
filterp = aanfilter;
|
||||||
else if (strcmp(args[0], "nofilter") != 0)
|
else if (strcmp(args[0], "nofilter") != 0)
|
||||||
fatal("import filter argument unsupported: %s\n", args[0]);
|
fatal("import filter argument unsupported: %s", args[0]);
|
||||||
|
|
||||||
if (strcmp(args[1], "ssl") == 0)
|
if (strcmp(args[1], "ssl") == 0)
|
||||||
encproto = Encssl;
|
encproto = Encssl;
|
||||||
else if (strcmp(args[1], "tls") == 0)
|
else if (strcmp(args[1], "tls") == 0)
|
||||||
encproto = Enctls;
|
encproto = Enctls;
|
||||||
else if (strcmp(args[1], "clear") != 0)
|
else if (strcmp(args[1], "clear") != 0)
|
||||||
fatal("import encryption proto unsupported: %s\n", args[1]);
|
fatal("import encryption proto unsupported: %s", args[1]);
|
||||||
|
|
||||||
if (encproto == Enctls)
|
if (encproto == Enctls)
|
||||||
sysfatal("%s: tls has not yet been implemented", argv[0]);
|
fatal("%s: tls has not yet been implemented", argv[0]);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (encproto != Encnone && ealgs && ai) {
|
if (encproto != Encnone && ealgs && ai) {
|
||||||
uchar key[16];
|
uchar key[16], digest[SHA1dlen];
|
||||||
uchar digest[SHA1dlen];
|
|
||||||
char fromclientsecret[21];
|
char fromclientsecret[21];
|
||||||
char fromserversecret[21];
|
char fromserversecret[21];
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
|
assert(ai->nsecret <= sizeof(key)-4);
|
||||||
memmove(key+4, ai->secret, ai->nsecret);
|
memmove(key+4, ai->secret, ai->nsecret);
|
||||||
|
|
||||||
/* exchange random numbers */
|
/* exchange random numbers */
|
||||||
|
@ -341,13 +337,13 @@ main(int argc, char **argv)
|
||||||
for(i = 0; i < 4; i++)
|
for(i = 0; i < 4; i++)
|
||||||
key[i+12] = rand();
|
key[i+12] = rand();
|
||||||
|
|
||||||
if (initial)
|
if (ini)
|
||||||
fatal("Protocol botch: old import\n");
|
fatal("Protocol botch: old import");
|
||||||
if(readn(netfd, key, 4) != 4)
|
if(readn(netfd, key, 4) != 4)
|
||||||
fatal("can't read key part; %r\n");
|
fatal("can't read key part; %r");
|
||||||
|
|
||||||
if(write(netfd, key+12, 4) != 4)
|
if(write(netfd, key+12, 4) != 4)
|
||||||
fatal("can't write key part; %r\n");
|
fatal("can't write key part; %r");
|
||||||
|
|
||||||
/* scramble into two secrets */
|
/* scramble into two secrets */
|
||||||
sha1(key, sizeof(key), digest, nil);
|
sha1(key, sizeof(key), digest, nil);
|
||||||
|
@ -364,18 +360,21 @@ main(int argc, char **argv)
|
||||||
break;
|
break;
|
||||||
case Enctls:
|
case Enctls:
|
||||||
default:
|
default:
|
||||||
fatal("Unsupported encryption protocol\n");
|
fatal("Unsupported encryption protocol");
|
||||||
}
|
}
|
||||||
|
|
||||||
if(netfd < 0)
|
if(netfd < 0)
|
||||||
fatal("can't establish ssl connection: %r");
|
fatal("can't establish ssl connection: %r");
|
||||||
}
|
}
|
||||||
else if (filterp) {
|
else if (filterp) {
|
||||||
if (initial)
|
if (ini)
|
||||||
fatal("Protocol botch: don't know how to deal with this\n");
|
fatal("Protocol botch: don't know how to deal with this");
|
||||||
netfd = filter(netfd, filterp);
|
netfd = filter(netfd, filterp);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(ai)
|
||||||
|
auth_freeAI(ai);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Start serving file requests from the network
|
* Start serving file requests from the network
|
||||||
*/
|
*/
|
||||||
|
@ -384,15 +383,15 @@ main(int argc, char **argv)
|
||||||
if(r == 0)
|
if(r == 0)
|
||||||
fatal("Out of service buffers");
|
fatal("Out of service buffers");
|
||||||
|
|
||||||
n = localread9pmsg(netfd, r->buf, messagesize, &initial);
|
n = localread9pmsg(netfd, r->buf, messagesize, ini);
|
||||||
if(n <= 0)
|
if(n <= 0)
|
||||||
fatal(nil);
|
fatal(nil);
|
||||||
|
|
||||||
if(convM2S(r->buf, n, &r->work) == 0)
|
if(convM2S(r->buf, n, &r->work) == 0)
|
||||||
fatal("convM2S format error");
|
fatal("convM2S format error");
|
||||||
|
|
||||||
DEBUG(DFD, "%F\n", &r->work);
|
DEBUG(DFD, "%F\n", &r->work);
|
||||||
(fcalls[r->work.type])(r);
|
(fcalls[r->work.type])(r);
|
||||||
|
ini = nil;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -402,7 +401,7 @@ main(int argc, char **argv)
|
||||||
* cpu relies on this (which needs to be fixed!) -- pb.
|
* cpu relies on this (which needs to be fixed!) -- pb.
|
||||||
*/
|
*/
|
||||||
static int
|
static int
|
||||||
localread9pmsg(int fd, void *abuf, uint n, ulong *initial)
|
localread9pmsg(int fd, void *abuf, uint n, void *ini)
|
||||||
{
|
{
|
||||||
int m, len;
|
int m, len;
|
||||||
uchar *buf;
|
uchar *buf;
|
||||||
|
@ -410,11 +409,8 @@ localread9pmsg(int fd, void *abuf, uint n, ulong *initial)
|
||||||
buf = abuf;
|
buf = abuf;
|
||||||
|
|
||||||
/* read count */
|
/* read count */
|
||||||
assert(BIT32SZ == sizeof(ulong));
|
if (ini)
|
||||||
if (*initial) {
|
memcpy(buf, ini, BIT32SZ);
|
||||||
memcpy(buf, initial, BIT32SZ);
|
|
||||||
*initial = 0;
|
|
||||||
}
|
|
||||||
else {
|
else {
|
||||||
m = readn(fd, buf, BIT32SZ);
|
m = readn(fd, buf, BIT32SZ);
|
||||||
if(m != BIT32SZ){
|
if(m != BIT32SZ){
|
||||||
|
@ -456,10 +452,10 @@ reply(Fcall *r, Fcall *t, char *err)
|
||||||
if(data == nil)
|
if(data == nil)
|
||||||
fatal(Enomem);
|
fatal(Enomem);
|
||||||
n = convS2M(t, data, messagesize);
|
n = convS2M(t, data, messagesize);
|
||||||
if(write(netfd, data, n)!=n)
|
if(write(netfd, data, n)!=n){
|
||||||
{syslog(0, "exportfs", "short write: %r");
|
syslog(0, "exportfs", "short write: %r");
|
||||||
fatal("mount write");
|
fatal("mount write");
|
||||||
}
|
}
|
||||||
free(data);
|
free(data);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -857,6 +853,7 @@ emallocz(uint n)
|
||||||
p = mallocz(n, 1);
|
p = mallocz(n, 1);
|
||||||
if(p == nil)
|
if(p == nil)
|
||||||
fatal(Enomem);
|
fatal(Enomem);
|
||||||
|
setmalloctag(p, getcallerpc(&n));
|
||||||
return p;
|
return p;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -868,6 +865,7 @@ estrdup(char *s)
|
||||||
t = strdup(s);
|
t = strdup(s);
|
||||||
if(t == nil)
|
if(t == nil)
|
||||||
fatal(Enomem);
|
fatal(Enomem);
|
||||||
|
setmalloctag(t, getcallerpc(&s));
|
||||||
return t;
|
return t;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -875,53 +873,51 @@ estrdup(char *s)
|
||||||
int
|
int
|
||||||
filter(int fd, char *cmd)
|
filter(int fd, char *cmd)
|
||||||
{
|
{
|
||||||
int p[2], lfd, len, nb, argc;
|
char buf[128], devdir[40], *s, *file, *argv[16];
|
||||||
char newport[128], buf[128], devdir[40], *s, *file, *argv[16];
|
int p[2], lfd, len, argc;
|
||||||
|
|
||||||
/* Get a free port and post it to the client. */
|
/* Get a free port and post it to the client. */
|
||||||
if (announce(anstring, devdir) < 0)
|
if (announce(anstring, devdir) < 0)
|
||||||
sysfatal("filter: Cannot announce %s: %r", anstring);
|
fatal("filter: Cannot announce %s: %r", anstring);
|
||||||
|
|
||||||
snprint(buf, sizeof(buf), "%s/local", devdir);
|
snprint(buf, sizeof(buf), "%s/local", devdir);
|
||||||
buf[sizeof buf - 1] = '\0';
|
|
||||||
if ((lfd = open(buf, OREAD)) < 0)
|
if ((lfd = open(buf, OREAD)) < 0)
|
||||||
sysfatal("filter: Cannot open %s: %r", buf);
|
fatal("filter: Cannot open %s: %r", buf);
|
||||||
if ((len = read(lfd, newport, sizeof newport - 1)) < 0)
|
if ((len = read(lfd, buf, sizeof buf - 1)) < 0)
|
||||||
sysfatal("filter: Cannot read %s: %r", buf);
|
fatal("filter: Cannot read %s: %r", buf);
|
||||||
close(lfd);
|
close(lfd);
|
||||||
newport[len] = '\0';
|
buf[len] = '\0';
|
||||||
|
if ((s = strchr(buf, '\n')) != nil)
|
||||||
if ((s = strchr(newport, '\n')) != nil)
|
|
||||||
*s = '\0';
|
*s = '\0';
|
||||||
|
len = strlen(buf);
|
||||||
|
if (write(fd, buf, len) != len)
|
||||||
|
fatal("filter: cannot write port; %r");
|
||||||
|
|
||||||
if ((nb = write(fd, newport, len)) < 0)
|
snprint(buf, sizeof(buf), "%s", cmd);
|
||||||
sysfatal("getport; cannot write port; %r");
|
argc = tokenize(buf, argv, nelem(argv)-2);
|
||||||
assert(nb == len);
|
|
||||||
|
|
||||||
argc = tokenize(cmd, argv, nelem(argv)-2);
|
|
||||||
if (argc == 0)
|
if (argc == 0)
|
||||||
sysfatal("filter: empty command");
|
fatal("filter: empty command");
|
||||||
argv[argc++] = buf;
|
argv[argc++] = devdir;
|
||||||
argv[argc] = nil;
|
argv[argc] = nil;
|
||||||
file = argv[0];
|
file = argv[0];
|
||||||
if (s = strrchr(argv[0], '/'))
|
if (s = strrchr(argv[0], '/'))
|
||||||
argv[0] = s+1;
|
argv[0] = s+1;
|
||||||
|
|
||||||
if(pipe(p) < 0)
|
if(pipe(p) < 0)
|
||||||
fatal("pipe");
|
fatal("filter: pipe; %r");
|
||||||
|
|
||||||
switch(rfork(RFNOWAIT|RFPROC|RFFDG)) {
|
switch(rfork(RFNOWAIT|RFPROC|RFMEM|RFFDG)) {
|
||||||
case -1:
|
case -1:
|
||||||
fatal("rfork record module");
|
fatal("filter: rfork; %r\n");
|
||||||
case 0:
|
case 0:
|
||||||
if (dup(p[0], 1) < 0)
|
if (dup(p[0], 1) < 0)
|
||||||
fatal("filter: Cannot dup to 1; %r\n");
|
fatal("filter: Cannot dup to 1; %r");
|
||||||
if (dup(p[0], 0) < 0)
|
if (dup(p[0], 0) < 0)
|
||||||
fatal("filter: Cannot dup to 0; %r\n");
|
fatal("filter: Cannot dup to 0; %r");
|
||||||
close(p[0]);
|
close(p[0]);
|
||||||
close(p[1]);
|
close(p[1]);
|
||||||
exec(file, argv);
|
exec(file, argv);
|
||||||
fatal("exec record module");
|
fatal("filter: exec; %r");
|
||||||
default:
|
default:
|
||||||
close(fd);
|
close(fd);
|
||||||
close(p[0]);
|
close(p[0]);
|
||||||
|
|
Loading…
Reference in a new issue