Fork us on GitHub Follow us on Facebook Follow us on Twitter

Changeset 132a6073 in mainline


Ignore:
Timestamp:
2011-07-25T16:56:55Z (10 years ago)
Author:
Jiri Svoboda <jiri@…>
Branches:
lfn, master
Children:
41ff85b
Parents:
358dc13
Message:

Repeat SCSI command in case of unit attention condition.
Use Read/Write? (10) instead of Read/Write? (12).

Location:
uspace
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • uspace/drv/bus/usb/usbmast/scsi_ms.c

    r358dc13 r132a6073  
    6161}
    6262
    63 static void usbmast_dump_sense(usbmast_fun_t *mfun)
    64 {
     63static void usbmast_dump_sense(scsi_sense_data_t *sense_buf)
     64{
     65        unsigned sense_key;
     66
     67        sense_key = sense_buf->flags_key & 0x0f;
     68        printf("Got sense data. Sense key: 0x%x (%s), ASC 0x%02x, "
     69            "ASCQ 0x%02x.\n", sense_key,
     70            scsi_get_sense_key_str(sense_key),
     71            sense_buf->additional_code,
     72            sense_buf->additional_cqual);
     73}
     74
     75/** Run SCSI command.
     76 *
     77 * Run command and repeat in case of unit attention.
     78 * XXX This is too simplified.
     79 */
     80static int usbmast_run_cmd(usbmast_fun_t *mfun, scsi_cmd_t *cmd)
     81{
     82        uint8_t sense_key;
    6583        scsi_sense_data_t sense_buf;
    66         unsigned sense_key;
    67         int rc;
    68 
    69         rc = usbmast_request_sense(mfun, &sense_buf, sizeof(sense_buf));
    70         if (rc == EOK) {
     84        int rc;
     85
     86        do {
     87                rc = usb_massstor_cmd(mfun, 0xDEADBEEF, cmd);
     88                if (rc != EOK) {
     89                        usb_log_error("Inquiry transport failed, device %s: %s.\n",
     90                           mfun->mdev->ddf_dev->name, str_error(rc));
     91                        return rc;
     92                }
     93
     94                if (cmd->status == CMDS_GOOD)
     95                        return EOK;
     96
     97                usb_log_error("SCSI command failed, device %s.\n",
     98                    mfun->mdev->ddf_dev->name);
     99
     100                rc = usbmast_request_sense(mfun, &sense_buf, sizeof(sense_buf));
     101                if (rc != EOK) {
     102                        usb_log_error("Failed to read sense data.\n");
     103                        return EIO;
     104                }
     105
     106                /* Dump sense data to log */
     107                usbmast_dump_sense(&sense_buf);
     108
     109                /* Get sense key */
    71110                sense_key = sense_buf.flags_key & 0x0f;
    72                 printf("Got sense data. Sense key: 0x%x (%s), ASC 0x%02x, "
    73                     "ASCQ 0x%02x.\n", sense_key,
    74                     scsi_get_sense_key_str(sense_key),
    75                     sense_buf.additional_code,
    76                     sense_buf.additional_cqual);
    77         } else {
    78                 printf("Failed to read sense data.\n");
    79         }
     111
     112                if (sense_key == SCSI_SK_UNIT_ATTENTION) {
     113                        printf("Got unit attention. Re-trying command.\n");
     114                }
     115
     116        } while (sense_key == SCSI_SK_UNIT_ATTENTION);
     117
     118        /* Command status is not good, nevertheless transport succeeded. */
     119        return EOK;
    80120}
    81121
     
    114154                usb_log_error("Inquiry command failed, device %s.\n",
    115155                   mfun->mdev->ddf_dev->name);
    116                 usbmast_dump_sense(mfun);
    117156                return EIO;
    118157        }
     
    214253        cmd.data_in_size = sizeof(data);
    215254
    216         rc = usb_massstor_cmd(mfun, 0xDEADBEEF, &cmd);
     255        rc = usbmast_run_cmd(mfun, &cmd);
    217256
    218257        if (rc != EOK) {
     
    225264                usb_log_error("Read Capacity (10) command failed, device %s.\n",
    226265                   mfun->mdev->ddf_dev->name);
    227                 usbmast_dump_sense(mfun);
    228266                return EIO;
    229267        }
     
    252290{
    253291        scsi_cmd_t cmd;
    254         scsi_cdb_read_12_t cdb;
     292        scsi_cdb_read_10_t cdb;
    255293        int rc;
    256294
     
    258296                return ELIMIT;
    259297
    260         if ((uint64_t)nblocks * mfun->block_size > UINT32_MAX)
     298        if (nblocks > UINT16_MAX)
    261299                return ELIMIT;
    262300
    263301        memset(&cdb, 0, sizeof(cdb));
    264         cdb.op_code = SCSI_CMD_READ_12;
     302        cdb.op_code = SCSI_CMD_READ_10;
    265303        cdb.lba = host2uint32_t_be(ba);
    266         cdb.xfer_len = host2uint32_t_be(nblocks);
     304        cdb.xfer_len = host2uint16_t_be(nblocks);
    267305
    268306        memset(&cmd, 0, sizeof(cmd));
     
    272310        cmd.data_in_size = nblocks * mfun->block_size;
    273311
    274         rc = usb_massstor_cmd(mfun, 0xDEADBEEF, &cmd);
     312        rc = usbmast_run_cmd(mfun, &cmd);
    275313
    276314        if (rc != EOK) {
    277                 usb_log_error("Read (12) transport failed, device %s: %s.\n",
     315                usb_log_error("Read (10) transport failed, device %s: %s.\n",
    278316                   mfun->mdev->ddf_dev->name, str_error(rc));
    279317                return rc;
     
    281319
    282320        if (cmd.status != CMDS_GOOD) {
    283                 usb_log_error("Read (12) command failed, device %s.\n",
     321                usb_log_error("Read (10) command failed, device %s.\n",
    284322                   mfun->mdev->ddf_dev->name);
    285                 usbmast_dump_sense(mfun);
    286323                return EIO;
    287324        }
     
    309346{
    310347        scsi_cmd_t cmd;
    311         scsi_cdb_write_12_t cdb;
     348        scsi_cdb_write_10_t cdb;
    312349        int rc;
    313350
     
    315352                return ELIMIT;
    316353
    317         if ((uint64_t)nblocks * mfun->block_size > UINT32_MAX)
     354        if (nblocks > UINT16_MAX)
    318355                return ELIMIT;
    319356
    320357        memset(&cdb, 0, sizeof(cdb));
    321         cdb.op_code = SCSI_CMD_WRITE_12;
     358        cdb.op_code = SCSI_CMD_WRITE_10;
    322359        cdb.lba = host2uint32_t_be(ba);
    323         cdb.xfer_len = host2uint32_t_be(nblocks);
     360        cdb.xfer_len = host2uint16_t_be(nblocks);
    324361
    325362        memset(&cmd, 0, sizeof(cmd));
     
    329366        cmd.data_out_size = nblocks * mfun->block_size;
    330367
    331         rc = usb_massstor_cmd(mfun, 0xDEADBEEF, &cmd);
     368        rc = usbmast_run_cmd(mfun, &cmd);
    332369
    333370        if (rc != EOK) {
    334                 usb_log_error("Write (12) transport failed, device %s: %s.\n",
     371                usb_log_error("Write (10) transport failed, device %s: %s.\n",
    335372                   mfun->mdev->ddf_dev->name, str_error(rc));
    336373                return rc;
     
    338375
    339376        if (cmd.status != CMDS_GOOD) {
    340                 usb_log_error("Write (12) command failed, device %s.\n",
     377                usb_log_error("Write (10) command failed, device %s.\n",
    341378                   mfun->mdev->ddf_dev->name);
    342                 usbmast_dump_sense(mfun);
    343379                return EIO;
    344380        }
  • uspace/lib/scsi/include/scsi/sbc.h

    r358dc13 r132a6073  
    5656};
    5757
     58/** SCSI Read (10) command */
     59typedef struct {
     60        /** Operation code (SCSI_CMD_READ_10) */
     61        uint8_t op_code;
     62        /** RdProtect, DPO, FUA, Reserved, FUA_NV, Obsolete */
     63        uint8_t flags;
     64        /** Logical block address */
     65        uint32_t lba;
     66        /** Reserved, Group Number */
     67        uint8_t group_no;
     68        /** Transfer length */
     69        uint16_t xfer_len;
     70        /** Control */
     71        uint8_t control;
     72} __attribute__((packed)) scsi_cdb_read_10_t;
     73
    5874/** SCSI Read (12) command */
    5975typedef struct {
    6076        /** Operation code (SCSI_CMD_READ_12) */
    6177        uint8_t op_code;
    62         /** RdProtect, DPO, FUA, Reserved, FUA_NV, Reserved */
     78        /** RdProtect, DPO, FUA, Reserved, FUA_NV, Obsolete */
    6379        uint8_t flags;
    6480        /** Logical block address */
     
    115131} scsi_read_capacity_10_data_t;
    116132
     133/** SCSI Write (10) command */
     134typedef struct {
     135        /** Operation code (SCSI_CMD_WRITE_10) */
     136        uint8_t op_code;
     137        /** WrProtect, DPO, FUA, Reserved, FUA_NV, Obsolete */
     138        uint8_t flags;
     139        /** Logical block address */
     140        uint32_t lba;
     141        /** Reserved, Group Number */
     142        uint8_t group_no;
     143        /** Transfer length */
     144        uint16_t xfer_len;
     145        /** Control */
     146        uint8_t control;
     147} __attribute__((packed)) scsi_cdb_write_10_t;
     148
    117149/** SCSI Write (12) command */
    118150typedef struct {
    119151        /** Operation code (SCSI_CMD_WRITE_12) */
    120152        uint8_t op_code;
    121         /** WrProtect, DPO, FUA, Reserved, FUA_NV, Reserved */
     153        /** WrProtect, DPO, FUA, Reserved, FUA_NV, Obsolete */
    122154        uint8_t flags;
    123155        /** Logical block address */
Note: See TracChangeset for help on using the changeset viewer.