示例#1
0
文件: usbd.c 项目: elbing/harvey
static void
portreset(Hub *h, int p)
{
	int sts;
	Dev *d, *nd;
	Port *pp;

	d = h->dev;
	pp = &h->port[p];
	nd = pp->dev;
	dprint(2, "%s: %s: port %d: resetting\n", argv0, d->dir, p);
	if(hubfeature(h, p, Fportreset, 1) < 0){
		dprint(2, "%s: %s: port %d: reset: %r\n", argv0, d->dir, p);
		goto Fail;
	}
	sleep(Resetdelay);
	sts = portstatus(h, p);
	if(sts < 0)
		goto Fail;
	if((sts & PSenable) == 0){
		dprint(2, "%s: %s: port %d: not enabled?\n", argv0, d->dir, p);
		hubfeature(h, p, Fportenable, 1);
		sts = portstatus(h, p);
		if((sts & PSenable) == 0)
			goto Fail;
	}
	nd = pp->dev;
	opendevdata(nd, ORDWR);
	if(usbcmd(nd, Rh2d|Rstd|Rdev, Rsetaddress, nd->id, 0, nil, 0) < 0){
		dprint(2, "%s: %s: port %d: setaddress: %r\n", argv0, d->dir, p);
		goto Fail;
	}
	if(devctl(nd, "address") < 0){
		dprint(2, "%s: %s: port %d: set address: %r\n", argv0, d->dir, p);
		goto Fail;
	}
	if(usbcmd(nd, Rh2d|Rstd|Rdev, Rsetconf, 1, 0, nil, 0) < 0){
		dprint(2, "%s: %s: port %d: setconf: %r\n", argv0, d->dir, p);
		unstall(nd, nd, Eout);
		if(usbcmd(nd, Rh2d|Rstd|Rdev, Rsetconf, 1, 0, nil, 0) < 0)
			goto Fail;
	}
	if(nd->dfd >= 0)
		close(nd->dfd);
	return;
Fail:
	pp->state = Pdisabled;
	pp->sts = 0;
	if(pp->hub != nil)
		pp->hub = nil;	/* hub closed by enumhub */
	hubfeature(h, p, Fportenable, 0);
	if(nd != nil)
		devctl(nd, "detach");
	closedev(nd);
}
示例#2
0
文件: dev.c 项目: vrthra/9front-tmp
int
loaddevconf(Dev *d, int n)
{
	uchar *buf;
	int nr;
	int type;

	if(n >= nelem(d->usb->conf)){
		werrstr("loaddevconf: bug: out of configurations in device");
		fprint(2, "%s: %r\n", argv0);
		return -1;
	}
	buf = emallocz(Maxdevconf, 0);
	type = Rd2h|Rstd|Rdev;
	nr = usbcmd(d, type, Rgetdesc, Dconf<<8|n, 0, buf, Maxdevconf);
	if(nr < Dconflen){
		free(buf);
		return -1;
	}
	if(d->usb->conf[n] == nil)
		d->usb->conf[n] = emallocz(sizeof(Conf), 1);
	nr = parseconf(d->usb, d->usb->conf[n], buf, nr);
	free(buf);
	return nr;
}
示例#3
0
static int
plsetparam(Serialport *p)
{
	uint8_t buf[ParamReqSz];
	int res;
	Serial *ser;

	ser = p->s;

	PUT4(buf, p->baud);

	if(p->stop == 1)
		buf[4] = 0;
	else if(p->stop == 2)
		buf[4] = 2; 			/* see comment in getparam */
	buf[5] = p->parity;
	buf[6] = p->bits;

	dsprint(2, "serial: setparam: ");
	if(serialdebug)
		dumpbuf(buf, sizeof buf);
	res = usbcmd(ser->dev, Rh2d | Rclass | Riface, SetLineReq,
		0, 0, buf, sizeof buf);
	plmodemctl(p, p->mctl);
	plgetparam(p);		/* make sure our state corresponds */

	dsprint(2, "serial: setparam res: %d\n", res);
	return res;
}
示例#4
0
文件: silabs.c 项目: dalmonian/harvey
static int
slput(Serialport *p, uint op, uint val)
{
	Serial *ser;

	ser = p->s;
	return usbcmd(ser->dev, Rh2d | Rvendor | Riface, op, val, p->interfc,
		nil, 0);
}
示例#5
0
文件: silabs.c 项目: dalmonian/harvey
static int
slread(Serialport *p, int req, void *buf, int len)
{
	Serial *ser;

	ser = p->s;
	return usbcmd(ser->dev, Rd2h | Rvendor | Riface, req, 0, p->interfc,
		buf, len);
}
示例#6
0
static int
setctlline(Serialport *p, uint8_t val)
{
	Serial *ser;

	ser = p->s;
	return usbcmd(ser->dev, Rh2d | Rclass | Riface, SetCtlReq,
		val, 0, nil, 0);
}
示例#7
0
static int
plsetbreak(Serialport *p, int val)
{
	Serial *ser;

	ser = p->s;
	return usbcmd(ser->dev, Rh2d | Rclass | Riface,
		(val != 0? BreakOn: BreakOff), val, 0, nil, 0);
}
示例#8
0
文件: usbd.c 项目: elbing/harvey
static int
confighub(Hub *h)
{
	int type;
	uint8_t buf[128];	/* room for extra descriptors */
	int i;
	Usbdev *d;
	DHub *dd;
	Port *pp;
	int nr;
	int nmap;
	uint8_t *PortPwrCtrlMask;
	int offset;
	int mask;

	d = h->dev->usb;
	for(i = 0; i < nelem(d->ddesc); i++)
		if(d->ddesc[i] == nil)
			break;
		else if(d->ddesc[i]->data.bDescriptorType == Dhub){
			dd = (DHub*)&d->ddesc[i]->data;
			nr = Dhublen;
			goto Config;
		}
	type = Rd2h|Rclass|Rdev;
	nr = usbcmd(h->dev, type, Rgetdesc, Dhub<<8|0, 0, buf, sizeof buf);
	if(nr < Dhublen){
		dprint(2, "%s: %s: getdesc hub: %r\n", argv0, h->dev->dir);
		return -1;
	}
	dd = (DHub*)buf;
Config:
	h->nport = dd->bNbrPorts;
	nmap = 1 + h->nport/8;
	if(nr < 7 + 2*nmap){
		fprint(2, "%s: %s: descr. too small\n", argv0, h->dev->dir);
		return -1;
	}
	h->port = emallocz((h->nport+1)*sizeof(Port), 1);
	h->pwrms = dd->bPwrOn2PwrGood*2;
	if(h->pwrms < Powerdelay)
		h->pwrms = Powerdelay;
	h->maxcurrent = dd->bHubContrCurrent;
	h->pwrmode = dd->wHubCharacteristics[0] & 3;
	h->compound = (dd->wHubCharacteristics[0] & (1<<2))!=0;
	h->leds = (dd->wHubCharacteristics[0] & (1<<7)) != 0;
	PortPwrCtrlMask = dd->DeviceRemovable + nmap;
	for(i = 1; i <= h->nport; i++){
		pp = &h->port[i];
		offset = i/8;
		mask = 1<<(i%8);
		pp->removable = (dd->DeviceRemovable[offset] & mask) != 0;
		pp->pwrctl = (PortPwrCtrlMask[offset] & mask) != 0;
	}
	return 0;
}
示例#9
0
Dev*
setupep(Dev *d, Ep *e, int speed)
{
	uchar b[4];
	Audio *x;
	Altc *a;
	int i;

	for(i = 0; i < nelem(e->iface->altc); i++)
		if(a = e->iface->altc[i])
			for(x = a->aux; x; x = x->next)
				if(speed >= x->minfreq && speed <= x->maxfreq)
					goto Foundaltc;

	werrstr("no altc found");
	return nil;

Foundaltc:
	if(usbcmd(d, Rh2d|Rstd|Riface, Rsetiface, i, e->iface->id, nil, 0) < 0){
		werrstr("set altc: %r");
		return nil;
	}

	b[0] = speed;
	b[1] = speed >> 8;
	b[2] = speed >> 16;
	if(usbcmd(d, Rh2d|Rclass|Rep, Rsetcur, 0x100, e->addr, b, 3) < 0)
		fprint(2, "warning: set freq: %r\n");

	if((d = openep(d, e->id)) == nil){
		werrstr("openep: %r");
		return nil;
	}
	devctl(d, "pollival %d", a->interval);
	devctl(d, "samplesz %d", audiochan*audiores/8);
	devctl(d, "sampledelay %d", audiodelay);
	devctl(d, "hz %d", speed);
	if(e->dir == Ein)
		devctl(d, "name audioin");
	else
		devctl(d, "name audio");
	return d;
}
示例#10
0
文件: usbd.c 项目: elbing/harvey
static int
hubfeature(Hub *h, int port, int f, int on)
{
	int cmd;

	if(on)
		cmd = Rsetfeature;
	else
		cmd = Rclearfeature;
	return usbcmd(h->dev, Rh2d|Rclass|Rother, cmd, f, port, nil, 0);
}
示例#11
0
int
setaudioalt(int rec, Audiocontrol *c, int control)
{
	dprint(2, "setcontrol %s: Set alt %d\n", c->name, control);
	curalt[rec] = control;
	if(usbcmd(ad, Rh2d|Rstd|Riface, Rsetiface, control, interface[rec], nil, 0) < 0){
		dprint(2, "setcontrol: setupcmd %s failed\n", c->name);
		return -1;
	}
	return control;
}
示例#12
0
static int
wr(Dev *d, int reg, int val)
{
	int ret;

	ret = usbcmd(d, Rh2d|Rvendor|Rdev, Writereg, 0, reg,
		(uchar*)&val, sizeof(val));
	if(ret < 0)
		fprint(2, "%s: wr(%x, %x): %r", argv0, reg, val);
	return ret;
}
示例#13
0
文件: asix.c 项目: 99years/plan9
static int
asixget(Dev *d, int c, uchar *buf, int l)
{
	int r;
	int ec;

	r = Rd2h|Rvendor|Rdev;
	ec = usbcmd(d, r, c, 0, 0, buf, l);
	if(ec < 0)
		deprint(2, "%s: asixget %x: %r\n", argv0, c);
	return ec;
}
示例#14
0
文件: asix.c 项目: 99years/plan9
static int
asixset(Dev *d, int c, int v)
{
	int r;
	int ec;

	r = Rh2d|Rvendor|Rdev;
	ec = usbcmd(d, r, c, v, 0, nil, 0);
	if(ec < 0)
		deprint(2, "%s: asixset %x %x: %r\n", argv0, c, v);
	return ec;
}
示例#15
0
文件: dev.c 项目: vrthra/9front-tmp
char*
loaddevstr(Dev *d, int sid)
{
	uchar buf[128];
	int type;
	int nr;

	if(sid == 0)
		return estrdup("none");
	type = Rd2h|Rstd|Rdev;
	nr=usbcmd(d, type, Rgetdesc, Dstr<<8|sid, 0, buf, sizeof(buf));
	return mkstr(buf, nr);
}
示例#16
0
static int
rr(Dev *d, int reg)
{
	int ret, rval;

	ret = usbcmd(d, Rd2h|Rvendor|Rdev, Readreg, 0, reg,
		(uchar*)&rval, sizeof(rval));
	if(ret < 0){
		fprint(2, "%s: rr(%x): %r", argv0, reg);
		return 0;
	}
	return rval;
}
示例#17
0
static int
vendorwrite(Serialport *p, int val, int index)
{
	int res;
	Serial *ser;

	ser = p->s;

	dsprint(2, "serial: vendorwrite val: 0x%x idx:%d\n", val, index);
	res = usbcmd(ser->dev, Rh2d | Rvendor | Rdev, VendorWriteReq,
		val, index, nil, 0);
	dsprint(2, "serial: vendorwrite res:%d\n", res);
	return res;
}
示例#18
0
static int
vendorread(Serialport *p, int val, int index, uint8_t *buf)
{
	int res;
	Serial *ser;

	ser = p->s;

	dsprint(2, "serial: vendorread val: 0x%x idx:%d buf:%p\n",
		val, index, buf);
	res = usbcmd(ser->dev,  Rd2h | Rvendor | Rdev, VendorReadReq,
		val, index, buf, 1);
	dsprint(2, "serial: vendorread res:%d\n", res);
	return res;
}
示例#19
0
文件: usbd.c 项目: elbing/harvey
static int
getmaxpkt(Dev *d, int islow)
{
	uint8_t buf[64];	/* More room to try to get device-specific descriptors */
	DDev *dd;

	dd = (DDev*)buf;
	if(islow)
		dd->bMaxPacketSize0 = 8;
	else
		dd->bMaxPacketSize0 = 64;
	if(usbcmd(d, Rd2h|Rstd|Rdev, Rgetdesc, Ddev<<8|0, 0, buf, sizeof(buf)) < 0)
		return -1;
	return dd->bMaxPacketSize0;
}
示例#20
0
文件: usbd.c 项目: elbing/harvey
/*
 * This may be used to detect overcurrent on the hub
 */
