NetBSD-Bugs archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

Re: kern/51395: USB Ethernet makes xhci hang



The following reply was made to PR kern/51395; it has been noted by GNATS.

From: Takahiro Hayashi <t425hash%gmail.com@localhost>
To: gnats-bugs%NetBSD.org@localhost, kern-bug-people%netbsd.org@localhost,
 gnats-admin%netbsd.org@localhost, netbsd-bugs%netbsd.org@localhost,
 Benny Siegert <bsiegert%gmail.com@localhost>
Cc: 
Subject: Re: kern/51395: USB Ethernet makes xhci hang
Date: Mon, 8 Aug 2016 22:45:02 +0900

 This is a multi-part message in MIME format.
 --------------D0B31FF0B77670F21EA67021
 Content-Type: text/plain; charset=windows-1252; format=flowed
 Content-Transfer-Encoding: 7bit
 
 I've found that the previous fix was imcomplete.
 
 Can you try attached patch?
 This patch tries to put Link TRB at the last of ring.
 This lacks handling that first TRB should be written at last.
 
 Thank you for reporting this problem.
 
 
 -- 
 t-hash
 
 --------------D0B31FF0B77670F21EA67021
 Content-Type: text/plain; charset=UTF-8;
  name="x-linktrb.diff"
 Content-Transfer-Encoding: 7bit
 Content-Disposition: attachment;
  filename="x-linktrb.diff"
 
 --- sys/dev/usb/xhci.c.orig	2016-07-18 07:07:53.000000000 +0900
 +++ sys/dev/usb/xhci.c	2016-08-08 22:06:19.000000000 +0900
 @@ -2374,25 +2397,24 @@ xhci_ring_put(struct xhci_softc * const 
  	 * The code should write the 'cycle' bit on the link trb AFTER
  	 * adding the other trb.
  	 */
 -	if (ri + ntrbs >= (xr->xr_ntrb - 1)) {
 -		parameter = xhci_ring_trbp(xr, 0);
 -		status = 0;
 -		control = XHCI_TRB_3_TYPE_SET(XHCI_TRB_TYPE_LINK) |
 -		    XHCI_TRB_3_TC_BIT | (cs ? XHCI_TRB_3_CYCLE_BIT : 0);
 -		xhci_trb_put(&xr->xr_trb[ri], parameter, status, control);
 -		usb_syncmem(&xr->xr_dma, XHCI_TRB_SIZE * ri, XHCI_TRB_SIZE * 1,
 -		    BUS_DMASYNC_PREWRITE);
 -		xr->xr_cookies[ri] = NULL;
 -		xr->xr_ep = 0;
 -		xr->xr_cs ^= 1;
 -		ri = xr->xr_ep;
 -		cs = xr->xr_cs;
 -	}
 -
 -	ri++;
 +	for (i = 0; i < ntrbs; ) {
 +		if (ri >= (xr->xr_ntrb - 1)) {
 +			parameter = xhci_ring_trbp(xr, 0);
 +			status = 0;
 +			control = XHCI_TRB_3_TYPE_SET(XHCI_TRB_TYPE_LINK) |
 +			    XHCI_TRB_3_TC_BIT | (cs ? XHCI_TRB_3_CYCLE_BIT : 0);
 +			xhci_trb_put(&xr->xr_trb[ri], parameter, status,
 +			    control);
 +			usb_syncmem(&xr->xr_dma, XHCI_TRB_SIZE * ri,
 +			    XHCI_TRB_SIZE * 1, BUS_DMASYNC_PREWRITE);
 +			xr->xr_cookies[ri] = NULL;
 +			xr->xr_ep = 0;
 +			xr->xr_cs ^= 1;
 +			ri = xr->xr_ep;
 +			cs = xr->xr_cs;
 +			continue;
 +		}
  
 -	/* Write any subsequent TRB first */
 -	for (i = 1; i < ntrbs; i++) {
  		parameter = trbs[i].trb_0;
  		status = trbs[i].trb_2;
  		control = trbs[i].trb_3;
 @@ -2408,25 +2430,9 @@ xhci_ring_put(struct xhci_softc * const 
  		    BUS_DMASYNC_PREWRITE);
  		xr->xr_cookies[ri] = cookie;
  		ri++;
 +		i++;
  	}
  
 -	/* Write the first TRB last */
 -	i = 0;
 -	parameter = trbs[i].trb_0;
 -	status = trbs[i].trb_2;
 -	control = trbs[i].trb_3;
 -
 -	if (xr->xr_cs) {
 -		control |= XHCI_TRB_3_CYCLE_BIT;
 -	} else {
 -		control &= ~XHCI_TRB_3_CYCLE_BIT;
 -	}
 -
 -	xhci_trb_put(&xr->xr_trb[xr->xr_ep], parameter, status, control);
 -	usb_syncmem(&xr->xr_dma, XHCI_TRB_SIZE * xr->xr_ep, XHCI_TRB_SIZE * 1,
 -	    BUS_DMASYNC_PREWRITE);
 -	xr->xr_cookies[xr->xr_ep] = cookie;
 -
  	xr->xr_ep = ri;
  	xr->xr_cs = cs;
  
 
 --------------D0B31FF0B77670F21EA67021--
 


Home | Main Index | Thread Index | Old Index