scsi: be2iscsi: Handle only NET_PARAM in iface_get_param
[cascardo/linux.git] / drivers / scsi / be2iscsi / be_mgmt.c
1 /**
2  * Copyright (C) 2005 - 2015 Emulex
3  * All rights reserved.
4  *
5  * This program is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU General Public License version 2
7  * as published by the Free Software Foundation.  The full GNU General
8  * Public License is included in this distribution in the file called COPYING.
9  *
10  * Written by: Jayamohan Kallickal (jayamohan.kallickal@avagotech.com)
11  *
12  * Contact Information:
13  * linux-drivers@avagotech.com
14  *
15  * Emulex
16  * 3333 Susan Street
17  * Costa Mesa, CA 92626
18  */
19
20 #include <linux/bsg-lib.h>
21 #include <scsi/scsi_transport_iscsi.h>
22 #include <scsi/scsi_bsg_iscsi.h>
23 #include "be_mgmt.h"
24 #include "be_iscsi.h"
25 #include "be_main.h"
26
27 /* UE Status Low CSR */
28 static const char * const desc_ue_status_low[] = {
29         "CEV",
30         "CTX",
31         "DBUF",
32         "ERX",
33         "Host",
34         "MPU",
35         "NDMA",
36         "PTC ",
37         "RDMA ",
38         "RXF ",
39         "RXIPS ",
40         "RXULP0 ",
41         "RXULP1 ",
42         "RXULP2 ",
43         "TIM ",
44         "TPOST ",
45         "TPRE ",
46         "TXIPS ",
47         "TXULP0 ",
48         "TXULP1 ",
49         "UC ",
50         "WDMA ",
51         "TXULP2 ",
52         "HOST1 ",
53         "P0_OB_LINK ",
54         "P1_OB_LINK ",
55         "HOST_GPIO ",
56         "MBOX ",
57         "AXGMAC0",
58         "AXGMAC1",
59         "JTAG",
60         "MPU_INTPEND"
61 };
62
63 /* UE Status High CSR */
64 static const char * const desc_ue_status_hi[] = {
65         "LPCMEMHOST",
66         "MGMT_MAC",
67         "PCS0ONLINE",
68         "MPU_IRAM",
69         "PCS1ONLINE",
70         "PCTL0",
71         "PCTL1",
72         "PMEM",
73         "RR",
74         "TXPB",
75         "RXPP",
76         "XAUI",
77         "TXP",
78         "ARM",
79         "IPC",
80         "HOST2",
81         "HOST3",
82         "HOST4",
83         "HOST5",
84         "HOST6",
85         "HOST7",
86         "HOST8",
87         "HOST9",
88         "NETC",
89         "Unknown",
90         "Unknown",
91         "Unknown",
92         "Unknown",
93         "Unknown",
94         "Unknown",
95         "Unknown",
96         "Unknown"
97 };
98
99 /*
100  * beiscsi_ue_detec()- Detect Unrecoverable Error on adapter
101  * @phba: Driver priv structure
102  *
103  * Read registers linked to UE and check for the UE status
104  **/
105 void beiscsi_ue_detect(struct beiscsi_hba *phba)
106 {
107         uint32_t ue_hi = 0, ue_lo = 0;
108         uint32_t ue_mask_hi = 0, ue_mask_lo = 0;
109         uint8_t i = 0;
110
111         if (phba->ue_detected)
112                 return;
113
114         pci_read_config_dword(phba->pcidev,
115                               PCICFG_UE_STATUS_LOW, &ue_lo);
116         pci_read_config_dword(phba->pcidev,
117                               PCICFG_UE_STATUS_MASK_LOW,
118                               &ue_mask_lo);
119         pci_read_config_dword(phba->pcidev,
120                               PCICFG_UE_STATUS_HIGH,
121                               &ue_hi);
122         pci_read_config_dword(phba->pcidev,
123                               PCICFG_UE_STATUS_MASK_HI,
124                               &ue_mask_hi);
125
126         ue_lo = (ue_lo & ~ue_mask_lo);
127         ue_hi = (ue_hi & ~ue_mask_hi);
128
129
130         if (ue_lo || ue_hi) {
131                 phba->ue_detected = true;
132                 beiscsi_log(phba, KERN_ERR,
133                             BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX,
134                             "BG_%d : Error detected on the adapter\n");
135         }
136
137         if (ue_lo) {
138                 for (i = 0; ue_lo; ue_lo >>= 1, i++) {
139                         if (ue_lo & 1)
140                                 beiscsi_log(phba, KERN_ERR,
141                                             BEISCSI_LOG_CONFIG,
142                                             "BG_%d : UE_LOW %s bit set\n",
143                                             desc_ue_status_low[i]);
144                 }
145         }
146
147         if (ue_hi) {
148                 for (i = 0; ue_hi; ue_hi >>= 1, i++) {
149                         if (ue_hi & 1)
150                                 beiscsi_log(phba, KERN_ERR,
151                                             BEISCSI_LOG_CONFIG,
152                                             "BG_%d : UE_HIGH %s bit set\n",
153                                             desc_ue_status_hi[i]);
154                 }
155         }
156 }
157
158 int be_cmd_modify_eq_delay(struct beiscsi_hba *phba,
159                  struct be_set_eqd *set_eqd, int num)
160 {
161         struct be_ctrl_info *ctrl = &phba->ctrl;
162         struct be_mcc_wrb *wrb;
163         struct be_cmd_req_modify_eq_delay *req;
164         unsigned int tag;
165         int i;
166
167         mutex_lock(&ctrl->mbox_lock);
168         wrb = alloc_mcc_wrb(phba, &tag);
169         if (!wrb) {
170                 mutex_unlock(&ctrl->mbox_lock);
171                 return 0;
172         }
173
174         req = embedded_payload(wrb);
175         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
176         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_COMMON,
177                 OPCODE_COMMON_MODIFY_EQ_DELAY, sizeof(*req));
178
179         req->num_eq = cpu_to_le32(num);
180         for (i = 0; i < num; i++) {
181                 req->delay[i].eq_id = cpu_to_le32(set_eqd[i].eq_id);
182                 req->delay[i].phase = 0;
183                 req->delay[i].delay_multiplier =
184                                 cpu_to_le32(set_eqd[i].delay_multiplier);
185         }
186
187         be_mcc_notify(phba, tag);
188         mutex_unlock(&ctrl->mbox_lock);
189         return tag;
190 }
191
192 /**
193  * mgmt_reopen_session()- Reopen a session based on reopen_type
194  * @phba: Device priv structure instance
195  * @reopen_type: Type of reopen_session FW should do.
196  * @sess_handle: Session Handle of the session to be re-opened
197  *
198  * return
199  *      the TAG used for MBOX Command
200  *
201  **/
202 unsigned int mgmt_reopen_session(struct beiscsi_hba *phba,
203                                   unsigned int reopen_type,
204                                   unsigned int sess_handle)
205 {
206         struct be_ctrl_info *ctrl = &phba->ctrl;
207         struct be_mcc_wrb *wrb;
208         struct be_cmd_reopen_session_req *req;
209         unsigned int tag;
210
211         beiscsi_log(phba, KERN_INFO,
212                     BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX,
213                     "BG_%d : In bescsi_get_boot_target\n");
214
215         mutex_lock(&ctrl->mbox_lock);
216         wrb = alloc_mcc_wrb(phba, &tag);
217         if (!wrb) {
218                 mutex_unlock(&ctrl->mbox_lock);
219                 return 0;
220         }
221
222         req = embedded_payload(wrb);
223         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
224         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI_INI,
225                            OPCODE_ISCSI_INI_DRIVER_REOPEN_ALL_SESSIONS,
226                            sizeof(struct be_cmd_reopen_session_resp));
227
228         /* set the reopen_type,sess_handle */
229         req->reopen_type = reopen_type;
230         req->session_handle = sess_handle;
231
232         be_mcc_notify(phba, tag);
233         mutex_unlock(&ctrl->mbox_lock);
234         return tag;
235 }
236
237 unsigned int mgmt_get_boot_target(struct beiscsi_hba *phba)
238 {
239         struct be_ctrl_info *ctrl = &phba->ctrl;
240         struct be_mcc_wrb *wrb;
241         struct be_cmd_get_boot_target_req *req;
242         unsigned int tag;
243
244         beiscsi_log(phba, KERN_INFO,
245                     BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX,
246                     "BG_%d : In bescsi_get_boot_target\n");
247
248         mutex_lock(&ctrl->mbox_lock);
249         wrb = alloc_mcc_wrb(phba, &tag);
250         if (!wrb) {
251                 mutex_unlock(&ctrl->mbox_lock);
252                 return 0;
253         }
254
255         req = embedded_payload(wrb);
256         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
257         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI_INI,
258                            OPCODE_ISCSI_INI_BOOT_GET_BOOT_TARGET,
259                            sizeof(struct be_cmd_get_boot_target_resp));
260
261         be_mcc_notify(phba, tag);
262         mutex_unlock(&ctrl->mbox_lock);
263         return tag;
264 }
265
266 unsigned int mgmt_get_session_info(struct beiscsi_hba *phba,
267                                    u32 boot_session_handle,
268                                    struct be_dma_mem *nonemb_cmd)
269 {
270         struct be_ctrl_info *ctrl = &phba->ctrl;
271         struct be_mcc_wrb *wrb;
272         unsigned int tag;
273         struct  be_cmd_get_session_req *req;
274         struct be_cmd_get_session_resp *resp;
275         struct be_sge *sge;
276
277         beiscsi_log(phba, KERN_INFO,
278                     BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX,
279                     "BG_%d : In beiscsi_get_session_info\n");
280
281         mutex_lock(&ctrl->mbox_lock);
282         wrb = alloc_mcc_wrb(phba, &tag);
283         if (!wrb) {
284                 mutex_unlock(&ctrl->mbox_lock);
285                 return 0;
286         }
287
288         nonemb_cmd->size = sizeof(*resp);
289         req = nonemb_cmd->va;
290         memset(req, 0, sizeof(*req));
291         sge = nonembedded_sgl(wrb);
292         be_wrb_hdr_prepare(wrb, sizeof(*req), false, 1);
293         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI_INI,
294                            OPCODE_ISCSI_INI_SESSION_GET_A_SESSION,
295                            sizeof(*resp));
296         req->session_handle = boot_session_handle;
297         sge->pa_hi = cpu_to_le32(upper_32_bits(nonemb_cmd->dma));
298         sge->pa_lo = cpu_to_le32(nonemb_cmd->dma & 0xFFFFFFFF);
299         sge->len = cpu_to_le32(nonemb_cmd->size);
300
301         be_mcc_notify(phba, tag);
302         mutex_unlock(&ctrl->mbox_lock);
303         return tag;
304 }
305
306 /**
307  * mgmt_get_port_name()- Get port name for the function
308  * @ctrl: ptr to Ctrl Info
309  * @phba: ptr to the dev priv structure
310  *
311  * Get the alphanumeric character for port
312  *
313  **/
314 int mgmt_get_port_name(struct be_ctrl_info *ctrl,
315                        struct beiscsi_hba *phba)
316 {
317         int ret = 0;
318         struct be_mcc_wrb *wrb;
319         struct be_cmd_get_port_name *ioctl;
320
321         mutex_lock(&ctrl->mbox_lock);
322         wrb = wrb_from_mbox(&ctrl->mbox_mem);
323         memset(wrb, 0, sizeof(*wrb));
324         ioctl = embedded_payload(wrb);
325
326         be_wrb_hdr_prepare(wrb, sizeof(*ioctl), true, 0);
327         be_cmd_hdr_prepare(&ioctl->h.req_hdr, CMD_SUBSYSTEM_COMMON,
328                            OPCODE_COMMON_GET_PORT_NAME,
329                            EMBED_MBX_MAX_PAYLOAD_SIZE);
330         ret = be_mbox_notify(ctrl);
331         phba->port_name = 0;
332         if (!ret) {
333                 phba->port_name = ioctl->p.resp.port_names >>
334                                   (phba->fw_config.phys_port * 8) & 0xff;
335         } else {
336                 beiscsi_log(phba, KERN_INFO, BEISCSI_LOG_INIT,
337                             "BG_%d : GET_PORT_NAME ret 0x%x status 0x%x\n",
338                             ret, ioctl->h.resp_hdr.status);
339         }
340
341         if (phba->port_name == 0)
342                 phba->port_name = '?';
343
344         mutex_unlock(&ctrl->mbox_lock);
345         return ret;
346 }
347
348 /**
349  * mgmt_get_fw_config()- Get the FW config for the function
350  * @ctrl: ptr to Ctrl Info
351  * @phba: ptr to the dev priv structure
352  *
353  * Get the FW config and resources available for the function.
354  * The resources are created based on the count received here.
355  *
356  * return
357  *      Success: 0
358  *      Failure: Non-Zero Value
359  **/
360 int mgmt_get_fw_config(struct be_ctrl_info *ctrl,
361                                 struct beiscsi_hba *phba)
362 {
363         struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem);
364         struct be_fw_cfg *pfw_cfg = embedded_payload(wrb);
365         uint32_t cid_count, icd_count;
366         int status = -EINVAL;
367         uint8_t ulp_num = 0;
368
369         mutex_lock(&ctrl->mbox_lock);
370         memset(wrb, 0, sizeof(*wrb));
371         be_wrb_hdr_prepare(wrb, sizeof(*pfw_cfg), true, 0);
372
373         be_cmd_hdr_prepare(&pfw_cfg->hdr, CMD_SUBSYSTEM_COMMON,
374                            OPCODE_COMMON_QUERY_FIRMWARE_CONFIG,
375                            EMBED_MBX_MAX_PAYLOAD_SIZE);
376
377         if (be_mbox_notify(ctrl)) {
378                 beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_INIT,
379                             "BG_%d : Failed in mgmt_get_fw_config\n");
380                 goto fail_init;
381         }
382
383         /* FW response formats depend on port id */
384         phba->fw_config.phys_port = pfw_cfg->phys_port;
385         if (phba->fw_config.phys_port >= BEISCSI_PHYS_PORT_MAX) {
386                 beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_INIT,
387                             "BG_%d : invalid physical port id %d\n",
388                             phba->fw_config.phys_port);
389                 goto fail_init;
390         }
391
392         /* populate and check FW config against min and max values */
393         if (!is_chip_be2_be3r(phba)) {
394                 phba->fw_config.eqid_count = pfw_cfg->eqid_count;
395                 phba->fw_config.cqid_count = pfw_cfg->cqid_count;
396                 if (phba->fw_config.eqid_count == 0 ||
397                     phba->fw_config.eqid_count > 2048) {
398                         beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_INIT,
399                                     "BG_%d : invalid EQ count %d\n",
400                                     phba->fw_config.eqid_count);
401                         goto fail_init;
402                 }
403                 if (phba->fw_config.cqid_count == 0 ||
404                     phba->fw_config.cqid_count > 4096) {
405                         beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_INIT,
406                                     "BG_%d : invalid CQ count %d\n",
407                                     phba->fw_config.cqid_count);
408                         goto fail_init;
409                 }
410                 beiscsi_log(phba, KERN_INFO, BEISCSI_LOG_INIT,
411                             "BG_%d : EQ_Count : %d CQ_Count : %d\n",
412                             phba->fw_config.eqid_count,
413                             phba->fw_config.cqid_count);
414         }
415
416         /**
417          * Check on which all ULP iSCSI Protocol is loaded.
418          * Set the Bit for those ULP. This set flag is used
419          * at all places in the code to check on which ULP
420          * iSCSi Protocol is loaded
421          **/
422         for (ulp_num = 0; ulp_num < BEISCSI_ULP_COUNT; ulp_num++) {
423                 if (pfw_cfg->ulp[ulp_num].ulp_mode &
424                     BEISCSI_ULP_ISCSI_INI_MODE) {
425                         set_bit(ulp_num, &phba->fw_config.ulp_supported);
426
427                         /* Get the CID, ICD and Chain count for each ULP */
428                         phba->fw_config.iscsi_cid_start[ulp_num] =
429                                 pfw_cfg->ulp[ulp_num].sq_base;
430                         phba->fw_config.iscsi_cid_count[ulp_num] =
431                                 pfw_cfg->ulp[ulp_num].sq_count;
432
433                         phba->fw_config.iscsi_icd_start[ulp_num] =
434                                 pfw_cfg->ulp[ulp_num].icd_base;
435                         phba->fw_config.iscsi_icd_count[ulp_num] =
436                                 pfw_cfg->ulp[ulp_num].icd_count;
437
438                         phba->fw_config.iscsi_chain_start[ulp_num] =
439                                 pfw_cfg->chain_icd[ulp_num].chain_base;
440                         phba->fw_config.iscsi_chain_count[ulp_num] =
441                                 pfw_cfg->chain_icd[ulp_num].chain_count;
442
443                         beiscsi_log(phba, KERN_INFO, BEISCSI_LOG_INIT,
444                                     "BG_%d : Function loaded on ULP : %d\n"
445                                     "\tiscsi_cid_count : %d\n"
446                                     "\tiscsi_cid_start : %d\n"
447                                     "\t iscsi_icd_count : %d\n"
448                                     "\t iscsi_icd_start : %d\n",
449                                     ulp_num,
450                                     phba->fw_config.
451                                     iscsi_cid_count[ulp_num],
452                                     phba->fw_config.
453                                     iscsi_cid_start[ulp_num],
454                                     phba->fw_config.
455                                     iscsi_icd_count[ulp_num],
456                                     phba->fw_config.
457                                     iscsi_icd_start[ulp_num]);
458                 }
459         }
460
461         if (phba->fw_config.ulp_supported == 0) {
462                 beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_INIT,
463                             "BG_%d : iSCSI initiator mode not set: ULP0 %x ULP1 %x\n",
464                             pfw_cfg->ulp[BEISCSI_ULP0].ulp_mode,
465                             pfw_cfg->ulp[BEISCSI_ULP1].ulp_mode);
466                 goto fail_init;
467         }
468
469         /**
470          * ICD is shared among ULPs. Use icd_count of any one loaded ULP
471          **/
472         for (ulp_num = 0; ulp_num < BEISCSI_ULP_COUNT; ulp_num++)
473                 if (test_bit(ulp_num, &phba->fw_config.ulp_supported))
474                         break;
475         icd_count = phba->fw_config.iscsi_icd_count[ulp_num];
476         if (icd_count == 0 || icd_count > 65536) {
477                 beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_INIT,
478                             "BG_%d: invalid ICD count %d\n", icd_count);
479                 goto fail_init;
480         }
481
482         cid_count = BEISCSI_GET_CID_COUNT(phba, BEISCSI_ULP0) +
483                     BEISCSI_GET_CID_COUNT(phba, BEISCSI_ULP1);
484         if (cid_count == 0 || cid_count > 4096) {
485                 beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_INIT,
486                             "BG_%d: invalid CID count %d\n", cid_count);
487                 goto fail_init;
488         }
489
490         /**
491          * Check FW is dual ULP aware i.e. can handle either
492          * of the protocols.
493          */
494         phba->fw_config.dual_ulp_aware = (pfw_cfg->function_mode &
495                                           BEISCSI_FUNC_DUA_MODE);
496
497         beiscsi_log(phba, KERN_INFO, BEISCSI_LOG_INIT,
498                     "BG_%d : DUA Mode : 0x%x\n",
499                     phba->fw_config.dual_ulp_aware);
500
501         /* all set, continue using this FW config */
502         status = 0;
503 fail_init:
504         mutex_unlock(&ctrl->mbox_lock);
505         return status;
506 }
507
508 int mgmt_check_supported_fw(struct be_ctrl_info *ctrl,
509                                       struct beiscsi_hba *phba)
510 {
511         struct be_dma_mem nonemb_cmd;
512         struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem);
513         struct be_mgmt_controller_attributes *req;
514         struct be_sge *sge = nonembedded_sgl(wrb);
515         int status = 0;
516
517         nonemb_cmd.va = pci_alloc_consistent(ctrl->pdev,
518                                 sizeof(struct be_mgmt_controller_attributes),
519                                 &nonemb_cmd.dma);
520         if (nonemb_cmd.va == NULL) {
521                 beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_INIT,
522                             "BG_%d : Failed to allocate memory for "
523                             "mgmt_check_supported_fw\n");
524                 return -ENOMEM;
525         }
526         nonemb_cmd.size = sizeof(struct be_mgmt_controller_attributes);
527         req = nonemb_cmd.va;
528         memset(req, 0, sizeof(*req));
529         mutex_lock(&ctrl->mbox_lock);
530         memset(wrb, 0, sizeof(*wrb));
531         be_wrb_hdr_prepare(wrb, sizeof(*req), false, 1);
532         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_COMMON,
533                            OPCODE_COMMON_GET_CNTL_ATTRIBUTES, sizeof(*req));
534         sge->pa_hi = cpu_to_le32(upper_32_bits(nonemb_cmd.dma));
535         sge->pa_lo = cpu_to_le32(nonemb_cmd.dma & 0xFFFFFFFF);
536         sge->len = cpu_to_le32(nonemb_cmd.size);
537         status = be_mbox_notify(ctrl);
538         if (!status) {
539                 struct be_mgmt_controller_attributes_resp *resp = nonemb_cmd.va;
540                 beiscsi_log(phba, KERN_INFO, BEISCSI_LOG_INIT,
541                             "BG_%d : Firmware Version of CMD : %s\n"
542                             "Firmware Version is : %s\n"
543                             "Developer Build, not performing version check...\n",
544                             resp->params.hba_attribs
545                             .flashrom_version_string,
546                             resp->params.hba_attribs.
547                             firmware_version_string);
548
549                 phba->fw_config.iscsi_features =
550                                 resp->params.hba_attribs.iscsi_features;
551                 beiscsi_log(phba, KERN_INFO, BEISCSI_LOG_INIT,
552                             "BM_%d : phba->fw_config.iscsi_features = %d\n",
553                             phba->fw_config.iscsi_features);
554                 memcpy(phba->fw_ver_str, resp->params.hba_attribs.
555                        firmware_version_string, BEISCSI_VER_STRLEN);
556         } else
557                 beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_INIT,
558                             "BG_%d :  Failed in mgmt_check_supported_fw\n");
559         mutex_unlock(&ctrl->mbox_lock);
560         if (nonemb_cmd.va)
561                 pci_free_consistent(ctrl->pdev, nonemb_cmd.size,
562                                     nonemb_cmd.va, nonemb_cmd.dma);
563
564         return status;
565 }
566
567 unsigned int mgmt_vendor_specific_fw_cmd(struct be_ctrl_info *ctrl,
568                                          struct beiscsi_hba *phba,
569                                          struct bsg_job *job,
570                                          struct be_dma_mem *nonemb_cmd)
571 {
572         struct be_cmd_resp_hdr *resp;
573         struct be_mcc_wrb *wrb;
574         struct be_sge *mcc_sge;
575         unsigned int tag = 0;
576         struct iscsi_bsg_request *bsg_req = job->request;
577         struct be_bsg_vendor_cmd *req = nonemb_cmd->va;
578         unsigned short region, sector_size, sector, offset;
579
580         nonemb_cmd->size = job->request_payload.payload_len;
581         memset(nonemb_cmd->va, 0, nonemb_cmd->size);
582         resp = nonemb_cmd->va;
583         region =  bsg_req->rqst_data.h_vendor.vendor_cmd[1];
584         sector_size =  bsg_req->rqst_data.h_vendor.vendor_cmd[2];
585         sector =  bsg_req->rqst_data.h_vendor.vendor_cmd[3];
586         offset =  bsg_req->rqst_data.h_vendor.vendor_cmd[4];
587         req->region = region;
588         req->sector = sector;
589         req->offset = offset;
590
591         if (mutex_lock_interruptible(&ctrl->mbox_lock))
592                 return 0;
593         switch (bsg_req->rqst_data.h_vendor.vendor_cmd[0]) {
594         case BEISCSI_WRITE_FLASH:
595                 offset = sector * sector_size + offset;
596                 be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI,
597                                    OPCODE_COMMON_WRITE_FLASH, sizeof(*req));
598                 sg_copy_to_buffer(job->request_payload.sg_list,
599                                   job->request_payload.sg_cnt,
600                                   nonemb_cmd->va + offset, job->request_len);
601                 break;
602         case BEISCSI_READ_FLASH:
603                 be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI,
604                            OPCODE_COMMON_READ_FLASH, sizeof(*req));
605                 break;
606         default:
607                 beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
608                             "BG_%d : Unsupported cmd = 0x%x\n\n",
609                             bsg_req->rqst_data.h_vendor.vendor_cmd[0]);
610
611                 mutex_unlock(&ctrl->mbox_lock);
612                 return -EPERM;
613         }
614
615         wrb = alloc_mcc_wrb(phba, &tag);
616         if (!wrb) {
617                 mutex_unlock(&ctrl->mbox_lock);
618                 return 0;
619         }
620
621         mcc_sge = nonembedded_sgl(wrb);
622         be_wrb_hdr_prepare(wrb, nonemb_cmd->size, false,
623                            job->request_payload.sg_cnt);
624         mcc_sge->pa_hi = cpu_to_le32(upper_32_bits(nonemb_cmd->dma));
625         mcc_sge->pa_lo = cpu_to_le32(nonemb_cmd->dma & 0xFFFFFFFF);
626         mcc_sge->len = cpu_to_le32(nonemb_cmd->size);
627
628         be_mcc_notify(phba, tag);
629
630         mutex_unlock(&ctrl->mbox_lock);
631         return tag;
632 }
633
634 /**
635  * mgmt_epfw_cleanup()- Inform FW to cleanup data structures.
636  * @phba: pointer to dev priv structure
637  * @ulp_num: ULP number.
638  *
639  * return
640  *      Success: 0
641  *      Failure: Non-Zero Value
642  **/
643 int mgmt_epfw_cleanup(struct beiscsi_hba *phba, unsigned short ulp_num)
644 {
645         struct be_ctrl_info *ctrl = &phba->ctrl;
646         struct be_mcc_wrb *wrb;
647         struct iscsi_cleanup_req *req;
648         unsigned int tag;
649         int status;
650
651         mutex_lock(&ctrl->mbox_lock);
652         wrb = alloc_mcc_wrb(phba, &tag);
653         if (!wrb) {
654                 mutex_unlock(&ctrl->mbox_lock);
655                 return -EBUSY;
656         }
657
658         req = embedded_payload(wrb);
659         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
660         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI,
661                            OPCODE_COMMON_ISCSI_CLEANUP, sizeof(*req));
662
663         req->chute = (1 << ulp_num);
664         req->hdr_ring_id = cpu_to_le16(HWI_GET_DEF_HDRQ_ID(phba, ulp_num));
665         req->data_ring_id = cpu_to_le16(HWI_GET_DEF_BUFQ_ID(phba, ulp_num));
666
667         be_mcc_notify(phba, tag);
668         status = be_mcc_compl_poll(phba, tag);
669         if (status)
670                 beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_INIT,
671                             "BG_%d : mgmt_epfw_cleanup , FAILED\n");
672         mutex_unlock(&ctrl->mbox_lock);
673         return status;
674 }
675
676 unsigned int  mgmt_invalidate_icds(struct beiscsi_hba *phba,
677                                 struct invalidate_command_table *inv_tbl,
678                                 unsigned int num_invalidate, unsigned int cid,
679                                 struct be_dma_mem *nonemb_cmd)
680
681 {
682         struct be_ctrl_info *ctrl = &phba->ctrl;
683         struct be_mcc_wrb *wrb;
684         struct be_sge *sge;
685         struct invalidate_commands_params_in *req;
686         unsigned int i, tag;
687
688         mutex_lock(&ctrl->mbox_lock);
689         wrb = alloc_mcc_wrb(phba, &tag);
690         if (!wrb) {
691                 mutex_unlock(&ctrl->mbox_lock);
692                 return 0;
693         }
694
695         req = nonemb_cmd->va;
696         memset(req, 0, sizeof(*req));
697         sge = nonembedded_sgl(wrb);
698
699         be_wrb_hdr_prepare(wrb, sizeof(*req), false, 1);
700         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI,
701                         OPCODE_COMMON_ISCSI_ERROR_RECOVERY_INVALIDATE_COMMANDS,
702                         sizeof(*req));
703         req->ref_handle = 0;
704         req->cleanup_type = CMD_ISCSI_COMMAND_INVALIDATE;
705         for (i = 0; i < num_invalidate; i++) {
706                 req->table[i].icd = inv_tbl->icd;
707                 req->table[i].cid = inv_tbl->cid;
708                 req->icd_count++;
709                 inv_tbl++;
710         }
711         sge->pa_hi = cpu_to_le32(upper_32_bits(nonemb_cmd->dma));
712         sge->pa_lo = cpu_to_le32(nonemb_cmd->dma & 0xFFFFFFFF);
713         sge->len = cpu_to_le32(nonemb_cmd->size);
714
715         be_mcc_notify(phba, tag);
716         mutex_unlock(&ctrl->mbox_lock);
717         return tag;
718 }
719
720 unsigned int mgmt_invalidate_connection(struct beiscsi_hba *phba,
721                                          struct beiscsi_endpoint *beiscsi_ep,
722                                          unsigned short cid,
723                                          unsigned short issue_reset,
724                                          unsigned short savecfg_flag)
725 {
726         struct be_ctrl_info *ctrl = &phba->ctrl;
727         struct be_mcc_wrb *wrb;
728         struct iscsi_invalidate_connection_params_in *req;
729         unsigned int tag = 0;
730
731         mutex_lock(&ctrl->mbox_lock);
732         wrb = alloc_mcc_wrb(phba, &tag);
733         if (!wrb) {
734                 mutex_unlock(&ctrl->mbox_lock);
735                 return 0;
736         }
737
738         req = embedded_payload(wrb);
739         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
740         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI_INI,
741                            OPCODE_ISCSI_INI_DRIVER_INVALIDATE_CONNECTION,
742                            sizeof(*req));
743         req->session_handle = beiscsi_ep->fw_handle;
744         req->cid = cid;
745         if (issue_reset)
746                 req->cleanup_type = CMD_ISCSI_CONNECTION_ISSUE_TCP_RST;
747         else
748                 req->cleanup_type = CMD_ISCSI_CONNECTION_INVALIDATE;
749         req->save_cfg = savecfg_flag;
750         be_mcc_notify(phba, tag);
751         mutex_unlock(&ctrl->mbox_lock);
752         return tag;
753 }
754
755 unsigned int mgmt_upload_connection(struct beiscsi_hba *phba,
756                                 unsigned short cid, unsigned int upload_flag)
757 {
758         struct be_ctrl_info *ctrl = &phba->ctrl;
759         struct be_mcc_wrb *wrb;
760         struct tcp_upload_params_in *req;
761         unsigned int tag;
762
763         mutex_lock(&ctrl->mbox_lock);
764         wrb = alloc_mcc_wrb(phba, &tag);
765         if (!wrb) {
766                 mutex_unlock(&ctrl->mbox_lock);
767                 return 0;
768         }
769
770         req = embedded_payload(wrb);
771         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
772         be_cmd_hdr_prepare(&req->hdr, CMD_COMMON_TCP_UPLOAD,
773                            OPCODE_COMMON_TCP_UPLOAD, sizeof(*req));
774         req->id = (unsigned short)cid;
775         req->upload_type = (unsigned char)upload_flag;
776         be_mcc_notify(phba, tag);
777         mutex_unlock(&ctrl->mbox_lock);
778         return tag;
779 }
780
781 /**
782  * mgmt_open_connection()- Establish a TCP CXN
783  * @dst_addr: Destination Address
784  * @beiscsi_ep: ptr to device endpoint struct
785  * @nonemb_cmd: ptr to memory allocated for command
786  *
787  * return
788  *      Success: Tag number of the MBX Command issued
789  *      Failure: Error code
790  **/
791 int mgmt_open_connection(struct beiscsi_hba *phba,
792                          struct sockaddr *dst_addr,
793                          struct beiscsi_endpoint *beiscsi_ep,
794                          struct be_dma_mem *nonemb_cmd)
795 {
796         struct hwi_controller *phwi_ctrlr;
797         struct hwi_context_memory *phwi_context;
798         struct sockaddr_in *daddr_in = (struct sockaddr_in *)dst_addr;
799         struct sockaddr_in6 *daddr_in6 = (struct sockaddr_in6 *)dst_addr;
800         struct be_ctrl_info *ctrl = &phba->ctrl;
801         struct be_mcc_wrb *wrb;
802         struct tcp_connect_and_offload_in_v1 *req;
803         unsigned short def_hdr_id;
804         unsigned short def_data_id;
805         struct phys_addr template_address = { 0, 0 };
806         struct phys_addr *ptemplate_address;
807         unsigned int tag = 0;
808         unsigned int i, ulp_num;
809         unsigned short cid = beiscsi_ep->ep_cid;
810         struct be_sge *sge;
811
812         if (dst_addr->sa_family != PF_INET && dst_addr->sa_family != PF_INET6) {
813                 beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_CONFIG,
814                             "BG_%d : unknown addr family %d\n",
815                             dst_addr->sa_family);
816                 return -EINVAL;
817         }
818
819         phwi_ctrlr = phba->phwi_ctrlr;
820         phwi_context = phwi_ctrlr->phwi_ctxt;
821
822         ulp_num = phwi_ctrlr->wrb_context[BE_GET_CRI_FROM_CID(cid)].ulp_num;
823
824         def_hdr_id = (unsigned short)HWI_GET_DEF_HDRQ_ID(phba, ulp_num);
825         def_data_id = (unsigned short)HWI_GET_DEF_BUFQ_ID(phba, ulp_num);
826
827         ptemplate_address = &template_address;
828         ISCSI_GET_PDU_TEMPLATE_ADDRESS(phba, ptemplate_address);
829         if (mutex_lock_interruptible(&ctrl->mbox_lock))
830                 return 0;
831         wrb = alloc_mcc_wrb(phba, &tag);
832         if (!wrb) {
833                 mutex_unlock(&ctrl->mbox_lock);
834                 return 0;
835         }
836
837         sge = nonembedded_sgl(wrb);
838         req = nonemb_cmd->va;
839         memset(req, 0, sizeof(*req));
840
841         be_wrb_hdr_prepare(wrb, nonemb_cmd->size, false, 1);
842         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI,
843                            OPCODE_COMMON_ISCSI_TCP_CONNECT_AND_OFFLOAD,
844                            nonemb_cmd->size);
845         if (dst_addr->sa_family == PF_INET) {
846                 __be32 s_addr = daddr_in->sin_addr.s_addr;
847                 req->ip_address.ip_type = BE2_IPV4;
848                 req->ip_address.addr[0] = s_addr & 0x000000ff;
849                 req->ip_address.addr[1] = (s_addr & 0x0000ff00) >> 8;
850                 req->ip_address.addr[2] = (s_addr & 0x00ff0000) >> 16;
851                 req->ip_address.addr[3] = (s_addr & 0xff000000) >> 24;
852                 req->tcp_port = ntohs(daddr_in->sin_port);
853                 beiscsi_ep->dst_addr = daddr_in->sin_addr.s_addr;
854                 beiscsi_ep->dst_tcpport = ntohs(daddr_in->sin_port);
855                 beiscsi_ep->ip_type = BE2_IPV4;
856         } else {
857                 /* else its PF_INET6 family */
858                 req->ip_address.ip_type = BE2_IPV6;
859                 memcpy(&req->ip_address.addr,
860                        &daddr_in6->sin6_addr.in6_u.u6_addr8, 16);
861                 req->tcp_port = ntohs(daddr_in6->sin6_port);
862                 beiscsi_ep->dst_tcpport = ntohs(daddr_in6->sin6_port);
863                 memcpy(&beiscsi_ep->dst6_addr,
864                        &daddr_in6->sin6_addr.in6_u.u6_addr8, 16);
865                 beiscsi_ep->ip_type = BE2_IPV6;
866         }
867         req->cid = cid;
868         i = phba->nxt_cqid++;
869         if (phba->nxt_cqid == phba->num_cpus)
870                 phba->nxt_cqid = 0;
871         req->cq_id = phwi_context->be_cq[i].id;
872         beiscsi_log(phba, KERN_INFO, BEISCSI_LOG_CONFIG,
873                     "BG_%d : i=%d cq_id=%d\n", i, req->cq_id);
874         req->defq_id = def_hdr_id;
875         req->hdr_ring_id = def_hdr_id;
876         req->data_ring_id = def_data_id;
877         req->do_offload = 1;
878         req->dataout_template_pa.lo = ptemplate_address->lo;
879         req->dataout_template_pa.hi = ptemplate_address->hi;
880         sge->pa_hi = cpu_to_le32(upper_32_bits(nonemb_cmd->dma));
881         sge->pa_lo = cpu_to_le32(nonemb_cmd->dma & 0xFFFFFFFF);
882         sge->len = cpu_to_le32(nonemb_cmd->size);
883
884         if (!is_chip_be2_be3r(phba)) {
885                 req->hdr.version = MBX_CMD_VER1;
886                 req->tcp_window_size = 0;
887                 req->tcp_window_scale_count = 2;
888         }
889
890         be_mcc_notify(phba, tag);
891         mutex_unlock(&ctrl->mbox_lock);
892         return tag;
893 }
894
895 /*
896  * mgmt_exec_nonemb_cmd()- Execute Non Embedded MBX Cmd
897  * @phba: Driver priv structure
898  * @nonemb_cmd: Address of the MBX command issued
899  * @resp_buf: Buffer to copy the MBX cmd response
900  * @resp_buf_len: respone lenght to be copied
901  *
902  **/
903 static int mgmt_exec_nonemb_cmd(struct beiscsi_hba *phba,
904                                 struct be_dma_mem *nonemb_cmd, void *resp_buf,
905                                 int resp_buf_len)
906 {
907         struct be_ctrl_info *ctrl = &phba->ctrl;
908         struct be_mcc_wrb *wrb;
909         struct be_sge *sge;
910         unsigned int tag;
911         int rc = 0;
912
913         mutex_lock(&ctrl->mbox_lock);
914         wrb = alloc_mcc_wrb(phba, &tag);
915         if (!wrb) {
916                 mutex_unlock(&ctrl->mbox_lock);
917                 rc = -ENOMEM;
918                 goto free_cmd;
919         }
920
921         sge = nonembedded_sgl(wrb);
922         be_wrb_hdr_prepare(wrb, nonemb_cmd->size, false, 1);
923         sge->pa_hi = cpu_to_le32(upper_32_bits(nonemb_cmd->dma));
924         sge->pa_lo = cpu_to_le32(lower_32_bits(nonemb_cmd->dma));
925         sge->len = cpu_to_le32(nonemb_cmd->size);
926
927         be_mcc_notify(phba, tag);
928         mutex_unlock(&ctrl->mbox_lock);
929
930         rc = beiscsi_mccq_compl_wait(phba, tag, NULL, nonemb_cmd);
931
932         if (resp_buf)
933                 memcpy(resp_buf, nonemb_cmd->va, resp_buf_len);
934
935         if (rc) {
936                 /* Check if the MBX Cmd needs to be re-issued */
937                 if (rc == -EAGAIN)
938                         return rc;
939
940                 beiscsi_log(phba, KERN_WARNING,
941                             BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX,
942                             "BG_%d : mgmt_exec_nonemb_cmd Failed status\n");
943
944                 if (rc != -EBUSY)
945                         goto free_cmd;
946                 else
947                         return rc;
948         }
949 free_cmd:
950         pci_free_consistent(ctrl->pdev, nonemb_cmd->size,
951                             nonemb_cmd->va, nonemb_cmd->dma);
952         return rc;
953 }
954
955 static int mgmt_alloc_cmd_data(struct beiscsi_hba *phba, struct be_dma_mem *cmd,
956                                int iscsi_cmd, int size)
957 {
958         cmd->va = pci_zalloc_consistent(phba->ctrl.pdev, size, &cmd->dma);
959         if (!cmd->va) {
960                 beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_CONFIG,
961                             "BG_%d : Failed to allocate memory for if info\n");
962                 return -ENOMEM;
963         }
964         cmd->size = size;
965         be_cmd_hdr_prepare(cmd->va, CMD_SUBSYSTEM_ISCSI, iscsi_cmd, size);
966         beiscsi_log(phba, KERN_INFO, BEISCSI_LOG_CONFIG,
967                     "BG_%d : subsystem iSCSI cmd %d size %d\n",
968                     iscsi_cmd, size);
969         return 0;
970 }
971
972 unsigned int beiscsi_if_get_handle(struct beiscsi_hba *phba)
973 {
974         struct be_ctrl_info *ctrl = &phba->ctrl;
975         struct be_mcc_wrb *wrb;
976         struct be_cmd_get_all_if_id_req *req;
977         struct be_cmd_get_all_if_id_req *pbe_allid;
978         unsigned int tag;
979         int status = 0;
980
981         if (mutex_lock_interruptible(&ctrl->mbox_lock))
982                 return -EINTR;
983         wrb = alloc_mcc_wrb(phba, &tag);
984         if (!wrb) {
985                 mutex_unlock(&ctrl->mbox_lock);
986                 return -ENOMEM;
987         }
988
989         req = embedded_payload(wrb);
990         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
991         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI,
992                            OPCODE_COMMON_ISCSI_NTWK_GET_ALL_IF_ID,
993                            sizeof(*req));
994         be_mcc_notify(phba, tag);
995         mutex_unlock(&ctrl->mbox_lock);
996
997         status = beiscsi_mccq_compl_wait(phba, tag, &wrb, NULL);
998         if (status) {
999                 beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
1000                             "BG_%d : %s failed: %d\n", __func__, status);
1001                 return -EBUSY;
1002         }
1003
1004         pbe_allid = embedded_payload(wrb);
1005         /* we now support only one interface per function */
1006         phba->interface_handle = pbe_allid->if_hndl_list[0];
1007
1008         return status;
1009 }
1010
1011 static int beiscsi_if_mod_gw(struct beiscsi_hba *phba,
1012                              u32 action, u32 ip_type, u8 *gw)
1013 {
1014         struct be_cmd_set_def_gateway_req *req;
1015         struct be_dma_mem nonemb_cmd;
1016         int rt_val;
1017
1018         rt_val = mgmt_alloc_cmd_data(phba, &nonemb_cmd,
1019                                 OPCODE_COMMON_ISCSI_NTWK_MODIFY_DEFAULT_GATEWAY,
1020                                 sizeof(*req));
1021         if (rt_val)
1022                 return rt_val;
1023
1024         req = nonemb_cmd.va;
1025         req->action = action;
1026         req->ip_addr.ip_type = ip_type;
1027         memcpy(req->ip_addr.addr, gw,
1028                (ip_type == BE2_IPV4) ? IP_V4_LEN : IP_V6_LEN);
1029         return mgmt_exec_nonemb_cmd(phba, &nonemb_cmd, NULL, 0);
1030 }
1031
1032 int beiscsi_if_set_gw(struct beiscsi_hba *phba, u32 ip_type, u8 *gw)
1033 {
1034         struct be_cmd_get_def_gateway_resp gw_resp;
1035         int rt_val;
1036
1037         memset(&gw_resp, 0, sizeof(gw_resp));
1038         rt_val = beiscsi_if_get_gw(phba, ip_type, &gw_resp);
1039         if (rt_val) {
1040                 beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
1041                             "BG_%d : Failed to Get Gateway Addr\n");
1042                 return rt_val;
1043         }
1044
1045         rt_val = beiscsi_if_mod_gw(phba, IP_ACTION_DEL, ip_type,
1046                                    gw_resp.ip_addr.addr);
1047         if (rt_val) {
1048                 beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
1049                                 "BG_%d : Failed to clear Gateway Addr Set\n");
1050                 return rt_val;
1051         }
1052
1053         rt_val = beiscsi_if_mod_gw(phba, IP_ACTION_ADD, ip_type, gw);
1054         if (rt_val)
1055                 beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
1056                             "BG_%d : Failed to Set Gateway Addr\n");
1057
1058         return rt_val;
1059 }
1060
1061 int beiscsi_if_get_gw(struct beiscsi_hba *phba, u32 ip_type,
1062                       struct be_cmd_get_def_gateway_resp *resp)
1063 {
1064         struct be_cmd_get_def_gateway_req *req;
1065         struct be_dma_mem nonemb_cmd;
1066         int rc;
1067
1068         rc = mgmt_alloc_cmd_data(phba, &nonemb_cmd,
1069                                  OPCODE_COMMON_ISCSI_NTWK_GET_DEFAULT_GATEWAY,
1070                                  sizeof(*resp));
1071         if (rc)
1072                 return rc;
1073
1074         req = nonemb_cmd.va;
1075         req->ip_type = ip_type;
1076
1077         return mgmt_exec_nonemb_cmd(phba, &nonemb_cmd, resp,
1078                                     sizeof(*resp));
1079 }
1080
1081 static int
1082 beiscsi_if_clr_ip(struct beiscsi_hba *phba,
1083                   struct be_cmd_get_if_info_resp *if_info)
1084 {
1085         struct be_cmd_set_ip_addr_req *req;
1086         struct be_dma_mem nonemb_cmd;
1087         int rc;
1088
1089         rc = mgmt_alloc_cmd_data(phba, &nonemb_cmd,
1090                                  OPCODE_COMMON_ISCSI_NTWK_MODIFY_IP_ADDR,
1091                                  sizeof(*req));
1092         if (rc)
1093                 return rc;
1094
1095         req = nonemb_cmd.va;
1096         req->ip_params.record_entry_count = 1;
1097         req->ip_params.ip_record.action = IP_ACTION_DEL;
1098         req->ip_params.ip_record.interface_hndl =
1099                 phba->interface_handle;
1100         req->ip_params.ip_record.ip_addr.size_of_structure =
1101                 sizeof(struct be_ip_addr_subnet_format);
1102         req->ip_params.ip_record.ip_addr.ip_type = if_info->ip_addr.ip_type;
1103         memcpy(req->ip_params.ip_record.ip_addr.addr,
1104                if_info->ip_addr.addr,
1105                sizeof(if_info->ip_addr.addr));
1106         memcpy(req->ip_params.ip_record.ip_addr.subnet_mask,
1107                if_info->ip_addr.subnet_mask,
1108                sizeof(if_info->ip_addr.subnet_mask));
1109         rc = mgmt_exec_nonemb_cmd(phba, &nonemb_cmd, NULL, 0);
1110         if (rc < 0 || req->ip_params.ip_record.status) {
1111                 beiscsi_log(phba, KERN_INFO, BEISCSI_LOG_CONFIG,
1112                             "BG_%d : failed to clear IP: rc %d status %d\n",
1113                             rc, req->ip_params.ip_record.status);
1114         }
1115         return rc;
1116 }
1117
1118 static int
1119 beiscsi_if_set_ip(struct beiscsi_hba *phba, u8 *ip,
1120                   u8 *subnet, u32 ip_type)
1121 {
1122         struct be_cmd_set_ip_addr_req *req;
1123         struct be_dma_mem nonemb_cmd;
1124         uint32_t ip_len;
1125         int rc;
1126
1127         rc = mgmt_alloc_cmd_data(phba, &nonemb_cmd,
1128                                  OPCODE_COMMON_ISCSI_NTWK_MODIFY_IP_ADDR,
1129                                  sizeof(*req));
1130         if (rc)
1131                 return rc;
1132
1133         req = nonemb_cmd.va;
1134         req->ip_params.record_entry_count = 1;
1135         req->ip_params.ip_record.action = IP_ACTION_ADD;
1136         req->ip_params.ip_record.interface_hndl =
1137                 phba->interface_handle;
1138         req->ip_params.ip_record.ip_addr.size_of_structure =
1139                 sizeof(struct be_ip_addr_subnet_format);
1140         req->ip_params.ip_record.ip_addr.ip_type = ip_type;
1141         ip_len = ip_type == BE2_IPV4 ? IP_V4_LEN : IP_V6_LEN;
1142         memcpy(req->ip_params.ip_record.ip_addr.addr, ip, ip_len);
1143         if (subnet)
1144                 memcpy(req->ip_params.ip_record.ip_addr.subnet_mask,
1145                        subnet, ip_len);
1146
1147         rc = mgmt_exec_nonemb_cmd(phba, &nonemb_cmd, NULL, 0);
1148         /**
1149          * In some cases, host needs to look into individual record status
1150          * even though FW reported success for that IOCTL.
1151          */
1152         if (rc < 0 || req->ip_params.ip_record.status) {
1153                 __beiscsi_log(phba, KERN_ERR,
1154                             "BG_%d : failed to set IP: rc %d status %d\n",
1155                             rc, req->ip_params.ip_record.status);
1156                 if (req->ip_params.ip_record.status)
1157                         rc = -EINVAL;
1158         }
1159         return rc;
1160 }
1161
1162 int beiscsi_if_en_static(struct beiscsi_hba *phba, u32 ip_type,
1163                          u8 *ip, u8 *subnet)
1164 {
1165         struct be_cmd_get_if_info_resp *if_info;
1166         struct be_cmd_rel_dhcp_req *reldhcp;
1167         struct be_dma_mem nonemb_cmd;
1168         int rc;
1169
1170         rc = beiscsi_if_get_info(phba, ip_type, &if_info);
1171         if (rc)
1172                 return rc;
1173
1174         if (if_info->dhcp_state) {
1175                 rc = mgmt_alloc_cmd_data(phba, &nonemb_cmd,
1176                                 OPCODE_COMMON_ISCSI_NTWK_REL_STATELESS_IP_ADDR,
1177                                 sizeof(*reldhcp));
1178                 if (rc)
1179                         goto exit;
1180
1181                 reldhcp = nonemb_cmd.va;
1182                 reldhcp->interface_hndl = phba->interface_handle;
1183                 reldhcp->ip_type = ip_type;
1184                 rc = mgmt_exec_nonemb_cmd(phba, &nonemb_cmd, NULL, 0);
1185                 if (rc < 0) {
1186                         beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
1187                                     "BG_%d : failed to release existing DHCP: %d\n",
1188                                     rc);
1189                         goto exit;
1190                 }
1191         }
1192
1193         /* first delete any old IP set */
1194         rc = beiscsi_if_clr_ip(phba, if_info);
1195         if (rc)
1196                 goto exit;
1197
1198         /* if ip == NULL then this is called just to release DHCP IP */
1199         if (ip)
1200                 rc = beiscsi_if_set_ip(phba, ip, subnet, ip_type);
1201 exit:
1202         kfree(if_info);
1203         return rc;
1204 }
1205
1206 int beiscsi_if_en_dhcp(struct beiscsi_hba *phba, u32 ip_type)
1207 {
1208         struct be_cmd_get_def_gateway_resp gw_resp;
1209         struct be_cmd_get_if_info_resp *if_info;
1210         struct be_cmd_set_dhcp_req *dhcpreq;
1211         struct be_dma_mem nonemb_cmd;
1212         u8 *gw;
1213         int rc;
1214
1215         rc = beiscsi_if_get_info(phba, ip_type, &if_info);
1216         if (rc)
1217                 return rc;
1218
1219         if (if_info->dhcp_state) {
1220                 beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
1221                                 "BG_%d : DHCP Already Enabled\n");
1222                 goto exit;
1223         }
1224
1225         /* first delete any old static IP set */
1226         rc = beiscsi_if_clr_ip(phba, if_info);
1227         if (rc)
1228                 goto exit;
1229
1230         /* delete gateway settings if mode change is to DHCP */
1231         memset(&gw_resp, 0, sizeof(gw_resp));
1232         /* use ip_type provided in if_info */
1233         rc = beiscsi_if_get_gw(phba, if_info->ip_addr.ip_type, &gw_resp);
1234         if (rc) {
1235                 beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
1236                             "BG_%d : Failed to Get Gateway Addr\n");
1237                 goto exit;
1238         }
1239         gw = (u8 *)&gw_resp.ip_addr.addr;
1240         rc = beiscsi_if_mod_gw(phba, IP_ACTION_DEL,
1241                                if_info->ip_addr.ip_type, gw);
1242         if (rc) {
1243                 beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
1244                                 "BG_%d : Failed to clear Gateway Addr Set\n");
1245                 goto exit;
1246         }
1247
1248         rc = mgmt_alloc_cmd_data(phba, &nonemb_cmd,
1249                         OPCODE_COMMON_ISCSI_NTWK_CONFIG_STATELESS_IP_ADDR,
1250                         sizeof(*dhcpreq));
1251         if (rc)
1252                 goto exit;
1253
1254         dhcpreq = nonemb_cmd.va;
1255         dhcpreq->flags = BLOCKING;
1256         dhcpreq->retry_count = 1;
1257         dhcpreq->interface_hndl = phba->interface_handle;
1258         dhcpreq->ip_type = ip_type;
1259         rc = mgmt_exec_nonemb_cmd(phba, &nonemb_cmd, NULL, 0);
1260
1261 exit:
1262         kfree(if_info);
1263         return rc;
1264 }
1265
1266 /**
1267  * beiscsi_if_set_vlan()- Issue and wait for CMD completion
1268  * @phba: device private structure instance
1269  * @vlan_tag: VLAN tag
1270  *
1271  * Issue the MBX Cmd and wait for the completion of the
1272  * command.
1273  *
1274  * returns
1275  *      Success: 0
1276  *      Failure: Non-Xero Value
1277  **/
1278 int beiscsi_if_set_vlan(struct beiscsi_hba *phba, uint16_t vlan_tag)
1279 {
1280         int rc;
1281         unsigned int tag;
1282
1283         tag = be_cmd_set_vlan(phba, vlan_tag);
1284         if (!tag) {
1285                 beiscsi_log(phba, KERN_ERR,
1286                             (BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX),
1287                             "BG_%d : VLAN Setting Failed\n");
1288                 return -EBUSY;
1289         }
1290
1291         rc = beiscsi_mccq_compl_wait(phba, tag, NULL, NULL);
1292         if (rc) {
1293                 beiscsi_log(phba, KERN_ERR,
1294                             (BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX),
1295                             "BS_%d : VLAN MBX Cmd Failed\n");
1296                 return rc;
1297         }
1298         return rc;
1299 }
1300
1301
1302 int beiscsi_if_get_info(struct beiscsi_hba *phba, int ip_type,
1303                         struct be_cmd_get_if_info_resp **if_info)
1304 {
1305         struct be_cmd_get_if_info_req *req;
1306         struct be_dma_mem nonemb_cmd;
1307         uint32_t ioctl_size = sizeof(struct be_cmd_get_if_info_resp);
1308         int rc;
1309
1310         rc = beiscsi_if_get_handle(phba);
1311         if (rc)
1312                 return rc;
1313
1314         do {
1315                 rc = mgmt_alloc_cmd_data(phba, &nonemb_cmd,
1316                                          OPCODE_COMMON_ISCSI_NTWK_GET_IF_INFO,
1317                                          ioctl_size);
1318                 if (rc)
1319                         return rc;
1320
1321                 req = nonemb_cmd.va;
1322                 req->interface_hndl = phba->interface_handle;
1323                 req->ip_type = ip_type;
1324
1325                 /* Allocate memory for if_info */
1326                 *if_info = kzalloc(ioctl_size, GFP_KERNEL);
1327                 if (!*if_info) {
1328                         beiscsi_log(phba, KERN_ERR,
1329                                     BEISCSI_LOG_INIT | BEISCSI_LOG_CONFIG,
1330                                     "BG_%d : Memory Allocation Failure\n");
1331
1332                                 /* Free the DMA memory for the IOCTL issuing */
1333                                 pci_free_consistent(phba->ctrl.pdev,
1334                                                     nonemb_cmd.size,
1335                                                     nonemb_cmd.va,
1336                                                     nonemb_cmd.dma);
1337                                 return -ENOMEM;
1338                 }
1339
1340                 rc =  mgmt_exec_nonemb_cmd(phba, &nonemb_cmd, *if_info,
1341                                            ioctl_size);
1342
1343                 /* Check if the error is because of Insufficent_Buffer */
1344                 if (rc == -EAGAIN) {
1345
1346                         /* Get the new memory size */
1347                         ioctl_size = ((struct be_cmd_resp_hdr *)
1348                                       nonemb_cmd.va)->actual_resp_len;
1349                         ioctl_size += sizeof(struct be_cmd_req_hdr);
1350
1351                         /* Free the previous allocated DMA memory */
1352                         pci_free_consistent(phba->ctrl.pdev, nonemb_cmd.size,
1353                                             nonemb_cmd.va,
1354                                             nonemb_cmd.dma);
1355
1356                         /* Free the virtual memory */
1357                         kfree(*if_info);
1358                 } else
1359                         break;
1360         } while (true);
1361         return rc;
1362 }
1363
1364 int mgmt_get_nic_conf(struct beiscsi_hba *phba,
1365                       struct be_cmd_get_nic_conf_resp *nic)
1366 {
1367         struct be_dma_mem nonemb_cmd;
1368         int rc;
1369
1370         rc = mgmt_alloc_cmd_data(phba, &nonemb_cmd,
1371                                  OPCODE_COMMON_ISCSI_NTWK_GET_NIC_CONFIG,
1372                                  sizeof(*nic));
1373         if (rc)
1374                 return rc;
1375
1376         return mgmt_exec_nonemb_cmd(phba, &nonemb_cmd, nic, sizeof(*nic));
1377 }
1378
1379
1380
1381 unsigned int be_cmd_get_initname(struct beiscsi_hba *phba)
1382 {
1383         unsigned int tag;
1384         struct be_mcc_wrb *wrb;
1385         struct be_cmd_hba_name *req;
1386         struct be_ctrl_info *ctrl = &phba->ctrl;
1387
1388         if (mutex_lock_interruptible(&ctrl->mbox_lock))
1389                 return 0;
1390         wrb = alloc_mcc_wrb(phba, &tag);
1391         if (!wrb) {
1392                 mutex_unlock(&ctrl->mbox_lock);
1393                 return 0;
1394         }
1395
1396         req = embedded_payload(wrb);
1397         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
1398         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI_INI,
1399                         OPCODE_ISCSI_INI_CFG_GET_HBA_NAME,
1400                         sizeof(*req));
1401
1402         be_mcc_notify(phba, tag);
1403         mutex_unlock(&ctrl->mbox_lock);
1404         return tag;
1405 }
1406
1407 /**
1408  * be_mgmt_get_boot_shandle()- Get the session handle
1409  * @phba: device priv structure instance
1410  * @s_handle: session handle returned for boot session.
1411  *
1412  * Get the boot target session handle. In case of
1413  * crashdump mode driver has to issue and MBX Cmd
1414  * for FW to login to boot target
1415  *
1416  * return
1417  *      Success: 0
1418  *      Failure: Non-Zero value
1419  *
1420  **/
1421 int be_mgmt_get_boot_shandle(struct beiscsi_hba *phba,
1422                               unsigned int *s_handle)
1423 {
1424         struct be_cmd_get_boot_target_resp *boot_resp;
1425         struct be_mcc_wrb *wrb;
1426         unsigned int tag;
1427         uint8_t boot_retry = 3;
1428         int rc;
1429
1430         do {
1431                 /* Get the Boot Target Session Handle and Count*/
1432                 tag = mgmt_get_boot_target(phba);
1433                 if (!tag) {
1434                         beiscsi_log(phba, KERN_ERR,
1435                                     BEISCSI_LOG_CONFIG | BEISCSI_LOG_INIT,
1436                                     "BG_%d : Getting Boot Target Info Failed\n");
1437                         return -EAGAIN;
1438                 }
1439
1440                 rc = beiscsi_mccq_compl_wait(phba, tag, &wrb, NULL);
1441                 if (rc) {
1442                         beiscsi_log(phba, KERN_ERR,
1443                                     BEISCSI_LOG_INIT | BEISCSI_LOG_CONFIG,
1444                                     "BG_%d : MBX CMD get_boot_target Failed\n");
1445                         return -EBUSY;
1446                 }
1447
1448                 boot_resp = embedded_payload(wrb);
1449
1450                 /* Check if the there are any Boot targets configured */
1451                 if (!boot_resp->boot_session_count) {
1452                         beiscsi_log(phba, KERN_INFO,
1453                                     BEISCSI_LOG_INIT | BEISCSI_LOG_CONFIG,
1454                                     "BG_%d  ;No boot targets configured\n");
1455                         return -ENXIO;
1456                 }
1457
1458                 /* FW returns the session handle of the boot session */
1459                 if (boot_resp->boot_session_handle != INVALID_SESS_HANDLE) {
1460                         *s_handle = boot_resp->boot_session_handle;
1461                         return 0;
1462                 }
1463
1464                 /* Issue MBX Cmd to FW to login to the boot target */
1465                 tag = mgmt_reopen_session(phba, BE_REOPEN_BOOT_SESSIONS,
1466                                           INVALID_SESS_HANDLE);
1467                 if (!tag) {
1468                         beiscsi_log(phba, KERN_ERR,
1469                                     BEISCSI_LOG_INIT | BEISCSI_LOG_CONFIG,
1470                                     "BG_%d : mgmt_reopen_session Failed\n");
1471                         return -EAGAIN;
1472                 }
1473
1474                 rc = beiscsi_mccq_compl_wait(phba, tag, NULL, NULL);
1475                 if (rc) {
1476                         beiscsi_log(phba, KERN_ERR,
1477                                     BEISCSI_LOG_INIT | BEISCSI_LOG_CONFIG,
1478                                     "BG_%d : mgmt_reopen_session Failed");
1479                         return rc;
1480                 }
1481         } while (--boot_retry);
1482
1483         /* Couldn't log into the boot target */
1484         beiscsi_log(phba, KERN_ERR,
1485                     BEISCSI_LOG_INIT | BEISCSI_LOG_CONFIG,
1486                     "BG_%d : Login to Boot Target Failed\n");
1487         return -ENXIO;
1488 }
1489
1490 /**
1491  * beiscsi_drvr_ver_disp()- Display the driver Name and Version
1492  * @dev: ptr to device not used.
1493  * @attr: device attribute, not used.
1494  * @buf: contains formatted text driver name and version
1495  *
1496  * return
1497  * size of the formatted string
1498  **/
1499 ssize_t
1500 beiscsi_drvr_ver_disp(struct device *dev, struct device_attribute *attr,
1501                        char *buf)
1502 {
1503         return snprintf(buf, PAGE_SIZE, BE_NAME "\n");
1504 }
1505
1506 /**
1507  * beiscsi_fw_ver_disp()- Display Firmware Version
1508  * @dev: ptr to device not used.
1509  * @attr: device attribute, not used.
1510  * @buf: contains formatted text Firmware version
1511  *
1512  * return
1513  * size of the formatted string
1514  **/
1515 ssize_t
1516 beiscsi_fw_ver_disp(struct device *dev, struct device_attribute *attr,
1517                      char *buf)
1518 {
1519         struct Scsi_Host *shost = class_to_shost(dev);
1520         struct beiscsi_hba *phba = iscsi_host_priv(shost);
1521
1522         return snprintf(buf, PAGE_SIZE, "%s\n", phba->fw_ver_str);
1523 }
1524
1525 /**
1526  * beiscsi_active_session_disp()- Display Sessions Active
1527  * @dev: ptr to device not used.
1528  * @attr: device attribute, not used.
1529  * @buf: contains formatted text Session Count
1530  *
1531  * return
1532  * size of the formatted string
1533  **/
1534 ssize_t
1535 beiscsi_active_session_disp(struct device *dev, struct device_attribute *attr,
1536                          char *buf)
1537 {
1538         struct Scsi_Host *shost = class_to_shost(dev);
1539         struct beiscsi_hba *phba = iscsi_host_priv(shost);
1540         uint16_t avlbl_cids = 0, ulp_num, len = 0, total_cids = 0;
1541
1542         for (ulp_num = 0; ulp_num < BEISCSI_ULP_COUNT; ulp_num++) {
1543                 if (test_bit(ulp_num, (void *)&phba->fw_config.ulp_supported)) {
1544                         avlbl_cids = BEISCSI_ULP_AVLBL_CID(phba, ulp_num);
1545                         total_cids = BEISCSI_GET_CID_COUNT(phba, ulp_num);
1546                         len += snprintf(buf+len, PAGE_SIZE - len,
1547                                         "ULP%d : %d\n", ulp_num,
1548                                         (total_cids - avlbl_cids));
1549                 } else
1550                         len += snprintf(buf+len, PAGE_SIZE - len,
1551                                         "ULP%d : %d\n", ulp_num, 0);
1552         }
1553
1554         return len;
1555 }
1556
1557 /**
1558  * beiscsi_free_session_disp()- Display Avaliable Session
1559  * @dev: ptr to device not used.
1560  * @attr: device attribute, not used.
1561  * @buf: contains formatted text Session Count
1562  *
1563  * return
1564  * size of the formatted string
1565  **/
1566 ssize_t
1567 beiscsi_free_session_disp(struct device *dev, struct device_attribute *attr,
1568                        char *buf)
1569 {
1570         struct Scsi_Host *shost = class_to_shost(dev);
1571         struct beiscsi_hba *phba = iscsi_host_priv(shost);
1572         uint16_t ulp_num, len = 0;
1573
1574         for (ulp_num = 0; ulp_num < BEISCSI_ULP_COUNT; ulp_num++) {
1575                 if (test_bit(ulp_num, (void *)&phba->fw_config.ulp_supported))
1576                         len += snprintf(buf+len, PAGE_SIZE - len,
1577                                         "ULP%d : %d\n", ulp_num,
1578                                         BEISCSI_ULP_AVLBL_CID(phba, ulp_num));
1579                 else
1580                         len += snprintf(buf+len, PAGE_SIZE - len,
1581                                         "ULP%d : %d\n", ulp_num, 0);
1582         }
1583
1584         return len;
1585 }
1586
1587 /**
1588  * beiscsi_adap_family_disp()- Display adapter family.
1589  * @dev: ptr to device to get priv structure
1590  * @attr: device attribute, not used.
1591  * @buf: contains formatted text driver name and version
1592  *
1593  * return
1594  * size of the formatted string
1595  **/
1596 ssize_t
1597 beiscsi_adap_family_disp(struct device *dev, struct device_attribute *attr,
1598                           char *buf)
1599 {
1600         uint16_t dev_id = 0;
1601         struct Scsi_Host *shost = class_to_shost(dev);
1602         struct beiscsi_hba *phba = iscsi_host_priv(shost);
1603
1604         dev_id = phba->pcidev->device;
1605         switch (dev_id) {
1606         case BE_DEVICE_ID1:
1607         case OC_DEVICE_ID1:
1608         case OC_DEVICE_ID2:
1609                 return snprintf(buf, PAGE_SIZE, "BE2 Adapter Family\n");
1610                 break;
1611         case BE_DEVICE_ID2:
1612         case OC_DEVICE_ID3:
1613                 return snprintf(buf, PAGE_SIZE, "BE3-R Adapter Family\n");
1614                 break;
1615         case OC_SKH_ID1:
1616                 return snprintf(buf, PAGE_SIZE, "Skyhawk-R Adapter Family\n");
1617                 break;
1618         default:
1619                 return snprintf(buf, PAGE_SIZE,
1620                                 "Unknown Adapter Family: 0x%x\n", dev_id);
1621                 break;
1622         }
1623 }
1624
1625 /**
1626  * beiscsi_phys_port()- Display Physical Port Identifier
1627  * @dev: ptr to device not used.
1628  * @attr: device attribute, not used.
1629  * @buf: contains formatted text port identifier
1630  *
1631  * return
1632  * size of the formatted string
1633  **/
1634 ssize_t
1635 beiscsi_phys_port_disp(struct device *dev, struct device_attribute *attr,
1636                          char *buf)
1637 {
1638         struct Scsi_Host *shost = class_to_shost(dev);
1639         struct beiscsi_hba *phba = iscsi_host_priv(shost);
1640
1641         return snprintf(buf, PAGE_SIZE, "Port Identifier : %d\n",
1642                         phba->fw_config.phys_port);
1643 }
1644
1645 void beiscsi_offload_cxn_v0(struct beiscsi_offload_params *params,
1646                              struct wrb_handle *pwrb_handle,
1647                              struct be_mem_descriptor *mem_descr,
1648                              struct hwi_wrb_context *pwrb_context)
1649 {
1650         struct iscsi_wrb *pwrb = pwrb_handle->pwrb;
1651
1652         memset(pwrb, 0, sizeof(*pwrb));
1653         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb,
1654                       max_send_data_segment_length, pwrb,
1655                       params->dw[offsetof(struct amap_beiscsi_offload_params,
1656                       max_send_data_segment_length) / 32]);
1657         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, type, pwrb,
1658                       BE_TGT_CTX_UPDT_CMD);
1659         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb,
1660                       first_burst_length,
1661                       pwrb,
1662                       params->dw[offsetof(struct amap_beiscsi_offload_params,
1663                       first_burst_length) / 32]);
1664         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, erl, pwrb,
1665                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1666                       erl) / 32] & OFFLD_PARAMS_ERL));
1667         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, dde, pwrb,
1668                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1669                        dde) / 32] & OFFLD_PARAMS_DDE) >> 2);
1670         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, hde, pwrb,
1671                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1672                       hde) / 32] & OFFLD_PARAMS_HDE) >> 3);
1673         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, ir2t, pwrb,
1674                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1675                       ir2t) / 32] & OFFLD_PARAMS_IR2T) >> 4);
1676         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, imd, pwrb,
1677                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1678                       imd) / 32] & OFFLD_PARAMS_IMD) >> 5);
1679         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, stat_sn,
1680                       pwrb,
1681                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1682                       exp_statsn) / 32] + 1));
1683         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, wrb_idx,
1684                       pwrb, pwrb_handle->wrb_index);
1685
1686         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb,
1687                       max_burst_length, pwrb, params->dw[offsetof
1688                       (struct amap_beiscsi_offload_params,
1689                       max_burst_length) / 32]);
1690
1691         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, ptr2nextwrb,
1692                       pwrb, pwrb_handle->wrb_index);
1693         if (pwrb_context->plast_wrb)
1694                 AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb,
1695                               ptr2nextwrb,
1696                               pwrb_context->plast_wrb,
1697                               pwrb_handle->wrb_index);
1698         pwrb_context->plast_wrb = pwrb;
1699
1700         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb,
1701                       session_state, pwrb, 0);
1702         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, compltonack,
1703                       pwrb, 1);
1704         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, notpredblq,
1705                       pwrb, 0);
1706         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, mode, pwrb,
1707                       0);
1708
1709         mem_descr += ISCSI_MEM_GLOBAL_HEADER;
1710         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb,
1711                       pad_buffer_addr_hi, pwrb,
1712                       mem_descr->mem_array[0].bus_address.u.a32.address_hi);
1713         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb,
1714                       pad_buffer_addr_lo, pwrb,
1715                       mem_descr->mem_array[0].bus_address.u.a32.address_lo);
1716 }
1717
1718 void beiscsi_offload_cxn_v2(struct beiscsi_offload_params *params,
1719                              struct wrb_handle *pwrb_handle,
1720                              struct hwi_wrb_context *pwrb_context)
1721 {
1722         struct iscsi_wrb *pwrb = pwrb_handle->pwrb;
1723
1724         memset(pwrb, 0, sizeof(*pwrb));
1725
1726         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1727                       max_burst_length, pwrb, params->dw[offsetof
1728                       (struct amap_beiscsi_offload_params,
1729                       max_burst_length) / 32]);
1730         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1731                       type, pwrb,
1732                       BE_TGT_CTX_UPDT_CMD);
1733         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1734                       ptr2nextwrb,
1735                       pwrb, pwrb_handle->wrb_index);
1736         if (pwrb_context->plast_wrb)
1737                 AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1738                               ptr2nextwrb,
1739                               pwrb_context->plast_wrb,
1740                               pwrb_handle->wrb_index);
1741         pwrb_context->plast_wrb = pwrb;
1742
1743         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2, wrb_idx,
1744                       pwrb, pwrb_handle->wrb_index);
1745         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1746                       max_send_data_segment_length, pwrb,
1747                       params->dw[offsetof(struct amap_beiscsi_offload_params,
1748                       max_send_data_segment_length) / 32]);
1749         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1750                       first_burst_length, pwrb,
1751                       params->dw[offsetof(struct amap_beiscsi_offload_params,
1752                       first_burst_length) / 32]);
1753         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1754                       max_recv_dataseg_len, pwrb,
1755                       params->dw[offsetof(struct amap_beiscsi_offload_params,
1756                       max_recv_data_segment_length) / 32]);
1757         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1758                       max_cxns, pwrb, BEISCSI_MAX_CXNS);
1759         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2, erl, pwrb,
1760                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1761                       erl) / 32] & OFFLD_PARAMS_ERL));
1762         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2, dde, pwrb,
1763                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1764                       dde) / 32] & OFFLD_PARAMS_DDE) >> 2);
1765         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2, hde, pwrb,
1766                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1767                       hde) / 32] & OFFLD_PARAMS_HDE) >> 3);
1768         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1769                       ir2t, pwrb,
1770                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1771                       ir2t) / 32] & OFFLD_PARAMS_IR2T) >> 4);
1772         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2, imd, pwrb,
1773                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1774                       imd) / 32] & OFFLD_PARAMS_IMD) >> 5);
1775         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1776                       data_seq_inorder,
1777                       pwrb,
1778                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1779                       data_seq_inorder) / 32] &
1780                       OFFLD_PARAMS_DATA_SEQ_INORDER) >> 6);
1781         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1782                       pdu_seq_inorder,
1783                       pwrb,
1784                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1785                       pdu_seq_inorder) / 32] &
1786                       OFFLD_PARAMS_PDU_SEQ_INORDER) >> 7);
1787         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2, max_r2t,
1788                       pwrb,
1789                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1790                       max_r2t) / 32] &
1791                       OFFLD_PARAMS_MAX_R2T) >> 8);
1792         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2, stat_sn,
1793                       pwrb,
1794                      (params->dw[offsetof(struct amap_beiscsi_offload_params,
1795                       exp_statsn) / 32] + 1));
1796 }
1797
1798 /**
1799  * beiscsi_logout_fw_sess()- Firmware Session Logout
1800  * @phba: Device priv structure instance
1801  * @fw_sess_handle: FW session handle
1802  *
1803  * Logout from the FW established sessions.
1804  * returns
1805  *  Success: 0
1806  *  Failure: Non-Zero Value
1807  *
1808  */
1809 int beiscsi_logout_fw_sess(struct beiscsi_hba *phba,
1810                 uint32_t fw_sess_handle)
1811 {
1812         struct be_ctrl_info *ctrl = &phba->ctrl;
1813         struct be_mcc_wrb *wrb;
1814         struct be_cmd_req_logout_fw_sess *req;
1815         struct be_cmd_resp_logout_fw_sess *resp;
1816         unsigned int tag;
1817         int rc;
1818
1819         beiscsi_log(phba, KERN_INFO,
1820                     BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX,
1821                     "BG_%d : In bescsi_logout_fwboot_sess\n");
1822
1823         mutex_lock(&ctrl->mbox_lock);
1824         wrb = alloc_mcc_wrb(phba, &tag);
1825         if (!wrb) {
1826                 mutex_unlock(&ctrl->mbox_lock);
1827                 beiscsi_log(phba, KERN_INFO,
1828                             BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX,
1829                             "BG_%d : MBX Tag Failure\n");
1830                 return -EINVAL;
1831         }
1832
1833         req = embedded_payload(wrb);
1834         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
1835         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI_INI,
1836                            OPCODE_ISCSI_INI_SESSION_LOGOUT_TARGET,
1837                            sizeof(struct be_cmd_req_logout_fw_sess));
1838
1839         /* Set the session handle */
1840         req->session_handle = fw_sess_handle;
1841         be_mcc_notify(phba, tag);
1842         mutex_unlock(&ctrl->mbox_lock);
1843
1844         rc = beiscsi_mccq_compl_wait(phba, tag, &wrb, NULL);
1845         if (rc) {
1846                 beiscsi_log(phba, KERN_ERR,
1847                             BEISCSI_LOG_INIT | BEISCSI_LOG_CONFIG,
1848                             "BG_%d : MBX CMD FW_SESSION_LOGOUT_TARGET Failed\n");
1849                 return -EBUSY;
1850         }
1851
1852         resp = embedded_payload(wrb);
1853         if (resp->session_status !=
1854                 BEISCSI_MGMT_SESSION_CLOSE) {
1855                 beiscsi_log(phba, KERN_ERR,
1856                             BEISCSI_LOG_INIT | BEISCSI_LOG_CONFIG,
1857                             "BG_%d : FW_SESSION_LOGOUT_TARGET resp : 0x%x\n",
1858                             resp->session_status);
1859                 rc = -EINVAL;
1860         }
1861
1862         return rc;
1863 }