changelog shortlog tags branches files raw gz bz2 help

Mercurial > hg > plan9front / changeset: nusb/usbd: work around devices that ignore the high byte of wLength in control transfer reads

changeset 7214: d01edc4d026e
parent 7213: c250493e2340
child 7215: e4dad4f80c6c
author: cinap_lenrek@felloff.net
date: Tue, 07 May 2019 09:19:53 +0200
files: sys/src/cmd/nusb/kb/kb.c sys/src/cmd/nusb/lib/dev.c
description: nusb/usbd: work around devices that ignore the high byte of wLength in control transfer reads

there appear to be devices out there such as Realtek RTL2838UHIDIR
SDR that do not process control transfers correctly, ignoring the
high byte of the wLength field. to work around this, we specify an
odd number of bytes for read sizes >= 256 which keeps the low byte
0xFF.
     1.1--- a/sys/src/cmd/nusb/kb/kb.c
     1.2+++ b/sys/src/cmd/nusb/kb/kb.c
     1.3@@ -42,7 +42,12 @@ struct Hiddev
     1.4 
     1.5 	/* report descriptor */
     1.6 	int	nrep;
     1.7-	uchar	rep[512];
     1.8+
     1.9+	/*
    1.10+	 * use odd size as some devices ignore the high byte of
    1.11+	 * wLength in control transfer reads.
    1.12+	 */
    1.13+	uchar	rep[512-1];
    1.14 };
    1.15 
    1.16 typedef struct Hidreport Hidreport;
     2.1--- a/sys/src/cmd/nusb/lib/dev.c
     2.2+++ b/sys/src/cmd/nusb/lib/dev.c
     2.3@@ -136,8 +136,10 @@ enum
     2.4 	/*
     2.5 	 * Max device conf is also limited by max control request size as
     2.6 	 * limited by Maxctllen in the kernel usb.h (both limits are arbitrary).
     2.7+	 * Some devices ignore the high byte of control transfer reads so keep
     2.8+	 * the low byte all ones. asking for 16K kills Newsham's disk.
     2.9 	 */
    2.10-	Maxdevconf = 4 * 1024,	/* asking for 16K kills Newsham's disk */
    2.11+	Maxdevconf = 4*1024 - 1,
    2.12 };
    2.13 
    2.14 int
    2.15@@ -201,7 +203,7 @@ mkstr(uchar *b, int n)
    2.16 char*
    2.17 loaddevstr(Dev *d, int sid)
    2.18 {
    2.19-	uchar buf[256];
    2.20+	uchar buf[256-2];	/* keep size < 256 */
    2.21 	int langid;
    2.22 	int type;
    2.23 	int nr;