Skip to content

Commit ee3d7c6

Browse files
committed
Merge branch 'mlx5-updates'
Saeed Mahameed says: ==================== Mellanox 100G mlx5 updates 2016-11-29 The following series from Tariq and Roi, provides some critical fixes and updates for the mlx5e driver. From Tariq: - Fix driver coherent memory huge allocation issues by fragmenting completion queues, in a way that is transparent to the netdev driver by providing a new buffer type "mlx5_frag_buf" with the same access API. - Create UMR MKey per RQ to have better scalability. From Roi: - Some fixes for the encap-decap support and tc flower added lately to the mlx5e driver. v1->v2: - Fix start index in error flow of mlx5_frag_buf_alloc_node, pointed out by Eric. This series was generated against commit: 31ac1c1 ("geneve: fix ip_hdr_len reserved for geneve6 tunnel.") ==================== Signed-off-by: David S. Miller <davem@davemloft.net>
2 parents 6c0c620 + 5067b60 commit ee3d7c6

File tree

8 files changed

+215
-135
lines changed

8 files changed

+215
-135
lines changed

drivers/net/ethernet/mellanox/mlx5/core/alloc.c

Lines changed: 66 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -106,6 +106,63 @@ void mlx5_buf_free(struct mlx5_core_dev *dev, struct mlx5_buf *buf)
106106
}
107107
EXPORT_SYMBOL_GPL(mlx5_buf_free);
108108

109+
int mlx5_frag_buf_alloc_node(struct mlx5_core_dev *dev, int size,
110+
struct mlx5_frag_buf *buf, int node)
111+
{
112+
int i;
113+
114+
buf->size = size;
115+
buf->npages = 1 << get_order(size);
116+
buf->page_shift = PAGE_SHIFT;
117+
buf->frags = kcalloc(buf->npages, sizeof(struct mlx5_buf_list),
118+
GFP_KERNEL);
119+
if (!buf->frags)
120+
goto err_out;
121+
122+
for (i = 0; i < buf->npages; i++) {
123+
struct mlx5_buf_list *frag = &buf->frags[i];
124+
int frag_sz = min_t(int, size, PAGE_SIZE);
125+
126+
frag->buf = mlx5_dma_zalloc_coherent_node(dev, frag_sz,
127+
&frag->map, node);
128+
if (!frag->buf)
129+
goto err_free_buf;
130+
if (frag->map & ((1 << buf->page_shift) - 1)) {
131+
dma_free_coherent(&dev->pdev->dev, frag_sz,
132+
buf->frags[i].buf, buf->frags[i].map);
133+
mlx5_core_warn(dev, "unexpected map alignment: 0x%p, page_shift=%d\n",
134+
(void *)frag->map, buf->page_shift);
135+
goto err_free_buf;
136+
}
137+
size -= frag_sz;
138+
}
139+
140+
return 0;
141+
142+
err_free_buf:
143+
while (i--)
144+
dma_free_coherent(&dev->pdev->dev, PAGE_SIZE, buf->frags[i].buf,
145+
buf->frags[i].map);
146+
kfree(buf->frags);
147+
err_out:
148+
return -ENOMEM;
149+
}
150+
151+
void mlx5_frag_buf_free(struct mlx5_core_dev *dev, struct mlx5_frag_buf *buf)
152+
{
153+
int size = buf->size;
154+
int i;
155+
156+
for (i = 0; i < buf->npages; i++) {
157+
int frag_sz = min_t(int, size, PAGE_SIZE);
158+
159+
dma_free_coherent(&dev->pdev->dev, frag_sz, buf->frags[i].buf,
160+
buf->frags[i].map);
161+
size -= frag_sz;
162+
}
163+
kfree(buf->frags);
164+
}
165+
109166
static struct mlx5_db_pgdir *mlx5_alloc_db_pgdir(struct mlx5_core_dev *dev,
110167
int node)
111168
{
@@ -230,3 +287,12 @@ void mlx5_fill_page_array(struct mlx5_buf *buf, __be64 *pas)
230287
}
231288
}
232289
EXPORT_SYMBOL_GPL(mlx5_fill_page_array);
290+
291+
void mlx5_fill_page_frag_array(struct mlx5_frag_buf *buf, __be64 *pas)
292+
{
293+
int i;
294+
295+
for (i = 0; i < buf->npages; i++)
296+
pas[i] = cpu_to_be64(buf->frags[i].map);
297+
}
298+
EXPORT_SYMBOL_GPL(mlx5_fill_page_frag_array);

