xref: /dragonfly/sys/bus/u4b/storage/ustorage_fs.c (revision 2b3f93ea)
1 /* $FreeBSD$ */
2 /*-
3  * Copyright (C) 2003-2005 Alan Stern
4  * Copyright (C) 2008 Hans Petter Selasky
5  * All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  * 1. Redistributions of source code must retain the above copyright
11  *    notice, this list of conditions, and the following disclaimer,
12  *    without modification.
13  * 2. Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in the
15  *    documentation and/or other materials provided with the distribution.
16  * 3. The names of the above-listed copyright holders may not be used
17  *    to endorse or promote products derived from this software without
18  *    specific prior written permission.
19  *
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
22  * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
23  * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
24  * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
25  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
26  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
27  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
28  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
29  * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
30  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
31  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32  */
33 
34 /*
35  * NOTE: Much of the SCSI statemachine handling code derives from the
36  * Linux USB gadget stack.
37  */
38 
39 #include <sys/stdint.h>
40 #include <sys/param.h>
41 #include <sys/queue.h>
42 #include <sys/types.h>
43 #include <sys/systm.h>
44 #include <sys/kernel.h>
45 #include <sys/bus.h>
46 #include <sys/module.h>
47 #include <sys/lock.h>
48 #include <sys/condvar.h>
49 #include <sys/sysctl.h>
50 #include <sys/unistd.h>
51 #include <sys/callout.h>
52 #include <sys/malloc.h>
53 #include <sys/caps.h>
54 
55 #include <bus/u4b/usb.h>
56 #include <bus/u4b/usbdi.h>
57 #include "usbdevs.h"
58 #include "usb_if.h"
59 
60 #define	USB_DEBUG_VAR ustorage_fs_debug
61 #include <bus/u4b/usb_debug.h>
62 
63 #ifdef USB_DEBUG
64 static int ustorage_fs_debug = 0;
65 
66 SYSCTL_NODE(_hw_usb, OID_AUTO, ustorage_fs, CTLFLAG_RW, 0, "USB ustorage_fs");
67 SYSCTL_INT(_hw_usb_ustorage_fs, OID_AUTO, debug, CTLFLAG_RW,
68     &ustorage_fs_debug, 0, "ustorage_fs debug level");
69 #endif
70 
71 /* Define some limits */
72 
73 #ifndef USTORAGE_FS_BULK_SIZE
74 #define	USTORAGE_FS_BULK_SIZE (1UL << 17)	/* bytes */
75 #endif
76 
77 #ifndef	USTORAGE_FS_MAX_LUN
78 #define	USTORAGE_FS_MAX_LUN	8	/* units */
79 #endif
80 
81 #ifndef USTORAGE_QDATA_MAX
82 #define	USTORAGE_QDATA_MAX	40	/* bytes */
83 #endif
84 
85 #define sc_cmd_data sc_cbw.CBWCDB
86 
87 /*
88  * The SCSI ID string must be exactly 28 characters long
89  * exluding the terminating zero.
90  */
91 #ifndef USTORAGE_FS_ID_STRING
92 #define	USTORAGE_FS_ID_STRING \
93 	"FreeBSD " /* 8 */ \
94 	"File-Stor Gadget" /* 16 */ \
95 	"0101" /* 4 */
96 #endif
97 
98 /*
99  * The following macro defines the number of
100  * sectors to be allocated for the RAM disk:
101  */
102 #ifndef USTORAGE_FS_RAM_SECT
103 #define	USTORAGE_FS_RAM_SECT (1UL << 13)
104 #endif
105 
106 static uint8_t *ustorage_fs_ramdisk;
107 
108 /* USB transfer definitions */
109 
110 #define	USTORAGE_FS_T_BBB_COMMAND     0
111 #define	USTORAGE_FS_T_BBB_DATA_DUMP   1
112 #define	USTORAGE_FS_T_BBB_DATA_READ   2
113 #define	USTORAGE_FS_T_BBB_DATA_WRITE  3
114 #define	USTORAGE_FS_T_BBB_STATUS      4
115 #define	USTORAGE_FS_T_BBB_MAX         5
116 
117 /* USB data stage direction */
118 
119 #define	DIR_NONE	0
120 #define	DIR_READ	1
121 #define	DIR_WRITE	2
122 
123 /* USB interface specific control request */
124 
125 #define	UR_BBB_RESET		0xff	/* Bulk-Only reset */
126 #define	UR_BBB_GET_MAX_LUN	0xfe	/* Get maximum lun */
127 
128 /* Command Block Wrapper */
129 typedef struct {
130 	uDWord	dCBWSignature;
131 #define	CBWSIGNATURE	0x43425355
132 	uDWord	dCBWTag;
133 	uDWord	dCBWDataTransferLength;
134 	uByte	bCBWFlags;
135 #define	CBWFLAGS_OUT	0x00
136 #define	CBWFLAGS_IN	0x80
137 	uByte	bCBWLUN;
138 	uByte	bCDBLength;
139 #define	CBWCDBLENGTH	16
140 	uByte	CBWCDB[CBWCDBLENGTH];
141 } __packed ustorage_fs_bbb_cbw_t;
142 
143 #define	USTORAGE_FS_BBB_CBW_SIZE	31
144 
145 /* Command Status Wrapper */
146 typedef struct {
147 	uDWord	dCSWSignature;
148 #define	CSWSIGNATURE	0x53425355
149 	uDWord	dCSWTag;
150 	uDWord	dCSWDataResidue;
151 	uByte	bCSWStatus;
152 #define	CSWSTATUS_GOOD	0x0
153 #define	CSWSTATUS_FAILED	0x1
154 #define	CSWSTATUS_PHASE	0x2
155 } __packed ustorage_fs_bbb_csw_t;
156 
157 #define	USTORAGE_FS_BBB_CSW_SIZE	13
158 
159 struct ustorage_fs_lun {
160 
161 	uint8_t	*memory_image;
162 
163 	uint32_t num_sectors;
164 	uint32_t sense_data;
165 	uint32_t sense_data_info;
166 	uint32_t unit_attention_data;
167 
168 	uint8_t	read_only:1;
169 	uint8_t	prevent_medium_removal:1;
170 	uint8_t	info_valid:1;
171 	uint8_t	removable:1;
172 };
173 
174 struct ustorage_fs_softc {
175 
176 	ustorage_fs_bbb_cbw_t *sc_cbw;	/* Command Wrapper Block */
177 	ustorage_fs_bbb_csw_t *sc_csw;	/* Command Status Block */
178 	void *sc_dma_ptr;		/* Main data buffer */
179 
180 	struct lock sc_lock;
181 
182 	struct ustorage_fs_lun sc_lun[USTORAGE_FS_MAX_LUN];
183 
184 	struct {
185 		uint8_t *data_ptr;
186 		struct ustorage_fs_lun *currlun;
187 
188 		uint32_t data_rem;	/* bytes, as reported by the command
189 					 * block wrapper */
190 		uint32_t offset;	/* bytes */
191 
192 		uint8_t	cbw_dir;
193 		uint8_t	cmd_dir;
194 		uint8_t	lun;
195 		uint8_t	cmd_len;
196 		uint8_t	data_short:1;
197 		uint8_t	data_error:1;
198 	}	sc_transfer;
199 
200 	device_t sc_dev;
201 	struct usb_device *sc_udev;
202 	struct usb_xfer *sc_xfer[USTORAGE_FS_T_BBB_MAX];
203 
204 	uint8_t	sc_iface_no;		/* interface number */
205 	uint8_t	sc_last_lun;
206 	uint8_t	sc_last_xfer_index;
207 	uint8_t	sc_qdata[USTORAGE_QDATA_MAX];
208 };
209 
210 /* prototypes */
211 
212 static device_probe_t ustorage_fs_probe;
213 static device_attach_t ustorage_fs_attach;
214 static device_detach_t ustorage_fs_detach;
215 static device_suspend_t ustorage_fs_suspend;
216 static device_resume_t ustorage_fs_resume;
217 static usb_handle_request_t ustorage_fs_handle_request;
218 
219 static usb_callback_t ustorage_fs_t_bbb_command_callback;
220 static usb_callback_t ustorage_fs_t_bbb_data_dump_callback;
221 static usb_callback_t ustorage_fs_t_bbb_data_read_callback;
222 static usb_callback_t ustorage_fs_t_bbb_data_write_callback;
223 static usb_callback_t ustorage_fs_t_bbb_status_callback;
224 
225 static void ustorage_fs_transfer_start(struct ustorage_fs_softc *sc, uint8_t xfer_index);
226 static void ustorage_fs_transfer_stop(struct ustorage_fs_softc *sc);
227 
228 static uint8_t ustorage_fs_verify(struct ustorage_fs_softc *sc);
229 static uint8_t ustorage_fs_inquiry(struct ustorage_fs_softc *sc);
230 static uint8_t ustorage_fs_request_sense(struct ustorage_fs_softc *sc);
231 static uint8_t ustorage_fs_read_capacity(struct ustorage_fs_softc *sc);
232 static uint8_t ustorage_fs_mode_sense(struct ustorage_fs_softc *sc);
233 static uint8_t ustorage_fs_start_stop(struct ustorage_fs_softc *sc);
234 static uint8_t ustorage_fs_prevent_allow(struct ustorage_fs_softc *sc);
235 static uint8_t ustorage_fs_read_format_capacities(struct ustorage_fs_softc *sc);
236 static uint8_t ustorage_fs_mode_select(struct ustorage_fs_softc *sc);
237 static uint8_t ustorage_fs_min_len(struct ustorage_fs_softc *sc, uint32_t len, uint32_t mask);
238 static uint8_t ustorage_fs_read(struct ustorage_fs_softc *sc);
239 static uint8_t ustorage_fs_write(struct ustorage_fs_softc *sc);
240 static uint8_t ustorage_fs_check_cmd(struct ustorage_fs_softc *sc, uint8_t cmd_size, uint16_t mask, uint8_t needs_medium);
241 static uint8_t ustorage_fs_do_cmd(struct ustorage_fs_softc *sc);
242 
243 static device_method_t ustorage_fs_methods[] = {
244 	/* USB interface */
245 	DEVMETHOD(usb_handle_request, ustorage_fs_handle_request),
246 
247 	/* Device interface */
248 	DEVMETHOD(device_probe, ustorage_fs_probe),
249 	DEVMETHOD(device_attach, ustorage_fs_attach),
250 	DEVMETHOD(device_detach, ustorage_fs_detach),
251 	DEVMETHOD(device_suspend, ustorage_fs_suspend),
252 	DEVMETHOD(device_resume, ustorage_fs_resume),
253 
254 	DEVMETHOD_END
255 };
256 
257 static driver_t ustorage_fs_driver = {
258 	.name = "ustorage_fs",
259 	.methods = ustorage_fs_methods,
260 	.size = sizeof(struct ustorage_fs_softc),
261 };
262 
263 static devclass_t ustorage_fs_devclass;
264 
265 DRIVER_MODULE(ustorage_fs, uhub, ustorage_fs_driver, ustorage_fs_devclass, NULL, NULL);
266 MODULE_VERSION(ustorage_fs, 0);
267 MODULE_DEPEND(ustorage_fs, usb, 1, 1, 1);
268 
269 static struct usb_config ustorage_fs_bbb_config[USTORAGE_FS_T_BBB_MAX] = {
270 
271 	[USTORAGE_FS_T_BBB_COMMAND] = {
272 		.type = UE_BULK,
273 		.endpoint = UE_ADDR_ANY,
274 		.direction = UE_DIR_OUT,
275 		.bufsize = sizeof(ustorage_fs_bbb_cbw_t),
276 		.callback = &ustorage_fs_t_bbb_command_callback,
277 		.usb_mode = USB_MODE_DEVICE,
278 	},
279 
280 	[USTORAGE_FS_T_BBB_DATA_DUMP] = {
281 		.type = UE_BULK,
282 		.endpoint = UE_ADDR_ANY,
283 		.direction = UE_DIR_OUT,
284 		.bufsize = 0,	/* use wMaxPacketSize */
285 		.flags = {.proxy_buffer = 1,.short_xfer_ok = 1,},
286 		.callback = &ustorage_fs_t_bbb_data_dump_callback,
287 		.usb_mode = USB_MODE_DEVICE,
288 	},
289 
290 	[USTORAGE_FS_T_BBB_DATA_READ] = {
291 		.type = UE_BULK,
292 		.endpoint = UE_ADDR_ANY,
293 		.direction = UE_DIR_OUT,
294 		.bufsize = USTORAGE_FS_BULK_SIZE,
295 		.flags = {.proxy_buffer = 1,.short_xfer_ok = 1},
296 		.callback = &ustorage_fs_t_bbb_data_read_callback,
297 		.usb_mode = USB_MODE_DEVICE,
298 	},
299 
300 	[USTORAGE_FS_T_BBB_DATA_WRITE] = {
301 		.type = UE_BULK,
302 		.endpoint = UE_ADDR_ANY,
303 		.direction = UE_DIR_IN,
304 		.bufsize = USTORAGE_FS_BULK_SIZE,
305 		.flags = {.proxy_buffer = 1,.short_xfer_ok = 1,.ext_buffer = 1},
306 		.callback = &ustorage_fs_t_bbb_data_write_callback,
307 		.usb_mode = USB_MODE_DEVICE,
308 	},
309 
310 	[USTORAGE_FS_T_BBB_STATUS] = {
311 		.type = UE_BULK,
312 		.endpoint = UE_ADDR_ANY,
313 		.direction = UE_DIR_IN,
314 		.bufsize = sizeof(ustorage_fs_bbb_csw_t),
315 		.flags = {.short_xfer_ok = 1},
316 		.callback = &ustorage_fs_t_bbb_status_callback,
317 		.usb_mode = USB_MODE_DEVICE,
318 	},
319 };
320 
321 /*
322  * USB device probe/attach/detach
323  */
324 
325 static int
ustorage_fs_probe(device_t dev)326 ustorage_fs_probe(device_t dev)
327 {
328 	struct usb_attach_arg *uaa = device_get_ivars(dev);
329 	struct usb_interface_descriptor *id;
330 
331 	if (uaa->usb_mode != USB_MODE_DEVICE) {
332 		return (ENXIO);
333 	}
334 	/* Check for a standards compliant device */
335 	id = usbd_get_interface_descriptor(uaa->iface);
336 	if ((id == NULL) ||
337 	    (id->bInterfaceClass != UICLASS_MASS) ||
338 	    (id->bInterfaceSubClass != UISUBCLASS_SCSI) ||
339 	    (id->bInterfaceProtocol != UIPROTO_MASS_BBB)) {
340 		return (ENXIO);
341 	}
342 	return (BUS_PROBE_GENERIC);
343 }
344 
345 static int
ustorage_fs_attach(device_t dev)346 ustorage_fs_attach(device_t dev)
347 {
348 	struct ustorage_fs_softc *sc = device_get_softc(dev);
349 	struct usb_attach_arg *uaa = device_get_ivars(dev);
350 	struct usb_interface_descriptor *id;
351 	int err;
352 	int unit;
353 
354 	/*
355 	 * NOTE: the softc struct is cleared in device_set_driver.
356 	 * We can safely call ustorage_fs_detach without specifically
357 	 * initializing the struct.
358 	 */
359 
360 	sc->sc_dev = dev;
361 	sc->sc_udev = uaa->device;
362 	unit = device_get_unit(dev);
363 
364 	/* enable power saving mode */
365 	usbd_set_power_mode(uaa->device, USB_POWER_MODE_SAVE);
366 
367 	if (unit == 0) {
368 		if (ustorage_fs_ramdisk == NULL) {
369 			/*
370 			 * allocate a memory image for our ramdisk until
371 			 * further
372 			 */
373 			ustorage_fs_ramdisk =
374 			    kmalloc(USTORAGE_FS_RAM_SECT << 9, M_USB,
375 			    M_ZERO | M_WAITOK);
376 
377 			if (ustorage_fs_ramdisk == NULL) {
378 				return (ENOMEM);
379 			}
380 		}
381 		sc->sc_lun[0].memory_image = ustorage_fs_ramdisk;
382 		sc->sc_lun[0].num_sectors = USTORAGE_FS_RAM_SECT;
383 		sc->sc_lun[0].removable = 1;
384 	}
385 
386 	device_set_usb_desc(dev);
387 
388 	lockinit(&sc->sc_lock, "USTORAGE_FS lock", 0, LK_CANRECURSE);
389 
390 	/* get interface index */
391 
392 	id = usbd_get_interface_descriptor(uaa->iface);
393 	if (id == NULL) {
394 		device_printf(dev, "failed to get "
395 		    "interface number\n");
396 		goto detach;
397 	}
398 	sc->sc_iface_no = id->bInterfaceNumber;
399 
400 	err = usbd_transfer_setup(uaa->device,
401 	    &uaa->info.bIfaceIndex, sc->sc_xfer, ustorage_fs_bbb_config,
402 	    USTORAGE_FS_T_BBB_MAX, sc, &sc->sc_lock);
403 	if (err) {
404 		device_printf(dev, "could not setup required "
405 		    "transfers, %s\n", usbd_errstr(err));
406 		goto detach;
407 	}
408 
409 	sc->sc_cbw = usbd_xfer_get_frame_buffer(sc->sc_xfer[
410 	    USTORAGE_FS_T_BBB_COMMAND], 0);
411 	sc->sc_csw = usbd_xfer_get_frame_buffer(sc->sc_xfer[
412 	    USTORAGE_FS_T_BBB_STATUS], 0);
413  	sc->sc_dma_ptr = usbd_xfer_get_frame_buffer(sc->sc_xfer[
414 	    USTORAGE_FS_T_BBB_DATA_READ], 0);
415 
416 	/* start Mass Storage State Machine */
417 
418 	lockmgr(&sc->sc_lock, LK_EXCLUSIVE);
419 	ustorage_fs_transfer_start(sc, USTORAGE_FS_T_BBB_COMMAND);
420 	lockmgr(&sc->sc_lock, LK_RELEASE);
421 
422 	return (0);			/* success */
423 
424 detach:
425 	ustorage_fs_detach(dev);
426 	return (ENXIO);			/* failure */
427 }
428 
429 static int
ustorage_fs_detach(device_t dev)430 ustorage_fs_detach(device_t dev)
431 {
432 	struct ustorage_fs_softc *sc = device_get_softc(dev);
433 
434 	/* teardown our statemachine */
435 
436 	usbd_transfer_unsetup(sc->sc_xfer, USTORAGE_FS_T_BBB_MAX);
437 
438 	lockuninit(&sc->sc_lock);
439 
440 	return (0);			/* success */
441 }
442 
443 static int
ustorage_fs_suspend(device_t dev)444 ustorage_fs_suspend(device_t dev)
445 {
446 	device_printf(dev, "suspending\n");
447 	return (0);			/* success */
448 }
449 
450 static int
ustorage_fs_resume(device_t dev)451 ustorage_fs_resume(device_t dev)
452 {
453 	device_printf(dev, "resuming\n");
454 	return (0);			/* success */
455 }
456 
457 /*
458  * Generic functions to handle transfers
459  */
460 
461 static void
ustorage_fs_transfer_start(struct ustorage_fs_softc * sc,uint8_t xfer_index)462 ustorage_fs_transfer_start(struct ustorage_fs_softc *sc, uint8_t xfer_index)
463 {
464 	if (sc->sc_xfer[xfer_index]) {
465 		sc->sc_last_xfer_index = xfer_index;
466 		usbd_transfer_start(sc->sc_xfer[xfer_index]);
467 	}
468 }
469 
470 static void
ustorage_fs_transfer_stop(struct ustorage_fs_softc * sc)471 ustorage_fs_transfer_stop(struct ustorage_fs_softc *sc)
472 {
473 	usbd_transfer_stop(sc->sc_xfer[sc->sc_last_xfer_index]);
474 	lockmgr(&sc->sc_lock, LK_RELEASE);
475 	usbd_transfer_drain(sc->sc_xfer[sc->sc_last_xfer_index]);
476 	lockmgr(&sc->sc_lock, LK_EXCLUSIVE);
477 }
478 
479 static int
ustorage_fs_handle_request(device_t dev,const void * preq,void ** pptr,uint16_t * plen,uint16_t offset,uint8_t * pstate)480 ustorage_fs_handle_request(device_t dev,
481     const void *preq, void **pptr, uint16_t *plen,
482     uint16_t offset, uint8_t *pstate)
483 {
484 	struct ustorage_fs_softc *sc = device_get_softc(dev);
485 	const struct usb_device_request *req = preq;
486 	uint8_t is_complete = *pstate;
487 
488 	if (!is_complete) {
489 		if ((req->bmRequestType == UT_WRITE_CLASS_INTERFACE) &&
490 		    (req->bRequest == UR_BBB_RESET)) {
491 			*plen = 0;
492 			lockmgr(&sc->sc_lock, LK_EXCLUSIVE);
493 			ustorage_fs_transfer_stop(sc);
494 			sc->sc_transfer.data_error = 1;
495 			ustorage_fs_transfer_start(sc,
496 			    USTORAGE_FS_T_BBB_COMMAND);
497 			lockmgr(&sc->sc_lock, LK_RELEASE);
498 			return (0);
499 		} else if ((req->bmRequestType == UT_READ_CLASS_INTERFACE) &&
500 			   (req->bRequest == UR_BBB_GET_MAX_LUN)) {
501 			if (offset == 0) {
502 				*plen = 1;
503 				*pptr = &sc->sc_last_lun;
504 			} else {
505 				*plen = 0;
506 			}
507 			return (0);
508 		}
509 	}
510 	return (ENXIO);			/* use builtin handler */
511 }
512 
513 static void
ustorage_fs_t_bbb_command_callback(struct usb_xfer * xfer,usb_error_t error)514 ustorage_fs_t_bbb_command_callback(struct usb_xfer *xfer, usb_error_t error)
515 {
516 	struct ustorage_fs_softc *sc = usbd_xfer_softc(xfer);
517 	uint32_t tag;
518 	uint8_t err = 0;
519 
520 	DPRINTF("\n");
521 
522 	switch (USB_GET_STATE(xfer)) {
523 	case USB_ST_TRANSFERRED:
524 
525 		tag = UGETDW(sc->sc_cbw->dCBWSignature);
526 
527 		if (tag != CBWSIGNATURE) {
528 			/* do nothing */
529 			DPRINTF("invalid signature 0x%08x\n", tag);
530 			break;
531 		}
532 		tag = UGETDW(sc->sc_cbw->dCBWTag);
533 
534 		/* echo back tag */
535 		USETDW(sc->sc_csw->dCSWTag, tag);
536 
537 		/* reset status */
538 		sc->sc_csw->bCSWStatus = 0;
539 
540 		/* reset data offset, data length and data remainder */
541 		sc->sc_transfer.offset = 0;
542 		sc->sc_transfer.data_rem =
543 		    UGETDW(sc->sc_cbw->dCBWDataTransferLength);
544 
545 		/* reset data flags */
546 		sc->sc_transfer.data_short = 0;
547 
548 		/* extract LUN */
549 		sc->sc_transfer.lun = sc->sc_cbw->bCBWLUN;
550 
551 		if (sc->sc_transfer.data_rem == 0) {
552 			sc->sc_transfer.cbw_dir = DIR_NONE;
553 		} else {
554 			if (sc->sc_cbw->bCBWFlags & CBWFLAGS_IN) {
555 				sc->sc_transfer.cbw_dir = DIR_WRITE;
556 			} else {
557 				sc->sc_transfer.cbw_dir = DIR_READ;
558 			}
559 		}
560 
561 		sc->sc_transfer.cmd_len = sc->sc_cbw->bCDBLength;
562 		if ((sc->sc_transfer.cmd_len > sizeof(sc->sc_cbw->CBWCDB)) ||
563 		    (sc->sc_transfer.cmd_len == 0)) {
564 			/* just halt - this is invalid */
565 			DPRINTF("invalid command length %d bytes\n",
566 			    sc->sc_transfer.cmd_len);
567 			break;
568 		}
569 
570 		err = ustorage_fs_do_cmd(sc);
571 		if (err) {
572 			/* got an error */
573 			DPRINTF("command failed\n");
574 			break;
575 		}
576 		if ((sc->sc_transfer.data_rem > 0) &&
577 		    (sc->sc_transfer.cbw_dir != sc->sc_transfer.cmd_dir)) {
578 			/* contradicting data transfer direction */
579 			err = 1;
580 			DPRINTF("data direction mismatch\n");
581 			break;
582 		}
583 		switch (sc->sc_transfer.cbw_dir) {
584 		case DIR_READ:
585 			ustorage_fs_transfer_start(sc, USTORAGE_FS_T_BBB_DATA_READ);
586 			break;
587 		case DIR_WRITE:
588 			ustorage_fs_transfer_start(sc, USTORAGE_FS_T_BBB_DATA_WRITE);
589 			break;
590 		default:
591 			ustorage_fs_transfer_start(sc,
592 			    USTORAGE_FS_T_BBB_STATUS);
593 			break;
594 		}
595 		break;
596 
597 	case USB_ST_SETUP:
598 tr_setup:
599 		if (sc->sc_transfer.data_error) {
600 			sc->sc_transfer.data_error = 0;
601 			usbd_xfer_set_stall(xfer);
602 			DPRINTF("stall pipe\n");
603 		}
604 		usbd_xfer_set_frame_len(xfer, 0,
605 		    sizeof(ustorage_fs_bbb_cbw_t));
606 		usbd_transfer_submit(xfer);
607 		break;
608 
609 	default:			/* Error */
610 		DPRINTF("error\n");
611 		if (error == USB_ERR_CANCELLED) {
612 			break;
613 		}
614 		/* If the pipe is already stalled, don't do another stall */
615 		if (!usbd_xfer_is_stalled(xfer))
616 			sc->sc_transfer.data_error = 1;
617 
618 		/* try again */
619 		goto tr_setup;
620 	}
621 	if (err) {
622 		if (sc->sc_csw->bCSWStatus == 0) {
623 			/* set some default error code */
624 			sc->sc_csw->bCSWStatus = CSWSTATUS_FAILED;
625 		}
626 		if (sc->sc_transfer.cbw_dir == DIR_READ) {
627 			/* dump all data */
628 			ustorage_fs_transfer_start(sc,
629 			    USTORAGE_FS_T_BBB_DATA_DUMP);
630 			return;
631 		}
632 		if (sc->sc_transfer.cbw_dir == DIR_WRITE) {
633 			/* need to stall before status */
634 			sc->sc_transfer.data_error = 1;
635 		}
636 		ustorage_fs_transfer_start(sc, USTORAGE_FS_T_BBB_STATUS);
637 	}
638 }
639 
640 static void
ustorage_fs_t_bbb_data_dump_callback(struct usb_xfer * xfer,usb_error_t error)641 ustorage_fs_t_bbb_data_dump_callback(struct usb_xfer *xfer, usb_error_t error)
642 {
643 	struct ustorage_fs_softc *sc = usbd_xfer_softc(xfer);
644 	uint32_t max_bulk = usbd_xfer_max_len(xfer);
645 	int actlen, sumlen;
646 
647 	usbd_xfer_status(xfer, &actlen, &sumlen, NULL, NULL);
648 
649 	DPRINTF("\n");
650 
651 	switch (USB_GET_STATE(xfer)) {
652 	case USB_ST_TRANSFERRED:
653 		sc->sc_transfer.data_rem -= actlen;
654 		sc->sc_transfer.offset += actlen;
655 
656 		if (actlen != sumlen || sc->sc_transfer.data_rem == 0) {
657 			/* short transfer or end of data */
658 			ustorage_fs_transfer_start(sc,
659 			    USTORAGE_FS_T_BBB_STATUS);
660 			break;
661 		}
662 		/* Fallthrough */
663 
664 	case USB_ST_SETUP:
665 tr_setup:
666 		if (max_bulk > sc->sc_transfer.data_rem) {
667 			max_bulk = sc->sc_transfer.data_rem;
668 		}
669 		if (sc->sc_transfer.data_error) {
670 			sc->sc_transfer.data_error = 0;
671 			usbd_xfer_set_stall(xfer);
672 		}
673 		usbd_xfer_set_frame_len(xfer, 0, max_bulk);
674 		usbd_transfer_submit(xfer);
675 		break;
676 
677 	default:			/* Error */
678 		if (error == USB_ERR_CANCELLED) {
679 			break;
680 		}
681 		/*
682 		 * If the pipe is already stalled, don't do another stall:
683 		 */
684 		if (!usbd_xfer_is_stalled(xfer))
685 			sc->sc_transfer.data_error = 1;
686 
687 		/* try again */
688 		goto tr_setup;
689 	}
690 }
691 
692 static void
ustorage_fs_t_bbb_data_read_callback(struct usb_xfer * xfer,usb_error_t error)693 ustorage_fs_t_bbb_data_read_callback(struct usb_xfer *xfer, usb_error_t error)
694 {
695 	struct ustorage_fs_softc *sc = usbd_xfer_softc(xfer);
696 	uint32_t max_bulk = usbd_xfer_max_len(xfer);
697 	int actlen, sumlen;
698 
699 	usbd_xfer_status(xfer, &actlen, &sumlen, NULL, NULL);
700 
701 	DPRINTF("\n");
702 
703 	switch (USB_GET_STATE(xfer)) {
704 	case USB_ST_TRANSFERRED:
705 		/* XXX copy data from DMA buffer */
706 		memcpy(sc->sc_transfer.data_ptr, sc->sc_dma_ptr, actlen);
707 
708 		sc->sc_transfer.data_rem -= actlen;
709 		sc->sc_transfer.data_ptr += actlen;
710 		sc->sc_transfer.offset += actlen;
711 
712 		if (actlen != sumlen || sc->sc_transfer.data_rem == 0) {
713 			/* short transfer or end of data */
714 			ustorage_fs_transfer_start(sc,
715 			    USTORAGE_FS_T_BBB_STATUS);
716 			break;
717 		}
718 		/* Fallthrough */
719 
720 	case USB_ST_SETUP:
721 tr_setup:
722 		if (max_bulk > sc->sc_transfer.data_rem) {
723 			max_bulk = sc->sc_transfer.data_rem;
724 		}
725 		if (sc->sc_transfer.data_error) {
726 			sc->sc_transfer.data_error = 0;
727 			usbd_xfer_set_stall(xfer);
728 		}
729 
730 		usbd_xfer_set_frame_data(xfer, 0, sc->sc_dma_ptr, max_bulk);
731 		usbd_transfer_submit(xfer);
732 		break;
733 
734 	default:			/* Error */
735 		if (error == USB_ERR_CANCELLED) {
736 			break;
737 		}
738 		/* If the pipe is already stalled, don't do another stall */
739 		if (!usbd_xfer_is_stalled(xfer))
740 			sc->sc_transfer.data_error = 1;
741 
742 		/* try again */
743 		goto tr_setup;
744 	}
745 }
746 
747 static void
ustorage_fs_t_bbb_data_write_callback(struct usb_xfer * xfer,usb_error_t error)748 ustorage_fs_t_bbb_data_write_callback(struct usb_xfer *xfer, usb_error_t error)
749 {
750 	struct ustorage_fs_softc *sc = usbd_xfer_softc(xfer);
751 	uint32_t max_bulk = usbd_xfer_max_len(xfer);
752 	int actlen, sumlen;
753 
754 	usbd_xfer_status(xfer, &actlen, &sumlen, NULL, NULL);
755 
756 	DPRINTF("\n");
757 
758 	switch (USB_GET_STATE(xfer)) {
759 	case USB_ST_TRANSFERRED:
760 		sc->sc_transfer.data_rem -= actlen;
761 		sc->sc_transfer.data_ptr += actlen;
762 		sc->sc_transfer.offset += actlen;
763 
764 		if (actlen != sumlen || sc->sc_transfer.data_rem == 0) {
765 			/* short transfer or end of data */
766 			ustorage_fs_transfer_start(sc,
767 			    USTORAGE_FS_T_BBB_STATUS);
768 			break;
769 		}
770 	case USB_ST_SETUP:
771 tr_setup:
772 		if (max_bulk >= sc->sc_transfer.data_rem) {
773 			max_bulk = sc->sc_transfer.data_rem;
774 			if (sc->sc_transfer.data_short)
775 				usbd_xfer_set_flag(xfer, USB_FORCE_SHORT_XFER);
776 			else
777 				usbd_xfer_clr_flag(xfer, USB_FORCE_SHORT_XFER);
778 		} else
779 			usbd_xfer_clr_flag(xfer, USB_FORCE_SHORT_XFER);
780 
781 		if (sc->sc_transfer.data_error) {
782 			sc->sc_transfer.data_error = 0;
783 			usbd_xfer_set_stall(xfer);
784 		}
785 
786 		/* XXX copy data to DMA buffer */
787 		memcpy(sc->sc_dma_ptr, sc->sc_transfer.data_ptr, max_bulk);
788 
789 		usbd_xfer_set_frame_data(xfer, 0, sc->sc_dma_ptr, max_bulk);
790 		usbd_transfer_submit(xfer);
791 		break;
792 
793 	default:			/* Error */
794 		if (error == USB_ERR_CANCELLED) {
795 			break;
796 		}
797 		/*
798 		 * If the pipe is already stalled, don't do another
799 		 * stall
800 		 */
801 		if (!usbd_xfer_is_stalled(xfer))
802 			sc->sc_transfer.data_error = 1;
803 
804 		/* try again */
805 		goto tr_setup;
806 	}
807 }
808 
809 static void
ustorage_fs_t_bbb_status_callback(struct usb_xfer * xfer,usb_error_t error)810 ustorage_fs_t_bbb_status_callback(struct usb_xfer *xfer, usb_error_t error)
811 {
812 	struct ustorage_fs_softc *sc = usbd_xfer_softc(xfer);
813 
814 	DPRINTF("\n");
815 
816 	switch (USB_GET_STATE(xfer)) {
817 	case USB_ST_TRANSFERRED:
818 		ustorage_fs_transfer_start(sc, USTORAGE_FS_T_BBB_COMMAND);
819 		break;
820 
821 	case USB_ST_SETUP:
822 tr_setup:
823 		USETDW(sc->sc_csw->dCSWSignature, CSWSIGNATURE);
824 		USETDW(sc->sc_csw->dCSWDataResidue, sc->sc_transfer.data_rem);
825 
826 		if (sc->sc_transfer.data_error) {
827 			sc->sc_transfer.data_error = 0;
828 			usbd_xfer_set_stall(xfer);
829 		}
830 		usbd_xfer_set_frame_len(xfer, 0,
831 		    sizeof(ustorage_fs_bbb_csw_t));
832 		usbd_transfer_submit(xfer);
833 		break;
834 
835 	default:
836 		if (error == USB_ERR_CANCELLED) {
837 			break;
838 		}
839 		/* If the pipe is already stalled, don't do another stall */
840 		if (!usbd_xfer_is_stalled(xfer))
841 			sc->sc_transfer.data_error = 1;
842 
843 		/* try again */
844 		goto tr_setup;
845 	}
846 }
847 
848 /* SCSI commands that we recognize */
849 #define	SC_FORMAT_UNIT			0x04
850 #define	SC_INQUIRY			0x12
851 #define	SC_MODE_SELECT_6		0x15
852 #define	SC_MODE_SELECT_10		0x55
853 #define	SC_MODE_SENSE_6			0x1a
854 #define	SC_MODE_SENSE_10		0x5a
855 #define	SC_PREVENT_ALLOW_MEDIUM_REMOVAL	0x1e
856 #define	SC_READ_6			0x08
857 #define	SC_READ_10			0x28
858 #define	SC_READ_12			0xa8
859 #define	SC_READ_CAPACITY		0x25
860 #define	SC_READ_FORMAT_CAPACITIES	0x23
861 #define	SC_RELEASE			0x17
862 #define	SC_REQUEST_SENSE		0x03
863 #define	SC_RESERVE			0x16
864 #define	SC_SEND_DIAGNOSTIC		0x1d
865 #define	SC_START_STOP_UNIT		0x1b
866 #define	SC_SYNCHRONIZE_CACHE		0x35
867 #define	SC_TEST_UNIT_READY		0x00
868 #define	SC_VERIFY			0x2f
869 #define	SC_WRITE_6			0x0a
870 #define	SC_WRITE_10			0x2a
871 #define	SC_WRITE_12			0xaa
872 
873 /* SCSI Sense Key/Additional Sense Code/ASC Qualifier values */
874 #define	SS_NO_SENSE				0
875 #define	SS_COMMUNICATION_FAILURE		0x040800
876 #define	SS_INVALID_COMMAND			0x052000
877 #define	SS_INVALID_FIELD_IN_CDB			0x052400
878 #define	SS_LOGICAL_BLOCK_ADDRESS_OUT_OF_RANGE	0x052100
879 #define	SS_LOGICAL_UNIT_NOT_SUPPORTED		0x052500
880 #define	SS_MEDIUM_NOT_PRESENT			0x023a00
881 #define	SS_MEDIUM_REMOVAL_PREVENTED		0x055302
882 #define	SS_NOT_READY_TO_READY_TRANSITION	0x062800
883 #define	SS_RESET_OCCURRED			0x062900
884 #define	SS_SAVING_PARAMETERS_NOT_SUPPORTED	0x053900
885 #define	SS_UNRECOVERED_READ_ERROR		0x031100
886 #define	SS_WRITE_ERROR				0x030c02
887 #define	SS_WRITE_PROTECTED			0x072700
888 
889 #define	SK(x)		((uint8_t) ((x) >> 16))	/* Sense Key byte, etc. */
890 #define	ASC(x)		((uint8_t) ((x) >> 8))
891 #define	ASCQ(x)		((uint8_t) (x))
892 
893 /* Routines for unaligned data access */
894 
895 static uint16_t
get_be16(uint8_t * buf)896 get_be16(uint8_t *buf)
897 {
898 	return ((uint16_t)buf[0] << 8) | ((uint16_t)buf[1]);
899 }
900 
901 static uint32_t
get_be32(uint8_t * buf)902 get_be32(uint8_t *buf)
903 {
904 	return ((uint32_t)buf[0] << 24) | ((uint32_t)buf[1] << 16) |
905 	((uint32_t)buf[2] << 8) | ((uint32_t)buf[3]);
906 }
907 
908 static void
put_be16(uint8_t * buf,uint16_t val)909 put_be16(uint8_t *buf, uint16_t val)
910 {
911 	buf[0] = val >> 8;
912 	buf[1] = val;
913 }
914 
915 static void
put_be32(uint8_t * buf,uint32_t val)916 put_be32(uint8_t *buf, uint32_t val)
917 {
918 	buf[0] = val >> 24;
919 	buf[1] = val >> 16;
920 	buf[2] = val >> 8;
921 	buf[3] = val & 0xff;
922 }
923 
924 /*------------------------------------------------------------------------*
925  *	ustorage_fs_verify
926  *
927  * Returns:
928  *    0: Success
929  * Else: Failure
930  *------------------------------------------------------------------------*/
931 static uint8_t
ustorage_fs_verify(struct ustorage_fs_softc * sc)932 ustorage_fs_verify(struct ustorage_fs_softc *sc)
933 {
934 	struct ustorage_fs_lun *currlun = sc->sc_transfer.currlun;
935 	uint32_t lba;
936 	uint32_t vlen;
937 	uint64_t file_offset;
938 	uint64_t amount_left;
939 
940 	/*
941 	 * Get the starting Logical Block Address
942 	 */
943 	lba = get_be32(&sc->sc_cbw->CBWCDB[2]);
944 
945 	/*
946 	 * We allow DPO (Disable Page Out = don't save data in the cache)
947 	 * but we don't implement it.
948 	 */
949 	if ((sc->sc_cbw->CBWCDB[1] & ~0x10) != 0) {
950 		currlun->sense_data = SS_INVALID_FIELD_IN_CDB;
951 		return (1);
952 	}
953 	vlen = get_be16(&sc->sc_cbw->CBWCDB[7]);
954 	if (vlen == 0) {
955 		goto done;
956 	}
957 	/* No default reply */
958 
959 	/* Prepare to carry out the file verify */
960 	amount_left = vlen;
961 	amount_left <<= 9;
962 	file_offset = lba;
963 	file_offset <<= 9;
964 
965 	/* Range check */
966 	vlen += lba;
967 
968 	if ((vlen < lba) ||
969 	    (vlen > currlun->num_sectors) ||
970 	    (lba >= currlun->num_sectors)) {
971 		currlun->sense_data = SS_LOGICAL_BLOCK_ADDRESS_OUT_OF_RANGE;
972 		return (1);
973 	}
974 	/* XXX TODO: verify that data is readable */
975 done:
976 	return (ustorage_fs_min_len(sc, 0, -1U));
977 }
978 
979 /*------------------------------------------------------------------------*
980  *	ustorage_fs_inquiry
981  *
982  * Returns:
983  *    0: Success
984  * Else: Failure
985  *------------------------------------------------------------------------*/
986 static uint8_t
ustorage_fs_inquiry(struct ustorage_fs_softc * sc)987 ustorage_fs_inquiry(struct ustorage_fs_softc *sc)
988 {
989 	uint8_t *buf = sc->sc_transfer.data_ptr;
990 
991 	struct ustorage_fs_lun *currlun = sc->sc_transfer.currlun;
992 
993 	if (!sc->sc_transfer.currlun) {
994 		/* Unsupported LUNs are okay */
995 		memset(buf, 0, 36);
996 		buf[0] = 0x7f;
997 		/* Unsupported, no device - type */
998 		return (ustorage_fs_min_len(sc, 36, -1U));
999 	}
1000 	memset(buf, 0, 8);
1001 	/* Non - removable, direct - access device */
1002 	if (currlun->removable)
1003 		buf[1] = 0x80;
1004 	buf[2] = 2;
1005 	/* ANSI SCSI level 2 */
1006 	buf[3] = 2;
1007 	/* SCSI - 2 INQUIRY data format */
1008 	buf[4] = 31;
1009 	/* Additional length */
1010 	/* No special options */
1011 	/* Copy in ID string */
1012 	memcpy(buf + 8, USTORAGE_FS_ID_STRING, 28);
1013 
1014 #if (USTORAGE_QDATA_MAX < 36)
1015 #error "(USTORAGE_QDATA_MAX < 36)"
1016 #endif
1017 	return (ustorage_fs_min_len(sc, 36, -1U));
1018 }
1019 
1020 /*------------------------------------------------------------------------*
1021  *	ustorage_fs_request_sense
1022  *
1023  * Returns:
1024  *    0: Success
1025  * Else: Failure
1026  *------------------------------------------------------------------------*/
1027 static uint8_t
ustorage_fs_request_sense(struct ustorage_fs_softc * sc)1028 ustorage_fs_request_sense(struct ustorage_fs_softc *sc)
1029 {
1030 	uint8_t *buf = sc->sc_transfer.data_ptr;
1031 	struct ustorage_fs_lun *currlun = sc->sc_transfer.currlun;
1032 	uint32_t sd;
1033 	uint32_t sdinfo;
1034 	uint8_t valid;
1035 
1036 	/*
1037 	 * From the SCSI-2 spec., section 7.9 (Unit attention condition):
1038 	 *
1039 	 * If a REQUEST SENSE command is received from an initiator
1040 	 * with a pending unit attention condition (before the target
1041 	 * generates the contingent allegiance condition), then the
1042 	 * target shall either:
1043 	 *   a) report any pending sense data and preserve the unit
1044 	 *	attention condition on the logical unit, or,
1045 	 *   b) report the unit attention condition, may discard any
1046 	 *	pending sense data, and clear the unit attention
1047 	 *	condition on the logical unit for that initiator.
1048 	 *
1049 	 * FSG normally uses option a); enable this code to use option b).
1050 	 */
1051 #if 0
1052 	if (currlun && currlun->unit_attention_data != SS_NO_SENSE) {
1053 		currlun->sense_data = currlun->unit_attention_data;
1054 		currlun->unit_attention_data = SS_NO_SENSE;
1055 	}
1056 #endif
1057 
1058 	if (!currlun) {
1059 		/* Unsupported LUNs are okay */
1060 		sd = SS_LOGICAL_UNIT_NOT_SUPPORTED;
1061 		sdinfo = 0;
1062 		valid = 0;
1063 	} else {
1064 		sd = currlun->sense_data;
1065 		sdinfo = currlun->sense_data_info;
1066 		valid = currlun->info_valid << 7;
1067 		currlun->sense_data = SS_NO_SENSE;
1068 		currlun->sense_data_info = 0;
1069 		currlun->info_valid = 0;
1070 	}
1071 
1072 	memset(buf, 0, 18);
1073 	buf[0] = valid | 0x70;
1074 	/* Valid, current error */
1075 	buf[2] = SK(sd);
1076 	put_be32(&buf[3], sdinfo);
1077 	/* Sense information */
1078 	buf[7] = 18 - 8;
1079 	/* Additional sense length */
1080 	buf[12] = ASC(sd);
1081 	buf[13] = ASCQ(sd);
1082 
1083 #if (USTORAGE_QDATA_MAX < 18)
1084 #error "(USTORAGE_QDATA_MAX < 18)"
1085 #endif
1086 	return (ustorage_fs_min_len(sc, 18, -1U));
1087 }
1088 
1089 /*------------------------------------------------------------------------*
1090  *	ustorage_fs_read_capacity
1091  *
1092  * Returns:
1093  *    0: Success
1094  * Else: Failure
1095  *------------------------------------------------------------------------*/
1096 static uint8_t
ustorage_fs_read_capacity(struct ustorage_fs_softc * sc)1097 ustorage_fs_read_capacity(struct ustorage_fs_softc *sc)
1098 {
1099 	uint8_t *buf = sc->sc_transfer.data_ptr;
1100 	struct ustorage_fs_lun *currlun = sc->sc_transfer.currlun;
1101 	uint32_t lba = get_be32(&sc->sc_cbw->CBWCDB[2]);
1102 	uint8_t pmi = sc->sc_cbw->CBWCDB[8];
1103 
1104 	/* Check the PMI and LBA fields */
1105 	if ((pmi > 1) || ((pmi == 0) && (lba != 0))) {
1106 		currlun->sense_data = SS_INVALID_FIELD_IN_CDB;
1107 		return (1);
1108 	}
1109 	/* Max logical block */
1110 	put_be32(&buf[0], currlun->num_sectors - 1);
1111 	/* Block length */
1112 	put_be32(&buf[4], 512);
1113 
1114 #if (USTORAGE_QDATA_MAX < 8)
1115 #error "(USTORAGE_QDATA_MAX < 8)"
1116 #endif
1117 	return (ustorage_fs_min_len(sc, 8, -1U));
1118 }
1119 
1120 /*------------------------------------------------------------------------*
1121  *	ustorage_fs_mode_sense
1122  *
1123  * Returns:
1124  *    0: Success
1125  * Else: Failure
1126  *------------------------------------------------------------------------*/
1127 static uint8_t
ustorage_fs_mode_sense(struct ustorage_fs_softc * sc)1128 ustorage_fs_mode_sense(struct ustorage_fs_softc *sc)
1129 {
1130 	uint8_t *buf = sc->sc_transfer.data_ptr;
1131 	struct ustorage_fs_lun *currlun = sc->sc_transfer.currlun;
1132 	uint8_t *buf0;
1133 	uint16_t len;
1134 	uint16_t limit;
1135 	uint8_t mscmnd = sc->sc_cbw->CBWCDB[0];
1136 	uint8_t pc;
1137 	uint8_t page_code;
1138 	uint8_t changeable_values;
1139 	uint8_t all_pages;
1140 
1141 	buf0 = buf;
1142 
1143 	if ((sc->sc_cbw->CBWCDB[1] & ~0x08) != 0) {
1144 		/* Mask away DBD */
1145 		currlun->sense_data = SS_INVALID_FIELD_IN_CDB;
1146 		return (1);
1147 	}
1148 	pc = sc->sc_cbw->CBWCDB[2] >> 6;
1149 	page_code = sc->sc_cbw->CBWCDB[2] & 0x3f;
1150 	if (pc == 3) {
1151 		currlun->sense_data = SS_SAVING_PARAMETERS_NOT_SUPPORTED;
1152 		return (1);
1153 	}
1154 	changeable_values = (pc == 1);
1155 	all_pages = (page_code == 0x3f);
1156 
1157 	/*
1158 	 * Write the mode parameter header.  Fixed values are: default
1159 	 * medium type, no cache control (DPOFUA), and no block descriptors.
1160 	 * The only variable value is the WriteProtect bit.  We will fill in
1161 	 * the mode data length later.
1162 	 */
1163 	memset(buf, 0, 8);
1164 	if (mscmnd == SC_MODE_SENSE_6) {
1165 		buf[2] = (currlun->read_only ? 0x80 : 0x00);
1166 		/* WP, DPOFUA */
1167 		buf += 4;
1168 		limit = 255;
1169 	} else {
1170 		/* SC_MODE_SENSE_10 */
1171 		buf[3] = (currlun->read_only ? 0x80 : 0x00);
1172 		/* WP, DPOFUA */
1173 		buf += 8;
1174 		limit = 65535;
1175 		/* Should really be mod_data.buflen */
1176 	}
1177 
1178 	/* No block descriptors */
1179 
1180 	/*
1181 	 * The mode pages, in numerical order.
1182 	 */
1183 	if ((page_code == 0x08) || all_pages) {
1184 		buf[0] = 0x08;
1185 		/* Page code */
1186 		buf[1] = 10;
1187 		/* Page length */
1188 		memset(buf + 2, 0, 10);
1189 		/* None of the fields are changeable */
1190 
1191 		if (!changeable_values) {
1192 			buf[2] = 0x04;
1193 			/* Write cache enable, */
1194 			/* Read cache not disabled */
1195 			/* No cache retention priorities */
1196 			put_be16(&buf[4], 0xffff);
1197 			/* Don 't disable prefetch */
1198 			/* Minimum prefetch = 0 */
1199 			put_be16(&buf[8], 0xffff);
1200 			/* Maximum prefetch */
1201 			put_be16(&buf[10], 0xffff);
1202 			/* Maximum prefetch ceiling */
1203 		}
1204 		buf += 12;
1205 	}
1206 	/*
1207 	 * Check that a valid page was requested and the mode data length
1208 	 * isn't too long.
1209 	 */
1210 	len = buf - buf0;
1211 	if (len > limit) {
1212 		currlun->sense_data = SS_INVALID_FIELD_IN_CDB;
1213 		return (1);
1214 	}
1215 	/* Store the mode data length */
1216 	if (mscmnd == SC_MODE_SENSE_6)
1217 		buf0[0] = len - 1;
1218 	else
1219 		put_be16(buf0, len - 2);
1220 
1221 #if (USTORAGE_QDATA_MAX < 24)
1222 #error "(USTORAGE_QDATA_MAX < 24)"
1223 #endif
1224 	return (ustorage_fs_min_len(sc, len, -1U));
1225 }
1226 
1227 /*------------------------------------------------------------------------*
1228  *	ustorage_fs_start_stop
1229  *
1230  * Returns:
1231  *    0: Success
1232  * Else: Failure
1233  *------------------------------------------------------------------------*/
1234 static uint8_t
ustorage_fs_start_stop(struct ustorage_fs_softc * sc)1235 ustorage_fs_start_stop(struct ustorage_fs_softc *sc)
1236 {
1237 	struct ustorage_fs_lun *currlun = sc->sc_transfer.currlun;
1238 	uint8_t loej;
1239 	uint8_t start;
1240 	uint8_t immed;
1241 
1242 	if (!currlun->removable) {
1243 		currlun->sense_data = SS_INVALID_COMMAND;
1244 		return (1);
1245 	}
1246 	immed = sc->sc_cbw->CBWCDB[1] & 0x01;
1247 	loej = sc->sc_cbw->CBWCDB[4] & 0x02;
1248 	start = sc->sc_cbw->CBWCDB[4] & 0x01;
1249 
1250 	if (immed || loej || start) {
1251 		/* compile fix */
1252 	}
1253 	return (0);
1254 }
1255 
1256 /*------------------------------------------------------------------------*
1257  *	ustorage_fs_prevent_allow
1258  *
1259  * Returns:
1260  *    0: Success
1261  * Else: Failure
1262  *------------------------------------------------------------------------*/
1263 static uint8_t
ustorage_fs_prevent_allow(struct ustorage_fs_softc * sc)1264 ustorage_fs_prevent_allow(struct ustorage_fs_softc *sc)
1265 {
1266 	struct ustorage_fs_lun *currlun = sc->sc_transfer.currlun;
1267 	uint8_t prevent;
1268 
1269 	if (!currlun->removable) {
1270 		currlun->sense_data = SS_INVALID_COMMAND;
1271 		return (1);
1272 	}
1273 	prevent = sc->sc_cbw->CBWCDB[4] & 0x01;
1274 	if ((sc->sc_cbw->CBWCDB[4] & ~0x01) != 0) {
1275 		/* Mask away Prevent */
1276 		currlun->sense_data = SS_INVALID_FIELD_IN_CDB;
1277 		return (1);
1278 	}
1279 	if (currlun->prevent_medium_removal && !prevent) {
1280 		//fsync_sub(currlun);
1281 	}
1282 	currlun->prevent_medium_removal = prevent;
1283 	return (0);
1284 }
1285 
1286 /*------------------------------------------------------------------------*
1287  *	ustorage_fs_read_format_capacities
1288  *
1289  * Returns:
1290  *    0: Success
1291  * Else: Failure
1292  *------------------------------------------------------------------------*/
1293 static uint8_t
ustorage_fs_read_format_capacities(struct ustorage_fs_softc * sc)1294 ustorage_fs_read_format_capacities(struct ustorage_fs_softc *sc)
1295 {
1296 	uint8_t *buf = sc->sc_transfer.data_ptr;
1297 	struct ustorage_fs_lun *currlun = sc->sc_transfer.currlun;
1298 
1299 	buf[0] = buf[1] = buf[2] = 0;
1300 	buf[3] = 8;
1301 	/* Only the Current / Maximum Capacity Descriptor */
1302 	buf += 4;
1303 
1304 	/* Number of blocks */
1305 	put_be32(&buf[0], currlun->num_sectors);
1306 	/* Block length */
1307 	put_be32(&buf[4], 512);
1308 	/* Current capacity */
1309 	buf[4] = 0x02;
1310 
1311 #if (USTORAGE_QDATA_MAX < 12)
1312 #error "(USTORAGE_QDATA_MAX < 12)"
1313 #endif
1314 	return (ustorage_fs_min_len(sc, 12, -1U));
1315 }
1316 
1317 /*------------------------------------------------------------------------*
1318  *	ustorage_fs_mode_select
1319  *
1320  * Return values:
1321  *    0: Success
1322  * Else: Failure
1323  *------------------------------------------------------------------------*/
1324 static uint8_t
ustorage_fs_mode_select(struct ustorage_fs_softc * sc)1325 ustorage_fs_mode_select(struct ustorage_fs_softc *sc)
1326 {
1327 	struct ustorage_fs_lun *currlun = sc->sc_transfer.currlun;
1328 
1329 	/* We don't support MODE SELECT */
1330 	currlun->sense_data = SS_INVALID_COMMAND;
1331 	return (1);
1332 }
1333 
1334 /*------------------------------------------------------------------------*
1335  *	ustorage_fs_synchronize_cache
1336  *
1337  * Return values:
1338  *    0: Success
1339  * Else: Failure
1340  *------------------------------------------------------------------------*/
1341 static uint8_t
ustorage_fs_synchronize_cache(struct ustorage_fs_softc * sc)1342 ustorage_fs_synchronize_cache(struct ustorage_fs_softc *sc)
1343 {
1344 #if 0
1345 	struct ustorage_fs_lun *currlun = sc->sc_transfer.currlun;
1346 	uint8_t rc;
1347 
1348 	/*
1349 	 * We ignore the requested LBA and write out all dirty data buffers.
1350 	 */
1351 	rc = 0;
1352 	if (rc) {
1353 		currlun->sense_data = SS_WRITE_ERROR;
1354 	}
1355 #endif
1356 	return (0);
1357 }
1358 
1359 /*------------------------------------------------------------------------*
1360  *	ustorage_fs_read - read data from disk
1361  *
1362  * Return values:
1363  *    0: Success
1364  * Else: Failure
1365  *------------------------------------------------------------------------*/
1366 static uint8_t
ustorage_fs_read(struct ustorage_fs_softc * sc)1367 ustorage_fs_read(struct ustorage_fs_softc *sc)
1368 {
1369 	struct ustorage_fs_lun *currlun = sc->sc_transfer.currlun;
1370 	uint64_t file_offset;
1371 	uint32_t lba;
1372 	uint32_t len;
1373 
1374 	/*
1375 	 * Get the starting Logical Block Address and check that it's not
1376 	 * too big
1377 	 */
1378 	if (sc->sc_cbw->CBWCDB[0] == SC_READ_6) {
1379 		lba = (((uint32_t)sc->sc_cbw->CBWCDB[1]) << 16) |
1380 		    get_be16(&sc->sc_cbw->CBWCDB[2]);
1381 	} else {
1382 		lba = get_be32(&sc->sc_cbw->CBWCDB[2]);
1383 
1384 		/*
1385 		 * We allow DPO (Disable Page Out = don't save data in the
1386 		 * cache) and FUA (Force Unit Access = don't read from the
1387 		 * cache), but we don't implement them.
1388 		 */
1389 		if ((sc->sc_cbw->CBWCDB[1] & ~0x18) != 0) {
1390 			currlun->sense_data = SS_INVALID_FIELD_IN_CDB;
1391 			return (1);
1392 		}
1393 	}
1394 	len = sc->sc_transfer.data_rem >> 9;
1395 	len += lba;
1396 
1397 	if ((len < lba) ||
1398 	    (len > currlun->num_sectors) ||
1399 	    (lba >= currlun->num_sectors)) {
1400 		currlun->sense_data = SS_LOGICAL_BLOCK_ADDRESS_OUT_OF_RANGE;
1401 		return (1);
1402 	}
1403 	file_offset = lba;
1404 	file_offset <<= 9;
1405 
1406 	sc->sc_transfer.data_ptr = currlun->memory_image + file_offset;
1407 
1408 	return (0);
1409 }
1410 
1411 /*------------------------------------------------------------------------*
1412  *	ustorage_fs_write - write data to disk
1413  *
1414  * Return values:
1415  *    0: Success
1416  * Else: Failure
1417  *------------------------------------------------------------------------*/
1418 static uint8_t
ustorage_fs_write(struct ustorage_fs_softc * sc)1419 ustorage_fs_write(struct ustorage_fs_softc *sc)
1420 {
1421 	struct ustorage_fs_lun *currlun = sc->sc_transfer.currlun;
1422 	uint64_t file_offset;
1423 	uint32_t lba;
1424 	uint32_t len;
1425 
1426 	if (currlun->read_only) {
1427 		currlun->sense_data = SS_WRITE_PROTECTED;
1428 		return (1);
1429 	}
1430 	/* XXX clear SYNC */
1431 
1432 	/*
1433 	 * Get the starting Logical Block Address and check that it's not
1434 	 * too big.
1435 	 */
1436 	if (sc->sc_cbw->CBWCDB[0] == SC_WRITE_6)
1437 		lba = (((uint32_t)sc->sc_cbw->CBWCDB[1]) << 16) |
1438 		    get_be16(&sc->sc_cbw->CBWCDB[2]);
1439 	else {
1440 		lba = get_be32(&sc->sc_cbw->CBWCDB[2]);
1441 
1442 		/*
1443 		 * We allow DPO (Disable Page Out = don't save data in the
1444 		 * cache) and FUA (Force Unit Access = write directly to the
1445 		 * medium).  We don't implement DPO; we implement FUA by
1446 		 * performing synchronous output.
1447 		 */
1448 		if ((sc->sc_cbw->CBWCDB[1] & ~0x18) != 0) {
1449 			currlun->sense_data = SS_INVALID_FIELD_IN_CDB;
1450 			return (1);
1451 		}
1452 		if (sc->sc_cbw->CBWCDB[1] & 0x08) {
1453 			/* FUA */
1454 			/* XXX set SYNC flag here */
1455 		}
1456 	}
1457 
1458 	len = sc->sc_transfer.data_rem >> 9;
1459 	len += lba;
1460 
1461 	if ((len < lba) ||
1462 	    (len > currlun->num_sectors) ||
1463 	    (lba >= currlun->num_sectors)) {
1464 		currlun->sense_data = SS_LOGICAL_BLOCK_ADDRESS_OUT_OF_RANGE;
1465 		return (1);
1466 	}
1467 	file_offset = lba;
1468 	file_offset <<= 9;
1469 
1470 	sc->sc_transfer.data_ptr = currlun->memory_image + file_offset;
1471 
1472 	return (0);
1473 }
1474 
1475 /*------------------------------------------------------------------------*
1476  *	ustorage_fs_min_len
1477  *
1478  * Return values:
1479  *    0: Success
1480  * Else: Failure
1481  *------------------------------------------------------------------------*/
1482 static uint8_t
ustorage_fs_min_len(struct ustorage_fs_softc * sc,uint32_t len,uint32_t mask)1483 ustorage_fs_min_len(struct ustorage_fs_softc *sc, uint32_t len, uint32_t mask)
1484 {
1485 	if (len != sc->sc_transfer.data_rem) {
1486 
1487 		if (sc->sc_transfer.cbw_dir == DIR_READ) {
1488 			/*
1489 			 * there must be something wrong about this SCSI
1490 			 * command
1491 			 */
1492 			sc->sc_csw->bCSWStatus = CSWSTATUS_PHASE;
1493 			return (1);
1494 		}
1495 		/* compute the minimum length */
1496 
1497 		if (sc->sc_transfer.data_rem > len) {
1498 			/* data ends prematurely */
1499 			sc->sc_transfer.data_rem = len;
1500 			sc->sc_transfer.data_short = 1;
1501 		}
1502 		/* check length alignment */
1503 
1504 		if (sc->sc_transfer.data_rem & ~mask) {
1505 			/* data ends prematurely */
1506 			sc->sc_transfer.data_rem &= mask;
1507 			sc->sc_transfer.data_short = 1;
1508 		}
1509 	}
1510 	return (0);
1511 }
1512 
1513 /*------------------------------------------------------------------------*
1514  *	ustorage_fs_check_cmd - check command routine
1515  *
1516  * Check whether the command is properly formed and whether its data
1517  * size and direction agree with the values we already have.
1518  *
1519  * Return values:
1520  *    0: Success
1521  * Else: Failure
1522  *------------------------------------------------------------------------*/
1523 static uint8_t
ustorage_fs_check_cmd(struct ustorage_fs_softc * sc,uint8_t min_cmd_size,uint16_t mask,uint8_t needs_medium)1524 ustorage_fs_check_cmd(struct ustorage_fs_softc *sc, uint8_t min_cmd_size,
1525     uint16_t mask, uint8_t needs_medium)
1526 {
1527 	struct ustorage_fs_lun *currlun;
1528 	uint8_t lun = (sc->sc_cbw->CBWCDB[1] >> 5);
1529 	uint8_t i;
1530 
1531 	/* Verify the length of the command itself */
1532 	if (min_cmd_size > sc->sc_transfer.cmd_len) {
1533 		DPRINTF("%u > %u\n",
1534 		    min_cmd_size, sc->sc_transfer.cmd_len);
1535 		sc->sc_csw->bCSWStatus = CSWSTATUS_PHASE;
1536 		return (1);
1537 	}
1538 	/* Mask away the LUN */
1539 	sc->sc_cbw->CBWCDB[1] &= 0x1f;
1540 
1541 	/* Check if LUN is correct */
1542 	if (lun != sc->sc_transfer.lun) {
1543 
1544 	}
1545 	/* Check the LUN */
1546 	if (sc->sc_transfer.lun <= sc->sc_last_lun) {
1547 		sc->sc_transfer.currlun = currlun =
1548 		    sc->sc_lun + sc->sc_transfer.lun;
1549 		if (sc->sc_cbw->CBWCDB[0] != SC_REQUEST_SENSE) {
1550 			currlun->sense_data = SS_NO_SENSE;
1551 			currlun->sense_data_info = 0;
1552 			currlun->info_valid = 0;
1553 		}
1554 		/*
1555 		 * If a unit attention condition exists, only INQUIRY
1556 		 * and REQUEST SENSE commands are allowed. Anything
1557 		 * else must fail!
1558 		 */
1559 		if ((currlun->unit_attention_data != SS_NO_SENSE) &&
1560 		    (sc->sc_cbw->CBWCDB[0] != SC_INQUIRY) &&
1561 		    (sc->sc_cbw->CBWCDB[0] != SC_REQUEST_SENSE)) {
1562 			currlun->sense_data = currlun->unit_attention_data;
1563 			currlun->unit_attention_data = SS_NO_SENSE;
1564 			return (1);
1565 		}
1566 	} else {
1567 		sc->sc_transfer.currlun = currlun = NULL;
1568 
1569 		/*
1570 		 * INQUIRY and REQUEST SENSE commands are explicitly allowed
1571 		 * to use unsupported LUNs; all others may not.
1572 		 */
1573 		if ((sc->sc_cbw->CBWCDB[0] != SC_INQUIRY) &&
1574 		    (sc->sc_cbw->CBWCDB[0] != SC_REQUEST_SENSE)) {
1575 			return (1);
1576 		}
1577 	}
1578 
1579 	/*
1580 	 * Check that only command bytes listed in the mask are
1581 	 * non-zero.
1582 	 */
1583 	for (i = 0; i != min_cmd_size; i++) {
1584 		if (sc->sc_cbw->CBWCDB[i] && !(mask & (1UL << i))) {
1585 			if (currlun) {
1586 				currlun->sense_data = SS_INVALID_FIELD_IN_CDB;
1587 			}
1588 			return (1);
1589 		}
1590 	}
1591 
1592 	/*
1593 	 * If the medium isn't mounted and the command needs to access
1594 	 * it, return an error.
1595 	 */
1596 	if (currlun && (!currlun->memory_image) && needs_medium) {
1597 		currlun->sense_data = SS_MEDIUM_NOT_PRESENT;
1598 		return (1);
1599 	}
1600 	return (0);
1601 }
1602 
1603 /*------------------------------------------------------------------------*
1604  *	ustorage_fs_do_cmd - do command
1605  *
1606  * Return values:
1607  *    0: Success
1608  * Else: Failure
1609  *------------------------------------------------------------------------*/
1610 static uint8_t
ustorage_fs_do_cmd(struct ustorage_fs_softc * sc)1611 ustorage_fs_do_cmd(struct ustorage_fs_softc *sc)
1612 {
1613 	uint8_t error = 1;
1614 	uint8_t i;
1615 	uint32_t temp;
1616 	const uint32_t mask9 = (0xFFFFFFFFUL >> 9) << 9;
1617 
1618 	/* set default data transfer pointer */
1619 	sc->sc_transfer.data_ptr = sc->sc_qdata;
1620 
1621 	DPRINTF("cmd_data[0]=0x%02x, data_rem=0x%08x\n",
1622 	    sc->sc_cbw->CBWCDB[0], sc->sc_transfer.data_rem);
1623 
1624 	switch (sc->sc_cbw->CBWCDB[0]) {
1625 	case SC_INQUIRY:
1626 		sc->sc_transfer.cmd_dir = DIR_WRITE;
1627 		error = ustorage_fs_min_len(sc, sc->sc_cbw->CBWCDB[4], -1U);
1628 		if (error) {
1629 			break;
1630 		}
1631 		error = ustorage_fs_check_cmd(sc, 6,
1632 		    (1UL << 4) | 1, 0);
1633 		if (error) {
1634 			break;
1635 		}
1636 		error = ustorage_fs_inquiry(sc);
1637 
1638 		break;
1639 
1640 	case SC_MODE_SELECT_6:
1641 		sc->sc_transfer.cmd_dir = DIR_READ;
1642 		error = ustorage_fs_min_len(sc, sc->sc_cbw->CBWCDB[4], -1U);
1643 		if (error) {
1644 			break;
1645 		}
1646 		error = ustorage_fs_check_cmd(sc, 6,
1647 		    (1UL << 1) | (1UL << 4) | 1, 0);
1648 		if (error) {
1649 			break;
1650 		}
1651 		error = ustorage_fs_mode_select(sc);
1652 
1653 		break;
1654 
1655 	case SC_MODE_SELECT_10:
1656 		sc->sc_transfer.cmd_dir = DIR_READ;
1657 		error = ustorage_fs_min_len(sc,
1658 		    get_be16(&sc->sc_cbw->CBWCDB[7]), -1U);
1659 		if (error) {
1660 			break;
1661 		}
1662 		error = ustorage_fs_check_cmd(sc, 10,
1663 		    (1UL << 1) | (3UL << 7) | 1, 0);
1664 		if (error) {
1665 			break;
1666 		}
1667 		error = ustorage_fs_mode_select(sc);
1668 
1669 		break;
1670 
1671 	case SC_MODE_SENSE_6:
1672 		sc->sc_transfer.cmd_dir = DIR_WRITE;
1673 		error = ustorage_fs_min_len(sc, sc->sc_cbw->CBWCDB[4], -1U);
1674 		if (error) {
1675 			break;
1676 		}
1677 		error = ustorage_fs_check_cmd(sc, 6,
1678 		    (1UL << 1) | (1UL << 2) | (1UL << 4) | 1, 0);
1679 		if (error) {
1680 			break;
1681 		}
1682 		error = ustorage_fs_mode_sense(sc);
1683 
1684 		break;
1685 
1686 	case SC_MODE_SENSE_10:
1687 		sc->sc_transfer.cmd_dir = DIR_WRITE;
1688 		error = ustorage_fs_min_len(sc,
1689 		    get_be16(&sc->sc_cbw->CBWCDB[7]), -1U);
1690 		if (error) {
1691 			break;
1692 		}
1693 		error = ustorage_fs_check_cmd(sc, 10,
1694 		    (1UL << 1) | (1UL << 2) | (3UL << 7) | 1, 0);
1695 		if (error) {
1696 			break;
1697 		}
1698 		error = ustorage_fs_mode_sense(sc);
1699 
1700 		break;
1701 
1702 	case SC_PREVENT_ALLOW_MEDIUM_REMOVAL:
1703 		error = ustorage_fs_min_len(sc, 0, -1U);
1704 		if (error) {
1705 			break;
1706 		}
1707 		error = ustorage_fs_check_cmd(sc, 6,
1708 		    (1UL << 4) | 1, 0);
1709 		if (error) {
1710 			break;
1711 		}
1712 		error = ustorage_fs_prevent_allow(sc);
1713 
1714 		break;
1715 
1716 	case SC_READ_6:
1717 		i = sc->sc_cbw->CBWCDB[4];
1718 		sc->sc_transfer.cmd_dir = DIR_WRITE;
1719 		temp = ((i == 0) ? 256UL : i);
1720 		error = ustorage_fs_min_len(sc, temp << 9, mask9);
1721 		if (error) {
1722 			break;
1723 		}
1724 		error = ustorage_fs_check_cmd(sc, 6,
1725 		    (7UL << 1) | (1UL << 4) | 1, 1);
1726 		if (error) {
1727 			break;
1728 		}
1729 		error = ustorage_fs_read(sc);
1730 
1731 		break;
1732 
1733 	case SC_READ_10:
1734 		sc->sc_transfer.cmd_dir = DIR_WRITE;
1735 		temp = get_be16(&sc->sc_cbw->CBWCDB[7]);
1736 		error = ustorage_fs_min_len(sc, temp << 9, mask9);
1737 		if (error) {
1738 			break;
1739 		}
1740 		error = ustorage_fs_check_cmd(sc, 10,
1741 		    (1UL << 1) | (0xfUL << 2) | (3UL << 7) | 1, 1);
1742 		if (error) {
1743 			break;
1744 		}
1745 		error = ustorage_fs_read(sc);
1746 
1747 		break;
1748 
1749 	case SC_READ_12:
1750 		sc->sc_transfer.cmd_dir = DIR_WRITE;
1751 		temp = get_be32(&sc->sc_cbw->CBWCDB[6]);
1752 		if (temp >= (1UL << (32 - 9))) {
1753 			/* numerical overflow */
1754 			sc->sc_csw->bCSWStatus = CSWSTATUS_FAILED;
1755 			error = 1;
1756 			break;
1757 		}
1758 		error = ustorage_fs_min_len(sc, temp << 9, mask9);
1759 		if (error) {
1760 			break;
1761 		}
1762 		error = ustorage_fs_check_cmd(sc, 12,
1763 		    (1UL << 1) | (0xfUL << 2) | (0xfUL << 6) | 1, 1);
1764 		if (error) {
1765 			break;
1766 		}
1767 		error = ustorage_fs_read(sc);
1768 
1769 		break;
1770 
1771 	case SC_READ_CAPACITY:
1772 		sc->sc_transfer.cmd_dir = DIR_WRITE;
1773 		error = ustorage_fs_check_cmd(sc, 10,
1774 		    (0xfUL << 2) | (1UL << 8) | 1, 1);
1775 		if (error) {
1776 			break;
1777 		}
1778 		error = ustorage_fs_read_capacity(sc);
1779 
1780 		break;
1781 
1782 	case SC_READ_FORMAT_CAPACITIES:
1783 		sc->sc_transfer.cmd_dir = DIR_WRITE;
1784 		error = ustorage_fs_min_len(sc,
1785 		    get_be16(&sc->sc_cbw->CBWCDB[7]), -1U);
1786 		if (error) {
1787 			break;
1788 		}
1789 		error = ustorage_fs_check_cmd(sc, 10,
1790 		    (3UL << 7) | 1, 1);
1791 		if (error) {
1792 			break;
1793 		}
1794 		error = ustorage_fs_read_format_capacities(sc);
1795 
1796 		break;
1797 
1798 	case SC_REQUEST_SENSE:
1799 		sc->sc_transfer.cmd_dir = DIR_WRITE;
1800 		error = ustorage_fs_min_len(sc, sc->sc_cbw->CBWCDB[4], -1U);
1801 		if (error) {
1802 			break;
1803 		}
1804 		error = ustorage_fs_check_cmd(sc, 6,
1805 		    (1UL << 4) | 1, 0);
1806 		if (error) {
1807 			break;
1808 		}
1809 		error = ustorage_fs_request_sense(sc);
1810 
1811 		break;
1812 
1813 	case SC_START_STOP_UNIT:
1814 		error = ustorage_fs_min_len(sc, 0, -1U);
1815 		if (error) {
1816 			break;
1817 		}
1818 		error = ustorage_fs_check_cmd(sc, 6,
1819 		    (1UL << 1) | (1UL << 4) | 1, 0);
1820 		if (error) {
1821 			break;
1822 		}
1823 		error = ustorage_fs_start_stop(sc);
1824 
1825 		break;
1826 
1827 	case SC_SYNCHRONIZE_CACHE:
1828 		error = ustorage_fs_min_len(sc, 0, -1U);
1829 		if (error) {
1830 			break;
1831 		}
1832 		error = ustorage_fs_check_cmd(sc, 10,
1833 		    (0xfUL << 2) | (3UL << 7) | 1, 1);
1834 		if (error) {
1835 			break;
1836 		}
1837 		error = ustorage_fs_synchronize_cache(sc);
1838 
1839 		break;
1840 
1841 	case SC_TEST_UNIT_READY:
1842 		error = ustorage_fs_min_len(sc, 0, -1U);
1843 		if (error) {
1844 			break;
1845 		}
1846 		error = ustorage_fs_check_cmd(sc, 6,
1847 		    0 | 1, 1);
1848 		break;
1849 
1850 		/*
1851 		 * Although optional, this command is used by MS-Windows.
1852 		 * We support a minimal version: BytChk must be 0.
1853 		 */
1854 	case SC_VERIFY:
1855 		error = ustorage_fs_min_len(sc, 0, -1U);
1856 		if (error) {
1857 			break;
1858 		}
1859 		error = ustorage_fs_check_cmd(sc, 10,
1860 		    (1UL << 1) | (0xfUL << 2) | (3UL << 7) | 1, 1);
1861 		if (error) {
1862 			break;
1863 		}
1864 		error = ustorage_fs_verify(sc);
1865 
1866 		break;
1867 
1868 	case SC_WRITE_6:
1869 		i = sc->sc_cbw->CBWCDB[4];
1870 		sc->sc_transfer.cmd_dir = DIR_READ;
1871 		temp = ((i == 0) ? 256UL : i);
1872 		error = ustorage_fs_min_len(sc, temp << 9, mask9);
1873 		if (error) {
1874 			break;
1875 		}
1876 		error = ustorage_fs_check_cmd(sc, 6,
1877 		    (7UL << 1) | (1UL << 4) | 1, 1);
1878 		if (error) {
1879 			break;
1880 		}
1881 		error = ustorage_fs_write(sc);
1882 
1883 		break;
1884 
1885 	case SC_WRITE_10:
1886 		sc->sc_transfer.cmd_dir = DIR_READ;
1887 		temp = get_be16(&sc->sc_cbw->CBWCDB[7]);
1888 		error = ustorage_fs_min_len(sc, temp << 9, mask9);
1889 		if (error) {
1890 			break;
1891 		}
1892 		error = ustorage_fs_check_cmd(sc, 10,
1893 		    (1UL << 1) | (0xfUL << 2) | (3UL << 7) | 1, 1);
1894 		if (error) {
1895 			break;
1896 		}
1897 		error = ustorage_fs_write(sc);
1898 
1899 		break;
1900 
1901 	case SC_WRITE_12:
1902 		sc->sc_transfer.cmd_dir = DIR_READ;
1903 		temp = get_be32(&sc->sc_cbw->CBWCDB[6]);
1904 		if (temp > (mask9 >> 9)) {
1905 			/* numerical overflow */
1906 			sc->sc_csw->bCSWStatus = CSWSTATUS_FAILED;
1907 			error = 1;
1908 			break;
1909 		}
1910 		error = ustorage_fs_min_len(sc, temp << 9, mask9);
1911 		if (error) {
1912 			break;
1913 		}
1914 		error = ustorage_fs_check_cmd(sc, 12,
1915 		    (1UL << 1) | (0xfUL << 2) | (0xfUL << 6) | 1, 1);
1916 		if (error) {
1917 			break;
1918 		}
1919 		error = ustorage_fs_write(sc);
1920 
1921 		break;
1922 
1923 		/*
1924 		 * Some mandatory commands that we recognize but don't
1925 		 * implement.  They don't mean much in this setting.
1926 		 * It's left as an exercise for anyone interested to
1927 		 * implement RESERVE and RELEASE in terms of Posix
1928 		 * locks.
1929 		 */
1930 	case SC_FORMAT_UNIT:
1931 	case SC_RELEASE:
1932 	case SC_RESERVE:
1933 	case SC_SEND_DIAGNOSTIC:
1934 		/* Fallthrough */
1935 
1936 	default:
1937 		error = ustorage_fs_min_len(sc, 0, -1U);
1938 		if (error) {
1939 			break;
1940 		}
1941 		error = ustorage_fs_check_cmd(sc, sc->sc_transfer.cmd_len,
1942 		    0xff, 0);
1943 		if (error) {
1944 			break;
1945 		}
1946 		sc->sc_transfer.currlun->sense_data =
1947 		    SS_INVALID_COMMAND;
1948 		error = 1;
1949 
1950 		break;
1951 	}
1952 	return (error);
1953 }
1954