1 /*
2 * Broadcom NetXtreme-E RoCE driver.
3 *
4 * Copyright (c) 2016 - 2017, Broadcom. All rights reserved. The term
5 * Broadcom refers to Broadcom Limited and/or its subsidiaries.
6 *
7 * This software is available to you under a choice of one of two
8 * licenses. You may choose to be licensed under the terms of the GNU
9 * General Public License (GPL) Version 2, available from the file
10 * COPYING in the main directory of this source tree, or the
11 * BSD license below:
12 *
13 * Redistribution and use in source and binary forms, with or without
14 * modification, are permitted provided that the following conditions
15 * are met:
16 *
17 * 1. Redistributions of source code must retain the above copyright
18 * notice, this list of conditions and the following disclaimer.
19 * 2. Redistributions in binary form must reproduce the above copyright
20 * notice, this list of conditions and the following disclaimer in
21 * the documentation and/or other materials provided with the
22 * distribution.
23 *
24 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS''
25 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
26 * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
27 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS
28 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
29 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
30 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
31 * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
32 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
33 * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
34 * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
35 *
36 * Description: QPLib resource manager
37 */
38
39 #define dev_fmt(fmt) "QPLIB: " fmt
40
41 #include <linux/spinlock.h>
42 #include <linux/pci.h>
43 #include <linux/interrupt.h>
44 #include <linux/inetdevice.h>
45 #include <linux/dma-mapping.h>
46 #include <linux/if_vlan.h>
47 #include <linux/vmalloc.h>
48 #include <rdma/ib_verbs.h>
49 #include <rdma/ib_umem.h>
50
51 #include "roce_hsi.h"
52 #include "qplib_res.h"
53 #include "qplib_sp.h"
54 #include "qplib_rcfw.h"
55
56 /* PBL */
__free_pbl(struct bnxt_qplib_res * res,struct bnxt_qplib_pbl * pbl,bool is_umem)57 static void __free_pbl(struct bnxt_qplib_res *res, struct bnxt_qplib_pbl *pbl,
58 bool is_umem)
59 {
60 struct pci_dev *pdev = res->pdev;
61 int i;
62
63 if (!is_umem) {
64 for (i = 0; i < pbl->pg_count; i++) {
65 if (pbl->pg_arr[i])
66 dma_free_coherent(&pdev->dev, pbl->pg_size,
67 pbl->pg_arr[i],
68 pbl->pg_map_arr[i]);
69 else
70 dev_warn(&pdev->dev,
71 "PBL free pg_arr[%d] empty?!\n", i);
72 pbl->pg_arr[i] = NULL;
73 }
74 }
75 vfree(pbl->pg_arr);
76 pbl->pg_arr = NULL;
77 vfree(pbl->pg_map_arr);
78 pbl->pg_map_arr = NULL;
79 pbl->pg_count = 0;
80 pbl->pg_size = 0;
81 }
82
bnxt_qplib_fill_user_dma_pages(struct bnxt_qplib_pbl * pbl,struct bnxt_qplib_sg_info * sginfo)83 static void bnxt_qplib_fill_user_dma_pages(struct bnxt_qplib_pbl *pbl,
84 struct bnxt_qplib_sg_info *sginfo)
85 {
86 struct ib_block_iter biter;
87 int i = 0;
88
89 rdma_umem_for_each_dma_block(sginfo->umem, &biter, sginfo->pgsize) {
90 pbl->pg_map_arr[i] = rdma_block_iter_dma_address(&biter);
91 pbl->pg_arr[i] = NULL;
92 pbl->pg_count++;
93 i++;
94 }
95 }
96
__alloc_pbl(struct bnxt_qplib_res * res,struct bnxt_qplib_pbl * pbl,struct bnxt_qplib_sg_info * sginfo)97 static int __alloc_pbl(struct bnxt_qplib_res *res,
98 struct bnxt_qplib_pbl *pbl,
99 struct bnxt_qplib_sg_info *sginfo)
100 {
101 struct pci_dev *pdev = res->pdev;
102 bool is_umem = false;
103 u32 pages;
104 int i;
105
106 if (sginfo->nopte)
107 return 0;
108 if (sginfo->umem)
109 pages = ib_umem_num_dma_blocks(sginfo->umem, sginfo->pgsize);
110 else
111 pages = sginfo->npages;
112 /* page ptr arrays */
113 pbl->pg_arr = vmalloc_array(pages, sizeof(void *));
114 if (!pbl->pg_arr)
115 return -ENOMEM;
116 memset(pbl->pg_arr, 0, pages * sizeof(void *));
117
118 pbl->pg_map_arr = vmalloc_array(pages, sizeof(dma_addr_t));
119 if (!pbl->pg_map_arr) {
120 vfree(pbl->pg_arr);
121 pbl->pg_arr = NULL;
122 return -ENOMEM;
123 }
124 memset(pbl->pg_map_arr, 0, pages * sizeof(dma_addr_t));
125 pbl->pg_count = 0;
126 pbl->pg_size = sginfo->pgsize;
127
128 if (!sginfo->umem) {
129 for (i = 0; i < pages; i++) {
130 pbl->pg_arr[i] = dma_alloc_coherent(&pdev->dev,
131 pbl->pg_size,
132 &pbl->pg_map_arr[i],
133 GFP_KERNEL);
134 if (!pbl->pg_arr[i])
135 goto fail;
136 pbl->pg_count++;
137 }
138 } else {
139 is_umem = true;
140 bnxt_qplib_fill_user_dma_pages(pbl, sginfo);
141 }
142
143 return 0;
144 fail:
145 __free_pbl(res, pbl, is_umem);
146 return -ENOMEM;
147 }
148
149 /* HWQ */
bnxt_qplib_free_hwq(struct bnxt_qplib_res * res,struct bnxt_qplib_hwq * hwq)150 void bnxt_qplib_free_hwq(struct bnxt_qplib_res *res,
151 struct bnxt_qplib_hwq *hwq)
152 {
153 int i;
154
155 if (!hwq->max_elements)
156 return;
157 if (hwq->level >= PBL_LVL_MAX)
158 return;
159
160 for (i = 0; i < hwq->level + 1; i++) {
161 if (i == hwq->level)
162 __free_pbl(res, &hwq->pbl[i], hwq->is_user);
163 else
164 __free_pbl(res, &hwq->pbl[i], false);
165 }
166
167 hwq->level = PBL_LVL_MAX;
168 hwq->max_elements = 0;
169 hwq->element_size = 0;
170 hwq->prod = 0;
171 hwq->cons = 0;
172 hwq->cp_bit = 0;
173 }
174
175 /* All HWQs are power of 2 in size */
176
bnxt_qplib_alloc_init_hwq(struct bnxt_qplib_hwq * hwq,struct bnxt_qplib_hwq_attr * hwq_attr)177 int bnxt_qplib_alloc_init_hwq(struct bnxt_qplib_hwq *hwq,
178 struct bnxt_qplib_hwq_attr *hwq_attr)
179 {
180 u32 npages, aux_slots, pg_size, aux_pages = 0, aux_size = 0;
181 struct bnxt_qplib_sg_info sginfo = {};
182 u32 depth, stride, npbl, npde;
183 dma_addr_t *src_phys_ptr, **dst_virt_ptr;
184 struct bnxt_qplib_res *res;
185 struct pci_dev *pdev;
186 int i, rc, lvl;
187
188 res = hwq_attr->res;
189 pdev = res->pdev;
190 pg_size = hwq_attr->sginfo->pgsize;
191 hwq->level = PBL_LVL_MAX;
192
193 depth = roundup_pow_of_two(hwq_attr->depth);
194 stride = roundup_pow_of_two(hwq_attr->stride);
195 if (hwq_attr->aux_depth) {
196 aux_slots = hwq_attr->aux_depth;
197 aux_size = roundup_pow_of_two(hwq_attr->aux_stride);
198 aux_pages = (aux_slots * aux_size) / pg_size;
199 if ((aux_slots * aux_size) % pg_size)
200 aux_pages++;
201 }
202
203 if (!hwq_attr->sginfo->umem) {
204 hwq->is_user = false;
205 npages = (depth * stride) / pg_size + aux_pages;
206 if ((depth * stride) % pg_size)
207 npages++;
208 if (!npages)
209 return -EINVAL;
210 hwq_attr->sginfo->npages = npages;
211 } else {
212 npages = ib_umem_num_dma_blocks(hwq_attr->sginfo->umem,
213 hwq_attr->sginfo->pgsize);
214 hwq->is_user = true;
215 }
216
217 if (npages == MAX_PBL_LVL_0_PGS && !hwq_attr->sginfo->nopte) {
218 /* This request is Level 0, map PTE */
219 rc = __alloc_pbl(res, &hwq->pbl[PBL_LVL_0], hwq_attr->sginfo);
220 if (rc)
221 goto fail;
222 hwq->level = PBL_LVL_0;
223 goto done;
224 }
225
226 if (npages >= MAX_PBL_LVL_0_PGS) {
227 if (npages > MAX_PBL_LVL_1_PGS) {
228 u32 flag = (hwq_attr->type == HWQ_TYPE_L2_CMPL) ?
229 0 : PTU_PTE_VALID;
230 /* 2 levels of indirection */
231 npbl = npages >> MAX_PBL_LVL_1_PGS_SHIFT;
232 if (npages % BIT(MAX_PBL_LVL_1_PGS_SHIFT))
233 npbl++;
234 npde = npbl >> MAX_PDL_LVL_SHIFT;
235 if (npbl % BIT(MAX_PDL_LVL_SHIFT))
236 npde++;
237 /* Alloc PDE pages */
238 sginfo.pgsize = npde * ROCE_PG_SIZE_4K;
239 sginfo.npages = 1;
240 rc = __alloc_pbl(res, &hwq->pbl[PBL_LVL_0], &sginfo);
241 if (rc)
242 goto fail;
243
244 /* Alloc PBL pages */
245 sginfo.npages = npbl;
246 sginfo.pgsize = ROCE_PG_SIZE_4K;
247 rc = __alloc_pbl(res, &hwq->pbl[PBL_LVL_1], &sginfo);
248 if (rc)
249 goto fail;
250 /* Fill PDL with PBL page pointers */
251 dst_virt_ptr =
252 (dma_addr_t **)hwq->pbl[PBL_LVL_0].pg_arr;
253 src_phys_ptr = hwq->pbl[PBL_LVL_1].pg_map_arr;
254 for (i = 0; i < hwq->pbl[PBL_LVL_1].pg_count; i++)
255 dst_virt_ptr[0][i] = src_phys_ptr[i] | flag;
256
257 /* Alloc or init PTEs */
258 rc = __alloc_pbl(res, &hwq->pbl[PBL_LVL_2],
259 hwq_attr->sginfo);
260 if (rc)
261 goto fail;
262 hwq->level = PBL_LVL_2;
263 if (hwq_attr->sginfo->nopte)
264 goto done;
265 /* Fill PBLs with PTE pointers */
266 dst_virt_ptr =
267 (dma_addr_t **)hwq->pbl[PBL_LVL_1].pg_arr;
268 src_phys_ptr = hwq->pbl[PBL_LVL_2].pg_map_arr;
269 for (i = 0; i < hwq->pbl[PBL_LVL_2].pg_count; i++) {
270 dst_virt_ptr[PTR_PG(i)][PTR_IDX(i)] =
271 src_phys_ptr[i] | PTU_PTE_VALID;
272 }
273 if (hwq_attr->type == HWQ_TYPE_QUEUE) {
274 /* Find the last pg of the size */
275 i = hwq->pbl[PBL_LVL_2].pg_count;
276 dst_virt_ptr[PTR_PG(i - 1)][PTR_IDX(i - 1)] |=
277 PTU_PTE_LAST;
278 if (i > 1)
279 dst_virt_ptr[PTR_PG(i - 2)]
280 [PTR_IDX(i - 2)] |=
281 PTU_PTE_NEXT_TO_LAST;
282 }
283 } else { /* pages < 512 npbl = 1, npde = 0 */
284 u32 flag = (hwq_attr->type == HWQ_TYPE_L2_CMPL) ?
285 0 : PTU_PTE_VALID;
286
287 /* 1 level of indirection */
288 npbl = npages >> MAX_PBL_LVL_1_PGS_SHIFT;
289 if (npages % BIT(MAX_PBL_LVL_1_PGS_SHIFT))
290 npbl++;
291 sginfo.npages = npbl;
292 sginfo.pgsize = PAGE_SIZE;
293 /* Alloc PBL page */
294 rc = __alloc_pbl(res, &hwq->pbl[PBL_LVL_0], &sginfo);
295 if (rc)
296 goto fail;
297 /* Alloc or init PTEs */
298 rc = __alloc_pbl(res, &hwq->pbl[PBL_LVL_1],
299 hwq_attr->sginfo);
300 if (rc)
301 goto fail;
302 hwq->level = PBL_LVL_1;
303 if (hwq_attr->sginfo->nopte)
304 goto done;
305 /* Fill PBL with PTE pointers */
306 dst_virt_ptr =
307 (dma_addr_t **)hwq->pbl[PBL_LVL_0].pg_arr;
308 src_phys_ptr = hwq->pbl[PBL_LVL_1].pg_map_arr;
309 for (i = 0; i < hwq->pbl[PBL_LVL_1].pg_count; i++)
310 dst_virt_ptr[PTR_PG(i)][PTR_IDX(i)] =
311 src_phys_ptr[i] | flag;
312 if (hwq_attr->type == HWQ_TYPE_QUEUE) {
313 /* Find the last pg of the size */
314 i = hwq->pbl[PBL_LVL_1].pg_count;
315 dst_virt_ptr[PTR_PG(i - 1)][PTR_IDX(i - 1)] |=
316 PTU_PTE_LAST;
317 if (i > 1)
318 dst_virt_ptr[PTR_PG(i - 2)]
319 [PTR_IDX(i - 2)] |=
320 PTU_PTE_NEXT_TO_LAST;
321 }
322 }
323 }
324 done:
325 hwq->prod = 0;
326 hwq->cons = 0;
327 hwq->pdev = pdev;
328 hwq->depth = hwq_attr->depth;
329 hwq->max_elements = hwq->depth;
330 hwq->element_size = stride;
331 hwq->qe_ppg = pg_size / stride;
332 /* For direct access to the elements */
333 lvl = hwq->level;
334 if (hwq_attr->sginfo->nopte && hwq->level)
335 lvl = hwq->level - 1;
336 hwq->pbl_ptr = hwq->pbl[lvl].pg_arr;
337 hwq->pbl_dma_ptr = hwq->pbl[lvl].pg_map_arr;
338 spin_lock_init(&hwq->lock);
339
340 return 0;
341 fail:
342 bnxt_qplib_free_hwq(res, hwq);
343 return -ENOMEM;
344 }
345
346 /* Context Tables */
bnxt_qplib_free_hwctx(struct bnxt_qplib_res * res,struct bnxt_qplib_ctx * ctx)347 void bnxt_qplib_free_hwctx(struct bnxt_qplib_res *res,
348 struct bnxt_qplib_ctx *ctx)
349 {
350 int i;
351
352 bnxt_qplib_free_hwq(res, &ctx->qpc_tbl);
353 bnxt_qplib_free_hwq(res, &ctx->mrw_tbl);
354 bnxt_qplib_free_hwq(res, &ctx->srqc_tbl);
355 bnxt_qplib_free_hwq(res, &ctx->cq_tbl);
356 bnxt_qplib_free_hwq(res, &ctx->tim_tbl);
357 for (i = 0; i < MAX_TQM_ALLOC_REQ; i++)
358 bnxt_qplib_free_hwq(res, &ctx->tqm_ctx.qtbl[i]);
359 /* restore original pde level before destroy */
360 ctx->tqm_ctx.pde.level = ctx->tqm_ctx.pde_level;
361 bnxt_qplib_free_hwq(res, &ctx->tqm_ctx.pde);
362 }
363
bnxt_qplib_alloc_tqm_rings(struct bnxt_qplib_res * res,struct bnxt_qplib_ctx * ctx)364 static int bnxt_qplib_alloc_tqm_rings(struct bnxt_qplib_res *res,
365 struct bnxt_qplib_ctx *ctx)
366 {
367 struct bnxt_qplib_hwq_attr hwq_attr = {};
368 struct bnxt_qplib_sg_info sginfo = {};
369 struct bnxt_qplib_tqm_ctx *tqmctx;
370 int rc;
371 int i;
372
373 tqmctx = &ctx->tqm_ctx;
374
375 sginfo.pgsize = PAGE_SIZE;
376 sginfo.pgshft = PAGE_SHIFT;
377 hwq_attr.sginfo = &sginfo;
378 hwq_attr.res = res;
379 hwq_attr.type = HWQ_TYPE_CTX;
380 hwq_attr.depth = 512;
381 hwq_attr.stride = sizeof(u64);
382 /* Alloc pdl buffer */
383 rc = bnxt_qplib_alloc_init_hwq(&tqmctx->pde, &hwq_attr);
384 if (rc)
385 goto out;
386 /* Save original pdl level */
387 tqmctx->pde_level = tqmctx->pde.level;
388
389 hwq_attr.stride = 1;
390 for (i = 0; i < MAX_TQM_ALLOC_REQ; i++) {
391 if (!tqmctx->qcount[i])
392 continue;
393 hwq_attr.depth = ctx->qpc_count * tqmctx->qcount[i];
394 rc = bnxt_qplib_alloc_init_hwq(&tqmctx->qtbl[i], &hwq_attr);
395 if (rc)
396 goto out;
397 }
398 out:
399 return rc;
400 }
401
bnxt_qplib_map_tqm_pgtbl(struct bnxt_qplib_tqm_ctx * ctx)402 static void bnxt_qplib_map_tqm_pgtbl(struct bnxt_qplib_tqm_ctx *ctx)
403 {
404 struct bnxt_qplib_hwq *tbl;
405 dma_addr_t *dma_ptr;
406 __le64 **pbl_ptr, *ptr;
407 int i, j, k;
408 int fnz_idx = -1;
409 int pg_count;
410
411 pbl_ptr = (__le64 **)ctx->pde.pbl_ptr;
412
413 for (i = 0, j = 0; i < MAX_TQM_ALLOC_REQ;
414 i++, j += MAX_TQM_ALLOC_BLK_SIZE) {
415 tbl = &ctx->qtbl[i];
416 if (!tbl->max_elements)
417 continue;
418 if (fnz_idx == -1)
419 fnz_idx = i; /* first non-zero index */
420 switch (tbl->level) {
421 case PBL_LVL_2:
422 pg_count = tbl->pbl[PBL_LVL_1].pg_count;
423 for (k = 0; k < pg_count; k++) {
424 ptr = &pbl_ptr[PTR_PG(j + k)][PTR_IDX(j + k)];
425 dma_ptr = &tbl->pbl[PBL_LVL_1].pg_map_arr[k];
426 *ptr = cpu_to_le64(*dma_ptr | PTU_PTE_VALID);
427 }
428 break;
429 case PBL_LVL_1:
430 case PBL_LVL_0:
431 default:
432 ptr = &pbl_ptr[PTR_PG(j)][PTR_IDX(j)];
433 *ptr = cpu_to_le64(tbl->pbl[PBL_LVL_0].pg_map_arr[0] |
434 PTU_PTE_VALID);
435 break;
436 }
437 }
438 if (fnz_idx == -1)
439 fnz_idx = 0;
440 /* update pde level as per page table programming */
441 ctx->pde.level = (ctx->qtbl[fnz_idx].level == PBL_LVL_2) ? PBL_LVL_2 :
442 ctx->qtbl[fnz_idx].level + 1;
443 }
444
bnxt_qplib_setup_tqm_rings(struct bnxt_qplib_res * res,struct bnxt_qplib_ctx * ctx)445 static int bnxt_qplib_setup_tqm_rings(struct bnxt_qplib_res *res,
446 struct bnxt_qplib_ctx *ctx)
447 {
448 int rc;
449
450 rc = bnxt_qplib_alloc_tqm_rings(res, ctx);
451 if (rc)
452 goto fail;
453
454 bnxt_qplib_map_tqm_pgtbl(&ctx->tqm_ctx);
455 fail:
456 return rc;
457 }
458
459 /*
460 * Routine: bnxt_qplib_alloc_hwctx
461 * Description:
462 * Context tables are memories which are used by the chip fw.
463 * The 6 tables defined are:
464 * QPC ctx - holds QP states
465 * MRW ctx - holds memory region and window
466 * SRQ ctx - holds shared RQ states
467 * CQ ctx - holds completion queue states
468 * TQM ctx - holds Tx Queue Manager context
469 * TIM ctx - holds timer context
470 * Depending on the size of the tbl requested, either a 1 Page Buffer List
471 * or a 1-to-2-stage indirection Page Directory List + 1 PBL is used
472 * instead.
473 * Table might be employed as follows:
474 * For 0 < ctx size <= 1 PAGE, 0 level of ind is used
475 * For 1 PAGE < ctx size <= 512 entries size, 1 level of ind is used
476 * For 512 < ctx size <= MAX, 2 levels of ind is used
477 * Returns:
478 * 0 if success, else -ERRORS
479 */
bnxt_qplib_alloc_hwctx(struct bnxt_qplib_res * res,struct bnxt_qplib_ctx * ctx)480 int bnxt_qplib_alloc_hwctx(struct bnxt_qplib_res *res,
481 struct bnxt_qplib_ctx *ctx)
482 {
483 struct bnxt_qplib_hwq_attr hwq_attr = {};
484 struct bnxt_qplib_sg_info sginfo = {};
485 int rc;
486
487 /* QPC Tables */
488 sginfo.pgsize = PAGE_SIZE;
489 sginfo.pgshft = PAGE_SHIFT;
490 hwq_attr.sginfo = &sginfo;
491
492 hwq_attr.res = res;
493 hwq_attr.depth = ctx->qpc_count;
494 hwq_attr.stride = BNXT_QPLIB_MAX_QP_CTX_ENTRY_SIZE;
495 hwq_attr.type = HWQ_TYPE_CTX;
496 rc = bnxt_qplib_alloc_init_hwq(&ctx->qpc_tbl, &hwq_attr);
497 if (rc)
498 goto fail;
499
500 /* MRW Tables */
501 hwq_attr.depth = ctx->mrw_count;
502 hwq_attr.stride = BNXT_QPLIB_MAX_MRW_CTX_ENTRY_SIZE;
503 rc = bnxt_qplib_alloc_init_hwq(&ctx->mrw_tbl, &hwq_attr);
504 if (rc)
505 goto fail;
506
507 /* SRQ Tables */
508 hwq_attr.depth = ctx->srqc_count;
509 hwq_attr.stride = BNXT_QPLIB_MAX_SRQ_CTX_ENTRY_SIZE;
510 rc = bnxt_qplib_alloc_init_hwq(&ctx->srqc_tbl, &hwq_attr);
511 if (rc)
512 goto fail;
513
514 /* CQ Tables */
515 hwq_attr.depth = ctx->cq_count;
516 hwq_attr.stride = BNXT_QPLIB_MAX_CQ_CTX_ENTRY_SIZE;
517 rc = bnxt_qplib_alloc_init_hwq(&ctx->cq_tbl, &hwq_attr);
518 if (rc)
519 goto fail;
520
521 /* TQM Buffer */
522 rc = bnxt_qplib_setup_tqm_rings(res, ctx);
523 if (rc)
524 goto fail;
525 /* TIM Buffer */
526 ctx->tim_tbl.max_elements = ctx->qpc_count * 16;
527 hwq_attr.depth = ctx->qpc_count * 16;
528 hwq_attr.stride = 1;
529 rc = bnxt_qplib_alloc_init_hwq(&ctx->tim_tbl, &hwq_attr);
530 if (rc)
531 goto fail;
532
533 return 0;
534
535 fail:
536 bnxt_qplib_free_hwctx(res, ctx);
537 return rc;
538 }
539
bnxt_qplib_free_sgid_tbl(struct bnxt_qplib_res * res,struct bnxt_qplib_sgid_tbl * sgid_tbl)540 static void bnxt_qplib_free_sgid_tbl(struct bnxt_qplib_res *res,
541 struct bnxt_qplib_sgid_tbl *sgid_tbl)
542 {
543 kfree(sgid_tbl->tbl);
544 kfree(sgid_tbl->hw_id);
545 kfree(sgid_tbl->ctx);
546 kfree(sgid_tbl->vlan);
547 sgid_tbl->tbl = NULL;
548 sgid_tbl->hw_id = NULL;
549 sgid_tbl->ctx = NULL;
550 sgid_tbl->vlan = NULL;
551 sgid_tbl->max = 0;
552 sgid_tbl->active = 0;
553 }
554
bnxt_qplib_alloc_sgid_tbl(struct bnxt_qplib_res * res,struct bnxt_qplib_sgid_tbl * sgid_tbl,u16 max)555 static int bnxt_qplib_alloc_sgid_tbl(struct bnxt_qplib_res *res,
556 struct bnxt_qplib_sgid_tbl *sgid_tbl,
557 u16 max)
558 {
559 sgid_tbl->tbl = kcalloc(max, sizeof(*sgid_tbl->tbl), GFP_KERNEL);
560 if (!sgid_tbl->tbl)
561 return -ENOMEM;
562
563 sgid_tbl->hw_id = kcalloc(max, sizeof(u16), GFP_KERNEL);
564 if (!sgid_tbl->hw_id)
565 goto out_free1;
566
567 sgid_tbl->ctx = kcalloc(max, sizeof(void *), GFP_KERNEL);
568 if (!sgid_tbl->ctx)
569 goto out_free2;
570
571 sgid_tbl->vlan = kcalloc(max, sizeof(u8), GFP_KERNEL);
572 if (!sgid_tbl->vlan)
573 goto out_free3;
574
575 sgid_tbl->max = max;
576 return 0;
577 out_free3:
578 kfree(sgid_tbl->ctx);
579 sgid_tbl->ctx = NULL;
580 out_free2:
581 kfree(sgid_tbl->hw_id);
582 sgid_tbl->hw_id = NULL;
583 out_free1:
584 kfree(sgid_tbl->tbl);
585 sgid_tbl->tbl = NULL;
586 return -ENOMEM;
587 };
588
bnxt_qplib_cleanup_sgid_tbl(struct bnxt_qplib_res * res,struct bnxt_qplib_sgid_tbl * sgid_tbl)589 static void bnxt_qplib_cleanup_sgid_tbl(struct bnxt_qplib_res *res,
590 struct bnxt_qplib_sgid_tbl *sgid_tbl)
591 {
592 int i;
593
594 for (i = 0; i < sgid_tbl->max; i++) {
595 if (memcmp(&sgid_tbl->tbl[i], &bnxt_qplib_gid_zero,
596 sizeof(bnxt_qplib_gid_zero)))
597 bnxt_qplib_del_sgid(sgid_tbl, &sgid_tbl->tbl[i].gid,
598 sgid_tbl->tbl[i].vlan_id, true);
599 }
600 memset(sgid_tbl->tbl, 0, sizeof(*sgid_tbl->tbl) * sgid_tbl->max);
601 memset(sgid_tbl->hw_id, -1, sizeof(u16) * sgid_tbl->max);
602 memset(sgid_tbl->vlan, 0, sizeof(u8) * sgid_tbl->max);
603 sgid_tbl->active = 0;
604 }
605
bnxt_qplib_init_sgid_tbl(struct bnxt_qplib_sgid_tbl * sgid_tbl,struct net_device * netdev)606 static void bnxt_qplib_init_sgid_tbl(struct bnxt_qplib_sgid_tbl *sgid_tbl,
607 struct net_device *netdev)
608 {
609 u32 i;
610
611 for (i = 0; i < sgid_tbl->max; i++)
612 sgid_tbl->tbl[i].vlan_id = 0xffff;
613
614 memset(sgid_tbl->hw_id, -1, sizeof(u16) * sgid_tbl->max);
615 }
616
617 /* PDs */
bnxt_qplib_alloc_pd(struct bnxt_qplib_res * res,struct bnxt_qplib_pd * pd)618 int bnxt_qplib_alloc_pd(struct bnxt_qplib_res *res, struct bnxt_qplib_pd *pd)
619 {
620 struct bnxt_qplib_pd_tbl *pdt = &res->pd_tbl;
621 u32 bit_num;
622 int rc = 0;
623
624 mutex_lock(&res->pd_tbl_lock);
625 bit_num = find_first_bit(pdt->tbl, pdt->max);
626 if (bit_num == pdt->max) {
627 rc = -ENOMEM;
628 goto exit;
629 }
630
631 /* Found unused PD */
632 clear_bit(bit_num, pdt->tbl);
633 pd->id = bit_num;
634 exit:
635 mutex_unlock(&res->pd_tbl_lock);
636 return rc;
637 }
638
bnxt_qplib_dealloc_pd(struct bnxt_qplib_res * res,struct bnxt_qplib_pd_tbl * pdt,struct bnxt_qplib_pd * pd)639 int bnxt_qplib_dealloc_pd(struct bnxt_qplib_res *res,
640 struct bnxt_qplib_pd_tbl *pdt,
641 struct bnxt_qplib_pd *pd)
642 {
643 int rc = 0;
644
645 mutex_lock(&res->pd_tbl_lock);
646 if (test_and_set_bit(pd->id, pdt->tbl)) {
647 dev_warn(&res->pdev->dev, "Freeing an unused PD? pdn = %d\n",
648 pd->id);
649 rc = -EINVAL;
650 goto exit;
651 }
652 pd->id = 0;
653 exit:
654 mutex_unlock(&res->pd_tbl_lock);
655 return rc;
656 }
657
bnxt_qplib_free_pd_tbl(struct bnxt_qplib_pd_tbl * pdt)658 static void bnxt_qplib_free_pd_tbl(struct bnxt_qplib_pd_tbl *pdt)
659 {
660 kfree(pdt->tbl);
661 pdt->tbl = NULL;
662 pdt->max = 0;
663 }
664
bnxt_qplib_alloc_pd_tbl(struct bnxt_qplib_res * res,struct bnxt_qplib_pd_tbl * pdt,u32 max)665 static int bnxt_qplib_alloc_pd_tbl(struct bnxt_qplib_res *res,
666 struct bnxt_qplib_pd_tbl *pdt,
667 u32 max)
668 {
669 u32 bytes;
670
671 bytes = max >> 3;
672 if (!bytes)
673 bytes = 1;
674 pdt->tbl = kmalloc(bytes, GFP_KERNEL);
675 if (!pdt->tbl)
676 return -ENOMEM;
677
678 pdt->max = max;
679 memset((u8 *)pdt->tbl, 0xFF, bytes);
680 mutex_init(&res->pd_tbl_lock);
681
682 return 0;
683 }
684
685 /* DPIs */
bnxt_qplib_alloc_dpi(struct bnxt_qplib_res * res,struct bnxt_qplib_dpi * dpi,void * app,u8 type)686 int bnxt_qplib_alloc_dpi(struct bnxt_qplib_res *res,
687 struct bnxt_qplib_dpi *dpi,
688 void *app, u8 type)
689 {
690 struct bnxt_qplib_dpi_tbl *dpit = &res->dpi_tbl;
691 struct bnxt_qplib_reg_desc *reg;
692 u32 bit_num;
693 u64 umaddr;
694
695 reg = &dpit->wcreg;
696 mutex_lock(&res->dpi_tbl_lock);
697
698 bit_num = find_first_bit(dpit->tbl, dpit->max);
699 if (bit_num == dpit->max) {
700 mutex_unlock(&res->dpi_tbl_lock);
701 return -ENOMEM;
702 }
703
704 /* Found unused DPI */
705 clear_bit(bit_num, dpit->tbl);
706 dpit->app_tbl[bit_num] = app;
707
708 dpi->bit = bit_num;
709 dpi->dpi = bit_num + (reg->offset - dpit->ucreg.offset) / PAGE_SIZE;
710
711 umaddr = reg->bar_base + reg->offset + bit_num * PAGE_SIZE;
712 dpi->umdbr = umaddr;
713
714 switch (type) {
715 case BNXT_QPLIB_DPI_TYPE_KERNEL:
716 /* privileged dbr was already mapped just initialize it. */
717 dpi->umdbr = dpit->ucreg.bar_base +
718 dpit->ucreg.offset + bit_num * PAGE_SIZE;
719 dpi->dbr = dpit->priv_db;
720 dpi->dpi = dpi->bit;
721 break;
722 case BNXT_QPLIB_DPI_TYPE_WC:
723 dpi->dbr = ioremap_wc(umaddr, PAGE_SIZE);
724 break;
725 default:
726 dpi->dbr = ioremap(umaddr, PAGE_SIZE);
727 break;
728 }
729
730 dpi->type = type;
731 mutex_unlock(&res->dpi_tbl_lock);
732 return 0;
733
734 }
735
bnxt_qplib_dealloc_dpi(struct bnxt_qplib_res * res,struct bnxt_qplib_dpi * dpi)736 int bnxt_qplib_dealloc_dpi(struct bnxt_qplib_res *res,
737 struct bnxt_qplib_dpi *dpi)
738 {
739 struct bnxt_qplib_dpi_tbl *dpit = &res->dpi_tbl;
740
741 mutex_lock(&res->dpi_tbl_lock);
742 if (dpi->dpi && dpi->type != BNXT_QPLIB_DPI_TYPE_KERNEL)
743 pci_iounmap(res->pdev, dpi->dbr);
744
745 if (test_and_set_bit(dpi->bit, dpit->tbl)) {
746 dev_warn(&res->pdev->dev,
747 "Freeing an unused DPI? dpi = %d, bit = %d\n",
748 dpi->dpi, dpi->bit);
749 mutex_unlock(&res->dpi_tbl_lock);
750 return -EINVAL;
751 }
752 if (dpit->app_tbl)
753 dpit->app_tbl[dpi->bit] = NULL;
754 memset(dpi, 0, sizeof(*dpi));
755 mutex_unlock(&res->dpi_tbl_lock);
756 return 0;
757 }
758
bnxt_qplib_free_dpi_tbl(struct bnxt_qplib_res * res,struct bnxt_qplib_dpi_tbl * dpit)759 static void bnxt_qplib_free_dpi_tbl(struct bnxt_qplib_res *res,
760 struct bnxt_qplib_dpi_tbl *dpit)
761 {
762 kfree(dpit->tbl);
763 kfree(dpit->app_tbl);
764 dpit->tbl = NULL;
765 dpit->app_tbl = NULL;
766 dpit->max = 0;
767 }
768
bnxt_qplib_alloc_dpi_tbl(struct bnxt_qplib_res * res,struct bnxt_qplib_dev_attr * dev_attr)769 static int bnxt_qplib_alloc_dpi_tbl(struct bnxt_qplib_res *res,
770 struct bnxt_qplib_dev_attr *dev_attr)
771 {
772 struct bnxt_qplib_dpi_tbl *dpit;
773 struct bnxt_qplib_reg_desc *reg;
774 unsigned long bar_len;
775 u32 dbr_offset;
776 u32 bytes;
777
778 dpit = &res->dpi_tbl;
779 reg = &dpit->wcreg;
780
781 if (!bnxt_qplib_is_chip_gen_p5_p7(res->cctx)) {
782 /* Offest should come from L2 driver */
783 dbr_offset = dev_attr->l2_db_size;
784 dpit->ucreg.offset = dbr_offset;
785 dpit->wcreg.offset = dbr_offset;
786 }
787
788 bar_len = pci_resource_len(res->pdev, reg->bar_id);
789 dpit->max = (bar_len - reg->offset) / PAGE_SIZE;
790 if (dev_attr->max_dpi)
791 dpit->max = min_t(u32, dpit->max, dev_attr->max_dpi);
792
793 dpit->app_tbl = kcalloc(dpit->max, sizeof(void *), GFP_KERNEL);
794 if (!dpit->app_tbl)
795 return -ENOMEM;
796
797 bytes = dpit->max >> 3;
798 if (!bytes)
799 bytes = 1;
800
801 dpit->tbl = kmalloc(bytes, GFP_KERNEL);
802 if (!dpit->tbl) {
803 kfree(dpit->app_tbl);
804 dpit->app_tbl = NULL;
805 return -ENOMEM;
806 }
807
808 memset((u8 *)dpit->tbl, 0xFF, bytes);
809 mutex_init(&res->dpi_tbl_lock);
810 dpit->priv_db = dpit->ucreg.bar_reg + dpit->ucreg.offset;
811
812 return 0;
813
814 }
815
816 /* Stats */
bnxt_qplib_free_stats_ctx(struct pci_dev * pdev,struct bnxt_qplib_stats * stats)817 void bnxt_qplib_free_stats_ctx(struct pci_dev *pdev,
818 struct bnxt_qplib_stats *stats)
819 {
820 if (stats->dma) {
821 dma_free_coherent(&pdev->dev, stats->size,
822 stats->dma, stats->dma_map);
823 }
824 memset(stats, 0, sizeof(*stats));
825 stats->fw_id = -1;
826 }
827
bnxt_qplib_alloc_stats_ctx(struct pci_dev * pdev,struct bnxt_qplib_chip_ctx * cctx,struct bnxt_qplib_stats * stats)828 int bnxt_qplib_alloc_stats_ctx(struct pci_dev *pdev,
829 struct bnxt_qplib_chip_ctx *cctx,
830 struct bnxt_qplib_stats *stats)
831 {
832 memset(stats, 0, sizeof(*stats));
833 stats->fw_id = -1;
834 stats->size = cctx->hw_stats_size;
835 stats->dma = dma_alloc_coherent(&pdev->dev, stats->size,
836 &stats->dma_map, GFP_KERNEL);
837 if (!stats->dma) {
838 dev_err(&pdev->dev, "Stats DMA allocation failed\n");
839 return -ENOMEM;
840 }
841 return 0;
842 }
843
bnxt_qplib_cleanup_res(struct bnxt_qplib_res * res)844 void bnxt_qplib_cleanup_res(struct bnxt_qplib_res *res)
845 {
846 bnxt_qplib_cleanup_sgid_tbl(res, &res->sgid_tbl);
847 }
848
bnxt_qplib_init_res(struct bnxt_qplib_res * res)849 int bnxt_qplib_init_res(struct bnxt_qplib_res *res)
850 {
851 bnxt_qplib_init_sgid_tbl(&res->sgid_tbl, res->netdev);
852
853 return 0;
854 }
855
bnxt_qplib_free_res(struct bnxt_qplib_res * res)856 void bnxt_qplib_free_res(struct bnxt_qplib_res *res)
857 {
858 kfree(res->rcfw->qp_tbl);
859 bnxt_qplib_free_sgid_tbl(res, &res->sgid_tbl);
860 bnxt_qplib_free_pd_tbl(&res->pd_tbl);
861 bnxt_qplib_free_dpi_tbl(res, &res->dpi_tbl);
862 }
863
bnxt_qplib_alloc_res(struct bnxt_qplib_res * res,struct net_device * netdev)864 int bnxt_qplib_alloc_res(struct bnxt_qplib_res *res, struct net_device *netdev)
865 {
866 struct bnxt_qplib_rcfw *rcfw = res->rcfw;
867 struct bnxt_qplib_dev_attr *dev_attr;
868 int rc;
869
870 res->netdev = netdev;
871 dev_attr = res->dattr;
872
873 /* Allocate one extra to hold the QP1 entries */
874 rcfw->qp_tbl_size = max_t(u32, BNXT_RE_MAX_QPC_COUNT + 1, dev_attr->max_qp);
875 rcfw->qp_tbl = kcalloc(rcfw->qp_tbl_size, sizeof(struct bnxt_qplib_qp_node),
876 GFP_KERNEL);
877 if (!rcfw->qp_tbl)
878 return -ENOMEM;
879
880 rc = bnxt_qplib_alloc_sgid_tbl(res, &res->sgid_tbl, dev_attr->max_sgid);
881 if (rc)
882 goto fail;
883
884 rc = bnxt_qplib_alloc_pd_tbl(res, &res->pd_tbl, dev_attr->max_pd);
885 if (rc)
886 goto fail;
887
888 rc = bnxt_qplib_alloc_dpi_tbl(res, dev_attr);
889 if (rc)
890 goto fail;
891
892 return 0;
893 fail:
894 bnxt_qplib_free_res(res);
895 return rc;
896 }
897
bnxt_qplib_unmap_db_bar(struct bnxt_qplib_res * res)898 void bnxt_qplib_unmap_db_bar(struct bnxt_qplib_res *res)
899 {
900 struct bnxt_qplib_reg_desc *reg;
901
902 reg = &res->dpi_tbl.ucreg;
903 if (reg->bar_reg)
904 pci_iounmap(res->pdev, reg->bar_reg);
905 reg->bar_reg = NULL;
906 reg->bar_base = 0;
907 reg->len = 0;
908 reg->bar_id = 0;
909 }
910
bnxt_qplib_map_db_bar(struct bnxt_qplib_res * res)911 int bnxt_qplib_map_db_bar(struct bnxt_qplib_res *res)
912 {
913 struct bnxt_qplib_reg_desc *ucreg;
914 struct bnxt_qplib_reg_desc *wcreg;
915
916 wcreg = &res->dpi_tbl.wcreg;
917 wcreg->bar_id = RCFW_DBR_PCI_BAR_REGION;
918 wcreg->bar_base = pci_resource_start(res->pdev, wcreg->bar_id);
919
920 ucreg = &res->dpi_tbl.ucreg;
921 ucreg->bar_id = RCFW_DBR_PCI_BAR_REGION;
922 ucreg->bar_base = pci_resource_start(res->pdev, ucreg->bar_id);
923 ucreg->len = ucreg->offset + PAGE_SIZE;
924 if (!ucreg->len || ((ucreg->len & (PAGE_SIZE - 1)) != 0)) {
925 dev_err(&res->pdev->dev, "QPLIB: invalid dbr length %d",
926 (int)ucreg->len);
927 return -EINVAL;
928 }
929 ucreg->bar_reg = ioremap(ucreg->bar_base, ucreg->len);
930 if (!ucreg->bar_reg) {
931 dev_err(&res->pdev->dev, "privileged dpi map failed!");
932 return -ENOMEM;
933 }
934
935 return 0;
936 }
937
bnxt_qplib_determine_atomics(struct pci_dev * dev)938 int bnxt_qplib_determine_atomics(struct pci_dev *dev)
939 {
940 int comp;
941 u16 ctl2;
942
943 comp = pci_enable_atomic_ops_to_root(dev,
944 PCI_EXP_DEVCAP2_ATOMIC_COMP32);
945 if (comp)
946 return -EOPNOTSUPP;
947 comp = pci_enable_atomic_ops_to_root(dev,
948 PCI_EXP_DEVCAP2_ATOMIC_COMP64);
949 if (comp)
950 return -EOPNOTSUPP;
951 pcie_capability_read_word(dev, PCI_EXP_DEVCTL2, &ctl2);
952 return !(ctl2 & PCI_EXP_DEVCTL2_ATOMIC_REQ);
953 }
954