git: 9front

Download patch

ref: 490ee029edb239129685ecf80264a93ff1d0a24f
parent: ed1498171c27e4a20781a2d80d91fdf8b634d05c
author: cinap_lenrek <cinap_lenrek@felloff.net>
date: Sat Mar 7 17:26:49 EST 2020

nusb/usbd: fix /env/usbbusy bug

run the usb hub poll "work()" proc in the same filedescriptor
group as the fileserver by forking the process in Srv.start
callback.

this also prevents the usbbusy filedescriptor from being kept
open by the fileserver process.

--- a/sys/src/cmd/nusb/usbd/dat.h
+++ b/sys/src/cmd/nusb/usbd/dat.h
@@ -122,3 +122,5 @@
 	uchar	wHubDelay[2];
 	uchar	DeviceRemovable[1];	/* variable length */
 };
+
+extern Hub *hubs;
--- a/sys/src/cmd/nusb/usbd/hub.c
+++ b/sys/src/cmd/nusb/usbd/hub.c
@@ -670,21 +670,8 @@
 void
 work(void)
 {
-	char *fn;
 	Hub *h;
 	int i;
-
-	hubs = nil;
-	while((fn = rendezvous(work, nil)) != nil){
-		dprint(2, "%s: %s starting\n", argv0, fn);
-		h = newhub(fn, nil);
-		if(h == nil)
-			fprint(2, "%s: %s: newhub failed: %r\n", argv0, fn);
-		free(fn);
-	}
-
-	if(hubs == nil)
-		return;
 
 	/*
 	 * Enumerate (and acknowledge after first enumeration).
--- a/sys/src/cmd/nusb/usbd/usbd.c
+++ b/sys/src/cmd/nusb/usbd/usbd.c
@@ -329,7 +329,17 @@
 	respond(req, nil);
 }
 
+static void
+usbdstart(Srv*)
+{
+	switch(rfork(RFPROC|RFMEM|RFNOWAIT)){
+	case -1: sysfatal("rfork: %r");
+	case 0: work(); exits(nil);
+	}
+}
+
 Srv usbdsrv = {
+	.start = usbdstart,
 	.attach = usbdattach,
 	.walk1 = usbdwalk,
 	.read = usbdread,
@@ -447,6 +457,7 @@
 main(int argc, char **argv)
 {
 	int fd, i, nd;
+	char *fn;
 	Dir *d;
 
 	ARGBEGIN {
@@ -458,34 +469,33 @@
 		break;
 	} ARGEND;
 
-	busyfd = create("/env/usbbusy", ORCLOSE, 0600);
 	quotefmtinstall();
 	fmtinstall('U', Ufmt);
 	initevent();
-	rfork(RFNOTEG);
-	switch(rfork(RFPROC|RFMEM|RFNOWAIT)){
-	case -1: sysfatal("rfork: %r");
-	case 0: work(); exits(nil);
-	}
+
+	hubs = nil;
 	if(argc == 0){
-		if((fd = open("/dev/usb", OREAD)) < 0){
-			rendezvous(work, nil);
+		if((fd = open("/dev/usb", OREAD)) < 0)
 			sysfatal("/dev/usb: %r");
-		}
 		nd = dirreadall(fd, &d);
 		close(fd);
-		if(nd < 2){
-			rendezvous(work, nil);
-			sysfatal("/dev/usb: no hubs");
+		for(i = 0; i < nd; i++){
+			if(strcmp(d[i].name, "ctl") != 0){
+				fn = smprint("/dev/usb/%s", d[i].name);
+				newhub(fn, nil);
+				free(fn);
+			}
 		}
-		for(i = 0; i < nd; i++)
-			if(strcmp(d[i].name, "ctl") != 0)
-				rendezvous(work, smprint("/dev/usb/%s", d[i].name));
 		free(d);
-	}else
+	}else {
 		for(i = 0; i < argc; i++)
-			rendezvous(work, estrdup9p(argv[i]));
-	rendezvous(work, nil);
+			newhub(argv[i], nil);
+	}
+
+	if(hubs == nil)
+		sysfatal("no hubs");
+
+	busyfd = create("/env/usbbusy", ORCLOSE, 0600);
 	postsharesrv(&usbdsrv, nil, "usb", "usbd");
 	exits(nil);
 }
--