upload tizen1.0 source
[kernel/linux-2.6.36.git] / drivers / scsi / qla4xxx / ql4_mbx.c
1 /*
2  * QLogic iSCSI HBA Driver
3  * Copyright (c)  2003-2006 QLogic Corporation
4  *
5  * See LICENSE.qla4xxx for copyright and licensing details.
6  */
7
8 #include "ql4_def.h"
9 #include "ql4_glbl.h"
10 #include "ql4_dbg.h"
11 #include "ql4_inline.h"
12
13
14 /**
15  * qla4xxx_mailbox_command - issues mailbox commands
16  * @ha: Pointer to host adapter structure.
17  * @inCount: number of mailbox registers to load.
18  * @outCount: number of mailbox registers to return.
19  * @mbx_cmd: data pointer for mailbox in registers.
20  * @mbx_sts: data pointer for mailbox out registers.
21  *
22  * This routine isssue mailbox commands and waits for completion.
23  * If outCount is 0, this routine completes successfully WITHOUT waiting
24  * for the mailbox command to complete.
25  **/
26 int qla4xxx_mailbox_command(struct scsi_qla_host *ha, uint8_t inCount,
27                             uint8_t outCount, uint32_t *mbx_cmd,
28                             uint32_t *mbx_sts)
29 {
30         int status = QLA_ERROR;
31         uint8_t i;
32         u_long wait_count;
33         uint32_t intr_status;
34         unsigned long flags = 0;
35
36         /* Make sure that pointers are valid */
37         if (!mbx_cmd || !mbx_sts) {
38                 DEBUG2(printk("scsi%ld: %s: Invalid mbx_cmd or mbx_sts "
39                               "pointer\n", ha->host_no, __func__));
40                 return status;
41         }
42
43         if (is_qla8022(ha) &&
44             test_bit(AF_FW_RECOVERY, &ha->flags)) {
45                 DEBUG2(ql4_printk(KERN_WARNING, ha, "scsi%ld: %s: prematurely "
46                     "completing mbx cmd as firmware recovery detected\n",
47                     ha->host_no, __func__));
48                 return status;
49         }
50
51         if ((is_aer_supported(ha)) &&
52             (test_bit(AF_PCI_CHANNEL_IO_PERM_FAILURE, &ha->flags))) {
53                 DEBUG2(printk(KERN_WARNING "scsi%ld: %s: Perm failure on EEH, "
54                     "timeout MBX Exiting.\n", ha->host_no, __func__));
55                 return status;
56         }
57
58         /* Mailbox code active */
59         wait_count = MBOX_TOV * 100;
60
61         while (wait_count--) {
62                 mutex_lock(&ha->mbox_sem);
63                 if (!test_bit(AF_MBOX_COMMAND, &ha->flags)) {
64                         set_bit(AF_MBOX_COMMAND, &ha->flags);
65                         mutex_unlock(&ha->mbox_sem);
66                         break;
67                 }
68                 mutex_unlock(&ha->mbox_sem);
69                 if (!wait_count) {
70                         DEBUG2(printk("scsi%ld: %s: mbox_sem failed\n",
71                                 ha->host_no, __func__));
72                         return status;
73                 }
74                 msleep(10);
75         }
76
77         /* To prevent overwriting mailbox registers for a command that has
78          * not yet been serviced, check to see if an active command
79          * (AEN, IOCB, etc.) is interrupting, then service it.
80          * -----------------------------------------------------------------
81          */
82         spin_lock_irqsave(&ha->hardware_lock, flags);
83
84         if (is_qla8022(ha)) {
85                 intr_status = readl(&ha->qla4_8xxx_reg->host_int);
86                 if (intr_status & ISRX_82XX_RISC_INT) {
87                         /* Service existing interrupt */
88                         DEBUG2(printk("scsi%ld: %s: "
89                             "servicing existing interrupt\n",
90                             ha->host_no, __func__));
91                         intr_status = readl(&ha->qla4_8xxx_reg->host_status);
92                         ha->isp_ops->interrupt_service_routine(ha, intr_status);
93                         clear_bit(AF_MBOX_COMMAND_DONE, &ha->flags);
94                         if (test_bit(AF_INTERRUPTS_ON, &ha->flags) &&
95                             test_bit(AF_INTx_ENABLED, &ha->flags))
96                                 qla4_8xxx_wr_32(ha,
97                                     ha->nx_legacy_intr.tgt_mask_reg,
98                                     0xfbff);
99                 }
100         } else {
101                 intr_status = readl(&ha->reg->ctrl_status);
102                 if (intr_status & CSR_SCSI_PROCESSOR_INTR) {
103                         /* Service existing interrupt */
104                         ha->isp_ops->interrupt_service_routine(ha, intr_status);
105                         clear_bit(AF_MBOX_COMMAND_DONE, &ha->flags);
106                 }
107         }
108
109         ha->mbox_status_count = outCount;
110         for (i = 0; i < outCount; i++)
111                 ha->mbox_status[i] = 0;
112
113         if (is_qla8022(ha)) {
114                 /* Load all mailbox registers, except mailbox 0. */
115                 DEBUG5(
116                     printk("scsi%ld: %s: Cmd ", ha->host_no, __func__);
117                     for (i = 0; i < inCount; i++)
118                         printk("mb%d=%04x ", i, mbx_cmd[i]);
119                     printk("\n"));
120
121                 for (i = 1; i < inCount; i++)
122                         writel(mbx_cmd[i], &ha->qla4_8xxx_reg->mailbox_in[i]);
123                 writel(mbx_cmd[0], &ha->qla4_8xxx_reg->mailbox_in[0]);
124                 readl(&ha->qla4_8xxx_reg->mailbox_in[0]);
125                 writel(HINT_MBX_INT_PENDING, &ha->qla4_8xxx_reg->hint);
126         } else {
127                 /* Load all mailbox registers, except mailbox 0. */
128                 for (i = 1; i < inCount; i++)
129                         writel(mbx_cmd[i], &ha->reg->mailbox[i]);
130
131                 /* Wakeup firmware  */
132                 writel(mbx_cmd[0], &ha->reg->mailbox[0]);
133                 readl(&ha->reg->mailbox[0]);
134                 writel(set_rmask(CSR_INTR_RISC), &ha->reg->ctrl_status);
135                 readl(&ha->reg->ctrl_status);
136         }
137
138         spin_unlock_irqrestore(&ha->hardware_lock, flags);
139
140         /* Wait for completion */
141
142         /*
143          * If we don't want status, don't wait for the mailbox command to
144          * complete.  For example, MBOX_CMD_RESET_FW doesn't return status,
145          * you must poll the inbound Interrupt Mask for completion.
146          */
147         if (outCount == 0) {
148                 status = QLA_SUCCESS;
149                 goto mbox_exit;
150         }
151
152         /*
153          * Wait for completion: Poll or completion queue
154          */
155         if (test_bit(AF_IRQ_ATTACHED, &ha->flags) &&
156             test_bit(AF_INTERRUPTS_ON, &ha->flags) &&
157             test_bit(AF_ONLINE, &ha->flags) &&
158             !test_bit(AF_HBA_GOING_AWAY, &ha->flags)) {
159                 /* Do not poll for completion. Use completion queue */
160                 set_bit(AF_MBOX_COMMAND_NOPOLL, &ha->flags);
161                 wait_for_completion_timeout(&ha->mbx_intr_comp, MBOX_TOV * HZ);
162                 clear_bit(AF_MBOX_COMMAND_NOPOLL, &ha->flags);
163         } else {
164                 /* Poll for command to complete */
165                 wait_count = jiffies + MBOX_TOV * HZ;
166                 while (test_bit(AF_MBOX_COMMAND_DONE, &ha->flags) == 0) {
167                         if (time_after_eq(jiffies, wait_count))
168                                 break;
169
170                         /*
171                          * Service the interrupt.
172                          * The ISR will save the mailbox status registers
173                          * to a temporary storage location in the adapter
174                          * structure.
175                          */
176
177                         spin_lock_irqsave(&ha->hardware_lock, flags);
178                         if (is_qla8022(ha)) {
179                                 intr_status =
180                                     readl(&ha->qla4_8xxx_reg->host_int);
181                                 if (intr_status & ISRX_82XX_RISC_INT) {
182                                         ha->mbox_status_count = outCount;
183                                         intr_status =
184                                          readl(&ha->qla4_8xxx_reg->host_status);
185                                         ha->isp_ops->interrupt_service_routine(
186                                             ha, intr_status);
187                                         if (test_bit(AF_INTERRUPTS_ON,
188                                             &ha->flags) &&
189                                             test_bit(AF_INTx_ENABLED,
190                                             &ha->flags))
191                                                 qla4_8xxx_wr_32(ha,
192                                                 ha->nx_legacy_intr.tgt_mask_reg,
193                                                 0xfbff);
194                                 }
195                         } else {
196                                 intr_status = readl(&ha->reg->ctrl_status);
197                                 if (intr_status & INTR_PENDING) {
198                                         /*
199                                          * Service the interrupt.
200                                          * The ISR will save the mailbox status
201                                          * registers to a temporary storage
202                                          * location in the adapter structure.
203                                          */
204                                         ha->mbox_status_count = outCount;
205                                         ha->isp_ops->interrupt_service_routine(
206                                             ha, intr_status);
207                                 }
208                         }
209                         spin_unlock_irqrestore(&ha->hardware_lock, flags);
210                         msleep(10);
211                 }
212         }
213
214         /* Check for mailbox timeout. */
215         if (!test_bit(AF_MBOX_COMMAND_DONE, &ha->flags)) {
216                 if (is_qla8022(ha) &&
217                     test_bit(AF_FW_RECOVERY, &ha->flags)) {
218                         DEBUG2(ql4_printk(KERN_INFO, ha,
219                             "scsi%ld: %s: prematurely completing mbx cmd as "
220                             "firmware recovery detected\n",
221                             ha->host_no, __func__));
222                         goto mbox_exit;
223                 }
224                 DEBUG2(printk("scsi%ld: Mailbox Cmd 0x%08X timed out ...,"
225                               " Scheduling Adapter Reset\n", ha->host_no,
226                               mbx_cmd[0]));
227                 ha->mailbox_timeout_count++;
228                 mbx_sts[0] = (-1);
229                 set_bit(DPC_RESET_HA, &ha->dpc_flags);
230                 goto mbox_exit;
231         }
232
233         /*
234          * Copy the mailbox out registers to the caller's mailbox in/out
235          * structure.
236          */
237         spin_lock_irqsave(&ha->hardware_lock, flags);
238         for (i = 0; i < outCount; i++)
239                 mbx_sts[i] = ha->mbox_status[i];
240
241         /* Set return status and error flags (if applicable). */
242         switch (ha->mbox_status[0]) {
243         case MBOX_STS_COMMAND_COMPLETE:
244                 status = QLA_SUCCESS;
245                 break;
246
247         case MBOX_STS_INTERMEDIATE_COMPLETION:
248                 status = QLA_SUCCESS;
249                 break;
250
251         case MBOX_STS_BUSY:
252                 DEBUG2( printk("scsi%ld: %s: Cmd = %08X, ISP BUSY\n",
253                                ha->host_no, __func__, mbx_cmd[0]));
254                 ha->mailbox_timeout_count++;
255                 break;
256
257         default:
258                 DEBUG2(printk("scsi%ld: %s: **** FAILED, cmd = %08X, "
259                               "sts = %08X ****\n", ha->host_no, __func__,
260                               mbx_cmd[0], mbx_sts[0]));
261                 break;
262         }
263         spin_unlock_irqrestore(&ha->hardware_lock, flags);
264
265 mbox_exit:
266         mutex_lock(&ha->mbox_sem);
267         clear_bit(AF_MBOX_COMMAND, &ha->flags);
268         mutex_unlock(&ha->mbox_sem);
269         clear_bit(AF_MBOX_COMMAND_DONE, &ha->flags);
270
271         return status;
272 }
273
274 void qla4xxx_mailbox_premature_completion(struct scsi_qla_host *ha)
275 {
276         set_bit(AF_FW_RECOVERY, &ha->flags);
277         ql4_printk(KERN_INFO, ha, "scsi%ld: %s: set FW RECOVERY!\n",
278             ha->host_no, __func__);
279
280         if (test_bit(AF_MBOX_COMMAND, &ha->flags)) {
281                 if (test_bit(AF_MBOX_COMMAND_NOPOLL, &ha->flags)) {
282                         complete(&ha->mbx_intr_comp);
283                         ql4_printk(KERN_INFO, ha, "scsi%ld: %s: Due to fw "
284                             "recovery, doing premature completion of "
285                             "mbx cmd\n", ha->host_no, __func__);
286
287                 } else {
288                         set_bit(AF_MBOX_COMMAND_DONE, &ha->flags);
289                         ql4_printk(KERN_INFO, ha, "scsi%ld: %s: Due to fw "
290                             "recovery, doing premature completion of "
291                             "polling mbx cmd\n", ha->host_no, __func__);
292                 }
293         }
294 }
295
296 static uint8_t
297 qla4xxx_set_ifcb(struct scsi_qla_host *ha, uint32_t *mbox_cmd,
298                  uint32_t *mbox_sts, dma_addr_t init_fw_cb_dma)
299 {
300         memset(mbox_cmd, 0, sizeof(mbox_cmd[0]) * MBOX_REG_COUNT);
301         memset(mbox_sts, 0, sizeof(mbox_sts[0]) * MBOX_REG_COUNT);
302         mbox_cmd[0] = MBOX_CMD_INITIALIZE_FIRMWARE;
303         mbox_cmd[1] = 0;
304         mbox_cmd[2] = LSDW(init_fw_cb_dma);
305         mbox_cmd[3] = MSDW(init_fw_cb_dma);
306         mbox_cmd[4] = sizeof(struct addr_ctrl_blk);
307         mbox_cmd[5] = (IFCB_VER_MAX << 8) | IFCB_VER_MIN;
308
309         if (qla4xxx_mailbox_command(ha, 6, 6, mbox_cmd, mbox_sts) !=
310             QLA_SUCCESS) {
311                 DEBUG2(printk(KERN_WARNING "scsi%ld: %s: "
312                               "MBOX_CMD_INITIALIZE_FIRMWARE"
313                               " failed w/ status %04X\n",
314                               ha->host_no, __func__, mbox_sts[0]));
315                 return QLA_ERROR;
316         }
317         return QLA_SUCCESS;
318 }
319
320 static uint8_t
321 qla4xxx_get_ifcb(struct scsi_qla_host *ha, uint32_t *mbox_cmd,
322                  uint32_t *mbox_sts, dma_addr_t init_fw_cb_dma)
323 {
324         memset(mbox_cmd, 0, sizeof(mbox_cmd[0]) * MBOX_REG_COUNT);
325         memset(mbox_sts, 0, sizeof(mbox_sts[0]) * MBOX_REG_COUNT);
326         mbox_cmd[0] = MBOX_CMD_GET_INIT_FW_CTRL_BLOCK;
327         mbox_cmd[2] = LSDW(init_fw_cb_dma);
328         mbox_cmd[3] = MSDW(init_fw_cb_dma);
329         mbox_cmd[4] = sizeof(struct addr_ctrl_blk);
330
331         if (qla4xxx_mailbox_command(ha, 5, 5, mbox_cmd, mbox_sts) !=
332             QLA_SUCCESS) {
333                 DEBUG2(printk(KERN_WARNING "scsi%ld: %s: "
334                               "MBOX_CMD_GET_INIT_FW_CTRL_BLOCK"
335                               " failed w/ status %04X\n",
336                               ha->host_no, __func__, mbox_sts[0]));
337                 return QLA_ERROR;
338         }
339         return QLA_SUCCESS;
340 }
341
342 static void
343 qla4xxx_update_local_ip(struct scsi_qla_host *ha,
344                          struct addr_ctrl_blk  *init_fw_cb)
345 {
346         /* Save IPv4 Address Info */
347         memcpy(ha->ip_address, init_fw_cb->ipv4_addr,
348                 min(sizeof(ha->ip_address), sizeof(init_fw_cb->ipv4_addr)));
349         memcpy(ha->subnet_mask, init_fw_cb->ipv4_subnet,
350                 min(sizeof(ha->subnet_mask), sizeof(init_fw_cb->ipv4_subnet)));
351         memcpy(ha->gateway, init_fw_cb->ipv4_gw_addr,
352                 min(sizeof(ha->gateway), sizeof(init_fw_cb->ipv4_gw_addr)));
353
354         if (is_ipv6_enabled(ha)) {
355                 /* Save IPv6 Address */
356                 ha->ipv6_link_local_state = init_fw_cb->ipv6_lnk_lcl_addr_state;
357                 ha->ipv6_addr0_state = init_fw_cb->ipv6_addr0_state;
358                 ha->ipv6_addr1_state = init_fw_cb->ipv6_addr1_state;
359                 ha->ipv6_default_router_state = init_fw_cb->ipv6_dflt_rtr_state;
360                 ha->ipv6_link_local_addr.in6_u.u6_addr8[0] = 0xFE;
361                 ha->ipv6_link_local_addr.in6_u.u6_addr8[1] = 0x80;
362
363                 memcpy(&ha->ipv6_link_local_addr.in6_u.u6_addr8[8],
364                         init_fw_cb->ipv6_if_id,
365                         min(sizeof(ha->ipv6_link_local_addr)/2,
366                         sizeof(init_fw_cb->ipv6_if_id)));
367                 memcpy(&ha->ipv6_addr0, init_fw_cb->ipv6_addr0,
368                         min(sizeof(ha->ipv6_addr0),
369                         sizeof(init_fw_cb->ipv6_addr0)));
370                 memcpy(&ha->ipv6_addr1, init_fw_cb->ipv6_addr1,
371                         min(sizeof(ha->ipv6_addr1),
372                         sizeof(init_fw_cb->ipv6_addr1)));
373                 memcpy(&ha->ipv6_default_router_addr,
374                         init_fw_cb->ipv6_dflt_rtr_addr,
375                         min(sizeof(ha->ipv6_default_router_addr),
376                         sizeof(init_fw_cb->ipv6_dflt_rtr_addr)));
377         }
378 }
379
380 static uint8_t
381 qla4xxx_update_local_ifcb(struct scsi_qla_host *ha,
382                           uint32_t *mbox_cmd,
383                           uint32_t *mbox_sts,
384                           struct addr_ctrl_blk  *init_fw_cb,
385                           dma_addr_t init_fw_cb_dma)
386 {
387         if (qla4xxx_get_ifcb(ha, mbox_cmd, mbox_sts, init_fw_cb_dma)
388             != QLA_SUCCESS) {
389                 DEBUG2(printk(KERN_WARNING
390                               "scsi%ld: %s: Failed to get init_fw_ctrl_blk\n",
391                               ha->host_no, __func__));
392                 return QLA_ERROR;
393         }
394
395         DEBUG2(qla4xxx_dump_buffer(init_fw_cb, sizeof(struct addr_ctrl_blk)));
396
397         /* Save some info in adapter structure. */
398         ha->acb_version = init_fw_cb->acb_version;
399         ha->firmware_options = le16_to_cpu(init_fw_cb->fw_options);
400         ha->tcp_options = le16_to_cpu(init_fw_cb->ipv4_tcp_opts);
401         ha->ipv4_options = le16_to_cpu(init_fw_cb->ipv4_ip_opts);
402         ha->ipv4_addr_state = le16_to_cpu(init_fw_cb->ipv4_addr_state);
403         ha->heartbeat_interval = init_fw_cb->hb_interval;
404         memcpy(ha->name_string, init_fw_cb->iscsi_name,
405                 min(sizeof(ha->name_string),
406                 sizeof(init_fw_cb->iscsi_name)));
407         /*memcpy(ha->alias, init_fw_cb->Alias,
408                min(sizeof(ha->alias), sizeof(init_fw_cb->Alias)));*/
409
410         /* Save Command Line Paramater info */
411         ha->discovery_wait = ql4xdiscoverywait;
412
413         if (ha->acb_version == ACB_SUPPORTED) {
414                 ha->ipv6_options = init_fw_cb->ipv6_opts;
415                 ha->ipv6_addl_options = init_fw_cb->ipv6_addtl_opts;
416         }
417         qla4xxx_update_local_ip(ha, init_fw_cb);
418
419         return QLA_SUCCESS;
420 }
421
422 /**
423  * qla4xxx_initialize_fw_cb - initializes firmware control block.
424  * @ha: Pointer to host adapter structure.
425  **/
426 int qla4xxx_initialize_fw_cb(struct scsi_qla_host * ha)
427 {
428         struct addr_ctrl_blk *init_fw_cb;
429         dma_addr_t init_fw_cb_dma;
430         uint32_t mbox_cmd[MBOX_REG_COUNT];
431         uint32_t mbox_sts[MBOX_REG_COUNT];
432         int status = QLA_ERROR;
433
434         init_fw_cb = dma_alloc_coherent(&ha->pdev->dev,
435                                         sizeof(struct addr_ctrl_blk),
436                                         &init_fw_cb_dma, GFP_KERNEL);
437         if (init_fw_cb == NULL) {
438                 DEBUG2(printk("scsi%ld: %s: Unable to alloc init_cb\n",
439                               ha->host_no, __func__));
440                 goto exit_init_fw_cb_no_free;
441         }
442         memset(init_fw_cb, 0, sizeof(struct addr_ctrl_blk));
443
444         /* Get Initialize Firmware Control Block. */
445         memset(&mbox_cmd, 0, sizeof(mbox_cmd));
446         memset(&mbox_sts, 0, sizeof(mbox_sts));
447
448         if (qla4xxx_get_ifcb(ha, &mbox_cmd[0], &mbox_sts[0], init_fw_cb_dma) !=
449             QLA_SUCCESS) {
450                 dma_free_coherent(&ha->pdev->dev,
451                                   sizeof(struct addr_ctrl_blk),
452                                   init_fw_cb, init_fw_cb_dma);
453                 goto exit_init_fw_cb;
454         }
455
456         /* Initialize request and response queues. */
457         qla4xxx_init_rings(ha);
458
459         /* Fill in the request and response queue information. */
460         init_fw_cb->rqq_consumer_idx = cpu_to_le16(ha->request_out);
461         init_fw_cb->compq_producer_idx = cpu_to_le16(ha->response_in);
462         init_fw_cb->rqq_len = __constant_cpu_to_le16(REQUEST_QUEUE_DEPTH);
463         init_fw_cb->compq_len = __constant_cpu_to_le16(RESPONSE_QUEUE_DEPTH);
464         init_fw_cb->rqq_addr_lo = cpu_to_le32(LSDW(ha->request_dma));
465         init_fw_cb->rqq_addr_hi = cpu_to_le32(MSDW(ha->request_dma));
466         init_fw_cb->compq_addr_lo = cpu_to_le32(LSDW(ha->response_dma));
467         init_fw_cb->compq_addr_hi = cpu_to_le32(MSDW(ha->response_dma));
468         init_fw_cb->shdwreg_addr_lo = cpu_to_le32(LSDW(ha->shadow_regs_dma));
469         init_fw_cb->shdwreg_addr_hi = cpu_to_le32(MSDW(ha->shadow_regs_dma));
470
471         /* Set up required options. */
472         init_fw_cb->fw_options |=
473                 __constant_cpu_to_le16(FWOPT_SESSION_MODE |
474                                        FWOPT_INITIATOR_MODE);
475         init_fw_cb->fw_options &= __constant_cpu_to_le16(~FWOPT_TARGET_MODE);
476
477         if (qla4xxx_set_ifcb(ha, &mbox_cmd[0], &mbox_sts[0], init_fw_cb_dma)
478                 != QLA_SUCCESS) {
479                 DEBUG2(printk(KERN_WARNING
480                               "scsi%ld: %s: Failed to set init_fw_ctrl_blk\n",
481                               ha->host_no, __func__));
482                 goto exit_init_fw_cb;
483         }
484
485         if (qla4xxx_update_local_ifcb(ha, &mbox_cmd[0], &mbox_sts[0],
486                 init_fw_cb, init_fw_cb_dma) != QLA_SUCCESS) {
487                 DEBUG2(printk("scsi%ld: %s: Failed to update local ifcb\n",
488                                 ha->host_no, __func__));
489                 goto exit_init_fw_cb;
490         }
491         status = QLA_SUCCESS;
492
493 exit_init_fw_cb:
494         dma_free_coherent(&ha->pdev->dev, sizeof(struct addr_ctrl_blk),
495                                 init_fw_cb, init_fw_cb_dma);
496 exit_init_fw_cb_no_free:
497         return status;
498 }
499
500 /**
501  * qla4xxx_get_dhcp_ip_address - gets HBA ip address via DHCP
502  * @ha: Pointer to host adapter structure.
503  **/
504 int qla4xxx_get_dhcp_ip_address(struct scsi_qla_host * ha)
505 {
506         struct addr_ctrl_blk *init_fw_cb;
507         dma_addr_t init_fw_cb_dma;
508         uint32_t mbox_cmd[MBOX_REG_COUNT];
509         uint32_t mbox_sts[MBOX_REG_COUNT];
510
511         init_fw_cb = dma_alloc_coherent(&ha->pdev->dev,
512                                         sizeof(struct addr_ctrl_blk),
513                                         &init_fw_cb_dma, GFP_KERNEL);
514         if (init_fw_cb == NULL) {
515                 printk("scsi%ld: %s: Unable to alloc init_cb\n", ha->host_no,
516                        __func__);
517                 return QLA_ERROR;
518         }
519
520         /* Get Initialize Firmware Control Block. */
521         memset(init_fw_cb, 0, sizeof(struct addr_ctrl_blk));
522         if (qla4xxx_get_ifcb(ha, &mbox_cmd[0], &mbox_sts[0], init_fw_cb_dma) !=
523             QLA_SUCCESS) {
524                 DEBUG2(printk("scsi%ld: %s: Failed to get init_fw_ctrl_blk\n",
525                               ha->host_no, __func__));
526                 dma_free_coherent(&ha->pdev->dev,
527                                   sizeof(struct addr_ctrl_blk),
528                                   init_fw_cb, init_fw_cb_dma);
529                 return QLA_ERROR;
530         }
531
532         /* Save IP Address. */
533         qla4xxx_update_local_ip(ha, init_fw_cb);
534         dma_free_coherent(&ha->pdev->dev, sizeof(struct addr_ctrl_blk),
535                                 init_fw_cb, init_fw_cb_dma);
536
537         return QLA_SUCCESS;
538 }
539
540 /**
541  * qla4xxx_get_firmware_state - gets firmware state of HBA
542  * @ha: Pointer to host adapter structure.
543  **/
544 int qla4xxx_get_firmware_state(struct scsi_qla_host * ha)
545 {
546         uint32_t mbox_cmd[MBOX_REG_COUNT];
547         uint32_t mbox_sts[MBOX_REG_COUNT];
548
549         /* Get firmware version */
550         memset(&mbox_cmd, 0, sizeof(mbox_cmd));
551         memset(&mbox_sts, 0, sizeof(mbox_sts));
552
553         mbox_cmd[0] = MBOX_CMD_GET_FW_STATE;
554
555         if (qla4xxx_mailbox_command(ha, MBOX_REG_COUNT, 4, &mbox_cmd[0], &mbox_sts[0]) !=
556             QLA_SUCCESS) {
557                 DEBUG2(printk("scsi%ld: %s: MBOX_CMD_GET_FW_STATE failed w/ "
558                               "status %04X\n", ha->host_no, __func__,
559                               mbox_sts[0]));
560                 return QLA_ERROR;
561         }
562         ha->firmware_state = mbox_sts[1];
563         ha->board_id = mbox_sts[2];
564         ha->addl_fw_state = mbox_sts[3];
565         DEBUG2(printk("scsi%ld: %s firmware_state=0x%x\n",
566                       ha->host_no, __func__, ha->firmware_state);)
567
568         return QLA_SUCCESS;
569 }
570
571 /**
572  * qla4xxx_get_firmware_status - retrieves firmware status
573  * @ha: Pointer to host adapter structure.
574  **/
575 int qla4xxx_get_firmware_status(struct scsi_qla_host * ha)
576 {
577         uint32_t mbox_cmd[MBOX_REG_COUNT];
578         uint32_t mbox_sts[MBOX_REG_COUNT];
579
580         /* Get firmware version */
581         memset(&mbox_cmd, 0, sizeof(mbox_cmd));
582         memset(&mbox_sts, 0, sizeof(mbox_sts));
583
584         mbox_cmd[0] = MBOX_CMD_GET_FW_STATUS;
585
586         if (qla4xxx_mailbox_command(ha, MBOX_REG_COUNT, 3, &mbox_cmd[0], &mbox_sts[0]) !=
587             QLA_SUCCESS) {
588                 DEBUG2(printk("scsi%ld: %s: MBOX_CMD_GET_FW_STATUS failed w/ "
589                               "status %04X\n", ha->host_no, __func__,
590                               mbox_sts[0]));
591                 return QLA_ERROR;
592         }
593
594         ql4_printk(KERN_INFO, ha, "%ld firmare IOCBs available (%d).\n",
595             ha->host_no, mbox_cmd[2]);
596
597         return QLA_SUCCESS;
598 }
599
600 /**
601  * qla4xxx_get_fwddb_entry - retrieves firmware ddb entry
602  * @ha: Pointer to host adapter structure.
603  * @fw_ddb_index: Firmware's device database index
604  * @fw_ddb_entry: Pointer to firmware's device database entry structure
605  * @num_valid_ddb_entries: Pointer to number of valid ddb entries
606  * @next_ddb_index: Pointer to next valid device database index
607  * @fw_ddb_device_state: Pointer to device state
608  **/
609 int qla4xxx_get_fwddb_entry(struct scsi_qla_host *ha,
610                             uint16_t fw_ddb_index,
611                             struct dev_db_entry *fw_ddb_entry,
612                             dma_addr_t fw_ddb_entry_dma,
613                             uint32_t *num_valid_ddb_entries,
614                             uint32_t *next_ddb_index,
615                             uint32_t *fw_ddb_device_state,
616                             uint32_t *conn_err_detail,
617                             uint16_t *tcp_source_port_num,
618                             uint16_t *connection_id)
619 {
620         int status = QLA_ERROR;
621         uint16_t options;
622         uint32_t mbox_cmd[MBOX_REG_COUNT];
623         uint32_t mbox_sts[MBOX_REG_COUNT];
624
625         /* Make sure the device index is valid */
626         if (fw_ddb_index >= MAX_DDB_ENTRIES) {
627                 DEBUG2(printk("scsi%ld: %s: ddb [%d] out of range.\n",
628                               ha->host_no, __func__, fw_ddb_index));
629                 goto exit_get_fwddb;
630         }
631         memset(&mbox_cmd, 0, sizeof(mbox_cmd));
632         memset(&mbox_sts, 0, sizeof(mbox_sts));
633
634         mbox_cmd[0] = MBOX_CMD_GET_DATABASE_ENTRY;
635         mbox_cmd[1] = (uint32_t) fw_ddb_index;
636         mbox_cmd[2] = LSDW(fw_ddb_entry_dma);
637         mbox_cmd[3] = MSDW(fw_ddb_entry_dma);
638         mbox_cmd[4] = sizeof(struct dev_db_entry);
639
640         if (qla4xxx_mailbox_command(ha, MBOX_REG_COUNT, 7, &mbox_cmd[0], &mbox_sts[0]) ==
641             QLA_ERROR) {
642                 DEBUG2(printk("scsi%ld: %s: MBOX_CMD_GET_DATABASE_ENTRY failed"
643                               " with status 0x%04X\n", ha->host_no, __func__,
644                               mbox_sts[0]));
645                 goto exit_get_fwddb;
646         }
647         if (fw_ddb_index != mbox_sts[1]) {
648                 DEBUG2(printk("scsi%ld: %s: ddb mismatch [%d] != [%d].\n",
649                               ha->host_no, __func__, fw_ddb_index,
650                               mbox_sts[1]));
651                 goto exit_get_fwddb;
652         }
653         if (fw_ddb_entry) {
654                 options = le16_to_cpu(fw_ddb_entry->options);
655                 if (options & DDB_OPT_IPV6_DEVICE) {
656                         ql4_printk(KERN_INFO, ha, "%s: DDB[%d] MB0 %04x Tot %d "
657                                 "Next %d State %04x ConnErr %08x %pI6 "
658                                 ":%04d \"%s\"\n", __func__, fw_ddb_index,
659                                 mbox_sts[0], mbox_sts[2], mbox_sts[3],
660                                 mbox_sts[4], mbox_sts[5],
661                                 fw_ddb_entry->ip_addr,
662                                 le16_to_cpu(fw_ddb_entry->port),
663                                 fw_ddb_entry->iscsi_name);
664                 } else {
665                         ql4_printk(KERN_INFO, ha, "%s: DDB[%d] MB0 %04x Tot %d "
666                                 "Next %d State %04x ConnErr %08x %pI4 "
667                                 ":%04d \"%s\"\n", __func__, fw_ddb_index,
668                                 mbox_sts[0], mbox_sts[2], mbox_sts[3],
669                                 mbox_sts[4], mbox_sts[5],
670                                 fw_ddb_entry->ip_addr,
671                                 le16_to_cpu(fw_ddb_entry->port),
672                                 fw_ddb_entry->iscsi_name);
673                 }
674         }
675         if (num_valid_ddb_entries)
676                 *num_valid_ddb_entries = mbox_sts[2];
677         if (next_ddb_index)
678                 *next_ddb_index = mbox_sts[3];
679         if (fw_ddb_device_state)
680                 *fw_ddb_device_state = mbox_sts[4];
681
682         /*
683          * RA: This mailbox has been changed to pass connection error and
684          * details.  Its true for ISP4010 as per Version E - Not sure when it
685          * was changed.  Get the time2wait from the fw_dd_entry field :
686          * default_time2wait which we call it as minTime2Wait DEV_DB_ENTRY
687          * struct.
688          */
689         if (conn_err_detail)
690                 *conn_err_detail = mbox_sts[5];
691         if (tcp_source_port_num)
692                 *tcp_source_port_num = (uint16_t) (mbox_sts[6] >> 16);
693         if (connection_id)
694                 *connection_id = (uint16_t) mbox_sts[6] & 0x00FF;
695         status = QLA_SUCCESS;
696
697 exit_get_fwddb:
698         return status;
699 }
700
701 /**
702  * qla4xxx_set_fwddb_entry - sets a ddb entry.
703  * @ha: Pointer to host adapter structure.
704  * @fw_ddb_index: Firmware's device database index
705  * @fw_ddb_entry: Pointer to firmware's ddb entry structure, or NULL.
706  *
707  * This routine initializes or updates the adapter's device database
708  * entry for the specified device. It also triggers a login for the
709  * specified device. Therefore, it may also be used as a secondary
710  * login routine when a NULL pointer is specified for the fw_ddb_entry.
711  **/
712 int qla4xxx_set_ddb_entry(struct scsi_qla_host * ha, uint16_t fw_ddb_index,
713                           dma_addr_t fw_ddb_entry_dma)
714 {
715         uint32_t mbox_cmd[MBOX_REG_COUNT];
716         uint32_t mbox_sts[MBOX_REG_COUNT];
717         int status;
718
719         /* Do not wait for completion. The firmware will send us an
720          * ASTS_DATABASE_CHANGED (0x8014) to notify us of the login status.
721          */
722         memset(&mbox_cmd, 0, sizeof(mbox_cmd));
723         memset(&mbox_sts, 0, sizeof(mbox_sts));
724
725         mbox_cmd[0] = MBOX_CMD_SET_DATABASE_ENTRY;
726         mbox_cmd[1] = (uint32_t) fw_ddb_index;
727         mbox_cmd[2] = LSDW(fw_ddb_entry_dma);
728         mbox_cmd[3] = MSDW(fw_ddb_entry_dma);
729         mbox_cmd[4] = sizeof(struct dev_db_entry);
730
731         status = qla4xxx_mailbox_command(ha, MBOX_REG_COUNT, 5, &mbox_cmd[0],
732             &mbox_sts[0]);
733         DEBUG2(printk("scsi%ld: %s: status=%d mbx0=0x%x mbx4=0x%x\n",
734             ha->host_no, __func__, status, mbox_sts[0], mbox_sts[4]);)
735
736         return status;
737 }
738
739 /**
740  * qla4xxx_get_crash_record - retrieves crash record.
741  * @ha: Pointer to host adapter structure.
742  *
743  * This routine retrieves a crash record from the QLA4010 after an 8002h aen.
744  **/
745 void qla4xxx_get_crash_record(struct scsi_qla_host * ha)
746 {
747         uint32_t mbox_cmd[MBOX_REG_COUNT];
748         uint32_t mbox_sts[MBOX_REG_COUNT];
749         struct crash_record *crash_record = NULL;
750         dma_addr_t crash_record_dma = 0;
751         uint32_t crash_record_size = 0;
752
753         memset(&mbox_cmd, 0, sizeof(mbox_cmd));
754         memset(&mbox_sts, 0, sizeof(mbox_cmd));
755
756         /* Get size of crash record. */
757         mbox_cmd[0] = MBOX_CMD_GET_CRASH_RECORD;
758
759         if (qla4xxx_mailbox_command(ha, MBOX_REG_COUNT, 5, &mbox_cmd[0], &mbox_sts[0]) !=
760             QLA_SUCCESS) {
761                 DEBUG2(printk("scsi%ld: %s: ERROR: Unable to retrieve size!\n",
762                               ha->host_no, __func__));
763                 goto exit_get_crash_record;
764         }
765         crash_record_size = mbox_sts[4];
766         if (crash_record_size == 0) {
767                 DEBUG2(printk("scsi%ld: %s: ERROR: Crash record size is 0!\n",
768                               ha->host_no, __func__));
769                 goto exit_get_crash_record;
770         }
771
772         /* Alloc Memory for Crash Record. */
773         crash_record = dma_alloc_coherent(&ha->pdev->dev, crash_record_size,
774                                           &crash_record_dma, GFP_KERNEL);
775         if (crash_record == NULL)
776                 goto exit_get_crash_record;
777
778         /* Get Crash Record. */
779         memset(&mbox_cmd, 0, sizeof(mbox_cmd));
780         memset(&mbox_sts, 0, sizeof(mbox_cmd));
781
782         mbox_cmd[0] = MBOX_CMD_GET_CRASH_RECORD;
783         mbox_cmd[2] = LSDW(crash_record_dma);
784         mbox_cmd[3] = MSDW(crash_record_dma);
785         mbox_cmd[4] = crash_record_size;
786
787         if (qla4xxx_mailbox_command(ha, MBOX_REG_COUNT, 5, &mbox_cmd[0], &mbox_sts[0]) !=
788             QLA_SUCCESS)
789                 goto exit_get_crash_record;
790
791         /* Dump Crash Record. */
792
793 exit_get_crash_record:
794         if (crash_record)
795                 dma_free_coherent(&ha->pdev->dev, crash_record_size,
796                                   crash_record, crash_record_dma);
797 }
798
799 /**
800  * qla4xxx_get_conn_event_log - retrieves connection event log
801  * @ha: Pointer to host adapter structure.
802  **/
803 void qla4xxx_get_conn_event_log(struct scsi_qla_host * ha)
804 {
805         uint32_t mbox_cmd[MBOX_REG_COUNT];
806         uint32_t mbox_sts[MBOX_REG_COUNT];
807         struct conn_event_log_entry *event_log = NULL;
808         dma_addr_t event_log_dma = 0;
809         uint32_t event_log_size = 0;
810         uint32_t num_valid_entries;
811         uint32_t      oldest_entry = 0;
812         uint32_t        max_event_log_entries;
813         uint8_t         i;
814
815
816         memset(&mbox_cmd, 0, sizeof(mbox_cmd));
817         memset(&mbox_sts, 0, sizeof(mbox_cmd));
818
819         /* Get size of crash record. */
820         mbox_cmd[0] = MBOX_CMD_GET_CONN_EVENT_LOG;
821
822         if (qla4xxx_mailbox_command(ha, MBOX_REG_COUNT, 5, &mbox_cmd[0], &mbox_sts[0]) !=
823             QLA_SUCCESS)
824                 goto exit_get_event_log;
825
826         event_log_size = mbox_sts[4];
827         if (event_log_size == 0)
828                 goto exit_get_event_log;
829
830         /* Alloc Memory for Crash Record. */
831         event_log = dma_alloc_coherent(&ha->pdev->dev, event_log_size,
832                                        &event_log_dma, GFP_KERNEL);
833         if (event_log == NULL)
834                 goto exit_get_event_log;
835
836         /* Get Crash Record. */
837         memset(&mbox_cmd, 0, sizeof(mbox_cmd));
838         memset(&mbox_sts, 0, sizeof(mbox_cmd));
839
840         mbox_cmd[0] = MBOX_CMD_GET_CONN_EVENT_LOG;
841         mbox_cmd[2] = LSDW(event_log_dma);
842         mbox_cmd[3] = MSDW(event_log_dma);
843
844         if (qla4xxx_mailbox_command(ha, MBOX_REG_COUNT, 5, &mbox_cmd[0], &mbox_sts[0]) !=
845             QLA_SUCCESS) {
846                 DEBUG2(printk("scsi%ld: %s: ERROR: Unable to retrieve event "
847                               "log!\n", ha->host_no, __func__));
848                 goto exit_get_event_log;
849         }
850
851         /* Dump Event Log. */
852         num_valid_entries = mbox_sts[1];
853
854         max_event_log_entries = event_log_size /
855                 sizeof(struct conn_event_log_entry);
856
857         if (num_valid_entries > max_event_log_entries)
858                 oldest_entry = num_valid_entries % max_event_log_entries;
859
860         DEBUG3(printk("scsi%ld: Connection Event Log Dump (%d entries):\n",
861                       ha->host_no, num_valid_entries));
862
863         if (ql4xextended_error_logging == 3) {
864                 if (oldest_entry == 0) {
865                         /* Circular Buffer has not wrapped around */
866                         for (i=0; i < num_valid_entries; i++) {
867                                 qla4xxx_dump_buffer((uint8_t *)event_log+
868                                                     (i*sizeof(*event_log)),
869                                                     sizeof(*event_log));
870                         }
871                 }
872                 else {
873                         /* Circular Buffer has wrapped around -
874                          * display accordingly*/
875                         for (i=oldest_entry; i < max_event_log_entries; i++) {
876                                 qla4xxx_dump_buffer((uint8_t *)event_log+
877                                                     (i*sizeof(*event_log)),
878                                                     sizeof(*event_log));
879                         }
880                         for (i=0; i < oldest_entry; i++) {
881                                 qla4xxx_dump_buffer((uint8_t *)event_log+
882                                                     (i*sizeof(*event_log)),
883                                                     sizeof(*event_log));
884                         }
885                 }
886         }
887
888 exit_get_event_log:
889         if (event_log)
890                 dma_free_coherent(&ha->pdev->dev, event_log_size, event_log,
891                                   event_log_dma);
892 }
893
894 /**
895  * qla4xxx_abort_task - issues Abort Task
896  * @ha: Pointer to host adapter structure.
897  * @srb: Pointer to srb entry
898  *
899  * This routine performs a LUN RESET on the specified target/lun.
900  * The caller must ensure that the ddb_entry and lun_entry pointers
901  * are valid before calling this routine.
902  **/
903 int qla4xxx_abort_task(struct scsi_qla_host *ha, struct srb *srb)
904 {
905         uint32_t mbox_cmd[MBOX_REG_COUNT];
906         uint32_t mbox_sts[MBOX_REG_COUNT];
907         struct scsi_cmnd *cmd = srb->cmd;
908         int status = QLA_SUCCESS;
909         unsigned long flags = 0;
910         uint32_t index;
911
912         /*
913          * Send abort task command to ISP, so that the ISP will return
914          * request with ABORT status
915          */
916         memset(&mbox_cmd, 0, sizeof(mbox_cmd));
917         memset(&mbox_sts, 0, sizeof(mbox_sts));
918
919         spin_lock_irqsave(&ha->hardware_lock, flags);
920         index = (unsigned long)(unsigned char *)cmd->host_scribble;
921         spin_unlock_irqrestore(&ha->hardware_lock, flags);
922
923         /* Firmware already posted completion on response queue */
924         if (index == MAX_SRBS)
925                 return status;
926
927         mbox_cmd[0] = MBOX_CMD_ABORT_TASK;
928         mbox_cmd[1] = srb->fw_ddb_index;
929         mbox_cmd[2] = index;
930         /* Immediate Command Enable */
931         mbox_cmd[5] = 0x01;
932
933         qla4xxx_mailbox_command(ha, MBOX_REG_COUNT, 5, &mbox_cmd[0],
934             &mbox_sts[0]);
935         if (mbox_sts[0] != MBOX_STS_COMMAND_COMPLETE) {
936                 status = QLA_ERROR;
937
938                 DEBUG2(printk(KERN_WARNING "scsi%ld:%d:%d: abort task FAILED: "
939                     "mbx0=%04X, mb1=%04X, mb2=%04X, mb3=%04X, mb4=%04X\n",
940                     ha->host_no, cmd->device->id, cmd->device->lun, mbox_sts[0],
941                     mbox_sts[1], mbox_sts[2], mbox_sts[3], mbox_sts[4]));
942         }
943
944         return status;
945 }
946
947 /**
948  * qla4xxx_reset_lun - issues LUN Reset
949  * @ha: Pointer to host adapter structure.
950  * @ddb_entry: Pointer to device database entry
951  * @lun: lun number
952  *
953  * This routine performs a LUN RESET on the specified target/lun.
954  * The caller must ensure that the ddb_entry and lun_entry pointers
955  * are valid before calling this routine.
956  **/
957 int qla4xxx_reset_lun(struct scsi_qla_host * ha, struct ddb_entry * ddb_entry,
958                       int lun)
959 {
960         uint32_t mbox_cmd[MBOX_REG_COUNT];
961         uint32_t mbox_sts[MBOX_REG_COUNT];
962         int status = QLA_SUCCESS;
963
964         DEBUG2(printk("scsi%ld:%d:%d: lun reset issued\n", ha->host_no,
965                       ddb_entry->fw_ddb_index, lun));
966
967         /*
968          * Send lun reset command to ISP, so that the ISP will return all
969          * outstanding requests with RESET status
970          */
971         memset(&mbox_cmd, 0, sizeof(mbox_cmd));
972         memset(&mbox_sts, 0, sizeof(mbox_sts));
973
974         mbox_cmd[0] = MBOX_CMD_LUN_RESET;
975         mbox_cmd[1] = ddb_entry->fw_ddb_index;
976         mbox_cmd[2] = lun << 8;
977         mbox_cmd[5] = 0x01;     /* Immediate Command Enable */
978
979         qla4xxx_mailbox_command(ha, MBOX_REG_COUNT, 1, &mbox_cmd[0], &mbox_sts[0]);
980         if (mbox_sts[0] != MBOX_STS_COMMAND_COMPLETE &&
981             mbox_sts[0] != MBOX_STS_COMMAND_ERROR)
982                 status = QLA_ERROR;
983
984         return status;
985 }
986
987 /**
988  * qla4xxx_reset_target - issues target Reset
989  * @ha: Pointer to host adapter structure.
990  * @db_entry: Pointer to device database entry
991  * @un_entry: Pointer to lun entry structure
992  *
993  * This routine performs a TARGET RESET on the specified target.
994  * The caller must ensure that the ddb_entry pointers
995  * are valid before calling this routine.
996  **/
997 int qla4xxx_reset_target(struct scsi_qla_host *ha,
998                          struct ddb_entry *ddb_entry)
999 {
1000         uint32_t mbox_cmd[MBOX_REG_COUNT];
1001         uint32_t mbox_sts[MBOX_REG_COUNT];
1002         int status = QLA_SUCCESS;
1003
1004         DEBUG2(printk("scsi%ld:%d: target reset issued\n", ha->host_no,
1005                       ddb_entry->fw_ddb_index));
1006
1007         /*
1008          * Send target reset command to ISP, so that the ISP will return all
1009          * outstanding requests with RESET status
1010          */
1011         memset(&mbox_cmd, 0, sizeof(mbox_cmd));
1012         memset(&mbox_sts, 0, sizeof(mbox_sts));
1013
1014         mbox_cmd[0] = MBOX_CMD_TARGET_WARM_RESET;
1015         mbox_cmd[1] = ddb_entry->fw_ddb_index;
1016         mbox_cmd[5] = 0x01;     /* Immediate Command Enable */
1017
1018         qla4xxx_mailbox_command(ha, MBOX_REG_COUNT, 1, &mbox_cmd[0],
1019                                 &mbox_sts[0]);
1020         if (mbox_sts[0] != MBOX_STS_COMMAND_COMPLETE &&
1021             mbox_sts[0] != MBOX_STS_COMMAND_ERROR)
1022                 status = QLA_ERROR;
1023
1024         return status;
1025 }
1026
1027 int qla4xxx_get_flash(struct scsi_qla_host * ha, dma_addr_t dma_addr,
1028                       uint32_t offset, uint32_t len)
1029 {
1030         uint32_t mbox_cmd[MBOX_REG_COUNT];
1031         uint32_t mbox_sts[MBOX_REG_COUNT];
1032
1033         memset(&mbox_cmd, 0, sizeof(mbox_cmd));
1034         memset(&mbox_sts, 0, sizeof(mbox_sts));
1035
1036         mbox_cmd[0] = MBOX_CMD_READ_FLASH;
1037         mbox_cmd[1] = LSDW(dma_addr);
1038         mbox_cmd[2] = MSDW(dma_addr);
1039         mbox_cmd[3] = offset;
1040         mbox_cmd[4] = len;
1041
1042         if (qla4xxx_mailbox_command(ha, MBOX_REG_COUNT, 2, &mbox_cmd[0], &mbox_sts[0]) !=
1043             QLA_SUCCESS) {
1044                 DEBUG2(printk("scsi%ld: %s: MBOX_CMD_READ_FLASH, failed w/ "
1045                     "status %04X %04X, offset %08x, len %08x\n", ha->host_no,
1046                     __func__, mbox_sts[0], mbox_sts[1], offset, len));
1047                 return QLA_ERROR;
1048         }
1049         return QLA_SUCCESS;
1050 }
1051
1052 /**
1053  * qla4xxx_get_fw_version - gets firmware version
1054  * @ha: Pointer to host adapter structure.
1055  *
1056  * Retrieves the firmware version on HBA. In QLA4010, mailboxes 2 & 3 may
1057  * hold an address for data.  Make sure that we write 0 to those mailboxes,
1058  * if unused.
1059  **/
1060 int qla4xxx_get_fw_version(struct scsi_qla_host * ha)
1061 {
1062         uint32_t mbox_cmd[MBOX_REG_COUNT];
1063         uint32_t mbox_sts[MBOX_REG_COUNT];
1064
1065         /* Get firmware version. */
1066         memset(&mbox_cmd, 0, sizeof(mbox_cmd));
1067         memset(&mbox_sts, 0, sizeof(mbox_sts));
1068
1069         mbox_cmd[0] = MBOX_CMD_ABOUT_FW;
1070
1071         if (qla4xxx_mailbox_command(ha, MBOX_REG_COUNT, 5, &mbox_cmd[0], &mbox_sts[0]) !=
1072             QLA_SUCCESS) {
1073                 DEBUG2(printk("scsi%ld: %s: MBOX_CMD_ABOUT_FW failed w/ "
1074                     "status %04X\n", ha->host_no, __func__, mbox_sts[0]));
1075                 return QLA_ERROR;
1076         }
1077
1078         /* Save firmware version information. */
1079         ha->firmware_version[0] = mbox_sts[1];
1080         ha->firmware_version[1] = mbox_sts[2];
1081         ha->patch_number = mbox_sts[3];
1082         ha->build_number = mbox_sts[4];
1083
1084         return QLA_SUCCESS;
1085 }
1086
1087 static int qla4xxx_get_default_ddb(struct scsi_qla_host *ha,
1088                                    dma_addr_t dma_addr)
1089 {
1090         uint32_t mbox_cmd[MBOX_REG_COUNT];
1091         uint32_t mbox_sts[MBOX_REG_COUNT];
1092
1093         memset(&mbox_cmd, 0, sizeof(mbox_cmd));
1094         memset(&mbox_sts, 0, sizeof(mbox_sts));
1095
1096         mbox_cmd[0] = MBOX_CMD_GET_DATABASE_ENTRY_DEFAULTS;
1097         mbox_cmd[2] = LSDW(dma_addr);
1098         mbox_cmd[3] = MSDW(dma_addr);
1099
1100         if (qla4xxx_mailbox_command(ha, MBOX_REG_COUNT, 1, &mbox_cmd[0], &mbox_sts[0]) !=
1101             QLA_SUCCESS) {
1102                 DEBUG2(printk("scsi%ld: %s: failed status %04X\n",
1103                      ha->host_no, __func__, mbox_sts[0]));
1104                 return QLA_ERROR;
1105         }
1106         return QLA_SUCCESS;
1107 }
1108
1109 static int qla4xxx_req_ddb_entry(struct scsi_qla_host *ha, uint32_t *ddb_index)
1110 {
1111         uint32_t mbox_cmd[MBOX_REG_COUNT];
1112         uint32_t mbox_sts[MBOX_REG_COUNT];
1113
1114         memset(&mbox_cmd, 0, sizeof(mbox_cmd));
1115         memset(&mbox_sts, 0, sizeof(mbox_sts));
1116
1117         mbox_cmd[0] = MBOX_CMD_REQUEST_DATABASE_ENTRY;
1118         mbox_cmd[1] = MAX_PRST_DEV_DB_ENTRIES;
1119
1120         if (qla4xxx_mailbox_command(ha, MBOX_REG_COUNT, 3, &mbox_cmd[0], &mbox_sts[0]) !=
1121             QLA_SUCCESS) {
1122                 if (mbox_sts[0] == MBOX_STS_COMMAND_ERROR) {
1123                         *ddb_index = mbox_sts[2];
1124                 } else {
1125                         DEBUG2(printk("scsi%ld: %s: failed status %04X\n",
1126                              ha->host_no, __func__, mbox_sts[0]));
1127                         return QLA_ERROR;
1128                 }
1129         } else {
1130                 *ddb_index = MAX_PRST_DEV_DB_ENTRIES;
1131         }
1132
1133         return QLA_SUCCESS;
1134 }
1135
1136
1137 int qla4xxx_send_tgts(struct scsi_qla_host *ha, char *ip, uint16_t port)
1138 {
1139         struct dev_db_entry *fw_ddb_entry;
1140         dma_addr_t fw_ddb_entry_dma;
1141         uint32_t ddb_index;
1142         int ret_val = QLA_SUCCESS;
1143
1144
1145         fw_ddb_entry = dma_alloc_coherent(&ha->pdev->dev,
1146                                           sizeof(*fw_ddb_entry),
1147                                           &fw_ddb_entry_dma, GFP_KERNEL);
1148         if (!fw_ddb_entry) {
1149                 DEBUG2(printk("scsi%ld: %s: Unable to allocate dma buffer.\n",
1150                               ha->host_no, __func__));
1151                 ret_val = QLA_ERROR;
1152                 goto exit_send_tgts_no_free;
1153         }
1154
1155         ret_val = qla4xxx_get_default_ddb(ha, fw_ddb_entry_dma);
1156         if (ret_val != QLA_SUCCESS)
1157                 goto exit_send_tgts;
1158
1159         ret_val = qla4xxx_req_ddb_entry(ha, &ddb_index);
1160         if (ret_val != QLA_SUCCESS)
1161                 goto exit_send_tgts;
1162
1163         memset(fw_ddb_entry->iscsi_alias, 0,
1164                sizeof(fw_ddb_entry->iscsi_alias));
1165
1166         memset(fw_ddb_entry->iscsi_name, 0,
1167                sizeof(fw_ddb_entry->iscsi_name));
1168
1169         memset(fw_ddb_entry->ip_addr, 0, sizeof(fw_ddb_entry->ip_addr));
1170         memset(fw_ddb_entry->tgt_addr, 0,
1171                sizeof(fw_ddb_entry->tgt_addr));
1172
1173         fw_ddb_entry->options = (DDB_OPT_DISC_SESSION | DDB_OPT_TARGET);
1174         fw_ddb_entry->port = cpu_to_le16(ntohs(port));
1175
1176         fw_ddb_entry->ip_addr[0] = *ip;
1177         fw_ddb_entry->ip_addr[1] = *(ip + 1);
1178         fw_ddb_entry->ip_addr[2] = *(ip + 2);
1179         fw_ddb_entry->ip_addr[3] = *(ip + 3);
1180
1181         ret_val = qla4xxx_set_ddb_entry(ha, ddb_index, fw_ddb_entry_dma);
1182
1183 exit_send_tgts:
1184         dma_free_coherent(&ha->pdev->dev, sizeof(*fw_ddb_entry),
1185                           fw_ddb_entry, fw_ddb_entry_dma);
1186 exit_send_tgts_no_free:
1187         return ret_val;
1188 }
1189