drivers/net/ethernet/mellanox/mlx5/core/en.h

Lines changed: 6 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -77,9 +77,9 @@
7777
MLX5_MPWRQ_WQE_PAGE_ORDER)
7878

7979
#define MLX5_MTT_OCTW(npages) (ALIGN(npages, 8) / 2)
80-
#define MLX5E_REQUIRED_MTTS(rqs, wqes)\
81-
(rqs * wqes * ALIGN(MLX5_MPWRQ_PAGES_PER_WQE, 8))
82-
#define MLX5E_VALID_NUM_MTTS(num_mtts) (MLX5_MTT_OCTW(num_mtts) <= U16_MAX)
80+
#define MLX5E_REQUIRED_MTTS(wqes) \
81+
(wqes * ALIGN(MLX5_MPWRQ_PAGES_PER_WQE, 8))
82+
#define MLX5E_VALID_NUM_MTTS(num_mtts) (MLX5_MTT_OCTW(num_mtts) - 1 <= U16_MAX)
8383

8484
#define MLX5_UMR_ALIGN (2048)
8585
#define MLX5_MPWRQ_SMALL_PACKET_THRESHOLD (128)
@@ -286,7 +286,7 @@ struct mlx5e_cq {
286286
u16 decmprs_wqe_counter;
287287

288288
/* control */
289-
struct mlx5_wq_ctrl wq_ctrl;
289+
struct mlx5_frag_wq_ctrl wq_ctrl;
290290
} ____cacheline_aligned_in_smp;
291291