static void
checkhubstatus(Hub *h)
{
	uint8_t buf[4];
	int sts;

	if(h->isroot)	/* not for root hubs */
		return;
	if(usbcmd(h->dev, Rd2h|Rclass|Rdev, Rgetstatus, 0, 0, buf, 4) < 0){
		dprint(2, "%s: get hub status: %r\n", h->dev->dir);
		return;
	}
	sts = GET2(buf);
	dprint(2, "hub %s: status %#x\n", h->dev->dir, sts);
}
示例#21
0
static int
ftdiread(Serialport *p, int index, int req, uchar *buf, int len)
{
    int res;
    Serial *ser;

    ser = p->s;

    if(req != FTGETE2READ)
        index |= p->interfc + 1;
    dsprint(2, "serial: ftdiread %#p [%d] req: %#x val: %#x idx:%d buf:%p len:%d\n",
            p, p->interfc, req, 0, index, buf, len);
    res = usbcmd(ser->dev,  Rd2h | Rftdireq | Rdev, req, 0, index, buf, len);
    dsprint(2, "serial: ftdiread res:%d\n", res);
    return res;
}
示例#22
0
static int
ftdiwrite(Serialport *p, int val, int index, int req)
{
    int res;
    Serial *ser;

    ser = p->s;

    if(req != FTGETE2READ || req != FTSETE2ERASE || req != FTSETBAUDRATE)
        index |= p->interfc + 1;
    dsprint(2, "serial: ftdiwrite %#p [%d] req: %#x val: %#x idx:%d\n",
            p, p->interfc, req, val, index);
    res = usbcmd(ser->dev, Rh2d | Rftdireq | Rdev, req, val, index, nil, 0);
    dsprint(2, "serial: ftdiwrite res:%d\n", res);
    return res;
}
示例#23
0
文件: asix.c 项目: 99years/plan9
static int
miiread(Dev *d, int phy, int reg)
{
	int r;
	uchar v[2];

	r = Rd2h|Rvendor|Rdev;
	if(usbcmd(d, r, Crmii, phy, reg, v, 2) < 0){
		dprint(2, "%s: miiwrite: %r\n", argv0);
		return -1;
	}
	r = GET2(v);
	if(r == 0xFFFF)
		return -1;
	return r;
}
示例#24
0
文件: asix.c 项目: 99years/plan9
static int
eepromread(Dev *d, int i)
{
	int r;
	int ec;
	uchar buf[2];

	r = Rd2h|Rvendor|Rdev;
	ec = usbcmd(d, r, Creeprom, i, 0, buf, sizeof(buf));
	if(ec < 0)
		deprint(2, "%s: eepromread %d: %r\n", argv0, i);
	ec = GET2(buf);
	deprint(2, "%s: eeprom %#x = %#x\n", argv0, i, ec);
	if(ec == 0xFFFF)
		ec = -1;
	return ec;
}
示例#25
0
文件: asix.c 项目: 99years/plan9
static int
miiwrite(Dev *d, int phy, int reg, int val)
{
	int r;
	uchar v[2];

	if(asixset(d, Cswmii, 0) < 0)
		return -1;
	r = Rh2d|Rvendor|Rdev;
	PUT2(v, val);
	if(usbcmd(d, r, Cwmii, phy, reg, v, 2) < 0){
		deprint(2, "%s: miiwrite: %#x %#x %r\n", argv0, reg, val);
		return -1;
	}
	if(asixset(d, Chwmii, 0) < 0)
		return -1;
	return 0;
}
示例#26
0
文件: dev.c 项目: vrthra/9front-tmp
int
loaddevdesc(Dev *d)
{
	uchar buf[Ddevlen+255];
	int nr;
	int type;
	Ep *ep0;

	type = Rd2h|Rstd|Rdev;
	nr = sizeof(buf);
	memset(buf, 0, Ddevlen);
	if((nr=usbcmd(d, type, Rgetdesc, Ddev<<8|0, 0, buf, nr)) < 0)
		return -1;
	/*
	 * Several hubs are returning descriptors of 17 bytes, not 18.
	 * We accept them and leave number of configurations as zero.
	 * (a get configuration descriptor also fails for them!)
	 */
	if(nr < Ddevlen){
		print("%s: %s: warning: device with short descriptor\n",
			argv0, d->dir);
		if(nr < Ddevlen-1){
			werrstr("short device descriptor (%d bytes)", nr);
			return -1;
		}
	}
	d->usb = emallocz(sizeof(Usbdev), 1);
	ep0 = mkep(d->usb, 0);
	ep0->dir = Eboth;
	ep0->type = Econtrol;
	ep0->maxpkt = d->maxpkt = 8;		/* a default */
	nr = parsedev(d, buf, nr);
	if(nr >= 0){
		d->usb->vendor = loaddevstr(d, d->usb->vsid);
		if(strcmp(d->usb->vendor, "none") != 0){
			d->usb->product = loaddevstr(d, d->usb->psid);
			d->usb->serial = loaddevstr(d, d->usb->ssid);
		}
	}
	return nr;
}
示例#27
0
文件: usbd.c 项目: elbing/harvey
static int
portstatus(Hub *h, int p)
{
	Dev *d;
	uint8_t buf[4];
	int t;
	int sts;
	int dbg;

	dbg = usbdebug;
	if(dbg != 0 && dbg < 4)
		usbdebug = 1;	/* do not be too chatty */
	d = h->dev;
	t = Rd2h|Rclass|Rother;
	if(usbcmd(d, t, Rgetstatus, 0, p, buf, sizeof(buf)) < 0)
		sts = -1;
	else
		sts = GET2(buf);
	usbdebug = dbg;
	return sts;
}
示例#28
0
static int
plgetparam(Serialport *p)
{
	uint8_t buf[ParamReqSz];
	int res;
	Serial *ser;

	ser = p->s;


	res = usbcmd(ser->dev, Rd2h | Rclass | Riface, GetLineReq,
		0, 0, buf, sizeof buf);
	p->baud = GET4(buf);

	/*
	 * with the Pl9 interface it is not possible to set `1.5' as stop bits
	 * for the prologic:
	 *	0 is 1 stop bit
	 *	1 is 1.5 stop bits
	 *	2 is 2 stop bits
	 */
	if(buf[4] == 1)
		fprint(2, "warning, stop bit set to 1.5 unsupported");
	else if(buf[4] == 0)
		p->stop = 1;
	else if(buf[4] == 2)
		p->stop = 2;
	p->parity = buf[5];
	p->bits = buf[6];

	dsprint(2, "serial: getparam: ");
	if(serialdebug)
		dumpbuf(buf, sizeof buf);
	dsprint(2, "serial: getparam res: %d\n", res);
	return res;
}
示例#29
0
文件: usbd.c 项目: elbing/harvey
/*
 * BUG: does not consider max. power avail.
 */
