aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/ethernet/qlogic/qlcnic/qlcnic_ctx.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/net/ethernet/qlogic/qlcnic/qlcnic_ctx.c')
-rw-r--r--drivers/net/ethernet/qlogic/qlcnic/qlcnic_ctx.c727
1 files changed, 383 insertions, 344 deletions
diff --git a/drivers/net/ethernet/qlogic/qlcnic/qlcnic_ctx.c b/drivers/net/ethernet/qlogic/qlcnic/qlcnic_ctx.c
index b14b8f0787ea..a69097c6b84d 100644
--- a/drivers/net/ethernet/qlogic/qlcnic/qlcnic_ctx.c
+++ b/drivers/net/ethernet/qlogic/qlcnic/qlcnic_ctx.c
@@ -1,12 +1,92 @@
1/* 1/*
2 * QLogic qlcnic NIC Driver 2 * QLogic qlcnic NIC Driver
3 * Copyright (c) 2009-2010 QLogic Corporation 3 * Copyright (c) 2009-2013 QLogic Corporation
4 * 4 *
5 * See LICENSE.qlcnic for copyright and licensing details. 5 * See LICENSE.qlcnic for copyright and licensing details.
6 */ 6 */
7 7
8#include "qlcnic.h" 8#include "qlcnic.h"
9 9
10static const struct qlcnic_mailbox_metadata qlcnic_mbx_tbl[] = {
11 {QLCNIC_CMD_CREATE_RX_CTX, 4, 1},
12 {QLCNIC_CMD_DESTROY_RX_CTX, 2, 1},
13 {QLCNIC_CMD_CREATE_TX_CTX, 4, 1},
14 {QLCNIC_CMD_DESTROY_TX_CTX, 2, 1},
15 {QLCNIC_CMD_INTRPT_TEST, 4, 1},
16 {QLCNIC_CMD_SET_MTU, 4, 1},
17 {QLCNIC_CMD_READ_PHY, 4, 2},
18 {QLCNIC_CMD_WRITE_PHY, 5, 1},
19 {QLCNIC_CMD_READ_HW_REG, 4, 1},
20 {QLCNIC_CMD_GET_FLOW_CTL, 4, 2},
21 {QLCNIC_CMD_SET_FLOW_CTL, 4, 1},
22 {QLCNIC_CMD_READ_MAX_MTU, 4, 2},
23 {QLCNIC_CMD_READ_MAX_LRO, 4, 2},
24 {QLCNIC_CMD_MAC_ADDRESS, 4, 3},
25 {QLCNIC_CMD_GET_PCI_INFO, 4, 1},
26 {QLCNIC_CMD_GET_NIC_INFO, 4, 1},
27 {QLCNIC_CMD_SET_NIC_INFO, 4, 1},
28 {QLCNIC_CMD_GET_ESWITCH_CAPABILITY, 4, 3},
29 {QLCNIC_CMD_TOGGLE_ESWITCH, 4, 1},
30 {QLCNIC_CMD_GET_ESWITCH_STATUS, 4, 3},
31 {QLCNIC_CMD_SET_PORTMIRRORING, 4, 1},
32 {QLCNIC_CMD_CONFIGURE_ESWITCH, 4, 1},
33 {QLCNIC_CMD_GET_MAC_STATS, 4, 1},
34 {QLCNIC_CMD_GET_ESWITCH_PORT_CONFIG, 4, 3},
35 {QLCNIC_CMD_GET_ESWITCH_STATS, 5, 1},
36 {QLCNIC_CMD_CONFIG_PORT, 4, 1},
37 {QLCNIC_CMD_TEMP_SIZE, 4, 4},
38 {QLCNIC_CMD_GET_TEMP_HDR, 4, 1},
39 {QLCNIC_CMD_SET_DRV_VER, 4, 1},
40};
41
42static inline u32 qlcnic_get_cmd_signature(struct qlcnic_hardware_context *ahw)
43{
44 return (ahw->pci_func & 0xff) | ((ahw->fw_hal_version & 0xff) << 8) |
45 (0xcafe << 16);
46}
47
48/* Allocate mailbox registers */
49int qlcnic_82xx_alloc_mbx_args(struct qlcnic_cmd_args *mbx,
50 struct qlcnic_adapter *adapter, u32 type)
51{
52 int i, size;
53 const struct qlcnic_mailbox_metadata *mbx_tbl;
54
55 mbx_tbl = qlcnic_mbx_tbl;
56 size = ARRAY_SIZE(qlcnic_mbx_tbl);
57 for (i = 0; i < size; i++) {
58 if (type == mbx_tbl[i].cmd) {
59 mbx->req.num = mbx_tbl[i].in_args;
60 mbx->rsp.num = mbx_tbl[i].out_args;
61 mbx->req.arg = kcalloc(mbx->req.num,
62 sizeof(u32), GFP_ATOMIC);
63 if (!mbx->req.arg)
64 return -ENOMEM;
65 mbx->rsp.arg = kcalloc(mbx->rsp.num,
66 sizeof(u32), GFP_ATOMIC);
67 if (!mbx->rsp.arg) {
68 kfree(mbx->req.arg);
69 mbx->req.arg = NULL;
70 return -ENOMEM;
71 }
72 memset(mbx->req.arg, 0, sizeof(u32) * mbx->req.num);
73 memset(mbx->rsp.arg, 0, sizeof(u32) * mbx->rsp.num);
74 mbx->req.arg[0] = type;
75 break;
76 }
77 }
78 return 0;
79}
80
81/* Free up mailbox registers */
82void qlcnic_free_mbx_args(struct qlcnic_cmd_args *cmd)
83{
84 kfree(cmd->req.arg);
85 cmd->req.arg = NULL;
86 kfree(cmd->rsp.arg);
87 cmd->rsp.arg = NULL;
88}
89
10static int qlcnic_is_valid_nic_func(struct qlcnic_adapter *adapter, u8 pci_func) 90static int qlcnic_is_valid_nic_func(struct qlcnic_adapter *adapter, u8 pci_func)
11{ 91{
12 int i; 92 int i;
@@ -38,194 +118,123 @@ qlcnic_poll_rsp(struct qlcnic_adapter *adapter)
38 return rsp; 118 return rsp;
39} 119}
40 120
41void 121int qlcnic_82xx_issue_cmd(struct qlcnic_adapter *adapter,
42qlcnic_issue_cmd(struct qlcnic_adapter *adapter, struct qlcnic_cmd_args *cmd) 122 struct qlcnic_cmd_args *cmd)
43{ 123{
124 int i;
44 u32 rsp; 125 u32 rsp;
45 u32 signature; 126 u32 signature;
46 struct pci_dev *pdev = adapter->pdev; 127 struct pci_dev *pdev = adapter->pdev;
47 struct qlcnic_hardware_context *ahw = adapter->ahw; 128 struct qlcnic_hardware_context *ahw = adapter->ahw;
129 const char *fmt;
48 130
49 signature = QLCNIC_CDRP_SIGNATURE_MAKE(ahw->pci_func, 131 signature = qlcnic_get_cmd_signature(ahw);
50 adapter->ahw->fw_hal_version);
51 132
52 /* Acquire semaphore before accessing CRB */ 133 /* Acquire semaphore before accessing CRB */
53 if (qlcnic_api_lock(adapter)) { 134 if (qlcnic_api_lock(adapter)) {
54 cmd->rsp.cmd = QLCNIC_RCODE_TIMEOUT; 135 cmd->rsp.arg[0] = QLCNIC_RCODE_TIMEOUT;
55 return; 136 return cmd->rsp.arg[0];
56 } 137 }
57 138
58 QLCWR32(adapter, QLCNIC_SIGN_CRB_OFFSET, signature); 139 QLCWR32(adapter, QLCNIC_SIGN_CRB_OFFSET, signature);
59 QLCWR32(adapter, QLCNIC_ARG1_CRB_OFFSET, cmd->req.arg1); 140 for (i = 1; i < QLCNIC_CDRP_MAX_ARGS; i++)
60 QLCWR32(adapter, QLCNIC_ARG2_CRB_OFFSET, cmd->req.arg2); 141 QLCWR32(adapter, QLCNIC_CDRP_ARG(i), cmd->req.arg[i]);
61 QLCWR32(adapter, QLCNIC_ARG3_CRB_OFFSET, cmd->req.arg3);
62 QLCWR32(adapter, QLCNIC_CDRP_CRB_OFFSET, 142 QLCWR32(adapter, QLCNIC_CDRP_CRB_OFFSET,
63 QLCNIC_CDRP_FORM_CMD(cmd->req.cmd)); 143 QLCNIC_CDRP_FORM_CMD(cmd->req.arg[0]));
64
65 rsp = qlcnic_poll_rsp(adapter); 144 rsp = qlcnic_poll_rsp(adapter);
66 145
67 if (rsp == QLCNIC_CDRP_RSP_TIMEOUT) { 146 if (rsp == QLCNIC_CDRP_RSP_TIMEOUT) {
68 dev_err(&pdev->dev, "CDRP response timeout.\n"); 147 dev_err(&pdev->dev, "card response timeout.\n");
69 cmd->rsp.cmd = QLCNIC_RCODE_TIMEOUT; 148 cmd->rsp.arg[0] = QLCNIC_RCODE_TIMEOUT;
70 } else if (rsp == QLCNIC_CDRP_RSP_FAIL) { 149 } else if (rsp == QLCNIC_CDRP_RSP_FAIL) {
71 cmd->rsp.cmd = QLCRD32(adapter, QLCNIC_ARG1_CRB_OFFSET); 150 cmd->rsp.arg[0] = QLCRD32(adapter, QLCNIC_CDRP_ARG(1));
72 switch (cmd->rsp.cmd) { 151 switch (cmd->rsp.arg[0]) {
73 case QLCNIC_RCODE_INVALID_ARGS: 152 case QLCNIC_RCODE_INVALID_ARGS:
74 dev_err(&pdev->dev, "CDRP invalid args: 0x%x.\n", 153 fmt = "CDRP invalid args: [%d]\n";
75 cmd->rsp.cmd);
76 break; 154 break;
77 case QLCNIC_RCODE_NOT_SUPPORTED: 155 case QLCNIC_RCODE_NOT_SUPPORTED:
78 case QLCNIC_RCODE_NOT_IMPL: 156 case QLCNIC_RCODE_NOT_IMPL:
79 dev_err(&pdev->dev, 157 fmt = "CDRP command not supported: [%d]\n";
80 "CDRP command not supported: 0x%x.\n",
81 cmd->rsp.cmd);
82 break; 158 break;
83 case QLCNIC_RCODE_NOT_PERMITTED: 159 case QLCNIC_RCODE_NOT_PERMITTED:
84 dev_err(&pdev->dev, 160 fmt = "CDRP requested action not permitted: [%d]\n";
85 "CDRP requested action not permitted: 0x%x.\n",
86 cmd->rsp.cmd);
87 break; 161 break;
88 case QLCNIC_RCODE_INVALID: 162 case QLCNIC_RCODE_INVALID:
89 dev_err(&pdev->dev, 163 fmt = "CDRP invalid or unknown cmd received: [%d]\n";
90 "CDRP invalid or unknown cmd received: 0x%x.\n",
91 cmd->rsp.cmd);
92 break; 164 break;
93 case QLCNIC_RCODE_TIMEOUT: 165 case QLCNIC_RCODE_TIMEOUT:
94 dev_err(&pdev->dev, "CDRP command timeout: 0x%x.\n", 166 fmt = "CDRP command timeout: [%d]\n";
95 cmd->rsp.cmd);
96 break; 167 break;
97 default: 168 default:
98 dev_err(&pdev->dev, "CDRP command failed: 0x%x.\n", 169 fmt = "CDRP command failed: [%d]\n";
99 cmd->rsp.cmd); 170 break;
100 } 171 }
101 } else if (rsp == QLCNIC_CDRP_RSP_OK) { 172 dev_err(&pdev->dev, fmt, cmd->rsp.arg[0]);
102 cmd->rsp.cmd = QLCNIC_RCODE_SUCCESS; 173 } else if (rsp == QLCNIC_CDRP_RSP_OK)
103 if (cmd->rsp.arg2) 174 cmd->rsp.arg[0] = QLCNIC_RCODE_SUCCESS;
104 cmd->rsp.arg2 = QLCRD32(adapter, 175
105 QLCNIC_ARG2_CRB_OFFSET); 176 for (i = 1; i < cmd->rsp.num; i++)
106 if (cmd->rsp.arg3) 177 cmd->rsp.arg[i] = QLCRD32(adapter, QLCNIC_CDRP_ARG(i));
107 cmd->rsp.arg3 = QLCRD32(adapter,
108 QLCNIC_ARG3_CRB_OFFSET);
109 }
110 if (cmd->rsp.arg1)
111 cmd->rsp.arg1 = QLCRD32(adapter, QLCNIC_ARG1_CRB_OFFSET);
112 178
113 /* Release semaphore */ 179 /* Release semaphore */
114 qlcnic_api_unlock(adapter); 180 qlcnic_api_unlock(adapter);
115 181 return cmd->rsp.arg[0];
116}
117
118static uint32_t qlcnic_temp_checksum(uint32_t *temp_buffer, u32 temp_size)
119{
120 uint64_t sum = 0;
121 int count = temp_size / sizeof(uint32_t);
122 while (count-- > 0)
123 sum += *temp_buffer++;
124 while (sum >> 32)
125 sum = (sum & 0xFFFFFFFF) + (sum >> 32);
126 return ~sum;
127} 182}
128 183
129int qlcnic_fw_cmd_get_minidump_temp(struct qlcnic_adapter *adapter) 184int qlcnic_fw_cmd_set_drv_version(struct qlcnic_adapter *adapter)
130{ 185{
131 int err, i;
132 void *tmp_addr;
133 u32 temp_size, version, csum, *template;
134 __le32 *tmp_buf;
135 struct qlcnic_cmd_args cmd; 186 struct qlcnic_cmd_args cmd;
136 struct qlcnic_hardware_context *ahw; 187 u32 arg1, arg2, arg3;
137 struct qlcnic_dump_template_hdr *tmpl_hdr; 188 char drv_string[12];
138 dma_addr_t tmp_addr_t = 0; 189 int err = 0;
139
140 ahw = adapter->ahw;
141 memset(&cmd, 0, sizeof(cmd));
142 cmd.req.cmd = QLCNIC_CDRP_CMD_TEMP_SIZE;
143 memset(&cmd.rsp, 1, sizeof(struct _cdrp_cmd));
144 qlcnic_issue_cmd(adapter, &cmd);
145 if (cmd.rsp.cmd != QLCNIC_RCODE_SUCCESS) {
146 dev_info(&adapter->pdev->dev,
147 "Can't get template size %d\n", cmd.rsp.cmd);
148 err = -EIO;
149 return err;
150 }
151 temp_size = cmd.rsp.arg2;
152 version = cmd.rsp.arg3;
153 dev_info(&adapter->pdev->dev,
154 "minidump template version = 0x%x", version);
155 if (!temp_size)
156 return -EIO;
157 190
158 tmp_addr = dma_alloc_coherent(&adapter->pdev->dev, temp_size, 191 memset(drv_string, 0, sizeof(drv_string));
159 &tmp_addr_t, GFP_KERNEL); 192 snprintf(drv_string, sizeof(drv_string), "%d"".""%d"".""%d",
160 if (!tmp_addr) { 193 _QLCNIC_LINUX_MAJOR, _QLCNIC_LINUX_MINOR,
161 dev_err(&adapter->pdev->dev, 194 _QLCNIC_LINUX_SUBVERSION);
162 "Can't get memory for FW dump template\n");
163 return -ENOMEM;
164 }
165 memset(&cmd.rsp, 0, sizeof(struct _cdrp_cmd));
166 cmd.req.cmd = QLCNIC_CDRP_CMD_GET_TEMP_HDR;
167 cmd.req.arg1 = LSD(tmp_addr_t);
168 cmd.req.arg2 = MSD(tmp_addr_t);
169 cmd.req.arg3 = temp_size;
170 qlcnic_issue_cmd(adapter, &cmd);
171
172 err = cmd.rsp.cmd;
173 if (err != QLCNIC_RCODE_SUCCESS) {
174 dev_err(&adapter->pdev->dev,
175 "Failed to get mini dump template header %d\n", err);
176 err = -EIO;
177 goto error;
178 }
179 ahw->fw_dump.tmpl_hdr = vzalloc(temp_size);
180 if (!ahw->fw_dump.tmpl_hdr) {
181 err = -EIO;
182 goto error;
183 }
184 tmp_buf = tmp_addr;
185 template = (u32 *) ahw->fw_dump.tmpl_hdr;
186 for (i = 0; i < temp_size/sizeof(u32); i++)
187 *template++ = __le32_to_cpu(*tmp_buf++);
188 195
189 csum = qlcnic_temp_checksum((u32 *)ahw->fw_dump.tmpl_hdr, temp_size); 196 qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_SET_DRV_VER);
190 if (csum) { 197 memcpy(&arg1, drv_string, sizeof(u32));
191 dev_err(&adapter->pdev->dev, 198 memcpy(&arg2, drv_string + 4, sizeof(u32));
192 "Template header checksum validation failed\n"); 199 memcpy(&arg3, drv_string + 8, sizeof(u32));
193 err = -EIO; 200
194 goto error; 201 cmd.req.arg[1] = arg1;
202 cmd.req.arg[2] = arg2;
203 cmd.req.arg[3] = arg3;
204
205 err = qlcnic_issue_cmd(adapter, &cmd);
206 if (err) {
207 dev_info(&adapter->pdev->dev,
208 "Failed to set driver version in firmware\n");
209 return -EIO;
195 } 210 }
196 211
197 tmpl_hdr = ahw->fw_dump.tmpl_hdr; 212 return 0;
198 tmpl_hdr->drv_cap_mask = QLCNIC_DUMP_MASK_DEF;
199 ahw->fw_dump.enable = 1;
200error:
201 dma_free_coherent(&adapter->pdev->dev, temp_size, tmp_addr, tmp_addr_t);
202 return err;
203} 213}
204 214
205int 215int
206qlcnic_fw_cmd_set_mtu(struct qlcnic_adapter *adapter, int mtu) 216qlcnic_fw_cmd_set_mtu(struct qlcnic_adapter *adapter, int mtu)
207{ 217{
218 int err = 0;
208 struct qlcnic_cmd_args cmd; 219 struct qlcnic_cmd_args cmd;
209 struct qlcnic_recv_context *recv_ctx = adapter->recv_ctx; 220 struct qlcnic_recv_context *recv_ctx = adapter->recv_ctx;
210 221
211 memset(&cmd, 0, sizeof(cmd)); 222 if (recv_ctx->state != QLCNIC_HOST_CTX_STATE_ACTIVE)
212 cmd.req.cmd = QLCNIC_CDRP_CMD_SET_MTU; 223 return err;
213 cmd.req.arg1 = recv_ctx->context_id; 224 qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_SET_MTU);
214 cmd.req.arg2 = mtu; 225 cmd.req.arg[1] = recv_ctx->context_id;
215 cmd.req.arg3 = 0; 226 cmd.req.arg[2] = mtu;
216 if (recv_ctx->state == QLCNIC_HOST_CTX_STATE_ACTIVE) {
217 qlcnic_issue_cmd(adapter, &cmd);
218 if (cmd.rsp.cmd) {
219 dev_err(&adapter->pdev->dev, "Failed to set mtu\n");
220 return -EIO;
221 }
222 }
223 227
224 return 0; 228 err = qlcnic_issue_cmd(adapter, &cmd);
229 if (err) {
230 dev_err(&adapter->pdev->dev, "Failed to set mtu\n");
231 err = -EIO;
232 }
233 qlcnic_free_mbx_args(&cmd);
234 return err;
225} 235}
226 236
227static int 237int qlcnic_82xx_fw_cmd_create_rx_ctx(struct qlcnic_adapter *adapter)
228qlcnic_fw_cmd_create_rx_ctx(struct qlcnic_adapter *adapter)
229{ 238{
230 void *addr; 239 void *addr;
231 struct qlcnic_hostrq_rx_ctx *prq; 240 struct qlcnic_hostrq_rx_ctx *prq;
@@ -242,10 +251,10 @@ qlcnic_fw_cmd_create_rx_ctx(struct qlcnic_adapter *adapter)
242 u64 phys_addr; 251 u64 phys_addr;
243 252
244 u8 i, nrds_rings, nsds_rings; 253 u8 i, nrds_rings, nsds_rings;
254 u16 temp_u16;
245 size_t rq_size, rsp_size; 255 size_t rq_size, rsp_size;
246 u32 cap, reg, val, reg2; 256 u32 cap, reg, val, reg2;
247 int err; 257 int err;
248 u16 temp;
249 258
250 struct qlcnic_recv_context *recv_ctx = adapter->recv_ctx; 259 struct qlcnic_recv_context *recv_ctx = adapter->recv_ctx;
251 260
@@ -279,11 +288,8 @@ qlcnic_fw_cmd_create_rx_ctx(struct qlcnic_adapter *adapter)
279 | QLCNIC_CAP0_VALIDOFF); 288 | QLCNIC_CAP0_VALIDOFF);
280 cap |= (QLCNIC_CAP0_JUMBO_CONTIGUOUS | QLCNIC_CAP0_LRO_CONTIGUOUS); 289 cap |= (QLCNIC_CAP0_JUMBO_CONTIGUOUS | QLCNIC_CAP0_LRO_CONTIGUOUS);
281 290
282 if (adapter->flags & QLCNIC_FW_LRO_MSS_CAP) 291 temp_u16 = offsetof(struct qlcnic_hostrq_rx_ctx, msix_handler);
283 cap |= QLCNIC_CAP0_LRO_MSS; 292 prq->valid_field_offset = cpu_to_le16(temp_u16);
284
285 temp = offsetof(struct qlcnic_hostrq_rx_ctx, msix_handler);
286 prq->valid_field_offset = cpu_to_le16(temp);
287 prq->txrx_sds_binding = nsds_rings - 1; 293 prq->txrx_sds_binding = nsds_rings - 1;
288 294
289 prq->capabilities[0] = cpu_to_le32(cap); 295 prq->capabilities[0] = cpu_to_le32(cap);
@@ -329,20 +335,17 @@ qlcnic_fw_cmd_create_rx_ctx(struct qlcnic_adapter *adapter)
329 } 335 }
330 336
331 phys_addr = hostrq_phys_addr; 337 phys_addr = hostrq_phys_addr;
332 memset(&cmd, 0, sizeof(cmd)); 338 qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_CREATE_RX_CTX);
333 cmd.req.arg1 = (u32) (phys_addr >> 32); 339 cmd.req.arg[1] = MSD(phys_addr);
334 cmd.req.arg2 = (u32) (phys_addr & 0xffffffff); 340 cmd.req.arg[2] = LSD(phys_addr);
335 cmd.req.arg3 = rq_size; 341 cmd.req.arg[3] = rq_size;
336 cmd.req.cmd = QLCNIC_CDRP_CMD_CREATE_RX_CTX; 342 err = qlcnic_issue_cmd(adapter, &cmd);
337 qlcnic_issue_cmd(adapter, &cmd);
338 err = cmd.rsp.cmd;
339 if (err) { 343 if (err) {
340 dev_err(&adapter->pdev->dev, 344 dev_err(&adapter->pdev->dev,
341 "Failed to create rx ctx in firmware%d\n", err); 345 "Failed to create rx ctx in firmware%d\n", err);
342 goto out_free_rsp; 346 goto out_free_rsp;
343 } 347 }
344 348
345
346 prsp_rds = ((struct qlcnic_cardrsp_rds_ring *) 349 prsp_rds = ((struct qlcnic_cardrsp_rds_ring *)
347 &prsp->data[le32_to_cpu(prsp->rds_ring_offset)]); 350 &prsp->data[le32_to_cpu(prsp->rds_ring_offset)]);
348 351
@@ -373,6 +376,7 @@ qlcnic_fw_cmd_create_rx_ctx(struct qlcnic_adapter *adapter)
373out_free_rsp: 376out_free_rsp:
374 dma_free_coherent(&adapter->pdev->dev, rsp_size, prsp, 377 dma_free_coherent(&adapter->pdev->dev, rsp_size, prsp,
375 cardrsp_phys_addr); 378 cardrsp_phys_addr);
379 qlcnic_free_mbx_args(&cmd);
376out_free_rq: 380out_free_rq:
377 dma_free_coherent(&adapter->pdev->dev, rq_size, prq, hostrq_phys_addr); 381 dma_free_coherent(&adapter->pdev->dev, rq_size, prq, hostrq_phys_addr);
378 return err; 382 return err;
@@ -381,24 +385,24 @@ out_free_rq:
381static void 385static void
382qlcnic_fw_cmd_destroy_rx_ctx(struct qlcnic_adapter *adapter) 386qlcnic_fw_cmd_destroy_rx_ctx(struct qlcnic_adapter *adapter)
383{ 387{
388 int err;
384 struct qlcnic_cmd_args cmd; 389 struct qlcnic_cmd_args cmd;
385 struct qlcnic_recv_context *recv_ctx = adapter->recv_ctx; 390 struct qlcnic_recv_context *recv_ctx = adapter->recv_ctx;
386 391
387 memset(&cmd, 0, sizeof(cmd)); 392 qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_DESTROY_RX_CTX);
388 cmd.req.arg1 = recv_ctx->context_id; 393 cmd.req.arg[1] = recv_ctx->context_id;
389 cmd.req.arg2 = QLCNIC_DESTROY_CTX_RESET; 394 err = qlcnic_issue_cmd(adapter, &cmd);
390 cmd.req.arg3 = 0; 395 if (err)
391 cmd.req.cmd = QLCNIC_CDRP_CMD_DESTROY_RX_CTX;
392 qlcnic_issue_cmd(adapter, &cmd);
393 if (cmd.rsp.cmd)
394 dev_err(&adapter->pdev->dev, 396 dev_err(&adapter->pdev->dev,
395 "Failed to destroy rx ctx in firmware\n"); 397 "Failed to destroy rx ctx in firmware\n");
396 398
397 recv_ctx->state = QLCNIC_HOST_CTX_STATE_FREED; 399 recv_ctx->state = QLCNIC_HOST_CTX_STATE_FREED;
400 qlcnic_free_mbx_args(&cmd);
398} 401}
399 402
400static int 403int qlcnic_82xx_fw_cmd_create_tx_ctx(struct qlcnic_adapter *adapter,
401qlcnic_fw_cmd_create_tx_ctx(struct qlcnic_adapter *adapter) 404 struct qlcnic_host_tx_ring *tx_ring,
405 int ring)
402{ 406{
403 struct qlcnic_hostrq_tx_ctx *prq; 407 struct qlcnic_hostrq_tx_ctx *prq;
404 struct qlcnic_hostrq_cds_ring *prq_cds; 408 struct qlcnic_hostrq_cds_ring *prq_cds;
@@ -410,7 +414,6 @@ qlcnic_fw_cmd_create_tx_ctx(struct qlcnic_adapter *adapter)
410 int err; 414 int err;
411 u64 phys_addr; 415 u64 phys_addr;
412 dma_addr_t rq_phys_addr, rsp_phys_addr; 416 dma_addr_t rq_phys_addr, rsp_phys_addr;
413 struct qlcnic_host_tx_ring *tx_ring = adapter->tx_ring;
414 417
415 /* reset host resources */ 418 /* reset host resources */
416 tx_ring->producer = 0; 419 tx_ring->producer = 0;
@@ -445,9 +448,9 @@ qlcnic_fw_cmd_create_tx_ctx(struct qlcnic_adapter *adapter)
445 448
446 prq->host_int_crb_mode = 449 prq->host_int_crb_mode =
447 cpu_to_le32(QLCNIC_HOST_INT_CRB_MODE_SHARED); 450 cpu_to_le32(QLCNIC_HOST_INT_CRB_MODE_SHARED);
451 prq->msi_index = 0;
448 452
449 prq->interrupt_ctl = 0; 453 prq->interrupt_ctl = 0;
450 prq->msi_index = 0;
451 prq->cmd_cons_dma_addr = cpu_to_le64(tx_ring->hw_cons_phys_addr); 454 prq->cmd_cons_dma_addr = cpu_to_le64(tx_ring->hw_cons_phys_addr);
452 455
453 prq_cds = &prq->cds_ring; 456 prq_cds = &prq->cds_ring;
@@ -456,19 +459,17 @@ qlcnic_fw_cmd_create_tx_ctx(struct qlcnic_adapter *adapter)
456 prq_cds->ring_size = cpu_to_le32(tx_ring->num_desc); 459 prq_cds->ring_size = cpu_to_le32(tx_ring->num_desc);
457 460
458 phys_addr = rq_phys_addr; 461 phys_addr = rq_phys_addr;
459 memset(&cmd, 0, sizeof(cmd)); 462
460 cmd.req.arg1 = (u32)(phys_addr >> 32); 463 qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_CREATE_TX_CTX);
461 cmd.req.arg2 = ((u32)phys_addr & 0xffffffff); 464 cmd.req.arg[1] = MSD(phys_addr);
462 cmd.req.arg3 = rq_size; 465 cmd.req.arg[2] = LSD(phys_addr);
463 cmd.req.cmd = QLCNIC_CDRP_CMD_CREATE_TX_CTX; 466 cmd.req.arg[3] = rq_size;
464 qlcnic_issue_cmd(adapter, &cmd); 467 err = qlcnic_issue_cmd(adapter, &cmd);
465 err = cmd.rsp.cmd;
466 468
467 if (err == QLCNIC_RCODE_SUCCESS) { 469 if (err == QLCNIC_RCODE_SUCCESS) {
468 temp = le32_to_cpu(prsp->cds_ring.host_producer_crb); 470 temp = le32_to_cpu(prsp->cds_ring.host_producer_crb);
469 tx_ring->crb_cmd_producer = adapter->ahw->pci_base0 + temp; 471 tx_ring->crb_cmd_producer = adapter->ahw->pci_base0 + temp;
470 472 tx_ring->ctx_id = le16_to_cpu(prsp->context_id);
471 adapter->tx_ring->ctx_id = le16_to_cpu(prsp->context_id);
472 } else { 473 } else {
473 dev_err(&adapter->pdev->dev, 474 dev_err(&adapter->pdev->dev,
474 "Failed to create tx ctx in firmware%d\n", err); 475 "Failed to create tx ctx in firmware%d\n", err);
@@ -476,76 +477,81 @@ qlcnic_fw_cmd_create_tx_ctx(struct qlcnic_adapter *adapter)
476 } 477 }
477 478
478 dma_free_coherent(&adapter->pdev->dev, rsp_size, rsp_addr, 479 dma_free_coherent(&adapter->pdev->dev, rsp_size, rsp_addr,
479 rsp_phys_addr); 480 rsp_phys_addr);
480 481
481out_free_rq: 482out_free_rq:
482 dma_free_coherent(&adapter->pdev->dev, rq_size, rq_addr, rq_phys_addr); 483 dma_free_coherent(&adapter->pdev->dev, rq_size, rq_addr, rq_phys_addr);
484 qlcnic_free_mbx_args(&cmd);
483 485
484 return err; 486 return err;
485} 487}
486 488
487static void 489static void
488qlcnic_fw_cmd_destroy_tx_ctx(struct qlcnic_adapter *adapter) 490qlcnic_fw_cmd_destroy_tx_ctx(struct qlcnic_adapter *adapter,
491 struct qlcnic_host_tx_ring *tx_ring)
489{ 492{
490 struct qlcnic_cmd_args cmd; 493 struct qlcnic_cmd_args cmd;
491 494
492 memset(&cmd, 0, sizeof(cmd)); 495 qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_DESTROY_TX_CTX);
493 cmd.req.arg1 = adapter->tx_ring->ctx_id; 496 cmd.req.arg[1] = tx_ring->ctx_id;
494 cmd.req.arg2 = QLCNIC_DESTROY_CTX_RESET; 497 if (qlcnic_issue_cmd(adapter, &cmd))
495 cmd.req.arg3 = 0;
496 cmd.req.cmd = QLCNIC_CDRP_CMD_DESTROY_TX_CTX;
497 qlcnic_issue_cmd(adapter, &cmd);
498 if (cmd.rsp.cmd)
499 dev_err(&adapter->pdev->dev, 498 dev_err(&adapter->pdev->dev,
500 "Failed to destroy tx ctx in firmware\n"); 499 "Failed to destroy tx ctx in firmware\n");
500 qlcnic_free_mbx_args(&cmd);
501} 501}
502 502
503int 503int
504qlcnic_fw_cmd_set_port(struct qlcnic_adapter *adapter, u32 config) 504qlcnic_fw_cmd_set_port(struct qlcnic_adapter *adapter, u32 config)
505{ 505{
506 int err;
506 struct qlcnic_cmd_args cmd; 507 struct qlcnic_cmd_args cmd;
507 508
508 memset(&cmd, 0, sizeof(cmd)); 509 qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_CONFIG_PORT);
509 cmd.req.arg1 = config; 510 cmd.req.arg[1] = config;
510 cmd.req.cmd = QLCNIC_CDRP_CMD_CONFIG_PORT; 511 err = qlcnic_issue_cmd(adapter, &cmd);
511 qlcnic_issue_cmd(adapter, &cmd); 512 qlcnic_free_mbx_args(&cmd);
512 513 return err;
513 return cmd.rsp.cmd;
514} 514}
515 515
516int qlcnic_alloc_hw_resources(struct qlcnic_adapter *adapter) 516int qlcnic_alloc_hw_resources(struct qlcnic_adapter *adapter)
517{ 517{
518 void *addr; 518 void *addr;
519 int err; 519 int err, ring;
520 int ring;
521 struct qlcnic_recv_context *recv_ctx; 520 struct qlcnic_recv_context *recv_ctx;
522 struct qlcnic_host_rds_ring *rds_ring; 521 struct qlcnic_host_rds_ring *rds_ring;
523 struct qlcnic_host_sds_ring *sds_ring; 522 struct qlcnic_host_sds_ring *sds_ring;
524 struct qlcnic_host_tx_ring *tx_ring; 523 struct qlcnic_host_tx_ring *tx_ring;
524 __le32 *ptr;
525 525
526 struct pci_dev *pdev = adapter->pdev; 526 struct pci_dev *pdev = adapter->pdev;
527 527
528 recv_ctx = adapter->recv_ctx; 528 recv_ctx = adapter->recv_ctx;
529 tx_ring = adapter->tx_ring;
530 529
531 tx_ring->hw_consumer = (__le32 *) dma_alloc_coherent(&pdev->dev, 530 for (ring = 0; ring < adapter->max_drv_tx_rings; ring++) {
532 sizeof(u32), &tx_ring->hw_cons_phys_addr, GFP_KERNEL); 531 tx_ring = &adapter->tx_ring[ring];
533 if (tx_ring->hw_consumer == NULL) { 532 ptr = (__le32 *)dma_alloc_coherent(&pdev->dev, sizeof(u32),
534 dev_err(&pdev->dev, "failed to allocate tx consumer\n"); 533 &tx_ring->hw_cons_phys_addr,
535 return -ENOMEM; 534 GFP_KERNEL);
536 }
537 535
538 /* cmd desc ring */ 536 if (ptr == NULL) {
539 addr = dma_alloc_coherent(&pdev->dev, TX_DESC_RINGSIZE(tx_ring), 537 dev_err(&pdev->dev, "failed to allocate tx consumer\n");
540 &tx_ring->phys_addr, GFP_KERNEL); 538 return -ENOMEM;
539 }
540 tx_ring->hw_consumer = ptr;
541 /* cmd desc ring */
542 addr = dma_alloc_coherent(&pdev->dev, TX_DESC_RINGSIZE(tx_ring),
543 &tx_ring->phys_addr,
544 GFP_KERNEL);
541 545
542 if (addr == NULL) { 546 if (addr == NULL) {
543 dev_err(&pdev->dev, "failed to allocate tx desc ring\n"); 547 dev_err(&pdev->dev,
544 err = -ENOMEM; 548 "failed to allocate tx desc ring\n");
545 goto err_out_free; 549 err = -ENOMEM;
546 } 550 goto err_out_free;
551 }
547 552
548 tx_ring->desc_head = addr; 553 tx_ring->desc_head = addr;
554 }
549 555
550 for (ring = 0; ring < adapter->max_rds_rings; ring++) { 556 for (ring = 0; ring < adapter->max_rds_rings; ring++) {
551 rds_ring = &recv_ctx->rds_rings[ring]; 557 rds_ring = &recv_ctx->rds_rings[ring];
@@ -584,36 +590,70 @@ err_out_free:
584 return err; 590 return err;
585} 591}
586 592
587 593int qlcnic_fw_create_ctx(struct qlcnic_adapter *dev)
588int qlcnic_fw_create_ctx(struct qlcnic_adapter *adapter)
589{ 594{
590 int err; 595 int i, err, ring;
591 596
592 if (adapter->flags & QLCNIC_NEED_FLR) { 597 if (dev->flags & QLCNIC_NEED_FLR) {
593 pci_reset_function(adapter->pdev); 598 pci_reset_function(dev->pdev);
594 adapter->flags &= ~QLCNIC_NEED_FLR; 599 dev->flags &= ~QLCNIC_NEED_FLR;
595 } 600 }
596 601
597 err = qlcnic_fw_cmd_create_rx_ctx(adapter); 602 if (qlcnic_83xx_check(dev) && (dev->flags & QLCNIC_MSIX_ENABLED)) {
598 if (err) 603 if (dev->ahw->diag_test != QLCNIC_LOOPBACK_TEST) {
599 return err; 604 err = qlcnic_83xx_config_intrpt(dev, 1);
605 if (err)
606 return err;
607 }
608 }
600 609
601 err = qlcnic_fw_cmd_create_tx_ctx(adapter); 610 err = qlcnic_fw_cmd_create_rx_ctx(dev);
602 if (err) { 611 if (err)
603 qlcnic_fw_cmd_destroy_rx_ctx(adapter); 612 goto err_out;
604 return err; 613
614 for (ring = 0; ring < dev->max_drv_tx_rings; ring++) {
615 err = qlcnic_fw_cmd_create_tx_ctx(dev,
616 &dev->tx_ring[ring],
617 ring);
618 if (err) {
619 qlcnic_fw_cmd_destroy_rx_ctx(dev);
620 if (ring == 0)
621 goto err_out;
622
623 for (i = 0; i < ring; i++)
624 qlcnic_fw_cmd_destroy_tx_ctx(dev,
625 &dev->tx_ring[i]);
626
627 goto err_out;
628 }
605 } 629 }
606 630
607 set_bit(__QLCNIC_FW_ATTACHED, &adapter->state); 631 set_bit(__QLCNIC_FW_ATTACHED, &dev->state);
608 return 0; 632 return 0;
633
634err_out:
635 if (qlcnic_83xx_check(dev) && (dev->flags & QLCNIC_MSIX_ENABLED)) {
636 if (dev->ahw->diag_test != QLCNIC_LOOPBACK_TEST)
637 qlcnic_83xx_config_intrpt(dev, 0);
638 }
639 return err;
609} 640}
610 641
611void qlcnic_fw_destroy_ctx(struct qlcnic_adapter *adapter) 642void qlcnic_fw_destroy_ctx(struct qlcnic_adapter *adapter)
612{ 643{
644 int ring;
645
613 if (test_and_clear_bit(__QLCNIC_FW_ATTACHED, &adapter->state)) { 646 if (test_and_clear_bit(__QLCNIC_FW_ATTACHED, &adapter->state)) {
614 qlcnic_fw_cmd_destroy_rx_ctx(adapter); 647 qlcnic_fw_cmd_destroy_rx_ctx(adapter);
615 qlcnic_fw_cmd_destroy_tx_ctx(adapter); 648 for (ring = 0; ring < adapter->max_drv_tx_rings; ring++)
616 649 qlcnic_fw_cmd_destroy_tx_ctx(adapter,
650 &adapter->tx_ring[ring]);
651
652 if (qlcnic_83xx_check(adapter) &&
653 (adapter->flags & QLCNIC_MSIX_ENABLED)) {
654 if (adapter->ahw->diag_test != QLCNIC_LOOPBACK_TEST)
655 qlcnic_83xx_config_intrpt(adapter, 0);
656 }
617 /* Allow dma queues to drain after context reset */ 657 /* Allow dma queues to drain after context reset */
618 mdelay(20); 658 mdelay(20);
619 } 659 }
@@ -629,20 +669,23 @@ void qlcnic_free_hw_resources(struct qlcnic_adapter *adapter)
629 669
630 recv_ctx = adapter->recv_ctx; 670 recv_ctx = adapter->recv_ctx;
631 671
632 tx_ring = adapter->tx_ring; 672 for (ring = 0; ring < adapter->max_drv_tx_rings; ring++) {
633 if (tx_ring->hw_consumer != NULL) { 673 tx_ring = &adapter->tx_ring[ring];
634 dma_free_coherent(&adapter->pdev->dev, 674 if (tx_ring->hw_consumer != NULL) {
635 sizeof(u32), 675 dma_free_coherent(&adapter->pdev->dev, sizeof(u32),
636 tx_ring->hw_consumer, 676 tx_ring->hw_consumer,
637 tx_ring->hw_cons_phys_addr); 677 tx_ring->hw_cons_phys_addr);
638 tx_ring->hw_consumer = NULL;
639 }
640 678
641 if (tx_ring->desc_head != NULL) { 679 tx_ring->hw_consumer = NULL;
642 dma_free_coherent(&adapter->pdev->dev, 680 }
643 TX_DESC_RINGSIZE(tx_ring), 681
644 tx_ring->desc_head, tx_ring->phys_addr); 682 if (tx_ring->desc_head != NULL) {
645 tx_ring->desc_head = NULL; 683 dma_free_coherent(&adapter->pdev->dev,
684 TX_DESC_RINGSIZE(tx_ring),
685 tx_ring->desc_head,
686 tx_ring->phys_addr);
687 tx_ring->desc_head = NULL;
688 }
646 } 689 }
647 690
648 for (ring = 0; ring < adapter->max_rds_rings; ring++) { 691 for (ring = 0; ring < adapter->max_rds_rings; ring++) {
@@ -671,40 +714,43 @@ void qlcnic_free_hw_resources(struct qlcnic_adapter *adapter)
671} 714}
672 715
673 716
674/* Get MAC address of a NIC partition */ 717int qlcnic_82xx_get_mac_address(struct qlcnic_adapter *adapter, u8 *mac)
675int qlcnic_get_mac_address(struct qlcnic_adapter *adapter, u8 *mac)
676{ 718{
677 int err; 719 int err, i;
678 struct qlcnic_cmd_args cmd; 720 struct qlcnic_cmd_args cmd;
721 u32 mac_low, mac_high;
679 722
680 memset(&cmd, 0, sizeof(cmd)); 723 qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_MAC_ADDRESS);
681 cmd.req.arg1 = adapter->ahw->pci_func | BIT_8; 724 cmd.req.arg[1] = adapter->ahw->pci_func | BIT_8;
682 cmd.req.cmd = QLCNIC_CDRP_CMD_MAC_ADDRESS; 725 err = qlcnic_issue_cmd(adapter, &cmd);
683 cmd.rsp.arg1 = cmd.rsp.arg2 = 1;
684 qlcnic_issue_cmd(adapter, &cmd);
685 err = cmd.rsp.cmd;
686 726
687 if (err == QLCNIC_RCODE_SUCCESS) 727 if (err == QLCNIC_RCODE_SUCCESS) {
688 qlcnic_fetch_mac(cmd.rsp.arg1, cmd.rsp.arg2, 0, mac); 728 mac_low = cmd.rsp.arg[1];
689 else { 729 mac_high = cmd.rsp.arg[2];
730
731 for (i = 0; i < 2; i++)
732 mac[i] = (u8) (mac_high >> ((1 - i) * 8));
733 for (i = 2; i < 6; i++)
734 mac[i] = (u8) (mac_low >> ((5 - i) * 8));
735 } else {
690 dev_err(&adapter->pdev->dev, 736 dev_err(&adapter->pdev->dev,
691 "Failed to get mac address%d\n", err); 737 "Failed to get mac address%d\n", err);
692 err = -EIO; 738 err = -EIO;
693 } 739 }
694 740 qlcnic_free_mbx_args(&cmd);
695 return err; 741 return err;
696} 742}
697 743
698/* Get info of a NIC partition */ 744/* Get info of a NIC partition */
699int qlcnic_get_nic_info(struct qlcnic_adapter *adapter, 745int qlcnic_82xx_get_nic_info(struct qlcnic_adapter *adapter,
700 struct qlcnic_info *npar_info, u8 func_id) 746 struct qlcnic_info *npar_info, u8 func_id)
701{ 747{
702 int err; 748 int err;
703 dma_addr_t nic_dma_t; 749 dma_addr_t nic_dma_t;
704 struct qlcnic_info_le *nic_info; 750 const struct qlcnic_info_le *nic_info;
705 void *nic_info_addr; 751 void *nic_info_addr;
706 struct qlcnic_cmd_args cmd; 752 struct qlcnic_cmd_args cmd;
707 size_t nic_size = sizeof(struct qlcnic_info_le); 753 size_t nic_size = sizeof(struct qlcnic_info_le);
708 754
709 nic_info_addr = dma_alloc_coherent(&adapter->pdev->dev, nic_size, 755 nic_info_addr = dma_alloc_coherent(&adapter->pdev->dev, nic_size,
710 &nic_dma_t, GFP_KERNEL); 756 &nic_dma_t, GFP_KERNEL);
@@ -713,47 +759,39 @@ int qlcnic_get_nic_info(struct qlcnic_adapter *adapter,
713 memset(nic_info_addr, 0, nic_size); 759 memset(nic_info_addr, 0, nic_size);
714 760
715 nic_info = nic_info_addr; 761 nic_info = nic_info_addr;
716 memset(&cmd, 0, sizeof(cmd));
717 cmd.req.cmd = QLCNIC_CDRP_CMD_GET_NIC_INFO;
718 cmd.req.arg1 = MSD(nic_dma_t);
719 cmd.req.arg2 = LSD(nic_dma_t);
720 cmd.req.arg3 = (func_id << 16 | nic_size);
721 qlcnic_issue_cmd(adapter, &cmd);
722 err = cmd.rsp.cmd;
723 762
724 if (err == QLCNIC_RCODE_SUCCESS) { 763 qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_GET_NIC_INFO);
764 cmd.req.arg[1] = MSD(nic_dma_t);
765 cmd.req.arg[2] = LSD(nic_dma_t);
766 cmd.req.arg[3] = (func_id << 16 | nic_size);
767 err = qlcnic_issue_cmd(adapter, &cmd);
768 if (err != QLCNIC_RCODE_SUCCESS) {
769 dev_err(&adapter->pdev->dev,
770 "Failed to get nic info%d\n", err);
771 err = -EIO;
772 } else {
725 npar_info->pci_func = le16_to_cpu(nic_info->pci_func); 773 npar_info->pci_func = le16_to_cpu(nic_info->pci_func);
726 npar_info->op_mode = le16_to_cpu(nic_info->op_mode); 774 npar_info->op_mode = le16_to_cpu(nic_info->op_mode);
775 npar_info->min_tx_bw = le16_to_cpu(nic_info->min_tx_bw);
776 npar_info->max_tx_bw = le16_to_cpu(nic_info->max_tx_bw);
727 npar_info->phys_port = le16_to_cpu(nic_info->phys_port); 777 npar_info->phys_port = le16_to_cpu(nic_info->phys_port);
728 npar_info->switch_mode = le16_to_cpu(nic_info->switch_mode); 778 npar_info->switch_mode = le16_to_cpu(nic_info->switch_mode);
729 npar_info->max_tx_ques = le16_to_cpu(nic_info->max_tx_ques); 779 npar_info->max_tx_ques = le16_to_cpu(nic_info->max_tx_ques);
730 npar_info->max_rx_ques = le16_to_cpu(nic_info->max_rx_ques); 780 npar_info->max_rx_ques = le16_to_cpu(nic_info->max_rx_ques);
731 npar_info->min_tx_bw = le16_to_cpu(nic_info->min_tx_bw);
732 npar_info->max_tx_bw = le16_to_cpu(nic_info->max_tx_bw);
733 npar_info->capabilities = le32_to_cpu(nic_info->capabilities); 781 npar_info->capabilities = le32_to_cpu(nic_info->capabilities);
734 npar_info->max_mtu = le16_to_cpu(nic_info->max_mtu); 782 npar_info->max_mtu = le16_to_cpu(nic_info->max_mtu);
735
736 dev_info(&adapter->pdev->dev,
737 "phy port: %d switch_mode: %d,\n"
738 "\tmax_tx_q: %d max_rx_q: %d min_tx_bw: 0x%x,\n"
739 "\tmax_tx_bw: 0x%x max_mtu:0x%x, capabilities: 0x%x\n",
740 npar_info->phys_port, npar_info->switch_mode,
741 npar_info->max_tx_ques, npar_info->max_rx_ques,
742 npar_info->min_tx_bw, npar_info->max_tx_bw,
743 npar_info->max_mtu, npar_info->capabilities);
744 } else {
745 dev_err(&adapter->pdev->dev,
746 "Failed to get nic info%d\n", err);
747 err = -EIO;
748 } 783 }
749 784
750 dma_free_coherent(&adapter->pdev->dev, nic_size, nic_info_addr, 785 dma_free_coherent(&adapter->pdev->dev, nic_size, nic_info_addr,
751 nic_dma_t); 786 nic_dma_t);
787 qlcnic_free_mbx_args(&cmd);
788
752 return err; 789 return err;
753} 790}
754 791
755/* Configure a NIC partition */ 792/* Configure a NIC partition */
756int qlcnic_set_nic_info(struct qlcnic_adapter *adapter, struct qlcnic_info *nic) 793int qlcnic_82xx_set_nic_info(struct qlcnic_adapter *adapter,
794 struct qlcnic_info *nic)
757{ 795{
758 int err = -EIO; 796 int err = -EIO;
759 dma_addr_t nic_dma_t; 797 dma_addr_t nic_dma_t;
@@ -784,13 +822,11 @@ int qlcnic_set_nic_info(struct qlcnic_adapter *adapter, struct qlcnic_info *nic)
784 nic_info->min_tx_bw = cpu_to_le16(nic->min_tx_bw); 822 nic_info->min_tx_bw = cpu_to_le16(nic->min_tx_bw);
785 nic_info->max_tx_bw = cpu_to_le16(nic->max_tx_bw); 823 nic_info->max_tx_bw = cpu_to_le16(nic->max_tx_bw);
786 824
787 memset(&cmd, 0, sizeof(cmd)); 825 qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_SET_NIC_INFO);
788 cmd.req.cmd = QLCNIC_CDRP_CMD_SET_NIC_INFO; 826 cmd.req.arg[1] = MSD(nic_dma_t);
789 cmd.req.arg1 = MSD(nic_dma_t); 827 cmd.req.arg[2] = LSD(nic_dma_t);
790 cmd.req.arg2 = LSD(nic_dma_t); 828 cmd.req.arg[3] = ((nic->pci_func << 16) | nic_size);
791 cmd.req.arg3 = ((nic->pci_func << 16) | nic_size); 829 err = qlcnic_issue_cmd(adapter, &cmd);
792 qlcnic_issue_cmd(adapter, &cmd);
793 err = cmd.rsp.cmd;
794 830
795 if (err != QLCNIC_RCODE_SUCCESS) { 831 if (err != QLCNIC_RCODE_SUCCESS) {
796 dev_err(&adapter->pdev->dev, 832 dev_err(&adapter->pdev->dev,
@@ -800,12 +836,14 @@ int qlcnic_set_nic_info(struct qlcnic_adapter *adapter, struct qlcnic_info *nic)
800 836
801 dma_free_coherent(&adapter->pdev->dev, nic_size, nic_info_addr, 837 dma_free_coherent(&adapter->pdev->dev, nic_size, nic_info_addr,
802 nic_dma_t); 838 nic_dma_t);
839 qlcnic_free_mbx_args(&cmd);
840
803 return err; 841 return err;
804} 842}
805 843
806/* Get PCI Info of a partition */ 844/* Get PCI Info of a partition */
807int qlcnic_get_pci_info(struct qlcnic_adapter *adapter, 845int qlcnic_82xx_get_pci_info(struct qlcnic_adapter *adapter,
808 struct qlcnic_pci_info *pci_info) 846 struct qlcnic_pci_info *pci_info)
809{ 847{
810 int err = 0, i; 848 int err = 0, i;
811 struct qlcnic_cmd_args cmd; 849 struct qlcnic_cmd_args cmd;
@@ -822,13 +860,11 @@ int qlcnic_get_pci_info(struct qlcnic_adapter *adapter,
822 memset(pci_info_addr, 0, pci_size); 860 memset(pci_info_addr, 0, pci_size);
823 861
824 npar = pci_info_addr; 862 npar = pci_info_addr;
825 memset(&cmd, 0, sizeof(cmd)); 863 qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_GET_PCI_INFO);
826 cmd.req.cmd = QLCNIC_CDRP_CMD_GET_PCI_INFO; 864 cmd.req.arg[1] = MSD(pci_info_dma_t);
827 cmd.req.arg1 = MSD(pci_info_dma_t); 865 cmd.req.arg[2] = LSD(pci_info_dma_t);
828 cmd.req.arg2 = LSD(pci_info_dma_t); 866 cmd.req.arg[3] = pci_size;
829 cmd.req.arg3 = pci_size; 867 err = qlcnic_issue_cmd(adapter, &cmd);
830 qlcnic_issue_cmd(adapter, &cmd);
831 err = cmd.rsp.cmd;
832 868
833 adapter->ahw->act_pci_func = 0; 869 adapter->ahw->act_pci_func = 0;
834 if (err == QLCNIC_RCODE_SUCCESS) { 870 if (err == QLCNIC_RCODE_SUCCESS) {
@@ -854,6 +890,8 @@ int qlcnic_get_pci_info(struct qlcnic_adapter *adapter,
854 890
855 dma_free_coherent(&adapter->pdev->dev, pci_size, pci_info_addr, 891 dma_free_coherent(&adapter->pdev->dev, pci_size, pci_info_addr,
856 pci_info_dma_t); 892 pci_info_dma_t);
893 qlcnic_free_mbx_args(&cmd);
894
857 return err; 895 return err;
858} 896}
859 897
@@ -872,21 +910,19 @@ int qlcnic_config_port_mirroring(struct qlcnic_adapter *adapter, u8 id,
872 arg1 = id | (enable_mirroring ? BIT_4 : 0); 910 arg1 = id | (enable_mirroring ? BIT_4 : 0);
873 arg1 |= pci_func << 8; 911 arg1 |= pci_func << 8;
874 912
875 memset(&cmd, 0, sizeof(cmd)); 913 qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_SET_PORTMIRRORING);
876 cmd.req.cmd = QLCNIC_CDRP_CMD_SET_PORTMIRRORING; 914 cmd.req.arg[1] = arg1;
877 cmd.req.arg1 = arg1; 915 err = qlcnic_issue_cmd(adapter, &cmd);
878 qlcnic_issue_cmd(adapter, &cmd);
879 err = cmd.rsp.cmd;
880 916
881 if (err != QLCNIC_RCODE_SUCCESS) { 917 if (err != QLCNIC_RCODE_SUCCESS)
882 dev_err(&adapter->pdev->dev, 918 dev_err(&adapter->pdev->dev,
883 "Failed to configure port mirroring%d on eswitch:%d\n", 919 "Failed to configure port mirroring%d on eswitch:%d\n",
884 pci_func, id); 920 pci_func, id);
885 } else { 921 else
886 dev_info(&adapter->pdev->dev, 922 dev_info(&adapter->pdev->dev,
887 "Configured eSwitch %d for port mirroring:%d\n", 923 "Configured eSwitch %d for port mirroring:%d\n",
888 id, pci_func); 924 id, pci_func);
889 } 925 qlcnic_free_mbx_args(&cmd);
890 926
891 return err; 927 return err;
892} 928}
@@ -923,13 +959,11 @@ int qlcnic_get_port_stats(struct qlcnic_adapter *adapter, const u8 func,
923 arg1 = func | QLCNIC_STATS_VERSION << 8 | QLCNIC_STATS_PORT << 12; 959 arg1 = func | QLCNIC_STATS_VERSION << 8 | QLCNIC_STATS_PORT << 12;
924 arg1 |= rx_tx << 15 | stats_size << 16; 960 arg1 |= rx_tx << 15 | stats_size << 16;
925 961
926 memset(&cmd, 0, sizeof(cmd)); 962 qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_GET_ESWITCH_STATS);
927 cmd.req.cmd = QLCNIC_CDRP_CMD_GET_ESWITCH_STATS; 963 cmd.req.arg[1] = arg1;
928 cmd.req.arg1 = arg1; 964 cmd.req.arg[2] = MSD(stats_dma_t);
929 cmd.req.arg2 = MSD(stats_dma_t); 965 cmd.req.arg[3] = LSD(stats_dma_t);
930 cmd.req.arg3 = LSD(stats_dma_t); 966 err = qlcnic_issue_cmd(adapter, &cmd);
931 qlcnic_issue_cmd(adapter, &cmd);
932 err = cmd.rsp.cmd;
933 967
934 if (!err) { 968 if (!err) {
935 stats = stats_addr; 969 stats = stats_addr;
@@ -949,6 +983,8 @@ int qlcnic_get_port_stats(struct qlcnic_adapter *adapter, const u8 func,
949 983
950 dma_free_coherent(&adapter->pdev->dev, stats_size, stats_addr, 984 dma_free_coherent(&adapter->pdev->dev, stats_size, stats_addr,
951 stats_dma_t); 985 stats_dma_t);
986 qlcnic_free_mbx_args(&cmd);
987
952 return err; 988 return err;
953} 989}
954 990
@@ -963,6 +999,9 @@ int qlcnic_get_mac_stats(struct qlcnic_adapter *adapter,
963 void *stats_addr; 999 void *stats_addr;
964 int err; 1000 int err;
965 1001
1002 if (mac_stats == NULL)
1003 return -ENOMEM;
1004
966 stats_addr = dma_alloc_coherent(&adapter->pdev->dev, stats_size, 1005 stats_addr = dma_alloc_coherent(&adapter->pdev->dev, stats_size,
967 &stats_dma_t, GFP_KERNEL); 1006 &stats_dma_t, GFP_KERNEL);
968 if (!stats_addr) { 1007 if (!stats_addr) {
@@ -971,15 +1010,11 @@ int qlcnic_get_mac_stats(struct qlcnic_adapter *adapter,
971 return -ENOMEM; 1010 return -ENOMEM;
972 } 1011 }
973 memset(stats_addr, 0, stats_size); 1012 memset(stats_addr, 0, stats_size);
974 memset(&cmd, 0, sizeof(cmd)); 1013 qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_GET_MAC_STATS);
975 cmd.req.cmd = QLCNIC_CDRP_CMD_GET_MAC_STATS; 1014 cmd.req.arg[1] = stats_size << 16;
976 cmd.req.arg1 = stats_size << 16; 1015 cmd.req.arg[2] = MSD(stats_dma_t);
977 cmd.req.arg2 = MSD(stats_dma_t); 1016 cmd.req.arg[3] = LSD(stats_dma_t);
978 cmd.req.arg3 = LSD(stats_dma_t); 1017 err = qlcnic_issue_cmd(adapter, &cmd);
979
980 qlcnic_issue_cmd(adapter, &cmd);
981 err = cmd.rsp.cmd;
982
983 if (!err) { 1018 if (!err) {
984 stats = stats_addr; 1019 stats = stats_addr;
985 mac_stats->mac_tx_frames = le64_to_cpu(stats->mac_tx_frames); 1020 mac_stats->mac_tx_frames = le64_to_cpu(stats->mac_tx_frames);
@@ -1001,10 +1036,16 @@ int qlcnic_get_mac_stats(struct qlcnic_adapter *adapter,
1001 mac_stats->mac_rx_jabber = le64_to_cpu(stats->mac_rx_jabber); 1036 mac_stats->mac_rx_jabber = le64_to_cpu(stats->mac_rx_jabber);
1002 mac_stats->mac_rx_dropped = le64_to_cpu(stats->mac_rx_dropped); 1037 mac_stats->mac_rx_dropped = le64_to_cpu(stats->mac_rx_dropped);
1003 mac_stats->mac_rx_crc_error = le64_to_cpu(stats->mac_rx_crc_error); 1038 mac_stats->mac_rx_crc_error = le64_to_cpu(stats->mac_rx_crc_error);
1039 } else {
1040 dev_err(&adapter->pdev->dev,
1041 "%s: Get mac stats failed, err=%d.\n", __func__, err);
1004 } 1042 }
1005 1043
1006 dma_free_coherent(&adapter->pdev->dev, stats_size, stats_addr, 1044 dma_free_coherent(&adapter->pdev->dev, stats_size, stats_addr,
1007 stats_dma_t); 1045 stats_dma_t);
1046
1047 qlcnic_free_mbx_args(&cmd);
1048
1008 return err; 1049 return err;
1009} 1050}
1010 1051
@@ -1065,7 +1106,7 @@ int qlcnic_get_eswitch_stats(struct qlcnic_adapter *adapter, const u8 eswitch,
1065int qlcnic_clear_esw_stats(struct qlcnic_adapter *adapter, const u8 func_esw, 1106int qlcnic_clear_esw_stats(struct qlcnic_adapter *adapter, const u8 func_esw,
1066 const u8 port, const u8 rx_tx) 1107 const u8 port, const u8 rx_tx)
1067{ 1108{
1068 1109 int err;
1069 u32 arg1; 1110 u32 arg1;
1070 struct qlcnic_cmd_args cmd; 1111 struct qlcnic_cmd_args cmd;
1071 1112
@@ -1088,15 +1129,16 @@ int qlcnic_clear_esw_stats(struct qlcnic_adapter *adapter, const u8 func_esw,
1088 arg1 = port | QLCNIC_STATS_VERSION << 8 | func_esw << 12; 1129 arg1 = port | QLCNIC_STATS_VERSION << 8 | func_esw << 12;
1089 arg1 |= BIT_14 | rx_tx << 15; 1130 arg1 |= BIT_14 | rx_tx << 15;
1090 1131
1091 memset(&cmd, 0, sizeof(cmd)); 1132 qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_GET_ESWITCH_STATS);
1092 cmd.req.cmd = QLCNIC_CDRP_CMD_GET_ESWITCH_STATS; 1133 cmd.req.arg[1] = arg1;
1093 cmd.req.arg1 = arg1; 1134 err = qlcnic_issue_cmd(adapter, &cmd);
1094 qlcnic_issue_cmd(adapter, &cmd); 1135 qlcnic_free_mbx_args(&cmd);
1095 return cmd.rsp.cmd; 1136 return err;
1096 1137
1097err_ret: 1138err_ret:
1098 dev_err(&adapter->pdev->dev, "Invalid argument func_esw=%d port=%d" 1139 dev_err(&adapter->pdev->dev,
1099 "rx_ctx=%d\n", func_esw, port, rx_tx); 1140 "Invalid args func_esw %d port %d rx_ctx %d\n",
1141 func_esw, port, rx_tx);
1100 return -EIO; 1142 return -EIO;
1101} 1143}
1102 1144
@@ -1109,22 +1151,21 @@ __qlcnic_get_eswitch_port_config(struct qlcnic_adapter *adapter,
1109 u8 pci_func; 1151 u8 pci_func;
1110 pci_func = (*arg1 >> 8); 1152 pci_func = (*arg1 >> 8);
1111 1153
1112 cmd.req.cmd = QLCNIC_CDRP_CMD_GET_ESWITCH_PORT_CONFIG; 1154 qlcnic_alloc_mbx_args(&cmd, adapter,
1113 cmd.req.arg1 = *arg1; 1155 QLCNIC_CMD_GET_ESWITCH_PORT_CONFIG);
1114 cmd.rsp.arg1 = cmd.rsp.arg2 = 1; 1156 cmd.req.arg[1] = *arg1;
1115 qlcnic_issue_cmd(adapter, &cmd); 1157 err = qlcnic_issue_cmd(adapter, &cmd);
1116 *arg1 = cmd.rsp.arg1; 1158 *arg1 = cmd.rsp.arg[1];
1117 *arg2 = cmd.rsp.arg2; 1159 *arg2 = cmd.rsp.arg[2];
1118 err = cmd.rsp.cmd; 1160 qlcnic_free_mbx_args(&cmd);
1119 1161
1120 if (err == QLCNIC_RCODE_SUCCESS) { 1162 if (err == QLCNIC_RCODE_SUCCESS)
1121 dev_info(&adapter->pdev->dev, 1163 dev_info(&adapter->pdev->dev,
1122 "eSwitch port config for pci func %d\n", pci_func); 1164 "eSwitch port config for pci func %d\n", pci_func);
1123 } else { 1165 else
1124 dev_err(&adapter->pdev->dev, 1166 dev_err(&adapter->pdev->dev,
1125 "Failed to get eswitch port config for pci func %d\n", 1167 "Failed to get eswitch port config for pci func %d\n",
1126 pci_func); 1168 pci_func);
1127 }
1128 return err; 1169 return err;
1129} 1170}
1130/* Configure eSwitch port 1171/* Configure eSwitch port
@@ -1189,20 +1230,18 @@ int qlcnic_config_switch_port(struct qlcnic_adapter *adapter,
1189 return err; 1230 return err;
1190 } 1231 }
1191 1232
1192 memset(&cmd, 0, sizeof(cmd)); 1233 qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_CONFIGURE_ESWITCH);
1193 cmd.req.cmd = QLCNIC_CDRP_CMD_CONFIGURE_ESWITCH; 1234 cmd.req.arg[1] = arg1;
1194 cmd.req.arg1 = arg1; 1235 cmd.req.arg[2] = arg2;
1195 cmd.req.arg2 = arg2; 1236 err = qlcnic_issue_cmd(adapter, &cmd);
1196 qlcnic_issue_cmd(adapter, &cmd); 1237 qlcnic_free_mbx_args(&cmd);
1197 1238
1198 err = cmd.rsp.cmd; 1239 if (err != QLCNIC_RCODE_SUCCESS)
1199 if (err != QLCNIC_RCODE_SUCCESS) {
1200 dev_err(&adapter->pdev->dev, 1240 dev_err(&adapter->pdev->dev,
1201 "Failed to configure eswitch pci func %d\n", pci_func); 1241 "Failed to configure eswitch pci func %d\n", pci_func);
1202 } else { 1242 else
1203 dev_info(&adapter->pdev->dev, 1243 dev_info(&adapter->pdev->dev,
1204 "Configured eSwitch for pci func %d\n", pci_func); 1244 "Configured eSwitch for pci func %d\n", pci_func);
1205 }
1206 1245
1207 return err; 1246 return err;
1208} 1247}