Browse Source

Plan 9 from Bell Labs 2007-03-30

David du Colombier 17 years ago
parent
commit
340abdc391
5 changed files with 115 additions and 75 deletions
  1. 3 4
      dist/replica/_plan9.db
  2. 2 2
      dist/replica/plan9.db
  3. 2 0
      dist/replica/plan9.log
  4. 31 15
      sys/man/3/fs
  5. 77 54
      sys/src/9/port/devfs.c

+ 3 - 4
dist/replica/_plan9.db

@@ -7068,7 +7068,7 @@ sys/lib/tmac/mmt - 664 sys sys 964454718 40915
 sys/lib/tmac/name.sed - 664 sys sys 944956202 62
 sys/lib/tmac/sendcover - 775 sys sys 944956202 50
 sys/lib/tmac/strings.mm - 664 sys sys 964455723 2146
-sys/lib/tmac/tmac.an - 664 sys sys 1175140359 8441
+sys/lib/tmac/tmac.an - 664 sys sys 1175141775 8441
 sys/lib/tmac/tmac.anhtml - 664 sys sys 984696197 105
 sys/lib/tmac/tmac.antimes - 664 sys sys 964454718 7809
 sys/lib/tmac/tmac.bits - 664 sys sys 944956202 1089
@@ -7589,7 +7589,7 @@ sys/man/3/dup - 664 sys sys 1015024778 1099
 sys/man/3/env - 664 sys sys 1015024778 1409
 sys/man/3/ether - 664 sys sys 984709635 2563
 sys/man/3/floppy - 664 sys sys 954378905 881
-sys/man/3/fs - 664 sys sys 1174450141 2894
+sys/man/3/fs - 664 sys sys 1175145095 3147
 sys/man/3/i82365 - 664 sys sys 954378906 884
 sys/man/3/ip - 664 sys sys 1174771711 22618
 sys/man/3/kbmap - 664 sys sys 1131110122 1732
@@ -8114,7 +8114,7 @@ sys/src/9/port/devcons.c - 664 sys sys 1168304164 23127
 sys/src/9/port/devdraw.c - 664 sys sys 1147023550 44447
 sys/src/9/port/devdup.c - 664 sys sys 1014931172 2332
 sys/src/9/port/devenv.c - 664 sys sys 1169498893 7015
-sys/src/9/port/devfs.c - 664 sys sys 1158979963 10897
+sys/src/9/port/devfs.c - 664 sys sys 1175146085 11517
 sys/src/9/port/devkbmap.c - 664 sys sys 1130763846 3064
 sys/src/9/port/devkprof.c - 664 sys sys 1014931173 3111
 sys/src/9/port/devloopback.c - 664 sys sys 1138458368 14579
@@ -15767,4 +15767,3 @@ usr/glenda/lib/profile - 664 glenda glenda 1105128663 890
 usr/glenda/readme.acme - 664 glenda glenda 1019860628 4753
 usr/glenda/readme.rio - 664 glenda glenda 1019860628 6370
 usr/glenda/tmp - 20000000775 glenda glenda 1018802620 0
-sys/lib/tmac/tmac.an - 664 sys sys 1175141775 8441

+ 2 - 2
dist/replica/plan9.db

@@ -7589,7 +7589,7 @@ sys/man/3/dup - 664 sys sys 1015024778 1099
 sys/man/3/env - 664 sys sys 1015024778 1409
 sys/man/3/ether - 664 sys sys 984709635 2563
 sys/man/3/floppy - 664 sys sys 954378905 881
-sys/man/3/fs - 664 sys sys 1174450141 2894
+sys/man/3/fs - 664 sys sys 1175145095 3147
 sys/man/3/i82365 - 664 sys sys 954378906 884
 sys/man/3/ip - 664 sys sys 1174771711 22618
 sys/man/3/kbmap - 664 sys sys 1131110122 1732
@@ -8114,7 +8114,7 @@ sys/src/9/port/devcons.c - 664 sys sys 1168304164 23127
 sys/src/9/port/devdraw.c - 664 sys sys 1147023550 44447
 sys/src/9/port/devdup.c - 664 sys sys 1014931172 2332
 sys/src/9/port/devenv.c - 664 sys sys 1169498893 7015
-sys/src/9/port/devfs.c - 664 sys sys 1158979963 10897
+sys/src/9/port/devfs.c - 664 sys sys 1175146085 11517
 sys/src/9/port/devkbmap.c - 664 sys sys 1130763846 3064
 sys/src/9/port/devkprof.c - 664 sys sys 1014931173 3111
 sys/src/9/port/devloopback.c - 664 sys sys 1138458368 14579

