Orange Pi5 kernel

Deprecated Linux kernel 5.10.110 for OrangePi 5/5B/5+ boards

3 Commits   0 Branches   0 Tags   |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300    1) // SPDX-License-Identifier: GPL-2.0+
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300    2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300    3)  * Transport & Protocol Driver for In-System Design, Inc. ISD200 ASIC
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300    4)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300    5)  * Current development and maintenance:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300    6)  *   (C) 2001-2002 Björn Stenberg (bjorn@haxx.se)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300    7)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300    8)  * Developed with the assistance of:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300    9)  *   (C) 2002 Alan Stern <stern@rowland.org>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   10)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   11)  * Initial work:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   12)  *   (C) 2000 In-System Design, Inc. (support@in-system.com)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   13)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   14)  * The ISD200 ASIC does not natively support ATA devices.  The chip
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   15)  * does implement an interface, the ATA Command Block (ATACB) which provides
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   16)  * a means of passing ATA commands and ATA register accesses to a device.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   17)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   18)  * History:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   19)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   20)  *  2002-10-19: Removed the specialized transfer routines.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   21)  *		(Alan Stern <stern@rowland.harvard.edu>)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   22)  *  2001-02-24: Removed lots of duplicate code and simplified the structure.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   23)  *	      (bjorn@haxx.se)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   24)  *  2002-01-16: Fixed endianness bug so it works on the ppc arch.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   25)  *	      (Luc Saillard <luc@saillard.org>)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   26)  *  2002-01-17: All bitfields removed.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   27)  *	      (bjorn@haxx.se)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   28)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   29) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   30) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   31) /* Include files */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   32) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   33) #include <linux/jiffies.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   34) #include <linux/errno.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   35) #include <linux/module.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   36) #include <linux/slab.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   37) #include <linux/ata.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   38) #include <linux/hdreg.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   39) #include <linux/scatterlist.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   40) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   41) #include <scsi/scsi.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   42) #include <scsi/scsi_cmnd.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   43) #include <scsi/scsi_device.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   44) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   45) #include "usb.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   46) #include "transport.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   47) #include "protocol.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   48) #include "debug.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   49) #include "scsiglue.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   50) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   51) #define DRV_NAME "ums-isd200"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   52) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   53) MODULE_DESCRIPTION("Driver for In-System Design, Inc. ISD200 ASIC");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   54) MODULE_AUTHOR("Björn Stenberg <bjorn@haxx.se>");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   55) MODULE_LICENSE("GPL");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   56) MODULE_IMPORT_NS(USB_STORAGE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   57) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   58) static int isd200_Initialization(struct us_data *us);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   59) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   60) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   61) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   62)  * The table of devices
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   63)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   64) #define UNUSUAL_DEV(id_vendor, id_product, bcdDeviceMin, bcdDeviceMax, \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   65) 		    vendorName, productName, useProtocol, useTransport, \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   66) 		    initFunction, flags) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   67) { USB_DEVICE_VER(id_vendor, id_product, bcdDeviceMin, bcdDeviceMax), \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   68)   .driver_info = (flags) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   69) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   70) static struct usb_device_id isd200_usb_ids[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   71) #	include "unusual_isd200.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   72) 	{ }		/* Terminating entry */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   73) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   74) MODULE_DEVICE_TABLE(usb, isd200_usb_ids);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   75) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   76) #undef UNUSUAL_DEV
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   77) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   78) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   79)  * The flags table
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   80)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   81) #define UNUSUAL_DEV(idVendor, idProduct, bcdDeviceMin, bcdDeviceMax, \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   82) 		    vendor_name, product_name, use_protocol, use_transport, \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   83) 		    init_function, Flags) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   84) { \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   85) 	.vendorName = vendor_name,	\
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   86) 	.productName = product_name,	\
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   87) 	.useProtocol = use_protocol,	\
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   88) 	.useTransport = use_transport,	\
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   89) 	.initFunction = init_function,	\
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   90) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   91) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   92) static struct us_unusual_dev isd200_unusual_dev_list[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   93) #	include "unusual_isd200.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   94) 	{ }		/* Terminating entry */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   95) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   96) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   97) #undef UNUSUAL_DEV
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   98) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   99) /* Timeout defines (in Seconds) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  100) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  101) #define ISD200_ENUM_BSY_TIMEOUT		35
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  102) #define ISD200_ENUM_DETECT_TIMEOUT      30
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  103) #define ISD200_DEFAULT_TIMEOUT		30
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  104) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  105) /* device flags */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  106) #define DF_ATA_DEVICE		0x0001
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  107) #define DF_MEDIA_STATUS_ENABLED	0x0002
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  108) #define DF_REMOVABLE_MEDIA	0x0004
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  109) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  110) /* capability bit definitions */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  111) #define CAPABILITY_DMA		0x01
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  112) #define CAPABILITY_LBA		0x02
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  113) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  114) /* command_setX bit definitions */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  115) #define COMMANDSET_REMOVABLE	0x02
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  116) #define COMMANDSET_MEDIA_STATUS 0x10
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  117) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  118) /* ATA Vendor Specific defines */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  119) #define ATA_ADDRESS_DEVHEAD_STD      0xa0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  120) #define ATA_ADDRESS_DEVHEAD_LBA_MODE 0x40    
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  121) #define ATA_ADDRESS_DEVHEAD_SLAVE    0x10
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  122) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  123) /* Action Select bits */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  124) #define ACTION_SELECT_0	     0x01
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  125) #define ACTION_SELECT_1	     0x02
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  126) #define ACTION_SELECT_2	     0x04
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  127) #define ACTION_SELECT_3	     0x08
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  128) #define ACTION_SELECT_4	     0x10
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  129) #define ACTION_SELECT_5	     0x20
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  130) #define ACTION_SELECT_6	     0x40
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  131) #define ACTION_SELECT_7	     0x80
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  132) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  133) /* Register Select bits */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  134) #define REG_ALTERNATE_STATUS	0x01
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  135) #define REG_DEVICE_CONTROL	0x01
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  136) #define REG_ERROR		0x02
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  137) #define REG_FEATURES		0x02
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  138) #define REG_SECTOR_COUNT	0x04
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  139) #define REG_SECTOR_NUMBER	0x08
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  140) #define REG_CYLINDER_LOW	0x10
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  141) #define REG_CYLINDER_HIGH	0x20
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  142) #define REG_DEVICE_HEAD		0x40
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  143) #define REG_STATUS		0x80
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  144) #define REG_COMMAND		0x80
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  145) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  146) /* ATA registers offset definitions */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  147) #define ATA_REG_ERROR_OFFSET		1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  148) #define ATA_REG_LCYL_OFFSET		4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  149) #define ATA_REG_HCYL_OFFSET		5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  150) #define ATA_REG_STATUS_OFFSET		7
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  151) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  152) /* ATA error definitions not in <linux/hdreg.h> */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  153) #define ATA_ERROR_MEDIA_CHANGE		0x20
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  154) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  155) /* ATA command definitions not in <linux/hdreg.h> */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  156) #define ATA_COMMAND_GET_MEDIA_STATUS	0xDA
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  157) #define ATA_COMMAND_MEDIA_EJECT		0xED
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  158) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  159) /* ATA drive control definitions */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  160) #define ATA_DC_DISABLE_INTERRUPTS	0x02
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  161) #define ATA_DC_RESET_CONTROLLER		0x04
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  162) #define ATA_DC_REENABLE_CONTROLLER	0x00
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  163) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  164) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  165)  *  General purpose return codes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  166)  */ 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  167) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  168) #define ISD200_ERROR		-1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  169) #define ISD200_GOOD		 0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  170) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  171) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  172)  * Transport return codes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  173)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  174) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  175) #define ISD200_TRANSPORT_GOOD       0   /* Transport good, command good     */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  176) #define ISD200_TRANSPORT_FAILED     1   /* Transport good, command failed   */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  177) #define ISD200_TRANSPORT_ERROR      2   /* Transport bad (i.e. device dead) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  178) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  179) /* driver action codes */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  180) #define	ACTION_READ_STATUS	0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  181) #define	ACTION_RESET		1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  182) #define	ACTION_REENABLE		2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  183) #define	ACTION_SOFT_RESET	3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  184) #define	ACTION_ENUM		4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  185) #define	ACTION_IDENTIFY		5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  186) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  187) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  188) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  189)  * ata_cdb struct
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  190)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  191) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  192) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  193) union ata_cdb {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  194) 	struct {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  195) 		unsigned char SignatureByte0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  196) 		unsigned char SignatureByte1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  197) 		unsigned char ActionSelect;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  198) 		unsigned char RegisterSelect;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  199) 		unsigned char TransferBlockSize;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  200) 		unsigned char WriteData3F6;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  201) 		unsigned char WriteData1F1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  202) 		unsigned char WriteData1F2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  203) 		unsigned char WriteData1F3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  204) 		unsigned char WriteData1F4;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  205) 		unsigned char WriteData1F5;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  206) 		unsigned char WriteData1F6;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  207) 		unsigned char WriteData1F7;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  208) 		unsigned char Reserved[3];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  209) 	} generic;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  210) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  211) 	struct {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  212) 		unsigned char SignatureByte0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  213) 		unsigned char SignatureByte1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  214) 		unsigned char ActionSelect;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  215) 		unsigned char RegisterSelect;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  216) 		unsigned char TransferBlockSize;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  217) 		unsigned char AlternateStatusByte;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  218) 		unsigned char ErrorByte;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  219) 		unsigned char SectorCountByte;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  220) 		unsigned char SectorNumberByte;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  221) 		unsigned char CylinderLowByte;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  222) 		unsigned char CylinderHighByte;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  223) 		unsigned char DeviceHeadByte;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  224) 		unsigned char StatusByte;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  225) 		unsigned char Reserved[3];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  226) 	} read;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  227) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  228) 	struct {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  229) 		unsigned char SignatureByte0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  230) 		unsigned char SignatureByte1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  231) 		unsigned char ActionSelect;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  232) 		unsigned char RegisterSelect;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  233) 		unsigned char TransferBlockSize;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  234) 		unsigned char DeviceControlByte;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  235) 		unsigned char FeaturesByte;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  236) 		unsigned char SectorCountByte;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  237) 		unsigned char SectorNumberByte;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  238) 		unsigned char CylinderLowByte;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  239) 		unsigned char CylinderHighByte;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  240) 		unsigned char DeviceHeadByte;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  241) 		unsigned char CommandByte;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  242) 		unsigned char Reserved[3];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  243) 	} write;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  244) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  245) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  246) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  247) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  248)  * Inquiry data structure. This is the data returned from the target
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  249)  * after it receives an inquiry.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  250)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  251)  * This structure may be extended by the number of bytes specified
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  252)  * in the field AdditionalLength. The defined size constant only
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  253)  * includes fields through ProductRevisionLevel.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  254)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  255) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  256) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  257)  * DeviceType field
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  258)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  259) #define DIRECT_ACCESS_DEVICE	    0x00    /* disks */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  260) #define DEVICE_REMOVABLE		0x80
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  261) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  262) struct inquiry_data {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  263)    	unsigned char DeviceType;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  264) 	unsigned char DeviceTypeModifier;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  265) 	unsigned char Versions;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  266) 	unsigned char Format; 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  267) 	unsigned char AdditionalLength;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  268) 	unsigned char Reserved[2];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  269) 	unsigned char Capability;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  270) 	unsigned char VendorId[8];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  271) 	unsigned char ProductId[16];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  272) 	unsigned char ProductRevisionLevel[4];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  273) 	unsigned char VendorSpecific[20];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  274) 	unsigned char Reserved3[40];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  275) } __attribute__ ((packed));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  276) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  277) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  278)  * INQUIRY data buffer size
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  279)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  280) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  281) #define INQUIRYDATABUFFERSIZE 36
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  282) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  283) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  284) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  285)  * ISD200 CONFIG data struct
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  286)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  287) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  288) #define ATACFG_TIMING	  0x0f
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  289) #define ATACFG_ATAPI_RESET     0x10
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  290) #define ATACFG_MASTER	  0x20
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  291) #define ATACFG_BLOCKSIZE       0xa0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  292) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  293) #define ATACFGE_LAST_LUN       0x07
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  294) #define ATACFGE_DESC_OVERRIDE  0x08
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  295) #define ATACFGE_STATE_SUSPEND  0x10
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  296) #define ATACFGE_SKIP_BOOT      0x20
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  297) #define ATACFGE_CONF_DESC2     0x40
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  298) #define ATACFGE_INIT_STATUS    0x80
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  299) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  300) #define CFG_CAPABILITY_SRST    0x01
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  301) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  302) struct isd200_config {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  303) 	unsigned char EventNotification;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  304) 	unsigned char ExternalClock;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  305) 	unsigned char ATAInitTimeout;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  306) 	unsigned char ATAConfig;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  307) 	unsigned char ATAMajorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  308) 	unsigned char ATAMinorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  309) 	unsigned char ATAExtraConfig;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  310) 	unsigned char Capability;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  311) }__attribute__ ((packed));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  312) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  313) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  314) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  315)  * ISD200 driver information struct
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  316)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  317) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  318) struct isd200_info {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  319) 	struct inquiry_data InquiryData;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  320) 	u16 *id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  321) 	struct isd200_config ConfigData;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  322) 	unsigned char *RegsBuf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  323) 	unsigned char ATARegs[8];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  324) 	unsigned char DeviceHead;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  325) 	unsigned char DeviceFlags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  326) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  327) 	/* maximum number of LUNs supported */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  328) 	unsigned char MaxLUNs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  329) 	unsigned char cmnd[BLK_MAX_CDB];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  330) 	struct scsi_cmnd srb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  331) 	struct scatterlist sg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  332) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  333) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  334) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  335) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  336)  * Read Capacity Data - returned in Big Endian format
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  337)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  338) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  339) struct read_capacity_data {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  340) 	__be32 LogicalBlockAddress;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  341) 	__be32 BytesPerBlock;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  342) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  343) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  344) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  345)  * Read Block Limits Data - returned in Big Endian format
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  346)  * This structure returns the maximum and minimum block
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  347)  * size for a TAPE device.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  348)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  349) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  350) struct read_block_limits {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  351) 	unsigned char Reserved;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  352) 	unsigned char BlockMaximumSize[3];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  353) 	unsigned char BlockMinimumSize[2];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  354) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  355) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  356) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  357) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  358)  * Sense Data Format
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  359)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  360) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  361) #define SENSE_ERRCODE	   0x7f
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  362) #define SENSE_ERRCODE_VALID     0x80
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  363) #define SENSE_FLAG_SENSE_KEY    0x0f
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  364) #define SENSE_FLAG_BAD_LENGTH   0x20
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  365) #define SENSE_FLAG_END_OF_MEDIA 0x40
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  366) #define SENSE_FLAG_FILE_MARK    0x80
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  367) struct sense_data {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  368) 	unsigned char ErrorCode;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  369) 	unsigned char SegmentNumber;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  370) 	unsigned char Flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  371) 	unsigned char Information[4];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  372) 	unsigned char AdditionalSenseLength;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  373) 	unsigned char CommandSpecificInformation[4];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  374) 	unsigned char AdditionalSenseCode;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  375) 	unsigned char AdditionalSenseCodeQualifier;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  376) 	unsigned char FieldReplaceableUnitCode;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  377) 	unsigned char SenseKeySpecific[3];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  378) } __attribute__ ((packed));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  379) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  380) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  381)  * Default request sense buffer size
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  382)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  383) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  384) #define SENSE_BUFFER_SIZE 18
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  385) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  386) /***********************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  387)  * Helper routines
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  388)  ***********************************************************************/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  389) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  390) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  391)  * isd200_build_sense
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  392)  *									 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  393)  *  Builds an artificial sense buffer to report the results of a 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  394)  *  failed command.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  395)  *								       
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  396)  * RETURNS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  397)  *    void
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  398)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  399) static void isd200_build_sense(struct us_data *us, struct scsi_cmnd *srb)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  400) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  401) 	struct isd200_info *info = (struct isd200_info *)us->extra;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  402) 	struct sense_data *buf = (struct sense_data *) &srb->sense_buffer[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  403) 	unsigned char error = info->ATARegs[ATA_REG_ERROR_OFFSET];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  404) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  405) 	if(error & ATA_ERROR_MEDIA_CHANGE) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  406) 		buf->ErrorCode = 0x70 | SENSE_ERRCODE_VALID;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  407) 		buf->AdditionalSenseLength = 0xb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  408) 		buf->Flags = UNIT_ATTENTION;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  409) 		buf->AdditionalSenseCode = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  410) 		buf->AdditionalSenseCodeQualifier = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  411) 	} else if (error & ATA_MCR) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  412) 		buf->ErrorCode = 0x70 | SENSE_ERRCODE_VALID;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  413) 		buf->AdditionalSenseLength = 0xb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  414) 		buf->Flags =  UNIT_ATTENTION;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  415) 		buf->AdditionalSenseCode = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  416) 		buf->AdditionalSenseCodeQualifier = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  417) 	} else if (error & ATA_TRK0NF) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  418) 		buf->ErrorCode = 0x70 | SENSE_ERRCODE_VALID;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  419) 		buf->AdditionalSenseLength = 0xb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  420) 		buf->Flags =  NOT_READY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  421) 		buf->AdditionalSenseCode = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  422) 		buf->AdditionalSenseCodeQualifier = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  423) 	} else if (error & ATA_UNC) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  424) 		buf->ErrorCode = 0x70 | SENSE_ERRCODE_VALID;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  425) 		buf->AdditionalSenseLength = 0xb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  426) 		buf->Flags =  DATA_PROTECT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  427) 		buf->AdditionalSenseCode = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  428) 		buf->AdditionalSenseCodeQualifier = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  429) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  430) 		buf->ErrorCode = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  431) 		buf->AdditionalSenseLength = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  432) 		buf->Flags =  0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  433) 		buf->AdditionalSenseCode = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  434) 		buf->AdditionalSenseCodeQualifier = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  435) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  436) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  437) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  438) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  439) /***********************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  440)  * Transport routines
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  441)  ***********************************************************************/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  442) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  443) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  444)  *  isd200_set_srb(), isd200_srb_set_bufflen()
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  445)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  446)  * Two helpers to facilitate in initialization of scsi_cmnd structure
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  447)  * Will need to change when struct scsi_cmnd changes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  448)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  449) static void isd200_set_srb(struct isd200_info *info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  450) 	enum dma_data_direction dir, void* buff, unsigned bufflen)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  451) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  452) 	struct scsi_cmnd *srb = &info->srb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  453) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  454) 	if (buff)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  455) 		sg_init_one(&info->sg, buff, bufflen);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  456) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  457) 	srb->sc_data_direction = dir;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  458) 	srb->sdb.table.sgl = buff ? &info->sg : NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  459) 	srb->sdb.length = bufflen;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  460) 	srb->sdb.table.nents = buff ? 1 : 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  461) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  462) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  463) static void isd200_srb_set_bufflen(struct scsi_cmnd *srb, unsigned bufflen)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  464) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  465) 	srb->sdb.length = bufflen;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  466) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  467) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  468) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  469) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  470)  *  isd200_action
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  471)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  472)  * Routine for sending commands to the isd200
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  473)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  474)  * RETURNS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  475)  *    ISD status code
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  476)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  477) static int isd200_action( struct us_data *us, int action, 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  478) 			  void* pointer, int value )
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  479) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  480) 	union ata_cdb ata;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  481) 	/* static to prevent this large struct being placed on the valuable stack */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  482) 	static struct scsi_device srb_dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  483) 	struct isd200_info *info = (struct isd200_info *)us->extra;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  484) 	struct scsi_cmnd *srb = &info->srb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  485) 	int status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  486) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  487) 	memset(&ata, 0, sizeof(ata));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  488) 	srb->cmnd = info->cmnd;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  489) 	srb->device = &srb_dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  490) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  491) 	ata.generic.SignatureByte0 = info->ConfigData.ATAMajorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  492) 	ata.generic.SignatureByte1 = info->ConfigData.ATAMinorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  493) 	ata.generic.TransferBlockSize = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  494) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  495) 	switch ( action ) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  496) 	case ACTION_READ_STATUS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  497) 		usb_stor_dbg(us, "   isd200_action(READ_STATUS)\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  498) 		ata.generic.ActionSelect = ACTION_SELECT_0|ACTION_SELECT_2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  499) 		ata.generic.RegisterSelect =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  500) 		  REG_CYLINDER_LOW | REG_CYLINDER_HIGH |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  501) 		  REG_STATUS | REG_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  502) 		isd200_set_srb(info, DMA_FROM_DEVICE, pointer, value);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  503) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  504) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  505) 	case ACTION_ENUM:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  506) 		usb_stor_dbg(us, "   isd200_action(ENUM,0x%02x)\n", value);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  507) 		ata.generic.ActionSelect = ACTION_SELECT_1|ACTION_SELECT_2|
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  508) 					   ACTION_SELECT_3|ACTION_SELECT_4|
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  509) 					   ACTION_SELECT_5;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  510) 		ata.generic.RegisterSelect = REG_DEVICE_HEAD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  511) 		ata.write.DeviceHeadByte = value;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  512) 		isd200_set_srb(info, DMA_NONE, NULL, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  513) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  514) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  515) 	case ACTION_RESET:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  516) 		usb_stor_dbg(us, "   isd200_action(RESET)\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  517) 		ata.generic.ActionSelect = ACTION_SELECT_1|ACTION_SELECT_2|
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  518) 					   ACTION_SELECT_3|ACTION_SELECT_4;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  519) 		ata.generic.RegisterSelect = REG_DEVICE_CONTROL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  520) 		ata.write.DeviceControlByte = ATA_DC_RESET_CONTROLLER;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  521) 		isd200_set_srb(info, DMA_NONE, NULL, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  522) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  523) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  524) 	case ACTION_REENABLE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  525) 		usb_stor_dbg(us, "   isd200_action(REENABLE)\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  526) 		ata.generic.ActionSelect = ACTION_SELECT_1|ACTION_SELECT_2|
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  527) 					   ACTION_SELECT_3|ACTION_SELECT_4;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  528) 		ata.generic.RegisterSelect = REG_DEVICE_CONTROL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  529) 		ata.write.DeviceControlByte = ATA_DC_REENABLE_CONTROLLER;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  530) 		isd200_set_srb(info, DMA_NONE, NULL, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  531) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  532) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  533) 	case ACTION_SOFT_RESET:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  534) 		usb_stor_dbg(us, "   isd200_action(SOFT_RESET)\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  535) 		ata.generic.ActionSelect = ACTION_SELECT_1|ACTION_SELECT_5;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  536) 		ata.generic.RegisterSelect = REG_DEVICE_HEAD | REG_COMMAND;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  537) 		ata.write.DeviceHeadByte = info->DeviceHead;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  538) 		ata.write.CommandByte = ATA_CMD_DEV_RESET;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  539) 		isd200_set_srb(info, DMA_NONE, NULL, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  540) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  541) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  542) 	case ACTION_IDENTIFY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  543) 		usb_stor_dbg(us, "   isd200_action(IDENTIFY)\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  544) 		ata.generic.RegisterSelect = REG_COMMAND;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  545) 		ata.write.CommandByte = ATA_CMD_ID_ATA;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  546) 		isd200_set_srb(info, DMA_FROM_DEVICE, info->id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  547) 				ATA_ID_WORDS * 2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  548) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  549) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  550) 	default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  551) 		usb_stor_dbg(us, "Error: Undefined action %d\n", action);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  552) 		return ISD200_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  553) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  554) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  555) 	memcpy(srb->cmnd, &ata, sizeof(ata.generic));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  556) 	srb->cmd_len = sizeof(ata.generic);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  557) 	status = usb_stor_Bulk_transport(srb, us);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  558) 	if (status == USB_STOR_TRANSPORT_GOOD)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  559) 		status = ISD200_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  560) 	else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  561) 		usb_stor_dbg(us, "   isd200_action(0x%02x) error: %d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  562) 			     action, status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  563) 		status = ISD200_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  564) 		/* need to reset device here */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  565) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  566) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  567) 	return status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  568) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  569) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  570) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  571)  * isd200_read_regs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  572)  *									 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  573)  * Read ATA Registers
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  574)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  575)  * RETURNS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  576)  *    ISD status code
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  577)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  578) static int isd200_read_regs( struct us_data *us )
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  579) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  580) 	struct isd200_info *info = (struct isd200_info *)us->extra;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  581) 	int retStatus = ISD200_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  582) 	int transferStatus;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  583) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  584) 	usb_stor_dbg(us, "Entering isd200_IssueATAReadRegs\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  585) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  586) 	transferStatus = isd200_action( us, ACTION_READ_STATUS,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  587) 				    info->RegsBuf, sizeof(info->ATARegs) );
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  588) 	if (transferStatus != ISD200_TRANSPORT_GOOD) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  589) 		usb_stor_dbg(us, "   Error reading ATA registers\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  590) 		retStatus = ISD200_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  591) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  592) 		memcpy(info->ATARegs, info->RegsBuf, sizeof(info->ATARegs));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  593) 		usb_stor_dbg(us, "   Got ATA Register[ATA_REG_ERROR_OFFSET] = 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  594) 			     info->ATARegs[ATA_REG_ERROR_OFFSET]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  595) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  596) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  597) 	return retStatus;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  598) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  599) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  600) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  601) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  602)  * Invoke the transport and basic error-handling/recovery methods
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  603)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  604)  * This is used by the protocol layers to actually send the message to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  605)  * the device and receive the response.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  606)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  607) static void isd200_invoke_transport( struct us_data *us, 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  608) 			      struct scsi_cmnd *srb, 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  609) 			      union ata_cdb *ataCdb )
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  610) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  611) 	int need_auto_sense = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  612) 	int transferStatus;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  613) 	int result;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  614) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  615) 	/* send the command to the transport layer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  616) 	memcpy(srb->cmnd, ataCdb, sizeof(ataCdb->generic));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  617) 	srb->cmd_len = sizeof(ataCdb->generic);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  618) 	transferStatus = usb_stor_Bulk_transport(srb, us);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  619) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  620) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  621) 	 * if the command gets aborted by the higher layers, we need to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  622) 	 * short-circuit all other processing
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  623) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  624) 	if (test_bit(US_FLIDX_TIMED_OUT, &us->dflags)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  625) 		usb_stor_dbg(us, "-- command was aborted\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  626) 		goto Handle_Abort;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  627) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  628) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  629) 	switch (transferStatus) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  630) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  631) 	case USB_STOR_TRANSPORT_GOOD:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  632) 		/* Indicate a good result */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  633) 		srb->result = SAM_STAT_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  634) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  635) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  636) 	case USB_STOR_TRANSPORT_NO_SENSE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  637) 		usb_stor_dbg(us, "-- transport indicates protocol failure\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  638) 		srb->result = SAM_STAT_CHECK_CONDITION;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  639) 		return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  640) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  641) 	case USB_STOR_TRANSPORT_FAILED:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  642) 		usb_stor_dbg(us, "-- transport indicates command failure\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  643) 		need_auto_sense = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  644) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  645) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  646) 	case USB_STOR_TRANSPORT_ERROR:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  647) 		usb_stor_dbg(us, "-- transport indicates transport error\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  648) 		srb->result = DID_ERROR << 16;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  649) 		/* Need reset here */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  650) 		return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  651)     
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  652) 	default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  653) 		usb_stor_dbg(us, "-- transport indicates unknown error\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  654) 		srb->result = DID_ERROR << 16;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  655) 		/* Need reset here */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  656) 		return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  657) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  658) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  659) 	if ((scsi_get_resid(srb) > 0) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  660) 	    !((srb->cmnd[0] == REQUEST_SENSE) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  661) 	      (srb->cmnd[0] == INQUIRY) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  662) 	      (srb->cmnd[0] == MODE_SENSE) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  663) 	      (srb->cmnd[0] == LOG_SENSE) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  664) 	      (srb->cmnd[0] == MODE_SENSE_10))) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  665) 		usb_stor_dbg(us, "-- unexpectedly short transfer\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  666) 		need_auto_sense = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  667) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  668) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  669) 	if (need_auto_sense) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  670) 		result = isd200_read_regs(us);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  671) 		if (test_bit(US_FLIDX_TIMED_OUT, &us->dflags)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  672) 			usb_stor_dbg(us, "-- auto-sense aborted\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  673) 			goto Handle_Abort;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  674) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  675) 		if (result == ISD200_GOOD) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  676) 			isd200_build_sense(us, srb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  677) 			srb->result = SAM_STAT_CHECK_CONDITION;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  678) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  679) 			/* If things are really okay, then let's show that */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  680) 			if ((srb->sense_buffer[2] & 0xf) == 0x0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  681) 				srb->result = SAM_STAT_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  682) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  683) 			srb->result = DID_ERROR << 16;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  684) 			/* Need reset here */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  685) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  686) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  687) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  688) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  689) 	 * Regardless of auto-sense, if we _know_ we have an error
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  690) 	 * condition, show that in the result code
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  691) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  692) 	if (transferStatus == USB_STOR_TRANSPORT_FAILED)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  693) 		srb->result = SAM_STAT_CHECK_CONDITION;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  694) 	return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  695) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  696) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  697) 	 * abort processing: the bulk-only transport requires a reset
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  698) 	 * following an abort
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  699) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  700) 	Handle_Abort:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  701) 	srb->result = DID_ABORT << 16;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  702) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  703) 	/* permit the reset transfer to take place */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  704) 	clear_bit(US_FLIDX_ABORTING, &us->dflags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  705) 	/* Need reset here */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  706) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  707) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  708) #ifdef CONFIG_USB_STORAGE_DEBUG
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  709) static void isd200_log_config(struct us_data *us, struct isd200_info *info)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  710) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  711) 	usb_stor_dbg(us, "      Event Notification: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  712) 		     info->ConfigData.EventNotification);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  713) 	usb_stor_dbg(us, "      External Clock: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  714) 		     info->ConfigData.ExternalClock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  715) 	usb_stor_dbg(us, "      ATA Init Timeout: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  716) 		     info->ConfigData.ATAInitTimeout);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  717) 	usb_stor_dbg(us, "      ATAPI Command Block Size: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  718) 		     (info->ConfigData.ATAConfig & ATACFG_BLOCKSIZE) >> 6);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  719) 	usb_stor_dbg(us, "      Master/Slave Selection: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  720) 		     info->ConfigData.ATAConfig & ATACFG_MASTER);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  721) 	usb_stor_dbg(us, "      ATAPI Reset: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  722) 		     info->ConfigData.ATAConfig & ATACFG_ATAPI_RESET);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  723) 	usb_stor_dbg(us, "      ATA Timing: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  724) 		     info->ConfigData.ATAConfig & ATACFG_TIMING);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  725) 	usb_stor_dbg(us, "      ATA Major Command: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  726) 		     info->ConfigData.ATAMajorCommand);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  727) 	usb_stor_dbg(us, "      ATA Minor Command: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  728) 		     info->ConfigData.ATAMinorCommand);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  729) 	usb_stor_dbg(us, "      Init Status: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  730) 		     info->ConfigData.ATAExtraConfig & ATACFGE_INIT_STATUS);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  731) 	usb_stor_dbg(us, "      Config Descriptor 2: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  732) 		     info->ConfigData.ATAExtraConfig & ATACFGE_CONF_DESC2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  733) 	usb_stor_dbg(us, "      Skip Device Boot: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  734) 		     info->ConfigData.ATAExtraConfig & ATACFGE_SKIP_BOOT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  735) 	usb_stor_dbg(us, "      ATA 3 State Suspend: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  736) 		     info->ConfigData.ATAExtraConfig & ATACFGE_STATE_SUSPEND);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  737) 	usb_stor_dbg(us, "      Descriptor Override: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  738) 		     info->ConfigData.ATAExtraConfig & ATACFGE_DESC_OVERRIDE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  739) 	usb_stor_dbg(us, "      Last LUN Identifier: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  740) 		     info->ConfigData.ATAExtraConfig & ATACFGE_LAST_LUN);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  741) 	usb_stor_dbg(us, "      SRST Enable: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  742) 		     info->ConfigData.ATAExtraConfig & CFG_CAPABILITY_SRST);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  743) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  744) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  745) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  746) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  747)  * isd200_write_config
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  748)  *									 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  749)  * Write the ISD200 Configuration data
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  750)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  751)  * RETURNS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  752)  *    ISD status code
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  753)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  754) static int isd200_write_config( struct us_data *us ) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  755) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  756) 	struct isd200_info *info = (struct isd200_info *)us->extra;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  757) 	int retStatus = ISD200_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  758) 	int result;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  759) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  760) #ifdef CONFIG_USB_STORAGE_DEBUG
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  761) 	usb_stor_dbg(us, "Entering isd200_write_config\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  762) 	usb_stor_dbg(us, "   Writing the following ISD200 Config Data:\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  763) 	isd200_log_config(us, info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  764) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  765) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  766) 	/* let's send the command via the control pipe */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  767) 	result = usb_stor_ctrl_transfer(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  768) 		us, 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  769) 		us->send_ctrl_pipe,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  770) 		0x01, 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  771) 		USB_TYPE_VENDOR | USB_RECIP_DEVICE | USB_DIR_OUT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  772) 		0x0000, 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  773) 		0x0002, 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  774) 		(void *) &info->ConfigData, 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  775) 		sizeof(info->ConfigData));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  776) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  777) 	if (result >= 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  778) 		usb_stor_dbg(us, "   ISD200 Config Data was written successfully\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  779) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  780) 		usb_stor_dbg(us, "   Request to write ISD200 Config Data failed!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  781) 		retStatus = ISD200_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  782) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  783) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  784) 	usb_stor_dbg(us, "Leaving isd200_write_config %08X\n", retStatus);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  785) 	return retStatus;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  786) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  787) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  788) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  789) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  790)  * isd200_read_config
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  791)  *									 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  792)  * Reads the ISD200 Configuration data
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  793)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  794)  * RETURNS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  795)  *    ISD status code
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  796)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  797) static int isd200_read_config( struct us_data *us ) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  798) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  799) 	struct isd200_info *info = (struct isd200_info *)us->extra;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  800) 	int retStatus = ISD200_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  801) 	int result;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  802) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  803) 	usb_stor_dbg(us, "Entering isd200_read_config\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  804) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  805) 	/* read the configuration information from ISD200.  Use this to */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  806) 	/* determine what the special ATA CDB bytes are.		*/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  807) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  808) 	result = usb_stor_ctrl_transfer(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  809) 		us, 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  810) 		us->recv_ctrl_pipe,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  811) 		0x02, 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  812) 		USB_TYPE_VENDOR | USB_RECIP_DEVICE | USB_DIR_IN,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  813) 		0x0000, 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  814) 		0x0002, 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  815) 		(void *) &info->ConfigData, 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  816) 		sizeof(info->ConfigData));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  817) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  818) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  819) 	if (result >= 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  820) 		usb_stor_dbg(us, "   Retrieved the following ISD200 Config Data:\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  821) #ifdef CONFIG_USB_STORAGE_DEBUG
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  822) 		isd200_log_config(us, info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  823) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  824) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  825) 		usb_stor_dbg(us, "   Request to get ISD200 Config Data failed!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  826) 		retStatus = ISD200_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  827) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  828) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  829) 	usb_stor_dbg(us, "Leaving isd200_read_config %08X\n", retStatus);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  830) 	return retStatus;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  831) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  832) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  833) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  834) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  835)  * isd200_atapi_soft_reset
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  836)  *									 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  837)  * Perform an Atapi Soft Reset on the device
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  838)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  839)  * RETURNS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  840)  *    NT status code
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  841)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  842) static int isd200_atapi_soft_reset( struct us_data *us ) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  843) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  844) 	int retStatus = ISD200_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  845) 	int transferStatus;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  846) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  847) 	usb_stor_dbg(us, "Entering isd200_atapi_soft_reset\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  848) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  849) 	transferStatus = isd200_action( us, ACTION_SOFT_RESET, NULL, 0 );
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  850) 	if (transferStatus != ISD200_TRANSPORT_GOOD) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  851) 		usb_stor_dbg(us, "   Error issuing Atapi Soft Reset\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  852) 		retStatus = ISD200_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  853) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  854) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  855) 	usb_stor_dbg(us, "Leaving isd200_atapi_soft_reset %08X\n", retStatus);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  856) 	return retStatus;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  857) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  858) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  859) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  860) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  861)  * isd200_srst
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  862)  *									 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  863)  * Perform an SRST on the device
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  864)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  865)  * RETURNS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  866)  *    ISD status code
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  867)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  868) static int isd200_srst( struct us_data *us ) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  869) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  870) 	int retStatus = ISD200_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  871) 	int transferStatus;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  872) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  873) 	usb_stor_dbg(us, "Entering isd200_SRST\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  874) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  875) 	transferStatus = isd200_action( us, ACTION_RESET, NULL, 0 );
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  876) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  877) 	/* check to see if this request failed */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  878) 	if (transferStatus != ISD200_TRANSPORT_GOOD) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  879) 		usb_stor_dbg(us, "   Error issuing SRST\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  880) 		retStatus = ISD200_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  881) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  882) 		/* delay 10ms to give the drive a chance to see it */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  883) 		msleep(10);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  884) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  885) 		transferStatus = isd200_action( us, ACTION_REENABLE, NULL, 0 );
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  886) 		if (transferStatus != ISD200_TRANSPORT_GOOD) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  887) 			usb_stor_dbg(us, "   Error taking drive out of reset\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  888) 			retStatus = ISD200_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  889) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  890) 			/* delay 50ms to give the drive a chance to recover after SRST */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  891) 			msleep(50);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  892) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  893) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  894) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  895) 	usb_stor_dbg(us, "Leaving isd200_srst %08X\n", retStatus);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  896) 	return retStatus;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  897) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  898) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  899) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  900) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  901)  * isd200_try_enum
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  902)  *									 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  903)  * Helper function for isd200_manual_enum(). Does ENUM and READ_STATUS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  904)  * and tries to analyze the status registers
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  905)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  906)  * RETURNS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  907)  *    ISD status code
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  908)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  909) static int isd200_try_enum(struct us_data *us, unsigned char master_slave,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  910) 			   int detect )
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  911) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  912) 	int status = ISD200_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  913) 	unsigned long endTime;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  914) 	struct isd200_info *info = (struct isd200_info *)us->extra;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  915) 	unsigned char *regs = info->RegsBuf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  916) 	int recheckAsMaster = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  917) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  918) 	if ( detect )
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  919) 		endTime = jiffies + ISD200_ENUM_DETECT_TIMEOUT * HZ;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  920) 	else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  921) 		endTime = jiffies + ISD200_ENUM_BSY_TIMEOUT * HZ;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  922) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  923) 	/* loop until we detect !BSY or timeout */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  924) 	while(1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  925) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  926) 		status = isd200_action( us, ACTION_ENUM, NULL, master_slave );
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  927) 		if ( status != ISD200_GOOD )
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  928) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  929) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  930) 		status = isd200_action( us, ACTION_READ_STATUS, 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  931) 					regs, 8 );
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  932) 		if ( status != ISD200_GOOD )
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  933) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  934) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  935) 		if (!detect) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  936) 			if (regs[ATA_REG_STATUS_OFFSET] & ATA_BUSY) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  937) 				usb_stor_dbg(us, "   %s status is still BSY, try again...\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  938) 					     master_slave == ATA_ADDRESS_DEVHEAD_STD ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  939) 					     "Master" : "Slave");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  940) 			} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  941) 				usb_stor_dbg(us, "   %s status !BSY, continue with next operation\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  942) 					     master_slave == ATA_ADDRESS_DEVHEAD_STD ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  943) 					     "Master" : "Slave");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  944) 				break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  945) 			}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  946) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  947) 		/* check for ATA_BUSY and */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  948) 		/* ATA_DF (workaround ATA Zip drive) and */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  949) 		/* ATA_ERR (workaround for Archos CD-ROM) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  950) 		else if (regs[ATA_REG_STATUS_OFFSET] &
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  951) 			 (ATA_BUSY | ATA_DF | ATA_ERR)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  952) 			usb_stor_dbg(us, "   Status indicates it is not ready, try again...\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  953) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  954) 		/* check for DRDY, ATA devices set DRDY after SRST */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  955) 		else if (regs[ATA_REG_STATUS_OFFSET] & ATA_DRDY) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  956) 			usb_stor_dbg(us, "   Identified ATA device\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  957) 			info->DeviceFlags |= DF_ATA_DEVICE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  958) 			info->DeviceHead = master_slave;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  959) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  960) 		} 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  961) 		/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  962) 		 * check Cylinder High/Low to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  963) 		 * determine if it is an ATAPI device
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  964) 		 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  965) 		else if (regs[ATA_REG_HCYL_OFFSET] == 0xEB &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  966) 			 regs[ATA_REG_LCYL_OFFSET] == 0x14) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  967) 			/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  968) 			 * It seems that the RICOH
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  969) 			 * MP6200A CD/RW drive will
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  970) 			 * report itself okay as a
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  971) 			 * slave when it is really a
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  972) 			 * master. So this check again
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  973) 			 * as a master device just to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  974) 			 * make sure it doesn't report
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  975) 			 * itself okay as a master also
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  976) 			 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  977) 			if ((master_slave & ATA_ADDRESS_DEVHEAD_SLAVE) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  978) 			    !recheckAsMaster) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  979) 				usb_stor_dbg(us, "   Identified ATAPI device as slave.  Rechecking again as master\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  980) 				recheckAsMaster = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  981) 				master_slave = ATA_ADDRESS_DEVHEAD_STD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  982) 			} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  983) 				usb_stor_dbg(us, "   Identified ATAPI device\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  984) 				info->DeviceHead = master_slave;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  985) 			      
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  986) 				status = isd200_atapi_soft_reset(us);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  987) 				break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  988) 			}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  989) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  990) 			usb_stor_dbg(us, "   Not ATA, not ATAPI - Weird\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  991) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  992) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  993) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  994) 		/* check for timeout on this request */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  995) 		if (time_after_eq(jiffies, endTime)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  996) 			if (!detect)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  997) 				usb_stor_dbg(us, "   BSY check timeout, just continue with next operation...\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  998) 			else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  999) 				usb_stor_dbg(us, "   Device detect timeout!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1000) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1001) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1002) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1003) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1004) 	return status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1005) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1006) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1007) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1008)  * isd200_manual_enum
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1009)  *									 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1010)  * Determines if the drive attached is an ATA or ATAPI and if it is a
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1011)  * master or slave.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1012)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1013)  * RETURNS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1014)  *    ISD status code
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1015)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1016) static int isd200_manual_enum(struct us_data *us)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1017) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1018) 	struct isd200_info *info = (struct isd200_info *)us->extra;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1019) 	int retStatus = ISD200_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1020) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1021) 	usb_stor_dbg(us, "Entering isd200_manual_enum\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1022) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1023) 	retStatus = isd200_read_config(us);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1024) 	if (retStatus == ISD200_GOOD) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1025) 		int isslave;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1026) 		/* master or slave? */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1027) 		retStatus = isd200_try_enum( us, ATA_ADDRESS_DEVHEAD_STD, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1028) 		if (retStatus == ISD200_GOOD)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1029) 			retStatus = isd200_try_enum( us, ATA_ADDRESS_DEVHEAD_SLAVE, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1030) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1031) 		if (retStatus == ISD200_GOOD) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1032) 			retStatus = isd200_srst(us);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1033) 			if (retStatus == ISD200_GOOD)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1034) 				/* ata or atapi? */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1035) 				retStatus = isd200_try_enum( us, ATA_ADDRESS_DEVHEAD_STD, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1036) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1037) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1038) 		isslave = (info->DeviceHead & ATA_ADDRESS_DEVHEAD_SLAVE) ? 1 : 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1039) 		if (!(info->ConfigData.ATAConfig & ATACFG_MASTER)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1040) 			usb_stor_dbg(us, "   Setting Master/Slave selection to %d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1041) 				     isslave);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1042) 			info->ConfigData.ATAConfig &= 0x3f;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1043) 			info->ConfigData.ATAConfig |= (isslave<<6);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1044) 			retStatus = isd200_write_config(us);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1045) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1046) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1047) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1048) 	usb_stor_dbg(us, "Leaving isd200_manual_enum %08X\n", retStatus);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1049) 	return(retStatus);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1050) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1051) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1052) static void isd200_fix_driveid(u16 *id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1053) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1054) #ifndef __LITTLE_ENDIAN
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1055) # ifdef __BIG_ENDIAN
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1056) 	int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1057) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1058) 	for (i = 0; i < ATA_ID_WORDS; i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1059) 		id[i] = __le16_to_cpu(id[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1060) # else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1061) #  error "Please fix <asm/byteorder.h>"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1062) # endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1063) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1064) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1065) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1066) static void isd200_dump_driveid(struct us_data *us, u16 *id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1067) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1068) 	usb_stor_dbg(us, "   Identify Data Structure:\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1069) 	usb_stor_dbg(us, "      config = 0x%x\n",	id[ATA_ID_CONFIG]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1070) 	usb_stor_dbg(us, "      cyls = 0x%x\n",		id[ATA_ID_CYLS]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1071) 	usb_stor_dbg(us, "      heads = 0x%x\n",	id[ATA_ID_HEADS]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1072) 	usb_stor_dbg(us, "      track_bytes = 0x%x\n",	id[4]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1073) 	usb_stor_dbg(us, "      sector_bytes = 0x%x\n", id[5]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1074) 	usb_stor_dbg(us, "      sectors = 0x%x\n",	id[ATA_ID_SECTORS]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1075) 	usb_stor_dbg(us, "      serial_no[0] = 0x%x\n", *(char *)&id[ATA_ID_SERNO]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1076) 	usb_stor_dbg(us, "      buf_type = 0x%x\n",	id[20]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1077) 	usb_stor_dbg(us, "      buf_size = 0x%x\n",	id[ATA_ID_BUF_SIZE]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1078) 	usb_stor_dbg(us, "      ecc_bytes = 0x%x\n",	id[22]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1079) 	usb_stor_dbg(us, "      fw_rev[0] = 0x%x\n",	*(char *)&id[ATA_ID_FW_REV]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1080) 	usb_stor_dbg(us, "      model[0] = 0x%x\n",	*(char *)&id[ATA_ID_PROD]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1081) 	usb_stor_dbg(us, "      max_multsect = 0x%x\n", id[ATA_ID_MAX_MULTSECT] & 0xff);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1082) 	usb_stor_dbg(us, "      dword_io = 0x%x\n",	id[ATA_ID_DWORD_IO]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1083) 	usb_stor_dbg(us, "      capability = 0x%x\n",	id[ATA_ID_CAPABILITY] >> 8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1084) 	usb_stor_dbg(us, "      tPIO = 0x%x\n",	  id[ATA_ID_OLD_PIO_MODES] >> 8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1085) 	usb_stor_dbg(us, "      tDMA = 0x%x\n",	  id[ATA_ID_OLD_DMA_MODES] >> 8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1086) 	usb_stor_dbg(us, "      field_valid = 0x%x\n",	id[ATA_ID_FIELD_VALID]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1087) 	usb_stor_dbg(us, "      cur_cyls = 0x%x\n",	id[ATA_ID_CUR_CYLS]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1088) 	usb_stor_dbg(us, "      cur_heads = 0x%x\n",	id[ATA_ID_CUR_HEADS]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1089) 	usb_stor_dbg(us, "      cur_sectors = 0x%x\n",	id[ATA_ID_CUR_SECTORS]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1090) 	usb_stor_dbg(us, "      cur_capacity = 0x%x\n", ata_id_u32(id, 57));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1091) 	usb_stor_dbg(us, "      multsect = 0x%x\n",	id[ATA_ID_MULTSECT] & 0xff);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1092) 	usb_stor_dbg(us, "      lba_capacity = 0x%x\n", ata_id_u32(id, ATA_ID_LBA_CAPACITY));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1093) 	usb_stor_dbg(us, "      command_set_1 = 0x%x\n", id[ATA_ID_COMMAND_SET_1]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1094) 	usb_stor_dbg(us, "      command_set_2 = 0x%x\n", id[ATA_ID_COMMAND_SET_2]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1095) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1096) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1097) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1098)  * isd200_get_inquiry_data
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1099)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1100)  * Get inquiry data
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1101)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1102)  * RETURNS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1103)  *    ISD status code
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1104)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1105) static int isd200_get_inquiry_data( struct us_data *us )
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1106) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1107) 	struct isd200_info *info = (struct isd200_info *)us->extra;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1108) 	int retStatus = ISD200_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1109) 	u16 *id = info->id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1110) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1111) 	usb_stor_dbg(us, "Entering isd200_get_inquiry_data\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1112) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1113) 	/* set default to Master */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1114) 	info->DeviceHead = ATA_ADDRESS_DEVHEAD_STD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1115) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1116) 	/* attempt to manually enumerate this device */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1117) 	retStatus = isd200_manual_enum(us);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1118) 	if (retStatus == ISD200_GOOD) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1119) 		int transferStatus;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1120) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1121) 		/* check for an ATA device */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1122) 		if (info->DeviceFlags & DF_ATA_DEVICE) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1123) 			/* this must be an ATA device */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1124) 			/* perform an ATA Command Identify */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1125) 			transferStatus = isd200_action( us, ACTION_IDENTIFY,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1126) 							id, ATA_ID_WORDS * 2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1127) 			if (transferStatus != ISD200_TRANSPORT_GOOD) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1128) 				/* Error issuing ATA Command Identify */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1129) 				usb_stor_dbg(us, "   Error issuing ATA Command Identify\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1130) 				retStatus = ISD200_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1131) 			} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1132) 				/* ATA Command Identify successful */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1133) 				int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1134) 				__be16 *src;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1135) 				__u16 *dest;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1136) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1137) 				isd200_fix_driveid(id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1138) 				isd200_dump_driveid(us, id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1139) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1140) 				memset(&info->InquiryData, 0, sizeof(info->InquiryData));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1141) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1142) 				/* Standard IDE interface only supports disks */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1143) 				info->InquiryData.DeviceType = DIRECT_ACCESS_DEVICE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1144) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1145) 				/* The length must be at least 36 (5 + 31) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1146) 				info->InquiryData.AdditionalLength = 0x1F;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1147) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1148) 				if (id[ATA_ID_COMMAND_SET_1] & COMMANDSET_MEDIA_STATUS) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1149) 					/* set the removable bit */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1150) 					info->InquiryData.DeviceTypeModifier = DEVICE_REMOVABLE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1151) 					info->DeviceFlags |= DF_REMOVABLE_MEDIA;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1152) 				}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1153) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1154) 				/* Fill in vendor identification fields */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1155) 				src = (__be16 *)&id[ATA_ID_PROD];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1156) 				dest = (__u16*)info->InquiryData.VendorId;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1157) 				for (i = 0; i < 4; i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1158) 					dest[i] = be16_to_cpu(src[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1159) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1160) 				src = (__be16 *)&id[ATA_ID_PROD + 8/2];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1161) 				dest = (__u16*)info->InquiryData.ProductId;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1162) 				for (i=0;i<8;i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1163) 					dest[i] = be16_to_cpu(src[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1164) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1165) 				src = (__be16 *)&id[ATA_ID_FW_REV];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1166) 				dest = (__u16*)info->InquiryData.ProductRevisionLevel;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1167) 				for (i=0;i<2;i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1168) 					dest[i] = be16_to_cpu(src[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1169) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1170) 				/* determine if it supports Media Status Notification */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1171) 				if (id[ATA_ID_COMMAND_SET_2] & COMMANDSET_MEDIA_STATUS) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1172) 					usb_stor_dbg(us, "   Device supports Media Status Notification\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1173) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1174) 					/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1175) 					 * Indicate that it is enabled, even
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1176) 					 * though it is not.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1177) 					 * This allows the lock/unlock of the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1178) 					 * media to work correctly.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1179) 					 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1180) 					info->DeviceFlags |= DF_MEDIA_STATUS_ENABLED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1181) 				}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1182) 				else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1183) 					info->DeviceFlags &= ~DF_MEDIA_STATUS_ENABLED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1184) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1185) 			}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1186) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1187) 			/* 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1188) 			 * this must be an ATAPI device 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1189) 			 * use an ATAPI protocol (Transparent SCSI)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1190) 			 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1191) 			us->protocol_name = "Transparent SCSI";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1192) 			us->proto_handler = usb_stor_transparent_scsi_command;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1193) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1194) 			usb_stor_dbg(us, "Protocol changed to: %s\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1195) 				     us->protocol_name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1196) 	    
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1197) 			/* Free driver structure */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1198) 			us->extra_destructor(info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1199) 			kfree(info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1200) 			us->extra = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1201) 			us->extra_destructor = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1202) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1203) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1204) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1205) 	usb_stor_dbg(us, "Leaving isd200_get_inquiry_data %08X\n", retStatus);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1206) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1207) 	return(retStatus);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1208) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1209) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1210) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1211)  * isd200_scsi_to_ata
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1212)  *									 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1213)  * Translate SCSI commands to ATA commands.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1214)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1215)  * RETURNS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1216)  *    1 if the command needs to be sent to the transport layer
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1217)  *    0 otherwise
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1218)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1219) static int isd200_scsi_to_ata(struct scsi_cmnd *srb, struct us_data *us,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1220) 			      union ata_cdb * ataCdb)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1221) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1222) 	struct isd200_info *info = (struct isd200_info *)us->extra;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1223) 	u16 *id = info->id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1224) 	int sendToTransport = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1225) 	unsigned char sectnum, head;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1226) 	unsigned short cylinder;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1227) 	unsigned long lba;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1228) 	unsigned long blockCount;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1229) 	unsigned char senseData[8] = { 0, 0, 0, 0, 0, 0, 0, 0 };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1230) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1231) 	memset(ataCdb, 0, sizeof(union ata_cdb));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1232) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1233) 	/* SCSI Command */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1234) 	switch (srb->cmnd[0]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1235) 	case INQUIRY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1236) 		usb_stor_dbg(us, "   ATA OUT - INQUIRY\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1237) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1238) 		/* copy InquiryData */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1239) 		usb_stor_set_xfer_buf((unsigned char *) &info->InquiryData,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1240) 				sizeof(info->InquiryData), srb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1241) 		srb->result = SAM_STAT_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1242) 		sendToTransport = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1243) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1244) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1245) 	case MODE_SENSE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1246) 		usb_stor_dbg(us, "   ATA OUT - SCSIOP_MODE_SENSE\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1247) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1248) 		/* Initialize the return buffer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1249) 		usb_stor_set_xfer_buf(senseData, sizeof(senseData), srb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1250) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1251) 		if (info->DeviceFlags & DF_MEDIA_STATUS_ENABLED)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1252) 		{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1253) 			ataCdb->generic.SignatureByte0 = info->ConfigData.ATAMajorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1254) 			ataCdb->generic.SignatureByte1 = info->ConfigData.ATAMinorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1255) 			ataCdb->generic.TransferBlockSize = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1256) 			ataCdb->generic.RegisterSelect = REG_COMMAND;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1257) 			ataCdb->write.CommandByte = ATA_COMMAND_GET_MEDIA_STATUS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1258) 			isd200_srb_set_bufflen(srb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1259) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1260) 			usb_stor_dbg(us, "   Media Status not supported, just report okay\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1261) 			srb->result = SAM_STAT_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1262) 			sendToTransport = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1263) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1264) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1265) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1266) 	case TEST_UNIT_READY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1267) 		usb_stor_dbg(us, "   ATA OUT - SCSIOP_TEST_UNIT_READY\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1268) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1269) 		if (info->DeviceFlags & DF_MEDIA_STATUS_ENABLED)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1270) 		{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1271) 			ataCdb->generic.SignatureByte0 = info->ConfigData.ATAMajorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1272) 			ataCdb->generic.SignatureByte1 = info->ConfigData.ATAMinorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1273) 			ataCdb->generic.TransferBlockSize = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1274) 			ataCdb->generic.RegisterSelect = REG_COMMAND;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1275) 			ataCdb->write.CommandByte = ATA_COMMAND_GET_MEDIA_STATUS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1276) 			isd200_srb_set_bufflen(srb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1277) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1278) 			usb_stor_dbg(us, "   Media Status not supported, just report okay\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1279) 			srb->result = SAM_STAT_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1280) 			sendToTransport = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1281) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1282) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1283) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1284) 	case READ_CAPACITY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1285) 	{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1286) 		unsigned long capacity;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1287) 		struct read_capacity_data readCapacityData;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1288) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1289) 		usb_stor_dbg(us, "   ATA OUT - SCSIOP_READ_CAPACITY\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1290) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1291) 		if (ata_id_has_lba(id))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1292) 			capacity = ata_id_u32(id, ATA_ID_LBA_CAPACITY) - 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1293) 		else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1294) 			capacity = (id[ATA_ID_HEADS] * id[ATA_ID_CYLS] *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1295) 				    id[ATA_ID_SECTORS]) - 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1296) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1297) 		readCapacityData.LogicalBlockAddress = cpu_to_be32(capacity);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1298) 		readCapacityData.BytesPerBlock = cpu_to_be32(0x200);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1299) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1300) 		usb_stor_set_xfer_buf((unsigned char *) &readCapacityData,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1301) 				sizeof(readCapacityData), srb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1302) 		srb->result = SAM_STAT_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1303) 		sendToTransport = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1304) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1305) 	break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1306) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1307) 	case READ_10:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1308) 		usb_stor_dbg(us, "   ATA OUT - SCSIOP_READ\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1309) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1310) 		lba = be32_to_cpu(*(__be32 *)&srb->cmnd[2]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1311) 		blockCount = (unsigned long)srb->cmnd[7]<<8 | (unsigned long)srb->cmnd[8];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1312) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1313) 		if (ata_id_has_lba(id)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1314) 			sectnum = (unsigned char)(lba);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1315) 			cylinder = (unsigned short)(lba>>8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1316) 			head = ATA_ADDRESS_DEVHEAD_LBA_MODE | (unsigned char)(lba>>24 & 0x0F);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1317) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1318) 			sectnum = (u8)((lba % id[ATA_ID_SECTORS]) + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1319) 			cylinder = (u16)(lba / (id[ATA_ID_SECTORS] *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1320) 					id[ATA_ID_HEADS]));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1321) 			head = (u8)((lba / id[ATA_ID_SECTORS]) %
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1322) 					id[ATA_ID_HEADS]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1323) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1324) 		ataCdb->generic.SignatureByte0 = info->ConfigData.ATAMajorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1325) 		ataCdb->generic.SignatureByte1 = info->ConfigData.ATAMinorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1326) 		ataCdb->generic.TransferBlockSize = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1327) 		ataCdb->generic.RegisterSelect =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1328) 		  REG_SECTOR_COUNT | REG_SECTOR_NUMBER |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1329) 		  REG_CYLINDER_LOW | REG_CYLINDER_HIGH |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1330) 		  REG_DEVICE_HEAD  | REG_COMMAND;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1331) 		ataCdb->write.SectorCountByte = (unsigned char)blockCount;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1332) 		ataCdb->write.SectorNumberByte = sectnum;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1333) 		ataCdb->write.CylinderHighByte = (unsigned char)(cylinder>>8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1334) 		ataCdb->write.CylinderLowByte = (unsigned char)cylinder;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1335) 		ataCdb->write.DeviceHeadByte = (head | ATA_ADDRESS_DEVHEAD_STD);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1336) 		ataCdb->write.CommandByte = ATA_CMD_PIO_READ;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1337) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1338) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1339) 	case WRITE_10:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1340) 		usb_stor_dbg(us, "   ATA OUT - SCSIOP_WRITE\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1341) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1342) 		lba = be32_to_cpu(*(__be32 *)&srb->cmnd[2]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1343) 		blockCount = (unsigned long)srb->cmnd[7]<<8 | (unsigned long)srb->cmnd[8];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1344) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1345) 		if (ata_id_has_lba(id)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1346) 			sectnum = (unsigned char)(lba);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1347) 			cylinder = (unsigned short)(lba>>8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1348) 			head = ATA_ADDRESS_DEVHEAD_LBA_MODE | (unsigned char)(lba>>24 & 0x0F);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1349) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1350) 			sectnum = (u8)((lba % id[ATA_ID_SECTORS]) + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1351) 			cylinder = (u16)(lba / (id[ATA_ID_SECTORS] *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1352) 					id[ATA_ID_HEADS]));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1353) 			head = (u8)((lba / id[ATA_ID_SECTORS]) %
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1354) 					id[ATA_ID_HEADS]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1355) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1356) 		ataCdb->generic.SignatureByte0 = info->ConfigData.ATAMajorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1357) 		ataCdb->generic.SignatureByte1 = info->ConfigData.ATAMinorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1358) 		ataCdb->generic.TransferBlockSize = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1359) 		ataCdb->generic.RegisterSelect =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1360) 		  REG_SECTOR_COUNT | REG_SECTOR_NUMBER |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1361) 		  REG_CYLINDER_LOW | REG_CYLINDER_HIGH |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1362) 		  REG_DEVICE_HEAD  | REG_COMMAND;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1363) 		ataCdb->write.SectorCountByte = (unsigned char)blockCount;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1364) 		ataCdb->write.SectorNumberByte = sectnum;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1365) 		ataCdb->write.CylinderHighByte = (unsigned char)(cylinder>>8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1366) 		ataCdb->write.CylinderLowByte = (unsigned char)cylinder;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1367) 		ataCdb->write.DeviceHeadByte = (head | ATA_ADDRESS_DEVHEAD_STD);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1368) 		ataCdb->write.CommandByte = ATA_CMD_PIO_WRITE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1369) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1370) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1371) 	case ALLOW_MEDIUM_REMOVAL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1372) 		usb_stor_dbg(us, "   ATA OUT - SCSIOP_MEDIUM_REMOVAL\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1373) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1374) 		if (info->DeviceFlags & DF_REMOVABLE_MEDIA) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1375) 			usb_stor_dbg(us, "   srb->cmnd[4] = 0x%X\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1376) 				     srb->cmnd[4]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1377) 	    
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1378) 			ataCdb->generic.SignatureByte0 = info->ConfigData.ATAMajorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1379) 			ataCdb->generic.SignatureByte1 = info->ConfigData.ATAMinorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1380) 			ataCdb->generic.TransferBlockSize = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1381) 			ataCdb->generic.RegisterSelect = REG_COMMAND;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1382) 			ataCdb->write.CommandByte = (srb->cmnd[4] & 0x1) ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1383) 				ATA_CMD_MEDIA_LOCK : ATA_CMD_MEDIA_UNLOCK;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1384) 			isd200_srb_set_bufflen(srb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1385) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1386) 			usb_stor_dbg(us, "   Not removable media, just report okay\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1387) 			srb->result = SAM_STAT_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1388) 			sendToTransport = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1389) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1390) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1391) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1392) 	case START_STOP:    
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1393) 		usb_stor_dbg(us, "   ATA OUT - SCSIOP_START_STOP_UNIT\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1394) 		usb_stor_dbg(us, "   srb->cmnd[4] = 0x%X\n", srb->cmnd[4]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1395) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1396) 		if ((srb->cmnd[4] & 0x3) == 0x2) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1397) 			usb_stor_dbg(us, "   Media Eject\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1398) 			ataCdb->generic.SignatureByte0 = info->ConfigData.ATAMajorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1399) 			ataCdb->generic.SignatureByte1 = info->ConfigData.ATAMinorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1400) 			ataCdb->generic.TransferBlockSize = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1401) 			ataCdb->generic.RegisterSelect = REG_COMMAND;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1402) 			ataCdb->write.CommandByte = ATA_COMMAND_MEDIA_EJECT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1403) 		} else if ((srb->cmnd[4] & 0x3) == 0x1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1404) 			usb_stor_dbg(us, "   Get Media Status\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1405) 			ataCdb->generic.SignatureByte0 = info->ConfigData.ATAMajorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1406) 			ataCdb->generic.SignatureByte1 = info->ConfigData.ATAMinorCommand;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1407) 			ataCdb->generic.TransferBlockSize = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1408) 			ataCdb->generic.RegisterSelect = REG_COMMAND;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1409) 			ataCdb->write.CommandByte = ATA_COMMAND_GET_MEDIA_STATUS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1410) 			isd200_srb_set_bufflen(srb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1411) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1412) 			usb_stor_dbg(us, "   Nothing to do, just report okay\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1413) 			srb->result = SAM_STAT_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1414) 			sendToTransport = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1415) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1416) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1417) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1418) 	default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1419) 		usb_stor_dbg(us, "Unsupported SCSI command - 0x%X\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1420) 			     srb->cmnd[0]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1421) 		srb->result = DID_ERROR << 16;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1422) 		sendToTransport = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1423) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1424) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1425) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1426) 	return(sendToTransport);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1427) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1428) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1429) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1430) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1431)  * isd200_free_info
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1432)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1433)  * Frees the driver structure.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1434)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1435) static void isd200_free_info_ptrs(void *info_)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1436) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1437) 	struct isd200_info *info = (struct isd200_info *) info_;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1438) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1439) 	if (info) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1440) 		kfree(info->id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1441) 		kfree(info->RegsBuf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1442) 		kfree(info->srb.sense_buffer);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1443) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1444) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1445) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1446) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1447)  * isd200_init_info
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1448)  *									 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1449)  * Allocates (if necessary) and initializes the driver structure.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1450)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1451)  * RETURNS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1452)  *    ISD status code
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1453)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1454) static int isd200_init_info(struct us_data *us)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1455) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1456) 	struct isd200_info *info;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1457) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1458) 	info = kzalloc(sizeof(struct isd200_info), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1459) 	if (!info)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1460) 		return ISD200_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1461) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1462) 	info->id = kzalloc(ATA_ID_WORDS * 2, GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1463) 	info->RegsBuf = kmalloc(sizeof(info->ATARegs), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1464) 	info->srb.sense_buffer = kmalloc(SCSI_SENSE_BUFFERSIZE, GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1465) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1466) 	if (!info->id || !info->RegsBuf || !info->srb.sense_buffer) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1467) 		isd200_free_info_ptrs(info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1468) 		kfree(info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1469) 		return ISD200_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1470) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1471) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1472) 	us->extra = info;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1473) 	us->extra_destructor = isd200_free_info_ptrs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1474) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1475) 	return ISD200_GOOD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1476) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1477) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1478) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1479)  * Initialization for the ISD200 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1480)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1481) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1482) static int isd200_Initialization(struct us_data *us)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1483) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1484) 	usb_stor_dbg(us, "ISD200 Initialization...\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1485) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1486) 	/* Initialize ISD200 info struct */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1487) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1488) 	if (isd200_init_info(us) == ISD200_ERROR) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1489) 		usb_stor_dbg(us, "ERROR Initializing ISD200 Info struct\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1490) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1491) 		/* Get device specific data */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1492) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1493) 		if (isd200_get_inquiry_data(us) != ISD200_GOOD)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1494) 			usb_stor_dbg(us, "ISD200 Initialization Failure\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1495) 		else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1496) 			usb_stor_dbg(us, "ISD200 Initialization complete\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1497) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1498) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1499) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1500) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1501) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1502) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1503) /**************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1504)  * Protocol and Transport for the ISD200 ASIC
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1505)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1506)  * This protocol and transport are for ATA devices connected to an ISD200
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1507)  * ASIC.  An ATAPI device that is connected as a slave device will be
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1508)  * detected in the driver initialization function and the protocol will
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1509)  * be changed to an ATAPI protocol (Transparent SCSI).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1510)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1511)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1512) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1513) static void isd200_ata_command(struct scsi_cmnd *srb, struct us_data *us)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1514) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1515) 	int sendToTransport, orig_bufflen;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1516) 	union ata_cdb ataCdb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1517) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1518) 	/* Make sure driver was initialized */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1519) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1520) 	if (us->extra == NULL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1521) 		usb_stor_dbg(us, "ERROR Driver not initialized\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1522) 		srb->result = DID_ERROR << 16;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1523) 		return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1524) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1525) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1526) 	scsi_set_resid(srb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1527) 	/* scsi_bufflen might change in protocol translation to ata */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1528) 	orig_bufflen = scsi_bufflen(srb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1529) 	sendToTransport = isd200_scsi_to_ata(srb, us, &ataCdb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1530) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1531) 	/* send the command to the transport layer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1532) 	if (sendToTransport)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1533) 		isd200_invoke_transport(us, srb, &ataCdb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1534) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1535) 	isd200_srb_set_bufflen(srb, orig_bufflen);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1536) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1537) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1538) static struct scsi_host_template isd200_host_template;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1539) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1540) static int isd200_probe(struct usb_interface *intf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1541) 			 const struct usb_device_id *id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1542) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1543) 	struct us_data *us;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1544) 	int result;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1545) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1546) 	result = usb_stor_probe1(&us, intf, id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1547) 			(id - isd200_usb_ids) + isd200_unusual_dev_list,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1548) 			&isd200_host_template);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1549) 	if (result)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1550) 		return result;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1551) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1552) 	us->protocol_name = "ISD200 ATA/ATAPI";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1553) 	us->proto_handler = isd200_ata_command;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1554) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1555) 	result = usb_stor_probe2(us);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1556) 	return result;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1557) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1558) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1559) static struct usb_driver isd200_driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1560) 	.name =		DRV_NAME,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1561) 	.probe =	isd200_probe,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1562) 	.disconnect =	usb_stor_disconnect,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1563) 	.suspend =	usb_stor_suspend,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1564) 	.resume =	usb_stor_resume,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1565) 	.reset_resume =	usb_stor_reset_resume,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1566) 	.pre_reset =	usb_stor_pre_reset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1567) 	.post_reset =	usb_stor_post_reset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1568) 	.id_table =	isd200_usb_ids,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1569) 	.soft_unbind =	1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1570) 	.no_dynamic_id = 1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1571) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1572) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1573) module_usb_stor_driver(isd200_driver, isd200_host_template, DRV_NAME);