Date: Wed, 6 Oct 2004 02:21:56 -0700 From: Bruce M Simpson <bms@spc.org> To: freebsd-current@FreeBSD.org Subject: Help wanted re formatting USB floppies. Message-ID: <20041006092156.GA690@empiric.icir.org>
next in thread | raw e-mail | index | archive | help
--EuxKj2iCbKjpUGkD Content-Type: multipart/mixed; boundary="vtzGhvizbBRQ85DL" Content-Disposition: inline --vtzGhvizbBRQ85DL Content-Type: text/plain; charset=us-ascii Content-Disposition: inline Content-Transfer-Encoding: quoted-printable I am working on a hack to allow us to format floppies in USB drives. Could willing volunteers do the following: 1) Apply the attached patch to your umass driver, rebuild, and reboot. The patch is relative to /usr i.e. above the src directory, and is against RELENG_5. 2) Plug in your USB floppy drive. 3) Repeat the following command with the new driver loaded, for various combinations of: a) No disk in the drive b) Unformatted disk in the drive c) Formatted disk in the drive (even better if you can do this for multiple combinations of 360KB, 720KB, 1.44MB) and report the results back to me: camcontrol cmd ${DEVNAME} -v \ -c "23 00 00 00 00 00 00 00 20 00 00 00" \ -i 0x20 "{} *i3 {Len} i1 {Blocks} i4 {} *b6 {Code} b2 {Blocklen} i3" where ${DEVNAME} is the device name of your USB floppy (often da0 on laptop= s). You should get 4 numbers returned from this command, probably along the lin= es of: 32 2880 2 512. 4) Please do report the kind of disk, if you know what it is, that you got = the result from, and the make/model of your USB floppy which you should be able to see from "usbdevs -v" as root. Now I have a feeling what Windows does, when it encounters a USB floppy device, is to use the READ_FORMAT_CAPACITY SCSI command to determine which format(s) such a device supports; then read the flexible disk geometry page to determine=20 Regards, BMS P.S. I did hack a diff for forcing camcontrol(8) to use a MODE_SENSE_10 or MODE_SELECT_10 but it doesn't appear to do the right thing... the pages have different layouts/sizes, so e.g. "Data bytes per sector" is actually reported as "Starting cylinder-write precompensation". Could someone more knowledgable with CAM or SCSI than I suggest a better way of looking at the Flexible Disk Page? --vtzGhvizbBRQ85DL Content-Type: text/plain; charset=us-ascii Content-Disposition: attachment; filename="umass.diff" Content-Transfer-Encoding: quoted-printable Index: src/sys/dev/usb/umass.c =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D RCS file: /home/ncvs/src/sys/dev/usb/umass.c,v retrieving revision 1.112.2.1 diff -u -p -r1.112.2.1 umass.c --- src/sys/dev/usb/umass.c 20 Sep 2004 05:28:08 -0000 1.112.2.1 +++ src/sys/dev/usb/umass.c 6 Oct 2004 08:00:42 -0000 @@ -124,6 +124,7 @@ #include <cam/cam_xpt_sim.h> #include <cam/scsi/scsi_all.h> #include <cam/scsi/scsi_da.h> +#include <cam/scsi/scsi_ufi.h> =20 #include <cam/cam_periph.h> =20 @@ -2888,6 +2889,7 @@ umass_ufi_transform(struct umass_softc * } return 1; =20 + case FORMAT_UNIT: /* XXX */ case REZERO_UNIT: case REQUEST_SENSE: case INQUIRY: @@ -2902,12 +2904,14 @@ umass_ufi_transform(struct umass_softc * case MODE_SENSE_10: case READ_12: case WRITE_12: + case READ_FORMAT_CAPACITY: /* XXX */ memcpy(*rcmd, cmd, cmdlen); return 1; =20 - /* Other UFI commands: FORMAT_UNIT, READ_FORMAT_CAPACITY, - * VERIFY, WRITE_AND_VERIFY. + /* Other UFI commands: VERIFY, WRITE_AND_VERIFY. * These should be checked whether they somehow can be made to fit. + * XXX FORMAT_UNIT, READ_FORMAT_CAPACITY passed through above + * without checking. */ =20 default: --vtzGhvizbBRQ85DL Content-Type: text/plain; charset=us-ascii Content-Disposition: attachment; filename="scsi_ufi.diff" --- /dev/null Wed Oct 6 01:33:00 2004 +++ src/sys/cam/scsi/scsi_ufi.h Wed Oct 6 01:41:49 2004 @@ -0,0 +1,108 @@ +/* + * Structures and definitions for SCSI commands to UFI Floppy Devices, + * commonly used to format such devices. + * + * $FreeBSD$ + * + */ + +#ifndef _SCSI_SCSI_UFI_H +#define _SCSI_SCSI_UFI_H 1 + +#include <sys/cdefs.h> + +/* + * Opcodes + */ +#define READ_FORMAT_CAPACITY 0x23 +#define WRITE_AND_VERIFY 0x2E /* XXX */ +#define VERIFY 0x2F /* XXX */ + +/* + * READ_FORMAT_CAPACITY cdbs are *always* 12 bytes long, + * and must contain the LUN, and the length of the returned + * format capacity list which the host is able to handle. + */ + +struct scsi_read_format_capacity +{ + uint8_t opcode; /* READ_FORMAT_CAPACITY */ + uint8_t lun; /* top 3 bits contain LUN */ + uint8_t unused00[4]; + uint8_t alloc_len[2]; /* always scsi i.e. big endian */ + uint8_t unused01[3]; +}; + +/* + * VERIFY is used to verify the physical disk medium. It is a 12-byte CDB. + * Replies to this come in through the usual sense key mechanism. + */ + +struct scsi_verify +{ + uint8_t opcode; /* VERIFY */ + uint8_t lun; /* All other bits should be zero */ +#define SVFY_RELADR 0x01 /* Always 0 for UFI. */ +#define SVFY_BYTECHK 0x02 /* Always 0 for UFI. */ +#define SVFY_DPO 0x10 /* Always 0 for UFI. */ +#define SVFY_LUN_MASK 0xE0 /* Top 3 MSBs are LUN */ + uint8_t addr[4]; /* LBA to begin verification at */ + uint8_t unused00[1]; + uint8_t len[4]; /* number of blocks to verify */ + uint8_t unused01[3]; +}; + +/* + * WRITE_AND_VERIFY writes a track and verifies it. + * Replies to this come in through the usual sense key mechanism. + */ + +struct scsi_write_and_verify +{ + uint8_t opcode; /* WRITE_AND_VERIFY */ + uint8_t lun; /* All other bits should be zero */ +#define SVFY_RELADR 0x01 /* Always 0 for UFI. */ +#define SVFY_BYTECHK 0x02 /* Always 0 for UFI. */ +#define SVFY_DPO 0x10 /* Always 0 for UFI. */ +#define SVFY_LUN_MASK 0xE0 /* Top 3 MSBs are LUN */ + uint8_t addr[4]; /* LBA to begin verification at */ + uint8_t unused00[1]; + uint8_t len[4]; /* number of blocks to write and verify */ + uint8_t unused01[3]; +}; + +/* + * Replies to READ_FORMAT_CAPACITY look like this: + * + * scsi_capacity_list_hdr + * scsi_capacity_descriptor (maximum/current) + * + * The appropriate csio_decode() format string looks like this: + * "{} *i3 {Len} i1 {Blocks} i4 {} *b6 {Code} b2 {Blocklen} i3" + * + * If the capacity list header length is greater than + * sizeof(struct format_capacity_descriptor), then there are + * additional format capacity descriptors available which + * denote which format(s) the drive can handle. + * + */ + +struct format_capacity_list_header { + uint8_t unused[3]; + uint8_t capacity_list_length; +}; + +struct format_capacity_descriptor { + uint8_t num_blocks[4]; /* total number of LBAs */ + uint8_t code; /* only present in max/cur descriptor */ +#define FCD_CODE_MASK 0x03 /* mask for code field above */ +#define FCD_UNFORMATTED 0x01 /* unformatted media present, + * maximum capacity returned */ +#define FCD_FORMATTED 0x02 /* formatted media present, + * current capacity returned */ +#define FCD_NOMEDIA 0x03 /* no media present, + * maximum device capacity returned */ + uint8_t block_len[3]; /* length of an LBA in bytes */ +}; + +#endif /* _SCSI_SCSI_UFI_H */ --vtzGhvizbBRQ85DL-- --EuxKj2iCbKjpUGkD Content-Type: application/pgp-signature Content-Disposition: inline -----BEGIN PGP SIGNATURE----- Comment: '' iD8DBQFBY7kzueUpAYYNtTsRAs+kAJ98gs+LHx04M3ljfN3vnd6z4O3z9QCgiwLn DT/Uhy42n7JDWdX2fO99lMw= =KmbO -----END PGP SIGNATURE----- --EuxKj2iCbKjpUGkD--
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?20041006092156.GA690>