static Dev*
portattach(Hub *h, int p, int sts)
{
	Dev *d;
	Port *pp;
	Dev *nd;
	char fname[80];
	char buf[40];
	char *sp;
	int mp;
	int nr;

	d = h->dev;
	pp = &h->port[p];
	nd = nil;
	pp->state = Pattached;
	dprint(2, "%s: %s: port %d attach sts %#x\n", argv0, d->dir, p, sts);
	sleep(Connectdelay);
	if(hubfeature(h, p, Fportenable, 1) < 0)
		dprint(2, "%s: %s: port %d: enable: %r\n", argv0, d->dir, p);
	sleep(Enabledelay);
	if(hubfeature(h, p, Fportreset, 1) < 0){
		dprint(2, "%s: %s: port %d: reset: %r\n", argv0, d->dir, p);
		goto Fail;
	}
	sleep(Resetdelay);
	sts = portstatus(h, p);
	if(sts < 0)
		goto Fail;
	if((sts & PSenable) == 0){
		dprint(2, "%s: %s: port %d: not enabled?\n", argv0, d->dir, p);
		hubfeature(h, p, Fportenable, 1);
		sts = portstatus(h, p);
		if((sts & PSenable) == 0)
			goto Fail;
	}
	sp = "full";
	if(sts & PSslow)
		sp = "low";
	if(sts & PShigh)
		sp = "high";
	dprint(2, "%s: %s: port %d: attached status %#x\n", argv0, d->dir, p, sts);

	if(devctl(d, "newdev %s %d", sp, p) < 0){
		fprint(2, "%s: %s: port %d: newdev: %r\n", argv0, d->dir, p);
		goto Fail;
	}
	seek(d->cfd, 0, 0);
	nr = read(d->cfd, buf, sizeof(buf)-1);
	if(nr == 0){
		fprint(2, "%s: %s: port %d: newdev: eof\n", argv0, d->dir, p);
		goto Fail;
	}
	if(nr < 0){
		fprint(2, "%s: %s: port %d: newdev: %r\n", argv0, d->dir, p);
		goto Fail;
	}
	buf[nr] = 0;
	snprint(fname, sizeof(fname), "/dev/usb/%s", buf);
	nd = opendev(fname);
	if(nd == nil){
		fprint(2, "%s: %s: port %d: opendev: %r\n", argv0, d->dir, p);
		goto Fail;
	}
	if(usbdebug > 2)
		devctl(nd, "debug 1");
	if(opendevdata(nd, ORDWR) < 0){
		fprint(2, "%s: %s: opendevdata: %r\n", argv0, nd->dir);
		goto Fail;
	}
	if(usbcmd(nd, Rh2d|Rstd|Rdev, Rsetaddress, nd->id, 0, nil, 0) < 0){
		dprint(2, "%s: %s: port %d: setaddress: %r\n", argv0, d->dir, p);
		goto Fail;
	}
	if(devctl(nd, "address") < 0){
		dprint(2, "%s: %s: port %d: set address: %r\n", argv0, d->dir, p);
		goto Fail;
	}

	mp=getmaxpkt(nd, strcmp(sp, "low") == 0);
	if(mp < 0){
		dprint(2, "%s: %s: port %d: getmaxpkt: %r\n", argv0, d->dir, p);
		goto Fail;
	}else{
		dprint(2, "%s; %s: port %d: maxpkt %d\n", argv0, d->dir, p, mp);
		devctl(nd, "maxpkt %d", mp);
	}
	if((sts & PSslow) != 0 && strcmp(sp, "full") == 0)
		dprint(2, "%s: %s: port %d: %s is full speed when port is low\n",
			argv0, d->dir, p, nd->dir);
	if(configdev(nd) < 0){
		dprint(2, "%s: %s: port %d: configdev: %r\n", argv0, d->dir, p);
		goto Fail;
	}
	/*
	 * We always set conf #1. BUG.
	 */
	if(usbcmd(nd, Rh2d|Rstd|Rdev, Rsetconf, 1, 0, nil, 0) < 0){
		dprint(2, "%s: %s: port %d: setconf: %r\n", argv0, d->dir, p);
		unstall(nd, nd, Eout);
		if(usbcmd(nd, Rh2d|Rstd|Rdev, Rsetconf, 1, 0, nil, 0) < 0)
			goto Fail;
	}
	dprint(2, "%s: %U\n", argv0, nd);
	pp->state = Pconfiged;
	dprint(2, "%s: %s: port %d: configed: %s\n",
			argv0, d->dir, p, nd->dir);
	return pp->dev = nd;
Fail:
	pp->state = Pdisabled;
	pp->sts = 0;
	if(pp->hub != nil)
		pp->hub = nil;	/* hub closed by enumhub */
	hubfeature(h, p, Fportenable, 0);
	if(nd != nil)
		devctl(nd, "detach");
	closedev(nd);
	return nil;
}
示例#30
0
文件: ether.c 项目: npe9/harvey
static void
setalt(Dev *d, int ifcid, int altid)
{
	if(usbcmd(d, Rh2d|Rstd|Riface, Rsetiface, altid, ifcid, nil, 0) < 0)
		dprint(2, "%s: setalt ifc %d alt %d: %r\n", argv0, ifcid, altid);
}