292292
struct mlx5e_rq;
@@ -347,7 +347,6 @@ struct mlx5e_rq {
347347
struct {
348348
struct mlx5e_mpw_info *info;
349349
void *mtt_no_align;
350-
u32 mtt_offset;
351350
} mpwqe;
352351
};
353352
struct {
@@ -382,6 +381,7 @@ struct mlx5e_rq {
382381
u32 rqn;
383382
struct mlx5e_channel *channel;
384383
struct mlx5e_priv *priv;
384+
struct mlx5_core_mkey umr_mkey;
385385
} ____cacheline_aligned_in_smp;
386386

387387
struct mlx5e_umr_dma_info {
@@ -689,7 +689,6 @@ struct mlx5e_priv {
689689

690690
unsigned long state;
691691
struct mutex state_lock; /* Protects Interface state */
692-
struct mlx5_core_mkey umr_mkey;
693692
struct mlx5e_rq drop_rq;
694693

695694
struct mlx5e_channel **channel;
@@ -838,8 +837,7 @@ static inline void mlx5e_cq_arm(struct mlx5e_cq *cq)
838837

839838
static inline u32 mlx5e_get_wqe_mtt_offset(struct mlx5e_rq *rq, u16 wqe_ix)
840839
{
841-
return rq->mpwqe.mtt_offset +
842-
wqe_ix * ALIGN(MLX5_MPWRQ_PAGES_PER_WQE, 8);
840+
return wqe_ix * ALIGN(MLX5_MPWRQ_PAGES_PER_WQE, 8);
843841
}
844842

845843
static inline int mlx5e_get_max_num_channels(struct mlx5_core_dev *mdev)

drivers/net/ethernet/mellanox/mlx5/core/en_ethtool.c

Lines changed: 1 addition & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -499,8 +499,7 @@ static int mlx5e_set_ringparam(struct net_device *dev,
499499
return -EINVAL;
500500
}
501501

502-
num_mtts = MLX5E_REQUIRED_MTTS(priv->params.num_channels,
503-
rx_pending_wqes);
502+
num_mtts = MLX5E_REQUIRED_MTTS(rx_pending_wqes);
504503
if (priv->params.rq_wq_type == MLX5_WQ_TYPE_LINKED_LIST_STRIDING_RQ &&
505504
!MLX5E_VALID_NUM_MTTS(num_mtts)) {
506505
netdev_info(dev, "%s: rx_pending (%d) request can't be satisfied, try to reduce.\n",
@@ -565,7 +564,6 @@ static int mlx5e_set_channels(struct net_device *dev,
565564
unsigned int count = ch->combined_count;
566565
bool arfs_enabled;
567566
bool was_opened;
568-
u32 num_mtts;
569567
int err = 0;
570568

571569
if (!count) {
@@ -584,14 +582,6 @@ static int mlx5e_set_channels(struct net_device *dev,
584582
return -EINVAL;
585583
}
586584

587-
num_mtts = MLX5E_REQUIRED_MTTS(count, BIT(priv->params.log_rq_size));
588-
if (priv->params.rq_wq_type == MLX5_WQ_TYPE_LINKED_LIST_STRIDING_RQ &&
589-
!MLX5E_VALID_NUM_MTTS(num_mtts)) {
590-
netdev_info(dev, "%s: rx count (%d) request can't be satisfied, try to reduce.\n",
591-
__func__, count);
592-
return -EINVAL;
593-
}
594-
595585
if (priv->params.num_channels == count)
596586
return 0;
597587

drivers/net/ethernet/mellanox/mlx5/core/en_main.c

Lines changed: 63 additions & 58 deletions
Original file line numberDiff line numberDiff line change
@@ -471,6 +471,52 @@ static void mlx5e_rq_free_mpwqe_info(struct mlx5e_rq *rq)
471471
kfree(rq->mpwqe.info);
472472
}
473473

474+
static int mlx5e_create_umr_mkey(struct mlx5e_priv *priv,
475+
u64 npages, u8 page_shift,
476+
struct mlx5_core_mkey *umr_mkey)
477+
{
478+
struct mlx5_core_dev *mdev = priv->mdev;
479+
int inlen = MLX5_ST_SZ_BYTES(create_mkey_in);
480+
void *mkc;
481+
u32 *in;
482+
int err;
483+
484+
if (!MLX5E_VALID_NUM_MTTS(npages))
485+
return -EINVAL;
486+
487+
in = mlx5_vzalloc(inlen);
488+
if (!in)
489+
return -ENOMEM;
490+
491+
mkc = MLX5_ADDR_OF(create_mkey_in, in, memory_key_mkey_entry);
492+
493+
MLX5_SET(mkc, mkc, free, 1);
494+
MLX5_SET(mkc, mkc, umr_en, 1);
495+
MLX5_SET(mkc, mkc, lw, 1);
496+
MLX5_SET(mkc, mkc, lr, 1);
497+
MLX5_SET(mkc, mkc, access_mode, MLX5_MKC_ACCESS_MODE_MTT);
498+
499+
MLX5_SET(mkc, mkc, qpn, 0xffffff);
500+
MLX5_SET(mkc, mkc, pd, mdev->mlx5e_res.pdn);
501+
MLX5_SET64(mkc, mkc, len, npages << page_shift);
502+
MLX5_SET(mkc, mkc, translations_octword_size,
503+
MLX5_MTT_OCTW(npages));
504+
MLX5_SET(mkc, mkc, log_page_size, page_shift);
505+
506+
err = mlx5_core_create_mkey(mdev, umr_mkey, in, inlen);
507+
508+
kvfree(in);
509+
return err;
510+
}
511+
512+
static int mlx5e_create_rq_umr_mkey(struct mlx5e_rq *rq)
513+
{
514+
struct mlx5e_priv *priv = rq->priv;
515+
u64 num_mtts = MLX5E_REQUIRED_MTTS(BIT(priv->params.log_rq_size));
516+
517+
return mlx5e_create_umr_mkey(priv, num_mtts, PAGE_SHIFT, &rq->umr_mkey);
518+
}
519+
474520
static int mlx5e_create_rq(struct mlx5e_channel *c,
475521
struct mlx5e_rq_param *param,
476522
struct mlx5e_rq *rq)
@@ -527,18 +573,20 @@ static int mlx5e_create_rq(struct mlx5e_channel *c,
527573
rq->alloc_wqe = mlx5e_alloc_rx_mpwqe;
528574
rq->dealloc_wqe = mlx5e_dealloc_rx_mpwqe;
529575

530-
rq->mpwqe.mtt_offset = c->ix *
531-
MLX5E_REQUIRED_MTTS(1, BIT(priv->params.log_rq_size));
532-
533576
rq->mpwqe_stride_sz = BIT(priv->params.mpwqe_log_stride_sz);
534577
rq->mpwqe_num_strides = BIT(priv->params.mpwqe_log_num_strides);
535578

536579
rq->buff.wqe_sz = rq->mpwqe_stride_sz * rq->mpwqe_num_strides;
537580
byte_count = rq->buff.wqe_sz;
538-
rq->mkey_be = cpu_to_be32(c->priv->umr_mkey.key);
539-
err = mlx5e_rq_alloc_mpwqe_info(rq, c);
581+
582+
err = mlx5e_create_rq_umr_mkey(rq);
540583
if (err)
541584
goto err_rq_wq_destroy;
585+
rq->mkey_be = cpu_to_be32(rq->umr_mkey.key);
586+
587+
err = mlx5e_rq_alloc_mpwqe_info(rq, c);
588+
if (err)
589+
goto err_destroy_umr_mkey;
542590
break;
543591
default: /* MLX5_WQ_TYPE_LINKED_LIST */
544592
rq->dma_info = kzalloc_node(wq_sz * sizeof(*rq->dma_info),
@@ -589,6 +637,9 @@ static int mlx5e_create_rq(struct mlx5e_channel *c,
589637

590638
return 0;
591639

640+
err_destroy_umr_mkey:
641+
mlx5_core_destroy_mkey(mdev, &rq->umr_mkey);
642+
592643
err_rq_wq_destroy:
593644
if (rq->xdp_prog)
594645
bpf_prog_put(rq->xdp_prog);
@@ -607,6 +658,7 @@ static void mlx5e_destroy_rq(struct mlx5e_rq *rq)
607658
switch (rq->wq_type) {
608659
case MLX5_WQ_TYPE_LINKED_LIST_STRIDING_RQ:
609660
mlx5e_rq_free_mpwqe_info(rq);
661+
mlx5_core_destroy_mkey(rq->priv->mdev, &rq->umr_mkey);
610662
break;
611663
default: /* MLX5_WQ_TYPE_LINKED_LIST */
612664
kfree(rq->dma_info);
@@ -1201,7 +1253,7 @@ static int mlx5e_create_cq(struct mlx5e_channel *c,
12011253

12021254
static void mlx5e_destroy_cq(struct mlx5e_cq *cq)
12031255
{
1204-
mlx5_wq_destroy(&cq->wq_ctrl);
1256+
mlx5_cqwq_destroy(&cq->wq_ctrl);
12051257
}
12061258

12071259
static int mlx5e_enable_cq(struct mlx5e_cq *cq, struct mlx5e_cq_param *param)
@@ -1218,7 +1270,7 @@ static int mlx5e_enable_cq(struct mlx5e_cq *cq, struct mlx5e_cq_param *param)
12181270
int err;
12191271

12201272
inlen = MLX5_ST_SZ_BYTES(create_cq_in) +
1221-
sizeof(u64) * cq->wq_ctrl.buf.npages;
1273+
sizeof(u64) * cq->wq_ctrl.frag_buf.npages;
12221274
in = mlx5_vzalloc(inlen);
12231275
if (!in)
12241276
return -ENOMEM;
@@ -1227,15 +1279,15 @@ static int mlx5e_enable_cq(struct mlx5e_cq *cq, struct mlx5e_cq_param *param)
12271279

12281280
memcpy(cqc, param->cqc, sizeof(param->cqc));
12291281

1230-
mlx5_fill_page_array(&cq->wq_ctrl.buf,
1231-
(__be64 *)MLX5_ADDR_OF(create_cq_in, in, pas));
1282+
mlx5_fill_page_frag_array(&cq->wq_ctrl.frag_buf,
1283+
(__be64 *)MLX5_ADDR_OF(create_cq_in, in, pas));
12321284

12331285
mlx5_vector2eqn(mdev, param->eq_ix, &eqn, &irqn_not_used);
12341286

12351287
MLX5_SET(cqc, cqc, cq_period_mode, param->cq_period_mode);
12361288
MLX5_SET(cqc, cqc, c_eqn, eqn);
12371289
MLX5_SET(cqc, cqc, uar_page, mcq->uar->index);
1238-
MLX5_SET(cqc, cqc, log_page_size, cq->wq_ctrl.buf.page_shift -
1290+
MLX5_SET(cqc, cqc, log_page_size, cq->wq_ctrl.frag_buf.page_shift -
12391291
MLX5_ADAPTER_PAGE_SHIFT);
12401292
MLX5_SET64(cqc, cqc, dbr_addr, cq->wq_ctrl.db.dma);
12411293

@@ -3625,43 +3677,6 @@ static void mlx5e_destroy_q_counter(struct mlx5e_priv *priv)
36253677
mlx5_core_dealloc_q_counter(priv->mdev, priv->q_counter);
36263678
}
36273679

3628-
static int mlx5e_create_umr_mkey(struct mlx5e_priv *priv)
3629-
{
3630-
struct mlx5_core_dev *mdev = priv->mdev;
3631-
u64 npages = MLX5E_REQUIRED_MTTS(priv->profile->max_nch(mdev),
3632-
BIT(MLX5E_PARAMS_MAXIMUM_LOG_RQ_SIZE_MPW));
3633-
int inlen = MLX5_ST_SZ_BYTES(create_mkey_in);
3634-
void *mkc;
3635-
u32 *in;
3636-
int err;
3637-
3638-
in = mlx5_vzalloc(inlen);
3639-
if (!in)
3640-
return -ENOMEM;
3641-
3642-
mkc = MLX5_ADDR_OF(create_mkey_in, in, memory_key_mkey_entry);
3643-
3644-
npages = min_t(u32, ALIGN(U16_MAX, 4) * 2, npages);
3645-
3646-
MLX5_SET(mkc, mkc, free, 1);
3647-
MLX5_SET(mkc, mkc, umr_en, 1);
3648-
MLX5_SET(mkc, mkc, lw, 1);
3649-
MLX5_SET(mkc, mkc, lr, 1);
3650-
MLX5_SET(mkc, mkc, access_mode, MLX5_MKC_ACCESS_MODE_MTT);
3651-
3652-
MLX5_SET(mkc, mkc, qpn, 0xffffff);
3653-
MLX5_SET(mkc, mkc, pd, mdev->mlx5e_res.pdn);
3654-
MLX5_SET64(mkc, mkc, len, npages << PAGE_SHIFT);
3655-
MLX5_SET(mkc, mkc, translations_octword_size,
3656-
MLX5_MTT_OCTW(npages));
3657-
MLX5_SET(mkc, mkc, log_page_size, PAGE_SHIFT);
3658-
3659-
err = mlx5_core_create_mkey(mdev, &priv->umr_mkey, in, inlen);
3660-
3661-
kvfree(in);
3662-
return err;
3663-
}
3664-
36653680
static void mlx5e_nic_init(struct mlx5_core_dev *mdev,
36663681
struct net_device *netdev,
36673682
const struct mlx5e_profile *profile,
@@ -3868,15 +3883,9 @@ int mlx5e_attach_netdev(struct mlx5_core_dev *mdev, struct net_device *netdev)
38683883
profile = priv->profile;
38693884
clear_bit(MLX5E_STATE_DESTROYING, &priv->state);
38703885

3871-
err = mlx5e_create_umr_mkey(priv);
3872-
if (err) {
3873-
mlx5_core_err(mdev, "create umr mkey failed, %d\n", err);
3874-
goto out;
3875-
}
3876-
38773886
err = profile->init_tx(priv);
38783887
if (err)
3879-
goto err_destroy_umr_mkey;
3888+
goto out;
38803889

38813890
err = mlx5e_open_drop_rq(priv);
38823891
if (err) {
@@ -3916,9 +3925,6 @@ int mlx5e_attach_netdev(struct mlx5_core_dev *mdev, struct net_device *netdev)
39163925
err_cleanup_tx:
39173926
profile->cleanup_tx(priv);
39183927

3919-
err_destroy_umr_mkey:
3920-
mlx5_core_destroy_mkey(mdev, &priv->umr_mkey);
3921-
39223928
out:
39233929
return err;
39243930
}
@@ -3967,7 +3973,6 @@ void mlx5e_detach_netdev(struct mlx5_core_dev *mdev, struct net_device *netdev)
39673973
profile->cleanup_rx(priv);
39683974
mlx5e_close_drop_rq(priv);
39693975
profile->cleanup_tx(priv);
3970-
mlx5_core_destroy_mkey(priv->mdev, &priv->umr_mkey);
39713976
cancel_delayed_work_sync(&priv->update_stats_work);
39723977
}
39733978

0 commit comments

Comments
 (0)