* Allocate a mempool for Multi-Packet RQ. All configured Rx queues share the * mempool. If already allocated, reuse it if there're enough elements. * Otherwise, resize it. * * @param dev * Pointer to Ethernet device. * * @return * 0 on success, negative errno value on failure. */
| 1404 | * 0 on success, negative errno value on failure. |
| 1405 | */ |
| 1406 | int |
| 1407 | mlx5_mprq_alloc_mp(struct rte_eth_dev *dev) |
| 1408 | { |
| 1409 | struct mlx5_priv *priv = dev->data->dev_private; |
| 1410 | struct rte_mempool *mp = priv->mprq_mp; |
| 1411 | char name[RTE_MEMPOOL_NAMESIZE]; |
| 1412 | unsigned int desc = 0; |
| 1413 | unsigned int buf_len; |
| 1414 | unsigned int obj_num; |
| 1415 | unsigned int obj_size; |
| 1416 | unsigned int log_strd_num = 0; |
| 1417 | unsigned int log_strd_sz = 0; |
| 1418 | unsigned int i; |
| 1419 | unsigned int n_ibv = 0; |
| 1420 | int ret; |
| 1421 | |
| 1422 | if (!mlx5_mprq_enabled(dev)) |
| 1423 | return 0; |
| 1424 | /* Count the total number of descriptors configured. */ |
| 1425 | for (i = 0; i != priv->rxqs_n; ++i) { |
| 1426 | struct mlx5_rxq_ctrl *rxq_ctrl = mlx5_rxq_ctrl_get(dev, i); |
| 1427 | struct mlx5_rxq_data *rxq; |
| 1428 | |
| 1429 | if (rxq_ctrl == NULL || rxq_ctrl->is_hairpin) |
| 1430 | continue; |
| 1431 | rxq = &rxq_ctrl->rxq; |
| 1432 | n_ibv++; |
| 1433 | desc += 1 << rxq->elts_n; |
| 1434 | /* Get the max number of strides. */ |
| 1435 | if (log_strd_num < rxq->log_strd_num) |
| 1436 | log_strd_num = rxq->log_strd_num; |
| 1437 | /* Get the max size of a stride. */ |
| 1438 | if (log_strd_sz < rxq->log_strd_sz) |
| 1439 | log_strd_sz = rxq->log_strd_sz; |
| 1440 | } |
| 1441 | MLX5_ASSERT(log_strd_num && log_strd_sz); |
| 1442 | buf_len = RTE_BIT32(log_strd_num) * RTE_BIT32(log_strd_sz); |
| 1443 | obj_size = sizeof(struct mlx5_mprq_buf) + buf_len + |
| 1444 | RTE_BIT32(log_strd_num) * |
| 1445 | sizeof(struct rte_mbuf_ext_shared_info) + |
| 1446 | RTE_PKTMBUF_HEADROOM; |
| 1447 | /* |
| 1448 | * Received packets can be either memcpy'd or externally referenced. In |
| 1449 | * case that the packet is attached to an mbuf as an external buffer, as |
| 1450 | * it isn't possible to predict how the buffers will be queued by |
| 1451 | * application, there's no option to exactly pre-allocate needed buffers |
| 1452 | * in advance but to speculatively prepares enough buffers. |
| 1453 | * |
| 1454 | * In the data path, if this Mempool is depleted, PMD will try to memcpy |
| 1455 | * received packets to buffers provided by application (rxq->mp) until |
| 1456 | * this Mempool gets available again. |
| 1457 | */ |
| 1458 | desc *= 4; |
| 1459 | obj_num = desc + MLX5_MPRQ_MP_CACHE_SZ * n_ibv; |
| 1460 | /* |
| 1461 | * rte_mempool_create_empty() has sanity check to refuse large cache |
| 1462 | * size compared to the number of elements. |
| 1463 | * CACHE_FLUSHTHRESH_MULTIPLIER is defined in a C file, so using a |
no test coverage detected