Skip to content

Commit ab58a41

Browse files
Hariprasad Kelamdavem330
authored andcommitted
octeontx2-pf: cn10k: Get max mtu supported from admin function
CN10K supports max MTU of 16K on LMAC links and 64k on LBK links and Octeontx2 silicon supports 9K mtu on both links. Get the same from nix_get_hw_info mbox message in netdev probe. This patch also calculates receive buffer size required based on the MTU set. Signed-off-by: Hariprasad Kelam <[email protected]> Signed-off-by: Subbaraya Sundeep <[email protected]> Signed-off-by: Geetha sowjanya <[email protected]> Signed-off-by: Sunil Goutham <[email protected]> Signed-off-by: David S. Miller <[email protected]>
1 parent 6e54e1c commit ab58a41

File tree

7 files changed

+97
-18
lines changed

7 files changed

+97
-18
lines changed

drivers/net/ethernet/marvell/octeontx2/nic/cn10k.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -108,7 +108,7 @@ int cn10k_sq_aq_init(void *dev, u16 qidx, u16 sqb_aura)
108108
/* Only one SMQ is allocated, map all SQ's to that SMQ */
109109
aq->sq.smq = pfvf->hw.txschq_list[NIX_TXSCH_LVL_SMQ][0];
110110
/* FIXME: set based on NIX_AF_DWRR_RPM_MTU*/
111-
aq->sq.smq_rr_weight = OTX2_MAX_MTU;
111+
aq->sq.smq_rr_weight = pfvf->netdev->mtu;
112112
aq->sq.default_chan = pfvf->hw.tx_chan_base;
113113
aq->sq.sqe_stype = NIX_STYPE_STF; /* Cache SQB */
114114
aq->sq.sqb_aura = sqb_aura;

drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.c

Lines changed: 42 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -230,7 +230,6 @@ int otx2_hw_set_mtu(struct otx2_nic *pfvf, int mtu)
230230
return -ENOMEM;
231231
}
232232

233-
pfvf->max_frs = mtu + OTX2_ETH_HLEN;
234233
req->maxlen = pfvf->max_frs;
235234

236235
err = otx2_sync_mbox_msg(&pfvf->mbox);
@@ -606,8 +605,8 @@ int otx2_txschq_config(struct otx2_nic *pfvf, int lvl)
606605
/* Set topology e.t.c configuration */
607606
if (lvl == NIX_TXSCH_LVL_SMQ) {
608607
req->reg[0] = NIX_AF_SMQX_CFG(schq);
609-
req->regval[0] = ((OTX2_MAX_MTU + OTX2_ETH_HLEN) << 8) |
610-
OTX2_MIN_MTU;
608+
req->regval[0] = ((pfvf->netdev->max_mtu + OTX2_ETH_HLEN) << 8)
609+
| OTX2_MIN_MTU;
611610

612611
req->regval[0] |= (0x20ULL << 51) | (0x80ULL << 39) |
613612
(0x2ULL << 36);
@@ -1637,6 +1636,46 @@ void otx2_set_cints_affinity(struct otx2_nic *pfvf)
16371636
}
16381637
}
16391638

1639+
u16 otx2_get_max_mtu(struct otx2_nic *pfvf)
1640+
{
1641+
struct nix_hw_info *rsp;
1642+
struct msg_req *req;
1643+
u16 max_mtu;
1644+
int rc;
1645+
1646+
mutex_lock(&pfvf->mbox.lock);
1647+
1648+
req = otx2_mbox_alloc_msg_nix_get_hw_info(&pfvf->mbox);
1649+
if (!req) {
1650+
rc = -ENOMEM;
1651+
goto out;
1652+
}
1653+
1654+
rc = otx2_sync_mbox_msg(&pfvf->mbox);
1655+
if (!rc) {
1656+
rsp = (struct nix_hw_info *)
1657+
otx2_mbox_get_rsp(&pfvf->mbox.mbox, 0, &req->hdr);
1658+
1659+
/* HW counts VLAN insertion bytes (8 for double tag)
1660+
* irrespective of whether SQE is requesting to insert VLAN
1661+
* in the packet or not. Hence these 8 bytes have to be
1662+
* discounted from max packet size otherwise HW will throw
1663+
* SMQ errors
1664+
*/
1665+
max_mtu = rsp->max_mtu - 8 - OTX2_ETH_HLEN;
1666+
}
1667+
1668+
out:
1669+
mutex_unlock(&pfvf->mbox.lock);
1670+
if (rc) {
1671+
dev_warn(pfvf->dev,
1672+
"Failed to get MTU from hardware setting default value(1500)\n");
1673+
max_mtu = 1500;
1674+
}
1675+
return max_mtu;
1676+
}
1677+
EXPORT_SYMBOL(otx2_get_max_mtu);
1678+
16401679
#define M(_name, _id, _fn_name, _req_type, _rsp_type) \
16411680
int __weak \
16421681
otx2_mbox_up_handler_ ## _fn_name(struct otx2_nic *pfvf, \

drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -798,5 +798,5 @@ int otx2_del_macfilter(struct net_device *netdev, const u8 *mac);
798798
int otx2_add_macfilter(struct net_device *netdev, const u8 *mac);
799799
int otx2_enable_rxvlan(struct otx2_nic *pf, bool enable);
800800
int otx2_install_rxvlan_offload_flow(struct otx2_nic *pfvf);
801-
801+
u16 otx2_get_max_mtu(struct otx2_nic *pfvf);
802802
#endif /* OTX2_COMMON_H */

drivers/net/ethernet/marvell/octeontx2/nic/otx2_pf.c

Lines changed: 31 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1288,6 +1288,33 @@ static void otx2_free_sq_res(struct otx2_nic *pf)
12881288
}
12891289
}
12901290

1291+
static int otx2_get_rbuf_size(struct otx2_nic *pf, int mtu)
1292+
{
1293+
int frame_size;
1294+
int total_size;
1295+
int rbuf_size;
1296+
1297+
/* The data transferred by NIX to memory consists of actual packet
1298+
* plus additional data which has timestamp and/or EDSA/HIGIG2
1299+
* headers if interface is configured in corresponding modes.
1300+
* NIX transfers entire data using 6 segments/buffers and writes
1301+
* a CQE_RX descriptor with those segment addresses. First segment
1302+
* has additional data prepended to packet. Also software omits a
1303+
* headroom of 128 bytes and sizeof(struct skb_shared_info) in
1304+
* each segment. Hence the total size of memory needed
1305+
* to receive a packet with 'mtu' is:
1306+
* frame size = mtu + additional data;
1307+
* memory = frame_size + (headroom + struct skb_shared_info size) * 6;
1308+
* each receive buffer size = memory / 6;
1309+
*/
1310+
frame_size = mtu + OTX2_ETH_HLEN + OTX2_HW_TIMESTAMP_LEN;
1311+
total_size = frame_size + (OTX2_HEAD_ROOM +
1312+
OTX2_DATA_ALIGN(sizeof(struct skb_shared_info))) * 6;
1313+
rbuf_size = total_size / 6;
1314+
1315+
return ALIGN(rbuf_size, 2048);
1316+
}
1317+
12911318
static int otx2_init_hw_resources(struct otx2_nic *pf)
12921319
{
12931320
struct nix_lf_free_req *free_req;
@@ -1304,9 +1331,9 @@ static int otx2_init_hw_resources(struct otx2_nic *pf)
13041331
hw->sqpool_cnt = hw->tx_queues;
13051332
hw->pool_cnt = hw->rqpool_cnt + hw->sqpool_cnt;
13061333

1307-
/* Get the size of receive buffers to allocate */
1308-
pf->rbsize = RCV_FRAG_LEN(OTX2_HW_TIMESTAMP_LEN + pf->netdev->mtu +
1309-
OTX2_ETH_HLEN);
1334+
pf->max_frs = pf->netdev->mtu + OTX2_ETH_HLEN + OTX2_HW_TIMESTAMP_LEN;
1335+
1336+
pf->rbsize = otx2_get_rbuf_size(pf, pf->netdev->mtu);
13101337

13111338
mutex_lock(&mbox->lock);
13121339
/* NPA init */
@@ -2429,7 +2456,7 @@ static int otx2_probe(struct pci_dev *pdev, const struct pci_device_id *id)
24292456

24302457
/* MTU range: 64 - 9190 */
24312458
netdev->min_mtu = OTX2_MIN_MTU;
2432-
netdev->max_mtu = OTX2_MAX_MTU;
2459+
netdev->max_mtu = otx2_get_max_mtu(pf);
24332460

24342461
err = register_netdev(netdev);
24352462
if (err) {

drivers/net/ethernet/marvell/octeontx2/nic/otx2_txrx.c

Lines changed: 21 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -257,12 +257,11 @@ static bool otx2_check_rcv_errors(struct otx2_nic *pfvf,
257257
/* For now ignore all the NPC parser errors and
258258
* pass the packets to stack.
259259
*/
260-
if (cqe->sg.segs == 1)
261-
return false;
260+
return false;
262261
}
263262

264263
/* If RXALL is enabled pass on packets to stack. */
265-
if (cqe->sg.segs == 1 && (pfvf->netdev->features & NETIF_F_RXALL))
264+
if (pfvf->netdev->features & NETIF_F_RXALL)
266265
return false;
267266

268267
/* Free buffer back to pool */
@@ -277,9 +276,14 @@ static void otx2_rcv_pkt_handler(struct otx2_nic *pfvf,
277276
struct nix_cqe_rx_s *cqe)
278277
{
279278
struct nix_rx_parse_s *parse = &cqe->parse;
279+
struct nix_rx_sg_s *sg = &cqe->sg;
280280
struct sk_buff *skb = NULL;
281+
void *end, *start;
282+
u64 *seg_addr;
283+
u16 *seg_size;
284+
int seg;
281285

282-
if (unlikely(parse->errlev || parse->errcode || cqe->sg.segs > 1)) {
286+
if (unlikely(parse->errlev || parse->errcode)) {
283287
if (otx2_check_rcv_errors(pfvf, cqe, cq->cq_idx))
284288
return;
285289
}
@@ -288,9 +292,19 @@ static void otx2_rcv_pkt_handler(struct otx2_nic *pfvf,
288292
if (unlikely(!skb))
289293
return;
290294

291-
otx2_skb_add_frag(pfvf, skb, cqe->sg.seg_addr, cqe->sg.seg_size, parse);
292-
cq->pool_ptrs++;
293-
295+
start = (void *)sg;
296+
end = start + ((cqe->parse.desc_sizem1 + 1) * 16);
297+
while (start < end) {
298+
sg = (struct nix_rx_sg_s *)start;
299+
seg_addr = &sg->seg_addr;
300+
seg_size = (void *)sg;
301+
for (seg = 0; seg < sg->segs; seg++, seg_addr++) {
302+
otx2_skb_add_frag(pfvf, skb, *seg_addr, seg_size[seg],
303+
parse);
304+
cq->pool_ptrs++;
305+
}
306+
start += sizeof(*sg);
307+
}
294308
otx2_set_rxhash(pfvf, cqe, skb);
295309

296310
skb_record_rx_queue(skb, cq->cq_idx);

drivers/net/ethernet/marvell/octeontx2/nic/otx2_txrx.h

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,6 @@
2424

2525
#define OTX2_ETH_HLEN (VLAN_ETH_HLEN + VLAN_HLEN)
2626
#define OTX2_MIN_MTU 64
27-
#define OTX2_MAX_MTU (9212 - OTX2_ETH_HLEN)
2827

2928
#define OTX2_MAX_GSO_SEGS 255
3029
#define OTX2_MAX_FRAGS_IN_SQE 9

drivers/net/ethernet/marvell/octeontx2/nic/otx2_vf.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -586,7 +586,7 @@ static int otx2vf_probe(struct pci_dev *pdev, const struct pci_device_id *id)
586586

587587
/* MTU range: 68 - 9190 */
588588
netdev->min_mtu = OTX2_MIN_MTU;
589-
netdev->max_mtu = OTX2_MAX_MTU;
589+
netdev->max_mtu = otx2_get_max_mtu(vf);
590590

591591
INIT_WORK(&vf->reset_task, otx2vf_reset_task);
592592

0 commit comments

Comments
 (0)