shithub: riscv

Download patch

ref: 0255b1846b96ad18bada1e6d62b43fe4e7143684
parent: 145345bd862e5cecf0367599c3c4e7156ab99ad5
parent: 27fd88af23b165c1c3c454cb1e1f889d9b74784c
author: cinap_lenrek <cinap_lenrek@centraldogma>
date: Thu Jul 28 10:44:11 EDT 2011

merge

--- a/sys/src/9/pc/pccpuf
+++ b/sys/src/9/pc/pccpuf
@@ -9,6 +9,7 @@
 	proc
 	mnt
 	srv
+	shr
 	dup
 	rtc
 	ssl
--- a/sys/src/9/pc/pcf
+++ b/sys/src/9/pc/pcf
@@ -9,6 +9,7 @@
 	proc
 	mnt
 	srv
+	shr
 	dup
 	rtc
 	ssl
--- a/sys/src/9/port/auth.c
+++ b/sys/src/9/port/auth.c
@@ -134,6 +134,7 @@
 
 	renameuser(eve, buf);
 	srvrenameuser(eve, buf);
+	shrrenameuser(eve, buf);
 	kstrdup(&eve, buf);
 	kstrdup(&up->user, buf);
 	up->basepri = PriNormal;
--- a/sys/src/9/port/devshr.c
+++ b/sys/src/9/port/devshr.c
@@ -640,3 +640,15 @@
 	shrremove,
 	shrwstat,
 };
+
+void
+shrrenameuser(char *old, char *new)
+{
+	Shr *sp;
+
+	qlock(&shrlk);
+	for(sp = shr; sp; sp = sp->link)
+		if(sp->owner!=nil && strcmp(old, sp->owner)==0)
+			kstrdup(&sp->owner, new);
+	qunlock(&shrlk);
+}
\ No newline at end of file
--- a/sys/src/9/port/portfns.h
+++ b/sys/src/9/port/portfns.h
@@ -319,6 +319,7 @@
 void		splxpc(int);
 char*		srvname(Chan*);
 void		srvrenameuser(char*, char*);
+void		shrrenameuser(char*, char*);
 int		swapcount(ulong);
 int		swapfull(void);
 void		swapinit(void);
--- a/sys/src/cmd/nusb/disk/disk.c
+++ b/sys/src/cmd/nusb/disk/disk.c
@@ -24,6 +24,9 @@
 	Qmax = Maxparts,
 };
 