+ 2 - 0
dist/replica/plan9.log

@@ -48098,3 +48098,5 @@
 1175112005 0 c 386/9loaddebug - 775 sys sys 1175111768 401962
 1175140817 0 c sys/lib/tmac/tmac.an - 664 sys sys 1175140359 8441
 1175142616 0 c sys/lib/tmac/tmac.an - 664 sys sys 1175141775 8441
+1175146216 0 c sys/man/3/fs - 664 sys sys 1175145095 3147
+1175146216 1 c sys/src/9/port/devfs.c - 664 sys sys 1175146085 11517

+ 31 - 15
sys/man/3/fs

@@ -29,12 +29,25 @@ which in turn contains a
 .B ctl
 file and one file per configured device.
 .PP
-The control messages each introduce a new device, here named
+Most control messages each introduce a new device, here named
 .IR new .
 The
 .I file
 arguments are interpreted in the name space of the writer.
 .TP
+.BI cat " new files" \fR...
+The device
+.I new
+corresponds to the catenation of
+.IR files .
+.TP
+.BI inter " new files" \fR...
+The device
+.I new
+corresponds to the block interleaving of
+.IR files ;
+an 8192-byte block size is assumed.
+.TP
 .BI mirror " new files" \fR...
 The device
 .I new
@@ -42,11 +55,13 @@ corresponds to a RAID-1-like mirroring of
 .IR files .
 Writes to
 .BI new
-are handled by sequentially writing to the
+are handled by sequentially writing the same data to the
 .I files
 from right to left (the reverse of
 the order in the control message).
-If any write fails, the write is aborted.
+A failed write causes an eventual error return
+but does not prevent the rest of the writes
+to the other devices of the mirror set.
 Reads from
 .BI new
 are handled by sequentially reading from the
@@ -71,18 +86,10 @@ reaches past the end of
 .I length
 is silently reduced to fit.
 .TP
-.BI inter " new files" \fR...
-The device
-.I new
-corresponds to the block interleaving of
-.IR files ;
-an 8192-byte block size is assumed.
-.TP
-.BI cat " new files" \fR...
-The device
-.I new
-corresponds to the catenation of
-.IR files .
+.B clear
+Discard all
+.I fs
+device definitions.
 .PD
 .LP
 If the variable
@@ -145,6 +152,9 @@ add this to
 fsconfig=/dev/fd0disk
 .EE
 .SH "SEE ALSO"
+.I read
+in
+.IR cat (1),
 .IR dd (1),
 .IR kfs (4),
 .IR fs (8),
@@ -157,3 +167,9 @@ fsconfig=/dev/fd0disk
 Mirrors are RAID-like but not RAID.
 There is no fancy recovery mechanism and
 no automatic initial copying from a master drive to its mirror drives.
+.PP
+Each
+.I write
+system call on
+.B ctl
+may transmit at most one command.

+ 77 - 54
sys/src/9/port/devfs.c

@@ -1,9 +1,8 @@
 /*
  * File system devices.
- * '#k'.
  * Follows device config in Ken's file server.
- * Builds mirrors, device cats, interleaving, and partition of devices out of
- * other (inner) devices.
+ * Builds mirrors, concatenations, interleavings, and partitions
+ * of devices out of other (inner) devices.
  */
 
 #include "u.h"
@@ -20,23 +19,24 @@ enum {
 	Fcat,			/* catenation of others */
 	Finter,			/* interleaving of others */
 	Fpart,			/* part of others */
+	Fclear,			/* start over */
 
 	Blksize	= 8*1024,	/* for Finter only */
-	Maxconf	= 1024,		/* max length for config */
-
-	Ndevs	= 64,
-	Nfsdevs = 2*Ndevs,
 
 	Qtop	= 0,		/* top dir (contains "fs") */
-	Qdir	= 1,		/* actual dir */
-	Qctl	= 2,		/* ctl file */
-	Qfirst	= 3,		/* first fs file */
+	Qdir,			/* actual dir */
+	Qctl,			/* ctl file */
+	Qfirst,			/* first fs file */
+
+	/* tunable parameters */
+	Maxconf	= 4*1024,	/* max length for config */
+	Ndevs	= 32,		/* max. inner devs per command */
+	Nfsdevs = 128,		/* max. created devs, total */
 };
 
 #define	Cfgstr	"fsdev:\n"
 
 typedef struct Fsdev Fsdev;
-
 struct Fsdev
 {
 	int	type;
@@ -49,9 +49,11 @@ struct Fsdev
 	vlong	isize[Ndevs];	/* sizes for inner devices */
 };
 
