diff options
Diffstat (limited to 'drivers/scsi/mvumi.h')
-rw-r--r-- | drivers/scsi/mvumi.h | 235 |
1 files changed, 152 insertions, 83 deletions
diff --git a/drivers/scsi/mvumi.h b/drivers/scsi/mvumi.h index 10b9237566f0..e360135fd1bd 100644 --- a/drivers/scsi/mvumi.h +++ b/drivers/scsi/mvumi.h | |||
@@ -34,51 +34,87 @@ | |||
34 | #define MV_DRIVER_NAME "mvumi" | 34 | #define MV_DRIVER_NAME "mvumi" |
35 | #define PCI_VENDOR_ID_MARVELL_2 0x1b4b | 35 | #define PCI_VENDOR_ID_MARVELL_2 0x1b4b |
36 | #define PCI_DEVICE_ID_MARVELL_MV9143 0x9143 | 36 | #define PCI_DEVICE_ID_MARVELL_MV9143 0x9143 |
37 | #define PCI_DEVICE_ID_MARVELL_MV9580 0x9580 | ||
37 | 38 | ||
38 | #define MVUMI_INTERNAL_CMD_WAIT_TIME 45 | 39 | #define MVUMI_INTERNAL_CMD_WAIT_TIME 45 |
40 | #define MVUMI_INQUIRY_LENGTH 44 | ||
41 | #define MVUMI_INQUIRY_UUID_OFF 36 | ||
42 | #define MVUMI_INQUIRY_UUID_LEN 8 | ||
39 | 43 | ||
40 | #define IS_DMA64 (sizeof(dma_addr_t) == 8) | 44 | #define IS_DMA64 (sizeof(dma_addr_t) == 8) |
41 | 45 | ||
42 | enum mvumi_qc_result { | 46 | enum mvumi_qc_result { |
43 | MV_QUEUE_COMMAND_RESULT_SENT = 0, | 47 | MV_QUEUE_COMMAND_RESULT_SENT = 0, |
44 | MV_QUEUE_COMMAND_RESULT_NO_RESOURCE, | 48 | MV_QUEUE_COMMAND_RESULT_NO_RESOURCE, |
45 | }; | 49 | }; |
46 | 50 | ||
47 | enum { | 51 | struct mvumi_hw_regs { |
48 | /*******************************************/ | 52 | /* For CPU */ |
49 | 53 | void *main_int_cause_reg; | |
50 | /* ARM Mbus Registers Map */ | 54 | void *enpointa_mask_reg; |
51 | 55 | void *enpointb_mask_reg; | |
52 | /*******************************************/ | 56 | void *rstoutn_en_reg; |
53 | CPU_MAIN_INT_CAUSE_REG = 0x20200, | 57 | void *ctrl_sts_reg; |
54 | CPU_MAIN_IRQ_MASK_REG = 0x20204, | 58 | void *rstoutn_mask_reg; |
55 | CPU_MAIN_FIQ_MASK_REG = 0x20208, | 59 | void *sys_soft_rst_reg; |
56 | CPU_ENPOINTA_MASK_REG = 0x2020C, | 60 | |
57 | CPU_ENPOINTB_MASK_REG = 0x20210, | 61 | /* For Doorbell */ |
58 | 62 | void *pciea_to_arm_drbl_reg; | |
59 | INT_MAP_COMAERR = 1 << 6, | 63 | void *arm_to_pciea_drbl_reg; |
60 | INT_MAP_COMAIN = 1 << 7, | 64 | void *arm_to_pciea_mask_reg; |
61 | INT_MAP_COMAOUT = 1 << 8, | 65 | void *pciea_to_arm_msg0; |
62 | INT_MAP_COMBERR = 1 << 9, | 66 | void *pciea_to_arm_msg1; |
63 | INT_MAP_COMBIN = 1 << 10, | 67 | void *arm_to_pciea_msg0; |
64 | INT_MAP_COMBOUT = 1 << 11, | 68 | void *arm_to_pciea_msg1; |
65 | 69 | ||
66 | INT_MAP_COMAINT = (INT_MAP_COMAOUT | INT_MAP_COMAERR), | 70 | /* reset register */ |
67 | INT_MAP_COMBINT = (INT_MAP_COMBOUT | INT_MAP_COMBIN | INT_MAP_COMBERR), | 71 | void *reset_request; |
68 | 72 | void *reset_enable; | |
69 | INT_MAP_DL_PCIEA2CPU = 1 << 0, | 73 | |
70 | INT_MAP_DL_CPU2PCIEA = 1 << 1, | 74 | /* For Message Unit */ |
71 | 75 | void *inb_list_basel; | |
72 | /***************************************/ | 76 | void *inb_list_baseh; |
77 | void *inb_aval_count_basel; | ||
78 | void *inb_aval_count_baseh; | ||
79 | void *inb_write_pointer; | ||
80 | void *inb_read_pointer; | ||
81 | void *outb_list_basel; | ||
82 | void *outb_list_baseh; | ||
83 | void *outb_copy_basel; | ||
84 | void *outb_copy_baseh; | ||
85 | void *outb_copy_pointer; | ||
86 | void *outb_read_pointer; | ||
87 | void *inb_isr_cause; | ||
88 | void *outb_isr_cause; | ||
89 | void *outb_coal_cfg; | ||
90 | void *outb_coal_timeout; | ||
91 | |||
92 | /* Bit setting for HW */ | ||
93 | u32 int_comaout; | ||
94 | u32 int_comaerr; | ||
95 | u32 int_dl_cpu2pciea; | ||
96 | u32 int_mu; | ||
97 | u32 int_drbl_int_mask; | ||
98 | u32 int_main_int_mask; | ||
99 | u32 cl_pointer_toggle; | ||
100 | u32 cl_slot_num_mask; | ||
101 | u32 clic_irq; | ||
102 | u32 clic_in_err; | ||
103 | u32 clic_out_err; | ||
104 | }; | ||
73 | 105 | ||
74 | /* ARM Doorbell Registers Map */ | 106 | struct mvumi_dyn_list_entry { |
107 | u32 src_low_addr; | ||
108 | u32 src_high_addr; | ||
109 | u32 if_length; | ||
110 | u32 reserve; | ||
111 | }; | ||
75 | 112 | ||
76 | /***************************************/ | 113 | #define SCSI_CMD_MARVELL_SPECIFIC 0xE1 |
77 | CPU_PCIEA_TO_ARM_DRBL_REG = 0x20400, | 114 | #define CDB_CORE_MODULE 0x1 |
78 | CPU_PCIEA_TO_ARM_MASK_REG = 0x20404, | 115 | #define CDB_CORE_SHUTDOWN 0xB |
79 | CPU_ARM_TO_PCIEA_DRBL_REG = 0x20408, | ||
80 | CPU_ARM_TO_PCIEA_MASK_REG = 0x2040C, | ||
81 | 116 | ||
117 | enum { | ||
82 | DRBL_HANDSHAKE = 1 << 0, | 118 | DRBL_HANDSHAKE = 1 << 0, |
83 | DRBL_SOFT_RESET = 1 << 1, | 119 | DRBL_SOFT_RESET = 1 << 1, |
84 | DRBL_BUS_CHANGE = 1 << 2, | 120 | DRBL_BUS_CHANGE = 1 << 2, |
@@ -86,46 +122,6 @@ enum { | |||
86 | DRBL_MU_RESET = 1 << 4, | 122 | DRBL_MU_RESET = 1 << 4, |
87 | DRBL_HANDSHAKE_ISR = DRBL_HANDSHAKE, | 123 | DRBL_HANDSHAKE_ISR = DRBL_HANDSHAKE, |
88 | 124 | ||
89 | CPU_PCIEA_TO_ARM_MSG0 = 0x20430, | ||
90 | CPU_PCIEA_TO_ARM_MSG1 = 0x20434, | ||
91 | CPU_ARM_TO_PCIEA_MSG0 = 0x20438, | ||
92 | CPU_ARM_TO_PCIEA_MSG1 = 0x2043C, | ||
93 | |||
94 | /*******************************************/ | ||
95 | |||
96 | /* ARM Communication List Registers Map */ | ||
97 | |||
98 | /*******************************************/ | ||
99 | CLA_INB_LIST_BASEL = 0x500, | ||
100 | CLA_INB_LIST_BASEH = 0x504, | ||
101 | CLA_INB_AVAL_COUNT_BASEL = 0x508, | ||
102 | CLA_INB_AVAL_COUNT_BASEH = 0x50C, | ||
103 | CLA_INB_DESTI_LIST_BASEL = 0x510, | ||
104 | CLA_INB_DESTI_LIST_BASEH = 0x514, | ||
105 | CLA_INB_WRITE_POINTER = 0x518, | ||
106 | CLA_INB_READ_POINTER = 0x51C, | ||
107 | |||
108 | CLA_OUTB_LIST_BASEL = 0x530, | ||
109 | CLA_OUTB_LIST_BASEH = 0x534, | ||
110 | CLA_OUTB_SOURCE_LIST_BASEL = 0x538, | ||
111 | CLA_OUTB_SOURCE_LIST_BASEH = 0x53C, | ||
112 | CLA_OUTB_COPY_POINTER = 0x544, | ||
113 | CLA_OUTB_READ_POINTER = 0x548, | ||
114 | |||
115 | CLA_ISR_CAUSE = 0x560, | ||
116 | CLA_ISR_MASK = 0x564, | ||
117 | |||
118 | INT_MAP_MU = (INT_MAP_DL_CPU2PCIEA | INT_MAP_COMAINT), | ||
119 | |||
120 | CL_POINTER_TOGGLE = 1 << 12, | ||
121 | |||
122 | CLIC_IN_IRQ = 1 << 0, | ||
123 | CLIC_OUT_IRQ = 1 << 1, | ||
124 | CLIC_IN_ERR_IRQ = 1 << 8, | ||
125 | CLIC_OUT_ERR_IRQ = 1 << 12, | ||
126 | |||
127 | CL_SLOT_NUM_MASK = 0xFFF, | ||
128 | |||
129 | /* | 125 | /* |
130 | * Command flag is the flag for the CDB command itself | 126 | * Command flag is the flag for the CDB command itself |
131 | */ | 127 | */ |
@@ -137,15 +133,23 @@ enum { | |||
137 | CMD_FLAG_DATA_IN = 1 << 3, | 133 | CMD_FLAG_DATA_IN = 1 << 3, |
138 | /* 1-host write data */ | 134 | /* 1-host write data */ |
139 | CMD_FLAG_DATA_OUT = 1 << 4, | 135 | CMD_FLAG_DATA_OUT = 1 << 4, |
140 | 136 | CMD_FLAG_PRDT_IN_HOST = 1 << 5, | |
141 | SCSI_CMD_MARVELL_SPECIFIC = 0xE1, | ||
142 | CDB_CORE_SHUTDOWN = 0xB, | ||
143 | }; | 137 | }; |
144 | 138 | ||
145 | #define APICDB0_EVENT 0xF4 | 139 | #define APICDB0_EVENT 0xF4 |
146 | #define APICDB1_EVENT_GETEVENT 0 | 140 | #define APICDB1_EVENT_GETEVENT 0 |
141 | #define APICDB1_HOST_GETEVENT 1 | ||
147 | #define MAX_EVENTS_RETURNED 6 | 142 | #define MAX_EVENTS_RETURNED 6 |
148 | 143 | ||
144 | #define DEVICE_OFFLINE 0 | ||
145 | #define DEVICE_ONLINE 1 | ||
146 | |||
147 | struct mvumi_hotplug_event { | ||
148 | u16 size; | ||
149 | u8 dummy[2]; | ||
150 | u8 bitmap[0]; | ||
151 | }; | ||
152 | |||
149 | struct mvumi_driver_event { | 153 | struct mvumi_driver_event { |
150 | u32 time_stamp; | 154 | u32 time_stamp; |
151 | u32 sequence_no; | 155 | u32 sequence_no; |
@@ -172,8 +176,14 @@ struct mvumi_events_wq { | |||
172 | void *param; | 176 | void *param; |
173 | }; | 177 | }; |
174 | 178 | ||
179 | #define HS_CAPABILITY_SUPPORT_COMPACT_SG (1U << 4) | ||
180 | #define HS_CAPABILITY_SUPPORT_PRD_HOST (1U << 5) | ||
181 | #define HS_CAPABILITY_SUPPORT_DYN_SRC (1U << 6) | ||
182 | #define HS_CAPABILITY_NEW_PAGE_IO_DEPTH_DEF (1U << 14) | ||
183 | |||
175 | #define MVUMI_MAX_SG_ENTRY 32 | 184 | #define MVUMI_MAX_SG_ENTRY 32 |
176 | #define SGD_EOT (1L << 27) | 185 | #define SGD_EOT (1L << 27) |
186 | #define SGD_EOT_CP (1L << 22) | ||
177 | 187 | ||
178 | struct mvumi_sgl { | 188 | struct mvumi_sgl { |
179 | u32 baseaddr_l; | 189 | u32 baseaddr_l; |
@@ -181,6 +191,39 @@ struct mvumi_sgl { | |||
181 | u32 flags; | 191 | u32 flags; |
182 | u32 size; | 192 | u32 size; |
183 | }; | 193 | }; |
194 | struct mvumi_compact_sgl { | ||
195 | u32 baseaddr_l; | ||
196 | u32 baseaddr_h; | ||
197 | u32 flags; | ||
198 | }; | ||
199 | |||
200 | #define GET_COMPACT_SGD_SIZE(sgd) \ | ||
201 | ((((struct mvumi_compact_sgl *)(sgd))->flags) & 0x3FFFFFL) | ||
202 | |||
203 | #define SET_COMPACT_SGD_SIZE(sgd, sz) do { \ | ||
204 | (((struct mvumi_compact_sgl *)(sgd))->flags) &= ~0x3FFFFFL; \ | ||
205 | (((struct mvumi_compact_sgl *)(sgd))->flags) |= (sz); \ | ||
206 | } while (0) | ||
207 | #define sgd_getsz(_mhba, sgd, sz) do { \ | ||
208 | if (_mhba->hba_capability & HS_CAPABILITY_SUPPORT_COMPACT_SG) \ | ||
209 | (sz) = GET_COMPACT_SGD_SIZE(sgd); \ | ||
210 | else \ | ||
211 | (sz) = (sgd)->size; \ | ||
212 | } while (0) | ||
213 | |||
214 | #define sgd_setsz(_mhba, sgd, sz) do { \ | ||
215 | if (_mhba->hba_capability & HS_CAPABILITY_SUPPORT_COMPACT_SG) \ | ||
216 | SET_COMPACT_SGD_SIZE(sgd, sz); \ | ||
217 | else \ | ||
218 | (sgd)->size = (sz); \ | ||
219 | } while (0) | ||
220 | |||
221 | #define sgd_inc(_mhba, sgd) do { \ | ||
222 | if (_mhba->hba_capability & HS_CAPABILITY_SUPPORT_COMPACT_SG) \ | ||
223 | sgd = (struct mvumi_sgl *)(((unsigned char *) (sgd)) + 12); \ | ||
224 | else \ | ||
225 | sgd = (struct mvumi_sgl *)(((unsigned char *) (sgd)) + 16); \ | ||
226 | } while (0) | ||
184 | 227 | ||
185 | struct mvumi_res { | 228 | struct mvumi_res { |
186 | struct list_head entry; | 229 | struct list_head entry; |
@@ -197,7 +240,7 @@ enum resource_type { | |||
197 | }; | 240 | }; |
198 | 241 | ||
199 | struct mvumi_sense_data { | 242 | struct mvumi_sense_data { |
200 | u8 error_eode:7; | 243 | u8 error_code:7; |
201 | u8 valid:1; | 244 | u8 valid:1; |
202 | u8 segment_number; | 245 | u8 segment_number; |
203 | u8 sense_key:4; | 246 | u8 sense_key:4; |
@@ -220,6 +263,7 @@ struct mvumi_sense_data { | |||
220 | struct mvumi_cmd { | 263 | struct mvumi_cmd { |
221 | struct list_head queue_pointer; | 264 | struct list_head queue_pointer; |
222 | struct mvumi_msg_frame *frame; | 265 | struct mvumi_msg_frame *frame; |
266 | dma_addr_t frame_phys; | ||
223 | struct scsi_cmnd *scmd; | 267 | struct scsi_cmnd *scmd; |
224 | atomic_t sync_cmd; | 268 | atomic_t sync_cmd; |
225 | void *data_buf; | 269 | void *data_buf; |
@@ -393,7 +437,8 @@ struct mvumi_hs_page2 { | |||
393 | u16 frame_length; | 437 | u16 frame_length; |
394 | 438 | ||
395 | u8 host_type; | 439 | u8 host_type; |
396 | u8 reserved[3]; | 440 | u8 host_cap; |
441 | u8 reserved[2]; | ||
397 | struct version_info host_ver; | 442 | struct version_info host_ver; |
398 | u32 system_io_bus; | 443 | u32 system_io_bus; |
399 | u32 slot_number; | 444 | u32 slot_number; |
@@ -435,8 +480,17 @@ struct mvumi_tag { | |||
435 | unsigned short size; | 480 | unsigned short size; |
436 | }; | 481 | }; |
437 | 482 | ||
483 | struct mvumi_device { | ||
484 | struct list_head list; | ||
485 | struct scsi_device *sdev; | ||
486 | u64 wwid; | ||
487 | u8 dev_type; | ||
488 | int id; | ||
489 | }; | ||
490 | |||
438 | struct mvumi_hba { | 491 | struct mvumi_hba { |
439 | void *base_addr[MAX_BASE_ADDRESS]; | 492 | void *base_addr[MAX_BASE_ADDRESS]; |
493 | u32 pci_base[MAX_BASE_ADDRESS]; | ||
440 | void *mmio; | 494 | void *mmio; |
441 | struct list_head cmd_pool; | 495 | struct list_head cmd_pool; |
442 | struct Scsi_Host *shost; | 496 | struct Scsi_Host *shost; |
@@ -449,6 +503,9 @@ struct mvumi_hba { | |||
449 | void *ib_list; | 503 | void *ib_list; |
450 | dma_addr_t ib_list_phys; | 504 | dma_addr_t ib_list_phys; |
451 | 505 | ||
506 | void *ib_frame; | ||
507 | dma_addr_t ib_frame_phys; | ||
508 | |||
452 | void *ob_list; | 509 | void *ob_list; |
453 | dma_addr_t ob_list_phys; | 510 | dma_addr_t ob_list_phys; |
454 | 511 | ||
@@ -477,12 +534,14 @@ struct mvumi_hba { | |||
477 | unsigned char hba_total_pages; | 534 | unsigned char hba_total_pages; |
478 | unsigned char fw_flag; | 535 | unsigned char fw_flag; |
479 | unsigned char request_id_enabled; | 536 | unsigned char request_id_enabled; |
537 | unsigned char eot_flag; | ||
480 | unsigned short hba_capability; | 538 | unsigned short hba_capability; |
481 | unsigned short io_seq; | 539 | unsigned short io_seq; |
482 | 540 | ||
483 | unsigned int ib_cur_slot; | 541 | unsigned int ib_cur_slot; |
484 | unsigned int ob_cur_slot; | 542 | unsigned int ob_cur_slot; |
485 | unsigned int fw_state; | 543 | unsigned int fw_state; |
544 | struct mutex sas_discovery_mutex; | ||
486 | 545 | ||
487 | struct list_head ob_data_list; | 546 | struct list_head ob_data_list; |
488 | struct list_head free_ob_list; | 547 | struct list_head free_ob_list; |
@@ -491,14 +550,24 @@ struct mvumi_hba { | |||
491 | 550 | ||
492 | struct mvumi_tag tag_pool; | 551 | struct mvumi_tag tag_pool; |
493 | struct mvumi_cmd **tag_cmd; | 552 | struct mvumi_cmd **tag_cmd; |
553 | struct mvumi_hw_regs *regs; | ||
554 | struct mutex device_lock; | ||
555 | struct list_head mhba_dev_list; | ||
556 | struct list_head shost_dev_list; | ||
557 | struct task_struct *dm_thread; | ||
558 | atomic_t pnp_count; | ||
494 | }; | 559 | }; |
495 | 560 | ||
496 | struct mvumi_instance_template { | 561 | struct mvumi_instance_template { |
497 | void (*fire_cmd)(struct mvumi_hba *, struct mvumi_cmd *); | 562 | void (*fire_cmd) (struct mvumi_hba *, struct mvumi_cmd *); |
498 | void (*enable_intr)(void *) ; | 563 | void (*enable_intr) (struct mvumi_hba *); |
499 | void (*disable_intr)(void *); | 564 | void (*disable_intr) (struct mvumi_hba *); |
500 | int (*clear_intr)(void *); | 565 | int (*clear_intr) (void *); |
501 | unsigned int (*read_fw_status_reg)(void *); | 566 | unsigned int (*read_fw_status_reg) (struct mvumi_hba *); |
567 | unsigned int (*check_ib_list) (struct mvumi_hba *); | ||
568 | int (*check_ob_list) (struct mvumi_hba *, unsigned int *, | ||
569 | unsigned int *); | ||
570 | int (*reset_host) (struct mvumi_hba *); | ||
502 | }; | 571 | }; |
503 | 572 | ||
504 | extern struct timezone sys_tz; | 573 | extern struct timezone sys_tz; |