+Dev *dev;
+Ums *ums;
+
 typedef struct Dirtab Dirtab;
 struct Dirtab
 {
@@ -140,19 +143,15 @@
  */
 
 static char*
-ctlstring(Usbfs *fs)
+ctlstring(Umsc *lun)
 {
 	Part *p, *part;
 	Fmt fmt;
-	Umsc *lun;
-	Ums *ums;
 	
-	ums = fs->dev->aux;
-	lun = fs->aux;
 	part = &lun->part[0];
 
 	fmtstrinit(&fmt);
-	fmtprint(&fmt, "dev %s\n", fs->dev->dir);
+	fmtprint(&fmt, "dev %s\n", dev->dir);
 	fmtprint(&fmt, "lun %ld\n", lun - &ums->lun[0]);
 	if(lun->flags & Finqok)
 		fmtprint(&fmt, "inquiry %s\n", lun->inq);
@@ -166,14 +165,12 @@
 }
 
 static int
-ctlparse(Usbfs *fs, char *msg)
+ctlparse(Umsc *lun, char *msg)
 {
 	vlong start, end;
 	char *argv[16];
 	int argc;
-	Umsc *lun;
 	
-	lun = fs->aux;
 	argc = tokenize(msg, argv, nelem(argv));
 
 	if(argc < 1){
@@ -216,7 +213,7 @@
 }
 
 static int
-getmaxlun(Dev *dev)
+getmaxlun(void)
 {
 	uchar max;
 	int r;
@@ -233,12 +230,12 @@
 }
 
 static int
-umsreset(Ums *ums)
+umsreset(void)
 {
 	int r;
 
 	r = Rh2d|Rclass|Riface;
-	if(usbcmd(ums->dev, r, Umsreset, 0, 0, nil, 0) < 0){
+	if(usbcmd(dev, r, Umsreset, 0, 0, nil, 0) < 0){
 		fprint(2, "disk: reset: %r\n");
 		return -1;
 	}
@@ -246,27 +243,27 @@
 }
 
 static int
-umsrecover(Ums *ums)
+umsrecover(void)
 {
-	if(umsreset(ums) < 0)
+	if(umsreset() < 0)
 		return -1;
-	if(unstall(ums->dev, ums->epin, Ein) < 0)
+	if(unstall(dev, ums->epin, Ein) < 0)
 		dprint(2, "disk: unstall epin: %r\n");
 
 	/* do we need this when epin == epout? */
-	if(unstall(ums->dev, ums->epout, Eout) < 0)
+	if(unstall(dev, ums->epout, Eout) < 0)
 		dprint(2, "disk: unstall epout: %r\n");
 	return 0;
 }
 
 static void
-umsfatal(Ums *ums)
+umsfatal(void)
 {
-	int i;
+//	int i;
 
-	devctl(ums->dev, "detach");
-	for(i = 0; i < ums->maxlun; i++)
-		usbfsdel(&ums->lun[i].fs);
+	devctl(dev, "detach");
+//	for(i = 0; i < ums->maxlun; i++)
+//		usbfsdel(&ums->lun[i].fs);
 }
 
 static int
@@ -322,14 +319,14 @@
 }
 
 static int
-umsinit(Ums *ums)
+umsinit(void)
 {
 	uchar i;
 	Umsc *lun;
 	int some;
 
-	umsreset(ums);
-	ums->maxlun = getmaxlun(ums->dev);
+	umsreset();
+	ums->maxlun = getmaxlun();
 	ums->lun = mallocz((ums->maxlun+1) * sizeof(*ums->lun), 1);
 	some = 0;
 	for(i = 0; i <= ums->maxlun; i++){
@@ -364,7 +361,7 @@
 	}
 	if(some == 0){
 		dprint(2, "disk: all luns failed\n");
-		devctl(ums->dev, "detach");
+		devctl(dev, "detach");
 		return -1;
 	}
 	return 0;
@@ -430,7 +427,7 @@
 				fprint(2, "disk: data: %d bytes\n", n);
 		if(n <= 0)
 			if(data->write == 0)
-				unstall(ums->dev, ums->epin, Ein);
+				unstall(dev, ums->epin, Ein);
 	}
 
 	/* read the transfer's status */
@@ -437,7 +434,7 @@
 	n = read(ums->epin->dfd, &csw, CswLen);
 	if(n <= 0){
 		/* n == 0 means "stalled" */
-		unstall(ums->dev, ums->epin, Ein);
+		unstall(dev, ums->epin, Ein);
 		n = read(ums->epin->dfd, &csw, CswLen);
 	}
 
@@ -482,48 +479,61 @@
 Fail:
 	*status = STharderr;
 	if(ums->nerrs++ > 15){
-		fprint(2, "disk: %s: too many errors: device detached\n", ums->dev->dir);
-		umsfatal(ums);
+		fprint(2, "disk: %s: too many errors: device detached\n", dev->dir);
+		umsfatal();
 	}else
-		umsrecover(ums);
+		umsrecover();
 	return -1;
 }
 
-static int
-dwalk(Usbfs *fs, Fid *fid, char *name)
+static void
+dattach(Req *req)
 {
+	req->fid->qid = (Qid) {0, 0, QTDIR};
+	req->ofcall.qid = req->fid->qid;
+	respond(req, nil);
+}
+
+static char *
+dwalk(Fid *fid, char *name, Qid *qid)
+{
 	Umsc *lun;
 	Part *p;
-	
-	lun = fs->aux;
-	
-	if((fid->qid.type & QTDIR) == 0){
-		werrstr("walk in non-directory");
-		return -1;
+
+	if((fid->qid.type & QTDIR) == 0)
+		return "walk in non-directory";
+	if(strcmp(name, "..") == 0){
+		fid->qid = (Qid){0, 0, QTDIR};
+		*qid = fid->qid;
+		return nil;
 	}
-	if(strcmp(name, "..") == 0)
-		return 0;
-	
-	p = lookpart(lun, name);
-	if(p == nil){
-		werrstr(Enotfound);
-		return -1;
+	if(fid->qid.path == 0){
+		for(lun = ums->lun; lun <= ums->lun + ums->maxlun; lun++)
+			if(strcmp(lun->name, name) == 0){
+				fid->qid.path = (lun - ums->lun + 1) << 16;
+				fid->qid.vers = 0;
+				fid->qid.type = QTDIR;
+				*qid = fid->qid;
+				return nil;
+			}
+		return "does not exist";
 	}
-	fid->qid.path = p->id | fs->qid;
+	lun = ums->lun + (fid->qid.path >> 16) - 1;
+	p = lookpart(lun, name);
+	if(p == nil)
+		return "does not exist";
+	fid->qid.path |= p->id;
 	fid->qid.vers = p->vers;
 	fid->qid.type = p->mode >> 24;
-	return 0;
+	*qid = fid->qid;
+	return nil;
 }
-static int
-dstat(Usbfs *fs, Qid qid, Dir *d);
 
 static void
-dostat(Usbfs *fs, int path, Dir *d)
+dostat(Umsc *lun, int path, Dir *d)
 {
-	Umsc *lun;
 	Part *p;
 
-	lun = fs->aux;
 	p = &lun->part[path];
 	d->qid.path = path;
 	d->qid.vers = p->vers;
@@ -530,16 +540,19 @@
 	d->qid.type =p->mode >> 24;
 	d->mode = p->mode;
 	d->length = (vlong) p->length * lun->lbsize;
-	strecpy(d->name, d->name + Namesz - 1, p->name);
+	d->name = strdup(p->name);
+	d->uid = strdup(getuser());
+	d->gid = strdup(d->uid);
+	d->muid = strdup(d->uid);
 }
 
 static int
-dirgen(Usbfs *fs, Qid, int n, Dir *d, void*)
+dirgen(int n, Dir* d, void *aux)
 {
 	Umsc *lun;
 	int i;
 	
-	lun = fs->aux;
+	lun = aux;
 	for(i = Qctl; i < Qmax; i++){
 		if(lun->part[i].inuse == 0)
 			continue;
@@ -548,36 +561,71 @@
 	}
 	if(i == Qmax)
 		return -1;
-	dostat(fs, i, d);
-	d->qid.path |= fs->qid;
+	dostat(lun, i, d);
+	d->qid.path |= (lun - ums->lun) << 16;
 	return 0;
 }
 
 static int
-dstat(Usbfs *fs, Qid qid, Dir *d)
+rootgen(int n, Dir *d, void *)
 {
-	int path;
+	Umsc *lun;
 
-	path = qid.path & ~fs->qid;
-	dostat(fs, path, d);
-	d->qid.path |= fs->qid;
+	if(n > ums->maxlun)
+		return -1;
+	lun = ums->lun + n;
+	d->qid.path = (n + 1) << 16;
+	d->qid.type = QTDIR;
+	d->mode = 0555 | DMDIR;
+	d->name = strdup(lun->name);
+	d->uid = strdup(getuser());
+	d->gid = strdup(d->uid);
+	d->muid = strdup(d->uid);
 	return 0;
 }
 
-static int
-dopen(Usbfs *fs, Fid *fid, int)
+
+static void
+dstat(Req *req)
 {
+	int path;
+	Dir *d;
+	Umsc *lun;
+
+	d = &req->d;
+	d->qid = req->fid->qid;
+	if(req->fid->qid.path == 0){
+		d->name = strdup("");
+		d->mode = 0555 | DMDIR;
+		d->uid = strdup(getuser());
+		d->gid = strdup(d->uid);
+		d->muid = strdup(d->uid);
+	}else{
+		path = req->fid->qid.path & 0xFFFF;
+		lun = ums->lun + (req->fid->qid.path >> 16) - 1;
+		dostat(lun, path, d);
+	}
+	respond(req, nil);
+}
+
+static void
+dopen(Req *req)
+{
 	ulong path;
 	Umsc *lun;
 
-	path = fid->qid.path & ~fs->qid;
-	lun = fs->aux;
+	if(req->ofcall.qid.path == 0){
+		respond(req, nil);
+		return;
+	}
+	path = req->ofcall.qid.path & 0xFFFF;
+	lun = ums->lun + (req->ofcall.qid.path >> 16) - 1;
 	switch(path){
 	case Qraw:
 		lun->phase = Pcmd;
 		break;
 	}
-	return 0;
+	respond(req, nil);
 }
 
 /*
@@ -626,8 +674,8 @@
  * and ask again for the capacity of the media.
  * BUG: How to proceed to avoid confussing dossrv??
  */
-static long
-dread(Usbfs *fs, Fid *fid, void *data, long count, vlong offset)
+static void
+dread(Req *req)
 {
 	long n;
 	ulong path;
@@ -635,34 +683,44 @@
 	char *s;
 	Part *p;
 	Umsc *lun;
-	Ums *ums;
 	Qid q;
+	long count;
+	void *data;
+	vlong offset;
 
-	q = fid->qid;
-	path = fid->qid.path & ~fs->qid;
-	ums = fs->dev->aux;
-	lun = fs->aux;
+	q = req->fid->qid;
+	if(q.path == 0){
+		dirread9p(req, rootgen, nil);
+		respond(req, nil);
+		return;
+	}
+	path = q.path & 0xFFFF;
+	lun = ums->lun + (q.path >> 16) - 1;
+	count = req->ifcall.count;
+	data = req->ofcall.data;
+	offset = req->ifcall.offset;
 
 	qlock(ums);
 	switch(path){
 	case Qdir:
-		count = usbdirread(fs, q, data, count, offset, dirgen, nil);
+		dirread9p(req, dirgen, lun);
+		respond(req, nil);
 		break;
 	case Qctl:
-		s = ctlstring(fs);
-		count = usbreadbuf(data, count, offset, s, strlen(s));
+		s = ctlstring(lun);
+		readstr(req, s);
 		free(s);
+		respond(req, nil);
 		break;
 	case Qraw:
 		if(lun->lbsize <= 0 && umscapacity(lun) < 0){
-			count = -1;
+			respond(req, "phase error");
 			break;
 		}
 		switch(lun->phase){
 		case Pcmd:
-			qunlock(ums);
-			werrstr("phase error");
-			return -1;
+			respond(req, "phase error");
+			break;
 		case Pdata:
 			lun->data.p = data;
 			lun->data.count = count;
@@ -669,13 +727,19 @@
 			lun->data.write = 0;
 			count = umsrequest(lun,&lun->cmd,&lun->data,&lun->status);
 			lun->phase = Pstatus;
-			if(count < 0)
+			if(count < 0){
 				lun->lbsize = 0;  /* medium may have changed */
+				responderror(req);
+			}else{
+				req->ofcall.count = count;
+				respond(req, nil);
+			}
 			break;
 		case Pstatus:
 			n = snprint(buf, sizeof buf, "%11.0ud ", lun->status);
-			count = usbreadbuf(data, count, 0LL, buf, n);
+			readbuf(req, buf, n);
 			lun->phase = Pcmd;
+			respond(req, nil);
 			break;
 		}
 		break;
@@ -683,17 +747,19 @@
 	default:
 		p = &lun->part[path];
 		if(!p->inuse){
-			count = -1;
-			werrstr(Eperm);
+			respond(req, "permission denied");
 			break;
 		}
 		count = setup(lun, p, data, count, offset);
-		if (count <= 0)
+		if (count <= 0){
+			responderror(req);
 			break;
+		}
 		n = SRread(lun, lun->bufp, lun->nb * lun->lbsize);
 		if(n < 0){
 			lun->lbsize = 0;	/* medium may have changed */
-			count = -1;
+			responderror(req);
+			break;
 		} else if (lun->bufp == data)
 			count = n;
 		else{
@@ -706,53 +772,57 @@
 			if(count > 0)
 				memmove(data, lun->bufp + lun->off, count);
 		}
+		req->ofcall.count = count;
+		respond(req, nil);
 		break;
 	}
 	qunlock(ums);
-	return count;
 }
 
-static long
-dwrite(Usbfs *fs, Fid *fid, void *data, long count, vlong offset)
+static void
+dwrite(Req *req)
 {
 	long len, ocount;
 	ulong path;
 	uvlong bno;
-	Ums *ums;
 	Part *p;
 	Umsc *lun;
 	char *s;
+	long count;
+	void *data;
+	vlong offset;
 
-	ums = fs->dev->aux;
-	lun = fs->aux;
-	path = fid->qid.path & ~fs->qid;
+	lun = ums->lun + (req->fid->qid.path >> 16) - 1;
+	path = req->fid->qid.path & 0xFFFF;
+	count = req->ifcall.count;
+	data = req->ifcall.data;
+	offset = req->ifcall.offset;
 
 	qlock(ums);
 	switch(path){
-	case Qdir:
-		count = -1;
-		werrstr(Eperm);
-		break;
 	case Qctl:
 		s = emallocz(count+1, 1);
 		memmove(s, data, count);
 		if(s[count-1] == '\n')
 			s[count-1] = 0;
-		if(ctlparse(fs, s) == -1)
-			count = -1;
+		if(ctlparse(lun, s) == -1)
+			responderror(req);
+		else{
+			req->ofcall.count = count;
+			respond(req, nil);
+		}
 		free(s);
 		break;
 	case Qraw:
 		if(lun->lbsize <= 0 && umscapacity(lun) < 0){
-			count = -1;
+			respond(req, "phase error");
 			break;
 		}
 		switch(lun->phase){
 		case Pcmd:
 			if(count != 6 && count != 10){
-				qunlock(ums);
-				werrstr("bad command length");
-				return -1;
+				respond(req, "bad command length");
+				break;
 			}
 			memmove(lun->rawcmd, data, count);
 			lun->cmd.p = lun->rawcmd;
@@ -759,6 +829,8 @@
 			lun->cmd.count = count;
 			lun->cmd.write = 1;
 			lun->phase = Pdata;
+			req->ofcall.count = count;
+			respond(req, nil);
 			break;
 		case Pdata:
 			lun->data.p = data;
@@ -766,13 +838,17 @@
 			lun->data.write = 1;
 			count = umsrequest(lun,&lun->cmd,&lun->data,&lun->status);
 			lun->phase = Pstatus;
-			if(count < 0)
+			if(count < 0){
 				lun->lbsize = 0;  /* medium may have changed */
+				responderror(req);
+			}else{
+				req->ofcall.count = count;
+				respond(req, nil);
+			}
 			break;
 		case Pstatus:
 			lun->phase = Pcmd;
-			werrstr("phase error");
-			count = -1;
+			respond(req, "phase error");
 			break;
 		}
 		break;
@@ -780,19 +856,21 @@
 	default:
 		p = &lun->part[path];
 		if(!p->inuse){
-			count = -1;
-			werrstr(Eperm);
+			respond(req, "permission denied");
 			break;
 		}
 		len = ocount = count;
 		count = setup(lun, p, data, count, offset);
-		if (count <= 0)
+		if (count <= 0){
+			responderror(req);
 			break;
+		}
 		bno = lun->offset;
 		if (lun->bufp == lun->buf) {
 			count = SRread(lun, lun->bufp, lun->nb * lun->lbsize);
 			if(count < 0) {
 				lun->lbsize = 0;  /* medium may have changed */
+				responderror(req);
 				break;
 			}
 			/*
@@ -807,9 +885,11 @@
 
 		lun->offset = bno;
 		count = SRwrite(lun, lun->bufp, lun->nb * lun->lbsize);
-		if(count < 0)
+		if(count < 0){
 			lun->lbsize = 0;	/* medium may have changed */
-		else{
+			responderror(req);
+			break;
+		}else{
 			if(lun->off + len > count)
 				count -= lun->off; /* short write */
 			/* never report more bytes written than requested */
@@ -818,10 +898,11 @@
 			else if(count > ocount)
 				count = ocount;
 		}
+		req->ofcall.count = count;
+		respond(req, nil);
 		break;
 	}
 	qunlock(ums);
-	return count;
 }
 
 int
@@ -833,7 +914,7 @@
 	int i, epin, epout;
 
 	epin = epout = -1;
-	ud = ums->dev->usb;
+	ud = dev->usb;
 	for(i = 0; i < nelem(ud->ep); i++){
 		if((ep = ud->ep[i]) == nil)
 			continue;
@@ -855,7 +936,7 @@
 	dprint(2, "disk: ep ids: in %d out %d\n", epin, epout);
 	if(epin == -1 || epout == -1)
 		return -1;
-	ums->epin = openep(ums->dev, epin);
+	ums->epin = openep(dev, epin);
 	if(ums->epin == nil){
 		fprint(2, "disk: openep %d: %r\n", epin);
 		return -1;
@@ -864,7 +945,7 @@
 		incref(ums->epin);
 		ums->epout = ums->epin;
 	}else
-		ums->epout = openep(ums->dev, epout);
+		ums->epout = openep(dev, epout);
 	if(ums->epout == nil){
 		fprint(2, "disk: openep %d: %r\n", epout);
 		closedev(ums->epin);
@@ -890,16 +971,16 @@
 	if(usbdebug > 1 || diskdebug > 2){
 		devctl(ums->epin, "debug 1");
 		devctl(ums->epout, "debug 1");
-		devctl(ums->dev, "debug 1");
+		devctl(dev, "debug 1");
 	}
 	return 0;
 }
 
-static int
+static void
 usage(void)
 {
-	werrstr("usage: usb/disk [-d] [-N nb]");
-	return -1;
+	fprint(2, "usage: usb/disk [-d] devid");
+	exits("usage");
 }
 
 static void
@@ -917,7 +998,8 @@
 }
 
 static Srv diskfs = {
-	.walk = dwalk,
+	.attach = dattach,
+	.walk1 = dwalk,
 	.open =	 dopen,
 	.read =	 dread,
 	.write = dwrite,
@@ -924,38 +1006,31 @@
 	.stat =	 dstat,
 };
 
-int
-diskmain(Dev *dev, int argc, char **argv)
+void
+main(int argc, char **argv)
 {
-	Ums *ums;
 	Umsc *lun;
-	int i, devid;
+	int i;
 
-	devid = dev->id;
 	ARGBEGIN{
 	case 'd':
 		scsidebug(diskdebug);
 		diskdebug++;
 		break;
-	case 'N':
-		devid = atoi(EARGF(usage()));
-		break;
 	default:
-		return usage();
+		usage();
 	}ARGEND
-	if(argc != 0) {
-		return usage();
-	}
+	if(argc != 1)
+		usage();
 	
-//	notify(ding);
+	dev = getdev(atoi(*argv));
+	if(dev == nil)
+		sysfatal("getdev: %r");
 	ums = dev->aux = emallocz(sizeof(Ums), 1);
 	ums->maxlun = -1;
-	ums->dev = dev;
 	dev->free = umsdevfree;
-	if(findendpoints(ums) < 0){
-		werrstr("disk: endpoints not found");
-		return -1;
-	}
+	if(findendpoints(ums) < 0)
+		sysfatal("endpoints not found");
 
 	/*
 	 * SanDISK 512M gets residues wrong.
@@ -963,20 +1038,14 @@
 	if(dev->usb->vid == 0x0781 && dev->usb->did == 0x5150)
 		ums->wrongresidues = 1;
 
-	if(umsinit(ums) < 0){
-		dprint(2, "disk: umsinit: %r\n");
-		return -1;
-	}
+	if(umsinit() < 0)
+		sysfatal("umsinit: %r\n");
 
 	for(i = 0; i <= ums->maxlun; i++){
 		lun = &ums->lun[i];
-		lun->fs = diskfs;
-		snprint(lun->fs.name, sizeof(lun->fs.name), "sdU%d.%d", devid, i);
-		lun->fs.dev = dev;
-		incref(dev);
-		lun->fs.aux = lun;
+		snprint(lun->name, sizeof(lun->name), "sdU%d.%d", dev->id, i);
 		makeparts(lun);
-		usbfsadd(&lun->fs);
 	}
-	return 0;
+	postsharesrv(&diskfs, "usbdisk", "usb", "disk", "b");
+	exits(nil);
 }
--- a/sys/src/cmd/nusb/disk/mkfile
+++ b/sys/src/cmd/nusb/disk/mkfile
@@ -13,7 +13,7 @@
 
 LIB=../lib/usb.a$O
 
-BIN=/$objtype/bin/usb
+BIN=/$objtype/bin/nusb
 
 </sys/src/cmd/mkone
 CFLAGS=-I../lib $CFLAGS
--- a/sys/src/cmd/nusb/disk/ums.h
+++ b/sys/src/cmd/nusb/disk/ums.h
@@ -67,6 +67,7 @@
 struct Umsc
 {
 	ScsiReq;
+	char name[40];
 	uvlong	blocks;
 	vlong	capacity;
 
@@ -88,7 +89,6 @@
 struct Ums
 {
 	QLock;
-	Dev	*dev;
 	Dev	*epin;
 	Dev	*epout;
 	Umsc	*lun;