+extern Dev fsdevtab;		/* forward */
+
 /*
- * Once configured, a fsdev is never removed. The name of those
- * configured is never nil. We have no locks here.
+ * Once configured, a fsdev is never removed.  The name of those
+ * configured is never nil.  We have no locks here.
  */
 static Fsdev	fsdev[Nfsdevs];
 
@@ -64,6 +66,7 @@ static Cmdtab configs[] = {
 	Fcat,	"cat",		0,
 	Finter,	"inter",	0,
 	Fpart,	"part",		5,
+	Fclear,	"clear",	1,	
 };
 
 static char	confstr[Maxconf];
@@ -101,15 +104,15 @@ devalloc(void)
 static void
 setdsize(Fsdev* mp)
 {
-	uchar	buf[128];	/* old DIRLEN plus a little should be plenty */
 	int	i;
+	long	l;
+	uchar	buf[128];	/* old DIRLEN plus a little should be plenty */
 	Chan	*mc;
 	Dir	d;
-	long	l;
 
 	if (mp->type != Fpart){
 		mp->start= 0;
-		mp->size = 0LL;
+		mp->size = 0;
 	}
 	for (i = 0; i < mp->ndevs; i++){
 		mc = mp->idev[i];
@@ -118,7 +121,7 @@ setdsize(Fsdev* mp)
 		mp->isize[i] = d.length;
 		switch(mp->type){
 		case Fmirror:
-			if (mp->size == 0LL || mp->size > d.length)
+			if (mp->size == 0 || mp->size > d.length)
 				mp->size = d.length;
 			break;
 		case Fcat:
@@ -126,7 +129,7 @@ setdsize(Fsdev* mp)
 			break;
 		case Finter:
 			/* truncate to multiple of Blksize */
-			d.length = (d.length & ~(Blksize-1));
+			d.length &= ~(Blksize-1);
 			mp->isize[i] = d.length;
 			mp->size += d.length;
 			break;
@@ -164,22 +167,24 @@ mpshut(Fsdev *mp)
 static void
 mconfig(char* a, long n)	/* "name idev0 idev1" */
 {
-	static	QLock	lck;
+	int	i;
+	vlong	size, start;
+	char	*c, *oldc;
 	Cmdbuf	*cb;
 	Cmdtab	*ct;
 	Fsdev	*mp;
-	int	i;
-	char	*oldc;
-	char	*c;
-	vlong	size, start;
+	static	QLock	lck;
 
 	size = 0;
 	start = 0;
 	if (confstr[0] == 0)
-		seprint(confstr, confstr+sizeof(confstr), Cfgstr);
+		seprint(confstr, confstr + sizeof confstr, Cfgstr);
 	mp = nil;
 	cb = nil;
 	oldc = confstr + strlen(confstr);
+	if (*a == '\0' || *a == '#' || *a == '\n')
+		return;
+
 	qlock(&lck);
 	if (waserror()){
 		*oldc = 0;
@@ -190,32 +195,55 @@ mconfig(char* a, long n)	/* "name idev0 idev1" */
 			free(cb);
 		nexterror();
 	}
+
 	cb = parsecmd(a, n);
 	c = oldc;
 	for (i = 0; i < cb->nf; i++)
-		c = seprint(c, confstr+sizeof(confstr), "%s ", cb->f[i]);
-	*(c-1) = '\n';
+		c = seprint(c, confstr + sizeof confstr, "%s ", cb->f[i]);
+	if (c > confstr)
+		c[-1] = '\n';
 	ct = lookupcmd(cb, configs, nelem(configs));
-	cb->f++;		/* skip command */
+	cb->f++;			/* skip command */
 	cb->nf--;
-	if (ct->index == Fpart){
-		size = strtoll(cb->f[3], nil, 10);
-		cb->nf--;
+	if (cb->nf < 0)			/* nothing to see here, move along */
+		ct->index = -1;
+	switch (ct->index) {
+	case Fpart:
+		if (cb->nf < 4)
+			error("too few fields in fs config");
 		start = strtoll(cb->f[2], nil, 10);
-		cb->nf--;
+		size =  strtoll(cb->f[3], nil, 10);
+		cb->nf -= 2;
+		break;
+	case Fclear:
+		for (mp = fsdev; mp < fsdev + nelem(fsdev); mp++)
+			mpshut(mp);
+		*confstr = '\0';
+		/* FALL THROUGH */
+	case -1:
+		poperror();
+		qunlock(&lck);
+		free(cb);
+		return;
 	}
+	if (cb->nf < 2)
+		error("too few fields in fs config");
+
+	/* reject name if already in use */
 	for (i = 0; i < nelem(fsdev); i++)
 		if (fsdev[i].name != nil && strcmp(fsdev[i].name, cb->f[0])==0)
 			error(Eexist);
+
 	if (cb->nf - 1 > Ndevs)
 		error("too many devices; fix me, increase Ndevs");
 	for (i = 0; i < cb->nf; i++)
 		validname(cb->f[i], (i != 0));
+
 	mp = devalloc();
 	mp->type = ct->index;
 	if (mp->type == Fpart){
-		mp->size = size;
 		mp->start = start;
+		mp->size = size;
 	}
 	kstrdup(&mp->name, cb->f[0]);
 	for (i = 1; i < cb->nf; i++){
@@ -226,21 +254,18 @@ mconfig(char* a, long n)	/* "name idev0 idev1" */
 		mp->ndevs++;
 	}
 	setdsize(mp);
-	poperror();
 	configed = 1;
+
+	poperror();
 	qunlock(&lck);
 	free(cb);
-
 }
 
 static void
 rdconf(void)
 {
-	int	mustrd;
-	char	*s;
-	char	*c;
-	char	*p;
-	char	*e;
+	int mustrd;
+	char *c, *e, *p, *s;
 	Chan *cc;
 	Chan **ccp;
 
@@ -264,13 +289,13 @@ rdconf(void)
 		nexterror();
 	}
 	*ccp = namec(s, Aopen, OREAD, 0);
-	devtab[(*ccp)->type]->read(*ccp, confstr, sizeof(confstr), 0);
+	devtab[(*ccp)->type]->read(*ccp, confstr, sizeof confstr, 0);
 	cclose(*ccp);
 	*ccp = nil;
 	if (strncmp(confstr, Cfgstr, strlen(Cfgstr)) != 0)
 		error("Bad config, first line must be: 'fsdev:\\n'");
 	kstrdup(&c, confstr + strlen(Cfgstr));
-	memset(confstr, 0, sizeof(confstr));
+	memset(confstr, 0, sizeof confstr);
 	for (p = c; p != nil && *p != 0; p = e){
 		e = strchr(p, '\n');
 		if (e == nil)
@@ -334,7 +359,7 @@ static Chan*
 mattach(char *spec)
 {
 	*confstr = 0;
-	return devattach(L'k', spec);
+	return devattach(fsdevtab.dc, spec);
 }
 
 static Walkqid*
@@ -353,7 +378,7 @@ mstat(Chan *c, uchar *db, int n)
 	int	p;
 
 	p = c->qid.path;
-	memset(&d, 0, sizeof(d));
+	memset(&d, 0, sizeof d);
 	switch(p){
 	case Qtop:
 		devdir(c, tqid, "#k", 0, eve, DMDIR|0775, &d);
@@ -432,20 +457,19 @@ static long
 interio(Fsdev *mp, int isread, void *a, long n, vlong off)
 {
 	int	i;
-	Chan*	mc;
-	long	l, wl, wsz;
+	long	boff, res, l, wl, wsz;
 	vlong	woff, blk, mblk;
-	long	boff, res;
+	Chan*	mc;
 
 	blk  = off / Blksize;
 	boff = off % Blksize;
 	wsz  = Blksize - boff;
 	res = n;
 	while(n > 0){
+		mblk = blk / mp->ndevs;
 		i    = blk % mp->ndevs;
 		mc   = mp->idev[i];
-		mblk = blk / mp->ndevs;
-		woff = mblk * Blksize + boff;
+		woff = mblk*Blksize + boff;
 		if (n > wsz)
 			l = wsz;
 		else
@@ -469,10 +493,9 @@ static long
 mread(Chan *c, void *a, long n, vlong off)
 {
 	int	i;
-	Fsdev	*mp;
+	long	l, res;
 	Chan	*mc;
-	long	l;
-	long	res;
+	Fsdev	*mp;
 
 	if (c->qid.type & QTDIR)
 		return devdirread(c, a, n, 0, 0, mgen);
@@ -530,10 +553,10 @@ mread(Chan *c, void *a, long n, vlong off)
 static long
 mwrite(Chan *c, void *a, long n, vlong off)
 {
-	Fsdev	*mp;
-	long	l, res;
 	int	i;
+	long	l, res;
 	Chan	*mc;
+	Fsdev	*mp;
 
 	if (c->qid.type & QTDIR)
 		error(Eperm);
@@ -552,7 +575,7 @@ mwrite(Chan *c, void *a, long n, vlong off)
 	res = n;
 	switch(mp->type){
 	case Fmirror:
-		for (i = mp->ndevs-1; i >=0; i--){
+		for (i = mp->ndevs - 1; i >= 0; i--){
 			mc = mp->idev[i];
 			l = devtab[mc->type]->write(mc, a, n, off);
 			if (l < res)