Merge remote-tracking branches 'asoc/fix/rt5663', 'asoc/fix/samsung', 'asoc/fix/sti...
[sfrench/cifs-2.6.git] / drivers / scsi / be2iscsi / be_mgmt.c
1 /**
2  * Copyright (C) 2005 - 2016 Broadcom
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@broadcom.com)
11  *
12  * Contact Information:
13  * linux-drivers@broadcom.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 int beiscsi_modify_eq_delay(struct beiscsi_hba *phba,
28                             struct be_set_eqd *set_eqd,
29                             int num)
30 {
31         struct be_ctrl_info *ctrl = &phba->ctrl;
32         struct be_mcc_wrb *wrb;
33         struct be_cmd_req_modify_eq_delay *req;
34         unsigned int tag;
35         int i;
36
37         mutex_lock(&ctrl->mbox_lock);
38         wrb = alloc_mcc_wrb(phba, &tag);
39         if (!wrb) {
40                 mutex_unlock(&ctrl->mbox_lock);
41                 return 0;
42         }
43
44         req = embedded_payload(wrb);
45         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
46         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_COMMON,
47                            OPCODE_COMMON_MODIFY_EQ_DELAY, sizeof(*req));
48
49         req->num_eq = cpu_to_le32(num);
50         for (i = 0; i < num; i++) {
51                 req->delay[i].eq_id = cpu_to_le32(set_eqd[i].eq_id);
52                 req->delay[i].phase = 0;
53                 req->delay[i].delay_multiplier =
54                                 cpu_to_le32(set_eqd[i].delay_multiplier);
55         }
56
57         /* ignore the completion of this mbox command */
58         set_bit(MCC_TAG_STATE_IGNORE, &ctrl->ptag_state[tag].tag_state);
59         be_mcc_notify(phba, tag);
60         mutex_unlock(&ctrl->mbox_lock);
61         return tag;
62 }
63
64 unsigned int mgmt_vendor_specific_fw_cmd(struct be_ctrl_info *ctrl,
65                                          struct beiscsi_hba *phba,
66                                          struct bsg_job *job,
67                                          struct be_dma_mem *nonemb_cmd)
68 {
69         struct be_cmd_resp_hdr *resp;
70         struct be_mcc_wrb *wrb;
71         struct be_sge *mcc_sge;
72         unsigned int tag = 0;
73         struct iscsi_bsg_request *bsg_req = job->request;
74         struct be_bsg_vendor_cmd *req = nonemb_cmd->va;
75         unsigned short region, sector_size, sector, offset;
76
77         nonemb_cmd->size = job->request_payload.payload_len;
78         memset(nonemb_cmd->va, 0, nonemb_cmd->size);
79         resp = nonemb_cmd->va;
80         region =  bsg_req->rqst_data.h_vendor.vendor_cmd[1];
81         sector_size =  bsg_req->rqst_data.h_vendor.vendor_cmd[2];
82         sector =  bsg_req->rqst_data.h_vendor.vendor_cmd[3];
83         offset =  bsg_req->rqst_data.h_vendor.vendor_cmd[4];
84         req->region = region;
85         req->sector = sector;
86         req->offset = offset;
87
88         if (mutex_lock_interruptible(&ctrl->mbox_lock))
89                 return 0;
90         switch (bsg_req->rqst_data.h_vendor.vendor_cmd[0]) {
91         case BEISCSI_WRITE_FLASH:
92                 offset = sector * sector_size + offset;
93                 be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI,
94                                    OPCODE_COMMON_WRITE_FLASH, sizeof(*req));
95                 sg_copy_to_buffer(job->request_payload.sg_list,
96                                   job->request_payload.sg_cnt,
97                                   nonemb_cmd->va + offset, job->request_len);
98                 break;
99         case BEISCSI_READ_FLASH:
100                 be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI,
101                            OPCODE_COMMON_READ_FLASH, sizeof(*req));
102                 break;
103         default:
104                 beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
105                             "BG_%d : Unsupported cmd = 0x%x\n\n",
106                             bsg_req->rqst_data.h_vendor.vendor_cmd[0]);
107
108                 mutex_unlock(&ctrl->mbox_lock);
109                 return -EPERM;
110         }
111
112         wrb = alloc_mcc_wrb(phba, &tag);
113         if (!wrb) {
114                 mutex_unlock(&ctrl->mbox_lock);
115                 return 0;
116         }
117
118         mcc_sge = nonembedded_sgl(wrb);
119         be_wrb_hdr_prepare(wrb, nonemb_cmd->size, false,
120                            job->request_payload.sg_cnt);
121         mcc_sge->pa_hi = cpu_to_le32(upper_32_bits(nonemb_cmd->dma));
122         mcc_sge->pa_lo = cpu_to_le32(nonemb_cmd->dma & 0xFFFFFFFF);
123         mcc_sge->len = cpu_to_le32(nonemb_cmd->size);
124
125         be_mcc_notify(phba, tag);
126
127         mutex_unlock(&ctrl->mbox_lock);
128         return tag;
129 }
130
131 unsigned int  mgmt_invalidate_icds(struct beiscsi_hba *phba,
132                                 struct invalidate_command_table *inv_tbl,
133                                 unsigned int num_invalidate, unsigned int cid,
134                                 struct be_dma_mem *nonemb_cmd)
135
136 {
137         struct be_ctrl_info *ctrl = &phba->ctrl;
138         struct be_mcc_wrb *wrb;
139         struct be_sge *sge;
140         struct invalidate_commands_params_in *req;
141         unsigned int i, tag;
142
143         mutex_lock(&ctrl->mbox_lock);
144         wrb = alloc_mcc_wrb(phba, &tag);
145         if (!wrb) {
146                 mutex_unlock(&ctrl->mbox_lock);
147                 return 0;
148         }
149
150         req = nonemb_cmd->va;
151         memset(req, 0, sizeof(*req));
152         sge = nonembedded_sgl(wrb);
153
154         be_wrb_hdr_prepare(wrb, sizeof(*req), false, 1);
155         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI,
156                         OPCODE_COMMON_ISCSI_ERROR_RECOVERY_INVALIDATE_COMMANDS,
157                         sizeof(*req));
158         req->ref_handle = 0;
159         req->cleanup_type = CMD_ISCSI_COMMAND_INVALIDATE;
160         for (i = 0; i < num_invalidate; i++) {
161                 req->table[i].icd = inv_tbl->icd;
162                 req->table[i].cid = inv_tbl->cid;
163                 req->icd_count++;
164                 inv_tbl++;
165         }
166         sge->pa_hi = cpu_to_le32(upper_32_bits(nonemb_cmd->dma));
167         sge->pa_lo = cpu_to_le32(nonemb_cmd->dma & 0xFFFFFFFF);
168         sge->len = cpu_to_le32(nonemb_cmd->size);
169
170         be_mcc_notify(phba, tag);
171         mutex_unlock(&ctrl->mbox_lock);
172         return tag;
173 }
174
175 unsigned int mgmt_invalidate_connection(struct beiscsi_hba *phba,
176                                          struct beiscsi_endpoint *beiscsi_ep,
177                                          unsigned short cid,
178                                          unsigned short issue_reset,
179                                          unsigned short savecfg_flag)
180 {
181         struct be_ctrl_info *ctrl = &phba->ctrl;
182         struct be_mcc_wrb *wrb;
183         struct iscsi_invalidate_connection_params_in *req;
184         unsigned int tag = 0;
185
186         mutex_lock(&ctrl->mbox_lock);
187         wrb = alloc_mcc_wrb(phba, &tag);
188         if (!wrb) {
189                 mutex_unlock(&ctrl->mbox_lock);
190                 return 0;
191         }
192
193         req = embedded_payload(wrb);
194         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
195         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI_INI,
196                            OPCODE_ISCSI_INI_DRIVER_INVALIDATE_CONNECTION,
197                            sizeof(*req));
198         req->session_handle = beiscsi_ep->fw_handle;
199         req->cid = cid;
200         if (issue_reset)
201                 req->cleanup_type = CMD_ISCSI_CONNECTION_ISSUE_TCP_RST;
202         else
203                 req->cleanup_type = CMD_ISCSI_CONNECTION_INVALIDATE;
204         req->save_cfg = savecfg_flag;
205         be_mcc_notify(phba, tag);
206         mutex_unlock(&ctrl->mbox_lock);
207         return tag;
208 }
209
210 unsigned int mgmt_upload_connection(struct beiscsi_hba *phba,
211                                 unsigned short cid, unsigned int upload_flag)
212 {
213         struct be_ctrl_info *ctrl = &phba->ctrl;
214         struct be_mcc_wrb *wrb;
215         struct tcp_upload_params_in *req;
216         unsigned int tag;
217
218         mutex_lock(&ctrl->mbox_lock);
219         wrb = alloc_mcc_wrb(phba, &tag);
220         if (!wrb) {
221                 mutex_unlock(&ctrl->mbox_lock);
222                 return 0;
223         }
224
225         req = embedded_payload(wrb);
226         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
227         be_cmd_hdr_prepare(&req->hdr, CMD_COMMON_TCP_UPLOAD,
228                            OPCODE_COMMON_TCP_UPLOAD, sizeof(*req));
229         req->id = (unsigned short)cid;
230         req->upload_type = (unsigned char)upload_flag;
231         be_mcc_notify(phba, tag);
232         mutex_unlock(&ctrl->mbox_lock);
233         return tag;
234 }
235
236 /**
237  * mgmt_open_connection()- Establish a TCP CXN
238  * @dst_addr: Destination Address
239  * @beiscsi_ep: ptr to device endpoint struct
240  * @nonemb_cmd: ptr to memory allocated for command
241  *
242  * return
243  *      Success: Tag number of the MBX Command issued
244  *      Failure: Error code
245  **/
246 int mgmt_open_connection(struct beiscsi_hba *phba,
247                          struct sockaddr *dst_addr,
248                          struct beiscsi_endpoint *beiscsi_ep,
249                          struct be_dma_mem *nonemb_cmd)
250 {
251         struct hwi_controller *phwi_ctrlr;
252         struct hwi_context_memory *phwi_context;
253         struct sockaddr_in *daddr_in = (struct sockaddr_in *)dst_addr;
254         struct sockaddr_in6 *daddr_in6 = (struct sockaddr_in6 *)dst_addr;
255         struct be_ctrl_info *ctrl = &phba->ctrl;
256         struct be_mcc_wrb *wrb;
257         struct tcp_connect_and_offload_in_v1 *req;
258         unsigned short def_hdr_id;
259         unsigned short def_data_id;
260         struct phys_addr template_address = { 0, 0 };
261         struct phys_addr *ptemplate_address;
262         unsigned int tag = 0;
263         unsigned int i, ulp_num;
264         unsigned short cid = beiscsi_ep->ep_cid;
265         struct be_sge *sge;
266
267         if (dst_addr->sa_family != PF_INET && dst_addr->sa_family != PF_INET6) {
268                 beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_CONFIG,
269                             "BG_%d : unknown addr family %d\n",
270                             dst_addr->sa_family);
271                 return -EINVAL;
272         }
273
274         phwi_ctrlr = phba->phwi_ctrlr;
275         phwi_context = phwi_ctrlr->phwi_ctxt;
276
277         ulp_num = phwi_ctrlr->wrb_context[BE_GET_CRI_FROM_CID(cid)].ulp_num;
278
279         def_hdr_id = (unsigned short)HWI_GET_DEF_HDRQ_ID(phba, ulp_num);
280         def_data_id = (unsigned short)HWI_GET_DEF_BUFQ_ID(phba, ulp_num);
281
282         ptemplate_address = &template_address;
283         ISCSI_GET_PDU_TEMPLATE_ADDRESS(phba, ptemplate_address);
284         if (mutex_lock_interruptible(&ctrl->mbox_lock))
285                 return 0;
286         wrb = alloc_mcc_wrb(phba, &tag);
287         if (!wrb) {
288                 mutex_unlock(&ctrl->mbox_lock);
289                 return 0;
290         }
291
292         sge = nonembedded_sgl(wrb);
293         req = nonemb_cmd->va;
294         memset(req, 0, sizeof(*req));
295
296         be_wrb_hdr_prepare(wrb, nonemb_cmd->size, false, 1);
297         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI,
298                            OPCODE_COMMON_ISCSI_TCP_CONNECT_AND_OFFLOAD,
299                            nonemb_cmd->size);
300         if (dst_addr->sa_family == PF_INET) {
301                 __be32 s_addr = daddr_in->sin_addr.s_addr;
302                 req->ip_address.ip_type = BEISCSI_IP_TYPE_V4;
303                 req->ip_address.addr[0] = s_addr & 0x000000ff;
304                 req->ip_address.addr[1] = (s_addr & 0x0000ff00) >> 8;
305                 req->ip_address.addr[2] = (s_addr & 0x00ff0000) >> 16;
306                 req->ip_address.addr[3] = (s_addr & 0xff000000) >> 24;
307                 req->tcp_port = ntohs(daddr_in->sin_port);
308                 beiscsi_ep->dst_addr = daddr_in->sin_addr.s_addr;
309                 beiscsi_ep->dst_tcpport = ntohs(daddr_in->sin_port);
310                 beiscsi_ep->ip_type = BEISCSI_IP_TYPE_V4;
311         } else {
312                 /* else its PF_INET6 family */
313                 req->ip_address.ip_type = BEISCSI_IP_TYPE_V6;
314                 memcpy(&req->ip_address.addr,
315                        &daddr_in6->sin6_addr.in6_u.u6_addr8, 16);
316                 req->tcp_port = ntohs(daddr_in6->sin6_port);
317                 beiscsi_ep->dst_tcpport = ntohs(daddr_in6->sin6_port);
318                 memcpy(&beiscsi_ep->dst6_addr,
319                        &daddr_in6->sin6_addr.in6_u.u6_addr8, 16);
320                 beiscsi_ep->ip_type = BEISCSI_IP_TYPE_V6;
321         }
322         req->cid = cid;
323         i = phba->nxt_cqid++;
324         if (phba->nxt_cqid == phba->num_cpus)
325                 phba->nxt_cqid = 0;
326         req->cq_id = phwi_context->be_cq[i].id;
327         beiscsi_log(phba, KERN_INFO, BEISCSI_LOG_CONFIG,
328                     "BG_%d : i=%d cq_id=%d\n", i, req->cq_id);
329         req->defq_id = def_hdr_id;
330         req->hdr_ring_id = def_hdr_id;
331         req->data_ring_id = def_data_id;
332         req->do_offload = 1;
333         req->dataout_template_pa.lo = ptemplate_address->lo;
334         req->dataout_template_pa.hi = ptemplate_address->hi;
335         sge->pa_hi = cpu_to_le32(upper_32_bits(nonemb_cmd->dma));
336         sge->pa_lo = cpu_to_le32(nonemb_cmd->dma & 0xFFFFFFFF);
337         sge->len = cpu_to_le32(nonemb_cmd->size);
338
339         if (!is_chip_be2_be3r(phba)) {
340                 req->hdr.version = MBX_CMD_VER1;
341                 req->tcp_window_size = 0x8000;
342                 req->tcp_window_scale_count = 2;
343         }
344
345         be_mcc_notify(phba, tag);
346         mutex_unlock(&ctrl->mbox_lock);
347         return tag;
348 }
349
350 /*
351  * mgmt_exec_nonemb_cmd()- Execute Non Embedded MBX Cmd
352  * @phba: Driver priv structure
353  * @nonemb_cmd: Address of the MBX command issued
354  * @resp_buf: Buffer to copy the MBX cmd response
355  * @resp_buf_len: respone lenght to be copied
356  *
357  **/
358 static int mgmt_exec_nonemb_cmd(struct beiscsi_hba *phba,
359                                 struct be_dma_mem *nonemb_cmd, void *resp_buf,
360                                 int resp_buf_len)
361 {
362         struct be_ctrl_info *ctrl = &phba->ctrl;
363         struct be_mcc_wrb *wrb;
364         struct be_sge *sge;
365         unsigned int tag;
366         int rc = 0;
367
368         mutex_lock(&ctrl->mbox_lock);
369         wrb = alloc_mcc_wrb(phba, &tag);
370         if (!wrb) {
371                 mutex_unlock(&ctrl->mbox_lock);
372                 rc = -ENOMEM;
373                 goto free_cmd;
374         }
375
376         sge = nonembedded_sgl(wrb);
377         be_wrb_hdr_prepare(wrb, nonemb_cmd->size, false, 1);
378         sge->pa_hi = cpu_to_le32(upper_32_bits(nonemb_cmd->dma));
379         sge->pa_lo = cpu_to_le32(lower_32_bits(nonemb_cmd->dma));
380         sge->len = cpu_to_le32(nonemb_cmd->size);
381
382         be_mcc_notify(phba, tag);
383         mutex_unlock(&ctrl->mbox_lock);
384
385         rc = beiscsi_mccq_compl_wait(phba, tag, NULL, nonemb_cmd);
386
387         if (resp_buf)
388                 memcpy(resp_buf, nonemb_cmd->va, resp_buf_len);
389
390         if (rc) {
391                 /* Check if the MBX Cmd needs to be re-issued */
392                 if (rc == -EAGAIN)
393                         return rc;
394
395                 beiscsi_log(phba, KERN_WARNING,
396                             BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX,
397                             "BG_%d : mgmt_exec_nonemb_cmd Failed status\n");
398
399                 if (rc != -EBUSY)
400                         goto free_cmd;
401                 else
402                         return rc;
403         }
404 free_cmd:
405         pci_free_consistent(ctrl->pdev, nonemb_cmd->size,
406                             nonemb_cmd->va, nonemb_cmd->dma);
407         return rc;
408 }
409
410 static int mgmt_alloc_cmd_data(struct beiscsi_hba *phba, struct be_dma_mem *cmd,
411                                int iscsi_cmd, int size)
412 {
413         cmd->va = pci_zalloc_consistent(phba->ctrl.pdev, size, &cmd->dma);
414         if (!cmd->va) {
415                 beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_CONFIG,
416                             "BG_%d : Failed to allocate memory for if info\n");
417                 return -ENOMEM;
418         }
419         cmd->size = size;
420         be_cmd_hdr_prepare(cmd->va, CMD_SUBSYSTEM_ISCSI, iscsi_cmd, size);
421         beiscsi_log(phba, KERN_INFO, BEISCSI_LOG_CONFIG,
422                     "BG_%d : subsystem iSCSI cmd %d size %d\n",
423                     iscsi_cmd, size);
424         return 0;
425 }
426
427 unsigned int beiscsi_if_get_handle(struct beiscsi_hba *phba)
428 {
429         struct be_ctrl_info *ctrl = &phba->ctrl;
430         struct be_mcc_wrb *wrb;
431         struct be_cmd_get_all_if_id_req *req;
432         struct be_cmd_get_all_if_id_req *pbe_allid;
433         unsigned int tag;
434         int status = 0;
435
436         if (mutex_lock_interruptible(&ctrl->mbox_lock))
437                 return -EINTR;
438         wrb = alloc_mcc_wrb(phba, &tag);
439         if (!wrb) {
440                 mutex_unlock(&ctrl->mbox_lock);
441                 return -ENOMEM;
442         }
443
444         req = embedded_payload(wrb);
445         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
446         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI,
447                            OPCODE_COMMON_ISCSI_NTWK_GET_ALL_IF_ID,
448                            sizeof(*req));
449         be_mcc_notify(phba, tag);
450         mutex_unlock(&ctrl->mbox_lock);
451
452         status = beiscsi_mccq_compl_wait(phba, tag, &wrb, NULL);
453         if (status) {
454                 beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
455                             "BG_%d : %s failed: %d\n", __func__, status);
456                 return -EBUSY;
457         }
458
459         pbe_allid = embedded_payload(wrb);
460         /* we now support only one interface per function */
461         phba->interface_handle = pbe_allid->if_hndl_list[0];
462
463         return status;
464 }
465
466 static inline bool beiscsi_if_zero_ip(u8 *ip, u32 ip_type)
467 {
468         u32 len;
469
470         len = (ip_type < BEISCSI_IP_TYPE_V6) ? IP_V4_LEN : IP_V6_LEN;
471         while (len && !ip[len - 1])
472                 len--;
473         return (len == 0);
474 }
475
476 static int beiscsi_if_mod_gw(struct beiscsi_hba *phba,
477                              u32 action, u32 ip_type, u8 *gw)
478 {
479         struct be_cmd_set_def_gateway_req *req;
480         struct be_dma_mem nonemb_cmd;
481         int rt_val;
482
483         rt_val = mgmt_alloc_cmd_data(phba, &nonemb_cmd,
484                                 OPCODE_COMMON_ISCSI_NTWK_MODIFY_DEFAULT_GATEWAY,
485                                 sizeof(*req));
486         if (rt_val)
487                 return rt_val;
488
489         req = nonemb_cmd.va;
490         req->action = action;
491         req->ip_addr.ip_type = ip_type;
492         memcpy(req->ip_addr.addr, gw,
493                (ip_type < BEISCSI_IP_TYPE_V6) ? IP_V4_LEN : IP_V6_LEN);
494         return mgmt_exec_nonemb_cmd(phba, &nonemb_cmd, NULL, 0);
495 }
496
497 int beiscsi_if_set_gw(struct beiscsi_hba *phba, u32 ip_type, u8 *gw)
498 {
499         struct be_cmd_get_def_gateway_resp gw_resp;
500         int rt_val;
501
502         memset(&gw_resp, 0, sizeof(gw_resp));
503         rt_val = beiscsi_if_get_gw(phba, ip_type, &gw_resp);
504         if (rt_val) {
505                 beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
506                             "BG_%d : Failed to Get Gateway Addr\n");
507                 return rt_val;
508         }
509
510         if (!beiscsi_if_zero_ip(gw_resp.ip_addr.addr, ip_type)) {
511                 rt_val = beiscsi_if_mod_gw(phba, IP_ACTION_DEL, ip_type,
512                                            gw_resp.ip_addr.addr);
513                 if (rt_val) {
514                         beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
515                                     "BG_%d : Failed to clear Gateway Addr Set\n");
516                         return rt_val;
517                 }
518         }
519
520         rt_val = beiscsi_if_mod_gw(phba, IP_ACTION_ADD, ip_type, gw);
521         if (rt_val)
522                 beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
523                             "BG_%d : Failed to Set Gateway Addr\n");
524
525         return rt_val;
526 }
527
528 int beiscsi_if_get_gw(struct beiscsi_hba *phba, u32 ip_type,
529                       struct be_cmd_get_def_gateway_resp *resp)
530 {
531         struct be_cmd_get_def_gateway_req *req;
532         struct be_dma_mem nonemb_cmd;
533         int rc;
534
535         rc = mgmt_alloc_cmd_data(phba, &nonemb_cmd,
536                                  OPCODE_COMMON_ISCSI_NTWK_GET_DEFAULT_GATEWAY,
537                                  sizeof(*resp));
538         if (rc)
539                 return rc;
540
541         req = nonemb_cmd.va;
542         req->ip_type = ip_type;
543
544         return mgmt_exec_nonemb_cmd(phba, &nonemb_cmd, resp,
545                                     sizeof(*resp));
546 }
547
548 static int
549 beiscsi_if_clr_ip(struct beiscsi_hba *phba,
550                   struct be_cmd_get_if_info_resp *if_info)
551 {
552         struct be_cmd_set_ip_addr_req *req;
553         struct be_dma_mem nonemb_cmd;
554         int rc;
555
556         rc = mgmt_alloc_cmd_data(phba, &nonemb_cmd,
557                                  OPCODE_COMMON_ISCSI_NTWK_MODIFY_IP_ADDR,
558                                  sizeof(*req));
559         if (rc)
560                 return rc;
561
562         req = nonemb_cmd.va;
563         req->ip_params.record_entry_count = 1;
564         req->ip_params.ip_record.action = IP_ACTION_DEL;
565         req->ip_params.ip_record.interface_hndl =
566                 phba->interface_handle;
567         req->ip_params.ip_record.ip_addr.size_of_structure =
568                 sizeof(struct be_ip_addr_subnet_format);
569         req->ip_params.ip_record.ip_addr.ip_type = if_info->ip_addr.ip_type;
570         memcpy(req->ip_params.ip_record.ip_addr.addr,
571                if_info->ip_addr.addr,
572                sizeof(if_info->ip_addr.addr));
573         memcpy(req->ip_params.ip_record.ip_addr.subnet_mask,
574                if_info->ip_addr.subnet_mask,
575                sizeof(if_info->ip_addr.subnet_mask));
576         rc = mgmt_exec_nonemb_cmd(phba, &nonemb_cmd, NULL, 0);
577         if (rc < 0 || req->ip_params.ip_record.status) {
578                 beiscsi_log(phba, KERN_INFO, BEISCSI_LOG_CONFIG,
579                             "BG_%d : failed to clear IP: rc %d status %d\n",
580                             rc, req->ip_params.ip_record.status);
581         }
582         return rc;
583 }
584
585 static int
586 beiscsi_if_set_ip(struct beiscsi_hba *phba, u8 *ip,
587                   u8 *subnet, u32 ip_type)
588 {
589         struct be_cmd_set_ip_addr_req *req;
590         struct be_dma_mem nonemb_cmd;
591         uint32_t ip_len;
592         int rc;
593
594         rc = mgmt_alloc_cmd_data(phba, &nonemb_cmd,
595                                  OPCODE_COMMON_ISCSI_NTWK_MODIFY_IP_ADDR,
596                                  sizeof(*req));
597         if (rc)
598                 return rc;
599
600         req = nonemb_cmd.va;
601         req->ip_params.record_entry_count = 1;
602         req->ip_params.ip_record.action = IP_ACTION_ADD;
603         req->ip_params.ip_record.interface_hndl =
604                 phba->interface_handle;
605         req->ip_params.ip_record.ip_addr.size_of_structure =
606                 sizeof(struct be_ip_addr_subnet_format);
607         req->ip_params.ip_record.ip_addr.ip_type = ip_type;
608         ip_len = (ip_type < BEISCSI_IP_TYPE_V6) ? IP_V4_LEN : IP_V6_LEN;
609         memcpy(req->ip_params.ip_record.ip_addr.addr, ip, ip_len);
610         if (subnet)
611                 memcpy(req->ip_params.ip_record.ip_addr.subnet_mask,
612                        subnet, ip_len);
613
614         rc = mgmt_exec_nonemb_cmd(phba, &nonemb_cmd, NULL, 0);
615         /**
616          * In some cases, host needs to look into individual record status
617          * even though FW reported success for that IOCTL.
618          */
619         if (rc < 0 || req->ip_params.ip_record.status) {
620                 __beiscsi_log(phba, KERN_ERR,
621                             "BG_%d : failed to set IP: rc %d status %d\n",
622                             rc, req->ip_params.ip_record.status);
623                 if (req->ip_params.ip_record.status)
624                         rc = -EINVAL;
625         }
626         return rc;
627 }
628
629 int beiscsi_if_en_static(struct beiscsi_hba *phba, u32 ip_type,
630                          u8 *ip, u8 *subnet)
631 {
632         struct be_cmd_get_if_info_resp *if_info;
633         struct be_cmd_rel_dhcp_req *reldhcp;
634         struct be_dma_mem nonemb_cmd;
635         int rc;
636
637         rc = beiscsi_if_get_info(phba, ip_type, &if_info);
638         if (rc)
639                 return rc;
640
641         if (if_info->dhcp_state) {
642                 rc = mgmt_alloc_cmd_data(phba, &nonemb_cmd,
643                                 OPCODE_COMMON_ISCSI_NTWK_REL_STATELESS_IP_ADDR,
644                                 sizeof(*reldhcp));
645                 if (rc)
646                         goto exit;
647
648                 reldhcp = nonemb_cmd.va;
649                 reldhcp->interface_hndl = phba->interface_handle;
650                 reldhcp->ip_type = ip_type;
651                 rc = mgmt_exec_nonemb_cmd(phba, &nonemb_cmd, NULL, 0);
652                 if (rc < 0) {
653                         beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
654                                     "BG_%d : failed to release existing DHCP: %d\n",
655                                     rc);
656                         goto exit;
657                 }
658         }
659
660         /* first delete any IP set */
661         if (!beiscsi_if_zero_ip(if_info->ip_addr.addr, ip_type)) {
662                 rc = beiscsi_if_clr_ip(phba, if_info);
663                 if (rc)
664                         goto exit;
665         }
666
667         /* if ip == NULL then this is called just to release DHCP IP */
668         if (ip)
669                 rc = beiscsi_if_set_ip(phba, ip, subnet, ip_type);
670 exit:
671         kfree(if_info);
672         return rc;
673 }
674
675 int beiscsi_if_en_dhcp(struct beiscsi_hba *phba, u32 ip_type)
676 {
677         struct be_cmd_get_def_gateway_resp gw_resp;
678         struct be_cmd_get_if_info_resp *if_info;
679         struct be_cmd_set_dhcp_req *dhcpreq;
680         struct be_dma_mem nonemb_cmd;
681         u8 *gw;
682         int rc;
683
684         rc = beiscsi_if_get_info(phba, ip_type, &if_info);
685         if (rc)
686                 return rc;
687
688         if (if_info->dhcp_state) {
689                 beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
690                                 "BG_%d : DHCP Already Enabled\n");
691                 goto exit;
692         }
693
694         /* first delete any IP set */
695         if (!beiscsi_if_zero_ip(if_info->ip_addr.addr, ip_type)) {
696                 rc = beiscsi_if_clr_ip(phba, if_info);
697                 if (rc)
698                         goto exit;
699         }
700
701         /* delete gateway settings if mode change is to DHCP */
702         memset(&gw_resp, 0, sizeof(gw_resp));
703         /* use ip_type provided in if_info */
704         rc = beiscsi_if_get_gw(phba, if_info->ip_addr.ip_type, &gw_resp);
705         if (rc) {
706                 beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
707                             "BG_%d : Failed to Get Gateway Addr\n");
708                 goto exit;
709         }
710         gw = (u8 *)&gw_resp.ip_addr.addr;
711         if (!beiscsi_if_zero_ip(gw, if_info->ip_addr.ip_type)) {
712                 rc = beiscsi_if_mod_gw(phba, IP_ACTION_DEL,
713                                        if_info->ip_addr.ip_type, gw);
714                 if (rc) {
715                         beiscsi_log(phba, KERN_WARNING, BEISCSI_LOG_CONFIG,
716                                     "BG_%d : Failed to clear Gateway Addr Set\n");
717                         goto exit;
718                 }
719         }
720
721         rc = mgmt_alloc_cmd_data(phba, &nonemb_cmd,
722                         OPCODE_COMMON_ISCSI_NTWK_CONFIG_STATELESS_IP_ADDR,
723                         sizeof(*dhcpreq));
724         if (rc)
725                 goto exit;
726
727         dhcpreq = nonemb_cmd.va;
728         dhcpreq->flags = 1; /* 1 - blocking; 0 - non-blocking */
729         dhcpreq->retry_count = 1;
730         dhcpreq->interface_hndl = phba->interface_handle;
731         dhcpreq->ip_type = ip_type;
732         rc = mgmt_exec_nonemb_cmd(phba, &nonemb_cmd, NULL, 0);
733
734 exit:
735         kfree(if_info);
736         return rc;
737 }
738
739 /**
740  * beiscsi_if_set_vlan()- Issue and wait for CMD completion
741  * @phba: device private structure instance
742  * @vlan_tag: VLAN tag
743  *
744  * Issue the MBX Cmd and wait for the completion of the
745  * command.
746  *
747  * returns
748  *      Success: 0
749  *      Failure: Non-Xero Value
750  **/
751 int beiscsi_if_set_vlan(struct beiscsi_hba *phba, uint16_t vlan_tag)
752 {
753         int rc;
754         unsigned int tag;
755
756         tag = be_cmd_set_vlan(phba, vlan_tag);
757         if (!tag) {
758                 beiscsi_log(phba, KERN_ERR,
759                             (BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX),
760                             "BG_%d : VLAN Setting Failed\n");
761                 return -EBUSY;
762         }
763
764         rc = beiscsi_mccq_compl_wait(phba, tag, NULL, NULL);
765         if (rc) {
766                 beiscsi_log(phba, KERN_ERR,
767                             (BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX),
768                             "BS_%d : VLAN MBX Cmd Failed\n");
769                 return rc;
770         }
771         return rc;
772 }
773
774
775 int beiscsi_if_get_info(struct beiscsi_hba *phba, int ip_type,
776                         struct be_cmd_get_if_info_resp **if_info)
777 {
778         struct be_cmd_get_if_info_req *req;
779         struct be_dma_mem nonemb_cmd;
780         uint32_t ioctl_size = sizeof(struct be_cmd_get_if_info_resp);
781         int rc;
782
783         rc = beiscsi_if_get_handle(phba);
784         if (rc)
785                 return rc;
786
787         do {
788                 rc = mgmt_alloc_cmd_data(phba, &nonemb_cmd,
789                                          OPCODE_COMMON_ISCSI_NTWK_GET_IF_INFO,
790                                          ioctl_size);
791                 if (rc)
792                         return rc;
793
794                 req = nonemb_cmd.va;
795                 req->interface_hndl = phba->interface_handle;
796                 req->ip_type = ip_type;
797
798                 /* Allocate memory for if_info */
799                 *if_info = kzalloc(ioctl_size, GFP_KERNEL);
800                 if (!*if_info) {
801                         beiscsi_log(phba, KERN_ERR,
802                                     BEISCSI_LOG_INIT | BEISCSI_LOG_CONFIG,
803                                     "BG_%d : Memory Allocation Failure\n");
804
805                                 /* Free the DMA memory for the IOCTL issuing */
806                                 pci_free_consistent(phba->ctrl.pdev,
807                                                     nonemb_cmd.size,
808                                                     nonemb_cmd.va,
809                                                     nonemb_cmd.dma);
810                                 return -ENOMEM;
811                 }
812
813                 rc =  mgmt_exec_nonemb_cmd(phba, &nonemb_cmd, *if_info,
814                                            ioctl_size);
815
816                 /* Check if the error is because of Insufficent_Buffer */
817                 if (rc == -EAGAIN) {
818
819                         /* Get the new memory size */
820                         ioctl_size = ((struct be_cmd_resp_hdr *)
821                                       nonemb_cmd.va)->actual_resp_len;
822                         ioctl_size += sizeof(struct be_cmd_req_hdr);
823
824                         /* Free the previous allocated DMA memory */
825                         pci_free_consistent(phba->ctrl.pdev, nonemb_cmd.size,
826                                             nonemb_cmd.va,
827                                             nonemb_cmd.dma);
828
829                         /* Free the virtual memory */
830                         kfree(*if_info);
831                 } else
832                         break;
833         } while (true);
834         return rc;
835 }
836
837 int mgmt_get_nic_conf(struct beiscsi_hba *phba,
838                       struct be_cmd_get_nic_conf_resp *nic)
839 {
840         struct be_dma_mem nonemb_cmd;
841         int rc;
842
843         rc = mgmt_alloc_cmd_data(phba, &nonemb_cmd,
844                                  OPCODE_COMMON_ISCSI_NTWK_GET_NIC_CONFIG,
845                                  sizeof(*nic));
846         if (rc)
847                 return rc;
848
849         return mgmt_exec_nonemb_cmd(phba, &nonemb_cmd, nic, sizeof(*nic));
850 }
851
852
853
854 unsigned int be_cmd_get_initname(struct beiscsi_hba *phba)
855 {
856         unsigned int tag;
857         struct be_mcc_wrb *wrb;
858         struct be_cmd_hba_name *req;
859         struct be_ctrl_info *ctrl = &phba->ctrl;
860
861         if (mutex_lock_interruptible(&ctrl->mbox_lock))
862                 return 0;
863         wrb = alloc_mcc_wrb(phba, &tag);
864         if (!wrb) {
865                 mutex_unlock(&ctrl->mbox_lock);
866                 return 0;
867         }
868
869         req = embedded_payload(wrb);
870         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
871         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI_INI,
872                         OPCODE_ISCSI_INI_CFG_GET_HBA_NAME,
873                         sizeof(*req));
874
875         be_mcc_notify(phba, tag);
876         mutex_unlock(&ctrl->mbox_lock);
877         return tag;
878 }
879
880 static void beiscsi_boot_process_compl(struct beiscsi_hba *phba,
881                                        unsigned int tag)
882 {
883         struct be_cmd_get_boot_target_resp *boot_resp;
884         struct be_cmd_resp_logout_fw_sess *logo_resp;
885         struct be_cmd_get_session_resp *sess_resp;
886         struct be_mcc_wrb *wrb;
887         struct boot_struct *bs;
888         int boot_work, status;
889
890         if (!test_bit(BEISCSI_HBA_BOOT_WORK, &phba->state)) {
891                 __beiscsi_log(phba, KERN_ERR,
892                               "BG_%d : %s no boot work %lx\n",
893                               __func__, phba->state);
894                 return;
895         }
896
897         if (phba->boot_struct.tag != tag) {
898                 __beiscsi_log(phba, KERN_ERR,
899                               "BG_%d : %s tag mismatch %d:%d\n",
900                               __func__, tag, phba->boot_struct.tag);
901                 return;
902         }
903         bs = &phba->boot_struct;
904         boot_work = 1;
905         status = 0;
906         switch (bs->action) {
907         case BEISCSI_BOOT_REOPEN_SESS:
908                 status = __beiscsi_mcc_compl_status(phba, tag, NULL, NULL);
909                 if (!status)
910                         bs->action = BEISCSI_BOOT_GET_SHANDLE;
911                 else
912                         bs->retry--;
913                 break;
914         case BEISCSI_BOOT_GET_SHANDLE:
915                 status = __beiscsi_mcc_compl_status(phba, tag, &wrb, NULL);
916                 if (!status) {
917                         boot_resp = embedded_payload(wrb);
918                         bs->s_handle = boot_resp->boot_session_handle;
919                 }
920                 if (bs->s_handle == BE_BOOT_INVALID_SHANDLE) {
921                         bs->action = BEISCSI_BOOT_REOPEN_SESS;
922                         bs->retry--;
923                 } else {
924                         bs->action = BEISCSI_BOOT_GET_SINFO;
925                 }
926                 break;
927         case BEISCSI_BOOT_GET_SINFO:
928                 status = __beiscsi_mcc_compl_status(phba, tag, NULL,
929                                                     &bs->nonemb_cmd);
930                 if (!status) {
931                         sess_resp = bs->nonemb_cmd.va;
932                         memcpy(&bs->boot_sess, &sess_resp->session_info,
933                                sizeof(struct mgmt_session_info));
934                         bs->action = BEISCSI_BOOT_LOGOUT_SESS;
935                 } else {
936                         __beiscsi_log(phba, KERN_ERR,
937                                       "BG_%d : get boot session info error : 0x%x\n",
938                                       status);
939                         boot_work = 0;
940                 }
941                 pci_free_consistent(phba->ctrl.pdev, bs->nonemb_cmd.size,
942                                     bs->nonemb_cmd.va, bs->nonemb_cmd.dma);
943                 bs->nonemb_cmd.va = NULL;
944                 break;
945         case BEISCSI_BOOT_LOGOUT_SESS:
946                 status = __beiscsi_mcc_compl_status(phba, tag, &wrb, NULL);
947                 if (!status) {
948                         logo_resp = embedded_payload(wrb);
949                         if (logo_resp->session_status != BE_SESS_STATUS_CLOSE) {
950                                 __beiscsi_log(phba, KERN_ERR,
951                                               "BG_%d : FW boot session logout error : 0x%x\n",
952                                               logo_resp->session_status);
953                         }
954                 }
955                 /* continue to create boot_kset even if logout failed? */
956                 bs->action = BEISCSI_BOOT_CREATE_KSET;
957                 break;
958         default:
959                 break;
960         }
961
962         /* clear the tag so no other completion matches this tag */
963         bs->tag = 0;
964         if (!bs->retry) {
965                 boot_work = 0;
966                 __beiscsi_log(phba, KERN_ERR,
967                               "BG_%d : failed to setup boot target: status %d action %d\n",
968                               status, bs->action);
969         }
970         if (!boot_work) {
971                 /* wait for next event to start boot_work */
972                 clear_bit(BEISCSI_HBA_BOOT_WORK, &phba->state);
973                 return;
974         }
975         schedule_work(&phba->boot_work);
976 }
977
978 /**
979  * beiscsi_boot_logout_sess()- Logout from boot FW session
980  * @phba: Device priv structure instance
981  *
982  * return
983  *      the TAG used for MBOX Command
984  *
985  */
986 unsigned int beiscsi_boot_logout_sess(struct beiscsi_hba *phba)
987 {
988         struct be_ctrl_info *ctrl = &phba->ctrl;
989         struct be_mcc_wrb *wrb;
990         struct be_cmd_req_logout_fw_sess *req;
991         unsigned int tag;
992
993         mutex_lock(&ctrl->mbox_lock);
994         wrb = alloc_mcc_wrb(phba, &tag);
995         if (!wrb) {
996                 mutex_unlock(&ctrl->mbox_lock);
997                 return 0;
998         }
999
1000         req = embedded_payload(wrb);
1001         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
1002         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI_INI,
1003                            OPCODE_ISCSI_INI_SESSION_LOGOUT_TARGET,
1004                            sizeof(struct be_cmd_req_logout_fw_sess));
1005         /* Use the session handle copied into boot_sess */
1006         req->session_handle = phba->boot_struct.boot_sess.session_handle;
1007
1008         phba->boot_struct.tag = tag;
1009         set_bit(MCC_TAG_STATE_ASYNC, &ctrl->ptag_state[tag].tag_state);
1010         ctrl->ptag_state[tag].cbfn = beiscsi_boot_process_compl;
1011
1012         be_mcc_notify(phba, tag);
1013         mutex_unlock(&ctrl->mbox_lock);
1014
1015         return tag;
1016 }
1017 /**
1018  * beiscsi_boot_reopen_sess()- Reopen boot session
1019  * @phba: Device priv structure instance
1020  *
1021  * return
1022  *      the TAG used for MBOX Command
1023  *
1024  **/
1025 unsigned int beiscsi_boot_reopen_sess(struct beiscsi_hba *phba)
1026 {
1027         struct be_ctrl_info *ctrl = &phba->ctrl;
1028         struct be_mcc_wrb *wrb;
1029         struct be_cmd_reopen_session_req *req;
1030         unsigned int tag;
1031
1032         mutex_lock(&ctrl->mbox_lock);
1033         wrb = alloc_mcc_wrb(phba, &tag);
1034         if (!wrb) {
1035                 mutex_unlock(&ctrl->mbox_lock);
1036                 return 0;
1037         }
1038
1039         req = embedded_payload(wrb);
1040         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
1041         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI_INI,
1042                            OPCODE_ISCSI_INI_DRIVER_REOPEN_ALL_SESSIONS,
1043                            sizeof(struct be_cmd_reopen_session_resp));
1044         req->reopen_type = BE_REOPEN_BOOT_SESSIONS;
1045         req->session_handle = BE_BOOT_INVALID_SHANDLE;
1046
1047         phba->boot_struct.tag = tag;
1048         set_bit(MCC_TAG_STATE_ASYNC, &ctrl->ptag_state[tag].tag_state);
1049         ctrl->ptag_state[tag].cbfn = beiscsi_boot_process_compl;
1050
1051         be_mcc_notify(phba, tag);
1052         mutex_unlock(&ctrl->mbox_lock);
1053         return tag;
1054 }
1055
1056
1057 /**
1058  * beiscsi_boot_get_sinfo()- Get boot session info
1059  * @phba: device priv structure instance
1060  *
1061  * Fetches the boot_struct.s_handle info from FW.
1062  * return
1063  *      the TAG used for MBOX Command
1064  *
1065  **/
1066 unsigned int beiscsi_boot_get_sinfo(struct beiscsi_hba *phba)
1067 {
1068         struct be_ctrl_info *ctrl = &phba->ctrl;
1069         struct be_cmd_get_session_resp *resp;
1070         struct be_cmd_get_session_req *req;
1071         struct be_dma_mem *nonemb_cmd;
1072         struct be_mcc_wrb *wrb;
1073         struct be_sge *sge;
1074         unsigned int tag;
1075
1076         mutex_lock(&ctrl->mbox_lock);
1077         wrb = alloc_mcc_wrb(phba, &tag);
1078         if (!wrb) {
1079                 mutex_unlock(&ctrl->mbox_lock);
1080                 return 0;
1081         }
1082
1083         nonemb_cmd = &phba->boot_struct.nonemb_cmd;
1084         nonemb_cmd->size = sizeof(*resp);
1085         nonemb_cmd->va = pci_alloc_consistent(phba->ctrl.pdev,
1086                                               sizeof(nonemb_cmd->size),
1087                                               &nonemb_cmd->dma);
1088         if (!nonemb_cmd->va) {
1089                 mutex_unlock(&ctrl->mbox_lock);
1090                 return 0;
1091         }
1092
1093         req = nonemb_cmd->va;
1094         memset(req, 0, sizeof(*req));
1095         sge = nonembedded_sgl(wrb);
1096         be_wrb_hdr_prepare(wrb, sizeof(*req), false, 1);
1097         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI_INI,
1098                            OPCODE_ISCSI_INI_SESSION_GET_A_SESSION,
1099                            sizeof(*resp));
1100         req->session_handle = phba->boot_struct.s_handle;
1101         sge->pa_hi = cpu_to_le32(upper_32_bits(nonemb_cmd->dma));
1102         sge->pa_lo = cpu_to_le32(nonemb_cmd->dma & 0xFFFFFFFF);
1103         sge->len = cpu_to_le32(nonemb_cmd->size);
1104
1105         phba->boot_struct.tag = tag;
1106         set_bit(MCC_TAG_STATE_ASYNC, &ctrl->ptag_state[tag].tag_state);
1107         ctrl->ptag_state[tag].cbfn = beiscsi_boot_process_compl;
1108
1109         be_mcc_notify(phba, tag);
1110         mutex_unlock(&ctrl->mbox_lock);
1111         return tag;
1112 }
1113
1114 unsigned int __beiscsi_boot_get_shandle(struct beiscsi_hba *phba, int async)
1115 {
1116         struct be_ctrl_info *ctrl = &phba->ctrl;
1117         struct be_mcc_wrb *wrb;
1118         struct be_cmd_get_boot_target_req *req;
1119         unsigned int tag;
1120
1121         mutex_lock(&ctrl->mbox_lock);
1122         wrb = alloc_mcc_wrb(phba, &tag);
1123         if (!wrb) {
1124                 mutex_unlock(&ctrl->mbox_lock);
1125                 return 0;
1126         }
1127
1128         req = embedded_payload(wrb);
1129         be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0);
1130         be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI_INI,
1131                            OPCODE_ISCSI_INI_BOOT_GET_BOOT_TARGET,
1132                            sizeof(struct be_cmd_get_boot_target_resp));
1133
1134         if (async) {
1135                 phba->boot_struct.tag = tag;
1136                 set_bit(MCC_TAG_STATE_ASYNC, &ctrl->ptag_state[tag].tag_state);
1137                 ctrl->ptag_state[tag].cbfn = beiscsi_boot_process_compl;
1138         }
1139
1140         be_mcc_notify(phba, tag);
1141         mutex_unlock(&ctrl->mbox_lock);
1142         return tag;
1143 }
1144
1145 /**
1146  * beiscsi_boot_get_shandle()- Get boot session handle
1147  * @phba: device priv structure instance
1148  * @s_handle: session handle returned for boot session.
1149  *
1150  * return
1151  *      Success: 1
1152  *      Failure: negative
1153  *
1154  **/
1155 int beiscsi_boot_get_shandle(struct beiscsi_hba *phba, unsigned int *s_handle)
1156 {
1157         struct be_cmd_get_boot_target_resp *boot_resp;
1158         struct be_mcc_wrb *wrb;
1159         unsigned int tag;
1160         int rc;
1161
1162         *s_handle = BE_BOOT_INVALID_SHANDLE;
1163         /* get configured boot session count and handle */
1164         tag = __beiscsi_boot_get_shandle(phba, 0);
1165         if (!tag) {
1166                 beiscsi_log(phba, KERN_ERR,
1167                             BEISCSI_LOG_CONFIG | BEISCSI_LOG_INIT,
1168                             "BG_%d : Getting Boot Target Info Failed\n");
1169                 return -EAGAIN;
1170         }
1171
1172         rc = beiscsi_mccq_compl_wait(phba, tag, &wrb, NULL);
1173         if (rc) {
1174                 beiscsi_log(phba, KERN_ERR,
1175                             BEISCSI_LOG_INIT | BEISCSI_LOG_CONFIG,
1176                             "BG_%d : MBX CMD get_boot_target Failed\n");
1177                 return -EBUSY;
1178         }
1179
1180         boot_resp = embedded_payload(wrb);
1181         /* check if there are any boot targets configured */
1182         if (!boot_resp->boot_session_count) {
1183                 __beiscsi_log(phba, KERN_INFO,
1184                               "BG_%d : No boot targets configured\n");
1185                 return -ENXIO;
1186         }
1187
1188         /* only if FW has logged in to the boot target, s_handle is valid */
1189         *s_handle = boot_resp->boot_session_handle;
1190         return 1;
1191 }
1192
1193 /**
1194  * beiscsi_drvr_ver_disp()- Display the driver Name and Version
1195  * @dev: ptr to device not used.
1196  * @attr: device attribute, not used.
1197  * @buf: contains formatted text driver name and version
1198  *
1199  * return
1200  * size of the formatted string
1201  **/
1202 ssize_t
1203 beiscsi_drvr_ver_disp(struct device *dev, struct device_attribute *attr,
1204                        char *buf)
1205 {
1206         return snprintf(buf, PAGE_SIZE, BE_NAME "\n");
1207 }
1208
1209 /**
1210  * beiscsi_fw_ver_disp()- Display Firmware Version
1211  * @dev: ptr to device not used.
1212  * @attr: device attribute, not used.
1213  * @buf: contains formatted text Firmware version
1214  *
1215  * return
1216  * size of the formatted string
1217  **/
1218 ssize_t
1219 beiscsi_fw_ver_disp(struct device *dev, struct device_attribute *attr,
1220                      char *buf)
1221 {
1222         struct Scsi_Host *shost = class_to_shost(dev);
1223         struct beiscsi_hba *phba = iscsi_host_priv(shost);
1224
1225         return snprintf(buf, PAGE_SIZE, "%s\n", phba->fw_ver_str);
1226 }
1227
1228 /**
1229  * beiscsi_active_session_disp()- Display Sessions Active
1230  * @dev: ptr to device not used.
1231  * @attr: device attribute, not used.
1232  * @buf: contains formatted text Session Count
1233  *
1234  * return
1235  * size of the formatted string
1236  **/
1237 ssize_t
1238 beiscsi_active_session_disp(struct device *dev, struct device_attribute *attr,
1239                          char *buf)
1240 {
1241         struct Scsi_Host *shost = class_to_shost(dev);
1242         struct beiscsi_hba *phba = iscsi_host_priv(shost);
1243         uint16_t avlbl_cids = 0, ulp_num, len = 0, total_cids = 0;
1244
1245         for (ulp_num = 0; ulp_num < BEISCSI_ULP_COUNT; ulp_num++) {
1246                 if (test_bit(ulp_num, (void *)&phba->fw_config.ulp_supported)) {
1247                         avlbl_cids = BEISCSI_ULP_AVLBL_CID(phba, ulp_num);
1248                         total_cids = BEISCSI_GET_CID_COUNT(phba, ulp_num);
1249                         len += snprintf(buf+len, PAGE_SIZE - len,
1250                                         "ULP%d : %d\n", ulp_num,
1251                                         (total_cids - avlbl_cids));
1252                 } else
1253                         len += snprintf(buf+len, PAGE_SIZE - len,
1254                                         "ULP%d : %d\n", ulp_num, 0);
1255         }
1256
1257         return len;
1258 }
1259
1260 /**
1261  * beiscsi_free_session_disp()- Display Avaliable Session
1262  * @dev: ptr to device not used.
1263  * @attr: device attribute, not used.
1264  * @buf: contains formatted text Session Count
1265  *
1266  * return
1267  * size of the formatted string
1268  **/
1269 ssize_t
1270 beiscsi_free_session_disp(struct device *dev, struct device_attribute *attr,
1271                        char *buf)
1272 {
1273         struct Scsi_Host *shost = class_to_shost(dev);
1274         struct beiscsi_hba *phba = iscsi_host_priv(shost);
1275         uint16_t ulp_num, len = 0;
1276
1277         for (ulp_num = 0; ulp_num < BEISCSI_ULP_COUNT; ulp_num++) {
1278                 if (test_bit(ulp_num, (void *)&phba->fw_config.ulp_supported))
1279                         len += snprintf(buf+len, PAGE_SIZE - len,
1280                                         "ULP%d : %d\n", ulp_num,
1281                                         BEISCSI_ULP_AVLBL_CID(phba, ulp_num));
1282                 else
1283                         len += snprintf(buf+len, PAGE_SIZE - len,
1284                                         "ULP%d : %d\n", ulp_num, 0);
1285         }
1286
1287         return len;
1288 }
1289
1290 /**
1291  * beiscsi_adap_family_disp()- Display adapter family.
1292  * @dev: ptr to device to get priv structure
1293  * @attr: device attribute, not used.
1294  * @buf: contains formatted text driver name and version
1295  *
1296  * return
1297  * size of the formatted string
1298  **/
1299 ssize_t
1300 beiscsi_adap_family_disp(struct device *dev, struct device_attribute *attr,
1301                           char *buf)
1302 {
1303         uint16_t dev_id = 0;
1304         struct Scsi_Host *shost = class_to_shost(dev);
1305         struct beiscsi_hba *phba = iscsi_host_priv(shost);
1306
1307         dev_id = phba->pcidev->device;
1308         switch (dev_id) {
1309         case BE_DEVICE_ID1:
1310         case OC_DEVICE_ID1:
1311         case OC_DEVICE_ID2:
1312                 return snprintf(buf, PAGE_SIZE, "BE2 Adapter Family\n");
1313                 break;
1314         case BE_DEVICE_ID2:
1315         case OC_DEVICE_ID3:
1316                 return snprintf(buf, PAGE_SIZE, "BE3-R Adapter Family\n");
1317                 break;
1318         case OC_SKH_ID1:
1319                 return snprintf(buf, PAGE_SIZE, "Skyhawk-R Adapter Family\n");
1320                 break;
1321         default:
1322                 return snprintf(buf, PAGE_SIZE,
1323                                 "Unknown Adapter Family: 0x%x\n", dev_id);
1324                 break;
1325         }
1326 }
1327
1328 /**
1329  * beiscsi_phys_port()- Display Physical Port Identifier
1330  * @dev: ptr to device not used.
1331  * @attr: device attribute, not used.
1332  * @buf: contains formatted text port identifier
1333  *
1334  * return
1335  * size of the formatted string
1336  **/
1337 ssize_t
1338 beiscsi_phys_port_disp(struct device *dev, struct device_attribute *attr,
1339                          char *buf)
1340 {
1341         struct Scsi_Host *shost = class_to_shost(dev);
1342         struct beiscsi_hba *phba = iscsi_host_priv(shost);
1343
1344         return snprintf(buf, PAGE_SIZE, "Port Identifier : %d\n",
1345                         phba->fw_config.phys_port);
1346 }
1347
1348 void beiscsi_offload_cxn_v0(struct beiscsi_offload_params *params,
1349                              struct wrb_handle *pwrb_handle,
1350                              struct be_mem_descriptor *mem_descr,
1351                              struct hwi_wrb_context *pwrb_context)
1352 {
1353         struct iscsi_wrb *pwrb = pwrb_handle->pwrb;
1354
1355         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb,
1356                       max_send_data_segment_length, pwrb,
1357                       params->dw[offsetof(struct amap_beiscsi_offload_params,
1358                       max_send_data_segment_length) / 32]);
1359         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, type, pwrb,
1360                       BE_TGT_CTX_UPDT_CMD);
1361         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb,
1362                       first_burst_length,
1363                       pwrb,
1364                       params->dw[offsetof(struct amap_beiscsi_offload_params,
1365                       first_burst_length) / 32]);
1366         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, erl, pwrb,
1367                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1368                       erl) / 32] & OFFLD_PARAMS_ERL));
1369         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, dde, pwrb,
1370                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1371                        dde) / 32] & OFFLD_PARAMS_DDE) >> 2);
1372         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, hde, pwrb,
1373                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1374                       hde) / 32] & OFFLD_PARAMS_HDE) >> 3);
1375         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, ir2t, pwrb,
1376                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1377                       ir2t) / 32] & OFFLD_PARAMS_IR2T) >> 4);
1378         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, imd, pwrb,
1379                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1380                       imd) / 32] & OFFLD_PARAMS_IMD) >> 5);
1381         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, stat_sn,
1382                       pwrb,
1383                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1384                       exp_statsn) / 32] + 1));
1385         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, wrb_idx,
1386                       pwrb, pwrb_handle->wrb_index);
1387
1388         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb,
1389                       max_burst_length, pwrb, params->dw[offsetof
1390                       (struct amap_beiscsi_offload_params,
1391                       max_burst_length) / 32]);
1392
1393         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, ptr2nextwrb,
1394                       pwrb, pwrb_handle->wrb_index);
1395         if (pwrb_context->plast_wrb)
1396                 AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb,
1397                               ptr2nextwrb,
1398                               pwrb_context->plast_wrb,
1399                               pwrb_handle->wrb_index);
1400         pwrb_context->plast_wrb = pwrb;
1401
1402         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb,
1403                       session_state, pwrb, 0);
1404         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, compltonack,
1405                       pwrb, 1);
1406         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, notpredblq,
1407                       pwrb, 0);
1408         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, mode, pwrb,
1409                       0);
1410
1411         mem_descr += ISCSI_MEM_GLOBAL_HEADER;
1412         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb,
1413                       pad_buffer_addr_hi, pwrb,
1414                       mem_descr->mem_array[0].bus_address.u.a32.address_hi);
1415         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb,
1416                       pad_buffer_addr_lo, pwrb,
1417                       mem_descr->mem_array[0].bus_address.u.a32.address_lo);
1418 }
1419
1420 void beiscsi_offload_cxn_v2(struct beiscsi_offload_params *params,
1421                              struct wrb_handle *pwrb_handle,
1422                              struct hwi_wrb_context *pwrb_context)
1423 {
1424         struct iscsi_wrb *pwrb = pwrb_handle->pwrb;
1425
1426         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1427                       max_burst_length, pwrb, params->dw[offsetof
1428                       (struct amap_beiscsi_offload_params,
1429                       max_burst_length) / 32]);
1430         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1431                       type, pwrb,
1432                       BE_TGT_CTX_UPDT_CMD);
1433         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1434                       ptr2nextwrb,
1435                       pwrb, pwrb_handle->wrb_index);
1436         if (pwrb_context->plast_wrb)
1437                 AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1438                               ptr2nextwrb,
1439                               pwrb_context->plast_wrb,
1440                               pwrb_handle->wrb_index);
1441         pwrb_context->plast_wrb = pwrb;
1442
1443         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2, wrb_idx,
1444                       pwrb, pwrb_handle->wrb_index);
1445         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1446                       max_send_data_segment_length, pwrb,
1447                       params->dw[offsetof(struct amap_beiscsi_offload_params,
1448                       max_send_data_segment_length) / 32]);
1449         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1450                       first_burst_length, pwrb,
1451                       params->dw[offsetof(struct amap_beiscsi_offload_params,
1452                       first_burst_length) / 32]);
1453         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1454                       max_recv_dataseg_len, pwrb,
1455                       params->dw[offsetof(struct amap_beiscsi_offload_params,
1456                       max_recv_data_segment_length) / 32]);
1457         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1458                       max_cxns, pwrb, BEISCSI_MAX_CXNS);
1459         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2, erl, pwrb,
1460                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1461                       erl) / 32] & OFFLD_PARAMS_ERL));
1462         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2, dde, pwrb,
1463                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1464                       dde) / 32] & OFFLD_PARAMS_DDE) >> 2);
1465         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2, hde, pwrb,
1466                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1467                       hde) / 32] & OFFLD_PARAMS_HDE) >> 3);
1468         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1469                       ir2t, pwrb,
1470                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1471                       ir2t) / 32] & OFFLD_PARAMS_IR2T) >> 4);
1472         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2, imd, pwrb,
1473                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1474                       imd) / 32] & OFFLD_PARAMS_IMD) >> 5);
1475         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1476                       data_seq_inorder,
1477                       pwrb,
1478                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1479                       data_seq_inorder) / 32] &
1480                       OFFLD_PARAMS_DATA_SEQ_INORDER) >> 6);
1481         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2,
1482                       pdu_seq_inorder,
1483                       pwrb,
1484                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1485                       pdu_seq_inorder) / 32] &
1486                       OFFLD_PARAMS_PDU_SEQ_INORDER) >> 7);
1487         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2, max_r2t,
1488                       pwrb,
1489                       (params->dw[offsetof(struct amap_beiscsi_offload_params,
1490                       max_r2t) / 32] &
1491                       OFFLD_PARAMS_MAX_R2T) >> 8);
1492         AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb_v2, stat_sn,
1493                       pwrb,
1494                      (params->dw[offsetof(struct amap_beiscsi_offload_params,
1495                       exp_statsn) / 32] + 1));
1496 }