From sakichan@sakichan.org  Tue Oct 28 12:45:23 2003
Return-Path: <sakichan@sakichan.org>
Received: from mx1.FreeBSD.org (mx1.freebsd.org [216.136.204.125])
	by hub.freebsd.org (Postfix) with ESMTP id A1C8C16A4CE
	for <FreeBSD-gnats-submit@freebsd.org>; Tue, 28 Oct 2003 12:45:23 -0800 (PST)
Received: from deneb.buildkernel.org (deneb.buildkernel.org [219.117.195.152])
	by mx1.FreeBSD.org (Postfix) with ESMTP id 67F2C43F85
	for <FreeBSD-gnats-submit@freebsd.org>; Tue, 28 Oct 2003 12:45:22 -0800 (PST)
	(envelope-from sakichan@sakichan.org)
Received: from alioth.sakichan.org (alioth.sakichan.org [192.168.1.3])
	by deneb.buildkernel.org (Postfix) with ESMTP id 2E68C72503
	for <FreeBSD-gnats-submit@freebsd.org>; Wed, 29 Oct 2003 05:45:21 +0900 (JST)
Received: from castor.sakichan.org (castor.sakichan.org [192.168.1.4])
	by alioth.sakichan.org (Postfix) with ESMTP id EA2B431BF
	for <FreeBSD-gnats-submit@freebsd.org>; Wed, 29 Oct 2003 05:45:20 +0900 (JST)
Received: by castor.sakichan.org (Postfix, from userid 5408)
	id D1C3E22A6D; Wed, 29 Oct 2003 05:45:20 +0900 (JST)
Message-Id: <20031028204520.D1C3E22A6D@castor.sakichan.org>
Date: Wed, 29 Oct 2003 05:45:20 +0900 (JST)
From: SAKIYAMA Nobuo <sakichan@sakichan.org>
Reply-To: SAKIYAMA Nobuo <sakichan@sakichan.org>
To: FreeBSD-gnats-submit@freebsd.org
Cc:
Subject: [patch] USB CD-R writing patch
X-Send-Pr-Version: 3.113
X-GNATS-Notify:

>Number:         58649
>Category:       kern
>Synopsis:       [patch] USB CD-R writing patch
>Confidential:   no
>Severity:       serious
>Priority:       medium
>Responsible:    sanpei
>State:          closed
>Quarter:        
>Keywords:       
>Date-Required:  
>Class:          sw-bug
>Submitter-Id:   current-users
>Arrival-Date:   Tue Oct 28 12:50:14 PST 2003
>Closed-Date:    Sun Jan 18 01:21:42 PST 2004
>Last-Modified:  Sun Jan 18 01:21:42 PST 2004
>Originator:     SAKIYAMA Nobuo <sakichan@sakichan.org>
>Release:        FreeBSD 5.1-CURRENT i386
>Organization:
>Environment:
System: FreeBSD castor.sakichan.org 5.1-CURRENT FreeBSD 5.1-CURRENT #41: Wed Oct 29 04:24:21 JST 2003 root@castor.sakichan.org:/usr/obj/usr/src/sys/CASTOR i386


>Description:
	Problem 1. CD-R writing software such as cdrtools cannot write to ATAPI-based USB CD-R drives.
	Problem 2. CD-R writing software fails to fixate for USB CD-R drives.
>How-To-Repeat:
	Problem 1. install cdrtools port, and use cdrecord for ATAPI-based USB CD-R.
	Then you'll get several "Unsupported ATAPI command" errors from kernel and fail.
	Problem 2. use cdrecord for USB CD-R. Then, you'll get "BBB reset failed, TIMEOUT"
	from the umass device and fail to fixate.
>Fix:
	Problem 1. is because umass_atapi_transform() does not pass ATAPI MMC commands.
	Problem 2. is because timeout for wire transfer is not properly set.

	Below is a patch for both problems. The part of the timeout fix is very similar to
	the code of NetBSD-current. I've tested the patch with TEAC CD-W28E.

