1 // SPDX-License-Identifier: GPL-2.0-only
2 /*
3 * QLogic Fibre Channel HBA Driver
4 * Copyright (c) 2003-2014 QLogic Corporation
5 */
6 #include "qla_def.h"
7 #include "qla_target.h"
8
9 #include <linux/delay.h>
10 #include <linux/gfp.h>
11
12 #ifdef CONFIG_PPC
13 #define IS_PPCARCH true
14 #else
15 #define IS_PPCARCH false
16 #endif
17
18 static struct mb_cmd_name {
19 uint16_t cmd;
20 const char *str;
21 } mb_str[] = {
22 {MBC_GET_PORT_DATABASE, "GPDB"},
23 {MBC_GET_ID_LIST, "GIDList"},
24 {MBC_GET_LINK_PRIV_STATS, "Stats"},
25 {MBC_GET_RESOURCE_COUNTS, "ResCnt"},
26 };
27
mb_to_str(uint16_t cmd)28 static const char *mb_to_str(uint16_t cmd)
29 {
30 int i;
31 struct mb_cmd_name *e;
32
33 for (i = 0; i < ARRAY_SIZE(mb_str); i++) {
34 e = mb_str + i;
35 if (cmd == e->cmd)
36 return e->str;
37 }
38 return "unknown";
39 }
40
41 static struct rom_cmd {
42 uint16_t cmd;
43 } rom_cmds[] = {
44 { MBC_LOAD_RAM },
45 { MBC_EXECUTE_FIRMWARE },
46 { MBC_READ_RAM_WORD },
47 { MBC_MAILBOX_REGISTER_TEST },
48 { MBC_VERIFY_CHECKSUM },
49 { MBC_GET_FIRMWARE_VERSION },
50 { MBC_LOAD_RISC_RAM },
51 { MBC_DUMP_RISC_RAM },
52 { MBC_LOAD_RISC_RAM_EXTENDED },
53 { MBC_DUMP_RISC_RAM_EXTENDED },
54 { MBC_WRITE_RAM_WORD_EXTENDED },
55 { MBC_READ_RAM_EXTENDED },
56 { MBC_GET_RESOURCE_COUNTS },
57 { MBC_SET_FIRMWARE_OPTION },
58 { MBC_MID_INITIALIZE_FIRMWARE },
59 { MBC_GET_FIRMWARE_STATE },
60 { MBC_GET_MEM_OFFLOAD_CNTRL_STAT },
61 { MBC_GET_RETRY_COUNT },
62 { MBC_TRACE_CONTROL },
63 { MBC_INITIALIZE_MULTIQ },
64 { MBC_IOCB_COMMAND_A64 },
65 { MBC_GET_ADAPTER_LOOP_ID },
66 { MBC_READ_SFP },
67 { MBC_SET_RNID_PARAMS },
68 { MBC_GET_RNID_PARAMS },
69 { MBC_GET_SET_ZIO_THRESHOLD },
70 };
71
is_rom_cmd(uint16_t cmd)72 static int is_rom_cmd(uint16_t cmd)
73 {
74 int i;
75 struct rom_cmd *wc;
76
77 for (i = 0; i < ARRAY_SIZE(rom_cmds); i++) {
78 wc = rom_cmds + i;
79 if (wc->cmd == cmd)
80 return 1;
81 }
82
83 return 0;
84 }
85
86 /*
87 * qla2x00_mailbox_command
88 * Issue mailbox command and waits for completion.
89 *
90 * Input:
91 * ha = adapter block pointer.
92 * mcp = driver internal mbx struct pointer.
93 *
94 * Output:
95 * mb[MAX_MAILBOX_REGISTER_COUNT] = returned mailbox data.
96 *
97 * Returns:
98 * 0 : QLA_SUCCESS = cmd performed success
99 * 1 : QLA_FUNCTION_FAILED (error encountered)
100 * 6 : QLA_FUNCTION_TIMEOUT (timeout condition encountered)
101 *
102 * Context:
103 * Kernel context.
104 */
105 static int
qla2x00_mailbox_command(scsi_qla_host_t * vha,mbx_cmd_t * mcp)106 qla2x00_mailbox_command(scsi_qla_host_t *vha, mbx_cmd_t *mcp)
107 {
108 int rval, i;
109 unsigned long flags = 0;
110 device_reg_t *reg;
111 uint8_t abort_active, eeh_delay;
112 uint8_t io_lock_on;
113 uint16_t command = 0;
114 uint16_t *iptr;
115 __le16 __iomem *optr;
116 uint32_t cnt;
117 uint32_t mboxes;
118 unsigned long wait_time;
119 struct qla_hw_data *ha = vha->hw;
120 scsi_qla_host_t *base_vha = pci_get_drvdata(ha->pdev);
121 u32 chip_reset;
122
123
124 ql_dbg(ql_dbg_mbx, vha, 0x1000, "Entered %s.\n", __func__);
125
126 if (ha->pdev->error_state == pci_channel_io_perm_failure) {
127 ql_log(ql_log_warn, vha, 0x1001,
128 "PCI channel failed permanently, exiting.\n");
129 return QLA_FUNCTION_TIMEOUT;
130 }
131
132 if (vha->device_flags & DFLG_DEV_FAILED) {
133 ql_log(ql_log_warn, vha, 0x1002,
134 "Device in failed state, exiting.\n");
135 return QLA_FUNCTION_TIMEOUT;
136 }
137
138 /* if PCI error, then avoid mbx processing.*/
139 if (test_bit(PFLG_DISCONNECTED, &base_vha->dpc_flags) &&
140 test_bit(UNLOADING, &base_vha->dpc_flags)) {
141 ql_log(ql_log_warn, vha, 0xd04e,
142 "PCI error, exiting.\n");
143 return QLA_FUNCTION_TIMEOUT;
144 }
145 eeh_delay = 0;
146 reg = ha->iobase;
147 io_lock_on = base_vha->flags.init_done;
148
149 rval = QLA_SUCCESS;
150 abort_active = test_bit(ABORT_ISP_ACTIVE, &base_vha->dpc_flags);
151 chip_reset = ha->chip_reset;
152
153 if (ha->flags.pci_channel_io_perm_failure) {
154 ql_log(ql_log_warn, vha, 0x1003,
155 "Perm failure on EEH timeout MBX, exiting.\n");
156 return QLA_FUNCTION_TIMEOUT;
157 }
158
159 if (IS_P3P_TYPE(ha) && ha->flags.isp82xx_fw_hung) {
160 /* Setting Link-Down error */
161 mcp->mb[0] = MBS_LINK_DOWN_ERROR;
162 ql_log(ql_log_warn, vha, 0x1004,
163 "FW hung = %d.\n", ha->flags.isp82xx_fw_hung);
164 return QLA_FUNCTION_TIMEOUT;
165 }
166
167 /* check if ISP abort is active and return cmd with timeout */
168 if (((test_bit(ABORT_ISP_ACTIVE, &base_vha->dpc_flags) ||
169 test_bit(ISP_ABORT_RETRY, &base_vha->dpc_flags) ||
170 test_bit(ISP_ABORT_NEEDED, &base_vha->dpc_flags)) &&
171 !is_rom_cmd(mcp->mb[0])) || ha->flags.eeh_busy) {
172 ql_log(ql_log_info, vha, 0x1005,
173 "Cmd 0x%x aborted with timeout since ISP Abort is pending\n",
174 mcp->mb[0]);
175 return QLA_FUNCTION_TIMEOUT;
176 }
177
178 atomic_inc(&ha->num_pend_mbx_stage1);
179 /*
180 * Wait for active mailbox commands to finish by waiting at most tov
181 * seconds. This is to serialize actual issuing of mailbox cmds during
182 * non ISP abort time.
183 */
184 if (!wait_for_completion_timeout(&ha->mbx_cmd_comp, mcp->tov * HZ)) {
185 /* Timeout occurred. Return error. */
186 ql_log(ql_log_warn, vha, 0xd035,
187 "Cmd access timeout, cmd=0x%x, Exiting.\n",
188 mcp->mb[0]);
189 vha->hw_err_cnt++;
190 atomic_dec(&ha->num_pend_mbx_stage1);
191 return QLA_FUNCTION_TIMEOUT;
192 }
193 atomic_dec(&ha->num_pend_mbx_stage1);
194 if (ha->flags.purge_mbox || chip_reset != ha->chip_reset ||
195 ha->flags.eeh_busy) {
196 ql_log(ql_log_warn, vha, 0xd035,
197 "Error detected: purge[%d] eeh[%d] cmd=0x%x, Exiting.\n",
198 ha->flags.purge_mbox, ha->flags.eeh_busy, mcp->mb[0]);
199 rval = QLA_ABORTED;
200 goto premature_exit;
201 }
202
203
204 /* Save mailbox command for debug */
205 ha->mcp = mcp;
206
207 ql_dbg(ql_dbg_mbx, vha, 0x1006,
208 "Prepare to issue mbox cmd=0x%x.\n", mcp->mb[0]);
209
210 spin_lock_irqsave(&ha->hardware_lock, flags);
211
212 if (ha->flags.purge_mbox || chip_reset != ha->chip_reset ||
213 ha->flags.mbox_busy) {
214 rval = QLA_ABORTED;
215 spin_unlock_irqrestore(&ha->hardware_lock, flags);
216 goto premature_exit;
217 }
218 ha->flags.mbox_busy = 1;
219
220 /* Load mailbox registers. */
221 if (IS_P3P_TYPE(ha))
222 optr = ®->isp82.mailbox_in[0];
223 else if (IS_FWI2_CAPABLE(ha) && !(IS_P3P_TYPE(ha)))
224 optr = ®->isp24.mailbox0;
225 else
226 optr = MAILBOX_REG(ha, ®->isp, 0);
227
228 iptr = mcp->mb;
229 command = mcp->mb[0];
230 mboxes = mcp->out_mb;
231
232 ql_dbg(ql_dbg_mbx, vha, 0x1111,
233 "Mailbox registers (OUT):\n");
234 for (cnt = 0; cnt < ha->mbx_count; cnt++) {
235 if (IS_QLA2200(ha) && cnt == 8)
236 optr = MAILBOX_REG(ha, ®->isp, 8);
237 if (mboxes & BIT_0) {
238 ql_dbg(ql_dbg_mbx, vha, 0x1112,
239 "mbox[%d]<-0x%04x\n", cnt, *iptr);
240 wrt_reg_word(optr, *iptr);
241 } else {
242 wrt_reg_word(optr, 0);
243 }
244
245 mboxes >>= 1;
246 optr++;
247 iptr++;
248 }
249
250 ql_dbg(ql_dbg_mbx + ql_dbg_buffer, vha, 0x1117,
251 "I/O Address = %p.\n", optr);
252
253 /* Issue set host interrupt command to send cmd out. */
254 ha->flags.mbox_int = 0;
255 clear_bit(MBX_INTERRUPT, &ha->mbx_cmd_flags);
256
257 /* Unlock mbx registers and wait for interrupt */
258 ql_dbg(ql_dbg_mbx, vha, 0x100f,
259 "Going to unlock irq & waiting for interrupts. "
260 "jiffies=%lx.\n", jiffies);
261
262 /* Wait for mbx cmd completion until timeout */
263 atomic_inc(&ha->num_pend_mbx_stage2);
264 if ((!abort_active && io_lock_on) || IS_NOPOLLING_TYPE(ha)) {
265 set_bit(MBX_INTR_WAIT, &ha->mbx_cmd_flags);
266
267 if (IS_P3P_TYPE(ha))
268 wrt_reg_dword(®->isp82.hint, HINT_MBX_INT_PENDING);
269 else if (IS_FWI2_CAPABLE(ha))
270 wrt_reg_dword(®->isp24.hccr, HCCRX_SET_HOST_INT);
271 else
272 wrt_reg_word(®->isp.hccr, HCCR_SET_HOST_INT);
273 spin_unlock_irqrestore(&ha->hardware_lock, flags);
274
275 wait_time = jiffies;
276 if (!wait_for_completion_timeout(&ha->mbx_intr_comp,
277 mcp->tov * HZ)) {
278 ql_dbg(ql_dbg_mbx, vha, 0x117a,
279 "cmd=%x Timeout.\n", command);
280 spin_lock_irqsave(&ha->hardware_lock, flags);
281 clear_bit(MBX_INTR_WAIT, &ha->mbx_cmd_flags);
282 spin_unlock_irqrestore(&ha->hardware_lock, flags);
283
284 if (chip_reset != ha->chip_reset) {
285 eeh_delay = ha->flags.eeh_busy ? 1 : 0;
286
287 spin_lock_irqsave(&ha->hardware_lock, flags);
288 ha->flags.mbox_busy = 0;
289 spin_unlock_irqrestore(&ha->hardware_lock,
290 flags);
291 atomic_dec(&ha->num_pend_mbx_stage2);
292 rval = QLA_ABORTED;
293 goto premature_exit;
294 }
295 } else if (ha->flags.purge_mbox ||
296 chip_reset != ha->chip_reset) {
297 eeh_delay = ha->flags.eeh_busy ? 1 : 0;
298
299 spin_lock_irqsave(&ha->hardware_lock, flags);
300 ha->flags.mbox_busy = 0;
301 spin_unlock_irqrestore(&ha->hardware_lock, flags);
302 atomic_dec(&ha->num_pend_mbx_stage2);
303 rval = QLA_ABORTED;
304 goto premature_exit;
305 }
306
307 if (time_after(jiffies, wait_time + 5 * HZ))
308 ql_log(ql_log_warn, vha, 0x1015, "cmd=0x%x, waited %d msecs\n",
309 command, jiffies_to_msecs(jiffies - wait_time));
310 } else {
311 ql_dbg(ql_dbg_mbx, vha, 0x1011,
312 "Cmd=%x Polling Mode.\n", command);
313
314 if (IS_P3P_TYPE(ha)) {
315 if (rd_reg_dword(®->isp82.hint) &
316 HINT_MBX_INT_PENDING) {
317 ha->flags.mbox_busy = 0;
318 spin_unlock_irqrestore(&ha->hardware_lock,
319 flags);
320 atomic_dec(&ha->num_pend_mbx_stage2);
321 ql_dbg(ql_dbg_mbx, vha, 0x1012,
322 "Pending mailbox timeout, exiting.\n");
323 vha->hw_err_cnt++;
324 rval = QLA_FUNCTION_TIMEOUT;
325 goto premature_exit;
326 }
327 wrt_reg_dword(®->isp82.hint, HINT_MBX_INT_PENDING);
328 } else if (IS_FWI2_CAPABLE(ha))
329 wrt_reg_dword(®->isp24.hccr, HCCRX_SET_HOST_INT);
330 else
331 wrt_reg_word(®->isp.hccr, HCCR_SET_HOST_INT);
332 spin_unlock_irqrestore(&ha->hardware_lock, flags);
333
334 wait_time = jiffies + mcp->tov * HZ; /* wait at most tov secs */
335 while (!ha->flags.mbox_int) {
336 if (ha->flags.purge_mbox ||
337 chip_reset != ha->chip_reset) {
338 eeh_delay = ha->flags.eeh_busy ? 1 : 0;
339
340 spin_lock_irqsave(&ha->hardware_lock, flags);
341 ha->flags.mbox_busy = 0;
342 spin_unlock_irqrestore(&ha->hardware_lock,
343 flags);
344 atomic_dec(&ha->num_pend_mbx_stage2);
345 rval = QLA_ABORTED;
346 goto premature_exit;
347 }
348
349 if (time_after(jiffies, wait_time))
350 break;
351
352 /* Check for pending interrupts. */
353 qla2x00_poll(ha->rsp_q_map[0]);
354
355 if (!ha->flags.mbox_int &&
356 !(IS_QLA2200(ha) &&
357 command == MBC_LOAD_RISC_RAM_EXTENDED))
358 msleep(10);
359 } /* while */
360 ql_dbg(ql_dbg_mbx, vha, 0x1013,
361 "Waited %d sec.\n",
362 (uint)((jiffies - (wait_time - (mcp->tov * HZ)))/HZ));
363 }
364 atomic_dec(&ha->num_pend_mbx_stage2);
365
366 /* Check whether we timed out */
367 if (ha->flags.mbox_int) {
368 uint16_t *iptr2;
369
370 ql_dbg(ql_dbg_mbx, vha, 0x1014,
371 "Cmd=%x completed.\n", command);
372
373 /* Got interrupt. Clear the flag. */
374 ha->flags.mbox_int = 0;
375 clear_bit(MBX_INTERRUPT, &ha->mbx_cmd_flags);
376
377 if (IS_P3P_TYPE(ha) && ha->flags.isp82xx_fw_hung) {
378 spin_lock_irqsave(&ha->hardware_lock, flags);
379 ha->flags.mbox_busy = 0;
380 spin_unlock_irqrestore(&ha->hardware_lock, flags);
381
382 /* Setting Link-Down error */
383 mcp->mb[0] = MBS_LINK_DOWN_ERROR;
384 ha->mcp = NULL;
385 rval = QLA_FUNCTION_FAILED;
386 ql_log(ql_log_warn, vha, 0xd048,
387 "FW hung = %d.\n", ha->flags.isp82xx_fw_hung);
388 goto premature_exit;
389 }
390
391 if (ha->mailbox_out[0] != MBS_COMMAND_COMPLETE) {
392 ql_dbg(ql_dbg_mbx, vha, 0x11ff,
393 "mb_out[0] = %#x <> %#x\n", ha->mailbox_out[0],
394 MBS_COMMAND_COMPLETE);
395 rval = QLA_FUNCTION_FAILED;
396 }
397
398 /* Load return mailbox registers. */
399 iptr2 = mcp->mb;
400 iptr = (uint16_t *)&ha->mailbox_out[0];
401 mboxes = mcp->in_mb;
402
403 ql_dbg(ql_dbg_mbx, vha, 0x1113,
404 "Mailbox registers (IN):\n");
405 for (cnt = 0; cnt < ha->mbx_count; cnt++) {
406 if (mboxes & BIT_0) {
407 *iptr2 = *iptr;
408 ql_dbg(ql_dbg_mbx, vha, 0x1114,
409 "mbox[%d]->0x%04x\n", cnt, *iptr2);
410 }
411
412 mboxes >>= 1;
413 iptr2++;
414 iptr++;
415 }
416 } else {
417
418 uint16_t mb[8];
419 uint32_t ictrl, host_status, hccr;
420 uint16_t w;
421
422 if (IS_FWI2_CAPABLE(ha)) {
423 mb[0] = rd_reg_word(®->isp24.mailbox0);
424 mb[1] = rd_reg_word(®->isp24.mailbox1);
425 mb[2] = rd_reg_word(®->isp24.mailbox2);
426 mb[3] = rd_reg_word(®->isp24.mailbox3);
427 mb[7] = rd_reg_word(®->isp24.mailbox7);
428 ictrl = rd_reg_dword(®->isp24.ictrl);
429 host_status = rd_reg_dword(®->isp24.host_status);
430 hccr = rd_reg_dword(®->isp24.hccr);
431
432 ql_log(ql_log_warn, vha, 0xd04c,
433 "MBX Command timeout for cmd %x, iocontrol=%x jiffies=%lx "
434 "mb[0-3]=[0x%x 0x%x 0x%x 0x%x] mb7 0x%x host_status 0x%x hccr 0x%x\n",
435 command, ictrl, jiffies, mb[0], mb[1], mb[2], mb[3],
436 mb[7], host_status, hccr);
437 vha->hw_err_cnt++;
438
439 } else {
440 mb[0] = RD_MAILBOX_REG(ha, ®->isp, 0);
441 ictrl = rd_reg_word(®->isp.ictrl);
442 ql_dbg(ql_dbg_mbx + ql_dbg_buffer, vha, 0x1119,
443 "MBX Command timeout for cmd %x, iocontrol=%x jiffies=%lx "
444 "mb[0]=0x%x\n", command, ictrl, jiffies, mb[0]);
445 vha->hw_err_cnt++;
446 }
447 ql_dump_regs(ql_dbg_mbx + ql_dbg_buffer, vha, 0x1019);
448
449 /* Capture FW dump only, if PCI device active */
450 if (!pci_channel_offline(vha->hw->pdev)) {
451 pci_read_config_word(ha->pdev, PCI_VENDOR_ID, &w);
452 if (w == 0xffff || ictrl == 0xffffffff ||
453 (chip_reset != ha->chip_reset)) {
454 /* This is special case if there is unload
455 * of driver happening and if PCI device go
456 * into bad state due to PCI error condition
457 * then only PCI ERR flag would be set.
458 * we will do premature exit for above case.
459 */
460 spin_lock_irqsave(&ha->hardware_lock, flags);
461 ha->flags.mbox_busy = 0;
462 spin_unlock_irqrestore(&ha->hardware_lock,
463 flags);
464 rval = QLA_FUNCTION_TIMEOUT;
465 goto premature_exit;
466 }
467
468 /* Attempt to capture firmware dump for further
469 * anallysis of the current formware state. we do not
470 * need to do this if we are intentionally generating
471 * a dump
472 */
473 if (mcp->mb[0] != MBC_GEN_SYSTEM_ERROR)
474 qla2xxx_dump_fw(vha);
475 rval = QLA_FUNCTION_TIMEOUT;
476 }
477 }
478 spin_lock_irqsave(&ha->hardware_lock, flags);
479 ha->flags.mbox_busy = 0;
480 spin_unlock_irqrestore(&ha->hardware_lock, flags);
481
482 /* Clean up */
483 ha->mcp = NULL;
484
485 if ((abort_active || !io_lock_on) && !IS_NOPOLLING_TYPE(ha)) {
486 ql_dbg(ql_dbg_mbx, vha, 0x101a,
487 "Checking for additional resp interrupt.\n");
488
489 /* polling mode for non isp_abort commands. */
490 qla2x00_poll(ha->rsp_q_map[0]);
491 }
492
493 if (rval == QLA_FUNCTION_TIMEOUT &&
494 mcp->mb[0] != MBC_GEN_SYSTEM_ERROR) {
495 if (!io_lock_on || (mcp->flags & IOCTL_CMD) ||
496 ha->flags.eeh_busy) {
497 /* not in dpc. schedule it for dpc to take over. */
498 ql_dbg(ql_dbg_mbx, vha, 0x101b,
499 "Timeout, schedule isp_abort_needed.\n");
500
501 if (!test_bit(ISP_ABORT_NEEDED, &vha->dpc_flags) &&
502 !test_bit(ABORT_ISP_ACTIVE, &vha->dpc_flags) &&
503 !test_bit(ISP_ABORT_RETRY, &vha->dpc_flags)) {
504 if (IS_QLA82XX(ha)) {
505 ql_dbg(ql_dbg_mbx, vha, 0x112a,
506 "disabling pause transmit on port "
507 "0 & 1.\n");
508 qla82xx_wr_32(ha,
509 QLA82XX_CRB_NIU + 0x98,
510 CRB_NIU_XG_PAUSE_CTL_P0|
511 CRB_NIU_XG_PAUSE_CTL_P1);
512 }
513 ql_log(ql_log_info, base_vha, 0x101c,
514 "Mailbox cmd timeout occurred, cmd=0x%x, "
515 "mb[0]=0x%x, eeh_busy=0x%x. Scheduling ISP "
516 "abort.\n", command, mcp->mb[0],
517 ha->flags.eeh_busy);
518 vha->hw_err_cnt++;
519 set_bit(ISP_ABORT_NEEDED, &vha->dpc_flags);
520 qla2xxx_wake_dpc(vha);
521 }
522 } else if (current == ha->dpc_thread) {
523 /* call abort directly since we are in the DPC thread */
524 ql_dbg(ql_dbg_mbx, vha, 0x101d,
525 "Timeout, calling abort_isp.\n");
526
527 if (!test_bit(ISP_ABORT_NEEDED, &vha->dpc_flags) &&
528 !test_bit(ABORT_ISP_ACTIVE, &vha->dpc_flags) &&
529 !test_bit(ISP_ABORT_RETRY, &vha->dpc_flags)) {
530 if (IS_QLA82XX(ha)) {
531 ql_dbg(ql_dbg_mbx, vha, 0x112b,
532 "disabling pause transmit on port "
533 "0 & 1.\n");
534 qla82xx_wr_32(ha,
535 QLA82XX_CRB_NIU + 0x98,
536 CRB_NIU_XG_PAUSE_CTL_P0|
537 CRB_NIU_XG_PAUSE_CTL_P1);
538 }
539 ql_log(ql_log_info, base_vha, 0x101e,
540 "Mailbox cmd timeout occurred, cmd=0x%x, "
541 "mb[0]=0x%x. Scheduling ISP abort ",
542 command, mcp->mb[0]);
543 vha->hw_err_cnt++;
544 set_bit(ABORT_ISP_ACTIVE, &vha->dpc_flags);
545 clear_bit(ISP_ABORT_NEEDED, &vha->dpc_flags);
546 /* Allow next mbx cmd to come in. */
547 complete(&ha->mbx_cmd_comp);
548 if (ha->isp_ops->abort_isp(vha) &&
549 !ha->flags.eeh_busy) {
550 /* Failed. retry later. */
551 set_bit(ISP_ABORT_NEEDED,
552 &vha->dpc_flags);
553 }
554 clear_bit(ABORT_ISP_ACTIVE, &vha->dpc_flags);
555 ql_dbg(ql_dbg_mbx, vha, 0x101f,
556 "Finished abort_isp.\n");
557 goto mbx_done;
558 }
559 }
560 }
561
562 premature_exit:
563 /* Allow next mbx cmd to come in. */
564 complete(&ha->mbx_cmd_comp);
565
566 mbx_done:
567 if (rval == QLA_ABORTED) {
568 ql_log(ql_log_info, vha, 0xd035,
569 "Chip Reset in progress. Purging Mbox cmd=0x%x.\n",
570 mcp->mb[0]);
571 } else if (rval) {
572 if (ql2xextended_error_logging & (ql_dbg_disc|ql_dbg_mbx)) {
573 pr_warn("%s [%s]-%04x:%ld: **** Failed=%x", QL_MSGHDR,
574 dev_name(&ha->pdev->dev), 0x1020+0x800,
575 vha->host_no, rval);
576 mboxes = mcp->in_mb;
577 cnt = 4;
578 for (i = 0; i < ha->mbx_count && cnt; i++, mboxes >>= 1)
579 if (mboxes & BIT_0) {
580 printk(" mb[%u]=%x", i, mcp->mb[i]);
581 cnt--;
582 }
583 pr_warn(" cmd=%x ****\n", command);
584 }
585 if (IS_FWI2_CAPABLE(ha) && !(IS_P3P_TYPE(ha))) {
586 ql_dbg(ql_dbg_mbx, vha, 0x1198,
587 "host_status=%#x intr_ctrl=%#x intr_status=%#x\n",
588 rd_reg_dword(®->isp24.host_status),
589 rd_reg_dword(®->isp24.ictrl),
590 rd_reg_dword(®->isp24.istatus));
591 } else {
592 ql_dbg(ql_dbg_mbx, vha, 0x1206,
593 "ctrl_status=%#x ictrl=%#x istatus=%#x\n",
594 rd_reg_word(®->isp.ctrl_status),
595 rd_reg_word(®->isp.ictrl),
596 rd_reg_word(®->isp.istatus));
597 }
598 } else {
599 ql_dbg(ql_dbg_mbx, base_vha, 0x1021, "Done %s.\n", __func__);
600 }
601
602 i = 500;
603 while (i && eeh_delay && (ha->pci_error_state < QLA_PCI_SLOT_RESET)) {
604 /*
605 * The caller of this mailbox encounter pci error.
606 * Hold the thread until PCIE link reset complete to make
607 * sure caller does not unmap dma while recovery is
608 * in progress.
609 */
610 msleep(1);
611 i--;
612 }
613 return rval;
614 }
615
616 int
qla2x00_load_ram(scsi_qla_host_t * vha,dma_addr_t req_dma,uint32_t risc_addr,uint32_t risc_code_size)617 qla2x00_load_ram(scsi_qla_host_t *vha, dma_addr_t req_dma, uint32_t risc_addr,
618 uint32_t risc_code_size)
619 {
620 int rval;
621 struct qla_hw_data *ha = vha->hw;
622 mbx_cmd_t mc;
623 mbx_cmd_t *mcp = &mc;
624
625 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1022,
626 "Entered %s.\n", __func__);
627
628 if (MSW(risc_addr) || IS_FWI2_CAPABLE(ha)) {
629 mcp->mb[0] = MBC_LOAD_RISC_RAM_EXTENDED;
630 mcp->mb[8] = MSW(risc_addr);
631 mcp->out_mb = MBX_8|MBX_0;
632 } else {
633 mcp->mb[0] = MBC_LOAD_RISC_RAM;
634 mcp->out_mb = MBX_0;
635 }
636 mcp->mb[1] = LSW(risc_addr);
637 mcp->mb[2] = MSW(req_dma);
638 mcp->mb[3] = LSW(req_dma);
639 mcp->mb[6] = MSW(MSD(req_dma));
640 mcp->mb[7] = LSW(MSD(req_dma));
641 mcp->out_mb |= MBX_7|MBX_6|MBX_3|MBX_2|MBX_1;
642 if (IS_FWI2_CAPABLE(ha)) {
643 mcp->mb[4] = MSW(risc_code_size);
644 mcp->mb[5] = LSW(risc_code_size);
645 mcp->out_mb |= MBX_5|MBX_4;
646 } else {
647 mcp->mb[4] = LSW(risc_code_size);
648 mcp->out_mb |= MBX_4;
649 }
650
651 mcp->in_mb = MBX_1|MBX_0;
652 mcp->tov = MBX_TOV_SECONDS;
653 mcp->flags = 0;
654 rval = qla2x00_mailbox_command(vha, mcp);
655
656 if (rval != QLA_SUCCESS) {
657 ql_dbg(ql_dbg_mbx, vha, 0x1023,
658 "Failed=%x mb[0]=%x mb[1]=%x.\n",
659 rval, mcp->mb[0], mcp->mb[1]);
660 vha->hw_err_cnt++;
661 } else {
662 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1024,
663 "Done %s.\n", __func__);
664 }
665
666 return rval;
667 }
668
669 #define NVME_ENABLE_FLAG BIT_3
670 #define EDIF_HW_SUPPORT BIT_10
671
672 /*
673 * qla2x00_execute_fw
674 * Start adapter firmware.
675 *
676 * Input:
677 * ha = adapter block pointer.
678 * TARGET_QUEUE_LOCK must be released.
679 * ADAPTER_STATE_LOCK must be released.
680 *
681 * Returns:
682 * qla2x00 local function return status code.
683 *
684 * Context:
685 * Kernel context.
686 */
687 int
qla2x00_execute_fw(scsi_qla_host_t * vha,uint32_t risc_addr)688 qla2x00_execute_fw(scsi_qla_host_t *vha, uint32_t risc_addr)
689 {
690 int rval;
691 struct qla_hw_data *ha = vha->hw;
692 mbx_cmd_t mc;
693 mbx_cmd_t *mcp = &mc;
694 u8 semaphore = 0;
695 #define EXE_FW_FORCE_SEMAPHORE BIT_7
696 u8 retry = 3;
697
698 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1025,
699 "Entered %s.\n", __func__);
700
701 again:
702 mcp->mb[0] = MBC_EXECUTE_FIRMWARE;
703 mcp->out_mb = MBX_0;
704 mcp->in_mb = MBX_0;
705 if (IS_FWI2_CAPABLE(ha)) {
706 mcp->mb[1] = MSW(risc_addr);
707 mcp->mb[2] = LSW(risc_addr);
708 mcp->mb[3] = 0;
709 mcp->mb[4] = 0;
710 mcp->mb[11] = 0;
711
712 /* Enable BPM? */
713 if (ha->flags.lr_detected) {
714 mcp->mb[4] = BIT_0;
715 if (IS_BPM_RANGE_CAPABLE(ha))
716 mcp->mb[4] |=
717 ha->lr_distance << LR_DIST_FW_POS;
718 }
719
720 if (ql2xnvmeenable && (IS_QLA27XX(ha) || IS_QLA28XX(ha)))
721 mcp->mb[4] |= NVME_ENABLE_FLAG;
722
723 if (IS_QLA83XX(ha) || IS_QLA27XX(ha) || IS_QLA28XX(ha)) {
724 struct nvram_81xx *nv = ha->nvram;
725 /* set minimum speed if specified in nvram */
726 if (nv->min_supported_speed >= 2 &&
727 nv->min_supported_speed <= 5) {
728 mcp->mb[4] |= BIT_4;
729 mcp->mb[11] |= nv->min_supported_speed & 0xF;
730 mcp->out_mb |= MBX_11;
731 mcp->in_mb |= BIT_5;
732 vha->min_supported_speed =
733 nv->min_supported_speed;
734 }
735
736 if (IS_PPCARCH)
737 mcp->mb[11] |= BIT_4;
738 }
739
740 if (ha->flags.exlogins_enabled)
741 mcp->mb[4] |= ENABLE_EXTENDED_LOGIN;
742
743 if (ha->flags.exchoffld_enabled)
744 mcp->mb[4] |= ENABLE_EXCHANGE_OFFLD;
745
746 if (semaphore)
747 mcp->mb[11] |= EXE_FW_FORCE_SEMAPHORE;
748
749 mcp->out_mb |= MBX_4 | MBX_3 | MBX_2 | MBX_1 | MBX_11;
750 mcp->in_mb |= MBX_5 | MBX_3 | MBX_2 | MBX_1;
751 } else {
752 mcp->mb[1] = LSW(risc_addr);
753 mcp->out_mb |= MBX_1;
754 if (IS_QLA2322(ha) || IS_QLA6322(ha)) {
755 mcp->mb[2] = 0;
756 mcp->out_mb |= MBX_2;
757 }
758 }
759
760 mcp->tov = MBX_TOV_SECONDS;
761 mcp->flags = 0;
762 rval = qla2x00_mailbox_command(vha, mcp);
763
764 if (rval != QLA_SUCCESS) {
765 if (IS_QLA28XX(ha) && rval == QLA_COMMAND_ERROR &&
766 mcp->mb[1] == 0x27 && retry) {
767 semaphore = 1;
768 retry--;
769 ql_dbg(ql_dbg_async, vha, 0x1026,
770 "Exe FW: force semaphore.\n");
771 goto again;
772 }
773
774 ql_dbg(ql_dbg_mbx, vha, 0x1026,
775 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
776 vha->hw_err_cnt++;
777 return rval;
778 }
779
780 if (!IS_FWI2_CAPABLE(ha))
781 goto done;
782
783 ha->fw_ability_mask = mcp->mb[3] << 16 | mcp->mb[2];
784 ql_dbg(ql_dbg_mbx, vha, 0x119a,
785 "fw_ability_mask=%x.\n", ha->fw_ability_mask);
786 ql_dbg(ql_dbg_mbx, vha, 0x1027, "exchanges=%x.\n", mcp->mb[1]);
787 if (IS_QLA27XX(ha) || IS_QLA28XX(ha)) {
788 ha->max_supported_speed = mcp->mb[2] & (BIT_0|BIT_1);
789 ql_dbg(ql_dbg_mbx, vha, 0x119b, "max_supported_speed=%s.\n",
790 ha->max_supported_speed == 0 ? "16Gps" :
791 ha->max_supported_speed == 1 ? "32Gps" :
792 ha->max_supported_speed == 2 ? "64Gps" : "unknown");
793 if (vha->min_supported_speed) {
794 ha->min_supported_speed = mcp->mb[5] &
795 (BIT_0 | BIT_1 | BIT_2);
796 ql_dbg(ql_dbg_mbx, vha, 0x119c,
797 "min_supported_speed=%s.\n",
798 ha->min_supported_speed == 6 ? "64Gps" :
799 ha->min_supported_speed == 5 ? "32Gps" :
800 ha->min_supported_speed == 4 ? "16Gps" :
801 ha->min_supported_speed == 3 ? "8Gps" :
802 ha->min_supported_speed == 2 ? "4Gps" : "unknown");
803 }
804 }
805
806 if (IS_QLA28XX(ha) && (mcp->mb[5] & EDIF_HW_SUPPORT)) {
807 ha->flags.edif_hw = 1;
808 ql_log(ql_log_info, vha, 0xffff,
809 "%s: edif HW\n", __func__);
810 }
811
812 done:
813 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1028,
814 "Done %s.\n", __func__);
815
816 return rval;
817 }
818
819 /*
820 * qla_get_exlogin_status
821 * Get extended login status
822 * uses the memory offload control/status Mailbox
823 *
824 * Input:
825 * ha: adapter state pointer.
826 * fwopt: firmware options
827 *
828 * Returns:
829 * qla2x00 local function status
830 *
831 * Context:
832 * Kernel context.
833 */
834 #define FETCH_XLOGINS_STAT 0x8
835 int
qla_get_exlogin_status(scsi_qla_host_t * vha,uint16_t * buf_sz,uint16_t * ex_logins_cnt)836 qla_get_exlogin_status(scsi_qla_host_t *vha, uint16_t *buf_sz,
837 uint16_t *ex_logins_cnt)
838 {
839 int rval;
840 mbx_cmd_t mc;
841 mbx_cmd_t *mcp = &mc;
842
843 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x118f,
844 "Entered %s\n", __func__);
845
846 memset(mcp->mb, 0 , sizeof(mcp->mb));
847 mcp->mb[0] = MBC_GET_MEM_OFFLOAD_CNTRL_STAT;
848 mcp->mb[1] = FETCH_XLOGINS_STAT;
849 mcp->out_mb = MBX_1|MBX_0;
850 mcp->in_mb = MBX_10|MBX_4|MBX_0;
851 mcp->tov = MBX_TOV_SECONDS;
852 mcp->flags = 0;
853
854 rval = qla2x00_mailbox_command(vha, mcp);
855 if (rval != QLA_SUCCESS) {
856 ql_dbg(ql_dbg_mbx, vha, 0x1115, "Failed=%x.\n", rval);
857 } else {
858 *buf_sz = mcp->mb[4];
859 *ex_logins_cnt = mcp->mb[10];
860
861 ql_log(ql_log_info, vha, 0x1190,
862 "buffer size 0x%x, exchange login count=%d\n",
863 mcp->mb[4], mcp->mb[10]);
864
865 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1116,
866 "Done %s.\n", __func__);
867 }
868
869 return rval;
870 }
871
872 /*
873 * qla_set_exlogin_mem_cfg
874 * set extended login memory configuration
875 * Mbx needs to be issues before init_cb is set
876 *
877 * Input:
878 * ha: adapter state pointer.
879 * buffer: buffer pointer
880 * phys_addr: physical address of buffer
881 * size: size of buffer
882 * TARGET_QUEUE_LOCK must be released
883 * ADAPTER_STATE_LOCK must be release
884 *
885 * Returns:
886 * qla2x00 local funxtion status code.
887 *
888 * Context:
889 * Kernel context.
890 */
891 #define CONFIG_XLOGINS_MEM 0x9
892 int
qla_set_exlogin_mem_cfg(scsi_qla_host_t * vha,dma_addr_t phys_addr)893 qla_set_exlogin_mem_cfg(scsi_qla_host_t *vha, dma_addr_t phys_addr)
894 {
895 int rval;
896 mbx_cmd_t mc;
897 mbx_cmd_t *mcp = &mc;
898 struct qla_hw_data *ha = vha->hw;
899
900 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x111a,
901 "Entered %s.\n", __func__);
902
903 memset(mcp->mb, 0 , sizeof(mcp->mb));
904 mcp->mb[0] = MBC_GET_MEM_OFFLOAD_CNTRL_STAT;
905 mcp->mb[1] = CONFIG_XLOGINS_MEM;
906 mcp->mb[2] = MSW(phys_addr);
907 mcp->mb[3] = LSW(phys_addr);
908 mcp->mb[6] = MSW(MSD(phys_addr));
909 mcp->mb[7] = LSW(MSD(phys_addr));
910 mcp->mb[8] = MSW(ha->exlogin_size);
911 mcp->mb[9] = LSW(ha->exlogin_size);
912 mcp->out_mb = MBX_9|MBX_8|MBX_7|MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
913 mcp->in_mb = MBX_11|MBX_0;
914 mcp->tov = MBX_TOV_SECONDS;
915 mcp->flags = 0;
916 rval = qla2x00_mailbox_command(vha, mcp);
917 if (rval != QLA_SUCCESS) {
918 ql_dbg(ql_dbg_mbx, vha, 0x111b,
919 "EXlogin Failed=%x. MB0=%x MB11=%x\n",
920 rval, mcp->mb[0], mcp->mb[11]);
921 } else {
922 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x118c,
923 "Done %s.\n", __func__);
924 }
925
926 return rval;
927 }
928
929 /*
930 * qla_get_exchoffld_status
931 * Get exchange offload status
932 * uses the memory offload control/status Mailbox
933 *
934 * Input:
935 * ha: adapter state pointer.
936 * fwopt: firmware options
937 *
938 * Returns:
939 * qla2x00 local function status
940 *
941 * Context:
942 * Kernel context.
943 */
944 #define FETCH_XCHOFFLD_STAT 0x2
945 int
qla_get_exchoffld_status(scsi_qla_host_t * vha,uint16_t * buf_sz,uint16_t * ex_logins_cnt)946 qla_get_exchoffld_status(scsi_qla_host_t *vha, uint16_t *buf_sz,
947 uint16_t *ex_logins_cnt)
948 {
949 int rval;
950 mbx_cmd_t mc;
951 mbx_cmd_t *mcp = &mc;
952
953 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1019,
954 "Entered %s\n", __func__);
955
956 memset(mcp->mb, 0 , sizeof(mcp->mb));
957 mcp->mb[0] = MBC_GET_MEM_OFFLOAD_CNTRL_STAT;
958 mcp->mb[1] = FETCH_XCHOFFLD_STAT;
959 mcp->out_mb = MBX_1|MBX_0;
960 mcp->in_mb = MBX_10|MBX_4|MBX_0;
961 mcp->tov = MBX_TOV_SECONDS;
962 mcp->flags = 0;
963
964 rval = qla2x00_mailbox_command(vha, mcp);
965 if (rval != QLA_SUCCESS) {
966 ql_dbg(ql_dbg_mbx, vha, 0x1155, "Failed=%x.\n", rval);
967 } else {
968 *buf_sz = mcp->mb[4];
969 *ex_logins_cnt = mcp->mb[10];
970
971 ql_log(ql_log_info, vha, 0x118e,
972 "buffer size 0x%x, exchange offload count=%d\n",
973 mcp->mb[4], mcp->mb[10]);
974
975 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1156,
976 "Done %s.\n", __func__);
977 }
978
979 return rval;
980 }
981
982 /*
983 * qla_set_exchoffld_mem_cfg
984 * Set exchange offload memory configuration
985 * Mbx needs to be issues before init_cb is set
986 *
987 * Input:
988 * ha: adapter state pointer.
989 * buffer: buffer pointer
990 * phys_addr: physical address of buffer
991 * size: size of buffer
992 * TARGET_QUEUE_LOCK must be released
993 * ADAPTER_STATE_LOCK must be release
994 *
995 * Returns:
996 * qla2x00 local funxtion status code.
997 *
998 * Context:
999 * Kernel context.
1000 */
1001 #define CONFIG_XCHOFFLD_MEM 0x3
1002 int
qla_set_exchoffld_mem_cfg(scsi_qla_host_t * vha)1003 qla_set_exchoffld_mem_cfg(scsi_qla_host_t *vha)
1004 {
1005 int rval;
1006 mbx_cmd_t mc;
1007 mbx_cmd_t *mcp = &mc;
1008 struct qla_hw_data *ha = vha->hw;
1009
1010 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1157,
1011 "Entered %s.\n", __func__);
1012
1013 memset(mcp->mb, 0 , sizeof(mcp->mb));
1014 mcp->mb[0] = MBC_GET_MEM_OFFLOAD_CNTRL_STAT;
1015 mcp->mb[1] = CONFIG_XCHOFFLD_MEM;
1016 mcp->mb[2] = MSW(ha->exchoffld_buf_dma);
1017 mcp->mb[3] = LSW(ha->exchoffld_buf_dma);
1018 mcp->mb[6] = MSW(MSD(ha->exchoffld_buf_dma));
1019 mcp->mb[7] = LSW(MSD(ha->exchoffld_buf_dma));
1020 mcp->mb[8] = MSW(ha->exchoffld_size);
1021 mcp->mb[9] = LSW(ha->exchoffld_size);
1022 mcp->out_mb = MBX_9|MBX_8|MBX_7|MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
1023 mcp->in_mb = MBX_11|MBX_0;
1024 mcp->tov = MBX_TOV_SECONDS;
1025 mcp->flags = 0;
1026 rval = qla2x00_mailbox_command(vha, mcp);
1027 if (rval != QLA_SUCCESS) {
1028 /*EMPTY*/
1029 ql_dbg(ql_dbg_mbx, vha, 0x1158, "Failed=%x.\n", rval);
1030 } else {
1031 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1192,
1032 "Done %s.\n", __func__);
1033 }
1034
1035 return rval;
1036 }
1037
1038 /*
1039 * qla2x00_get_fw_version
1040 * Get firmware version.
1041 *
1042 * Input:
1043 * ha: adapter state pointer.
1044 * major: pointer for major number.
1045 * minor: pointer for minor number.
1046 * subminor: pointer for subminor number.
1047 *
1048 * Returns:
1049 * qla2x00 local function return status code.
1050 *
1051 * Context:
1052 * Kernel context.
1053 */
1054 int
qla2x00_get_fw_version(scsi_qla_host_t * vha)1055 qla2x00_get_fw_version(scsi_qla_host_t *vha)
1056 {
1057 int rval;
1058 mbx_cmd_t mc;
1059 mbx_cmd_t *mcp = &mc;
1060 struct qla_hw_data *ha = vha->hw;
1061
1062 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1029,
1063 "Entered %s.\n", __func__);
1064
1065 mcp->mb[0] = MBC_GET_FIRMWARE_VERSION;
1066 mcp->out_mb = MBX_0;
1067 mcp->in_mb = MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
1068 if (IS_QLA81XX(vha->hw) || IS_QLA8031(ha) || IS_QLA8044(ha))
1069 mcp->in_mb |= MBX_13|MBX_12|MBX_11|MBX_10|MBX_9|MBX_8;
1070 if (IS_FWI2_CAPABLE(ha))
1071 mcp->in_mb |= MBX_17|MBX_16|MBX_15;
1072 if (IS_QLA27XX(ha) || IS_QLA28XX(ha))
1073 mcp->in_mb |=
1074 MBX_25|MBX_24|MBX_23|MBX_22|MBX_21|MBX_20|MBX_19|MBX_18|
1075 MBX_14|MBX_13|MBX_11|MBX_10|MBX_9|MBX_8|MBX_7;
1076
1077 mcp->flags = 0;
1078 mcp->tov = MBX_TOV_SECONDS;
1079 rval = qla2x00_mailbox_command(vha, mcp);
1080 if (rval != QLA_SUCCESS)
1081 goto failed;
1082
1083 /* Return mailbox data. */
1084 ha->fw_major_version = mcp->mb[1];
1085 ha->fw_minor_version = mcp->mb[2];
1086 ha->fw_subminor_version = mcp->mb[3];
1087 ha->fw_attributes = mcp->mb[6];
1088 if (IS_QLA2100(vha->hw) || IS_QLA2200(vha->hw))
1089 ha->fw_memory_size = 0x1FFFF; /* Defaults to 128KB. */
1090 else
1091 ha->fw_memory_size = (mcp->mb[5] << 16) | mcp->mb[4];
1092
1093 if (IS_QLA81XX(vha->hw) || IS_QLA8031(vha->hw) || IS_QLA8044(ha)) {
1094 ha->mpi_version[0] = mcp->mb[10] & 0xff;
1095 ha->mpi_version[1] = mcp->mb[11] >> 8;
1096 ha->mpi_version[2] = mcp->mb[11] & 0xff;
1097 ha->mpi_capabilities = (mcp->mb[12] << 16) | mcp->mb[13];
1098 ha->phy_version[0] = mcp->mb[8] & 0xff;
1099 ha->phy_version[1] = mcp->mb[9] >> 8;
1100 ha->phy_version[2] = mcp->mb[9] & 0xff;
1101 }
1102
1103 if (IS_FWI2_CAPABLE(ha)) {
1104 ha->fw_attributes_h = mcp->mb[15];
1105 ha->fw_attributes_ext[0] = mcp->mb[16];
1106 ha->fw_attributes_ext[1] = mcp->mb[17];
1107 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1139,
1108 "%s: FW_attributes Upper: 0x%x, Lower: 0x%x.\n",
1109 __func__, mcp->mb[15], mcp->mb[6]);
1110 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x112f,
1111 "%s: Ext_FwAttributes Upper: 0x%x, Lower: 0x%x.\n",
1112 __func__, mcp->mb[17], mcp->mb[16]);
1113
1114 if (ha->fw_attributes_h & 0x4)
1115 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x118d,
1116 "%s: Firmware supports Extended Login 0x%x\n",
1117 __func__, ha->fw_attributes_h);
1118
1119 if (ha->fw_attributes_h & 0x8)
1120 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1191,
1121 "%s: Firmware supports Exchange Offload 0x%x\n",
1122 __func__, ha->fw_attributes_h);
1123
1124 /*
1125 * FW supports nvme and driver load parameter requested nvme.
1126 * BIT 26 of fw_attributes indicates NVMe support.
1127 */
1128 if ((ha->fw_attributes_h &
1129 (FW_ATTR_H_NVME | FW_ATTR_H_NVME_UPDATED)) &&
1130 ql2xnvmeenable) {
1131 if (ha->fw_attributes_h & FW_ATTR_H_NVME_FBURST)
1132 vha->flags.nvme_first_burst = 1;
1133
1134 vha->flags.nvme_enabled = 1;
1135 ql_log(ql_log_info, vha, 0xd302,
1136 "%s: FC-NVMe is Enabled (0x%x)\n",
1137 __func__, ha->fw_attributes_h);
1138 }
1139
1140 /* BIT_13 of Extended FW Attributes informs about NVMe2 support */
1141 if (ha->fw_attributes_ext[0] & FW_ATTR_EXT0_NVME2) {
1142 ql_log(ql_log_info, vha, 0xd302,
1143 "Firmware supports NVMe2 0x%x\n",
1144 ha->fw_attributes_ext[0]);
1145 vha->flags.nvme2_enabled = 1;
1146 }
1147
1148 if (IS_QLA28XX(ha) && ha->flags.edif_hw && ql2xsecenable &&
1149 (ha->fw_attributes_ext[0] & FW_ATTR_EXT0_EDIF)) {
1150 ha->flags.edif_enabled = 1;
1151 ql_log(ql_log_info, vha, 0xffff,
1152 "%s: edif is enabled\n", __func__);
1153 }
1154 }
1155
1156 if (IS_QLA27XX(ha) || IS_QLA28XX(ha)) {
1157 ha->serdes_version[0] = mcp->mb[7] & 0xff;
1158 ha->serdes_version[1] = mcp->mb[8] >> 8;
1159 ha->serdes_version[2] = mcp->mb[8] & 0xff;
1160 ha->mpi_version[0] = mcp->mb[10] & 0xff;
1161 ha->mpi_version[1] = mcp->mb[11] >> 8;
1162 ha->mpi_version[2] = mcp->mb[11] & 0xff;
1163 ha->pep_version[0] = mcp->mb[13] & 0xff;
1164 ha->pep_version[1] = mcp->mb[14] >> 8;
1165 ha->pep_version[2] = mcp->mb[14] & 0xff;
1166 ha->fw_shared_ram_start = (mcp->mb[19] << 16) | mcp->mb[18];
1167 ha->fw_shared_ram_end = (mcp->mb[21] << 16) | mcp->mb[20];
1168 ha->fw_ddr_ram_start = (mcp->mb[23] << 16) | mcp->mb[22];
1169 ha->fw_ddr_ram_end = (mcp->mb[25] << 16) | mcp->mb[24];
1170 if (IS_QLA28XX(ha)) {
1171 if (mcp->mb[16] & BIT_10)
1172 ha->flags.secure_fw = 1;
1173
1174 ql_log(ql_log_info, vha, 0xffff,
1175 "Secure Flash Update in FW: %s\n",
1176 (ha->flags.secure_fw) ? "Supported" :
1177 "Not Supported");
1178 }
1179
1180 if (ha->flags.scm_supported_a &&
1181 (ha->fw_attributes_ext[0] & FW_ATTR_EXT0_SCM_SUPPORTED)) {
1182 ha->flags.scm_supported_f = 1;
1183 ha->sf_init_cb->flags |= cpu_to_le16(BIT_13);
1184 }
1185 ql_log(ql_log_info, vha, 0x11a3, "SCM in FW: %s\n",
1186 (ha->flags.scm_supported_f) ? "Supported" :
1187 "Not Supported");
1188
1189 if (vha->flags.nvme2_enabled) {
1190 /* set BIT_15 of special feature control block for SLER */
1191 ha->sf_init_cb->flags |= cpu_to_le16(BIT_15);
1192 /* set BIT_14 of special feature control block for PI CTRL*/
1193 ha->sf_init_cb->flags |= cpu_to_le16(BIT_14);
1194 }
1195 }
1196
1197 failed:
1198 if (rval != QLA_SUCCESS) {
1199 /*EMPTY*/
1200 ql_dbg(ql_dbg_mbx, vha, 0x102a, "Failed=%x.\n", rval);
1201 } else {
1202 /*EMPTY*/
1203 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x102b,
1204 "Done %s.\n", __func__);
1205 }
1206 return rval;
1207 }
1208
1209 /*
1210 * qla2x00_get_fw_options
1211 * Set firmware options.
1212 *
1213 * Input:
1214 * ha = adapter block pointer.
1215 * fwopt = pointer for firmware options.
1216 *
1217 * Returns:
1218 * qla2x00 local function return status code.
1219 *
1220 * Context:
1221 * Kernel context.
1222 */
1223 int
qla2x00_get_fw_options(scsi_qla_host_t * vha,uint16_t * fwopts)1224 qla2x00_get_fw_options(scsi_qla_host_t *vha, uint16_t *fwopts)
1225 {
1226 int rval;
1227 mbx_cmd_t mc;
1228 mbx_cmd_t *mcp = &mc;
1229
1230 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x102c,
1231 "Entered %s.\n", __func__);
1232
1233 mcp->mb[0] = MBC_GET_FIRMWARE_OPTION;
1234 mcp->out_mb = MBX_0;
1235 mcp->in_mb = MBX_3|MBX_2|MBX_1|MBX_0;
1236 mcp->tov = MBX_TOV_SECONDS;
1237 mcp->flags = 0;
1238 rval = qla2x00_mailbox_command(vha, mcp);
1239
1240 if (rval != QLA_SUCCESS) {
1241 /*EMPTY*/
1242 ql_dbg(ql_dbg_mbx, vha, 0x102d, "Failed=%x.\n", rval);
1243 } else {
1244 fwopts[0] = mcp->mb[0];
1245 fwopts[1] = mcp->mb[1];
1246 fwopts[2] = mcp->mb[2];
1247 fwopts[3] = mcp->mb[3];
1248
1249 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x102e,
1250 "Done %s.\n", __func__);
1251 }
1252
1253 return rval;
1254 }
1255
1256
1257 /*
1258 * qla2x00_set_fw_options
1259 * Set firmware options.
1260 *
1261 * Input:
1262 * ha = adapter block pointer.
1263 * fwopt = pointer for firmware options.
1264 *
1265 * Returns:
1266 * qla2x00 local function return status code.
1267 *
1268 * Context:
1269 * Kernel context.
1270 */
1271 int
qla2x00_set_fw_options(scsi_qla_host_t * vha,uint16_t * fwopts)1272 qla2x00_set_fw_options(scsi_qla_host_t *vha, uint16_t *fwopts)
1273 {
1274 int rval;
1275 mbx_cmd_t mc;
1276 mbx_cmd_t *mcp = &mc;
1277
1278 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x102f,
1279 "Entered %s.\n", __func__);
1280
1281 mcp->mb[0] = MBC_SET_FIRMWARE_OPTION;
1282 mcp->mb[1] = fwopts[1];
1283 mcp->mb[2] = fwopts[2];
1284 mcp->mb[3] = fwopts[3];
1285 mcp->out_mb = MBX_3|MBX_2|MBX_1|MBX_0;
1286 mcp->in_mb = MBX_0;
1287 if (IS_FWI2_CAPABLE(vha->hw)) {
1288 mcp->in_mb |= MBX_1;
1289 mcp->mb[10] = fwopts[10];
1290 mcp->out_mb |= MBX_10;
1291 } else {
1292 mcp->mb[10] = fwopts[10];
1293 mcp->mb[11] = fwopts[11];
1294 mcp->mb[12] = 0; /* Undocumented, but used */
1295 mcp->out_mb |= MBX_12|MBX_11|MBX_10;
1296 }
1297 mcp->tov = MBX_TOV_SECONDS;
1298 mcp->flags = 0;
1299 rval = qla2x00_mailbox_command(vha, mcp);
1300
1301 fwopts[0] = mcp->mb[0];
1302
1303 if (rval != QLA_SUCCESS) {
1304 /*EMPTY*/
1305 ql_dbg(ql_dbg_mbx, vha, 0x1030,
1306 "Failed=%x (%x/%x).\n", rval, mcp->mb[0], mcp->mb[1]);
1307 } else {
1308 /*EMPTY*/
1309 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1031,
1310 "Done %s.\n", __func__);
1311 }
1312
1313 return rval;
1314 }
1315
1316 /*
1317 * qla2x00_mbx_reg_test
1318 * Mailbox register wrap test.
1319 *
1320 * Input:
1321 * ha = adapter block pointer.
1322 * TARGET_QUEUE_LOCK must be released.
1323 * ADAPTER_STATE_LOCK must be released.
1324 *
1325 * Returns:
1326 * qla2x00 local function return status code.
1327 *
1328 * Context:
1329 * Kernel context.
1330 */
1331 int
qla2x00_mbx_reg_test(scsi_qla_host_t * vha)1332 qla2x00_mbx_reg_test(scsi_qla_host_t *vha)
1333 {
1334 int rval;
1335 mbx_cmd_t mc;
1336 mbx_cmd_t *mcp = &mc;
1337
1338 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1032,
1339 "Entered %s.\n", __func__);
1340
1341 mcp->mb[0] = MBC_MAILBOX_REGISTER_TEST;
1342 mcp->mb[1] = 0xAAAA;
1343 mcp->mb[2] = 0x5555;
1344 mcp->mb[3] = 0xAA55;
1345 mcp->mb[4] = 0x55AA;
1346 mcp->mb[5] = 0xA5A5;
1347 mcp->mb[6] = 0x5A5A;
1348 mcp->mb[7] = 0x2525;
1349 mcp->out_mb = MBX_7|MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
1350 mcp->in_mb = MBX_7|MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
1351 mcp->tov = MBX_TOV_SECONDS;
1352 mcp->flags = 0;
1353 rval = qla2x00_mailbox_command(vha, mcp);
1354
1355 if (rval == QLA_SUCCESS) {
1356 if (mcp->mb[1] != 0xAAAA || mcp->mb[2] != 0x5555 ||
1357 mcp->mb[3] != 0xAA55 || mcp->mb[4] != 0x55AA)
1358 rval = QLA_FUNCTION_FAILED;
1359 if (mcp->mb[5] != 0xA5A5 || mcp->mb[6] != 0x5A5A ||
1360 mcp->mb[7] != 0x2525)
1361 rval = QLA_FUNCTION_FAILED;
1362 }
1363
1364 if (rval != QLA_SUCCESS) {
1365 /*EMPTY*/
1366 ql_dbg(ql_dbg_mbx, vha, 0x1033, "Failed=%x.\n", rval);
1367 vha->hw_err_cnt++;
1368 } else {
1369 /*EMPTY*/
1370 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1034,
1371 "Done %s.\n", __func__);
1372 }
1373
1374 return rval;
1375 }
1376
1377 /*
1378 * qla2x00_verify_checksum
1379 * Verify firmware checksum.
1380 *
1381 * Input:
1382 * ha = adapter block pointer.
1383 * TARGET_QUEUE_LOCK must be released.
1384 * ADAPTER_STATE_LOCK must be released.
1385 *
1386 * Returns:
1387 * qla2x00 local function return status code.
1388 *
1389 * Context:
1390 * Kernel context.
1391 */
1392 int
qla2x00_verify_checksum(scsi_qla_host_t * vha,uint32_t risc_addr)1393 qla2x00_verify_checksum(scsi_qla_host_t *vha, uint32_t risc_addr)
1394 {
1395 int rval;
1396 mbx_cmd_t mc;
1397 mbx_cmd_t *mcp = &mc;
1398
1399 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1035,
1400 "Entered %s.\n", __func__);
1401
1402 mcp->mb[0] = MBC_VERIFY_CHECKSUM;
1403 mcp->out_mb = MBX_0;
1404 mcp->in_mb = MBX_0;
1405 if (IS_FWI2_CAPABLE(vha->hw)) {
1406 mcp->mb[1] = MSW(risc_addr);
1407 mcp->mb[2] = LSW(risc_addr);
1408 mcp->out_mb |= MBX_2|MBX_1;
1409 mcp->in_mb |= MBX_2|MBX_1;
1410 } else {
1411 mcp->mb[1] = LSW(risc_addr);
1412 mcp->out_mb |= MBX_1;
1413 mcp->in_mb |= MBX_1;
1414 }
1415
1416 mcp->tov = MBX_TOV_SECONDS;
1417 mcp->flags = 0;
1418 rval = qla2x00_mailbox_command(vha, mcp);
1419
1420 if (rval != QLA_SUCCESS) {
1421 ql_dbg(ql_dbg_mbx, vha, 0x1036,
1422 "Failed=%x chm sum=%x.\n", rval, IS_FWI2_CAPABLE(vha->hw) ?
1423 (mcp->mb[2] << 16) | mcp->mb[1] : mcp->mb[1]);
1424 } else {
1425 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1037,
1426 "Done %s.\n", __func__);
1427 }
1428
1429 return rval;
1430 }
1431
1432 /*
1433 * qla2x00_issue_iocb
1434 * Issue IOCB using mailbox command
1435 *
1436 * Input:
1437 * ha = adapter state pointer.
1438 * buffer = buffer pointer.
1439 * phys_addr = physical address of buffer.
1440 * size = size of buffer.
1441 * TARGET_QUEUE_LOCK must be released.
1442 * ADAPTER_STATE_LOCK must be released.
1443 *
1444 * Returns:
1445 * qla2x00 local function return status code.
1446 *
1447 * Context:
1448 * Kernel context.
1449 */
1450 int
qla2x00_issue_iocb_timeout(scsi_qla_host_t * vha,void * buffer,dma_addr_t phys_addr,size_t size,uint32_t tov)1451 qla2x00_issue_iocb_timeout(scsi_qla_host_t *vha, void *buffer,
1452 dma_addr_t phys_addr, size_t size, uint32_t tov)
1453 {
1454 int rval;
1455 mbx_cmd_t mc;
1456 mbx_cmd_t *mcp = &mc;
1457
1458 if (!vha->hw->flags.fw_started)
1459 return QLA_INVALID_COMMAND;
1460
1461 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1038,
1462 "Entered %s.\n", __func__);
1463
1464 mcp->mb[0] = MBC_IOCB_COMMAND_A64;
1465 mcp->mb[1] = 0;
1466 mcp->mb[2] = MSW(LSD(phys_addr));
1467 mcp->mb[3] = LSW(LSD(phys_addr));
1468 mcp->mb[6] = MSW(MSD(phys_addr));
1469 mcp->mb[7] = LSW(MSD(phys_addr));
1470 mcp->out_mb = MBX_7|MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
1471 mcp->in_mb = MBX_1|MBX_0;
1472 mcp->tov = tov;
1473 mcp->flags = 0;
1474 rval = qla2x00_mailbox_command(vha, mcp);
1475
1476 if (rval != QLA_SUCCESS) {
1477 /*EMPTY*/
1478 ql_dbg(ql_dbg_mbx, vha, 0x1039, "Failed=%x.\n", rval);
1479 } else {
1480 sts_entry_t *sts_entry = buffer;
1481
1482 /* Mask reserved bits. */
1483 sts_entry->entry_status &=
1484 IS_FWI2_CAPABLE(vha->hw) ? RF_MASK_24XX : RF_MASK;
1485 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x103a,
1486 "Done %s (status=%x).\n", __func__,
1487 sts_entry->entry_status);
1488 }
1489
1490 return rval;
1491 }
1492
1493 int
qla2x00_issue_iocb(scsi_qla_host_t * vha,void * buffer,dma_addr_t phys_addr,size_t size)1494 qla2x00_issue_iocb(scsi_qla_host_t *vha, void *buffer, dma_addr_t phys_addr,
1495 size_t size)
1496 {
1497 return qla2x00_issue_iocb_timeout(vha, buffer, phys_addr, size,
1498 MBX_TOV_SECONDS);
1499 }
1500
1501 /*
1502 * qla2x00_abort_command
1503 * Abort command aborts a specified IOCB.
1504 *
1505 * Input:
1506 * ha = adapter block pointer.
1507 * sp = SB structure pointer.
1508 *
1509 * Returns:
1510 * qla2x00 local function return status code.
1511 *
1512 * Context:
1513 * Kernel context.
1514 */
1515 int
qla2x00_abort_command(srb_t * sp)1516 qla2x00_abort_command(srb_t *sp)
1517 {
1518 unsigned long flags = 0;
1519 int rval;
1520 uint32_t handle = 0;
1521 mbx_cmd_t mc;
1522 mbx_cmd_t *mcp = &mc;
1523 fc_port_t *fcport = sp->fcport;
1524 scsi_qla_host_t *vha = fcport->vha;
1525 struct qla_hw_data *ha = vha->hw;
1526 struct req_que *req;
1527 struct scsi_cmnd *cmd = GET_CMD_SP(sp);
1528
1529 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x103b,
1530 "Entered %s.\n", __func__);
1531
1532 if (sp->qpair)
1533 req = sp->qpair->req;
1534 else
1535 req = vha->req;
1536
1537 spin_lock_irqsave(&ha->hardware_lock, flags);
1538 for (handle = 1; handle < req->num_outstanding_cmds; handle++) {
1539 if (req->outstanding_cmds[handle] == sp)
1540 break;
1541 }
1542 spin_unlock_irqrestore(&ha->hardware_lock, flags);
1543
1544 if (handle == req->num_outstanding_cmds) {
1545 /* command not found */
1546 return QLA_FUNCTION_FAILED;
1547 }
1548
1549 mcp->mb[0] = MBC_ABORT_COMMAND;
1550 if (HAS_EXTENDED_IDS(ha))
1551 mcp->mb[1] = fcport->loop_id;
1552 else
1553 mcp->mb[1] = fcport->loop_id << 8;
1554 mcp->mb[2] = (uint16_t)handle;
1555 mcp->mb[3] = (uint16_t)(handle >> 16);
1556 mcp->mb[6] = (uint16_t)cmd->device->lun;
1557 mcp->out_mb = MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
1558 mcp->in_mb = MBX_0;
1559 mcp->tov = MBX_TOV_SECONDS;
1560 mcp->flags = 0;
1561 rval = qla2x00_mailbox_command(vha, mcp);
1562
1563 if (rval != QLA_SUCCESS) {
1564 ql_dbg(ql_dbg_mbx, vha, 0x103c, "Failed=%x.\n", rval);
1565 } else {
1566 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x103d,
1567 "Done %s.\n", __func__);
1568 }
1569
1570 return rval;
1571 }
1572
1573 int
qla2x00_abort_target(struct fc_port * fcport,uint64_t l,int tag)1574 qla2x00_abort_target(struct fc_port *fcport, uint64_t l, int tag)
1575 {
1576 int rval, rval2;
1577 mbx_cmd_t mc;
1578 mbx_cmd_t *mcp = &mc;
1579 scsi_qla_host_t *vha;
1580
1581 vha = fcport->vha;
1582
1583 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x103e,
1584 "Entered %s.\n", __func__);
1585
1586 mcp->mb[0] = MBC_ABORT_TARGET;
1587 mcp->out_mb = MBX_9|MBX_2|MBX_1|MBX_0;
1588 if (HAS_EXTENDED_IDS(vha->hw)) {
1589 mcp->mb[1] = fcport->loop_id;
1590 mcp->mb[10] = 0;
1591 mcp->out_mb |= MBX_10;
1592 } else {
1593 mcp->mb[1] = fcport->loop_id << 8;
1594 }
1595 mcp->mb[2] = vha->hw->loop_reset_delay;
1596 mcp->mb[9] = vha->vp_idx;
1597
1598 mcp->in_mb = MBX_0;
1599 mcp->tov = MBX_TOV_SECONDS;
1600 mcp->flags = 0;
1601 rval = qla2x00_mailbox_command(vha, mcp);
1602 if (rval != QLA_SUCCESS) {
1603 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x103f,
1604 "Failed=%x.\n", rval);
1605 }
1606
1607 /* Issue marker IOCB. */
1608 rval2 = qla2x00_marker(vha, vha->hw->base_qpair, fcport->loop_id, 0,
1609 MK_SYNC_ID);
1610 if (rval2 != QLA_SUCCESS) {
1611 ql_dbg(ql_dbg_mbx, vha, 0x1040,
1612 "Failed to issue marker IOCB (%x).\n", rval2);
1613 } else {
1614 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1041,
1615 "Done %s.\n", __func__);
1616 }
1617
1618 return rval;
1619 }
1620
1621 int
qla2x00_lun_reset(struct fc_port * fcport,uint64_t l,int tag)1622 qla2x00_lun_reset(struct fc_port *fcport, uint64_t l, int tag)
1623 {
1624 int rval, rval2;
1625 mbx_cmd_t mc;
1626 mbx_cmd_t *mcp = &mc;
1627 scsi_qla_host_t *vha;
1628
1629 vha = fcport->vha;
1630
1631 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1042,
1632 "Entered %s.\n", __func__);
1633
1634 mcp->mb[0] = MBC_LUN_RESET;
1635 mcp->out_mb = MBX_9|MBX_3|MBX_2|MBX_1|MBX_0;
1636 if (HAS_EXTENDED_IDS(vha->hw))
1637 mcp->mb[1] = fcport->loop_id;
1638 else
1639 mcp->mb[1] = fcport->loop_id << 8;
1640 mcp->mb[2] = (u32)l;
1641 mcp->mb[3] = 0;
1642 mcp->mb[9] = vha->vp_idx;
1643
1644 mcp->in_mb = MBX_0;
1645 mcp->tov = MBX_TOV_SECONDS;
1646 mcp->flags = 0;
1647 rval = qla2x00_mailbox_command(vha, mcp);
1648 if (rval != QLA_SUCCESS) {
1649 ql_dbg(ql_dbg_mbx, vha, 0x1043, "Failed=%x.\n", rval);
1650 }
1651
1652 /* Issue marker IOCB. */
1653 rval2 = qla2x00_marker(vha, vha->hw->base_qpair, fcport->loop_id, l,
1654 MK_SYNC_ID_LUN);
1655 if (rval2 != QLA_SUCCESS) {
1656 ql_dbg(ql_dbg_mbx, vha, 0x1044,
1657 "Failed to issue marker IOCB (%x).\n", rval2);
1658 } else {
1659 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1045,
1660 "Done %s.\n", __func__);
1661 }
1662
1663 return rval;
1664 }
1665
1666 /*
1667 * qla2x00_get_adapter_id
1668 * Get adapter ID and topology.
1669 *
1670 * Input:
1671 * ha = adapter block pointer.
1672 * id = pointer for loop ID.
1673 * al_pa = pointer for AL_PA.
1674 * area = pointer for area.
1675 * domain = pointer for domain.
1676 * top = pointer for topology.
1677 * TARGET_QUEUE_LOCK must be released.
1678 * ADAPTER_STATE_LOCK must be released.
1679 *
1680 * Returns:
1681 * qla2x00 local function return status code.
1682 *
1683 * Context:
1684 * Kernel context.
1685 */
1686 int
qla2x00_get_adapter_id(scsi_qla_host_t * vha,uint16_t * id,uint8_t * al_pa,uint8_t * area,uint8_t * domain,uint16_t * top,uint16_t * sw_cap)1687 qla2x00_get_adapter_id(scsi_qla_host_t *vha, uint16_t *id, uint8_t *al_pa,
1688 uint8_t *area, uint8_t *domain, uint16_t *top, uint16_t *sw_cap)
1689 {
1690 int rval;
1691 mbx_cmd_t mc;
1692 mbx_cmd_t *mcp = &mc;
1693
1694 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1046,
1695 "Entered %s.\n", __func__);
1696
1697 mcp->mb[0] = MBC_GET_ADAPTER_LOOP_ID;
1698 mcp->mb[9] = vha->vp_idx;
1699 mcp->out_mb = MBX_9|MBX_0;
1700 mcp->in_mb = MBX_9|MBX_7|MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
1701 if (IS_CNA_CAPABLE(vha->hw))
1702 mcp->in_mb |= MBX_13|MBX_12|MBX_11|MBX_10;
1703 if (IS_FWI2_CAPABLE(vha->hw))
1704 mcp->in_mb |= MBX_19|MBX_18|MBX_17|MBX_16;
1705 if (IS_QLA27XX(vha->hw) || IS_QLA28XX(vha->hw))
1706 mcp->in_mb |= MBX_15|MBX_21|MBX_22|MBX_23;
1707
1708 mcp->tov = MBX_TOV_SECONDS;
1709 mcp->flags = 0;
1710 rval = qla2x00_mailbox_command(vha, mcp);
1711 if (mcp->mb[0] == MBS_COMMAND_ERROR)
1712 rval = QLA_COMMAND_ERROR;
1713 else if (mcp->mb[0] == MBS_INVALID_COMMAND)
1714 rval = QLA_INVALID_COMMAND;
1715
1716 /* Return data. */
1717 *id = mcp->mb[1];
1718 *al_pa = LSB(mcp->mb[2]);
1719 *area = MSB(mcp->mb[2]);
1720 *domain = LSB(mcp->mb[3]);
1721 *top = mcp->mb[6];
1722 *sw_cap = mcp->mb[7];
1723
1724 if (rval != QLA_SUCCESS) {
1725 /*EMPTY*/
1726 ql_dbg(ql_dbg_mbx, vha, 0x1047, "Failed=%x.\n", rval);
1727 } else {
1728 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1048,
1729 "Done %s.\n", __func__);
1730
1731 if (IS_CNA_CAPABLE(vha->hw)) {
1732 vha->fcoe_vlan_id = mcp->mb[9] & 0xfff;
1733 vha->fcoe_fcf_idx = mcp->mb[10];
1734 vha->fcoe_vn_port_mac[5] = mcp->mb[11] >> 8;
1735 vha->fcoe_vn_port_mac[4] = mcp->mb[11] & 0xff;
1736 vha->fcoe_vn_port_mac[3] = mcp->mb[12] >> 8;
1737 vha->fcoe_vn_port_mac[2] = mcp->mb[12] & 0xff;
1738 vha->fcoe_vn_port_mac[1] = mcp->mb[13] >> 8;
1739 vha->fcoe_vn_port_mac[0] = mcp->mb[13] & 0xff;
1740 }
1741 /* If FA-WWN supported */
1742 if (IS_FAWWN_CAPABLE(vha->hw)) {
1743 if (mcp->mb[7] & BIT_14) {
1744 vha->port_name[0] = MSB(mcp->mb[16]);
1745 vha->port_name[1] = LSB(mcp->mb[16]);
1746 vha->port_name[2] = MSB(mcp->mb[17]);
1747 vha->port_name[3] = LSB(mcp->mb[17]);
1748 vha->port_name[4] = MSB(mcp->mb[18]);
1749 vha->port_name[5] = LSB(mcp->mb[18]);
1750 vha->port_name[6] = MSB(mcp->mb[19]);
1751 vha->port_name[7] = LSB(mcp->mb[19]);
1752 fc_host_port_name(vha->host) =
1753 wwn_to_u64(vha->port_name);
1754 ql_dbg(ql_dbg_mbx, vha, 0x10ca,
1755 "FA-WWN acquired %016llx\n",
1756 wwn_to_u64(vha->port_name));
1757 }
1758 }
1759
1760 if (IS_QLA27XX(vha->hw) || IS_QLA28XX(vha->hw)) {
1761 vha->bbcr = mcp->mb[15];
1762 if (mcp->mb[7] & SCM_EDC_ACC_RECEIVED) {
1763 ql_log(ql_log_info, vha, 0x11a4,
1764 "SCM: EDC ELS completed, flags 0x%x\n",
1765 mcp->mb[21]);
1766 }
1767 if (mcp->mb[7] & SCM_RDF_ACC_RECEIVED) {
1768 vha->hw->flags.scm_enabled = 1;
1769 vha->scm_fabric_connection_flags |=
1770 SCM_FLAG_RDF_COMPLETED;
1771 ql_log(ql_log_info, vha, 0x11a5,
1772 "SCM: RDF ELS completed, flags 0x%x\n",
1773 mcp->mb[23]);
1774 }
1775 }
1776 }
1777
1778 return rval;
1779 }
1780
1781 /*
1782 * qla2x00_get_retry_cnt
1783 * Get current firmware login retry count and delay.
1784 *
1785 * Input:
1786 * ha = adapter block pointer.
1787 * retry_cnt = pointer to login retry count.
1788 * tov = pointer to login timeout value.
1789 *
1790 * Returns:
1791 * qla2x00 local function return status code.
1792 *
1793 * Context:
1794 * Kernel context.
1795 */
1796 int
qla2x00_get_retry_cnt(scsi_qla_host_t * vha,uint8_t * retry_cnt,uint8_t * tov,uint16_t * r_a_tov)1797 qla2x00_get_retry_cnt(scsi_qla_host_t *vha, uint8_t *retry_cnt, uint8_t *tov,
1798 uint16_t *r_a_tov)
1799 {
1800 int rval;
1801 uint16_t ratov;
1802 mbx_cmd_t mc;
1803 mbx_cmd_t *mcp = &mc;
1804
1805 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1049,
1806 "Entered %s.\n", __func__);
1807
1808 mcp->mb[0] = MBC_GET_RETRY_COUNT;
1809 mcp->out_mb = MBX_0;
1810 mcp->in_mb = MBX_3|MBX_2|MBX_1|MBX_0;
1811 mcp->tov = MBX_TOV_SECONDS;
1812 mcp->flags = 0;
1813 rval = qla2x00_mailbox_command(vha, mcp);
1814
1815 if (rval != QLA_SUCCESS) {
1816 /*EMPTY*/
1817 ql_dbg(ql_dbg_mbx, vha, 0x104a,
1818 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
1819 } else {
1820 /* Convert returned data and check our values. */
1821 *r_a_tov = mcp->mb[3] / 2;
1822 ratov = (mcp->mb[3]/2) / 10; /* mb[3] value is in 100ms */
1823 if (mcp->mb[1] * ratov > (*retry_cnt) * (*tov)) {
1824 /* Update to the larger values */
1825 *retry_cnt = (uint8_t)mcp->mb[1];
1826 *tov = ratov;
1827 }
1828
1829 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x104b,
1830 "Done %s mb3=%d ratov=%d.\n", __func__, mcp->mb[3], ratov);
1831 }
1832
1833 return rval;
1834 }
1835
1836 /*
1837 * qla2x00_init_firmware
1838 * Initialize adapter firmware.
1839 *
1840 * Input:
1841 * ha = adapter block pointer.
1842 * dptr = Initialization control block pointer.
1843 * size = size of initialization control block.
1844 * TARGET_QUEUE_LOCK must be released.
1845 * ADAPTER_STATE_LOCK must be released.
1846 *
1847 * Returns:
1848 * qla2x00 local function return status code.
1849 *
1850 * Context:
1851 * Kernel context.
1852 */
1853 int
qla2x00_init_firmware(scsi_qla_host_t * vha,uint16_t size)1854 qla2x00_init_firmware(scsi_qla_host_t *vha, uint16_t size)
1855 {
1856 int rval;
1857 mbx_cmd_t mc;
1858 mbx_cmd_t *mcp = &mc;
1859 struct qla_hw_data *ha = vha->hw;
1860
1861 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x104c,
1862 "Entered %s.\n", __func__);
1863
1864 if (IS_P3P_TYPE(ha) && ql2xdbwr)
1865 qla82xx_wr_32(ha, (uintptr_t __force)ha->nxdb_wr_ptr,
1866 (0x04 | (ha->portnum << 5) | (0 << 8) | (0 << 16)));
1867
1868 if (ha->flags.npiv_supported)
1869 mcp->mb[0] = MBC_MID_INITIALIZE_FIRMWARE;
1870 else
1871 mcp->mb[0] = MBC_INITIALIZE_FIRMWARE;
1872
1873 mcp->mb[1] = 0;
1874 mcp->mb[2] = MSW(ha->init_cb_dma);
1875 mcp->mb[3] = LSW(ha->init_cb_dma);
1876 mcp->mb[6] = MSW(MSD(ha->init_cb_dma));
1877 mcp->mb[7] = LSW(MSD(ha->init_cb_dma));
1878 mcp->out_mb = MBX_7|MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
1879 if (ha->ex_init_cb && ha->ex_init_cb->ex_version) {
1880 mcp->mb[1] = BIT_0;
1881 mcp->mb[10] = MSW(ha->ex_init_cb_dma);
1882 mcp->mb[11] = LSW(ha->ex_init_cb_dma);
1883 mcp->mb[12] = MSW(MSD(ha->ex_init_cb_dma));
1884 mcp->mb[13] = LSW(MSD(ha->ex_init_cb_dma));
1885 mcp->mb[14] = sizeof(*ha->ex_init_cb);
1886 mcp->out_mb |= MBX_14|MBX_13|MBX_12|MBX_11|MBX_10;
1887 }
1888
1889 if (ha->flags.scm_supported_f || vha->flags.nvme2_enabled) {
1890 mcp->mb[1] |= BIT_1;
1891 mcp->mb[16] = MSW(ha->sf_init_cb_dma);
1892 mcp->mb[17] = LSW(ha->sf_init_cb_dma);
1893 mcp->mb[18] = MSW(MSD(ha->sf_init_cb_dma));
1894 mcp->mb[19] = LSW(MSD(ha->sf_init_cb_dma));
1895 mcp->mb[15] = sizeof(*ha->sf_init_cb);
1896 mcp->out_mb |= MBX_19|MBX_18|MBX_17|MBX_16|MBX_15;
1897 }
1898
1899 /* 1 and 2 should normally be captured. */
1900 mcp->in_mb = MBX_2|MBX_1|MBX_0;
1901 if (IS_QLA83XX(ha) || IS_QLA27XX(ha) || IS_QLA28XX(ha))
1902 /* mb3 is additional info about the installed SFP. */
1903 mcp->in_mb |= MBX_3;
1904 mcp->buf_size = size;
1905 mcp->flags = MBX_DMA_OUT;
1906 mcp->tov = MBX_TOV_SECONDS;
1907 rval = qla2x00_mailbox_command(vha, mcp);
1908
1909 if (rval != QLA_SUCCESS) {
1910 /*EMPTY*/
1911 ql_dbg(ql_dbg_mbx, vha, 0x104d,
1912 "Failed=%x mb[0]=%x, mb[1]=%x, mb[2]=%x, mb[3]=%x.\n",
1913 rval, mcp->mb[0], mcp->mb[1], mcp->mb[2], mcp->mb[3]);
1914 if (ha->init_cb) {
1915 ql_dbg(ql_dbg_mbx, vha, 0x104d, "init_cb:\n");
1916 ql_dump_buffer(ql_dbg_init + ql_dbg_verbose, vha,
1917 0x0104d, ha->init_cb, sizeof(*ha->init_cb));
1918 }
1919 if (ha->ex_init_cb && ha->ex_init_cb->ex_version) {
1920 ql_dbg(ql_dbg_mbx, vha, 0x104d, "ex_init_cb:\n");
1921 ql_dump_buffer(ql_dbg_init + ql_dbg_verbose, vha,
1922 0x0104d, ha->ex_init_cb, sizeof(*ha->ex_init_cb));
1923 }
1924 } else {
1925 if (IS_QLA27XX(ha) || IS_QLA28XX(ha)) {
1926 if (mcp->mb[2] == 6 || mcp->mb[3] == 2)
1927 ql_dbg(ql_dbg_mbx, vha, 0x119d,
1928 "Invalid SFP/Validation Failed\n");
1929 }
1930 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x104e,
1931 "Done %s.\n", __func__);
1932 }
1933
1934 return rval;
1935 }
1936
1937
1938 /*
1939 * qla2x00_get_port_database
1940 * Issue normal/enhanced get port database mailbox command
1941 * and copy device name as necessary.
1942 *
1943 * Input:
1944 * ha = adapter state pointer.
1945 * dev = structure pointer.
1946 * opt = enhanced cmd option byte.
1947 *
1948 * Returns:
1949 * qla2x00 local function return status code.
1950 *
1951 * Context:
1952 * Kernel context.
1953 */
1954 int
qla2x00_get_port_database(scsi_qla_host_t * vha,fc_port_t * fcport,uint8_t opt)1955 qla2x00_get_port_database(scsi_qla_host_t *vha, fc_port_t *fcport, uint8_t opt)
1956 {
1957 int rval;
1958 mbx_cmd_t mc;
1959 mbx_cmd_t *mcp = &mc;
1960 port_database_t *pd;
1961 struct port_database_24xx *pd24;
1962 dma_addr_t pd_dma;
1963 struct qla_hw_data *ha = vha->hw;
1964
1965 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x104f,
1966 "Entered %s.\n", __func__);
1967
1968 pd24 = NULL;
1969 pd = dma_pool_zalloc(ha->s_dma_pool, GFP_KERNEL, &pd_dma);
1970 if (pd == NULL) {
1971 ql_log(ql_log_warn, vha, 0x1050,
1972 "Failed to allocate port database structure.\n");
1973 fcport->query = 0;
1974 return QLA_MEMORY_ALLOC_FAILED;
1975 }
1976
1977 mcp->mb[0] = MBC_GET_PORT_DATABASE;
1978 if (opt != 0 && !IS_FWI2_CAPABLE(ha))
1979 mcp->mb[0] = MBC_ENHANCED_GET_PORT_DATABASE;
1980 mcp->mb[2] = MSW(pd_dma);
1981 mcp->mb[3] = LSW(pd_dma);
1982 mcp->mb[6] = MSW(MSD(pd_dma));
1983 mcp->mb[7] = LSW(MSD(pd_dma));
1984 mcp->mb[9] = vha->vp_idx;
1985 mcp->out_mb = MBX_9|MBX_7|MBX_6|MBX_3|MBX_2|MBX_0;
1986 mcp->in_mb = MBX_0;
1987 if (IS_FWI2_CAPABLE(ha)) {
1988 mcp->mb[1] = fcport->loop_id;
1989 mcp->mb[10] = opt;
1990 mcp->out_mb |= MBX_10|MBX_1;
1991 mcp->in_mb |= MBX_1;
1992 } else if (HAS_EXTENDED_IDS(ha)) {
1993 mcp->mb[1] = fcport->loop_id;
1994 mcp->mb[10] = opt;
1995 mcp->out_mb |= MBX_10|MBX_1;
1996 } else {
1997 mcp->mb[1] = fcport->loop_id << 8 | opt;
1998 mcp->out_mb |= MBX_1;
1999 }
2000 mcp->buf_size = IS_FWI2_CAPABLE(ha) ?
2001 PORT_DATABASE_24XX_SIZE : PORT_DATABASE_SIZE;
2002 mcp->flags = MBX_DMA_IN;
2003 mcp->tov = (ha->login_timeout * 2) + (ha->login_timeout / 2);
2004 rval = qla2x00_mailbox_command(vha, mcp);
2005 if (rval != QLA_SUCCESS)
2006 goto gpd_error_out;
2007
2008 if (IS_FWI2_CAPABLE(ha)) {
2009 uint64_t zero = 0;
2010 u8 current_login_state, last_login_state;
2011
2012 pd24 = (struct port_database_24xx *) pd;
2013
2014 /* Check for logged in state. */
2015 if (NVME_TARGET(ha, fcport)) {
2016 current_login_state = pd24->current_login_state >> 4;
2017 last_login_state = pd24->last_login_state >> 4;
2018 } else {
2019 current_login_state = pd24->current_login_state & 0xf;
2020 last_login_state = pd24->last_login_state & 0xf;
2021 }
2022 fcport->current_login_state = pd24->current_login_state;
2023 fcport->last_login_state = pd24->last_login_state;
2024
2025 /* Check for logged in state. */
2026 if (current_login_state != PDS_PRLI_COMPLETE &&
2027 last_login_state != PDS_PRLI_COMPLETE) {
2028 ql_dbg(ql_dbg_mbx, vha, 0x119a,
2029 "Unable to verify login-state (%x/%x) for loop_id %x.\n",
2030 current_login_state, last_login_state,
2031 fcport->loop_id);
2032 rval = QLA_FUNCTION_FAILED;
2033
2034 if (!fcport->query)
2035 goto gpd_error_out;
2036 }
2037
2038 if (fcport->loop_id == FC_NO_LOOP_ID ||
2039 (memcmp(fcport->port_name, (uint8_t *)&zero, 8) &&
2040 memcmp(fcport->port_name, pd24->port_name, 8))) {
2041 /* We lost the device mid way. */
2042 rval = QLA_NOT_LOGGED_IN;
2043 goto gpd_error_out;
2044 }
2045
2046 /* Names are little-endian. */
2047 memcpy(fcport->node_name, pd24->node_name, WWN_SIZE);
2048 memcpy(fcport->port_name, pd24->port_name, WWN_SIZE);
2049
2050 /* Get port_id of device. */
2051 fcport->d_id.b.domain = pd24->port_id[0];
2052 fcport->d_id.b.area = pd24->port_id[1];
2053 fcport->d_id.b.al_pa = pd24->port_id[2];
2054 fcport->d_id.b.rsvd_1 = 0;
2055
2056 /* If not target must be initiator or unknown type. */
2057 if ((pd24->prli_svc_param_word_3[0] & BIT_4) == 0)
2058 fcport->port_type = FCT_INITIATOR;
2059 else
2060 fcport->port_type = FCT_TARGET;
2061
2062 /* Passback COS information. */
2063 fcport->supported_classes = (pd24->flags & PDF_CLASS_2) ?
2064 FC_COS_CLASS2 : FC_COS_CLASS3;
2065
2066 if (pd24->prli_svc_param_word_3[0] & BIT_7)
2067 fcport->flags |= FCF_CONF_COMP_SUPPORTED;
2068 } else {
2069 uint64_t zero = 0;
2070
2071 /* Check for logged in state. */
2072 if (pd->master_state != PD_STATE_PORT_LOGGED_IN &&
2073 pd->slave_state != PD_STATE_PORT_LOGGED_IN) {
2074 ql_dbg(ql_dbg_mbx, vha, 0x100a,
2075 "Unable to verify login-state (%x/%x) - "
2076 "portid=%02x%02x%02x.\n", pd->master_state,
2077 pd->slave_state, fcport->d_id.b.domain,
2078 fcport->d_id.b.area, fcport->d_id.b.al_pa);
2079 rval = QLA_FUNCTION_FAILED;
2080 goto gpd_error_out;
2081 }
2082
2083 if (fcport->loop_id == FC_NO_LOOP_ID ||
2084 (memcmp(fcport->port_name, (uint8_t *)&zero, 8) &&
2085 memcmp(fcport->port_name, pd->port_name, 8))) {
2086 /* We lost the device mid way. */
2087 rval = QLA_NOT_LOGGED_IN;
2088 goto gpd_error_out;
2089 }
2090
2091 /* Names are little-endian. */
2092 memcpy(fcport->node_name, pd->node_name, WWN_SIZE);
2093 memcpy(fcport->port_name, pd->port_name, WWN_SIZE);
2094
2095 /* Get port_id of device. */
2096 fcport->d_id.b.domain = pd->port_id[0];
2097 fcport->d_id.b.area = pd->port_id[3];
2098 fcport->d_id.b.al_pa = pd->port_id[2];
2099 fcport->d_id.b.rsvd_1 = 0;
2100
2101 /* If not target must be initiator or unknown type. */
2102 if ((pd->prli_svc_param_word_3[0] & BIT_4) == 0)
2103 fcport->port_type = FCT_INITIATOR;
2104 else
2105 fcport->port_type = FCT_TARGET;
2106
2107 /* Passback COS information. */
2108 fcport->supported_classes = (pd->options & BIT_4) ?
2109 FC_COS_CLASS2 : FC_COS_CLASS3;
2110 }
2111
2112 gpd_error_out:
2113 dma_pool_free(ha->s_dma_pool, pd, pd_dma);
2114 fcport->query = 0;
2115
2116 if (rval != QLA_SUCCESS) {
2117 ql_dbg(ql_dbg_mbx, vha, 0x1052,
2118 "Failed=%x mb[0]=%x mb[1]=%x.\n", rval,
2119 mcp->mb[0], mcp->mb[1]);
2120 } else {
2121 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1053,
2122 "Done %s.\n", __func__);
2123 }
2124
2125 return rval;
2126 }
2127
2128 int
qla24xx_get_port_database(scsi_qla_host_t * vha,u16 nport_handle,struct port_database_24xx * pdb)2129 qla24xx_get_port_database(scsi_qla_host_t *vha, u16 nport_handle,
2130 struct port_database_24xx *pdb)
2131 {
2132 mbx_cmd_t mc;
2133 mbx_cmd_t *mcp = &mc;
2134 dma_addr_t pdb_dma;
2135 int rval;
2136
2137 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1115,
2138 "Entered %s.\n", __func__);
2139
2140 memset(pdb, 0, sizeof(*pdb));
2141
2142 pdb_dma = dma_map_single(&vha->hw->pdev->dev, pdb,
2143 sizeof(*pdb), DMA_FROM_DEVICE);
2144 if (!pdb_dma) {
2145 ql_log(ql_log_warn, vha, 0x1116, "Failed to map dma buffer.\n");
2146 return QLA_MEMORY_ALLOC_FAILED;
2147 }
2148
2149 mcp->mb[0] = MBC_GET_PORT_DATABASE;
2150 mcp->mb[1] = nport_handle;
2151 mcp->mb[2] = MSW(LSD(pdb_dma));
2152 mcp->mb[3] = LSW(LSD(pdb_dma));
2153 mcp->mb[6] = MSW(MSD(pdb_dma));
2154 mcp->mb[7] = LSW(MSD(pdb_dma));
2155 mcp->mb[9] = 0;
2156 mcp->mb[10] = 0;
2157 mcp->out_mb = MBX_10|MBX_9|MBX_7|MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
2158 mcp->in_mb = MBX_1|MBX_0;
2159 mcp->buf_size = sizeof(*pdb);
2160 mcp->flags = MBX_DMA_IN;
2161 mcp->tov = vha->hw->login_timeout * 2;
2162 rval = qla2x00_mailbox_command(vha, mcp);
2163
2164 if (rval != QLA_SUCCESS) {
2165 ql_dbg(ql_dbg_mbx, vha, 0x111a,
2166 "Failed=%x mb[0]=%x mb[1]=%x.\n",
2167 rval, mcp->mb[0], mcp->mb[1]);
2168 } else {
2169 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x111b,
2170 "Done %s.\n", __func__);
2171 }
2172
2173 dma_unmap_single(&vha->hw->pdev->dev, pdb_dma,
2174 sizeof(*pdb), DMA_FROM_DEVICE);
2175
2176 return rval;
2177 }
2178
2179 /*
2180 * qla2x00_get_firmware_state
2181 * Get adapter firmware state.
2182 *
2183 * Input:
2184 * ha = adapter block pointer.
2185 * dptr = pointer for firmware state.
2186 * TARGET_QUEUE_LOCK must be released.
2187 * ADAPTER_STATE_LOCK must be released.
2188 *
2189 * Returns:
2190 * qla2x00 local function return status code.
2191 *
2192 * Context:
2193 * Kernel context.
2194 */
2195 int
qla2x00_get_firmware_state(scsi_qla_host_t * vha,uint16_t * states)2196 qla2x00_get_firmware_state(scsi_qla_host_t *vha, uint16_t *states)
2197 {
2198 int rval;
2199 mbx_cmd_t mc;
2200 mbx_cmd_t *mcp = &mc;
2201 struct qla_hw_data *ha = vha->hw;
2202
2203 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1054,
2204 "Entered %s.\n", __func__);
2205
2206 if (!ha->flags.fw_started)
2207 return QLA_FUNCTION_FAILED;
2208
2209 mcp->mb[0] = MBC_GET_FIRMWARE_STATE;
2210 mcp->out_mb = MBX_0;
2211 if (IS_FWI2_CAPABLE(vha->hw))
2212 mcp->in_mb = MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
2213 else
2214 mcp->in_mb = MBX_1|MBX_0;
2215 mcp->tov = MBX_TOV_SECONDS;
2216 mcp->flags = 0;
2217 rval = qla2x00_mailbox_command(vha, mcp);
2218
2219 /* Return firmware states. */
2220 states[0] = mcp->mb[1];
2221 if (IS_FWI2_CAPABLE(vha->hw)) {
2222 states[1] = mcp->mb[2];
2223 states[2] = mcp->mb[3]; /* SFP info */
2224 states[3] = mcp->mb[4];
2225 states[4] = mcp->mb[5];
2226 states[5] = mcp->mb[6]; /* DPORT status */
2227 }
2228
2229 if (rval != QLA_SUCCESS) {
2230 /*EMPTY*/
2231 ql_dbg(ql_dbg_mbx, vha, 0x1055, "Failed=%x.\n", rval);
2232 } else {
2233 if (IS_QLA27XX(ha) || IS_QLA28XX(ha)) {
2234 if (mcp->mb[2] == 6 || mcp->mb[3] == 2)
2235 ql_dbg(ql_dbg_mbx, vha, 0x119e,
2236 "Invalid SFP/Validation Failed\n");
2237 }
2238 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1056,
2239 "Done %s.\n", __func__);
2240 }
2241
2242 return rval;
2243 }
2244
2245 /*
2246 * qla2x00_get_port_name
2247 * Issue get port name mailbox command.
2248 * Returned name is in big endian format.
2249 *
2250 * Input:
2251 * ha = adapter block pointer.
2252 * loop_id = loop ID of device.
2253 * name = pointer for name.
2254 * TARGET_QUEUE_LOCK must be released.
2255 * ADAPTER_STATE_LOCK must be released.
2256 *
2257 * Returns:
2258 * qla2x00 local function return status code.
2259 *
2260 * Context:
2261 * Kernel context.
2262 */
2263 int
qla2x00_get_port_name(scsi_qla_host_t * vha,uint16_t loop_id,uint8_t * name,uint8_t opt)2264 qla2x00_get_port_name(scsi_qla_host_t *vha, uint16_t loop_id, uint8_t *name,
2265 uint8_t opt)
2266 {
2267 int rval;
2268 mbx_cmd_t mc;
2269 mbx_cmd_t *mcp = &mc;
2270
2271 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1057,
2272 "Entered %s.\n", __func__);
2273
2274 mcp->mb[0] = MBC_GET_PORT_NAME;
2275 mcp->mb[9] = vha->vp_idx;
2276 mcp->out_mb = MBX_9|MBX_1|MBX_0;
2277 if (HAS_EXTENDED_IDS(vha->hw)) {
2278 mcp->mb[1] = loop_id;
2279 mcp->mb[10] = opt;
2280 mcp->out_mb |= MBX_10;
2281 } else {
2282 mcp->mb[1] = loop_id << 8 | opt;
2283 }
2284
2285 mcp->in_mb = MBX_7|MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
2286 mcp->tov = MBX_TOV_SECONDS;
2287 mcp->flags = 0;
2288 rval = qla2x00_mailbox_command(vha, mcp);
2289
2290 if (rval != QLA_SUCCESS) {
2291 /*EMPTY*/
2292 ql_dbg(ql_dbg_mbx, vha, 0x1058, "Failed=%x.\n", rval);
2293 } else {
2294 if (name != NULL) {
2295 /* This function returns name in big endian. */
2296 name[0] = MSB(mcp->mb[2]);
2297 name[1] = LSB(mcp->mb[2]);
2298 name[2] = MSB(mcp->mb[3]);
2299 name[3] = LSB(mcp->mb[3]);
2300 name[4] = MSB(mcp->mb[6]);
2301 name[5] = LSB(mcp->mb[6]);
2302 name[6] = MSB(mcp->mb[7]);
2303 name[7] = LSB(mcp->mb[7]);
2304 }
2305
2306 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1059,
2307 "Done %s.\n", __func__);
2308 }
2309
2310 return rval;
2311 }
2312
2313 /*
2314 * qla24xx_link_initialization
2315 * Issue link initialization mailbox command.
2316 *
2317 * Input:
2318 * ha = adapter block pointer.
2319 * TARGET_QUEUE_LOCK must be released.
2320 * ADAPTER_STATE_LOCK must be released.
2321 *
2322 * Returns:
2323 * qla2x00 local function return status code.
2324 *
2325 * Context:
2326 * Kernel context.
2327 */
2328 int
qla24xx_link_initialize(scsi_qla_host_t * vha)2329 qla24xx_link_initialize(scsi_qla_host_t *vha)
2330 {
2331 int rval;
2332 mbx_cmd_t mc;
2333 mbx_cmd_t *mcp = &mc;
2334
2335 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1152,
2336 "Entered %s.\n", __func__);
2337
2338 if (!IS_FWI2_CAPABLE(vha->hw) || IS_CNA_CAPABLE(vha->hw))
2339 return QLA_FUNCTION_FAILED;
2340
2341 mcp->mb[0] = MBC_LINK_INITIALIZATION;
2342 mcp->mb[1] = BIT_4;
2343 if (vha->hw->operating_mode == LOOP)
2344 mcp->mb[1] |= BIT_6;
2345 else
2346 mcp->mb[1] |= BIT_5;
2347 mcp->mb[2] = 0;
2348 mcp->mb[3] = 0;
2349 mcp->out_mb = MBX_3|MBX_2|MBX_1|MBX_0;
2350 mcp->in_mb = MBX_0;
2351 mcp->tov = MBX_TOV_SECONDS;
2352 mcp->flags = 0;
2353 rval = qla2x00_mailbox_command(vha, mcp);
2354
2355 if (rval != QLA_SUCCESS) {
2356 ql_dbg(ql_dbg_mbx, vha, 0x1153, "Failed=%x.\n", rval);
2357 } else {
2358 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1154,
2359 "Done %s.\n", __func__);
2360 }
2361
2362 return rval;
2363 }
2364
2365 /*
2366 * qla2x00_lip_reset
2367 * Issue LIP reset mailbox command.
2368 *
2369 * Input:
2370 * ha = adapter block pointer.
2371 * TARGET_QUEUE_LOCK must be released.
2372 * ADAPTER_STATE_LOCK must be released.
2373 *
2374 * Returns:
2375 * qla2x00 local function return status code.
2376 *
2377 * Context:
2378 * Kernel context.
2379 */
2380 int
qla2x00_lip_reset(scsi_qla_host_t * vha)2381 qla2x00_lip_reset(scsi_qla_host_t *vha)
2382 {
2383 int rval;
2384 mbx_cmd_t mc;
2385 mbx_cmd_t *mcp = &mc;
2386
2387 ql_dbg(ql_dbg_disc, vha, 0x105a,
2388 "Entered %s.\n", __func__);
2389
2390 if (IS_CNA_CAPABLE(vha->hw)) {
2391 /* Logout across all FCFs. */
2392 mcp->mb[0] = MBC_LIP_FULL_LOGIN;
2393 mcp->mb[1] = BIT_1;
2394 mcp->mb[2] = 0;
2395 mcp->out_mb = MBX_2|MBX_1|MBX_0;
2396 } else if (IS_FWI2_CAPABLE(vha->hw)) {
2397 mcp->mb[0] = MBC_LIP_FULL_LOGIN;
2398 mcp->mb[1] = BIT_4;
2399 mcp->mb[2] = 0;
2400 mcp->mb[3] = vha->hw->loop_reset_delay;
2401 mcp->out_mb = MBX_3|MBX_2|MBX_1|MBX_0;
2402 } else {
2403 mcp->mb[0] = MBC_LIP_RESET;
2404 mcp->out_mb = MBX_3|MBX_2|MBX_1|MBX_0;
2405 if (HAS_EXTENDED_IDS(vha->hw)) {
2406 mcp->mb[1] = 0x00ff;
2407 mcp->mb[10] = 0;
2408 mcp->out_mb |= MBX_10;
2409 } else {
2410 mcp->mb[1] = 0xff00;
2411 }
2412 mcp->mb[2] = vha->hw->loop_reset_delay;
2413 mcp->mb[3] = 0;
2414 }
2415 mcp->in_mb = MBX_0;
2416 mcp->tov = MBX_TOV_SECONDS;
2417 mcp->flags = 0;
2418 rval = qla2x00_mailbox_command(vha, mcp);
2419
2420 if (rval != QLA_SUCCESS) {
2421 /*EMPTY*/
2422 ql_dbg(ql_dbg_mbx, vha, 0x105b, "Failed=%x.\n", rval);
2423 } else {
2424 /*EMPTY*/
2425 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x105c,
2426 "Done %s.\n", __func__);
2427 }
2428
2429 return rval;
2430 }
2431
2432 /*
2433 * qla2x00_send_sns
2434 * Send SNS command.
2435 *
2436 * Input:
2437 * ha = adapter block pointer.
2438 * sns = pointer for command.
2439 * cmd_size = command size.
2440 * buf_size = response/command size.
2441 * TARGET_QUEUE_LOCK must be released.
2442 * ADAPTER_STATE_LOCK must be released.
2443 *
2444 * Returns:
2445 * qla2x00 local function return status code.
2446 *
2447 * Context:
2448 * Kernel context.
2449 */
2450 int
qla2x00_send_sns(scsi_qla_host_t * vha,dma_addr_t sns_phys_address,uint16_t cmd_size,size_t buf_size)2451 qla2x00_send_sns(scsi_qla_host_t *vha, dma_addr_t sns_phys_address,
2452 uint16_t cmd_size, size_t buf_size)
2453 {
2454 int rval;
2455 mbx_cmd_t mc;
2456 mbx_cmd_t *mcp = &mc;
2457
2458 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x105d,
2459 "Entered %s.\n", __func__);
2460
2461 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x105e,
2462 "Retry cnt=%d ratov=%d total tov=%d.\n",
2463 vha->hw->retry_count, vha->hw->login_timeout, mcp->tov);
2464
2465 mcp->mb[0] = MBC_SEND_SNS_COMMAND;
2466 mcp->mb[1] = cmd_size;
2467 mcp->mb[2] = MSW(sns_phys_address);
2468 mcp->mb[3] = LSW(sns_phys_address);
2469 mcp->mb[6] = MSW(MSD(sns_phys_address));
2470 mcp->mb[7] = LSW(MSD(sns_phys_address));
2471 mcp->out_mb = MBX_7|MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
2472 mcp->in_mb = MBX_0|MBX_1;
2473 mcp->buf_size = buf_size;
2474 mcp->flags = MBX_DMA_OUT|MBX_DMA_IN;
2475 mcp->tov = (vha->hw->login_timeout * 2) + (vha->hw->login_timeout / 2);
2476 rval = qla2x00_mailbox_command(vha, mcp);
2477
2478 if (rval != QLA_SUCCESS) {
2479 /*EMPTY*/
2480 ql_dbg(ql_dbg_mbx, vha, 0x105f,
2481 "Failed=%x mb[0]=%x mb[1]=%x.\n",
2482 rval, mcp->mb[0], mcp->mb[1]);
2483 } else {
2484 /*EMPTY*/
2485 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1060,
2486 "Done %s.\n", __func__);
2487 }
2488
2489 return rval;
2490 }
2491
2492 int
qla24xx_login_fabric(scsi_qla_host_t * vha,uint16_t loop_id,uint8_t domain,uint8_t area,uint8_t al_pa,uint16_t * mb,uint8_t opt)2493 qla24xx_login_fabric(scsi_qla_host_t *vha, uint16_t loop_id, uint8_t domain,
2494 uint8_t area, uint8_t al_pa, uint16_t *mb, uint8_t opt)
2495 {
2496 int rval;
2497
2498 struct logio_entry_24xx *lg;
2499 dma_addr_t lg_dma;
2500 uint32_t iop[2];
2501 struct qla_hw_data *ha = vha->hw;
2502 struct req_que *req;
2503
2504 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1061,
2505 "Entered %s.\n", __func__);
2506
2507 if (vha->vp_idx && vha->qpair)
2508 req = vha->qpair->req;
2509 else
2510 req = ha->req_q_map[0];
2511
2512 lg = dma_pool_zalloc(ha->s_dma_pool, GFP_KERNEL, &lg_dma);
2513 if (lg == NULL) {
2514 ql_log(ql_log_warn, vha, 0x1062,
2515 "Failed to allocate login IOCB.\n");
2516 return QLA_MEMORY_ALLOC_FAILED;
2517 }
2518
2519 lg->entry_type = LOGINOUT_PORT_IOCB_TYPE;
2520 lg->entry_count = 1;
2521 lg->handle = make_handle(req->id, lg->handle);
2522 lg->nport_handle = cpu_to_le16(loop_id);
2523 lg->control_flags = cpu_to_le16(LCF_COMMAND_PLOGI);
2524 if (opt & BIT_0)
2525 lg->control_flags |= cpu_to_le16(LCF_COND_PLOGI);
2526 if (opt & BIT_1)
2527 lg->control_flags |= cpu_to_le16(LCF_SKIP_PRLI);
2528 lg->port_id[0] = al_pa;
2529 lg->port_id[1] = area;
2530 lg->port_id[2] = domain;
2531 lg->vp_index = vha->vp_idx;
2532 rval = qla2x00_issue_iocb_timeout(vha, lg, lg_dma, 0,
2533 (ha->r_a_tov / 10 * 2) + 2);
2534 if (rval != QLA_SUCCESS) {
2535 ql_dbg(ql_dbg_mbx, vha, 0x1063,
2536 "Failed to issue login IOCB (%x).\n", rval);
2537 } else if (lg->entry_status != 0) {
2538 ql_dbg(ql_dbg_mbx, vha, 0x1064,
2539 "Failed to complete IOCB -- error status (%x).\n",
2540 lg->entry_status);
2541 rval = QLA_FUNCTION_FAILED;
2542 } else if (lg->comp_status != cpu_to_le16(CS_COMPLETE)) {
2543 iop[0] = le32_to_cpu(lg->io_parameter[0]);
2544 iop[1] = le32_to_cpu(lg->io_parameter[1]);
2545
2546 ql_dbg(ql_dbg_mbx, vha, 0x1065,
2547 "Failed to complete IOCB -- completion status (%x) "
2548 "ioparam=%x/%x.\n", le16_to_cpu(lg->comp_status),
2549 iop[0], iop[1]);
2550
2551 switch (iop[0]) {
2552 case LSC_SCODE_PORTID_USED:
2553 mb[0] = MBS_PORT_ID_USED;
2554 mb[1] = LSW(iop[1]);
2555 break;
2556 case LSC_SCODE_NPORT_USED:
2557 mb[0] = MBS_LOOP_ID_USED;
2558 break;
2559 case LSC_SCODE_NOLINK:
2560 case LSC_SCODE_NOIOCB:
2561 case LSC_SCODE_NOXCB:
2562 case LSC_SCODE_CMD_FAILED:
2563 case LSC_SCODE_NOFABRIC:
2564 case LSC_SCODE_FW_NOT_READY:
2565 case LSC_SCODE_NOT_LOGGED_IN:
2566 case LSC_SCODE_NOPCB:
2567 case LSC_SCODE_ELS_REJECT:
2568 case LSC_SCODE_CMD_PARAM_ERR:
2569 case LSC_SCODE_NONPORT:
2570 case LSC_SCODE_LOGGED_IN:
2571 case LSC_SCODE_NOFLOGI_ACC:
2572 default:
2573 mb[0] = MBS_COMMAND_ERROR;
2574 break;
2575 }
2576 } else {
2577 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1066,
2578 "Done %s.\n", __func__);
2579
2580 iop[0] = le32_to_cpu(lg->io_parameter[0]);
2581
2582 mb[0] = MBS_COMMAND_COMPLETE;
2583 mb[1] = 0;
2584 if (iop[0] & BIT_4) {
2585 if (iop[0] & BIT_8)
2586 mb[1] |= BIT_1;
2587 } else
2588 mb[1] = BIT_0;
2589
2590 /* Passback COS information. */
2591 mb[10] = 0;
2592 if (lg->io_parameter[7] || lg->io_parameter[8])
2593 mb[10] |= BIT_0; /* Class 2. */
2594 if (lg->io_parameter[9] || lg->io_parameter[10])
2595 mb[10] |= BIT_1; /* Class 3. */
2596 if (lg->io_parameter[0] & cpu_to_le32(BIT_7))
2597 mb[10] |= BIT_7; /* Confirmed Completion
2598 * Allowed
2599 */
2600 }
2601
2602 dma_pool_free(ha->s_dma_pool, lg, lg_dma);
2603
2604 return rval;
2605 }
2606
2607 /*
2608 * qla2x00_login_fabric
2609 * Issue login fabric port mailbox command.
2610 *
2611 * Input:
2612 * ha = adapter block pointer.
2613 * loop_id = device loop ID.
2614 * domain = device domain.
2615 * area = device area.
2616 * al_pa = device AL_PA.
2617 * status = pointer for return status.
2618 * opt = command options.
2619 * TARGET_QUEUE_LOCK must be released.
2620 * ADAPTER_STATE_LOCK must be released.
2621 *
2622 * Returns:
2623 * qla2x00 local function return status code.
2624 *
2625 * Context:
2626 * Kernel context.
2627 */
2628 int
qla2x00_login_fabric(scsi_qla_host_t * vha,uint16_t loop_id,uint8_t domain,uint8_t area,uint8_t al_pa,uint16_t * mb,uint8_t opt)2629 qla2x00_login_fabric(scsi_qla_host_t *vha, uint16_t loop_id, uint8_t domain,
2630 uint8_t area, uint8_t al_pa, uint16_t *mb, uint8_t opt)
2631 {
2632 int rval;
2633 mbx_cmd_t mc;
2634 mbx_cmd_t *mcp = &mc;
2635 struct qla_hw_data *ha = vha->hw;
2636
2637 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1067,
2638 "Entered %s.\n", __func__);
2639
2640 mcp->mb[0] = MBC_LOGIN_FABRIC_PORT;
2641 mcp->out_mb = MBX_3|MBX_2|MBX_1|MBX_0;
2642 if (HAS_EXTENDED_IDS(ha)) {
2643 mcp->mb[1] = loop_id;
2644 mcp->mb[10] = opt;
2645 mcp->out_mb |= MBX_10;
2646 } else {
2647 mcp->mb[1] = (loop_id << 8) | opt;
2648 }
2649 mcp->mb[2] = domain;
2650 mcp->mb[3] = area << 8 | al_pa;
2651
2652 mcp->in_mb = MBX_7|MBX_6|MBX_2|MBX_1|MBX_0;
2653 mcp->tov = (ha->login_timeout * 2) + (ha->login_timeout / 2);
2654 mcp->flags = 0;
2655 rval = qla2x00_mailbox_command(vha, mcp);
2656
2657 /* Return mailbox statuses. */
2658 if (mb != NULL) {
2659 mb[0] = mcp->mb[0];
2660 mb[1] = mcp->mb[1];
2661 mb[2] = mcp->mb[2];
2662 mb[6] = mcp->mb[6];
2663 mb[7] = mcp->mb[7];
2664 /* COS retrieved from Get-Port-Database mailbox command. */
2665 mb[10] = 0;
2666 }
2667
2668 if (rval != QLA_SUCCESS) {
2669 /* RLU tmp code: need to change main mailbox_command function to
2670 * return ok even when the mailbox completion value is not
2671 * SUCCESS. The caller needs to be responsible to interpret
2672 * the return values of this mailbox command if we're not
2673 * to change too much of the existing code.
2674 */
2675 if (mcp->mb[0] == 0x4001 || mcp->mb[0] == 0x4002 ||
2676 mcp->mb[0] == 0x4003 || mcp->mb[0] == 0x4005 ||
2677 mcp->mb[0] == 0x4006)
2678 rval = QLA_SUCCESS;
2679
2680 /*EMPTY*/
2681 ql_dbg(ql_dbg_mbx, vha, 0x1068,
2682 "Failed=%x mb[0]=%x mb[1]=%x mb[2]=%x.\n",
2683 rval, mcp->mb[0], mcp->mb[1], mcp->mb[2]);
2684 } else {
2685 /*EMPTY*/
2686 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1069,
2687 "Done %s.\n", __func__);
2688 }
2689
2690 return rval;
2691 }
2692
2693 /*
2694 * qla2x00_login_local_device
2695 * Issue login loop port mailbox command.
2696 *
2697 * Input:
2698 * ha = adapter block pointer.
2699 * loop_id = device loop ID.
2700 * opt = command options.
2701 *
2702 * Returns:
2703 * Return status code.
2704 *
2705 * Context:
2706 * Kernel context.
2707 *
2708 */
2709 int
qla2x00_login_local_device(scsi_qla_host_t * vha,fc_port_t * fcport,uint16_t * mb_ret,uint8_t opt)2710 qla2x00_login_local_device(scsi_qla_host_t *vha, fc_port_t *fcport,
2711 uint16_t *mb_ret, uint8_t opt)
2712 {
2713 int rval;
2714 mbx_cmd_t mc;
2715 mbx_cmd_t *mcp = &mc;
2716 struct qla_hw_data *ha = vha->hw;
2717
2718 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x106a,
2719 "Entered %s.\n", __func__);
2720
2721 if (IS_FWI2_CAPABLE(ha))
2722 return qla24xx_login_fabric(vha, fcport->loop_id,
2723 fcport->d_id.b.domain, fcport->d_id.b.area,
2724 fcport->d_id.b.al_pa, mb_ret, opt);
2725
2726 mcp->mb[0] = MBC_LOGIN_LOOP_PORT;
2727 if (HAS_EXTENDED_IDS(ha))
2728 mcp->mb[1] = fcport->loop_id;
2729 else
2730 mcp->mb[1] = fcport->loop_id << 8;
2731 mcp->mb[2] = opt;
2732 mcp->out_mb = MBX_2|MBX_1|MBX_0;
2733 mcp->in_mb = MBX_7|MBX_6|MBX_1|MBX_0;
2734 mcp->tov = (ha->login_timeout * 2) + (ha->login_timeout / 2);
2735 mcp->flags = 0;
2736 rval = qla2x00_mailbox_command(vha, mcp);
2737
2738 /* Return mailbox statuses. */
2739 if (mb_ret != NULL) {
2740 mb_ret[0] = mcp->mb[0];
2741 mb_ret[1] = mcp->mb[1];
2742 mb_ret[6] = mcp->mb[6];
2743 mb_ret[7] = mcp->mb[7];
2744 }
2745
2746 if (rval != QLA_SUCCESS) {
2747 /* AV tmp code: need to change main mailbox_command function to
2748 * return ok even when the mailbox completion value is not
2749 * SUCCESS. The caller needs to be responsible to interpret
2750 * the return values of this mailbox command if we're not
2751 * to change too much of the existing code.
2752 */
2753 if (mcp->mb[0] == 0x4005 || mcp->mb[0] == 0x4006)
2754 rval = QLA_SUCCESS;
2755
2756 ql_dbg(ql_dbg_mbx, vha, 0x106b,
2757 "Failed=%x mb[0]=%x mb[1]=%x mb[6]=%x mb[7]=%x.\n",
2758 rval, mcp->mb[0], mcp->mb[1], mcp->mb[6], mcp->mb[7]);
2759 } else {
2760 /*EMPTY*/
2761 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x106c,
2762 "Done %s.\n", __func__);
2763 }
2764
2765 return (rval);
2766 }
2767
2768 int
qla24xx_fabric_logout(scsi_qla_host_t * vha,uint16_t loop_id,uint8_t domain,uint8_t area,uint8_t al_pa)2769 qla24xx_fabric_logout(scsi_qla_host_t *vha, uint16_t loop_id, uint8_t domain,
2770 uint8_t area, uint8_t al_pa)
2771 {
2772 int rval;
2773 struct logio_entry_24xx *lg;
2774 dma_addr_t lg_dma;
2775 struct qla_hw_data *ha = vha->hw;
2776 struct req_que *req;
2777
2778 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x106d,
2779 "Entered %s.\n", __func__);
2780
2781 lg = dma_pool_zalloc(ha->s_dma_pool, GFP_KERNEL, &lg_dma);
2782 if (lg == NULL) {
2783 ql_log(ql_log_warn, vha, 0x106e,
2784 "Failed to allocate logout IOCB.\n");
2785 return QLA_MEMORY_ALLOC_FAILED;
2786 }
2787
2788 req = vha->req;
2789 lg->entry_type = LOGINOUT_PORT_IOCB_TYPE;
2790 lg->entry_count = 1;
2791 lg->handle = make_handle(req->id, lg->handle);
2792 lg->nport_handle = cpu_to_le16(loop_id);
2793 lg->control_flags =
2794 cpu_to_le16(LCF_COMMAND_LOGO|LCF_IMPL_LOGO|
2795 LCF_FREE_NPORT);
2796 lg->port_id[0] = al_pa;
2797 lg->port_id[1] = area;
2798 lg->port_id[2] = domain;
2799 lg->vp_index = vha->vp_idx;
2800 rval = qla2x00_issue_iocb_timeout(vha, lg, lg_dma, 0,
2801 (ha->r_a_tov / 10 * 2) + 2);
2802 if (rval != QLA_SUCCESS) {
2803 ql_dbg(ql_dbg_mbx, vha, 0x106f,
2804 "Failed to issue logout IOCB (%x).\n", rval);
2805 } else if (lg->entry_status != 0) {
2806 ql_dbg(ql_dbg_mbx, vha, 0x1070,
2807 "Failed to complete IOCB -- error status (%x).\n",
2808 lg->entry_status);
2809 rval = QLA_FUNCTION_FAILED;
2810 } else if (lg->comp_status != cpu_to_le16(CS_COMPLETE)) {
2811 ql_dbg(ql_dbg_mbx, vha, 0x1071,
2812 "Failed to complete IOCB -- completion status (%x) "
2813 "ioparam=%x/%x.\n", le16_to_cpu(lg->comp_status),
2814 le32_to_cpu(lg->io_parameter[0]),
2815 le32_to_cpu(lg->io_parameter[1]));
2816 } else {
2817 /*EMPTY*/
2818 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1072,
2819 "Done %s.\n", __func__);
2820 }
2821
2822 dma_pool_free(ha->s_dma_pool, lg, lg_dma);
2823
2824 return rval;
2825 }
2826
2827 /*
2828 * qla2x00_fabric_logout
2829 * Issue logout fabric port mailbox command.
2830 *
2831 * Input:
2832 * ha = adapter block pointer.
2833 * loop_id = device loop ID.
2834 * TARGET_QUEUE_LOCK must be released.
2835 * ADAPTER_STATE_LOCK must be released.
2836 *
2837 * Returns:
2838 * qla2x00 local function return status code.
2839 *
2840 * Context:
2841 * Kernel context.
2842 */
2843 int
qla2x00_fabric_logout(scsi_qla_host_t * vha,uint16_t loop_id,uint8_t domain,uint8_t area,uint8_t al_pa)2844 qla2x00_fabric_logout(scsi_qla_host_t *vha, uint16_t loop_id, uint8_t domain,
2845 uint8_t area, uint8_t al_pa)
2846 {
2847 int rval;
2848 mbx_cmd_t mc;
2849 mbx_cmd_t *mcp = &mc;
2850
2851 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1073,
2852 "Entered %s.\n", __func__);
2853
2854 mcp->mb[0] = MBC_LOGOUT_FABRIC_PORT;
2855 mcp->out_mb = MBX_1|MBX_0;
2856 if (HAS_EXTENDED_IDS(vha->hw)) {
2857 mcp->mb[1] = loop_id;
2858 mcp->mb[10] = 0;
2859 mcp->out_mb |= MBX_10;
2860 } else {
2861 mcp->mb[1] = loop_id << 8;
2862 }
2863
2864 mcp->in_mb = MBX_1|MBX_0;
2865 mcp->tov = MBX_TOV_SECONDS;
2866 mcp->flags = 0;
2867 rval = qla2x00_mailbox_command(vha, mcp);
2868
2869 if (rval != QLA_SUCCESS) {
2870 /*EMPTY*/
2871 ql_dbg(ql_dbg_mbx, vha, 0x1074,
2872 "Failed=%x mb[1]=%x.\n", rval, mcp->mb[1]);
2873 } else {
2874 /*EMPTY*/
2875 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1075,
2876 "Done %s.\n", __func__);
2877 }
2878
2879 return rval;
2880 }
2881
2882 /*
2883 * qla2x00_full_login_lip
2884 * Issue full login LIP mailbox command.
2885 *
2886 * Input:
2887 * ha = adapter block pointer.
2888 * TARGET_QUEUE_LOCK must be released.
2889 * ADAPTER_STATE_LOCK must be released.
2890 *
2891 * Returns:
2892 * qla2x00 local function return status code.
2893 *
2894 * Context:
2895 * Kernel context.
2896 */
2897 int
qla2x00_full_login_lip(scsi_qla_host_t * vha)2898 qla2x00_full_login_lip(scsi_qla_host_t *vha)
2899 {
2900 int rval;
2901 mbx_cmd_t mc;
2902 mbx_cmd_t *mcp = &mc;
2903
2904 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1076,
2905 "Entered %s.\n", __func__);
2906
2907 mcp->mb[0] = MBC_LIP_FULL_LOGIN;
2908 mcp->mb[1] = IS_FWI2_CAPABLE(vha->hw) ? BIT_4 : 0;
2909 mcp->mb[2] = 0;
2910 mcp->mb[3] = 0;
2911 mcp->out_mb = MBX_3|MBX_2|MBX_1|MBX_0;
2912 mcp->in_mb = MBX_0;
2913 mcp->tov = MBX_TOV_SECONDS;
2914 mcp->flags = 0;
2915 rval = qla2x00_mailbox_command(vha, mcp);
2916
2917 if (rval != QLA_SUCCESS) {
2918 /*EMPTY*/
2919 ql_dbg(ql_dbg_mbx, vha, 0x1077, "Failed=%x.\n", rval);
2920 } else {
2921 /*EMPTY*/
2922 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1078,
2923 "Done %s.\n", __func__);
2924 }
2925
2926 return rval;
2927 }
2928
2929 /*
2930 * qla2x00_get_id_list
2931 *
2932 * Input:
2933 * ha = adapter block pointer.
2934 *
2935 * Returns:
2936 * qla2x00 local function return status code.
2937 *
2938 * Context:
2939 * Kernel context.
2940 */
2941 int
qla2x00_get_id_list(scsi_qla_host_t * vha,void * id_list,dma_addr_t id_list_dma,uint16_t * entries)2942 qla2x00_get_id_list(scsi_qla_host_t *vha, void *id_list, dma_addr_t id_list_dma,
2943 uint16_t *entries)
2944 {
2945 int rval;
2946 mbx_cmd_t mc;
2947 mbx_cmd_t *mcp = &mc;
2948
2949 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1079,
2950 "Entered %s.\n", __func__);
2951
2952 if (id_list == NULL)
2953 return QLA_FUNCTION_FAILED;
2954
2955 mcp->mb[0] = MBC_GET_ID_LIST;
2956 mcp->out_mb = MBX_0;
2957 if (IS_FWI2_CAPABLE(vha->hw)) {
2958 mcp->mb[2] = MSW(id_list_dma);
2959 mcp->mb[3] = LSW(id_list_dma);
2960 mcp->mb[6] = MSW(MSD(id_list_dma));
2961 mcp->mb[7] = LSW(MSD(id_list_dma));
2962 mcp->mb[8] = 0;
2963 mcp->mb[9] = vha->vp_idx;
2964 mcp->out_mb |= MBX_9|MBX_8|MBX_7|MBX_6|MBX_3|MBX_2;
2965 } else {
2966 mcp->mb[1] = MSW(id_list_dma);
2967 mcp->mb[2] = LSW(id_list_dma);
2968 mcp->mb[3] = MSW(MSD(id_list_dma));
2969 mcp->mb[6] = LSW(MSD(id_list_dma));
2970 mcp->out_mb |= MBX_6|MBX_3|MBX_2|MBX_1;
2971 }
2972 mcp->in_mb = MBX_1|MBX_0;
2973 mcp->tov = MBX_TOV_SECONDS;
2974 mcp->flags = 0;
2975 rval = qla2x00_mailbox_command(vha, mcp);
2976
2977 if (rval != QLA_SUCCESS) {
2978 /*EMPTY*/
2979 ql_dbg(ql_dbg_mbx, vha, 0x107a, "Failed=%x.\n", rval);
2980 } else {
2981 *entries = mcp->mb[1];
2982 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x107b,
2983 "Done %s.\n", __func__);
2984 }
2985
2986 return rval;
2987 }
2988
2989 /*
2990 * qla2x00_get_resource_cnts
2991 * Get current firmware resource counts.
2992 *
2993 * Input:
2994 * ha = adapter block pointer.
2995 *
2996 * Returns:
2997 * qla2x00 local function return status code.
2998 *
2999 * Context:
3000 * Kernel context.
3001 */
3002 int
qla2x00_get_resource_cnts(scsi_qla_host_t * vha)3003 qla2x00_get_resource_cnts(scsi_qla_host_t *vha)
3004 {
3005 struct qla_hw_data *ha = vha->hw;
3006 int rval;
3007 mbx_cmd_t mc;
3008 mbx_cmd_t *mcp = &mc;
3009
3010 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x107c,
3011 "Entered %s.\n", __func__);
3012
3013 mcp->mb[0] = MBC_GET_RESOURCE_COUNTS;
3014 mcp->out_mb = MBX_0;
3015 mcp->in_mb = MBX_11|MBX_10|MBX_7|MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
3016 if (IS_QLA81XX(ha) || IS_QLA83XX(ha) ||
3017 IS_QLA27XX(ha) || IS_QLA28XX(ha))
3018 mcp->in_mb |= MBX_12;
3019 mcp->tov = MBX_TOV_SECONDS;
3020 mcp->flags = 0;
3021 rval = qla2x00_mailbox_command(vha, mcp);
3022
3023 if (rval != QLA_SUCCESS) {
3024 /*EMPTY*/
3025 ql_dbg(ql_dbg_mbx, vha, 0x107d,
3026 "Failed mb[0]=%x.\n", mcp->mb[0]);
3027 } else {
3028 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x107e,
3029 "Done %s mb1=%x mb2=%x mb3=%x mb6=%x mb7=%x mb10=%x "
3030 "mb11=%x mb12=%x.\n", __func__, mcp->mb[1], mcp->mb[2],
3031 mcp->mb[3], mcp->mb[6], mcp->mb[7], mcp->mb[10],
3032 mcp->mb[11], mcp->mb[12]);
3033
3034 ha->orig_fw_tgt_xcb_count = mcp->mb[1];
3035 ha->cur_fw_tgt_xcb_count = mcp->mb[2];
3036 ha->cur_fw_xcb_count = mcp->mb[3];
3037 ha->orig_fw_xcb_count = mcp->mb[6];
3038 ha->cur_fw_iocb_count = mcp->mb[7];
3039 ha->orig_fw_iocb_count = mcp->mb[10];
3040 if (ha->flags.npiv_supported)
3041 ha->max_npiv_vports = mcp->mb[11];
3042 if (IS_QLA81XX(ha) || IS_QLA83XX(ha))
3043 ha->fw_max_fcf_count = mcp->mb[12];
3044 }
3045
3046 return (rval);
3047 }
3048
3049 /*
3050 * qla2x00_get_fcal_position_map
3051 * Get FCAL (LILP) position map using mailbox command
3052 *
3053 * Input:
3054 * ha = adapter state pointer.
3055 * pos_map = buffer pointer (can be NULL).
3056 *
3057 * Returns:
3058 * qla2x00 local function return status code.
3059 *
3060 * Context:
3061 * Kernel context.
3062 */
3063 int
qla2x00_get_fcal_position_map(scsi_qla_host_t * vha,char * pos_map,u8 * num_entries)3064 qla2x00_get_fcal_position_map(scsi_qla_host_t *vha, char *pos_map,
3065 u8 *num_entries)
3066 {
3067 int rval;
3068 mbx_cmd_t mc;
3069 mbx_cmd_t *mcp = &mc;
3070 char *pmap;
3071 dma_addr_t pmap_dma;
3072 struct qla_hw_data *ha = vha->hw;
3073
3074 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x107f,
3075 "Entered %s.\n", __func__);
3076
3077 pmap = dma_pool_zalloc(ha->s_dma_pool, GFP_KERNEL, &pmap_dma);
3078 if (pmap == NULL) {
3079 ql_log(ql_log_warn, vha, 0x1080,
3080 "Memory alloc failed.\n");
3081 return QLA_MEMORY_ALLOC_FAILED;
3082 }
3083
3084 mcp->mb[0] = MBC_GET_FC_AL_POSITION_MAP;
3085 mcp->mb[2] = MSW(pmap_dma);
3086 mcp->mb[3] = LSW(pmap_dma);
3087 mcp->mb[6] = MSW(MSD(pmap_dma));
3088 mcp->mb[7] = LSW(MSD(pmap_dma));
3089 mcp->out_mb = MBX_7|MBX_6|MBX_3|MBX_2|MBX_0;
3090 mcp->in_mb = MBX_1|MBX_0;
3091 mcp->buf_size = FCAL_MAP_SIZE;
3092 mcp->flags = MBX_DMA_IN;
3093 mcp->tov = (ha->login_timeout * 2) + (ha->login_timeout / 2);
3094 rval = qla2x00_mailbox_command(vha, mcp);
3095
3096 if (rval == QLA_SUCCESS) {
3097 ql_dbg(ql_dbg_mbx + ql_dbg_buffer, vha, 0x1081,
3098 "mb0/mb1=%x/%X FC/AL position map size (%x).\n",
3099 mcp->mb[0], mcp->mb[1], (unsigned)pmap[0]);
3100 ql_dump_buffer(ql_dbg_mbx + ql_dbg_buffer, vha, 0x111d,
3101 pmap, pmap[0] + 1);
3102
3103 if (pos_map)
3104 memcpy(pos_map, pmap, FCAL_MAP_SIZE);
3105 if (num_entries)
3106 *num_entries = pmap[0];
3107 }
3108 dma_pool_free(ha->s_dma_pool, pmap, pmap_dma);
3109
3110 if (rval != QLA_SUCCESS) {
3111 ql_dbg(ql_dbg_mbx, vha, 0x1082, "Failed=%x.\n", rval);
3112 } else {
3113 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1083,
3114 "Done %s.\n", __func__);
3115 }
3116
3117 return rval;
3118 }
3119
3120 /*
3121 * qla2x00_get_link_status
3122 *
3123 * Input:
3124 * ha = adapter block pointer.
3125 * loop_id = device loop ID.
3126 * ret_buf = pointer to link status return buffer.
3127 *
3128 * Returns:
3129 * 0 = success.
3130 * BIT_0 = mem alloc error.
3131 * BIT_1 = mailbox error.
3132 */
3133 int
qla2x00_get_link_status(scsi_qla_host_t * vha,uint16_t loop_id,struct link_statistics * stats,dma_addr_t stats_dma)3134 qla2x00_get_link_status(scsi_qla_host_t *vha, uint16_t loop_id,
3135 struct link_statistics *stats, dma_addr_t stats_dma)
3136 {
3137 int rval;
3138 mbx_cmd_t mc;
3139 mbx_cmd_t *mcp = &mc;
3140 uint32_t *iter = (uint32_t *)stats;
3141 ushort dwords = offsetof(typeof(*stats), link_up_cnt)/sizeof(*iter);
3142 struct qla_hw_data *ha = vha->hw;
3143
3144 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1084,
3145 "Entered %s.\n", __func__);
3146
3147 mcp->mb[0] = MBC_GET_LINK_STATUS;
3148 mcp->mb[2] = MSW(LSD(stats_dma));
3149 mcp->mb[3] = LSW(LSD(stats_dma));
3150 mcp->mb[6] = MSW(MSD(stats_dma));
3151 mcp->mb[7] = LSW(MSD(stats_dma));
3152 mcp->out_mb = MBX_7|MBX_6|MBX_3|MBX_2|MBX_0;
3153 mcp->in_mb = MBX_0;
3154 if (IS_FWI2_CAPABLE(ha)) {
3155 mcp->mb[1] = loop_id;
3156 mcp->mb[4] = 0;
3157 mcp->mb[10] = 0;
3158 mcp->out_mb |= MBX_10|MBX_4|MBX_1;
3159 mcp->in_mb |= MBX_1;
3160 } else if (HAS_EXTENDED_IDS(ha)) {
3161 mcp->mb[1] = loop_id;
3162 mcp->mb[10] = 0;
3163 mcp->out_mb |= MBX_10|MBX_1;
3164 } else {
3165 mcp->mb[1] = loop_id << 8;
3166 mcp->out_mb |= MBX_1;
3167 }
3168 mcp->tov = MBX_TOV_SECONDS;
3169 mcp->flags = IOCTL_CMD;
3170 rval = qla2x00_mailbox_command(vha, mcp);
3171
3172 if (rval == QLA_SUCCESS) {
3173 if (mcp->mb[0] != MBS_COMMAND_COMPLETE) {
3174 ql_dbg(ql_dbg_mbx, vha, 0x1085,
3175 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
3176 rval = QLA_FUNCTION_FAILED;
3177 } else {
3178 /* Re-endianize - firmware data is le32. */
3179 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1086,
3180 "Done %s.\n", __func__);
3181 for ( ; dwords--; iter++)
3182 le32_to_cpus(iter);
3183 }
3184 } else {
3185 /* Failed. */
3186 ql_dbg(ql_dbg_mbx, vha, 0x1087, "Failed=%x.\n", rval);
3187 }
3188
3189 return rval;
3190 }
3191
3192 int
qla24xx_get_isp_stats(scsi_qla_host_t * vha,struct link_statistics * stats,dma_addr_t stats_dma,uint16_t options)3193 qla24xx_get_isp_stats(scsi_qla_host_t *vha, struct link_statistics *stats,
3194 dma_addr_t stats_dma, uint16_t options)
3195 {
3196 int rval;
3197 mbx_cmd_t mc;
3198 mbx_cmd_t *mcp = &mc;
3199 uint32_t *iter = (uint32_t *)stats;
3200 ushort dwords = sizeof(*stats)/sizeof(*iter);
3201
3202 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1088,
3203 "Entered %s.\n", __func__);
3204
3205 memset(&mc, 0, sizeof(mc));
3206 mc.mb[0] = MBC_GET_LINK_PRIV_STATS;
3207 mc.mb[2] = MSW(LSD(stats_dma));
3208 mc.mb[3] = LSW(LSD(stats_dma));
3209 mc.mb[6] = MSW(MSD(stats_dma));
3210 mc.mb[7] = LSW(MSD(stats_dma));
3211 mc.mb[8] = dwords;
3212 mc.mb[9] = vha->vp_idx;
3213 mc.mb[10] = options;
3214
3215 rval = qla24xx_send_mb_cmd(vha, &mc);
3216
3217 if (rval == QLA_SUCCESS) {
3218 if (mcp->mb[0] != MBS_COMMAND_COMPLETE) {
3219 ql_dbg(ql_dbg_mbx, vha, 0x1089,
3220 "Failed mb[0]=%x.\n", mcp->mb[0]);
3221 rval = QLA_FUNCTION_FAILED;
3222 } else {
3223 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x108a,
3224 "Done %s.\n", __func__);
3225 /* Re-endianize - firmware data is le32. */
3226 for ( ; dwords--; iter++)
3227 le32_to_cpus(iter);
3228 }
3229 } else {
3230 /* Failed. */
3231 ql_dbg(ql_dbg_mbx, vha, 0x108b, "Failed=%x.\n", rval);
3232 }
3233
3234 return rval;
3235 }
3236
3237 int
qla24xx_abort_command(srb_t * sp)3238 qla24xx_abort_command(srb_t *sp)
3239 {
3240 int rval;
3241 unsigned long flags = 0;
3242
3243 struct abort_entry_24xx *abt;
3244 dma_addr_t abt_dma;
3245 uint32_t handle;
3246 fc_port_t *fcport = sp->fcport;
3247 struct scsi_qla_host *vha = fcport->vha;
3248 struct qla_hw_data *ha = vha->hw;
3249 struct req_que *req = vha->req;
3250 struct qla_qpair *qpair = sp->qpair;
3251
3252 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x108c,
3253 "Entered %s.\n", __func__);
3254
3255 if (sp->qpair)
3256 req = sp->qpair->req;
3257 else
3258 return QLA_ERR_NO_QPAIR;
3259
3260 if (ql2xasynctmfenable)
3261 return qla24xx_async_abort_command(sp);
3262
3263 spin_lock_irqsave(qpair->qp_lock_ptr, flags);
3264 for (handle = 1; handle < req->num_outstanding_cmds; handle++) {
3265 if (req->outstanding_cmds[handle] == sp)
3266 break;
3267 }
3268 spin_unlock_irqrestore(qpair->qp_lock_ptr, flags);
3269 if (handle == req->num_outstanding_cmds) {
3270 /* Command not found. */
3271 return QLA_ERR_NOT_FOUND;
3272 }
3273
3274 abt = dma_pool_zalloc(ha->s_dma_pool, GFP_KERNEL, &abt_dma);
3275 if (abt == NULL) {
3276 ql_log(ql_log_warn, vha, 0x108d,
3277 "Failed to allocate abort IOCB.\n");
3278 return QLA_MEMORY_ALLOC_FAILED;
3279 }
3280
3281 abt->entry_type = ABORT_IOCB_TYPE;
3282 abt->entry_count = 1;
3283 abt->handle = make_handle(req->id, abt->handle);
3284 abt->nport_handle = cpu_to_le16(fcport->loop_id);
3285 abt->handle_to_abort = make_handle(req->id, handle);
3286 abt->port_id[0] = fcport->d_id.b.al_pa;
3287 abt->port_id[1] = fcport->d_id.b.area;
3288 abt->port_id[2] = fcport->d_id.b.domain;
3289 abt->vp_index = fcport->vha->vp_idx;
3290
3291 abt->req_que_no = cpu_to_le16(req->id);
3292 /* Need to pass original sp */
3293 qla_nvme_abort_set_option(abt, sp);
3294
3295 rval = qla2x00_issue_iocb(vha, abt, abt_dma, 0);
3296 if (rval != QLA_SUCCESS) {
3297 ql_dbg(ql_dbg_mbx, vha, 0x108e,
3298 "Failed to issue IOCB (%x).\n", rval);
3299 } else if (abt->entry_status != 0) {
3300 ql_dbg(ql_dbg_mbx, vha, 0x108f,
3301 "Failed to complete IOCB -- error status (%x).\n",
3302 abt->entry_status);
3303 rval = QLA_FUNCTION_FAILED;
3304 } else if (abt->nport_handle != cpu_to_le16(0)) {
3305 ql_dbg(ql_dbg_mbx, vha, 0x1090,
3306 "Failed to complete IOCB -- completion status (%x).\n",
3307 le16_to_cpu(abt->nport_handle));
3308 if (abt->nport_handle == cpu_to_le16(CS_IOCB_ERROR))
3309 rval = QLA_FUNCTION_PARAMETER_ERROR;
3310 else
3311 rval = QLA_FUNCTION_FAILED;
3312 } else {
3313 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1091,
3314 "Done %s.\n", __func__);
3315 }
3316 if (rval == QLA_SUCCESS)
3317 qla_nvme_abort_process_comp_status(abt, sp);
3318
3319 qla_wait_nvme_release_cmd_kref(sp);
3320
3321 dma_pool_free(ha->s_dma_pool, abt, abt_dma);
3322
3323 return rval;
3324 }
3325
3326 struct tsk_mgmt_cmd {
3327 union {
3328 struct tsk_mgmt_entry tsk;
3329 struct sts_entry_24xx sts;
3330 } p;
3331 };
3332
3333 static int
__qla24xx_issue_tmf(char * name,uint32_t type,struct fc_port * fcport,uint64_t l,int tag)3334 __qla24xx_issue_tmf(char *name, uint32_t type, struct fc_port *fcport,
3335 uint64_t l, int tag)
3336 {
3337 int rval, rval2;
3338 struct tsk_mgmt_cmd *tsk;
3339 struct sts_entry_24xx *sts;
3340 dma_addr_t tsk_dma;
3341 scsi_qla_host_t *vha;
3342 struct qla_hw_data *ha;
3343 struct req_que *req;
3344 struct qla_qpair *qpair;
3345
3346 vha = fcport->vha;
3347 ha = vha->hw;
3348 req = vha->req;
3349
3350 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1092,
3351 "Entered %s.\n", __func__);
3352
3353 if (vha->vp_idx && vha->qpair) {
3354 /* NPIV port */
3355 qpair = vha->qpair;
3356 req = qpair->req;
3357 }
3358
3359 tsk = dma_pool_zalloc(ha->s_dma_pool, GFP_KERNEL, &tsk_dma);
3360 if (tsk == NULL) {
3361 ql_log(ql_log_warn, vha, 0x1093,
3362 "Failed to allocate task management IOCB.\n");
3363 return QLA_MEMORY_ALLOC_FAILED;
3364 }
3365
3366 tsk->p.tsk.entry_type = TSK_MGMT_IOCB_TYPE;
3367 tsk->p.tsk.entry_count = 1;
3368 tsk->p.tsk.handle = make_handle(req->id, tsk->p.tsk.handle);
3369 tsk->p.tsk.nport_handle = cpu_to_le16(fcport->loop_id);
3370 tsk->p.tsk.timeout = cpu_to_le16(ha->r_a_tov / 10 * 2);
3371 tsk->p.tsk.control_flags = cpu_to_le32(type);
3372 tsk->p.tsk.port_id[0] = fcport->d_id.b.al_pa;
3373 tsk->p.tsk.port_id[1] = fcport->d_id.b.area;
3374 tsk->p.tsk.port_id[2] = fcport->d_id.b.domain;
3375 tsk->p.tsk.vp_index = fcport->vha->vp_idx;
3376 if (type == TCF_LUN_RESET) {
3377 int_to_scsilun(l, &tsk->p.tsk.lun);
3378 host_to_fcp_swap((uint8_t *)&tsk->p.tsk.lun,
3379 sizeof(tsk->p.tsk.lun));
3380 }
3381
3382 sts = &tsk->p.sts;
3383 rval = qla2x00_issue_iocb(vha, tsk, tsk_dma, 0);
3384 if (rval != QLA_SUCCESS) {
3385 ql_dbg(ql_dbg_mbx, vha, 0x1094,
3386 "Failed to issue %s reset IOCB (%x).\n", name, rval);
3387 } else if (sts->entry_status != 0) {
3388 ql_dbg(ql_dbg_mbx, vha, 0x1095,
3389 "Failed to complete IOCB -- error status (%x).\n",
3390 sts->entry_status);
3391 rval = QLA_FUNCTION_FAILED;
3392 } else if (sts->comp_status != cpu_to_le16(CS_COMPLETE)) {
3393 ql_dbg(ql_dbg_mbx, vha, 0x1096,
3394 "Failed to complete IOCB -- completion status (%x).\n",
3395 le16_to_cpu(sts->comp_status));
3396 rval = QLA_FUNCTION_FAILED;
3397 } else if (le16_to_cpu(sts->scsi_status) &
3398 SS_RESPONSE_INFO_LEN_VALID) {
3399 if (le32_to_cpu(sts->rsp_data_len) < 4) {
3400 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1097,
3401 "Ignoring inconsistent data length -- not enough "
3402 "response info (%d).\n",
3403 le32_to_cpu(sts->rsp_data_len));
3404 } else if (sts->data[3]) {
3405 ql_dbg(ql_dbg_mbx, vha, 0x1098,
3406 "Failed to complete IOCB -- response (%x).\n",
3407 sts->data[3]);
3408 rval = QLA_FUNCTION_FAILED;
3409 }
3410 }
3411
3412 /* Issue marker IOCB. */
3413 rval2 = qla2x00_marker(vha, ha->base_qpair, fcport->loop_id, l,
3414 type == TCF_LUN_RESET ? MK_SYNC_ID_LUN : MK_SYNC_ID);
3415 if (rval2 != QLA_SUCCESS) {
3416 ql_dbg(ql_dbg_mbx, vha, 0x1099,
3417 "Failed to issue marker IOCB (%x).\n", rval2);
3418 } else {
3419 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x109a,
3420 "Done %s.\n", __func__);
3421 }
3422
3423 dma_pool_free(ha->s_dma_pool, tsk, tsk_dma);
3424
3425 return rval;
3426 }
3427
3428 int
qla24xx_abort_target(struct fc_port * fcport,uint64_t l,int tag)3429 qla24xx_abort_target(struct fc_port *fcport, uint64_t l, int tag)
3430 {
3431 struct qla_hw_data *ha = fcport->vha->hw;
3432
3433 if ((ql2xasynctmfenable) && IS_FWI2_CAPABLE(ha))
3434 return qla2x00_async_tm_cmd(fcport, TCF_TARGET_RESET, l, tag);
3435
3436 return __qla24xx_issue_tmf("Target", TCF_TARGET_RESET, fcport, l, tag);
3437 }
3438
3439 int
qla24xx_lun_reset(struct fc_port * fcport,uint64_t l,int tag)3440 qla24xx_lun_reset(struct fc_port *fcport, uint64_t l, int tag)
3441 {
3442 struct qla_hw_data *ha = fcport->vha->hw;
3443
3444 if ((ql2xasynctmfenable) && IS_FWI2_CAPABLE(ha))
3445 return qla2x00_async_tm_cmd(fcport, TCF_LUN_RESET, l, tag);
3446
3447 return __qla24xx_issue_tmf("Lun", TCF_LUN_RESET, fcport, l, tag);
3448 }
3449
3450 int
qla2x00_system_error(scsi_qla_host_t * vha)3451 qla2x00_system_error(scsi_qla_host_t *vha)
3452 {
3453 int rval;
3454 mbx_cmd_t mc;
3455 mbx_cmd_t *mcp = &mc;
3456 struct qla_hw_data *ha = vha->hw;
3457
3458 if (!IS_QLA23XX(ha) && !IS_FWI2_CAPABLE(ha))
3459 return QLA_FUNCTION_FAILED;
3460
3461 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x109b,
3462 "Entered %s.\n", __func__);
3463
3464 mcp->mb[0] = MBC_GEN_SYSTEM_ERROR;
3465 mcp->out_mb = MBX_0;
3466 mcp->in_mb = MBX_0;
3467 mcp->tov = 5;
3468 mcp->flags = 0;
3469 rval = qla2x00_mailbox_command(vha, mcp);
3470
3471 if (rval != QLA_SUCCESS) {
3472 ql_dbg(ql_dbg_mbx, vha, 0x109c, "Failed=%x.\n", rval);
3473 } else {
3474 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x109d,
3475 "Done %s.\n", __func__);
3476 }
3477
3478 return rval;
3479 }
3480
3481 int
qla2x00_write_serdes_word(scsi_qla_host_t * vha,uint16_t addr,uint16_t data)3482 qla2x00_write_serdes_word(scsi_qla_host_t *vha, uint16_t addr, uint16_t data)
3483 {
3484 int rval;
3485 mbx_cmd_t mc;
3486 mbx_cmd_t *mcp = &mc;
3487
3488 if (!IS_QLA25XX(vha->hw) && !IS_QLA2031(vha->hw) &&
3489 !IS_QLA27XX(vha->hw) && !IS_QLA28XX(vha->hw))
3490 return QLA_FUNCTION_FAILED;
3491
3492 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1182,
3493 "Entered %s.\n", __func__);
3494
3495 mcp->mb[0] = MBC_WRITE_SERDES;
3496 mcp->mb[1] = addr;
3497 if (IS_QLA2031(vha->hw))
3498 mcp->mb[2] = data & 0xff;
3499 else
3500 mcp->mb[2] = data;
3501
3502 mcp->mb[3] = 0;
3503 mcp->out_mb = MBX_3|MBX_2|MBX_1|MBX_0;
3504 mcp->in_mb = MBX_0;
3505 mcp->tov = MBX_TOV_SECONDS;
3506 mcp->flags = 0;
3507 rval = qla2x00_mailbox_command(vha, mcp);
3508
3509 if (rval != QLA_SUCCESS) {
3510 ql_dbg(ql_dbg_mbx, vha, 0x1183,
3511 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
3512 } else {
3513 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1184,
3514 "Done %s.\n", __func__);
3515 }
3516
3517 return rval;
3518 }
3519
3520 int
qla2x00_read_serdes_word(scsi_qla_host_t * vha,uint16_t addr,uint16_t * data)3521 qla2x00_read_serdes_word(scsi_qla_host_t *vha, uint16_t addr, uint16_t *data)
3522 {
3523 int rval;
3524 mbx_cmd_t mc;
3525 mbx_cmd_t *mcp = &mc;
3526
3527 if (!IS_QLA25XX(vha->hw) && !IS_QLA2031(vha->hw) &&
3528 !IS_QLA27XX(vha->hw) && !IS_QLA28XX(vha->hw))
3529 return QLA_FUNCTION_FAILED;
3530
3531 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1185,
3532 "Entered %s.\n", __func__);
3533
3534 mcp->mb[0] = MBC_READ_SERDES;
3535 mcp->mb[1] = addr;
3536 mcp->mb[3] = 0;
3537 mcp->out_mb = MBX_3|MBX_1|MBX_0;
3538 mcp->in_mb = MBX_1|MBX_0;
3539 mcp->tov = MBX_TOV_SECONDS;
3540 mcp->flags = 0;
3541 rval = qla2x00_mailbox_command(vha, mcp);
3542
3543 if (IS_QLA2031(vha->hw))
3544 *data = mcp->mb[1] & 0xff;
3545 else
3546 *data = mcp->mb[1];
3547
3548 if (rval != QLA_SUCCESS) {
3549 ql_dbg(ql_dbg_mbx, vha, 0x1186,
3550 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
3551 } else {
3552 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1187,
3553 "Done %s.\n", __func__);
3554 }
3555
3556 return rval;
3557 }
3558
3559 int
qla8044_write_serdes_word(scsi_qla_host_t * vha,uint32_t addr,uint32_t data)3560 qla8044_write_serdes_word(scsi_qla_host_t *vha, uint32_t addr, uint32_t data)
3561 {
3562 int rval;
3563 mbx_cmd_t mc;
3564 mbx_cmd_t *mcp = &mc;
3565
3566 if (!IS_QLA8044(vha->hw))
3567 return QLA_FUNCTION_FAILED;
3568
3569 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x11a0,
3570 "Entered %s.\n", __func__);
3571
3572 mcp->mb[0] = MBC_SET_GET_ETH_SERDES_REG;
3573 mcp->mb[1] = HCS_WRITE_SERDES;
3574 mcp->mb[3] = LSW(addr);
3575 mcp->mb[4] = MSW(addr);
3576 mcp->mb[5] = LSW(data);
3577 mcp->mb[6] = MSW(data);
3578 mcp->out_mb = MBX_6|MBX_5|MBX_4|MBX_3|MBX_1|MBX_0;
3579 mcp->in_mb = MBX_0;
3580 mcp->tov = MBX_TOV_SECONDS;
3581 mcp->flags = 0;
3582 rval = qla2x00_mailbox_command(vha, mcp);
3583
3584 if (rval != QLA_SUCCESS) {
3585 ql_dbg(ql_dbg_mbx, vha, 0x11a1,
3586 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
3587 } else {
3588 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1188,
3589 "Done %s.\n", __func__);
3590 }
3591
3592 return rval;
3593 }
3594
3595 int
qla8044_read_serdes_word(scsi_qla_host_t * vha,uint32_t addr,uint32_t * data)3596 qla8044_read_serdes_word(scsi_qla_host_t *vha, uint32_t addr, uint32_t *data)
3597 {
3598 int rval;
3599 mbx_cmd_t mc;
3600 mbx_cmd_t *mcp = &mc;
3601
3602 if (!IS_QLA8044(vha->hw))
3603 return QLA_FUNCTION_FAILED;
3604
3605 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1189,
3606 "Entered %s.\n", __func__);
3607
3608 mcp->mb[0] = MBC_SET_GET_ETH_SERDES_REG;
3609 mcp->mb[1] = HCS_READ_SERDES;
3610 mcp->mb[3] = LSW(addr);
3611 mcp->mb[4] = MSW(addr);
3612 mcp->out_mb = MBX_4|MBX_3|MBX_1|MBX_0;
3613 mcp->in_mb = MBX_2|MBX_1|MBX_0;
3614 mcp->tov = MBX_TOV_SECONDS;
3615 mcp->flags = 0;
3616 rval = qla2x00_mailbox_command(vha, mcp);
3617
3618 *data = mcp->mb[2] << 16 | mcp->mb[1];
3619
3620 if (rval != QLA_SUCCESS) {
3621 ql_dbg(ql_dbg_mbx, vha, 0x118a,
3622 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
3623 } else {
3624 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x118b,
3625 "Done %s.\n", __func__);
3626 }
3627
3628 return rval;
3629 }
3630
3631 /**
3632 * qla2x00_set_serdes_params() -
3633 * @vha: HA context
3634 * @sw_em_1g: serial link options
3635 * @sw_em_2g: serial link options
3636 * @sw_em_4g: serial link options
3637 *
3638 * Returns
3639 */
3640 int
qla2x00_set_serdes_params(scsi_qla_host_t * vha,uint16_t sw_em_1g,uint16_t sw_em_2g,uint16_t sw_em_4g)3641 qla2x00_set_serdes_params(scsi_qla_host_t *vha, uint16_t sw_em_1g,
3642 uint16_t sw_em_2g, uint16_t sw_em_4g)
3643 {
3644 int rval;
3645 mbx_cmd_t mc;
3646 mbx_cmd_t *mcp = &mc;
3647
3648 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x109e,
3649 "Entered %s.\n", __func__);
3650
3651 mcp->mb[0] = MBC_SERDES_PARAMS;
3652 mcp->mb[1] = BIT_0;
3653 mcp->mb[2] = sw_em_1g | BIT_15;
3654 mcp->mb[3] = sw_em_2g | BIT_15;
3655 mcp->mb[4] = sw_em_4g | BIT_15;
3656 mcp->out_mb = MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
3657 mcp->in_mb = MBX_0;
3658 mcp->tov = MBX_TOV_SECONDS;
3659 mcp->flags = 0;
3660 rval = qla2x00_mailbox_command(vha, mcp);
3661
3662 if (rval != QLA_SUCCESS) {
3663 /*EMPTY*/
3664 ql_dbg(ql_dbg_mbx, vha, 0x109f,
3665 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
3666 } else {
3667 /*EMPTY*/
3668 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10a0,
3669 "Done %s.\n", __func__);
3670 }
3671
3672 return rval;
3673 }
3674
3675 int
qla2x00_stop_firmware(scsi_qla_host_t * vha)3676 qla2x00_stop_firmware(scsi_qla_host_t *vha)
3677 {
3678 int rval;
3679 mbx_cmd_t mc;
3680 mbx_cmd_t *mcp = &mc;
3681
3682 if (!IS_FWI2_CAPABLE(vha->hw))
3683 return QLA_FUNCTION_FAILED;
3684
3685 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10a1,
3686 "Entered %s.\n", __func__);
3687
3688 mcp->mb[0] = MBC_STOP_FIRMWARE;
3689 mcp->mb[1] = 0;
3690 mcp->out_mb = MBX_1|MBX_0;
3691 mcp->in_mb = MBX_0;
3692 mcp->tov = 5;
3693 mcp->flags = 0;
3694 rval = qla2x00_mailbox_command(vha, mcp);
3695
3696 if (rval != QLA_SUCCESS) {
3697 ql_dbg(ql_dbg_mbx, vha, 0x10a2, "Failed=%x.\n", rval);
3698 if (mcp->mb[0] == MBS_INVALID_COMMAND)
3699 rval = QLA_INVALID_COMMAND;
3700 } else {
3701 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10a3,
3702 "Done %s.\n", __func__);
3703 }
3704
3705 return rval;
3706 }
3707
3708 int
qla2x00_enable_eft_trace(scsi_qla_host_t * vha,dma_addr_t eft_dma,uint16_t buffers)3709 qla2x00_enable_eft_trace(scsi_qla_host_t *vha, dma_addr_t eft_dma,
3710 uint16_t buffers)
3711 {
3712 int rval;
3713 mbx_cmd_t mc;
3714 mbx_cmd_t *mcp = &mc;
3715
3716 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10a4,
3717 "Entered %s.\n", __func__);
3718
3719 if (!IS_FWI2_CAPABLE(vha->hw))
3720 return QLA_FUNCTION_FAILED;
3721
3722 if (unlikely(pci_channel_offline(vha->hw->pdev)))
3723 return QLA_FUNCTION_FAILED;
3724
3725 mcp->mb[0] = MBC_TRACE_CONTROL;
3726 mcp->mb[1] = TC_EFT_ENABLE;
3727 mcp->mb[2] = LSW(eft_dma);
3728 mcp->mb[3] = MSW(eft_dma);
3729 mcp->mb[4] = LSW(MSD(eft_dma));
3730 mcp->mb[5] = MSW(MSD(eft_dma));
3731 mcp->mb[6] = buffers;
3732 mcp->mb[7] = TC_AEN_DISABLE;
3733 mcp->out_mb = MBX_7|MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
3734 mcp->in_mb = MBX_1|MBX_0;
3735 mcp->tov = MBX_TOV_SECONDS;
3736 mcp->flags = 0;
3737 rval = qla2x00_mailbox_command(vha, mcp);
3738 if (rval != QLA_SUCCESS) {
3739 ql_dbg(ql_dbg_mbx, vha, 0x10a5,
3740 "Failed=%x mb[0]=%x mb[1]=%x.\n",
3741 rval, mcp->mb[0], mcp->mb[1]);
3742 } else {
3743 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10a6,
3744 "Done %s.\n", __func__);
3745 }
3746
3747 return rval;
3748 }
3749
3750 int
qla2x00_disable_eft_trace(scsi_qla_host_t * vha)3751 qla2x00_disable_eft_trace(scsi_qla_host_t *vha)
3752 {
3753 int rval;
3754 mbx_cmd_t mc;
3755 mbx_cmd_t *mcp = &mc;
3756
3757 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10a7,
3758 "Entered %s.\n", __func__);
3759
3760 if (!IS_FWI2_CAPABLE(vha->hw))
3761 return QLA_FUNCTION_FAILED;
3762
3763 if (unlikely(pci_channel_offline(vha->hw->pdev)))
3764 return QLA_FUNCTION_FAILED;
3765
3766 mcp->mb[0] = MBC_TRACE_CONTROL;
3767 mcp->mb[1] = TC_EFT_DISABLE;
3768 mcp->out_mb = MBX_1|MBX_0;
3769 mcp->in_mb = MBX_1|MBX_0;
3770 mcp->tov = MBX_TOV_SECONDS;
3771 mcp->flags = 0;
3772 rval = qla2x00_mailbox_command(vha, mcp);
3773 if (rval != QLA_SUCCESS) {
3774 ql_dbg(ql_dbg_mbx, vha, 0x10a8,
3775 "Failed=%x mb[0]=%x mb[1]=%x.\n",
3776 rval, mcp->mb[0], mcp->mb[1]);
3777 } else {
3778 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10a9,
3779 "Done %s.\n", __func__);
3780 }
3781
3782 return rval;
3783 }
3784
3785 int
qla2x00_enable_fce_trace(scsi_qla_host_t * vha,dma_addr_t fce_dma,uint16_t buffers,uint16_t * mb,uint32_t * dwords)3786 qla2x00_enable_fce_trace(scsi_qla_host_t *vha, dma_addr_t fce_dma,
3787 uint16_t buffers, uint16_t *mb, uint32_t *dwords)
3788 {
3789 int rval;
3790 mbx_cmd_t mc;
3791 mbx_cmd_t *mcp = &mc;
3792
3793 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10aa,
3794 "Entered %s.\n", __func__);
3795
3796 if (!IS_QLA25XX(vha->hw) && !IS_QLA81XX(vha->hw) &&
3797 !IS_QLA83XX(vha->hw) && !IS_QLA27XX(vha->hw) &&
3798 !IS_QLA28XX(vha->hw))
3799 return QLA_FUNCTION_FAILED;
3800
3801 if (unlikely(pci_channel_offline(vha->hw->pdev)))
3802 return QLA_FUNCTION_FAILED;
3803
3804 mcp->mb[0] = MBC_TRACE_CONTROL;
3805 mcp->mb[1] = TC_FCE_ENABLE;
3806 mcp->mb[2] = LSW(fce_dma);
3807 mcp->mb[3] = MSW(fce_dma);
3808 mcp->mb[4] = LSW(MSD(fce_dma));
3809 mcp->mb[5] = MSW(MSD(fce_dma));
3810 mcp->mb[6] = buffers;
3811 mcp->mb[7] = TC_AEN_DISABLE;
3812 mcp->mb[8] = 0;
3813 mcp->mb[9] = TC_FCE_DEFAULT_RX_SIZE;
3814 mcp->mb[10] = TC_FCE_DEFAULT_TX_SIZE;
3815 mcp->out_mb = MBX_10|MBX_9|MBX_8|MBX_7|MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|
3816 MBX_1|MBX_0;
3817 mcp->in_mb = MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
3818 mcp->tov = MBX_TOV_SECONDS;
3819 mcp->flags = 0;
3820 rval = qla2x00_mailbox_command(vha, mcp);
3821 if (rval != QLA_SUCCESS) {
3822 ql_dbg(ql_dbg_mbx, vha, 0x10ab,
3823 "Failed=%x mb[0]=%x mb[1]=%x.\n",
3824 rval, mcp->mb[0], mcp->mb[1]);
3825 } else {
3826 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10ac,
3827 "Done %s.\n", __func__);
3828
3829 if (mb)
3830 memcpy(mb, mcp->mb, 8 * sizeof(*mb));
3831 if (dwords)
3832 *dwords = buffers;
3833 }
3834
3835 return rval;
3836 }
3837
3838 int
qla2x00_disable_fce_trace(scsi_qla_host_t * vha,uint64_t * wr,uint64_t * rd)3839 qla2x00_disable_fce_trace(scsi_qla_host_t *vha, uint64_t *wr, uint64_t *rd)
3840 {
3841 int rval;
3842 mbx_cmd_t mc;
3843 mbx_cmd_t *mcp = &mc;
3844
3845 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10ad,
3846 "Entered %s.\n", __func__);
3847
3848 if (!IS_FWI2_CAPABLE(vha->hw))
3849 return QLA_FUNCTION_FAILED;
3850
3851 if (unlikely(pci_channel_offline(vha->hw->pdev)))
3852 return QLA_FUNCTION_FAILED;
3853
3854 mcp->mb[0] = MBC_TRACE_CONTROL;
3855 mcp->mb[1] = TC_FCE_DISABLE;
3856 mcp->mb[2] = TC_FCE_DISABLE_TRACE;
3857 mcp->out_mb = MBX_2|MBX_1|MBX_0;
3858 mcp->in_mb = MBX_9|MBX_8|MBX_7|MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|
3859 MBX_1|MBX_0;
3860 mcp->tov = MBX_TOV_SECONDS;
3861 mcp->flags = 0;
3862 rval = qla2x00_mailbox_command(vha, mcp);
3863 if (rval != QLA_SUCCESS) {
3864 ql_dbg(ql_dbg_mbx, vha, 0x10ae,
3865 "Failed=%x mb[0]=%x mb[1]=%x.\n",
3866 rval, mcp->mb[0], mcp->mb[1]);
3867 } else {
3868 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10af,
3869 "Done %s.\n", __func__);
3870
3871 if (wr)
3872 *wr = (uint64_t) mcp->mb[5] << 48 |
3873 (uint64_t) mcp->mb[4] << 32 |
3874 (uint64_t) mcp->mb[3] << 16 |
3875 (uint64_t) mcp->mb[2];
3876 if (rd)
3877 *rd = (uint64_t) mcp->mb[9] << 48 |
3878 (uint64_t) mcp->mb[8] << 32 |
3879 (uint64_t) mcp->mb[7] << 16 |
3880 (uint64_t) mcp->mb[6];
3881 }
3882
3883 return rval;
3884 }
3885
3886 int
qla2x00_get_idma_speed(scsi_qla_host_t * vha,uint16_t loop_id,uint16_t * port_speed,uint16_t * mb)3887 qla2x00_get_idma_speed(scsi_qla_host_t *vha, uint16_t loop_id,
3888 uint16_t *port_speed, uint16_t *mb)
3889 {
3890 int rval;
3891 mbx_cmd_t mc;
3892 mbx_cmd_t *mcp = &mc;
3893
3894 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10b0,
3895 "Entered %s.\n", __func__);
3896
3897 if (!IS_IIDMA_CAPABLE(vha->hw))
3898 return QLA_FUNCTION_FAILED;
3899
3900 mcp->mb[0] = MBC_PORT_PARAMS;
3901 mcp->mb[1] = loop_id;
3902 mcp->mb[2] = mcp->mb[3] = 0;
3903 mcp->mb[9] = vha->vp_idx;
3904 mcp->out_mb = MBX_9|MBX_3|MBX_2|MBX_1|MBX_0;
3905 mcp->in_mb = MBX_3|MBX_1|MBX_0;
3906 mcp->tov = MBX_TOV_SECONDS;
3907 mcp->flags = 0;
3908 rval = qla2x00_mailbox_command(vha, mcp);
3909
3910 /* Return mailbox statuses. */
3911 if (mb) {
3912 mb[0] = mcp->mb[0];
3913 mb[1] = mcp->mb[1];
3914 mb[3] = mcp->mb[3];
3915 }
3916
3917 if (rval != QLA_SUCCESS) {
3918 ql_dbg(ql_dbg_mbx, vha, 0x10b1, "Failed=%x.\n", rval);
3919 } else {
3920 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10b2,
3921 "Done %s.\n", __func__);
3922 if (port_speed)
3923 *port_speed = mcp->mb[3];
3924 }
3925
3926 return rval;
3927 }
3928
3929 int
qla2x00_set_idma_speed(scsi_qla_host_t * vha,uint16_t loop_id,uint16_t port_speed,uint16_t * mb)3930 qla2x00_set_idma_speed(scsi_qla_host_t *vha, uint16_t loop_id,
3931 uint16_t port_speed, uint16_t *mb)
3932 {
3933 int rval;
3934 mbx_cmd_t mc;
3935 mbx_cmd_t *mcp = &mc;
3936
3937 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10b3,
3938 "Entered %s.\n", __func__);
3939
3940 if (!IS_IIDMA_CAPABLE(vha->hw))
3941 return QLA_FUNCTION_FAILED;
3942
3943 mcp->mb[0] = MBC_PORT_PARAMS;
3944 mcp->mb[1] = loop_id;
3945 mcp->mb[2] = BIT_0;
3946 mcp->mb[3] = port_speed & 0x3F;
3947 mcp->mb[9] = vha->vp_idx;
3948 mcp->out_mb = MBX_9|MBX_3|MBX_2|MBX_1|MBX_0;
3949 mcp->in_mb = MBX_3|MBX_1|MBX_0;
3950 mcp->tov = MBX_TOV_SECONDS;
3951 mcp->flags = 0;
3952 rval = qla2x00_mailbox_command(vha, mcp);
3953
3954 /* Return mailbox statuses. */
3955 if (mb) {
3956 mb[0] = mcp->mb[0];
3957 mb[1] = mcp->mb[1];
3958 mb[3] = mcp->mb[3];
3959 }
3960
3961 if (rval != QLA_SUCCESS) {
3962 ql_dbg(ql_dbg_mbx, vha, 0x10b4,
3963 "Failed=%x.\n", rval);
3964 } else {
3965 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10b5,
3966 "Done %s.\n", __func__);
3967 }
3968
3969 return rval;
3970 }
3971
3972 void
qla24xx_report_id_acquisition(scsi_qla_host_t * vha,struct vp_rpt_id_entry_24xx * rptid_entry)3973 qla24xx_report_id_acquisition(scsi_qla_host_t *vha,
3974 struct vp_rpt_id_entry_24xx *rptid_entry)
3975 {
3976 struct qla_hw_data *ha = vha->hw;
3977 scsi_qla_host_t *vp = NULL;
3978 unsigned long flags;
3979 int found;
3980 port_id_t id;
3981 struct fc_port *fcport;
3982
3983 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10b6,
3984 "Entered %s.\n", __func__);
3985
3986 if (rptid_entry->entry_status != 0)
3987 return;
3988
3989 id.b.domain = rptid_entry->port_id[2];
3990 id.b.area = rptid_entry->port_id[1];
3991 id.b.al_pa = rptid_entry->port_id[0];
3992 id.b.rsvd_1 = 0;
3993 ha->flags.n2n_ae = 0;
3994
3995 if (rptid_entry->format == 0) {
3996 /* loop */
3997 ql_dbg(ql_dbg_async, vha, 0x10b7,
3998 "Format 0 : Number of VPs setup %d, number of "
3999 "VPs acquired %d.\n", rptid_entry->vp_setup,
4000 rptid_entry->vp_acquired);
4001 ql_dbg(ql_dbg_async, vha, 0x10b8,
4002 "Primary port id %02x%02x%02x.\n",
4003 rptid_entry->port_id[2], rptid_entry->port_id[1],
4004 rptid_entry->port_id[0]);
4005 ha->current_topology = ISP_CFG_NL;
4006 qlt_update_host_map(vha, id);
4007
4008 } else if (rptid_entry->format == 1) {
4009 /* fabric */
4010 ql_dbg(ql_dbg_async, vha, 0x10b9,
4011 "Format 1: VP[%d] enabled - status %d - with "
4012 "port id %02x%02x%02x.\n", rptid_entry->vp_idx,
4013 rptid_entry->vp_status,
4014 rptid_entry->port_id[2], rptid_entry->port_id[1],
4015 rptid_entry->port_id[0]);
4016 ql_dbg(ql_dbg_async, vha, 0x5075,
4017 "Format 1: Remote WWPN %8phC.\n",
4018 rptid_entry->u.f1.port_name);
4019
4020 ql_dbg(ql_dbg_async, vha, 0x5075,
4021 "Format 1: WWPN %8phC.\n",
4022 vha->port_name);
4023
4024 switch (rptid_entry->u.f1.flags & TOPO_MASK) {
4025 case TOPO_N2N:
4026 ha->current_topology = ISP_CFG_N;
4027 spin_lock_irqsave(&vha->hw->tgt.sess_lock, flags);
4028 list_for_each_entry(fcport, &vha->vp_fcports, list) {
4029 fcport->scan_state = QLA_FCPORT_SCAN;
4030 fcport->n2n_flag = 0;
4031 }
4032 id.b24 = 0;
4033 if (wwn_to_u64(vha->port_name) >
4034 wwn_to_u64(rptid_entry->u.f1.port_name)) {
4035 vha->d_id.b24 = 0;
4036 vha->d_id.b.al_pa = 1;
4037 ha->flags.n2n_bigger = 1;
4038
4039 id.b.al_pa = 2;
4040 ql_dbg(ql_dbg_async, vha, 0x5075,
4041 "Format 1: assign local id %x remote id %x\n",
4042 vha->d_id.b24, id.b24);
4043 } else {
4044 ql_dbg(ql_dbg_async, vha, 0x5075,
4045 "Format 1: Remote login - Waiting for WWPN %8phC.\n",
4046 rptid_entry->u.f1.port_name);
4047 ha->flags.n2n_bigger = 0;
4048 }
4049
4050 fcport = qla2x00_find_fcport_by_wwpn(vha,
4051 rptid_entry->u.f1.port_name, 1);
4052 spin_unlock_irqrestore(&vha->hw->tgt.sess_lock, flags);
4053
4054
4055 if (fcport) {
4056 fcport->plogi_nack_done_deadline = jiffies + HZ;
4057 fcport->dm_login_expire = jiffies +
4058 QLA_N2N_WAIT_TIME * HZ;
4059 fcport->scan_state = QLA_FCPORT_FOUND;
4060 fcport->n2n_flag = 1;
4061 fcport->keep_nport_handle = 1;
4062 fcport->login_retry = vha->hw->login_retry_count;
4063 fcport->fc4_type = FS_FC4TYPE_FCP;
4064 if (vha->flags.nvme_enabled)
4065 fcport->fc4_type |= FS_FC4TYPE_NVME;
4066
4067 if (wwn_to_u64(vha->port_name) >
4068 wwn_to_u64(fcport->port_name)) {
4069 fcport->d_id = id;
4070 }
4071
4072 switch (fcport->disc_state) {
4073 case DSC_DELETED:
4074 set_bit(RELOGIN_NEEDED,
4075 &vha->dpc_flags);
4076 break;
4077 case DSC_DELETE_PEND:
4078 break;
4079 default:
4080 qlt_schedule_sess_for_deletion(fcport);
4081 break;
4082 }
4083 } else {
4084 qla24xx_post_newsess_work(vha, &id,
4085 rptid_entry->u.f1.port_name,
4086 rptid_entry->u.f1.node_name,
4087 NULL,
4088 FS_FCP_IS_N2N);
4089 }
4090
4091 /* if our portname is higher then initiate N2N login */
4092
4093 set_bit(N2N_LOGIN_NEEDED, &vha->dpc_flags);
4094 return;
4095 case TOPO_FL:
4096 ha->current_topology = ISP_CFG_FL;
4097 break;
4098 case TOPO_F:
4099 ha->current_topology = ISP_CFG_F;
4100 break;
4101 default:
4102 break;
4103 }
4104
4105 ha->flags.gpsc_supported = 1;
4106 ha->current_topology = ISP_CFG_F;
4107 /* buffer to buffer credit flag */
4108 vha->flags.bbcr_enable = (rptid_entry->u.f1.bbcr & 0xf) != 0;
4109
4110 if (rptid_entry->vp_idx == 0) {
4111 if (rptid_entry->vp_status == VP_STAT_COMPL) {
4112 /* FA-WWN is only for physical port */
4113 if (qla_ini_mode_enabled(vha) &&
4114 ha->flags.fawwpn_enabled &&
4115 (rptid_entry->u.f1.flags &
4116 BIT_6)) {
4117 memcpy(vha->port_name,
4118 rptid_entry->u.f1.port_name,
4119 WWN_SIZE);
4120 }
4121
4122 qlt_update_host_map(vha, id);
4123 }
4124
4125 set_bit(REGISTER_FC4_NEEDED, &vha->dpc_flags);
4126 set_bit(REGISTER_FDMI_NEEDED, &vha->dpc_flags);
4127 } else {
4128 if (rptid_entry->vp_status != VP_STAT_COMPL &&
4129 rptid_entry->vp_status != VP_STAT_ID_CHG) {
4130 ql_dbg(ql_dbg_mbx, vha, 0x10ba,
4131 "Could not acquire ID for VP[%d].\n",
4132 rptid_entry->vp_idx);
4133 return;
4134 }
4135
4136 found = 0;
4137 spin_lock_irqsave(&ha->vport_slock, flags);
4138 list_for_each_entry(vp, &ha->vp_list, list) {
4139 if (rptid_entry->vp_idx == vp->vp_idx) {
4140 found = 1;
4141 break;
4142 }
4143 }
4144 spin_unlock_irqrestore(&ha->vport_slock, flags);
4145
4146 if (!found)
4147 return;
4148
4149 qlt_update_host_map(vp, id);
4150
4151 /*
4152 * Cannot configure here as we are still sitting on the
4153 * response queue. Handle it in dpc context.
4154 */
4155 set_bit(VP_IDX_ACQUIRED, &vp->vp_flags);
4156 set_bit(REGISTER_FC4_NEEDED, &vp->dpc_flags);
4157 set_bit(REGISTER_FDMI_NEEDED, &vp->dpc_flags);
4158 }
4159 set_bit(VP_DPC_NEEDED, &vha->dpc_flags);
4160 qla2xxx_wake_dpc(vha);
4161 } else if (rptid_entry->format == 2) {
4162 ql_dbg(ql_dbg_async, vha, 0x505f,
4163 "RIDA: format 2/N2N Primary port id %02x%02x%02x.\n",
4164 rptid_entry->port_id[2], rptid_entry->port_id[1],
4165 rptid_entry->port_id[0]);
4166
4167 ql_dbg(ql_dbg_async, vha, 0x5075,
4168 "N2N: Remote WWPN %8phC.\n",
4169 rptid_entry->u.f2.port_name);
4170
4171 /* N2N. direct connect */
4172 ha->current_topology = ISP_CFG_N;
4173 ha->flags.rida_fmt2 = 1;
4174 vha->d_id.b.domain = rptid_entry->port_id[2];
4175 vha->d_id.b.area = rptid_entry->port_id[1];
4176 vha->d_id.b.al_pa = rptid_entry->port_id[0];
4177
4178 ha->flags.n2n_ae = 1;
4179 spin_lock_irqsave(&ha->vport_slock, flags);
4180 qlt_update_vp_map(vha, SET_AL_PA);
4181 spin_unlock_irqrestore(&ha->vport_slock, flags);
4182
4183 list_for_each_entry(fcport, &vha->vp_fcports, list) {
4184 fcport->scan_state = QLA_FCPORT_SCAN;
4185 fcport->n2n_flag = 0;
4186 }
4187
4188 fcport = qla2x00_find_fcport_by_wwpn(vha,
4189 rptid_entry->u.f2.port_name, 1);
4190
4191 if (fcport) {
4192 fcport->login_retry = vha->hw->login_retry_count;
4193 fcport->plogi_nack_done_deadline = jiffies + HZ;
4194 fcport->scan_state = QLA_FCPORT_FOUND;
4195 fcport->keep_nport_handle = 1;
4196 fcport->n2n_flag = 1;
4197 fcport->d_id.b.domain =
4198 rptid_entry->u.f2.remote_nport_id[2];
4199 fcport->d_id.b.area =
4200 rptid_entry->u.f2.remote_nport_id[1];
4201 fcport->d_id.b.al_pa =
4202 rptid_entry->u.f2.remote_nport_id[0];
4203
4204 /*
4205 * For the case where remote port sending PRLO, FW
4206 * sends up RIDA Format 2 as an indication of session
4207 * loss. In other word, FW state change from PRLI
4208 * complete back to PLOGI complete. Delete the
4209 * session and let relogin drive the reconnect.
4210 */
4211 if (atomic_read(&fcport->state) == FCS_ONLINE)
4212 qlt_schedule_sess_for_deletion(fcport);
4213 }
4214 }
4215 }
4216
4217 /*
4218 * qla24xx_modify_vp_config
4219 * Change VP configuration for vha
4220 *
4221 * Input:
4222 * vha = adapter block pointer.
4223 *
4224 * Returns:
4225 * qla2xxx local function return status code.
4226 *
4227 * Context:
4228 * Kernel context.
4229 */
4230 int
qla24xx_modify_vp_config(scsi_qla_host_t * vha)4231 qla24xx_modify_vp_config(scsi_qla_host_t *vha)
4232 {
4233 int rval;
4234 struct vp_config_entry_24xx *vpmod;
4235 dma_addr_t vpmod_dma;
4236 struct qla_hw_data *ha = vha->hw;
4237 struct scsi_qla_host *base_vha = pci_get_drvdata(ha->pdev);
4238
4239 /* This can be called by the parent */
4240
4241 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10bb,
4242 "Entered %s.\n", __func__);
4243
4244 vpmod = dma_pool_zalloc(ha->s_dma_pool, GFP_KERNEL, &vpmod_dma);
4245 if (!vpmod) {
4246 ql_log(ql_log_warn, vha, 0x10bc,
4247 "Failed to allocate modify VP IOCB.\n");
4248 return QLA_MEMORY_ALLOC_FAILED;
4249 }
4250
4251 vpmod->entry_type = VP_CONFIG_IOCB_TYPE;
4252 vpmod->entry_count = 1;
4253 vpmod->command = VCT_COMMAND_MOD_ENABLE_VPS;
4254 vpmod->vp_count = 1;
4255 vpmod->vp_index1 = vha->vp_idx;
4256 vpmod->options_idx1 = BIT_3|BIT_4|BIT_5;
4257
4258 qlt_modify_vp_config(vha, vpmod);
4259
4260 memcpy(vpmod->node_name_idx1, vha->node_name, WWN_SIZE);
4261 memcpy(vpmod->port_name_idx1, vha->port_name, WWN_SIZE);
4262 vpmod->entry_count = 1;
4263
4264 rval = qla2x00_issue_iocb(base_vha, vpmod, vpmod_dma, 0);
4265 if (rval != QLA_SUCCESS) {
4266 ql_dbg(ql_dbg_mbx, vha, 0x10bd,
4267 "Failed to issue VP config IOCB (%x).\n", rval);
4268 } else if (vpmod->comp_status != 0) {
4269 ql_dbg(ql_dbg_mbx, vha, 0x10be,
4270 "Failed to complete IOCB -- error status (%x).\n",
4271 vpmod->comp_status);
4272 rval = QLA_FUNCTION_FAILED;
4273 } else if (vpmod->comp_status != cpu_to_le16(CS_COMPLETE)) {
4274 ql_dbg(ql_dbg_mbx, vha, 0x10bf,
4275 "Failed to complete IOCB -- completion status (%x).\n",
4276 le16_to_cpu(vpmod->comp_status));
4277 rval = QLA_FUNCTION_FAILED;
4278 } else {
4279 /* EMPTY */
4280 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10c0,
4281 "Done %s.\n", __func__);
4282 fc_vport_set_state(vha->fc_vport, FC_VPORT_INITIALIZING);
4283 }
4284 dma_pool_free(ha->s_dma_pool, vpmod, vpmod_dma);
4285
4286 return rval;
4287 }
4288
4289 /*
4290 * qla2x00_send_change_request
4291 * Receive or disable RSCN request from fabric controller
4292 *
4293 * Input:
4294 * ha = adapter block pointer
4295 * format = registration format:
4296 * 0 - Reserved
4297 * 1 - Fabric detected registration
4298 * 2 - N_port detected registration
4299 * 3 - Full registration
4300 * FF - clear registration
4301 * vp_idx = Virtual port index
4302 *
4303 * Returns:
4304 * qla2x00 local function return status code.
4305 *
4306 * Context:
4307 * Kernel Context
4308 */
4309
4310 int
qla2x00_send_change_request(scsi_qla_host_t * vha,uint16_t format,uint16_t vp_idx)4311 qla2x00_send_change_request(scsi_qla_host_t *vha, uint16_t format,
4312 uint16_t vp_idx)
4313 {
4314 int rval;
4315 mbx_cmd_t mc;
4316 mbx_cmd_t *mcp = &mc;
4317
4318 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10c7,
4319 "Entered %s.\n", __func__);
4320
4321 mcp->mb[0] = MBC_SEND_CHANGE_REQUEST;
4322 mcp->mb[1] = format;
4323 mcp->mb[9] = vp_idx;
4324 mcp->out_mb = MBX_9|MBX_1|MBX_0;
4325 mcp->in_mb = MBX_0|MBX_1;
4326 mcp->tov = MBX_TOV_SECONDS;
4327 mcp->flags = 0;
4328 rval = qla2x00_mailbox_command(vha, mcp);
4329
4330 if (rval == QLA_SUCCESS) {
4331 if (mcp->mb[0] != MBS_COMMAND_COMPLETE) {
4332 rval = BIT_1;
4333 }
4334 } else
4335 rval = BIT_1;
4336
4337 return rval;
4338 }
4339
4340 int
qla2x00_dump_ram(scsi_qla_host_t * vha,dma_addr_t req_dma,uint32_t addr,uint32_t size)4341 qla2x00_dump_ram(scsi_qla_host_t *vha, dma_addr_t req_dma, uint32_t addr,
4342 uint32_t size)
4343 {
4344 int rval;
4345 mbx_cmd_t mc;
4346 mbx_cmd_t *mcp = &mc;
4347
4348 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1009,
4349 "Entered %s.\n", __func__);
4350
4351 if (MSW(addr) || IS_FWI2_CAPABLE(vha->hw)) {
4352 mcp->mb[0] = MBC_DUMP_RISC_RAM_EXTENDED;
4353 mcp->mb[8] = MSW(addr);
4354 mcp->mb[10] = 0;
4355 mcp->out_mb = MBX_10|MBX_8|MBX_0;
4356 } else {
4357 mcp->mb[0] = MBC_DUMP_RISC_RAM;
4358 mcp->out_mb = MBX_0;
4359 }
4360 mcp->mb[1] = LSW(addr);
4361 mcp->mb[2] = MSW(req_dma);
4362 mcp->mb[3] = LSW(req_dma);
4363 mcp->mb[6] = MSW(MSD(req_dma));
4364 mcp->mb[7] = LSW(MSD(req_dma));
4365 mcp->out_mb |= MBX_7|MBX_6|MBX_3|MBX_2|MBX_1;
4366 if (IS_FWI2_CAPABLE(vha->hw)) {
4367 mcp->mb[4] = MSW(size);
4368 mcp->mb[5] = LSW(size);
4369 mcp->out_mb |= MBX_5|MBX_4;
4370 } else {
4371 mcp->mb[4] = LSW(size);
4372 mcp->out_mb |= MBX_4;
4373 }
4374
4375 mcp->in_mb = MBX_0;
4376 mcp->tov = MBX_TOV_SECONDS;
4377 mcp->flags = 0;
4378 rval = qla2x00_mailbox_command(vha, mcp);
4379
4380 if (rval != QLA_SUCCESS) {
4381 ql_dbg(ql_dbg_mbx, vha, 0x1008,
4382 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
4383 } else {
4384 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1007,
4385 "Done %s.\n", __func__);
4386 }
4387
4388 return rval;
4389 }
4390 /* 84XX Support **************************************************************/
4391
4392 struct cs84xx_mgmt_cmd {
4393 union {
4394 struct verify_chip_entry_84xx req;
4395 struct verify_chip_rsp_84xx rsp;
4396 } p;
4397 };
4398
4399 int
qla84xx_verify_chip(struct scsi_qla_host * vha,uint16_t * status)4400 qla84xx_verify_chip(struct scsi_qla_host *vha, uint16_t *status)
4401 {
4402 int rval, retry;
4403 struct cs84xx_mgmt_cmd *mn;
4404 dma_addr_t mn_dma;
4405 uint16_t options;
4406 unsigned long flags;
4407 struct qla_hw_data *ha = vha->hw;
4408
4409 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10c8,
4410 "Entered %s.\n", __func__);
4411
4412 mn = dma_pool_alloc(ha->s_dma_pool, GFP_KERNEL, &mn_dma);
4413 if (mn == NULL) {
4414 return QLA_MEMORY_ALLOC_FAILED;
4415 }
4416
4417 /* Force Update? */
4418 options = ha->cs84xx->fw_update ? VCO_FORCE_UPDATE : 0;
4419 /* Diagnostic firmware? */
4420 /* options |= MENLO_DIAG_FW; */
4421 /* We update the firmware with only one data sequence. */
4422 options |= VCO_END_OF_DATA;
4423
4424 do {
4425 retry = 0;
4426 memset(mn, 0, sizeof(*mn));
4427 mn->p.req.entry_type = VERIFY_CHIP_IOCB_TYPE;
4428 mn->p.req.entry_count = 1;
4429 mn->p.req.options = cpu_to_le16(options);
4430
4431 ql_dbg(ql_dbg_mbx + ql_dbg_buffer, vha, 0x111c,
4432 "Dump of Verify Request.\n");
4433 ql_dump_buffer(ql_dbg_mbx + ql_dbg_buffer, vha, 0x111e,
4434 mn, sizeof(*mn));
4435
4436 rval = qla2x00_issue_iocb_timeout(vha, mn, mn_dma, 0, 120);
4437 if (rval != QLA_SUCCESS) {
4438 ql_dbg(ql_dbg_mbx, vha, 0x10cb,
4439 "Failed to issue verify IOCB (%x).\n", rval);
4440 goto verify_done;
4441 }
4442
4443 ql_dbg(ql_dbg_mbx + ql_dbg_buffer, vha, 0x1110,
4444 "Dump of Verify Response.\n");
4445 ql_dump_buffer(ql_dbg_mbx + ql_dbg_buffer, vha, 0x1118,
4446 mn, sizeof(*mn));
4447
4448 status[0] = le16_to_cpu(mn->p.rsp.comp_status);
4449 status[1] = status[0] == CS_VCS_CHIP_FAILURE ?
4450 le16_to_cpu(mn->p.rsp.failure_code) : 0;
4451 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10ce,
4452 "cs=%x fc=%x.\n", status[0], status[1]);
4453
4454 if (status[0] != CS_COMPLETE) {
4455 rval = QLA_FUNCTION_FAILED;
4456 if (!(options & VCO_DONT_UPDATE_FW)) {
4457 ql_dbg(ql_dbg_mbx, vha, 0x10cf,
4458 "Firmware update failed. Retrying "
4459 "without update firmware.\n");
4460 options |= VCO_DONT_UPDATE_FW;
4461 options &= ~VCO_FORCE_UPDATE;
4462 retry = 1;
4463 }
4464 } else {
4465 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10d0,
4466 "Firmware updated to %x.\n",
4467 le32_to_cpu(mn->p.rsp.fw_ver));
4468
4469 /* NOTE: we only update OP firmware. */
4470 spin_lock_irqsave(&ha->cs84xx->access_lock, flags);
4471 ha->cs84xx->op_fw_version =
4472 le32_to_cpu(mn->p.rsp.fw_ver);
4473 spin_unlock_irqrestore(&ha->cs84xx->access_lock,
4474 flags);
4475 }
4476 } while (retry);
4477
4478 verify_done:
4479 dma_pool_free(ha->s_dma_pool, mn, mn_dma);
4480
4481 if (rval != QLA_SUCCESS) {
4482 ql_dbg(ql_dbg_mbx, vha, 0x10d1,
4483 "Failed=%x.\n", rval);
4484 } else {
4485 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10d2,
4486 "Done %s.\n", __func__);
4487 }
4488
4489 return rval;
4490 }
4491
4492 int
qla25xx_init_req_que(struct scsi_qla_host * vha,struct req_que * req)4493 qla25xx_init_req_que(struct scsi_qla_host *vha, struct req_que *req)
4494 {
4495 int rval;
4496 unsigned long flags;
4497 mbx_cmd_t mc;
4498 mbx_cmd_t *mcp = &mc;
4499 struct qla_hw_data *ha = vha->hw;
4500
4501 if (!ha->flags.fw_started)
4502 return QLA_SUCCESS;
4503
4504 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10d3,
4505 "Entered %s.\n", __func__);
4506
4507 if (IS_SHADOW_REG_CAPABLE(ha))
4508 req->options |= BIT_13;
4509
4510 mcp->mb[0] = MBC_INITIALIZE_MULTIQ;
4511 mcp->mb[1] = req->options;
4512 mcp->mb[2] = MSW(LSD(req->dma));
4513 mcp->mb[3] = LSW(LSD(req->dma));
4514 mcp->mb[6] = MSW(MSD(req->dma));
4515 mcp->mb[7] = LSW(MSD(req->dma));
4516 mcp->mb[5] = req->length;
4517 if (req->rsp)
4518 mcp->mb[10] = req->rsp->id;
4519 mcp->mb[12] = req->qos;
4520 mcp->mb[11] = req->vp_idx;
4521 mcp->mb[13] = req->rid;
4522 if (IS_QLA83XX(ha) || IS_QLA27XX(ha) || IS_QLA28XX(ha))
4523 mcp->mb[15] = 0;
4524
4525 mcp->mb[4] = req->id;
4526 /* que in ptr index */
4527 mcp->mb[8] = 0;
4528 /* que out ptr index */
4529 mcp->mb[9] = *req->out_ptr = 0;
4530 mcp->out_mb = MBX_14|MBX_13|MBX_12|MBX_11|MBX_10|MBX_9|MBX_8|MBX_7|
4531 MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
4532 mcp->in_mb = MBX_0;
4533 mcp->flags = MBX_DMA_OUT;
4534 mcp->tov = MBX_TOV_SECONDS * 2;
4535
4536 if (IS_QLA81XX(ha) || IS_QLA83XX(ha) || IS_QLA27XX(ha) ||
4537 IS_QLA28XX(ha))
4538 mcp->in_mb |= MBX_1;
4539 if (IS_QLA83XX(ha) || IS_QLA27XX(ha) || IS_QLA28XX(ha)) {
4540 mcp->out_mb |= MBX_15;
4541 /* debug q create issue in SR-IOV */
4542 mcp->in_mb |= MBX_9 | MBX_8 | MBX_7;
4543 }
4544
4545 spin_lock_irqsave(&ha->hardware_lock, flags);
4546 if (!(req->options & BIT_0)) {
4547 wrt_reg_dword(req->req_q_in, 0);
4548 if (!IS_QLA83XX(ha) && !IS_QLA27XX(ha) && !IS_QLA28XX(ha))
4549 wrt_reg_dword(req->req_q_out, 0);
4550 }
4551 spin_unlock_irqrestore(&ha->hardware_lock, flags);
4552
4553 rval = qla2x00_mailbox_command(vha, mcp);
4554 if (rval != QLA_SUCCESS) {
4555 ql_dbg(ql_dbg_mbx, vha, 0x10d4,
4556 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
4557 } else {
4558 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10d5,
4559 "Done %s.\n", __func__);
4560 }
4561
4562 return rval;
4563 }
4564
4565 int
qla25xx_init_rsp_que(struct scsi_qla_host * vha,struct rsp_que * rsp)4566 qla25xx_init_rsp_que(struct scsi_qla_host *vha, struct rsp_que *rsp)
4567 {
4568 int rval;
4569 unsigned long flags;
4570 mbx_cmd_t mc;
4571 mbx_cmd_t *mcp = &mc;
4572 struct qla_hw_data *ha = vha->hw;
4573
4574 if (!ha->flags.fw_started)
4575 return QLA_SUCCESS;
4576
4577 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10d6,
4578 "Entered %s.\n", __func__);
4579
4580 if (IS_SHADOW_REG_CAPABLE(ha))
4581 rsp->options |= BIT_13;
4582
4583 mcp->mb[0] = MBC_INITIALIZE_MULTIQ;
4584 mcp->mb[1] = rsp->options;
4585 mcp->mb[2] = MSW(LSD(rsp->dma));
4586 mcp->mb[3] = LSW(LSD(rsp->dma));
4587 mcp->mb[6] = MSW(MSD(rsp->dma));
4588 mcp->mb[7] = LSW(MSD(rsp->dma));
4589 mcp->mb[5] = rsp->length;
4590 mcp->mb[14] = rsp->msix->entry;
4591 mcp->mb[13] = rsp->rid;
4592 if (IS_QLA83XX(ha) || IS_QLA27XX(ha) || IS_QLA28XX(ha))
4593 mcp->mb[15] = 0;
4594
4595 mcp->mb[4] = rsp->id;
4596 /* que in ptr index */
4597 mcp->mb[8] = *rsp->in_ptr = 0;
4598 /* que out ptr index */
4599 mcp->mb[9] = 0;
4600 mcp->out_mb = MBX_14|MBX_13|MBX_9|MBX_8|MBX_7
4601 |MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
4602 mcp->in_mb = MBX_0;
4603 mcp->flags = MBX_DMA_OUT;
4604 mcp->tov = MBX_TOV_SECONDS * 2;
4605
4606 if (IS_QLA81XX(ha)) {
4607 mcp->out_mb |= MBX_12|MBX_11|MBX_10;
4608 mcp->in_mb |= MBX_1;
4609 } else if (IS_QLA83XX(ha) || IS_QLA27XX(ha) || IS_QLA28XX(ha)) {
4610 mcp->out_mb |= MBX_15|MBX_12|MBX_11|MBX_10;
4611 mcp->in_mb |= MBX_1;
4612 /* debug q create issue in SR-IOV */
4613 mcp->in_mb |= MBX_9 | MBX_8 | MBX_7;
4614 }
4615
4616 spin_lock_irqsave(&ha->hardware_lock, flags);
4617 if (!(rsp->options & BIT_0)) {
4618 wrt_reg_dword(rsp->rsp_q_out, 0);
4619 if (!IS_QLA83XX(ha) && !IS_QLA27XX(ha) && !IS_QLA28XX(ha))
4620 wrt_reg_dword(rsp->rsp_q_in, 0);
4621 }
4622
4623 spin_unlock_irqrestore(&ha->hardware_lock, flags);
4624
4625 rval = qla2x00_mailbox_command(vha, mcp);
4626 if (rval != QLA_SUCCESS) {
4627 ql_dbg(ql_dbg_mbx, vha, 0x10d7,
4628 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
4629 } else {
4630 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10d8,
4631 "Done %s.\n", __func__);
4632 }
4633
4634 return rval;
4635 }
4636
4637 int
qla81xx_idc_ack(scsi_qla_host_t * vha,uint16_t * mb)4638 qla81xx_idc_ack(scsi_qla_host_t *vha, uint16_t *mb)
4639 {
4640 int rval;
4641 mbx_cmd_t mc;
4642 mbx_cmd_t *mcp = &mc;
4643
4644 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10d9,
4645 "Entered %s.\n", __func__);
4646
4647 mcp->mb[0] = MBC_IDC_ACK;
4648 memcpy(&mcp->mb[1], mb, QLA_IDC_ACK_REGS * sizeof(uint16_t));
4649 mcp->out_mb = MBX_7|MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
4650 mcp->in_mb = MBX_0;
4651 mcp->tov = MBX_TOV_SECONDS;
4652 mcp->flags = 0;
4653 rval = qla2x00_mailbox_command(vha, mcp);
4654
4655 if (rval != QLA_SUCCESS) {
4656 ql_dbg(ql_dbg_mbx, vha, 0x10da,
4657 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
4658 } else {
4659 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10db,
4660 "Done %s.\n", __func__);
4661 }
4662
4663 return rval;
4664 }
4665
4666 int
qla81xx_fac_get_sector_size(scsi_qla_host_t * vha,uint32_t * sector_size)4667 qla81xx_fac_get_sector_size(scsi_qla_host_t *vha, uint32_t *sector_size)
4668 {
4669 int rval;
4670 mbx_cmd_t mc;
4671 mbx_cmd_t *mcp = &mc;
4672
4673 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10dc,
4674 "Entered %s.\n", __func__);
4675
4676 if (!IS_QLA81XX(vha->hw) && !IS_QLA83XX(vha->hw) &&
4677 !IS_QLA27XX(vha->hw) && !IS_QLA28XX(vha->hw))
4678 return QLA_FUNCTION_FAILED;
4679
4680 mcp->mb[0] = MBC_FLASH_ACCESS_CTRL;
4681 mcp->mb[1] = FAC_OPT_CMD_GET_SECTOR_SIZE;
4682 mcp->out_mb = MBX_1|MBX_0;
4683 mcp->in_mb = MBX_1|MBX_0;
4684 mcp->tov = MBX_TOV_SECONDS;
4685 mcp->flags = 0;
4686 rval = qla2x00_mailbox_command(vha, mcp);
4687
4688 if (rval != QLA_SUCCESS) {
4689 ql_dbg(ql_dbg_mbx, vha, 0x10dd,
4690 "Failed=%x mb[0]=%x mb[1]=%x.\n",
4691 rval, mcp->mb[0], mcp->mb[1]);
4692 } else {
4693 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10de,
4694 "Done %s.\n", __func__);
4695 *sector_size = mcp->mb[1];
4696 }
4697
4698 return rval;
4699 }
4700
4701 int
qla81xx_fac_do_write_enable(scsi_qla_host_t * vha,int enable)4702 qla81xx_fac_do_write_enable(scsi_qla_host_t *vha, int enable)
4703 {
4704 int rval;
4705 mbx_cmd_t mc;
4706 mbx_cmd_t *mcp = &mc;
4707
4708 if (!IS_QLA81XX(vha->hw) && !IS_QLA83XX(vha->hw) &&
4709 !IS_QLA27XX(vha->hw) && !IS_QLA28XX(vha->hw))
4710 return QLA_FUNCTION_FAILED;
4711
4712 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10df,
4713 "Entered %s.\n", __func__);
4714
4715 mcp->mb[0] = MBC_FLASH_ACCESS_CTRL;
4716 mcp->mb[1] = enable ? FAC_OPT_CMD_WRITE_ENABLE :
4717 FAC_OPT_CMD_WRITE_PROTECT;
4718 mcp->out_mb = MBX_1|MBX_0;
4719 mcp->in_mb = MBX_1|MBX_0;
4720 mcp->tov = MBX_TOV_SECONDS;
4721 mcp->flags = 0;
4722 rval = qla2x00_mailbox_command(vha, mcp);
4723
4724 if (rval != QLA_SUCCESS) {
4725 ql_dbg(ql_dbg_mbx, vha, 0x10e0,
4726 "Failed=%x mb[0]=%x mb[1]=%x.\n",
4727 rval, mcp->mb[0], mcp->mb[1]);
4728 } else {
4729 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10e1,
4730 "Done %s.\n", __func__);
4731 }
4732
4733 return rval;
4734 }
4735
4736 int
qla81xx_fac_erase_sector(scsi_qla_host_t * vha,uint32_t start,uint32_t finish)4737 qla81xx_fac_erase_sector(scsi_qla_host_t *vha, uint32_t start, uint32_t finish)
4738 {
4739 int rval;
4740 mbx_cmd_t mc;
4741 mbx_cmd_t *mcp = &mc;
4742
4743 if (!IS_QLA81XX(vha->hw) && !IS_QLA83XX(vha->hw) &&
4744 !IS_QLA27XX(vha->hw) && !IS_QLA28XX(vha->hw))
4745 return QLA_FUNCTION_FAILED;
4746
4747 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10e2,
4748 "Entered %s.\n", __func__);
4749
4750 mcp->mb[0] = MBC_FLASH_ACCESS_CTRL;
4751 mcp->mb[1] = FAC_OPT_CMD_ERASE_SECTOR;
4752 mcp->mb[2] = LSW(start);
4753 mcp->mb[3] = MSW(start);
4754 mcp->mb[4] = LSW(finish);
4755 mcp->mb[5] = MSW(finish);
4756 mcp->out_mb = MBX_5|MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
4757 mcp->in_mb = MBX_2|MBX_1|MBX_0;
4758 mcp->tov = MBX_TOV_SECONDS;
4759 mcp->flags = 0;
4760 rval = qla2x00_mailbox_command(vha, mcp);
4761
4762 if (rval != QLA_SUCCESS) {
4763 ql_dbg(ql_dbg_mbx, vha, 0x10e3,
4764 "Failed=%x mb[0]=%x mb[1]=%x mb[2]=%x.\n",
4765 rval, mcp->mb[0], mcp->mb[1], mcp->mb[2]);
4766 } else {
4767 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10e4,
4768 "Done %s.\n", __func__);
4769 }
4770
4771 return rval;
4772 }
4773
4774 int
qla81xx_fac_semaphore_access(scsi_qla_host_t * vha,int lock)4775 qla81xx_fac_semaphore_access(scsi_qla_host_t *vha, int lock)
4776 {
4777 int rval = QLA_SUCCESS;
4778 mbx_cmd_t mc;
4779 mbx_cmd_t *mcp = &mc;
4780 struct qla_hw_data *ha = vha->hw;
4781
4782 if (!IS_QLA81XX(ha) && !IS_QLA83XX(ha) &&
4783 !IS_QLA27XX(ha) && !IS_QLA28XX(ha))
4784 return rval;
4785
4786 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10e2,
4787 "Entered %s.\n", __func__);
4788
4789 mcp->mb[0] = MBC_FLASH_ACCESS_CTRL;
4790 mcp->mb[1] = (lock ? FAC_OPT_CMD_LOCK_SEMAPHORE :
4791 FAC_OPT_CMD_UNLOCK_SEMAPHORE);
4792 mcp->out_mb = MBX_1|MBX_0;
4793 mcp->in_mb = MBX_1|MBX_0;
4794 mcp->tov = MBX_TOV_SECONDS;
4795 mcp->flags = 0;
4796 rval = qla2x00_mailbox_command(vha, mcp);
4797
4798 if (rval != QLA_SUCCESS) {
4799 ql_dbg(ql_dbg_mbx, vha, 0x10e3,
4800 "Failed=%x mb[0]=%x mb[1]=%x mb[2]=%x.\n",
4801 rval, mcp->mb[0], mcp->mb[1], mcp->mb[2]);
4802 } else {
4803 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10e4,
4804 "Done %s.\n", __func__);
4805 }
4806
4807 return rval;
4808 }
4809
4810 int
qla81xx_restart_mpi_firmware(scsi_qla_host_t * vha)4811 qla81xx_restart_mpi_firmware(scsi_qla_host_t *vha)
4812 {
4813 int rval = 0;
4814 mbx_cmd_t mc;
4815 mbx_cmd_t *mcp = &mc;
4816
4817 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10e5,
4818 "Entered %s.\n", __func__);
4819
4820 mcp->mb[0] = MBC_RESTART_MPI_FW;
4821 mcp->out_mb = MBX_0;
4822 mcp->in_mb = MBX_0|MBX_1;
4823 mcp->tov = MBX_TOV_SECONDS;
4824 mcp->flags = 0;
4825 rval = qla2x00_mailbox_command(vha, mcp);
4826
4827 if (rval != QLA_SUCCESS) {
4828 ql_dbg(ql_dbg_mbx, vha, 0x10e6,
4829 "Failed=%x mb[0]=%x mb[1]=%x.\n",
4830 rval, mcp->mb[0], mcp->mb[1]);
4831 } else {
4832 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10e7,
4833 "Done %s.\n", __func__);
4834 }
4835
4836 return rval;
4837 }
4838
4839 int
qla82xx_set_driver_version(scsi_qla_host_t * vha,char * version)4840 qla82xx_set_driver_version(scsi_qla_host_t *vha, char *version)
4841 {
4842 int rval;
4843 mbx_cmd_t mc;
4844 mbx_cmd_t *mcp = &mc;
4845 int i;
4846 int len;
4847 __le16 *str;
4848 struct qla_hw_data *ha = vha->hw;
4849
4850 if (!IS_P3P_TYPE(ha))
4851 return QLA_FUNCTION_FAILED;
4852
4853 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x117b,
4854 "Entered %s.\n", __func__);
4855
4856 str = (__force __le16 *)version;
4857 len = strlen(version);
4858
4859 mcp->mb[0] = MBC_SET_RNID_PARAMS;
4860 mcp->mb[1] = RNID_TYPE_SET_VERSION << 8;
4861 mcp->out_mb = MBX_1|MBX_0;
4862 for (i = 4; i < 16 && len; i++, str++, len -= 2) {
4863 mcp->mb[i] = le16_to_cpup(str);
4864 mcp->out_mb |= 1<<i;
4865 }
4866 for (; i < 16; i++) {
4867 mcp->mb[i] = 0;
4868 mcp->out_mb |= 1<<i;
4869 }
4870 mcp->in_mb = MBX_1|MBX_0;
4871 mcp->tov = MBX_TOV_SECONDS;
4872 mcp->flags = 0;
4873 rval = qla2x00_mailbox_command(vha, mcp);
4874
4875 if (rval != QLA_SUCCESS) {
4876 ql_dbg(ql_dbg_mbx, vha, 0x117c,
4877 "Failed=%x mb[0]=%x,%x.\n", rval, mcp->mb[0], mcp->mb[1]);
4878 } else {
4879 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x117d,
4880 "Done %s.\n", __func__);
4881 }
4882
4883 return rval;
4884 }
4885
4886 int
qla25xx_set_driver_version(scsi_qla_host_t * vha,char * version)4887 qla25xx_set_driver_version(scsi_qla_host_t *vha, char *version)
4888 {
4889 int rval;
4890 mbx_cmd_t mc;
4891 mbx_cmd_t *mcp = &mc;
4892 int len;
4893 uint16_t dwlen;
4894 uint8_t *str;
4895 dma_addr_t str_dma;
4896 struct qla_hw_data *ha = vha->hw;
4897
4898 if (!IS_FWI2_CAPABLE(ha) || IS_QLA24XX_TYPE(ha) || IS_QLA81XX(ha) ||
4899 IS_P3P_TYPE(ha))
4900 return QLA_FUNCTION_FAILED;
4901
4902 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x117e,
4903 "Entered %s.\n", __func__);
4904
4905 str = dma_pool_alloc(ha->s_dma_pool, GFP_KERNEL, &str_dma);
4906 if (!str) {
4907 ql_log(ql_log_warn, vha, 0x117f,
4908 "Failed to allocate driver version param.\n");
4909 return QLA_MEMORY_ALLOC_FAILED;
4910 }
4911
4912 memcpy(str, "\x7\x3\x11\x0", 4);
4913 dwlen = str[0];
4914 len = dwlen * 4 - 4;
4915 memset(str + 4, 0, len);
4916 if (len > strlen(version))
4917 len = strlen(version);
4918 memcpy(str + 4, version, len);
4919
4920 mcp->mb[0] = MBC_SET_RNID_PARAMS;
4921 mcp->mb[1] = RNID_TYPE_SET_VERSION << 8 | dwlen;
4922 mcp->mb[2] = MSW(LSD(str_dma));
4923 mcp->mb[3] = LSW(LSD(str_dma));
4924 mcp->mb[6] = MSW(MSD(str_dma));
4925 mcp->mb[7] = LSW(MSD(str_dma));
4926 mcp->out_mb = MBX_7|MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
4927 mcp->in_mb = MBX_1|MBX_0;
4928 mcp->tov = MBX_TOV_SECONDS;
4929 mcp->flags = 0;
4930 rval = qla2x00_mailbox_command(vha, mcp);
4931
4932 if (rval != QLA_SUCCESS) {
4933 ql_dbg(ql_dbg_mbx, vha, 0x1180,
4934 "Failed=%x mb[0]=%x,%x.\n", rval, mcp->mb[0], mcp->mb[1]);
4935 } else {
4936 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1181,
4937 "Done %s.\n", __func__);
4938 }
4939
4940 dma_pool_free(ha->s_dma_pool, str, str_dma);
4941
4942 return rval;
4943 }
4944
4945 int
qla24xx_get_port_login_templ(scsi_qla_host_t * vha,dma_addr_t buf_dma,void * buf,uint16_t bufsiz)4946 qla24xx_get_port_login_templ(scsi_qla_host_t *vha, dma_addr_t buf_dma,
4947 void *buf, uint16_t bufsiz)
4948 {
4949 int rval, i;
4950 mbx_cmd_t mc;
4951 mbx_cmd_t *mcp = &mc;
4952 uint32_t *bp;
4953
4954 if (!IS_FWI2_CAPABLE(vha->hw))
4955 return QLA_FUNCTION_FAILED;
4956
4957 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1159,
4958 "Entered %s.\n", __func__);
4959
4960 mcp->mb[0] = MBC_GET_RNID_PARAMS;
4961 mcp->mb[1] = RNID_TYPE_PORT_LOGIN << 8;
4962 mcp->mb[2] = MSW(buf_dma);
4963 mcp->mb[3] = LSW(buf_dma);
4964 mcp->mb[6] = MSW(MSD(buf_dma));
4965 mcp->mb[7] = LSW(MSD(buf_dma));
4966 mcp->mb[8] = bufsiz/4;
4967 mcp->out_mb = MBX_8|MBX_7|MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
4968 mcp->in_mb = MBX_1|MBX_0;
4969 mcp->tov = MBX_TOV_SECONDS;
4970 mcp->flags = 0;
4971 rval = qla2x00_mailbox_command(vha, mcp);
4972
4973 if (rval != QLA_SUCCESS) {
4974 ql_dbg(ql_dbg_mbx, vha, 0x115a,
4975 "Failed=%x mb[0]=%x,%x.\n", rval, mcp->mb[0], mcp->mb[1]);
4976 } else {
4977 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x115b,
4978 "Done %s.\n", __func__);
4979 bp = (uint32_t *) buf;
4980 for (i = 0; i < (bufsiz-4)/4; i++, bp++)
4981 *bp = le32_to_cpu((__force __le32)*bp);
4982 }
4983
4984 return rval;
4985 }
4986
4987 #define PUREX_CMD_COUNT 4
4988 int
qla25xx_set_els_cmds_supported(scsi_qla_host_t * vha)4989 qla25xx_set_els_cmds_supported(scsi_qla_host_t *vha)
4990 {
4991 int rval;
4992 mbx_cmd_t mc;
4993 mbx_cmd_t *mcp = &mc;
4994 uint8_t *els_cmd_map;
4995 uint8_t active_cnt = 0;
4996 dma_addr_t els_cmd_map_dma;
4997 uint8_t cmd_opcode[PUREX_CMD_COUNT];
4998 uint8_t i, index, purex_bit;
4999 struct qla_hw_data *ha = vha->hw;
5000
5001 if (!IS_QLA25XX(ha) && !IS_QLA2031(ha) &&
5002 !IS_QLA27XX(ha) && !IS_QLA28XX(ha))
5003 return QLA_SUCCESS;
5004
5005 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1197,
5006 "Entered %s.\n", __func__);
5007
5008 els_cmd_map = dma_alloc_coherent(&ha->pdev->dev, ELS_CMD_MAP_SIZE,
5009 &els_cmd_map_dma, GFP_KERNEL);
5010 if (!els_cmd_map) {
5011 ql_log(ql_log_warn, vha, 0x7101,
5012 "Failed to allocate RDP els command param.\n");
5013 return QLA_MEMORY_ALLOC_FAILED;
5014 }
5015
5016 /* List of Purex ELS */
5017 if (ql2xrdpenable) {
5018 cmd_opcode[active_cnt] = ELS_RDP;
5019 active_cnt++;
5020 }
5021 if (ha->flags.scm_supported_f) {
5022 cmd_opcode[active_cnt] = ELS_FPIN;
5023 active_cnt++;
5024 }
5025 if (ha->flags.edif_enabled) {
5026 cmd_opcode[active_cnt] = ELS_AUTH_ELS;
5027 active_cnt++;
5028 }
5029
5030 for (i = 0; i < active_cnt; i++) {
5031 index = cmd_opcode[i] / 8;
5032 purex_bit = cmd_opcode[i] % 8;
5033 els_cmd_map[index] |= 1 << purex_bit;
5034 }
5035
5036 mcp->mb[0] = MBC_SET_RNID_PARAMS;
5037 mcp->mb[1] = RNID_TYPE_ELS_CMD << 8;
5038 mcp->mb[2] = MSW(LSD(els_cmd_map_dma));
5039 mcp->mb[3] = LSW(LSD(els_cmd_map_dma));
5040 mcp->mb[6] = MSW(MSD(els_cmd_map_dma));
5041 mcp->mb[7] = LSW(MSD(els_cmd_map_dma));
5042 mcp->out_mb = MBX_7|MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
5043 mcp->in_mb = MBX_1|MBX_0;
5044 mcp->tov = MBX_TOV_SECONDS;
5045 mcp->flags = MBX_DMA_OUT;
5046 mcp->buf_size = ELS_CMD_MAP_SIZE;
5047 rval = qla2x00_mailbox_command(vha, mcp);
5048
5049 if (rval != QLA_SUCCESS) {
5050 ql_dbg(ql_dbg_mbx, vha, 0x118d,
5051 "Failed=%x (%x,%x).\n", rval, mcp->mb[0], mcp->mb[1]);
5052 } else {
5053 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x118c,
5054 "Done %s.\n", __func__);
5055 }
5056
5057 dma_free_coherent(&ha->pdev->dev, ELS_CMD_MAP_SIZE,
5058 els_cmd_map, els_cmd_map_dma);
5059
5060 return rval;
5061 }
5062
5063 static int
qla2x00_read_asic_temperature(scsi_qla_host_t * vha,uint16_t * temp)5064 qla2x00_read_asic_temperature(scsi_qla_host_t *vha, uint16_t *temp)
5065 {
5066 int rval;
5067 mbx_cmd_t mc;
5068 mbx_cmd_t *mcp = &mc;
5069
5070 if (!IS_FWI2_CAPABLE(vha->hw))
5071 return QLA_FUNCTION_FAILED;
5072
5073 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1159,
5074 "Entered %s.\n", __func__);
5075
5076 mcp->mb[0] = MBC_GET_RNID_PARAMS;
5077 mcp->mb[1] = RNID_TYPE_ASIC_TEMP << 8;
5078 mcp->out_mb = MBX_1|MBX_0;
5079 mcp->in_mb = MBX_1|MBX_0;
5080 mcp->tov = MBX_TOV_SECONDS;
5081 mcp->flags = 0;
5082 rval = qla2x00_mailbox_command(vha, mcp);
5083 *temp = mcp->mb[1];
5084
5085 if (rval != QLA_SUCCESS) {
5086 ql_dbg(ql_dbg_mbx, vha, 0x115a,
5087 "Failed=%x mb[0]=%x,%x.\n", rval, mcp->mb[0], mcp->mb[1]);
5088 } else {
5089 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x115b,
5090 "Done %s.\n", __func__);
5091 }
5092
5093 return rval;
5094 }
5095
5096 int
qla2x00_read_sfp(scsi_qla_host_t * vha,dma_addr_t sfp_dma,uint8_t * sfp,uint16_t dev,uint16_t off,uint16_t len,uint16_t opt)5097 qla2x00_read_sfp(scsi_qla_host_t *vha, dma_addr_t sfp_dma, uint8_t *sfp,
5098 uint16_t dev, uint16_t off, uint16_t len, uint16_t opt)
5099 {
5100 int rval;
5101 mbx_cmd_t mc;
5102 mbx_cmd_t *mcp = &mc;
5103 struct qla_hw_data *ha = vha->hw;
5104
5105 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10e8,
5106 "Entered %s.\n", __func__);
5107
5108 if (!IS_FWI2_CAPABLE(ha))
5109 return QLA_FUNCTION_FAILED;
5110
5111 if (len == 1)
5112 opt |= BIT_0;
5113
5114 mcp->mb[0] = MBC_READ_SFP;
5115 mcp->mb[1] = dev;
5116 mcp->mb[2] = MSW(LSD(sfp_dma));
5117 mcp->mb[3] = LSW(LSD(sfp_dma));
5118 mcp->mb[6] = MSW(MSD(sfp_dma));
5119 mcp->mb[7] = LSW(MSD(sfp_dma));
5120 mcp->mb[8] = len;
5121 mcp->mb[9] = off;
5122 mcp->mb[10] = opt;
5123 mcp->out_mb = MBX_10|MBX_9|MBX_8|MBX_7|MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
5124 mcp->in_mb = MBX_1|MBX_0;
5125 mcp->tov = MBX_TOV_SECONDS;
5126 mcp->flags = 0;
5127 rval = qla2x00_mailbox_command(vha, mcp);
5128
5129 if (opt & BIT_0)
5130 *sfp = mcp->mb[1];
5131
5132 if (rval != QLA_SUCCESS) {
5133 ql_dbg(ql_dbg_mbx, vha, 0x10e9,
5134 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
5135 if (mcp->mb[0] == MBS_COMMAND_ERROR && mcp->mb[1] == 0x22) {
5136 /* sfp is not there */
5137 rval = QLA_INTERFACE_ERROR;
5138 }
5139 } else {
5140 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10ea,
5141 "Done %s.\n", __func__);
5142 }
5143
5144 return rval;
5145 }
5146
5147 int
qla2x00_write_sfp(scsi_qla_host_t * vha,dma_addr_t sfp_dma,uint8_t * sfp,uint16_t dev,uint16_t off,uint16_t len,uint16_t opt)5148 qla2x00_write_sfp(scsi_qla_host_t *vha, dma_addr_t sfp_dma, uint8_t *sfp,
5149 uint16_t dev, uint16_t off, uint16_t len, uint16_t opt)
5150 {
5151 int rval;
5152 mbx_cmd_t mc;
5153 mbx_cmd_t *mcp = &mc;
5154 struct qla_hw_data *ha = vha->hw;
5155
5156 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10eb,
5157 "Entered %s.\n", __func__);
5158
5159 if (!IS_FWI2_CAPABLE(ha))
5160 return QLA_FUNCTION_FAILED;
5161
5162 if (len == 1)
5163 opt |= BIT_0;
5164
5165 if (opt & BIT_0)
5166 len = *sfp;
5167
5168 mcp->mb[0] = MBC_WRITE_SFP;
5169 mcp->mb[1] = dev;
5170 mcp->mb[2] = MSW(LSD(sfp_dma));
5171 mcp->mb[3] = LSW(LSD(sfp_dma));
5172 mcp->mb[6] = MSW(MSD(sfp_dma));
5173 mcp->mb[7] = LSW(MSD(sfp_dma));
5174 mcp->mb[8] = len;
5175 mcp->mb[9] = off;
5176 mcp->mb[10] = opt;
5177 mcp->out_mb = MBX_10|MBX_9|MBX_8|MBX_7|MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
5178 mcp->in_mb = MBX_1|MBX_0;
5179 mcp->tov = MBX_TOV_SECONDS;
5180 mcp->flags = 0;
5181 rval = qla2x00_mailbox_command(vha, mcp);
5182
5183 if (rval != QLA_SUCCESS) {
5184 ql_dbg(ql_dbg_mbx, vha, 0x10ec,
5185 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
5186 } else {
5187 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10ed,
5188 "Done %s.\n", __func__);
5189 }
5190
5191 return rval;
5192 }
5193
5194 int
qla2x00_get_xgmac_stats(scsi_qla_host_t * vha,dma_addr_t stats_dma,uint16_t size_in_bytes,uint16_t * actual_size)5195 qla2x00_get_xgmac_stats(scsi_qla_host_t *vha, dma_addr_t stats_dma,
5196 uint16_t size_in_bytes, uint16_t *actual_size)
5197 {
5198 int rval;
5199 mbx_cmd_t mc;
5200 mbx_cmd_t *mcp = &mc;
5201
5202 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10ee,
5203 "Entered %s.\n", __func__);
5204
5205 if (!IS_CNA_CAPABLE(vha->hw))
5206 return QLA_FUNCTION_FAILED;
5207
5208 mcp->mb[0] = MBC_GET_XGMAC_STATS;
5209 mcp->mb[2] = MSW(stats_dma);
5210 mcp->mb[3] = LSW(stats_dma);
5211 mcp->mb[6] = MSW(MSD(stats_dma));
5212 mcp->mb[7] = LSW(MSD(stats_dma));
5213 mcp->mb[8] = size_in_bytes >> 2;
5214 mcp->out_mb = MBX_8|MBX_7|MBX_6|MBX_3|MBX_2|MBX_0;
5215 mcp->in_mb = MBX_2|MBX_1|MBX_0;
5216 mcp->tov = MBX_TOV_SECONDS;
5217 mcp->flags = 0;
5218 rval = qla2x00_mailbox_command(vha, mcp);
5219
5220 if (rval != QLA_SUCCESS) {
5221 ql_dbg(ql_dbg_mbx, vha, 0x10ef,
5222 "Failed=%x mb[0]=%x mb[1]=%x mb[2]=%x.\n",
5223 rval, mcp->mb[0], mcp->mb[1], mcp->mb[2]);
5224 } else {
5225 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10f0,
5226 "Done %s.\n", __func__);
5227
5228
5229 *actual_size = mcp->mb[2] << 2;
5230 }
5231
5232 return rval;
5233 }
5234
5235 int
qla2x00_get_dcbx_params(scsi_qla_host_t * vha,dma_addr_t tlv_dma,uint16_t size)5236 qla2x00_get_dcbx_params(scsi_qla_host_t *vha, dma_addr_t tlv_dma,
5237 uint16_t size)
5238 {
5239 int rval;
5240 mbx_cmd_t mc;
5241 mbx_cmd_t *mcp = &mc;
5242
5243 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10f1,
5244 "Entered %s.\n", __func__);
5245
5246 if (!IS_CNA_CAPABLE(vha->hw))
5247 return QLA_FUNCTION_FAILED;
5248
5249 mcp->mb[0] = MBC_GET_DCBX_PARAMS;
5250 mcp->mb[1] = 0;
5251 mcp->mb[2] = MSW(tlv_dma);
5252 mcp->mb[3] = LSW(tlv_dma);
5253 mcp->mb[6] = MSW(MSD(tlv_dma));
5254 mcp->mb[7] = LSW(MSD(tlv_dma));
5255 mcp->mb[8] = size;
5256 mcp->out_mb = MBX_8|MBX_7|MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
5257 mcp->in_mb = MBX_2|MBX_1|MBX_0;
5258 mcp->tov = MBX_TOV_SECONDS;
5259 mcp->flags = 0;
5260 rval = qla2x00_mailbox_command(vha, mcp);
5261
5262 if (rval != QLA_SUCCESS) {
5263 ql_dbg(ql_dbg_mbx, vha, 0x10f2,
5264 "Failed=%x mb[0]=%x mb[1]=%x mb[2]=%x.\n",
5265 rval, mcp->mb[0], mcp->mb[1], mcp->mb[2]);
5266 } else {
5267 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10f3,
5268 "Done %s.\n", __func__);
5269 }
5270
5271 return rval;
5272 }
5273
5274 int
qla2x00_read_ram_word(scsi_qla_host_t * vha,uint32_t risc_addr,uint32_t * data)5275 qla2x00_read_ram_word(scsi_qla_host_t *vha, uint32_t risc_addr, uint32_t *data)
5276 {
5277 int rval;
5278 mbx_cmd_t mc;
5279 mbx_cmd_t *mcp = &mc;
5280
5281 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10f4,
5282 "Entered %s.\n", __func__);
5283
5284 if (!IS_FWI2_CAPABLE(vha->hw))
5285 return QLA_FUNCTION_FAILED;
5286
5287 mcp->mb[0] = MBC_READ_RAM_EXTENDED;
5288 mcp->mb[1] = LSW(risc_addr);
5289 mcp->mb[8] = MSW(risc_addr);
5290 mcp->out_mb = MBX_8|MBX_1|MBX_0;
5291 mcp->in_mb = MBX_3|MBX_2|MBX_0;
5292 mcp->tov = MBX_TOV_SECONDS;
5293 mcp->flags = 0;
5294 rval = qla2x00_mailbox_command(vha, mcp);
5295 if (rval != QLA_SUCCESS) {
5296 ql_dbg(ql_dbg_mbx, vha, 0x10f5,
5297 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
5298 } else {
5299 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10f6,
5300 "Done %s.\n", __func__);
5301 *data = mcp->mb[3] << 16 | mcp->mb[2];
5302 }
5303
5304 return rval;
5305 }
5306
5307 int
qla2x00_loopback_test(scsi_qla_host_t * vha,struct msg_echo_lb * mreq,uint16_t * mresp)5308 qla2x00_loopback_test(scsi_qla_host_t *vha, struct msg_echo_lb *mreq,
5309 uint16_t *mresp)
5310 {
5311 int rval;
5312 mbx_cmd_t mc;
5313 mbx_cmd_t *mcp = &mc;
5314
5315 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10f7,
5316 "Entered %s.\n", __func__);
5317
5318 memset(mcp->mb, 0 , sizeof(mcp->mb));
5319 mcp->mb[0] = MBC_DIAGNOSTIC_LOOP_BACK;
5320 mcp->mb[1] = mreq->options | BIT_6; // BIT_6 specifies 64 bit addressing
5321
5322 /* transfer count */
5323 mcp->mb[10] = LSW(mreq->transfer_size);
5324 mcp->mb[11] = MSW(mreq->transfer_size);
5325
5326 /* send data address */
5327 mcp->mb[14] = LSW(mreq->send_dma);
5328 mcp->mb[15] = MSW(mreq->send_dma);
5329 mcp->mb[20] = LSW(MSD(mreq->send_dma));
5330 mcp->mb[21] = MSW(MSD(mreq->send_dma));
5331
5332 /* receive data address */
5333 mcp->mb[16] = LSW(mreq->rcv_dma);
5334 mcp->mb[17] = MSW(mreq->rcv_dma);
5335 mcp->mb[6] = LSW(MSD(mreq->rcv_dma));
5336 mcp->mb[7] = MSW(MSD(mreq->rcv_dma));
5337
5338 /* Iteration count */
5339 mcp->mb[18] = LSW(mreq->iteration_count);
5340 mcp->mb[19] = MSW(mreq->iteration_count);
5341
5342 mcp->out_mb = MBX_21|MBX_20|MBX_19|MBX_18|MBX_17|MBX_16|MBX_15|
5343 MBX_14|MBX_13|MBX_12|MBX_11|MBX_10|MBX_7|MBX_6|MBX_1|MBX_0;
5344 if (IS_CNA_CAPABLE(vha->hw))
5345 mcp->out_mb |= MBX_2;
5346 mcp->in_mb = MBX_19|MBX_18|MBX_3|MBX_2|MBX_1|MBX_0;
5347
5348 mcp->buf_size = mreq->transfer_size;
5349 mcp->tov = MBX_TOV_SECONDS;
5350 mcp->flags = MBX_DMA_OUT|MBX_DMA_IN|IOCTL_CMD;
5351
5352 rval = qla2x00_mailbox_command(vha, mcp);
5353
5354 if (rval != QLA_SUCCESS) {
5355 ql_dbg(ql_dbg_mbx, vha, 0x10f8,
5356 "Failed=%x mb[0]=%x mb[1]=%x mb[2]=%x mb[3]=%x mb[18]=%x "
5357 "mb[19]=%x.\n", rval, mcp->mb[0], mcp->mb[1], mcp->mb[2],
5358 mcp->mb[3], mcp->mb[18], mcp->mb[19]);
5359 } else {
5360 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10f9,
5361 "Done %s.\n", __func__);
5362 }
5363
5364 /* Copy mailbox information */
5365 memcpy( mresp, mcp->mb, 64);
5366 return rval;
5367 }
5368
5369 int
qla2x00_echo_test(scsi_qla_host_t * vha,struct msg_echo_lb * mreq,uint16_t * mresp)5370 qla2x00_echo_test(scsi_qla_host_t *vha, struct msg_echo_lb *mreq,
5371 uint16_t *mresp)
5372 {
5373 int rval;
5374 mbx_cmd_t mc;
5375 mbx_cmd_t *mcp = &mc;
5376 struct qla_hw_data *ha = vha->hw;
5377
5378 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10fa,
5379 "Entered %s.\n", __func__);
5380
5381 memset(mcp->mb, 0 , sizeof(mcp->mb));
5382 mcp->mb[0] = MBC_DIAGNOSTIC_ECHO;
5383 /* BIT_6 specifies 64bit address */
5384 mcp->mb[1] = mreq->options | BIT_15 | BIT_6;
5385 if (IS_CNA_CAPABLE(ha)) {
5386 mcp->mb[2] = vha->fcoe_fcf_idx;
5387 }
5388 mcp->mb[16] = LSW(mreq->rcv_dma);
5389 mcp->mb[17] = MSW(mreq->rcv_dma);
5390 mcp->mb[6] = LSW(MSD(mreq->rcv_dma));
5391 mcp->mb[7] = MSW(MSD(mreq->rcv_dma));
5392
5393 mcp->mb[10] = LSW(mreq->transfer_size);
5394
5395 mcp->mb[14] = LSW(mreq->send_dma);
5396 mcp->mb[15] = MSW(mreq->send_dma);
5397 mcp->mb[20] = LSW(MSD(mreq->send_dma));
5398 mcp->mb[21] = MSW(MSD(mreq->send_dma));
5399
5400 mcp->out_mb = MBX_21|MBX_20|MBX_17|MBX_16|MBX_15|
5401 MBX_14|MBX_10|MBX_7|MBX_6|MBX_1|MBX_0;
5402 if (IS_CNA_CAPABLE(ha))
5403 mcp->out_mb |= MBX_2;
5404
5405 mcp->in_mb = MBX_0;
5406 if (IS_CNA_CAPABLE(ha) || IS_QLA24XX_TYPE(ha) || IS_QLA25XX(ha) ||
5407 IS_QLA2031(ha) || IS_QLA27XX(ha) || IS_QLA28XX(ha))
5408 mcp->in_mb |= MBX_1;
5409 if (IS_CNA_CAPABLE(ha) || IS_QLA2031(ha) || IS_QLA27XX(ha) ||
5410 IS_QLA28XX(ha))
5411 mcp->in_mb |= MBX_3;
5412
5413 mcp->tov = MBX_TOV_SECONDS;
5414 mcp->flags = MBX_DMA_OUT|MBX_DMA_IN|IOCTL_CMD;
5415 mcp->buf_size = mreq->transfer_size;
5416
5417 rval = qla2x00_mailbox_command(vha, mcp);
5418
5419 if (rval != QLA_SUCCESS) {
5420 ql_dbg(ql_dbg_mbx, vha, 0x10fb,
5421 "Failed=%x mb[0]=%x mb[1]=%x.\n",
5422 rval, mcp->mb[0], mcp->mb[1]);
5423 } else {
5424 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10fc,
5425 "Done %s.\n", __func__);
5426 }
5427
5428 /* Copy mailbox information */
5429 memcpy(mresp, mcp->mb, 64);
5430 return rval;
5431 }
5432
5433 int
qla84xx_reset_chip(scsi_qla_host_t * vha,uint16_t enable_diagnostic)5434 qla84xx_reset_chip(scsi_qla_host_t *vha, uint16_t enable_diagnostic)
5435 {
5436 int rval;
5437 mbx_cmd_t mc;
5438 mbx_cmd_t *mcp = &mc;
5439
5440 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10fd,
5441 "Entered %s enable_diag=%d.\n", __func__, enable_diagnostic);
5442
5443 mcp->mb[0] = MBC_ISP84XX_RESET;
5444 mcp->mb[1] = enable_diagnostic;
5445 mcp->out_mb = MBX_1|MBX_0;
5446 mcp->in_mb = MBX_1|MBX_0;
5447 mcp->tov = MBX_TOV_SECONDS;
5448 mcp->flags = MBX_DMA_OUT|MBX_DMA_IN|IOCTL_CMD;
5449 rval = qla2x00_mailbox_command(vha, mcp);
5450
5451 if (rval != QLA_SUCCESS)
5452 ql_dbg(ql_dbg_mbx, vha, 0x10fe, "Failed=%x.\n", rval);
5453 else
5454 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10ff,
5455 "Done %s.\n", __func__);
5456
5457 return rval;
5458 }
5459
5460 int
qla2x00_write_ram_word(scsi_qla_host_t * vha,uint32_t risc_addr,uint32_t data)5461 qla2x00_write_ram_word(scsi_qla_host_t *vha, uint32_t risc_addr, uint32_t data)
5462 {
5463 int rval;
5464 mbx_cmd_t mc;
5465 mbx_cmd_t *mcp = &mc;
5466
5467 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1100,
5468 "Entered %s.\n", __func__);
5469
5470 if (!IS_FWI2_CAPABLE(vha->hw))
5471 return QLA_FUNCTION_FAILED;
5472
5473 mcp->mb[0] = MBC_WRITE_RAM_WORD_EXTENDED;
5474 mcp->mb[1] = LSW(risc_addr);
5475 mcp->mb[2] = LSW(data);
5476 mcp->mb[3] = MSW(data);
5477 mcp->mb[8] = MSW(risc_addr);
5478 mcp->out_mb = MBX_8|MBX_3|MBX_2|MBX_1|MBX_0;
5479 mcp->in_mb = MBX_1|MBX_0;
5480 mcp->tov = MBX_TOV_SECONDS;
5481 mcp->flags = 0;
5482 rval = qla2x00_mailbox_command(vha, mcp);
5483 if (rval != QLA_SUCCESS) {
5484 ql_dbg(ql_dbg_mbx, vha, 0x1101,
5485 "Failed=%x mb[0]=%x mb[1]=%x.\n",
5486 rval, mcp->mb[0], mcp->mb[1]);
5487 } else {
5488 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1102,
5489 "Done %s.\n", __func__);
5490 }
5491
5492 return rval;
5493 }
5494
5495 int
qla81xx_write_mpi_register(scsi_qla_host_t * vha,uint16_t * mb)5496 qla81xx_write_mpi_register(scsi_qla_host_t *vha, uint16_t *mb)
5497 {
5498 int rval;
5499 uint32_t stat, timer;
5500 uint16_t mb0 = 0;
5501 struct qla_hw_data *ha = vha->hw;
5502 struct device_reg_24xx __iomem *reg = &ha->iobase->isp24;
5503
5504 rval = QLA_SUCCESS;
5505
5506 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1103,
5507 "Entered %s.\n", __func__);
5508
5509 clear_bit(MBX_INTERRUPT, &ha->mbx_cmd_flags);
5510
5511 /* Write the MBC data to the registers */
5512 wrt_reg_word(®->mailbox0, MBC_WRITE_MPI_REGISTER);
5513 wrt_reg_word(®->mailbox1, mb[0]);
5514 wrt_reg_word(®->mailbox2, mb[1]);
5515 wrt_reg_word(®->mailbox3, mb[2]);
5516 wrt_reg_word(®->mailbox4, mb[3]);
5517
5518 wrt_reg_dword(®->hccr, HCCRX_SET_HOST_INT);
5519
5520 /* Poll for MBC interrupt */
5521 for (timer = 6000000; timer; timer--) {
5522 /* Check for pending interrupts. */
5523 stat = rd_reg_dword(®->host_status);
5524 if (stat & HSRX_RISC_INT) {
5525 stat &= 0xff;
5526
5527 if (stat == 0x1 || stat == 0x2 ||
5528 stat == 0x10 || stat == 0x11) {
5529 set_bit(MBX_INTERRUPT,
5530 &ha->mbx_cmd_flags);
5531 mb0 = rd_reg_word(®->mailbox0);
5532 wrt_reg_dword(®->hccr,
5533 HCCRX_CLR_RISC_INT);
5534 rd_reg_dword(®->hccr);
5535 break;
5536 }
5537 }
5538 udelay(5);
5539 }
5540
5541 if (test_and_clear_bit(MBX_INTERRUPT, &ha->mbx_cmd_flags))
5542 rval = mb0 & MBS_MASK;
5543 else
5544 rval = QLA_FUNCTION_FAILED;
5545
5546 if (rval != QLA_SUCCESS) {
5547 ql_dbg(ql_dbg_mbx, vha, 0x1104,
5548 "Failed=%x mb[0]=%x.\n", rval, mb[0]);
5549 } else {
5550 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1105,
5551 "Done %s.\n", __func__);
5552 }
5553
5554 return rval;
5555 }
5556
5557 /* Set the specified data rate */
5558 int
qla2x00_set_data_rate(scsi_qla_host_t * vha,uint16_t mode)5559 qla2x00_set_data_rate(scsi_qla_host_t *vha, uint16_t mode)
5560 {
5561 int rval;
5562 mbx_cmd_t mc;
5563 mbx_cmd_t *mcp = &mc;
5564 struct qla_hw_data *ha = vha->hw;
5565 uint16_t val;
5566
5567 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1106,
5568 "Entered %s speed:0x%x mode:0x%x.\n", __func__, ha->set_data_rate,
5569 mode);
5570
5571 if (!IS_FWI2_CAPABLE(ha))
5572 return QLA_FUNCTION_FAILED;
5573
5574 memset(mcp, 0, sizeof(*mcp));
5575 switch (ha->set_data_rate) {
5576 case PORT_SPEED_AUTO:
5577 case PORT_SPEED_4GB:
5578 case PORT_SPEED_8GB:
5579 case PORT_SPEED_16GB:
5580 case PORT_SPEED_32GB:
5581 val = ha->set_data_rate;
5582 break;
5583 default:
5584 ql_log(ql_log_warn, vha, 0x1199,
5585 "Unrecognized speed setting:%d. Setting Autoneg\n",
5586 ha->set_data_rate);
5587 val = ha->set_data_rate = PORT_SPEED_AUTO;
5588 break;
5589 }
5590
5591 mcp->mb[0] = MBC_DATA_RATE;
5592 mcp->mb[1] = mode;
5593 mcp->mb[2] = val;
5594
5595 mcp->out_mb = MBX_2|MBX_1|MBX_0;
5596 mcp->in_mb = MBX_2|MBX_1|MBX_0;
5597 if (IS_QLA83XX(ha) || IS_QLA27XX(ha) || IS_QLA28XX(ha))
5598 mcp->in_mb |= MBX_4|MBX_3;
5599 mcp->tov = MBX_TOV_SECONDS;
5600 mcp->flags = 0;
5601 rval = qla2x00_mailbox_command(vha, mcp);
5602 if (rval != QLA_SUCCESS) {
5603 ql_dbg(ql_dbg_mbx, vha, 0x1107,
5604 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
5605 } else {
5606 if (mcp->mb[1] != 0x7)
5607 ql_dbg(ql_dbg_mbx, vha, 0x1179,
5608 "Speed set:0x%x\n", mcp->mb[1]);
5609
5610 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1108,
5611 "Done %s.\n", __func__);
5612 }
5613
5614 return rval;
5615 }
5616
5617 int
qla2x00_get_data_rate(scsi_qla_host_t * vha)5618 qla2x00_get_data_rate(scsi_qla_host_t *vha)
5619 {
5620 int rval;
5621 mbx_cmd_t mc;
5622 mbx_cmd_t *mcp = &mc;
5623 struct qla_hw_data *ha = vha->hw;
5624
5625 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1106,
5626 "Entered %s.\n", __func__);
5627
5628 if (!IS_FWI2_CAPABLE(ha))
5629 return QLA_FUNCTION_FAILED;
5630
5631 mcp->mb[0] = MBC_DATA_RATE;
5632 mcp->mb[1] = QLA_GET_DATA_RATE;
5633 mcp->out_mb = MBX_1|MBX_0;
5634 mcp->in_mb = MBX_2|MBX_1|MBX_0;
5635 if (IS_QLA83XX(ha) || IS_QLA27XX(ha) || IS_QLA28XX(ha))
5636 mcp->in_mb |= MBX_4|MBX_3;
5637 mcp->tov = MBX_TOV_SECONDS;
5638 mcp->flags = 0;
5639 rval = qla2x00_mailbox_command(vha, mcp);
5640 if (rval != QLA_SUCCESS) {
5641 ql_dbg(ql_dbg_mbx, vha, 0x1107,
5642 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
5643 } else {
5644 if (mcp->mb[1] != 0x7)
5645 ha->link_data_rate = mcp->mb[1];
5646
5647 if (IS_QLA83XX(ha) || IS_QLA27XX(ha) || IS_QLA28XX(ha)) {
5648 if (mcp->mb[4] & BIT_0)
5649 ql_log(ql_log_info, vha, 0x11a2,
5650 "FEC=enabled (data rate).\n");
5651 }
5652
5653 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1108,
5654 "Done %s.\n", __func__);
5655 if (mcp->mb[1] != 0x7)
5656 ha->link_data_rate = mcp->mb[1];
5657 }
5658
5659 return rval;
5660 }
5661
5662 int
qla81xx_get_port_config(scsi_qla_host_t * vha,uint16_t * mb)5663 qla81xx_get_port_config(scsi_qla_host_t *vha, uint16_t *mb)
5664 {
5665 int rval;
5666 mbx_cmd_t mc;
5667 mbx_cmd_t *mcp = &mc;
5668 struct qla_hw_data *ha = vha->hw;
5669
5670 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1109,
5671 "Entered %s.\n", __func__);
5672
5673 if (!IS_QLA81XX(ha) && !IS_QLA83XX(ha) && !IS_QLA8044(ha) &&
5674 !IS_QLA27XX(ha) && !IS_QLA28XX(ha))
5675 return QLA_FUNCTION_FAILED;
5676 mcp->mb[0] = MBC_GET_PORT_CONFIG;
5677 mcp->out_mb = MBX_0;
5678 mcp->in_mb = MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
5679 mcp->tov = MBX_TOV_SECONDS;
5680 mcp->flags = 0;
5681
5682 rval = qla2x00_mailbox_command(vha, mcp);
5683
5684 if (rval != QLA_SUCCESS) {
5685 ql_dbg(ql_dbg_mbx, vha, 0x110a,
5686 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
5687 } else {
5688 /* Copy all bits to preserve original value */
5689 memcpy(mb, &mcp->mb[1], sizeof(uint16_t) * 4);
5690
5691 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x110b,
5692 "Done %s.\n", __func__);
5693 }
5694 return rval;
5695 }
5696
5697 int
qla81xx_set_port_config(scsi_qla_host_t * vha,uint16_t * mb)5698 qla81xx_set_port_config(scsi_qla_host_t *vha, uint16_t *mb)
5699 {
5700 int rval;
5701 mbx_cmd_t mc;
5702 mbx_cmd_t *mcp = &mc;
5703
5704 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x110c,
5705 "Entered %s.\n", __func__);
5706
5707 mcp->mb[0] = MBC_SET_PORT_CONFIG;
5708 /* Copy all bits to preserve original setting */
5709 memcpy(&mcp->mb[1], mb, sizeof(uint16_t) * 4);
5710 mcp->out_mb = MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
5711 mcp->in_mb = MBX_0;
5712 mcp->tov = MBX_TOV_SECONDS;
5713 mcp->flags = 0;
5714 rval = qla2x00_mailbox_command(vha, mcp);
5715
5716 if (rval != QLA_SUCCESS) {
5717 ql_dbg(ql_dbg_mbx, vha, 0x110d,
5718 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
5719 } else
5720 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x110e,
5721 "Done %s.\n", __func__);
5722
5723 return rval;
5724 }
5725
5726
5727 int
qla24xx_set_fcp_prio(scsi_qla_host_t * vha,uint16_t loop_id,uint16_t priority,uint16_t * mb)5728 qla24xx_set_fcp_prio(scsi_qla_host_t *vha, uint16_t loop_id, uint16_t priority,
5729 uint16_t *mb)
5730 {
5731 int rval;
5732 mbx_cmd_t mc;
5733 mbx_cmd_t *mcp = &mc;
5734 struct qla_hw_data *ha = vha->hw;
5735
5736 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x110f,
5737 "Entered %s.\n", __func__);
5738
5739 if (!IS_QLA24XX_TYPE(ha) && !IS_QLA25XX(ha))
5740 return QLA_FUNCTION_FAILED;
5741
5742 mcp->mb[0] = MBC_PORT_PARAMS;
5743 mcp->mb[1] = loop_id;
5744 if (ha->flags.fcp_prio_enabled)
5745 mcp->mb[2] = BIT_1;
5746 else
5747 mcp->mb[2] = BIT_2;
5748 mcp->mb[4] = priority & 0xf;
5749 mcp->mb[9] = vha->vp_idx;
5750 mcp->out_mb = MBX_9|MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
5751 mcp->in_mb = MBX_4|MBX_3|MBX_1|MBX_0;
5752 mcp->tov = MBX_TOV_SECONDS;
5753 mcp->flags = 0;
5754 rval = qla2x00_mailbox_command(vha, mcp);
5755 if (mb != NULL) {
5756 mb[0] = mcp->mb[0];
5757 mb[1] = mcp->mb[1];
5758 mb[3] = mcp->mb[3];
5759 mb[4] = mcp->mb[4];
5760 }
5761
5762 if (rval != QLA_SUCCESS) {
5763 ql_dbg(ql_dbg_mbx, vha, 0x10cd, "Failed=%x.\n", rval);
5764 } else {
5765 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10cc,
5766 "Done %s.\n", __func__);
5767 }
5768
5769 return rval;
5770 }
5771
5772 int
qla2x00_get_thermal_temp(scsi_qla_host_t * vha,uint16_t * temp)5773 qla2x00_get_thermal_temp(scsi_qla_host_t *vha, uint16_t *temp)
5774 {
5775 int rval = QLA_FUNCTION_FAILED;
5776 struct qla_hw_data *ha = vha->hw;
5777 uint8_t byte;
5778
5779 if (!IS_FWI2_CAPABLE(ha) || IS_QLA24XX_TYPE(ha) || IS_QLA81XX(ha)) {
5780 ql_dbg(ql_dbg_mbx, vha, 0x1150,
5781 "Thermal not supported by this card.\n");
5782 return rval;
5783 }
5784
5785 if (IS_QLA25XX(ha)) {
5786 if (ha->pdev->subsystem_vendor == PCI_VENDOR_ID_QLOGIC &&
5787 ha->pdev->subsystem_device == 0x0175) {
5788 rval = qla2x00_read_sfp(vha, 0, &byte,
5789 0x98, 0x1, 1, BIT_13|BIT_0);
5790 *temp = byte;
5791 return rval;
5792 }
5793 if (ha->pdev->subsystem_vendor == PCI_VENDOR_ID_HP &&
5794 ha->pdev->subsystem_device == 0x338e) {
5795 rval = qla2x00_read_sfp(vha, 0, &byte,
5796 0x98, 0x1, 1, BIT_15|BIT_14|BIT_0);
5797 *temp = byte;
5798 return rval;
5799 }
5800 ql_dbg(ql_dbg_mbx, vha, 0x10c9,
5801 "Thermal not supported by this card.\n");
5802 return rval;
5803 }
5804
5805 if (IS_QLA82XX(ha)) {
5806 *temp = qla82xx_read_temperature(vha);
5807 rval = QLA_SUCCESS;
5808 return rval;
5809 } else if (IS_QLA8044(ha)) {
5810 *temp = qla8044_read_temperature(vha);
5811 rval = QLA_SUCCESS;
5812 return rval;
5813 }
5814
5815 rval = qla2x00_read_asic_temperature(vha, temp);
5816 return rval;
5817 }
5818
5819 int
qla82xx_mbx_intr_enable(scsi_qla_host_t * vha)5820 qla82xx_mbx_intr_enable(scsi_qla_host_t *vha)
5821 {
5822 int rval;
5823 struct qla_hw_data *ha = vha->hw;
5824 mbx_cmd_t mc;
5825 mbx_cmd_t *mcp = &mc;
5826
5827 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1017,
5828 "Entered %s.\n", __func__);
5829
5830 if (!IS_FWI2_CAPABLE(ha))
5831 return QLA_FUNCTION_FAILED;
5832
5833 memset(mcp, 0, sizeof(mbx_cmd_t));
5834 mcp->mb[0] = MBC_TOGGLE_INTERRUPT;
5835 mcp->mb[1] = 1;
5836
5837 mcp->out_mb = MBX_1|MBX_0;
5838 mcp->in_mb = MBX_0;
5839 mcp->tov = MBX_TOV_SECONDS;
5840 mcp->flags = 0;
5841
5842 rval = qla2x00_mailbox_command(vha, mcp);
5843 if (rval != QLA_SUCCESS) {
5844 ql_dbg(ql_dbg_mbx, vha, 0x1016,
5845 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
5846 } else {
5847 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x100e,
5848 "Done %s.\n", __func__);
5849 }
5850
5851 return rval;
5852 }
5853
5854 int
qla82xx_mbx_intr_disable(scsi_qla_host_t * vha)5855 qla82xx_mbx_intr_disable(scsi_qla_host_t *vha)
5856 {
5857 int rval;
5858 struct qla_hw_data *ha = vha->hw;
5859 mbx_cmd_t mc;
5860 mbx_cmd_t *mcp = &mc;
5861
5862 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x100d,
5863 "Entered %s.\n", __func__);
5864
5865 if (!IS_P3P_TYPE(ha))
5866 return QLA_FUNCTION_FAILED;
5867
5868 memset(mcp, 0, sizeof(mbx_cmd_t));
5869 mcp->mb[0] = MBC_TOGGLE_INTERRUPT;
5870 mcp->mb[1] = 0;
5871
5872 mcp->out_mb = MBX_1|MBX_0;
5873 mcp->in_mb = MBX_0;
5874 mcp->tov = MBX_TOV_SECONDS;
5875 mcp->flags = 0;
5876
5877 rval = qla2x00_mailbox_command(vha, mcp);
5878 if (rval != QLA_SUCCESS) {
5879 ql_dbg(ql_dbg_mbx, vha, 0x100c,
5880 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
5881 } else {
5882 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x100b,
5883 "Done %s.\n", __func__);
5884 }
5885
5886 return rval;
5887 }
5888
5889 int
qla82xx_md_get_template_size(scsi_qla_host_t * vha)5890 qla82xx_md_get_template_size(scsi_qla_host_t *vha)
5891 {
5892 struct qla_hw_data *ha = vha->hw;
5893 mbx_cmd_t mc;
5894 mbx_cmd_t *mcp = &mc;
5895 int rval = QLA_FUNCTION_FAILED;
5896
5897 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x111f,
5898 "Entered %s.\n", __func__);
5899
5900 memset(mcp->mb, 0 , sizeof(mcp->mb));
5901 mcp->mb[0] = LSW(MBC_DIAGNOSTIC_MINIDUMP_TEMPLATE);
5902 mcp->mb[1] = MSW(MBC_DIAGNOSTIC_MINIDUMP_TEMPLATE);
5903 mcp->mb[2] = LSW(RQST_TMPLT_SIZE);
5904 mcp->mb[3] = MSW(RQST_TMPLT_SIZE);
5905
5906 mcp->out_mb = MBX_3|MBX_2|MBX_1|MBX_0;
5907 mcp->in_mb = MBX_14|MBX_13|MBX_12|MBX_11|MBX_10|MBX_9|MBX_8|
5908 MBX_7|MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
5909
5910 mcp->flags = MBX_DMA_OUT|MBX_DMA_IN|IOCTL_CMD;
5911 mcp->tov = MBX_TOV_SECONDS;
5912 rval = qla2x00_mailbox_command(vha, mcp);
5913
5914 /* Always copy back return mailbox values. */
5915 if (rval != QLA_SUCCESS) {
5916 ql_dbg(ql_dbg_mbx, vha, 0x1120,
5917 "mailbox command FAILED=0x%x, subcode=%x.\n",
5918 (mcp->mb[1] << 16) | mcp->mb[0],
5919 (mcp->mb[3] << 16) | mcp->mb[2]);
5920 } else {
5921 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1121,
5922 "Done %s.\n", __func__);
5923 ha->md_template_size = ((mcp->mb[3] << 16) | mcp->mb[2]);
5924 if (!ha->md_template_size) {
5925 ql_dbg(ql_dbg_mbx, vha, 0x1122,
5926 "Null template size obtained.\n");
5927 rval = QLA_FUNCTION_FAILED;
5928 }
5929 }
5930 return rval;
5931 }
5932
5933 int
qla82xx_md_get_template(scsi_qla_host_t * vha)5934 qla82xx_md_get_template(scsi_qla_host_t *vha)
5935 {
5936 struct qla_hw_data *ha = vha->hw;
5937 mbx_cmd_t mc;
5938 mbx_cmd_t *mcp = &mc;
5939 int rval = QLA_FUNCTION_FAILED;
5940
5941 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1123,
5942 "Entered %s.\n", __func__);
5943
5944 ha->md_tmplt_hdr = dma_alloc_coherent(&ha->pdev->dev,
5945 ha->md_template_size, &ha->md_tmplt_hdr_dma, GFP_KERNEL);
5946 if (!ha->md_tmplt_hdr) {
5947 ql_log(ql_log_warn, vha, 0x1124,
5948 "Unable to allocate memory for Minidump template.\n");
5949 return rval;
5950 }
5951
5952 memset(mcp->mb, 0 , sizeof(mcp->mb));
5953 mcp->mb[0] = LSW(MBC_DIAGNOSTIC_MINIDUMP_TEMPLATE);
5954 mcp->mb[1] = MSW(MBC_DIAGNOSTIC_MINIDUMP_TEMPLATE);
5955 mcp->mb[2] = LSW(RQST_TMPLT);
5956 mcp->mb[3] = MSW(RQST_TMPLT);
5957 mcp->mb[4] = LSW(LSD(ha->md_tmplt_hdr_dma));
5958 mcp->mb[5] = MSW(LSD(ha->md_tmplt_hdr_dma));
5959 mcp->mb[6] = LSW(MSD(ha->md_tmplt_hdr_dma));
5960 mcp->mb[7] = MSW(MSD(ha->md_tmplt_hdr_dma));
5961 mcp->mb[8] = LSW(ha->md_template_size);
5962 mcp->mb[9] = MSW(ha->md_template_size);
5963
5964 mcp->flags = MBX_DMA_OUT|MBX_DMA_IN|IOCTL_CMD;
5965 mcp->tov = MBX_TOV_SECONDS;
5966 mcp->out_mb = MBX_11|MBX_10|MBX_9|MBX_8|
5967 MBX_7|MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
5968 mcp->in_mb = MBX_3|MBX_2|MBX_1|MBX_0;
5969 rval = qla2x00_mailbox_command(vha, mcp);
5970
5971 if (rval != QLA_SUCCESS) {
5972 ql_dbg(ql_dbg_mbx, vha, 0x1125,
5973 "mailbox command FAILED=0x%x, subcode=%x.\n",
5974 ((mcp->mb[1] << 16) | mcp->mb[0]),
5975 ((mcp->mb[3] << 16) | mcp->mb[2]));
5976 } else
5977 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1126,
5978 "Done %s.\n", __func__);
5979 return rval;
5980 }
5981
5982 int
qla8044_md_get_template(scsi_qla_host_t * vha)5983 qla8044_md_get_template(scsi_qla_host_t *vha)
5984 {
5985 struct qla_hw_data *ha = vha->hw;
5986 mbx_cmd_t mc;
5987 mbx_cmd_t *mcp = &mc;
5988 int rval = QLA_FUNCTION_FAILED;
5989 int offset = 0, size = MINIDUMP_SIZE_36K;
5990
5991 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0xb11f,
5992 "Entered %s.\n", __func__);
5993
5994 ha->md_tmplt_hdr = dma_alloc_coherent(&ha->pdev->dev,
5995 ha->md_template_size, &ha->md_tmplt_hdr_dma, GFP_KERNEL);
5996 if (!ha->md_tmplt_hdr) {
5997 ql_log(ql_log_warn, vha, 0xb11b,
5998 "Unable to allocate memory for Minidump template.\n");
5999 return rval;
6000 }
6001
6002 memset(mcp->mb, 0 , sizeof(mcp->mb));
6003 while (offset < ha->md_template_size) {
6004 mcp->mb[0] = LSW(MBC_DIAGNOSTIC_MINIDUMP_TEMPLATE);
6005 mcp->mb[1] = MSW(MBC_DIAGNOSTIC_MINIDUMP_TEMPLATE);
6006 mcp->mb[2] = LSW(RQST_TMPLT);
6007 mcp->mb[3] = MSW(RQST_TMPLT);
6008 mcp->mb[4] = LSW(LSD(ha->md_tmplt_hdr_dma + offset));
6009 mcp->mb[5] = MSW(LSD(ha->md_tmplt_hdr_dma + offset));
6010 mcp->mb[6] = LSW(MSD(ha->md_tmplt_hdr_dma + offset));
6011 mcp->mb[7] = MSW(MSD(ha->md_tmplt_hdr_dma + offset));
6012 mcp->mb[8] = LSW(size);
6013 mcp->mb[9] = MSW(size);
6014 mcp->mb[10] = offset & 0x0000FFFF;
6015 mcp->mb[11] = offset & 0xFFFF0000;
6016 mcp->flags = MBX_DMA_OUT|MBX_DMA_IN|IOCTL_CMD;
6017 mcp->tov = MBX_TOV_SECONDS;
6018 mcp->out_mb = MBX_11|MBX_10|MBX_9|MBX_8|
6019 MBX_7|MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
6020 mcp->in_mb = MBX_3|MBX_2|MBX_1|MBX_0;
6021 rval = qla2x00_mailbox_command(vha, mcp);
6022
6023 if (rval != QLA_SUCCESS) {
6024 ql_dbg(ql_dbg_mbx, vha, 0xb11c,
6025 "mailbox command FAILED=0x%x, subcode=%x.\n",
6026 ((mcp->mb[1] << 16) | mcp->mb[0]),
6027 ((mcp->mb[3] << 16) | mcp->mb[2]));
6028 return rval;
6029 } else
6030 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0xb11d,
6031 "Done %s.\n", __func__);
6032 offset = offset + size;
6033 }
6034 return rval;
6035 }
6036
6037 int
qla81xx_set_led_config(scsi_qla_host_t * vha,uint16_t * led_cfg)6038 qla81xx_set_led_config(scsi_qla_host_t *vha, uint16_t *led_cfg)
6039 {
6040 int rval;
6041 struct qla_hw_data *ha = vha->hw;
6042 mbx_cmd_t mc;
6043 mbx_cmd_t *mcp = &mc;
6044
6045 if (!IS_QLA81XX(ha) && !IS_QLA8031(ha))
6046 return QLA_FUNCTION_FAILED;
6047
6048 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1133,
6049 "Entered %s.\n", __func__);
6050
6051 memset(mcp, 0, sizeof(mbx_cmd_t));
6052 mcp->mb[0] = MBC_SET_LED_CONFIG;
6053 mcp->mb[1] = led_cfg[0];
6054 mcp->mb[2] = led_cfg[1];
6055 if (IS_QLA8031(ha)) {
6056 mcp->mb[3] = led_cfg[2];
6057 mcp->mb[4] = led_cfg[3];
6058 mcp->mb[5] = led_cfg[4];
6059 mcp->mb[6] = led_cfg[5];
6060 }
6061
6062 mcp->out_mb = MBX_2|MBX_1|MBX_0;
6063 if (IS_QLA8031(ha))
6064 mcp->out_mb |= MBX_6|MBX_5|MBX_4|MBX_3;
6065 mcp->in_mb = MBX_0;
6066 mcp->tov = MBX_TOV_SECONDS;
6067 mcp->flags = 0;
6068
6069 rval = qla2x00_mailbox_command(vha, mcp);
6070 if (rval != QLA_SUCCESS) {
6071 ql_dbg(ql_dbg_mbx, vha, 0x1134,
6072 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
6073 } else {
6074 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1135,
6075 "Done %s.\n", __func__);
6076 }
6077
6078 return rval;
6079 }
6080
6081 int
qla81xx_get_led_config(scsi_qla_host_t * vha,uint16_t * led_cfg)6082 qla81xx_get_led_config(scsi_qla_host_t *vha, uint16_t *led_cfg)
6083 {
6084 int rval;
6085 struct qla_hw_data *ha = vha->hw;
6086 mbx_cmd_t mc;
6087 mbx_cmd_t *mcp = &mc;
6088
6089 if (!IS_QLA81XX(ha) && !IS_QLA8031(ha))
6090 return QLA_FUNCTION_FAILED;
6091
6092 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1136,
6093 "Entered %s.\n", __func__);
6094
6095 memset(mcp, 0, sizeof(mbx_cmd_t));
6096 mcp->mb[0] = MBC_GET_LED_CONFIG;
6097
6098 mcp->out_mb = MBX_0;
6099 mcp->in_mb = MBX_2|MBX_1|MBX_0;
6100 if (IS_QLA8031(ha))
6101 mcp->in_mb |= MBX_6|MBX_5|MBX_4|MBX_3;
6102 mcp->tov = MBX_TOV_SECONDS;
6103 mcp->flags = 0;
6104
6105 rval = qla2x00_mailbox_command(vha, mcp);
6106 if (rval != QLA_SUCCESS) {
6107 ql_dbg(ql_dbg_mbx, vha, 0x1137,
6108 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
6109 } else {
6110 led_cfg[0] = mcp->mb[1];
6111 led_cfg[1] = mcp->mb[2];
6112 if (IS_QLA8031(ha)) {
6113 led_cfg[2] = mcp->mb[3];
6114 led_cfg[3] = mcp->mb[4];
6115 led_cfg[4] = mcp->mb[5];
6116 led_cfg[5] = mcp->mb[6];
6117 }
6118 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1138,
6119 "Done %s.\n", __func__);
6120 }
6121
6122 return rval;
6123 }
6124
6125 int
qla82xx_mbx_beacon_ctl(scsi_qla_host_t * vha,int enable)6126 qla82xx_mbx_beacon_ctl(scsi_qla_host_t *vha, int enable)
6127 {
6128 int rval;
6129 struct qla_hw_data *ha = vha->hw;
6130 mbx_cmd_t mc;
6131 mbx_cmd_t *mcp = &mc;
6132
6133 if (!IS_P3P_TYPE(ha))
6134 return QLA_FUNCTION_FAILED;
6135
6136 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1127,
6137 "Entered %s.\n", __func__);
6138
6139 memset(mcp, 0, sizeof(mbx_cmd_t));
6140 mcp->mb[0] = MBC_SET_LED_CONFIG;
6141 if (enable)
6142 mcp->mb[7] = 0xE;
6143 else
6144 mcp->mb[7] = 0xD;
6145
6146 mcp->out_mb = MBX_7|MBX_0;
6147 mcp->in_mb = MBX_0;
6148 mcp->tov = MBX_TOV_SECONDS;
6149 mcp->flags = 0;
6150
6151 rval = qla2x00_mailbox_command(vha, mcp);
6152 if (rval != QLA_SUCCESS) {
6153 ql_dbg(ql_dbg_mbx, vha, 0x1128,
6154 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
6155 } else {
6156 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1129,
6157 "Done %s.\n", __func__);
6158 }
6159
6160 return rval;
6161 }
6162
6163 int
qla83xx_wr_reg(scsi_qla_host_t * vha,uint32_t reg,uint32_t data)6164 qla83xx_wr_reg(scsi_qla_host_t *vha, uint32_t reg, uint32_t data)
6165 {
6166 int rval;
6167 struct qla_hw_data *ha = vha->hw;
6168 mbx_cmd_t mc;
6169 mbx_cmd_t *mcp = &mc;
6170
6171 if (!IS_QLA83XX(ha) && !IS_QLA27XX(ha) && !IS_QLA28XX(ha))
6172 return QLA_FUNCTION_FAILED;
6173
6174 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1130,
6175 "Entered %s.\n", __func__);
6176
6177 mcp->mb[0] = MBC_WRITE_REMOTE_REG;
6178 mcp->mb[1] = LSW(reg);
6179 mcp->mb[2] = MSW(reg);
6180 mcp->mb[3] = LSW(data);
6181 mcp->mb[4] = MSW(data);
6182 mcp->out_mb = MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
6183
6184 mcp->in_mb = MBX_1|MBX_0;
6185 mcp->tov = MBX_TOV_SECONDS;
6186 mcp->flags = 0;
6187 rval = qla2x00_mailbox_command(vha, mcp);
6188
6189 if (rval != QLA_SUCCESS) {
6190 ql_dbg(ql_dbg_mbx, vha, 0x1131,
6191 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
6192 } else {
6193 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1132,
6194 "Done %s.\n", __func__);
6195 }
6196
6197 return rval;
6198 }
6199
6200 int
qla2x00_port_logout(scsi_qla_host_t * vha,struct fc_port * fcport)6201 qla2x00_port_logout(scsi_qla_host_t *vha, struct fc_port *fcport)
6202 {
6203 int rval;
6204 struct qla_hw_data *ha = vha->hw;
6205 mbx_cmd_t mc;
6206 mbx_cmd_t *mcp = &mc;
6207
6208 if (IS_QLA2100(ha) || IS_QLA2200(ha)) {
6209 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x113b,
6210 "Implicit LOGO Unsupported.\n");
6211 return QLA_FUNCTION_FAILED;
6212 }
6213
6214
6215 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x113c,
6216 "Entering %s.\n", __func__);
6217
6218 /* Perform Implicit LOGO. */
6219 mcp->mb[0] = MBC_PORT_LOGOUT;
6220 mcp->mb[1] = fcport->loop_id;
6221 mcp->mb[10] = BIT_15;
6222 mcp->out_mb = MBX_10|MBX_1|MBX_0;
6223 mcp->in_mb = MBX_0;
6224 mcp->tov = MBX_TOV_SECONDS;
6225 mcp->flags = 0;
6226 rval = qla2x00_mailbox_command(vha, mcp);
6227 if (rval != QLA_SUCCESS)
6228 ql_dbg(ql_dbg_mbx, vha, 0x113d,
6229 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
6230 else
6231 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x113e,
6232 "Done %s.\n", __func__);
6233
6234 return rval;
6235 }
6236
6237 int
qla83xx_rd_reg(scsi_qla_host_t * vha,uint32_t reg,uint32_t * data)6238 qla83xx_rd_reg(scsi_qla_host_t *vha, uint32_t reg, uint32_t *data)
6239 {
6240 int rval;
6241 mbx_cmd_t mc;
6242 mbx_cmd_t *mcp = &mc;
6243 struct qla_hw_data *ha = vha->hw;
6244 unsigned long retry_max_time = jiffies + (2 * HZ);
6245
6246 if (!IS_QLA83XX(ha) && !IS_QLA27XX(ha) && !IS_QLA28XX(ha))
6247 return QLA_FUNCTION_FAILED;
6248
6249 ql_dbg(ql_dbg_mbx, vha, 0x114b, "Entered %s.\n", __func__);
6250
6251 retry_rd_reg:
6252 mcp->mb[0] = MBC_READ_REMOTE_REG;
6253 mcp->mb[1] = LSW(reg);
6254 mcp->mb[2] = MSW(reg);
6255 mcp->out_mb = MBX_2|MBX_1|MBX_0;
6256 mcp->in_mb = MBX_4|MBX_3|MBX_1|MBX_0;
6257 mcp->tov = MBX_TOV_SECONDS;
6258 mcp->flags = 0;
6259 rval = qla2x00_mailbox_command(vha, mcp);
6260
6261 if (rval != QLA_SUCCESS) {
6262 ql_dbg(ql_dbg_mbx, vha, 0x114c,
6263 "Failed=%x mb[0]=%x mb[1]=%x.\n",
6264 rval, mcp->mb[0], mcp->mb[1]);
6265 } else {
6266 *data = (mcp->mb[3] | (mcp->mb[4] << 16));
6267 if (*data == QLA8XXX_BAD_VALUE) {
6268 /*
6269 * During soft-reset CAMRAM register reads might
6270 * return 0xbad0bad0. So retry for MAX of 2 sec
6271 * while reading camram registers.
6272 */
6273 if (time_after(jiffies, retry_max_time)) {
6274 ql_dbg(ql_dbg_mbx, vha, 0x1141,
6275 "Failure to read CAMRAM register. "
6276 "data=0x%x.\n", *data);
6277 return QLA_FUNCTION_FAILED;
6278 }
6279 msleep(100);
6280 goto retry_rd_reg;
6281 }
6282 ql_dbg(ql_dbg_mbx, vha, 0x1142, "Done %s.\n", __func__);
6283 }
6284
6285 return rval;
6286 }
6287
6288 int
qla83xx_restart_nic_firmware(scsi_qla_host_t * vha)6289 qla83xx_restart_nic_firmware(scsi_qla_host_t *vha)
6290 {
6291 int rval;
6292 mbx_cmd_t mc;
6293 mbx_cmd_t *mcp = &mc;
6294 struct qla_hw_data *ha = vha->hw;
6295
6296 if (!IS_QLA83XX(ha))
6297 return QLA_FUNCTION_FAILED;
6298
6299 ql_dbg(ql_dbg_mbx, vha, 0x1143, "Entered %s.\n", __func__);
6300
6301 mcp->mb[0] = MBC_RESTART_NIC_FIRMWARE;
6302 mcp->out_mb = MBX_0;
6303 mcp->in_mb = MBX_1|MBX_0;
6304 mcp->tov = MBX_TOV_SECONDS;
6305 mcp->flags = 0;
6306 rval = qla2x00_mailbox_command(vha, mcp);
6307
6308 if (rval != QLA_SUCCESS) {
6309 ql_dbg(ql_dbg_mbx, vha, 0x1144,
6310 "Failed=%x mb[0]=%x mb[1]=%x.\n",
6311 rval, mcp->mb[0], mcp->mb[1]);
6312 qla2xxx_dump_fw(vha);
6313 } else {
6314 ql_dbg(ql_dbg_mbx, vha, 0x1145, "Done %s.\n", __func__);
6315 }
6316
6317 return rval;
6318 }
6319
6320 int
qla83xx_access_control(scsi_qla_host_t * vha,uint16_t options,uint32_t start_addr,uint32_t end_addr,uint16_t * sector_size)6321 qla83xx_access_control(scsi_qla_host_t *vha, uint16_t options,
6322 uint32_t start_addr, uint32_t end_addr, uint16_t *sector_size)
6323 {
6324 int rval;
6325 mbx_cmd_t mc;
6326 mbx_cmd_t *mcp = &mc;
6327 uint8_t subcode = (uint8_t)options;
6328 struct qla_hw_data *ha = vha->hw;
6329
6330 if (!IS_QLA8031(ha))
6331 return QLA_FUNCTION_FAILED;
6332
6333 ql_dbg(ql_dbg_mbx, vha, 0x1146, "Entered %s.\n", __func__);
6334
6335 mcp->mb[0] = MBC_SET_ACCESS_CONTROL;
6336 mcp->mb[1] = options;
6337 mcp->out_mb = MBX_1|MBX_0;
6338 if (subcode & BIT_2) {
6339 mcp->mb[2] = LSW(start_addr);
6340 mcp->mb[3] = MSW(start_addr);
6341 mcp->mb[4] = LSW(end_addr);
6342 mcp->mb[5] = MSW(end_addr);
6343 mcp->out_mb |= MBX_5|MBX_4|MBX_3|MBX_2;
6344 }
6345 mcp->in_mb = MBX_2|MBX_1|MBX_0;
6346 if (!(subcode & (BIT_2 | BIT_5)))
6347 mcp->in_mb |= MBX_4|MBX_3;
6348 mcp->tov = MBX_TOV_SECONDS;
6349 mcp->flags = 0;
6350 rval = qla2x00_mailbox_command(vha, mcp);
6351
6352 if (rval != QLA_SUCCESS) {
6353 ql_dbg(ql_dbg_mbx, vha, 0x1147,
6354 "Failed=%x mb[0]=%x mb[1]=%x mb[2]=%x mb[3]=%x mb[4]=%x.\n",
6355 rval, mcp->mb[0], mcp->mb[1], mcp->mb[2], mcp->mb[3],
6356 mcp->mb[4]);
6357 qla2xxx_dump_fw(vha);
6358 } else {
6359 if (subcode & BIT_5)
6360 *sector_size = mcp->mb[1];
6361 else if (subcode & (BIT_6 | BIT_7)) {
6362 ql_dbg(ql_dbg_mbx, vha, 0x1148,
6363 "Driver-lock id=%x%x", mcp->mb[4], mcp->mb[3]);
6364 } else if (subcode & (BIT_3 | BIT_4)) {
6365 ql_dbg(ql_dbg_mbx, vha, 0x1149,
6366 "Flash-lock id=%x%x", mcp->mb[4], mcp->mb[3]);
6367 }
6368 ql_dbg(ql_dbg_mbx, vha, 0x114a, "Done %s.\n", __func__);
6369 }
6370
6371 return rval;
6372 }
6373
6374 int
qla2x00_dump_mctp_data(scsi_qla_host_t * vha,dma_addr_t req_dma,uint32_t addr,uint32_t size)6375 qla2x00_dump_mctp_data(scsi_qla_host_t *vha, dma_addr_t req_dma, uint32_t addr,
6376 uint32_t size)
6377 {
6378 int rval;
6379 mbx_cmd_t mc;
6380 mbx_cmd_t *mcp = &mc;
6381
6382 if (!IS_MCTP_CAPABLE(vha->hw))
6383 return QLA_FUNCTION_FAILED;
6384
6385 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x114f,
6386 "Entered %s.\n", __func__);
6387
6388 mcp->mb[0] = MBC_DUMP_RISC_RAM_EXTENDED;
6389 mcp->mb[1] = LSW(addr);
6390 mcp->mb[2] = MSW(req_dma);
6391 mcp->mb[3] = LSW(req_dma);
6392 mcp->mb[4] = MSW(size);
6393 mcp->mb[5] = LSW(size);
6394 mcp->mb[6] = MSW(MSD(req_dma));
6395 mcp->mb[7] = LSW(MSD(req_dma));
6396 mcp->mb[8] = MSW(addr);
6397 /* Setting RAM ID to valid */
6398 /* For MCTP RAM ID is 0x40 */
6399 mcp->mb[10] = BIT_7 | 0x40;
6400
6401 mcp->out_mb |= MBX_10|MBX_8|MBX_7|MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|MBX_1|
6402 MBX_0;
6403
6404 mcp->in_mb = MBX_0;
6405 mcp->tov = MBX_TOV_SECONDS;
6406 mcp->flags = 0;
6407 rval = qla2x00_mailbox_command(vha, mcp);
6408
6409 if (rval != QLA_SUCCESS) {
6410 ql_dbg(ql_dbg_mbx, vha, 0x114e,
6411 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
6412 } else {
6413 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x114d,
6414 "Done %s.\n", __func__);
6415 }
6416
6417 return rval;
6418 }
6419
6420 int
qla26xx_dport_diagnostics(scsi_qla_host_t * vha,void * dd_buf,uint size,uint options)6421 qla26xx_dport_diagnostics(scsi_qla_host_t *vha,
6422 void *dd_buf, uint size, uint options)
6423 {
6424 int rval;
6425 mbx_cmd_t mc;
6426 mbx_cmd_t *mcp = &mc;
6427 dma_addr_t dd_dma;
6428
6429 if (!IS_QLA83XX(vha->hw) && !IS_QLA27XX(vha->hw) &&
6430 !IS_QLA28XX(vha->hw))
6431 return QLA_FUNCTION_FAILED;
6432
6433 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x119f,
6434 "Entered %s.\n", __func__);
6435
6436 dd_dma = dma_map_single(&vha->hw->pdev->dev,
6437 dd_buf, size, DMA_FROM_DEVICE);
6438 if (dma_mapping_error(&vha->hw->pdev->dev, dd_dma)) {
6439 ql_log(ql_log_warn, vha, 0x1194, "Failed to map dma buffer.\n");
6440 return QLA_MEMORY_ALLOC_FAILED;
6441 }
6442
6443 memset(dd_buf, 0, size);
6444
6445 mcp->mb[0] = MBC_DPORT_DIAGNOSTICS;
6446 mcp->mb[1] = options;
6447 mcp->mb[2] = MSW(LSD(dd_dma));
6448 mcp->mb[3] = LSW(LSD(dd_dma));
6449 mcp->mb[6] = MSW(MSD(dd_dma));
6450 mcp->mb[7] = LSW(MSD(dd_dma));
6451 mcp->mb[8] = size;
6452 mcp->out_mb = MBX_8|MBX_7|MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
6453 mcp->in_mb = MBX_3|MBX_2|MBX_1|MBX_0;
6454 mcp->buf_size = size;
6455 mcp->flags = MBX_DMA_IN;
6456 mcp->tov = MBX_TOV_SECONDS * 4;
6457 rval = qla2x00_mailbox_command(vha, mcp);
6458
6459 if (rval != QLA_SUCCESS) {
6460 ql_dbg(ql_dbg_mbx, vha, 0x1195, "Failed=%x.\n", rval);
6461 } else {
6462 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1196,
6463 "Done %s.\n", __func__);
6464 }
6465
6466 dma_unmap_single(&vha->hw->pdev->dev, dd_dma,
6467 size, DMA_FROM_DEVICE);
6468
6469 return rval;
6470 }
6471
qla2x00_async_mb_sp_done(srb_t * sp,int res)6472 static void qla2x00_async_mb_sp_done(srb_t *sp, int res)
6473 {
6474 sp->u.iocb_cmd.u.mbx.rc = res;
6475
6476 complete(&sp->u.iocb_cmd.u.mbx.comp);
6477 /* don't free sp here. Let the caller do the free */
6478 }
6479
6480 /*
6481 * This mailbox uses the iocb interface to send MB command.
6482 * This allows non-critial (non chip setup) command to go
6483 * out in parrallel.
6484 */
qla24xx_send_mb_cmd(struct scsi_qla_host * vha,mbx_cmd_t * mcp)6485 int qla24xx_send_mb_cmd(struct scsi_qla_host *vha, mbx_cmd_t *mcp)
6486 {
6487 int rval = QLA_FUNCTION_FAILED;
6488 srb_t *sp;
6489 struct srb_iocb *c;
6490
6491 if (!vha->hw->flags.fw_started)
6492 goto done;
6493
6494 /* ref: INIT */
6495 sp = qla2x00_get_sp(vha, NULL, GFP_KERNEL);
6496 if (!sp)
6497 goto done;
6498
6499 c = &sp->u.iocb_cmd;
6500 init_completion(&c->u.mbx.comp);
6501
6502 sp->type = SRB_MB_IOCB;
6503 sp->name = mb_to_str(mcp->mb[0]);
6504 qla2x00_init_async_sp(sp, qla2x00_get_async_timeout(vha) + 2,
6505 qla2x00_async_mb_sp_done);
6506
6507 memcpy(sp->u.iocb_cmd.u.mbx.out_mb, mcp->mb, SIZEOF_IOCB_MB_REG);
6508
6509 rval = qla2x00_start_sp(sp);
6510 if (rval != QLA_SUCCESS) {
6511 ql_dbg(ql_dbg_mbx, vha, 0x1018,
6512 "%s: %s Failed submission. %x.\n",
6513 __func__, sp->name, rval);
6514 goto done_free_sp;
6515 }
6516
6517 ql_dbg(ql_dbg_mbx, vha, 0x113f, "MB:%s hndl %x submitted\n",
6518 sp->name, sp->handle);
6519
6520 wait_for_completion(&c->u.mbx.comp);
6521 memcpy(mcp->mb, sp->u.iocb_cmd.u.mbx.in_mb, SIZEOF_IOCB_MB_REG);
6522
6523 rval = c->u.mbx.rc;
6524 switch (rval) {
6525 case QLA_FUNCTION_TIMEOUT:
6526 ql_dbg(ql_dbg_mbx, vha, 0x1140, "%s: %s Timeout. %x.\n",
6527 __func__, sp->name, rval);
6528 break;
6529 case QLA_SUCCESS:
6530 ql_dbg(ql_dbg_mbx, vha, 0x119d, "%s: %s done.\n",
6531 __func__, sp->name);
6532 break;
6533 default:
6534 ql_dbg(ql_dbg_mbx, vha, 0x119e, "%s: %s Failed. %x.\n",
6535 __func__, sp->name, rval);
6536 break;
6537 }
6538
6539 done_free_sp:
6540 /* ref: INIT */
6541 kref_put(&sp->cmd_kref, qla2x00_sp_release);
6542 done:
6543 return rval;
6544 }
6545
6546 /*
6547 * qla24xx_gpdb_wait
6548 * NOTE: Do not call this routine from DPC thread
6549 */
qla24xx_gpdb_wait(struct scsi_qla_host * vha,fc_port_t * fcport,u8 opt)6550 int qla24xx_gpdb_wait(struct scsi_qla_host *vha, fc_port_t *fcport, u8 opt)
6551 {
6552 int rval = QLA_FUNCTION_FAILED;
6553 dma_addr_t pd_dma;
6554 struct port_database_24xx *pd;
6555 struct qla_hw_data *ha = vha->hw;
6556 mbx_cmd_t mc;
6557
6558 if (!vha->hw->flags.fw_started)
6559 goto done;
6560
6561 pd = dma_pool_zalloc(ha->s_dma_pool, GFP_KERNEL, &pd_dma);
6562 if (pd == NULL) {
6563 ql_log(ql_log_warn, vha, 0xd047,
6564 "Failed to allocate port database structure.\n");
6565 goto done_free_sp;
6566 }
6567
6568 memset(&mc, 0, sizeof(mc));
6569 mc.mb[0] = MBC_GET_PORT_DATABASE;
6570 mc.mb[1] = fcport->loop_id;
6571 mc.mb[2] = MSW(pd_dma);
6572 mc.mb[3] = LSW(pd_dma);
6573 mc.mb[6] = MSW(MSD(pd_dma));
6574 mc.mb[7] = LSW(MSD(pd_dma));
6575 mc.mb[9] = vha->vp_idx;
6576 mc.mb[10] = opt;
6577
6578 rval = qla24xx_send_mb_cmd(vha, &mc);
6579 if (rval != QLA_SUCCESS) {
6580 ql_dbg(ql_dbg_mbx, vha, 0x1193,
6581 "%s: %8phC fail\n", __func__, fcport->port_name);
6582 goto done_free_sp;
6583 }
6584
6585 rval = __qla24xx_parse_gpdb(vha, fcport, pd);
6586
6587 ql_dbg(ql_dbg_mbx, vha, 0x1197, "%s: %8phC done\n",
6588 __func__, fcport->port_name);
6589
6590 done_free_sp:
6591 if (pd)
6592 dma_pool_free(ha->s_dma_pool, pd, pd_dma);
6593 done:
6594 return rval;
6595 }
6596
__qla24xx_parse_gpdb(struct scsi_qla_host * vha,fc_port_t * fcport,struct port_database_24xx * pd)6597 int __qla24xx_parse_gpdb(struct scsi_qla_host *vha, fc_port_t *fcport,
6598 struct port_database_24xx *pd)
6599 {
6600 int rval = QLA_SUCCESS;
6601 uint64_t zero = 0;
6602 u8 current_login_state, last_login_state;
6603
6604 if (NVME_TARGET(vha->hw, fcport)) {
6605 current_login_state = pd->current_login_state >> 4;
6606 last_login_state = pd->last_login_state >> 4;
6607 } else {
6608 current_login_state = pd->current_login_state & 0xf;
6609 last_login_state = pd->last_login_state & 0xf;
6610 }
6611
6612 /* Check for logged in state. */
6613 if (current_login_state != PDS_PRLI_COMPLETE) {
6614 ql_dbg(ql_dbg_mbx, vha, 0x119a,
6615 "Unable to verify login-state (%x/%x) for loop_id %x.\n",
6616 current_login_state, last_login_state, fcport->loop_id);
6617 rval = QLA_FUNCTION_FAILED;
6618 goto gpd_error_out;
6619 }
6620
6621 if (fcport->loop_id == FC_NO_LOOP_ID ||
6622 (memcmp(fcport->port_name, (uint8_t *)&zero, 8) &&
6623 memcmp(fcport->port_name, pd->port_name, 8))) {
6624 /* We lost the device mid way. */
6625 rval = QLA_NOT_LOGGED_IN;
6626 goto gpd_error_out;
6627 }
6628
6629 /* Names are little-endian. */
6630 memcpy(fcport->node_name, pd->node_name, WWN_SIZE);
6631 memcpy(fcport->port_name, pd->port_name, WWN_SIZE);
6632
6633 /* Get port_id of device. */
6634 fcport->d_id.b.domain = pd->port_id[0];
6635 fcport->d_id.b.area = pd->port_id[1];
6636 fcport->d_id.b.al_pa = pd->port_id[2];
6637 fcport->d_id.b.rsvd_1 = 0;
6638
6639 ql_dbg(ql_dbg_disc, vha, 0x2062,
6640 "%8phC SVC Param w3 %02x%02x",
6641 fcport->port_name,
6642 pd->prli_svc_param_word_3[1],
6643 pd->prli_svc_param_word_3[0]);
6644
6645 if (NVME_TARGET(vha->hw, fcport)) {
6646 fcport->port_type = FCT_NVME;
6647 if ((pd->prli_svc_param_word_3[0] & BIT_5) == 0)
6648 fcport->port_type |= FCT_NVME_INITIATOR;
6649 if ((pd->prli_svc_param_word_3[0] & BIT_4) == 0)
6650 fcport->port_type |= FCT_NVME_TARGET;
6651 if ((pd->prli_svc_param_word_3[0] & BIT_3) == 0)
6652 fcport->port_type |= FCT_NVME_DISCOVERY;
6653 } else {
6654 /* If not target must be initiator or unknown type. */
6655 if ((pd->prli_svc_param_word_3[0] & BIT_4) == 0)
6656 fcport->port_type = FCT_INITIATOR;
6657 else
6658 fcport->port_type = FCT_TARGET;
6659 }
6660 /* Passback COS information. */
6661 fcport->supported_classes = (pd->flags & PDF_CLASS_2) ?
6662 FC_COS_CLASS2 : FC_COS_CLASS3;
6663
6664 if (pd->prli_svc_param_word_3[0] & BIT_7) {
6665 fcport->flags |= FCF_CONF_COMP_SUPPORTED;
6666 fcport->conf_compl_supported = 1;
6667 }
6668
6669 gpd_error_out:
6670 return rval;
6671 }
6672
6673 /*
6674 * qla24xx_gidlist__wait
6675 * NOTE: don't call this routine from DPC thread.
6676 */
qla24xx_gidlist_wait(struct scsi_qla_host * vha,void * id_list,dma_addr_t id_list_dma,uint16_t * entries)6677 int qla24xx_gidlist_wait(struct scsi_qla_host *vha,
6678 void *id_list, dma_addr_t id_list_dma, uint16_t *entries)
6679 {
6680 int rval = QLA_FUNCTION_FAILED;
6681 mbx_cmd_t mc;
6682
6683 if (!vha->hw->flags.fw_started)
6684 goto done;
6685
6686 memset(&mc, 0, sizeof(mc));
6687 mc.mb[0] = MBC_GET_ID_LIST;
6688 mc.mb[2] = MSW(id_list_dma);
6689 mc.mb[3] = LSW(id_list_dma);
6690 mc.mb[6] = MSW(MSD(id_list_dma));
6691 mc.mb[7] = LSW(MSD(id_list_dma));
6692 mc.mb[8] = 0;
6693 mc.mb[9] = vha->vp_idx;
6694
6695 rval = qla24xx_send_mb_cmd(vha, &mc);
6696 if (rval != QLA_SUCCESS) {
6697 ql_dbg(ql_dbg_mbx, vha, 0x119b,
6698 "%s: fail\n", __func__);
6699 } else {
6700 *entries = mc.mb[1];
6701 ql_dbg(ql_dbg_mbx, vha, 0x119c,
6702 "%s: done\n", __func__);
6703 }
6704 done:
6705 return rval;
6706 }
6707
qla27xx_set_zio_threshold(scsi_qla_host_t * vha,uint16_t value)6708 int qla27xx_set_zio_threshold(scsi_qla_host_t *vha, uint16_t value)
6709 {
6710 int rval;
6711 mbx_cmd_t mc;
6712 mbx_cmd_t *mcp = &mc;
6713
6714 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1200,
6715 "Entered %s\n", __func__);
6716
6717 memset(mcp->mb, 0 , sizeof(mcp->mb));
6718 mcp->mb[0] = MBC_GET_SET_ZIO_THRESHOLD;
6719 mcp->mb[1] = 1;
6720 mcp->mb[2] = value;
6721 mcp->out_mb = MBX_2 | MBX_1 | MBX_0;
6722 mcp->in_mb = MBX_2 | MBX_0;
6723 mcp->tov = MBX_TOV_SECONDS;
6724 mcp->flags = 0;
6725
6726 rval = qla2x00_mailbox_command(vha, mcp);
6727
6728 ql_dbg(ql_dbg_mbx, vha, 0x1201, "%s %x\n",
6729 (rval != QLA_SUCCESS) ? "Failed" : "Done", rval);
6730
6731 return rval;
6732 }
6733
qla27xx_get_zio_threshold(scsi_qla_host_t * vha,uint16_t * value)6734 int qla27xx_get_zio_threshold(scsi_qla_host_t *vha, uint16_t *value)
6735 {
6736 int rval;
6737 mbx_cmd_t mc;
6738 mbx_cmd_t *mcp = &mc;
6739
6740 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1203,
6741 "Entered %s\n", __func__);
6742
6743 memset(mcp->mb, 0, sizeof(mcp->mb));
6744 mcp->mb[0] = MBC_GET_SET_ZIO_THRESHOLD;
6745 mcp->mb[1] = 0;
6746 mcp->out_mb = MBX_1 | MBX_0;
6747 mcp->in_mb = MBX_2 | MBX_0;
6748 mcp->tov = MBX_TOV_SECONDS;
6749 mcp->flags = 0;
6750
6751 rval = qla2x00_mailbox_command(vha, mcp);
6752 if (rval == QLA_SUCCESS)
6753 *value = mc.mb[2];
6754
6755 ql_dbg(ql_dbg_mbx, vha, 0x1205, "%s %x\n",
6756 (rval != QLA_SUCCESS) ? "Failed" : "Done", rval);
6757
6758 return rval;
6759 }
6760
6761 int
qla2x00_read_sfp_dev(struct scsi_qla_host * vha,char * buf,int count)6762 qla2x00_read_sfp_dev(struct scsi_qla_host *vha, char *buf, int count)
6763 {
6764 struct qla_hw_data *ha = vha->hw;
6765 uint16_t iter, addr, offset;
6766 dma_addr_t phys_addr;
6767 int rval, c;
6768 u8 *sfp_data;
6769
6770 memset(ha->sfp_data, 0, SFP_DEV_SIZE);
6771 addr = 0xa0;
6772 phys_addr = ha->sfp_data_dma;
6773 sfp_data = ha->sfp_data;
6774 offset = c = 0;
6775
6776 for (iter = 0; iter < SFP_DEV_SIZE / SFP_BLOCK_SIZE; iter++) {
6777 if (iter == 4) {
6778 /* Skip to next device address. */
6779 addr = 0xa2;
6780 offset = 0;
6781 }
6782
6783 rval = qla2x00_read_sfp(vha, phys_addr, sfp_data,
6784 addr, offset, SFP_BLOCK_SIZE, BIT_1);
6785 if (rval != QLA_SUCCESS) {
6786 ql_log(ql_log_warn, vha, 0x706d,
6787 "Unable to read SFP data (%x/%x/%x).\n", rval,
6788 addr, offset);
6789
6790 return rval;
6791 }
6792
6793 if (buf && (c < count)) {
6794 u16 sz;
6795
6796 if ((count - c) >= SFP_BLOCK_SIZE)
6797 sz = SFP_BLOCK_SIZE;
6798 else
6799 sz = count - c;
6800
6801 memcpy(buf, sfp_data, sz);
6802 buf += SFP_BLOCK_SIZE;
6803 c += sz;
6804 }
6805 phys_addr += SFP_BLOCK_SIZE;
6806 sfp_data += SFP_BLOCK_SIZE;
6807 offset += SFP_BLOCK_SIZE;
6808 }
6809
6810 return rval;
6811 }
6812
qla24xx_res_count_wait(struct scsi_qla_host * vha,uint16_t * out_mb,int out_mb_sz)6813 int qla24xx_res_count_wait(struct scsi_qla_host *vha,
6814 uint16_t *out_mb, int out_mb_sz)
6815 {
6816 int rval = QLA_FUNCTION_FAILED;
6817 mbx_cmd_t mc;
6818
6819 if (!vha->hw->flags.fw_started)
6820 goto done;
6821
6822 memset(&mc, 0, sizeof(mc));
6823 mc.mb[0] = MBC_GET_RESOURCE_COUNTS;
6824
6825 rval = qla24xx_send_mb_cmd(vha, &mc);
6826 if (rval != QLA_SUCCESS) {
6827 ql_dbg(ql_dbg_mbx, vha, 0xffff,
6828 "%s: fail\n", __func__);
6829 } else {
6830 if (out_mb_sz <= SIZEOF_IOCB_MB_REG)
6831 memcpy(out_mb, mc.mb, out_mb_sz);
6832 else
6833 memcpy(out_mb, mc.mb, SIZEOF_IOCB_MB_REG);
6834
6835 ql_dbg(ql_dbg_mbx, vha, 0xffff,
6836 "%s: done\n", __func__);
6837 }
6838 done:
6839 return rval;
6840 }
6841
qla28xx_secure_flash_update(scsi_qla_host_t * vha,uint16_t opts,uint16_t region,uint32_t len,dma_addr_t sfub_dma_addr,uint32_t sfub_len)6842 int qla28xx_secure_flash_update(scsi_qla_host_t *vha, uint16_t opts,
6843 uint16_t region, uint32_t len, dma_addr_t sfub_dma_addr,
6844 uint32_t sfub_len)
6845 {
6846 int rval;
6847 mbx_cmd_t mc;
6848 mbx_cmd_t *mcp = &mc;
6849
6850 mcp->mb[0] = MBC_SECURE_FLASH_UPDATE;
6851 mcp->mb[1] = opts;
6852 mcp->mb[2] = region;
6853 mcp->mb[3] = MSW(len);
6854 mcp->mb[4] = LSW(len);
6855 mcp->mb[5] = MSW(sfub_dma_addr);
6856 mcp->mb[6] = LSW(sfub_dma_addr);
6857 mcp->mb[7] = MSW(MSD(sfub_dma_addr));
6858 mcp->mb[8] = LSW(MSD(sfub_dma_addr));
6859 mcp->mb[9] = sfub_len;
6860 mcp->out_mb =
6861 MBX_9|MBX_8|MBX_7|MBX_6|MBX_5|MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
6862 mcp->in_mb = MBX_2|MBX_1|MBX_0;
6863 mcp->tov = MBX_TOV_SECONDS;
6864 mcp->flags = 0;
6865 rval = qla2x00_mailbox_command(vha, mcp);
6866
6867 if (rval != QLA_SUCCESS) {
6868 ql_dbg(ql_dbg_mbx, vha, 0xffff, "%s(%ld): failed rval 0x%x, %x %x %x",
6869 __func__, vha->host_no, rval, mcp->mb[0], mcp->mb[1],
6870 mcp->mb[2]);
6871 }
6872
6873 return rval;
6874 }
6875
qla2xxx_write_remote_register(scsi_qla_host_t * vha,uint32_t addr,uint32_t data)6876 int qla2xxx_write_remote_register(scsi_qla_host_t *vha, uint32_t addr,
6877 uint32_t data)
6878 {
6879 int rval;
6880 mbx_cmd_t mc;
6881 mbx_cmd_t *mcp = &mc;
6882
6883 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10e8,
6884 "Entered %s.\n", __func__);
6885
6886 mcp->mb[0] = MBC_WRITE_REMOTE_REG;
6887 mcp->mb[1] = LSW(addr);
6888 mcp->mb[2] = MSW(addr);
6889 mcp->mb[3] = LSW(data);
6890 mcp->mb[4] = MSW(data);
6891 mcp->out_mb = MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
6892 mcp->in_mb = MBX_1|MBX_0;
6893 mcp->tov = MBX_TOV_SECONDS;
6894 mcp->flags = 0;
6895 rval = qla2x00_mailbox_command(vha, mcp);
6896
6897 if (rval != QLA_SUCCESS) {
6898 ql_dbg(ql_dbg_mbx, vha, 0x10e9,
6899 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
6900 } else {
6901 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10ea,
6902 "Done %s.\n", __func__);
6903 }
6904
6905 return rval;
6906 }
6907
qla2xxx_read_remote_register(scsi_qla_host_t * vha,uint32_t addr,uint32_t * data)6908 int qla2xxx_read_remote_register(scsi_qla_host_t *vha, uint32_t addr,
6909 uint32_t *data)
6910 {
6911 int rval;
6912 mbx_cmd_t mc;
6913 mbx_cmd_t *mcp = &mc;
6914
6915 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10e8,
6916 "Entered %s.\n", __func__);
6917
6918 mcp->mb[0] = MBC_READ_REMOTE_REG;
6919 mcp->mb[1] = LSW(addr);
6920 mcp->mb[2] = MSW(addr);
6921 mcp->out_mb = MBX_2|MBX_1|MBX_0;
6922 mcp->in_mb = MBX_4|MBX_3|MBX_2|MBX_1|MBX_0;
6923 mcp->tov = MBX_TOV_SECONDS;
6924 mcp->flags = 0;
6925 rval = qla2x00_mailbox_command(vha, mcp);
6926
6927 *data = (uint32_t)((((uint32_t)mcp->mb[4]) << 16) | mcp->mb[3]);
6928
6929 if (rval != QLA_SUCCESS) {
6930 ql_dbg(ql_dbg_mbx, vha, 0x10e9,
6931 "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
6932 } else {
6933 ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10ea,
6934 "Done %s.\n", __func__);
6935 }
6936
6937 return rval;
6938 }
6939
6940 int
ql26xx_led_config(scsi_qla_host_t * vha,uint16_t options,uint16_t * led)6941 ql26xx_led_config(scsi_qla_host_t *vha, uint16_t options, uint16_t *led)
6942 {
6943 struct qla_hw_data *ha = vha->hw;
6944 mbx_cmd_t mc;
6945 mbx_cmd_t *mcp = &mc;
6946 int rval;
6947
6948 if (!IS_QLA2031(ha) && !IS_QLA27XX(ha) && !IS_QLA28XX(ha))
6949 return QLA_FUNCTION_FAILED;
6950
6951 ql_dbg(ql_dbg_mbx, vha, 0x7070, "Entered %s (options=%x).\n",
6952 __func__, options);
6953
6954 mcp->mb[0] = MBC_SET_GET_FC_LED_CONFIG;
6955 mcp->mb[1] = options;
6956 mcp->out_mb = MBX_1|MBX_0;
6957 mcp->in_mb = MBX_1|MBX_0;
6958 if (options & BIT_0) {
6959 if (options & BIT_1) {
6960 mcp->mb[2] = led[2];
6961 mcp->out_mb |= MBX_2;
6962 }
6963 if (options & BIT_2) {
6964 mcp->mb[3] = led[0];
6965 mcp->out_mb |= MBX_3;
6966 }
6967 if (options & BIT_3) {
6968 mcp->mb[4] = led[1];
6969 mcp->out_mb |= MBX_4;
6970 }
6971 } else {
6972 mcp->in_mb |= MBX_4|MBX_3|MBX_2;
6973 }
6974 mcp->tov = MBX_TOV_SECONDS;
6975 mcp->flags = 0;
6976 rval = qla2x00_mailbox_command(vha, mcp);
6977 if (rval) {
6978 ql_dbg(ql_dbg_mbx, vha, 0x7071, "Failed %s %x (mb=%x,%x)\n",
6979 __func__, rval, mcp->mb[0], mcp->mb[1]);
6980 return rval;
6981 }
6982
6983 if (options & BIT_0) {
6984 ha->beacon_blink_led = 0;
6985 ql_dbg(ql_dbg_mbx, vha, 0x7072, "Done %s\n", __func__);
6986 } else {
6987 led[2] = mcp->mb[2];
6988 led[0] = mcp->mb[3];
6989 led[1] = mcp->mb[4];
6990 ql_dbg(ql_dbg_mbx, vha, 0x7073, "Done %s (led=%x,%x,%x)\n",
6991 __func__, led[0], led[1], led[2]);
6992 }
6993
6994 return rval;
6995 }
6996
6997 /**
6998 * qla_no_op_mb(): This MB is used to check if FW is still alive and
6999 * able to generate an interrupt. Otherwise, a timeout will trigger
7000 * FW dump + reset
7001 * @vha: host adapter pointer
7002 * Return: None
7003 */
qla_no_op_mb(struct scsi_qla_host * vha)7004 void qla_no_op_mb(struct scsi_qla_host *vha)
7005 {
7006 mbx_cmd_t mc;
7007 mbx_cmd_t *mcp = &mc;
7008 int rval;
7009
7010 memset(&mc, 0, sizeof(mc));
7011 mcp->mb[0] = 0; // noop cmd= 0
7012 mcp->out_mb = MBX_0;
7013 mcp->in_mb = MBX_0;
7014 mcp->tov = 5;
7015 mcp->flags = 0;
7016 rval = qla2x00_mailbox_command(vha, mcp);
7017
7018 if (rval) {
7019 ql_dbg(ql_dbg_async, vha, 0x7071,
7020 "Failed %s %x\n", __func__, rval);
7021 }
7022 }
7023