aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/scsi/stex.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/scsi/stex.c')
-rw-r--r--drivers/scsi/stex.c197
1 files changed, 165 insertions, 32 deletions
diff --git a/drivers/scsi/stex.c b/drivers/scsi/stex.c
index 3cf3106a29b8..a54e6c1026b7 100644
--- a/drivers/scsi/stex.c
+++ b/drivers/scsi/stex.c
@@ -11,7 +11,7 @@
11 * Written By: 11 * Written By:
12 * Ed Lin <promise_linux@promise.com> 12 * Ed Lin <promise_linux@promise.com>
13 * 13 *
14 * Version: 2.9.0.13 14 * Version: 3.0.0.1
15 * 15 *
16 */ 16 */
17 17
@@ -37,11 +37,11 @@
37#include <scsi/scsi_tcq.h> 37#include <scsi/scsi_tcq.h>
38 38
39#define DRV_NAME "stex" 39#define DRV_NAME "stex"
40#define ST_DRIVER_VERSION "2.9.0.13" 40#define ST_DRIVER_VERSION "3.0.0.1"
41#define ST_VER_MAJOR 2 41#define ST_VER_MAJOR 3
42#define ST_VER_MINOR 9 42#define ST_VER_MINOR 0
43#define ST_OEM 0 43#define ST_OEM 0
44#define ST_BUILD_VER 13 44#define ST_BUILD_VER 1
45 45
46enum { 46enum {
47 /* MU register offset */ 47 /* MU register offset */
@@ -120,12 +120,18 @@ enum {
120 120
121 st_shasta = 0, 121 st_shasta = 0,
122 st_vsc = 1, 122 st_vsc = 1,
123 st_yosemite = 2,
123 124
124 PASSTHRU_REQ_TYPE = 0x00000001, 125 PASSTHRU_REQ_TYPE = 0x00000001,
125 PASSTHRU_REQ_NO_WAKEUP = 0x00000100, 126 PASSTHRU_REQ_NO_WAKEUP = 0x00000100,
126 ST_INTERNAL_TIMEOUT = 30, 127 ST_INTERNAL_TIMEOUT = 30,
127 128
129 ST_TO_CMD = 0,
130 ST_FROM_CMD = 1,
131
128 /* vendor specific commands of Promise */ 132 /* vendor specific commands of Promise */
133 MGT_CMD = 0xd8,
134 SINBAND_MGT_CMD = 0xd9,
129 ARRAY_CMD = 0xe0, 135 ARRAY_CMD = 0xe0,
130 CONTROLLER_CMD = 0xe1, 136 CONTROLLER_CMD = 0xe1,
131 DEBUGGING_CMD = 0xe2, 137 DEBUGGING_CMD = 0xe2,
@@ -133,14 +139,48 @@ enum {
133 139
134 PASSTHRU_GET_ADAPTER = 0x05, 140 PASSTHRU_GET_ADAPTER = 0x05,
135 PASSTHRU_GET_DRVVER = 0x10, 141 PASSTHRU_GET_DRVVER = 0x10,
142
143 CTLR_CONFIG_CMD = 0x03,
144 CTLR_SHUTDOWN = 0x0d,
145
136 CTLR_POWER_STATE_CHANGE = 0x0e, 146 CTLR_POWER_STATE_CHANGE = 0x0e,
137 CTLR_POWER_SAVING = 0x01, 147 CTLR_POWER_SAVING = 0x01,
138 148
139 PASSTHRU_SIGNATURE = 0x4e415041, 149 PASSTHRU_SIGNATURE = 0x4e415041,
150 MGT_CMD_SIGNATURE = 0xba,
140 151
141 INQUIRY_EVPD = 0x01, 152 INQUIRY_EVPD = 0x01,
142}; 153};
143 154
155/* SCSI inquiry data */
156typedef struct st_inq {
157 u8 DeviceType :5;
158 u8 DeviceTypeQualifier :3;
159 u8 DeviceTypeModifier :7;
160 u8 RemovableMedia :1;
161 u8 Versions;
162 u8 ResponseDataFormat :4;
163 u8 HiSupport :1;
164 u8 NormACA :1;
165 u8 ReservedBit :1;
166 u8 AERC :1;
167 u8 AdditionalLength;
168 u8 Reserved[2];
169 u8 SoftReset :1;
170 u8 CommandQueue :1;
171 u8 Reserved2 :1;
172 u8 LinkedCommands :1;
173 u8 Synchronous :1;
174 u8 Wide16Bit :1;
175 u8 Wide32Bit :1;
176 u8 RelativeAddressing :1;
177 u8 VendorId[8];
178 u8 ProductId[16];
179 u8 ProductRevisionLevel[4];
180 u8 VendorSpecific[20];
181 u8 Reserved3[40];
182} ST_INQ;
183
144struct st_sgitem { 184struct st_sgitem {
145 u8 ctrl; /* SG_CF_xxx */ 185 u8 ctrl; /* SG_CF_xxx */
146 u8 reserved[3]; 186 u8 reserved[3];
@@ -181,7 +221,7 @@ struct req_msg {
181 u8 task_attr; 221 u8 task_attr;
182 u8 task_manage; 222 u8 task_manage;
183 u8 prd_entry; 223 u8 prd_entry;
184 u8 payload_sz; /* payload size in 4-byte */ 224 u8 payload_sz; /* payload size in 4-byte, not used */
185 u8 cdb[STEX_CDB_LENGTH]; 225 u8 cdb[STEX_CDB_LENGTH];
186 u8 variable[REQ_VARIABLE_LEN]; 226 u8 variable[REQ_VARIABLE_LEN];
187}; 227};
@@ -242,7 +282,8 @@ struct st_drvver {
242#define MU_REQ_BUFFER_SIZE (MU_REQ_COUNT * sizeof(struct req_msg)) 282#define MU_REQ_BUFFER_SIZE (MU_REQ_COUNT * sizeof(struct req_msg))
243#define MU_STATUS_BUFFER_SIZE (MU_STATUS_COUNT * sizeof(struct status_msg)) 283#define MU_STATUS_BUFFER_SIZE (MU_STATUS_COUNT * sizeof(struct status_msg))
244#define MU_BUFFER_SIZE (MU_REQ_BUFFER_SIZE + MU_STATUS_BUFFER_SIZE) 284#define MU_BUFFER_SIZE (MU_REQ_BUFFER_SIZE + MU_STATUS_BUFFER_SIZE)
245#define STEX_BUFFER_SIZE (MU_BUFFER_SIZE + sizeof(struct st_frame)) 285#define STEX_EXTRA_SIZE max(sizeof(struct st_frame), sizeof(ST_INQ))
286#define STEX_BUFFER_SIZE (MU_BUFFER_SIZE + STEX_EXTRA_SIZE)
246 287
247struct st_ccb { 288struct st_ccb {
248 struct req_msg *req; 289 struct req_msg *req;
@@ -403,7 +444,7 @@ static int stex_map_sg(struct st_hba *hba,
403} 444}
404 445
405static void stex_internal_copy(struct scsi_cmnd *cmd, 446static void stex_internal_copy(struct scsi_cmnd *cmd,
406 const void *src, size_t *count, int sg_count) 447 const void *src, size_t *count, int sg_count, int direction)
407{ 448{
408 size_t lcount; 449 size_t lcount;
409 size_t len; 450 size_t len;
@@ -427,7 +468,10 @@ static void stex_internal_copy(struct scsi_cmnd *cmd,
427 } else 468 } else
428 d = cmd->request_buffer; 469 d = cmd->request_buffer;
429 470
430 memcpy(d, s, len); 471 if (direction == ST_TO_CMD)
472 memcpy(d, s, len);
473 else
474 memcpy(s, d, len);
431 475
432 lcount -= len; 476 lcount -= len;
433 if (cmd->use_sg) 477 if (cmd->use_sg)
@@ -449,7 +493,7 @@ static int stex_direct_copy(struct scsi_cmnd *cmd,
449 return 0; 493 return 0;
450 } 494 }
451 495
452 stex_internal_copy(cmd, src, &cp_len, n_elem); 496 stex_internal_copy(cmd, src, &cp_len, n_elem, ST_TO_CMD);
453 497
454 if (cmd->use_sg) 498 if (cmd->use_sg)
455 pci_unmap_sg(hba->pdev, cmd->request_buffer, 499 pci_unmap_sg(hba->pdev, cmd->request_buffer,
@@ -480,7 +524,7 @@ static void stex_controller_info(struct st_hba *hba, struct st_ccb *ccb)
480 p->subid = 524 p->subid =
481 hba->pdev->subsystem_vendor << 16 | hba->pdev->subsystem_device; 525 hba->pdev->subsystem_vendor << 16 | hba->pdev->subsystem_device;
482 526
483 stex_internal_copy(ccb->cmd, p, &count, ccb->sg_count); 527 stex_internal_copy(ccb->cmd, p, &count, ccb->sg_count, ST_TO_CMD);
484} 528}
485 529
486static void 530static void
@@ -489,7 +533,6 @@ stex_send_cmd(struct st_hba *hba, struct req_msg *req, u16 tag)
489 req->tag = cpu_to_le16(tag); 533 req->tag = cpu_to_le16(tag);
490 req->task_attr = TASK_ATTRIBUTE_SIMPLE; 534 req->task_attr = TASK_ATTRIBUTE_SIMPLE;
491 req->task_manage = 0; /* not supported yet */ 535 req->task_manage = 0; /* not supported yet */
492 req->payload_sz = (u8)(sizeof(struct req_msg)/sizeof(u32));
493 536
494 hba->ccb[tag].req = req; 537 hba->ccb[tag].req = req;
495 hba->out_req_cnt++; 538 hba->out_req_cnt++;
@@ -595,8 +638,14 @@ stex_queuecommand(struct scsi_cmnd *cmd, void (* done)(struct scsi_cmnd *))
595 return SCSI_MLQUEUE_HOST_BUSY; 638 return SCSI_MLQUEUE_HOST_BUSY;
596 639
597 req = stex_alloc_req(hba); 640 req = stex_alloc_req(hba);
598 req->lun = lun; 641
599 req->target = id; 642 if (hba->cardtype == st_yosemite) {
643 req->lun = lun * (ST_MAX_TARGET_NUM - 1) + id;
644 req->target = 0;
645 } else {
646 req->lun = lun;
647 req->target = id;
648 }
600 649
601 /* cdb */ 650 /* cdb */
602 memcpy(req->cdb, cmd->cmnd, STEX_CDB_LENGTH); 651 memcpy(req->cdb, cmd->cmnd, STEX_CDB_LENGTH);
@@ -680,7 +729,51 @@ static void stex_copy_data(struct st_ccb *ccb,
680 729
681 if (ccb->cmd == NULL) 730 if (ccb->cmd == NULL)
682 return; 731 return;
683 stex_internal_copy(ccb->cmd, resp->variable, &count, ccb->sg_count); 732 stex_internal_copy(ccb->cmd,
733 resp->variable, &count, ccb->sg_count, ST_TO_CMD);
734}
735
736static void stex_ys_commands(struct st_hba *hba,
737 struct st_ccb *ccb, struct status_msg *resp)
738{
739 size_t count;
740
741 if (ccb->cmd->cmnd[0] == MGT_CMD &&
742 resp->scsi_status != SAM_STAT_CHECK_CONDITION) {
743 ccb->cmd->request_bufflen =
744 le32_to_cpu(*(__le32 *)&resp->variable[0]);
745 return;
746 }
747
748 if (resp->srb_status != 0)
749 return;
750
751 /* determine inquiry command status by DeviceTypeQualifier */
752 if (ccb->cmd->cmnd[0] == INQUIRY &&
753 resp->scsi_status == SAM_STAT_GOOD) {
754 ST_INQ *inq_data;
755
756 count = STEX_EXTRA_SIZE;
757 stex_internal_copy(ccb->cmd, hba->copy_buffer,
758 &count, ccb->sg_count, ST_FROM_CMD);
759 inq_data = (ST_INQ *)hba->copy_buffer;
760 if (inq_data->DeviceTypeQualifier != 0)
761 ccb->srb_status = SRB_STATUS_SELECTION_TIMEOUT;
762 else
763 ccb->srb_status = SRB_STATUS_SUCCESS;
764 } else if (ccb->cmd->cmnd[0] == REPORT_LUNS) {
765 u8 *report_lun_data = (u8 *)hba->copy_buffer;
766
767 count = STEX_EXTRA_SIZE;
768 stex_internal_copy(ccb->cmd, report_lun_data,
769 &count, ccb->sg_count, ST_FROM_CMD);
770 if (report_lun_data[2] || report_lun_data[3]) {
771 report_lun_data[2] = 0x00;
772 report_lun_data[3] = 0x08;
773 stex_internal_copy(ccb->cmd, report_lun_data,
774 &count, ccb->sg_count, ST_TO_CMD);
775 }
776 }
684} 777}
685 778
686static void stex_mu_intr(struct st_hba *hba, u32 doorbell) 779static void stex_mu_intr(struct st_hba *hba, u32 doorbell)
@@ -702,8 +795,17 @@ static void stex_mu_intr(struct st_hba *hba, u32 doorbell)
702 return; 795 return;
703 } 796 }
704 797
705 if (unlikely(hba->mu_status != MU_STATE_STARTED || 798 /*
706 hba->out_req_cnt <= 0)) { 799 * it's not a valid status payload if:
800 * 1. there are no pending requests(e.g. during init stage)
801 * 2. there are some pending requests, but the controller is in
802 * reset status, and its type is not st_yosemite
803 * firmware of st_yosemite in reset status will return pending requests
804 * to driver, so we allow it to pass
805 */
806 if (unlikely(hba->out_req_cnt <= 0 ||
807 (hba->mu_status == MU_STATE_RESETTING &&
808 hba->cardtype != st_yosemite))) {
707 hba->status_tail = hba->status_head; 809 hba->status_tail = hba->status_head;
708 goto update_status; 810 goto update_status;
709 } 811 }
@@ -723,6 +825,7 @@ static void stex_mu_intr(struct st_hba *hba, u32 doorbell)
723 if (unlikely(ccb->req == NULL)) { 825 if (unlikely(ccb->req == NULL)) {
724 printk(KERN_WARNING DRV_NAME 826 printk(KERN_WARNING DRV_NAME
725 "(%s): lagging req\n", pci_name(hba->pdev)); 827 "(%s): lagging req\n", pci_name(hba->pdev));
828 hba->out_req_cnt--;
726 continue; 829 continue;
727 } 830 }
728 831
@@ -741,9 +844,13 @@ static void stex_mu_intr(struct st_hba *hba, u32 doorbell)
741 ccb->scsi_status = resp->scsi_status; 844 ccb->scsi_status = resp->scsi_status;
742 845
743 if (likely(ccb->cmd != NULL)) { 846 if (likely(ccb->cmd != NULL)) {
847 if (hba->cardtype == st_yosemite)
848 stex_ys_commands(hba, ccb, resp);
849
744 if (unlikely(ccb->cmd->cmnd[0] == PASSTHRU_CMD && 850 if (unlikely(ccb->cmd->cmnd[0] == PASSTHRU_CMD &&
745 ccb->cmd->cmnd[1] == PASSTHRU_GET_ADAPTER)) 851 ccb->cmd->cmnd[1] == PASSTHRU_GET_ADAPTER))
746 stex_controller_info(hba, ccb); 852 stex_controller_info(hba, ccb);
853
747 stex_unmap_sg(hba, ccb->cmd); 854 stex_unmap_sg(hba, ccb->cmd);
748 stex_scsi_done(ccb); 855 stex_scsi_done(ccb);
749 hba->out_req_cnt--; 856 hba->out_req_cnt--;
@@ -948,6 +1055,7 @@ static int stex_reset(struct scsi_cmnd *cmd)
948{ 1055{
949 struct st_hba *hba; 1056 struct st_hba *hba;
950 unsigned long flags; 1057 unsigned long flags;
1058 unsigned long before;
951 hba = (struct st_hba *) &cmd->device->host->hostdata[0]; 1059 hba = (struct st_hba *) &cmd->device->host->hostdata[0];
952 1060
953 hba->mu_status = MU_STATE_RESETTING; 1061 hba->mu_status = MU_STATE_RESETTING;
@@ -955,20 +1063,37 @@ static int stex_reset(struct scsi_cmnd *cmd)
955 if (hba->cardtype == st_shasta) 1063 if (hba->cardtype == st_shasta)
956 stex_hard_reset(hba); 1064 stex_hard_reset(hba);
957 1065
958 if (stex_handshake(hba)) { 1066 if (hba->cardtype != st_yosemite) {
959 printk(KERN_WARNING DRV_NAME 1067 if (stex_handshake(hba)) {
960 "(%s): resetting: handshake failed\n", 1068 printk(KERN_WARNING DRV_NAME
961 pci_name(hba->pdev)); 1069 "(%s): resetting: handshake failed\n",
962 return FAILED; 1070 pci_name(hba->pdev));
1071 return FAILED;
1072 }
1073 spin_lock_irqsave(hba->host->host_lock, flags);
1074 hba->req_head = 0;
1075 hba->req_tail = 0;
1076 hba->status_head = 0;
1077 hba->status_tail = 0;
1078 hba->out_req_cnt = 0;
1079 spin_unlock_irqrestore(hba->host->host_lock, flags);
1080 return SUCCESS;
1081 }
1082
1083 /* st_yosemite */
1084 writel(MU_INBOUND_DOORBELL_RESET, hba->mmio_base + IDBL);
1085 readl(hba->mmio_base + IDBL); /* flush */
1086 before = jiffies;
1087 while (hba->out_req_cnt > 0) {
1088 if (time_after(jiffies, before + ST_INTERNAL_TIMEOUT * HZ)) {
1089 printk(KERN_WARNING DRV_NAME
1090 "(%s): reset timeout\n", pci_name(hba->pdev));
1091 return FAILED;
1092 }
1093 msleep(1);
963 } 1094 }
964 spin_lock_irqsave(hba->host->host_lock, flags);
965 hba->req_head = 0;
966 hba->req_tail = 0;
967 hba->status_head = 0;
968 hba->status_tail = 0;
969 hba->out_req_cnt = 0;
970 spin_unlock_irqrestore(hba->host->host_lock, flags);
971 1095
1096 hba->mu_status = MU_STATE_STARTED;
972 return SUCCESS; 1097 return SUCCESS;
973} 1098}
974 1099
@@ -1156,9 +1281,16 @@ static void stex_hba_stop(struct st_hba *hba)
1156 req = stex_alloc_req(hba); 1281 req = stex_alloc_req(hba);
1157 memset(req->cdb, 0, STEX_CDB_LENGTH); 1282 memset(req->cdb, 0, STEX_CDB_LENGTH);
1158 1283
1159 req->cdb[0] = CONTROLLER_CMD; 1284 if (hba->cardtype == st_yosemite) {
1160 req->cdb[1] = CTLR_POWER_STATE_CHANGE; 1285 req->cdb[0] = MGT_CMD;
1161 req->cdb[2] = CTLR_POWER_SAVING; 1286 req->cdb[1] = MGT_CMD_SIGNATURE;
1287 req->cdb[2] = CTLR_CONFIG_CMD;
1288 req->cdb[3] = CTLR_SHUTDOWN;
1289 } else {
1290 req->cdb[0] = CONTROLLER_CMD;
1291 req->cdb[1] = CTLR_POWER_STATE_CHANGE;
1292 req->cdb[2] = CTLR_POWER_SAVING;
1293 }
1162 1294
1163 hba->ccb[tag].cmd = NULL; 1295 hba->ccb[tag].cmd = NULL;
1164 hba->ccb[tag].sg_count = 0; 1296 hba->ccb[tag].sg_count = 0;
@@ -1222,6 +1354,7 @@ static struct pci_device_id stex_pci_tbl[] = {
1222 { 0x105a, 0x8301, PCI_ANY_ID, PCI_ANY_ID, 0, 0, st_shasta }, 1354 { 0x105a, 0x8301, PCI_ANY_ID, PCI_ANY_ID, 0, 0, st_shasta },
1223 { 0x105a, 0x8302, PCI_ANY_ID, PCI_ANY_ID, 0, 0, st_shasta }, 1355 { 0x105a, 0x8302, PCI_ANY_ID, PCI_ANY_ID, 0, 0, st_shasta },
1224 { 0x1725, 0x7250, PCI_ANY_ID, PCI_ANY_ID, 0, 0, st_vsc }, 1356 { 0x1725, 0x7250, PCI_ANY_ID, PCI_ANY_ID, 0, 0, st_vsc },
1357 { 0x105a, 0x8650, PCI_ANY_ID, PCI_ANY_ID, 0, 0, st_yosemite },
1225 { } /* terminate list */ 1358 { } /* terminate list */
1226}; 1359};
1227MODULE_DEVICE_TABLE(pci, stex_pci_tbl); 1360MODULE_DEVICE_TABLE(pci, stex_pci_tbl);