--- umass_cdr_writing.patch begins here ---
Index: sys/dev/usb/umass.c
===================================================================
RCS file: /home/ncvs/src/sys/dev/usb/umass.c,v
retrieving revision 1.91
diff -u -r1.91 umass.c
--- sys/dev/usb/umass.c	20 Sep 2003 08:18:16 -0000	1.91
+++ sys/dev/usb/umass.c	28 Oct 2003 19:10:06 -0000
@@ -241,7 +241,7 @@
 typedef void (*wire_reset_f)	(struct umass_softc *sc, int status);
 typedef void (*wire_transfer_f)	(struct umass_softc *sc, int lun,
 				void *cmd, int cmdlen, void *data, int datalen,
-				int dir, transfer_cb_f cb, void *priv);
+				int dir, u_int timeout, transfer_cb_f cb, void *priv);
 typedef void (*wire_state_f)	(usbd_xfer_handle xfer,
 				usbd_private_handle priv, usbd_status err);
 
@@ -507,6 +507,8 @@
 	struct scsi_sense	cam_scsi_sense;
 	struct scsi_sense	cam_scsi_test_unit_ready;
 
+	int			timeout;		/* in msecs */
+
 	int			maxlun;			/* maximum LUN number */
 };
 
@@ -571,7 +573,7 @@
 Static void umass_bbb_reset	(struct umass_softc *sc, int status);
 Static void umass_bbb_transfer	(struct umass_softc *sc, int lun,
 				void *cmd, int cmdlen,
-		    		void *data, int datalen, int dir,
+		    		void *data, int datalen, int dir, u_int timeout,
 				transfer_cb_f cb, void *priv);
 Static void umass_bbb_state	(usbd_xfer_handle xfer,
 				usbd_private_handle priv,
@@ -586,7 +588,7 @@
 Static void umass_cbi_reset	(struct umass_softc *sc, int status);
 Static void umass_cbi_transfer	(struct umass_softc *sc, int lun,
 				void *cmd, int cmdlen,
-		    		void *data, int datalen, int dir,
+		    		void *data, int datalen, int dir, u_int timeout,
 				transfer_cb_f cb, void *priv);
 Static void umass_cbi_state	(usbd_xfer_handle xfer,
 				usbd_private_handle priv, usbd_status err);
@@ -1105,7 +1107,7 @@
 	/* Initialiase a USB transfer and then schedule it */
 
 	(void) usbd_setup_xfer(xfer, pipe, (void *) sc, buffer, buflen, flags,
-			UMASS_TIMEOUT, sc->state);
+			sc->timeout, sc->state);
 
 	err = usbd_transfer(xfer);
 	if (err && err != USBD_IN_PROGRESS) {
@@ -1129,7 +1131,7 @@
 	/* Initialiase a USB control transfer and then schedule it */
 
 	(void) usbd_setup_default_xfer(xfer, udev, (void *) sc,
-			UMASS_TIMEOUT, req, buffer, buflen, flags, sc->state);
+			sc->timeout, req, buffer, buflen, flags, sc->state);
 
 	err = usbd_transfer(xfer);
 	if (err && err != USBD_IN_PROGRESS) {
@@ -1226,13 +1228,16 @@
 
 Static void
 umass_bbb_transfer(struct umass_softc *sc, int lun, void *cmd, int cmdlen,
-		    void *data, int datalen, int dir,
+		    void *data, int datalen, int dir, u_int timeout,
 		    transfer_cb_f cb, void *priv)
 {
 	KASSERT(sc->proto & UMASS_PROTO_BBB,
 		("%s: umass_bbb_transfer: wrong sc->proto 0x%02x\n",
 			USBDEVNAME(sc->sc_dev), sc->proto));
 
+	/* Be a little generous. */
+	sc->timeout = timeout + UMASS_TIMEOUT;
+
 	/*
 	 * Do a Bulk-Only transfer with cmdlen bytes from cmd, possibly
 	 * a data phase of datalen bytes from/to the device and finally a
@@ -1739,12 +1744,15 @@
 Static void
 umass_cbi_transfer(struct umass_softc *sc, int lun,
 		void *cmd, int cmdlen, void *data, int datalen, int dir,
-		transfer_cb_f cb, void *priv)
+		u_int timeout, transfer_cb_f cb, void *priv)
 {
 	KASSERT(sc->proto & (UMASS_PROTO_CBI|UMASS_PROTO_CBI_I),
 		("%s: umass_cbi_transfer: wrong sc->proto 0x%02x\n",
 			USBDEVNAME(sc->sc_dev), sc->proto));
 
+	/* Be a little generous. */
+	sc->timeout = timeout + UMASS_TIMEOUT;
+
 	/*
 	 * Do a CBI transfer with cmdlen bytes from cmd, possibly
 	 * a data phase of datalen bytes from/to the device and finally a
@@ -2371,7 +2379,7 @@
 			}
 			sc->transfer(sc, ccb->ccb_h.target_lun, rcmd, rcmdlen,
 				     csio->data_ptr,
-				     csio->dxfer_len, dir,
+				     csio->dxfer_len, dir, ccb->ccb_h.timeout,
 				     umass_cam_cb, (void *) ccb);
 		} else {
 			ccb->ccb_h.status = CAM_REQ_INVALID;
@@ -2549,7 +2557,7 @@
 				sc->transfer(sc, ccb->ccb_h.target_lun,
 					     rcmd, rcmdlen,
 					     &csio->sense_data,
-					     csio->sense_len, DIR_IN,
+					     csio->sense_len, DIR_IN, ccb->ccb_h.timeout,
 					     umass_cam_sense_cb, (void *) ccb);
 			} else {
 				panic("transform(REQUEST_SENSE) failed");
@@ -2649,7 +2657,7 @@
 					&rcmd, &rcmdlen)) {
 				sc->transfer(sc, ccb->ccb_h.target_lun,
 					     rcmd, rcmdlen,
-					     NULL, 0, DIR_NONE,
+					     NULL, 0, DIR_NONE, ccb->ccb_h.timeout,
 					     umass_cam_quirk_cb, (void *) ccb);
 			} else {
 				panic("transform(TEST_UNIT_READY) failed");
@@ -2891,6 +2899,22 @@
 	case SYNCHRONIZE_CACHE:
 	case MODE_SELECT_10:
 	case MODE_SENSE_10:
+	case READ_BUFFER:
+	case 0x42: /* READ_SUBCHANNEL */
+	case 0x43: /* READ_TOC */
+	case 0x44: /* READ_HEADER */
+	case 0x51: /* READ_DISK_INFO */
+	case 0x52: /* READ_TRACK_INFO */
+	case 0x54: /* SEND_OPC */
+	case 0x59: /* READ_MASTER_CUE */
+	case 0x5b: /* CLOSE_TR_SESSION */
+	case 0x5c: /* READ_BUFFER_CAP */
+	case 0x5d: /* SEND_CUE_SHEET */
+	case 0xa6: /* EXCHANGE_MEDIUM */
+	case 0xbb: /* SET_CD_SPEED */
+	case 0xad: /* READ_DVD_STRUCTURE */
+	case 0xa1: /* BLANK */
+	case 0xe5: /* READ_TRACK_INFO_PHILIPS */
 		memcpy(*rcmd, cmd, cmdlen);
 		return 1;
 
--- umass_cdr_writing.patch ends here ---


>Release-Note:
>Audit-Trail:
Responsible-Changed-From-To: freebsd-bugs->joe 
Responsible-Changed-By: kris 
Responsible-Changed-When: Thu Oct 30 01:12:19 PST 2003 
Responsible-Changed-Why:  
Assign to USB maintainer 

http://www.freebsd.org/cgi/query-pr.cgi?pr=58649 
State-Changed-From-To: open->analyzed 
State-Changed-By: sanpei 
State-Changed-When: Sat Jan 3 05:31:31 PST 2004 
State-Changed-Why:  
Problem 1. (umass_atapi_transform() does not pass ATAPI MMC commands.) 
was committed. 
Problem 2. (timeout for wire transfer is not properly set) is 
need to sysctl or device specific quirk, I think. 


Responsible-Changed-From-To: joe->sanpei 
Responsible-Changed-By: sanpei 
Responsible-Changed-When: Sat Jan 3 05:31:31 PST 2004 
Responsible-Changed-Why:  
Problem 1. (umass_atapi_transform() does not pass ATAPI MMC commands.) 
was committed. 
Problem 2. (timeout for wire transfer is not properly set) is 
need to sysctl or device specific quirk, I think. 

http://www.freebsd.org/cgi/query-pr.cgi?pr=58649 
State-Changed-From-To: analyzed->closed 
State-Changed-By: sanpei 
State-Changed-When: Sun Jan 18 01:20:30 PST 2004 
State-Changed-Why:  
Commited Problem 2, umass.c rev. 1.99, thanks. 

http://www.freebsd.org/cgi/query-pr.cgi?pr=58649 
>Unformatted:
