Branch data Line data Source code
1 : : /* SPDX-License-Identifier: BSD-3-Clause
2 : : * Copyright(C) 2021 Marvell.
3 : : */
4 : : #include "cn10k_ethdev.h"
5 : : #include "cn10k_flow.h"
6 : : #include "cn10k_rx.h"
7 : : #include "cn10k_tx.h"
8 : : #include "cnxk_flow.h"
9 : :
10 : : static uint16_t
11 [ # # ]: 0 : nix_rx_offload_flags(struct rte_eth_dev *eth_dev)
12 : : {
13 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
14 : : struct rte_eth_dev_data *data = eth_dev->data;
15 : : struct rte_eth_conf *conf = &data->dev_conf;
16 : : struct rte_eth_rxmode *rxmode = &conf->rxmode;
17 : : uint16_t flags = 0;
18 : :
19 [ # # ]: 0 : if (rxmode->mq_mode == RTE_ETH_MQ_RX_RSS &&
20 [ # # ]: 0 : (dev->rx_offloads & RTE_ETH_RX_OFFLOAD_RSS_HASH))
21 : : flags |= NIX_RX_OFFLOAD_RSS_F;
22 : :
23 [ # # ]: 0 : if (dev->rx_offloads &
24 : : (RTE_ETH_RX_OFFLOAD_TCP_CKSUM | RTE_ETH_RX_OFFLOAD_UDP_CKSUM))
25 : 0 : flags |= NIX_RX_OFFLOAD_CHECKSUM_F;
26 : :
27 [ # # ]: 0 : if (dev->rx_offloads &
28 : : (RTE_ETH_RX_OFFLOAD_IPV4_CKSUM | RTE_ETH_RX_OFFLOAD_OUTER_IPV4_CKSUM))
29 : 0 : flags |= NIX_RX_OFFLOAD_CHECKSUM_F;
30 : :
31 [ # # ]: 0 : if (dev->rx_offloads & RTE_ETH_RX_OFFLOAD_SCATTER)
32 : 0 : flags |= NIX_RX_MULTI_SEG_F;
33 : :
34 [ # # # # ]: 0 : if ((dev->rx_offloads & RTE_ETH_RX_OFFLOAD_TIMESTAMP) || dev->ptp_en)
35 : 0 : flags |= NIX_RX_OFFLOAD_TSTAMP_F;
36 : :
37 [ # # ]: 0 : if (!dev->ptype_disable)
38 : 0 : flags |= NIX_RX_OFFLOAD_PTYPE_F;
39 : :
40 [ # # # # ]: 0 : if (dev->rx_offloads & RTE_ETH_RX_OFFLOAD_SECURITY && !dev->nix.custom_inb_sa)
41 : 0 : flags |= NIX_RX_OFFLOAD_SECURITY_F;
42 : :
43 : 0 : return flags;
44 : : }
45 : :
46 : : static uint16_t
47 [ # # ]: 0 : nix_tx_offload_flags(struct rte_eth_dev *eth_dev)
48 : : {
49 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
50 : 0 : uint64_t conf = dev->tx_offloads;
51 : : struct roc_nix *nix = &dev->nix;
52 : : uint16_t flags = 0;
53 : :
54 : : /* Fastpath is dependent on these enums */
55 : : RTE_BUILD_BUG_ON(RTE_MBUF_F_TX_TCP_CKSUM != (1ULL << 52));
56 : : RTE_BUILD_BUG_ON(RTE_MBUF_F_TX_SCTP_CKSUM != (2ULL << 52));
57 : : RTE_BUILD_BUG_ON(RTE_MBUF_F_TX_UDP_CKSUM != (3ULL << 52));
58 : : RTE_BUILD_BUG_ON(RTE_MBUF_F_TX_IP_CKSUM != (1ULL << 54));
59 : : RTE_BUILD_BUG_ON(RTE_MBUF_F_TX_IPV4 != (1ULL << 55));
60 : : RTE_BUILD_BUG_ON(RTE_MBUF_F_TX_OUTER_IP_CKSUM != (1ULL << 58));
61 : : RTE_BUILD_BUG_ON(RTE_MBUF_F_TX_OUTER_IPV4 != (1ULL << 59));
62 : : RTE_BUILD_BUG_ON(RTE_MBUF_F_TX_OUTER_IPV6 != (1ULL << 60));
63 : : RTE_BUILD_BUG_ON(RTE_MBUF_F_TX_OUTER_UDP_CKSUM != (1ULL << 41));
64 : : RTE_BUILD_BUG_ON(RTE_MBUF_L2_LEN_BITS != 7);
65 : : RTE_BUILD_BUG_ON(RTE_MBUF_L3_LEN_BITS != 9);
66 : : RTE_BUILD_BUG_ON(RTE_MBUF_OUTL2_LEN_BITS != 7);
67 : : RTE_BUILD_BUG_ON(RTE_MBUF_OUTL3_LEN_BITS != 9);
68 : : RTE_BUILD_BUG_ON(offsetof(struct rte_mbuf, data_off) !=
69 : : offsetof(struct rte_mbuf, buf_addr) + 16);
70 : : RTE_BUILD_BUG_ON(offsetof(struct rte_mbuf, ol_flags) !=
71 : : offsetof(struct rte_mbuf, buf_addr) + 24);
72 : : RTE_BUILD_BUG_ON(offsetof(struct rte_mbuf, pkt_len) !=
73 : : offsetof(struct rte_mbuf, ol_flags) + 12);
74 : : RTE_BUILD_BUG_ON(offsetof(struct rte_mbuf, tx_offload) !=
75 : : offsetof(struct rte_mbuf, pool) + 2 * sizeof(void *));
76 : :
77 [ # # ]: 0 : if (conf & RTE_ETH_TX_OFFLOAD_VLAN_INSERT ||
78 : : conf & RTE_ETH_TX_OFFLOAD_QINQ_INSERT)
79 : : flags |= NIX_TX_OFFLOAD_VLAN_QINQ_F;
80 : :
81 [ # # ]: 0 : if (conf & RTE_ETH_TX_OFFLOAD_OUTER_IPV4_CKSUM ||
82 : : conf & RTE_ETH_TX_OFFLOAD_OUTER_UDP_CKSUM)
83 : 0 : flags |= NIX_TX_OFFLOAD_OL3_OL4_CSUM_F;
84 : :
85 : 0 : if (conf & RTE_ETH_TX_OFFLOAD_IPV4_CKSUM ||
86 : : conf & RTE_ETH_TX_OFFLOAD_TCP_CKSUM ||
87 [ # # ]: 0 : conf & RTE_ETH_TX_OFFLOAD_UDP_CKSUM || conf & RTE_ETH_TX_OFFLOAD_SCTP_CKSUM)
88 : 0 : flags |= NIX_TX_OFFLOAD_L3_L4_CSUM_F;
89 : :
90 [ # # ]: 0 : if (!(conf & RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE))
91 : 0 : flags |= NIX_TX_OFFLOAD_MBUF_NOFF_F;
92 : :
93 [ # # ]: 0 : if (conf & RTE_ETH_TX_OFFLOAD_MULTI_SEGS)
94 : 0 : flags |= NIX_TX_MULTI_SEG_F;
95 : :
96 : : /* Enable Inner checksum for TSO */
97 [ # # ]: 0 : if (conf & RTE_ETH_TX_OFFLOAD_TCP_TSO)
98 : 0 : flags |= (NIX_TX_OFFLOAD_TSO_F | NIX_TX_OFFLOAD_L3_L4_CSUM_F);
99 : :
100 : : /* Enable Inner and Outer checksum for Tunnel TSO */
101 [ # # ]: 0 : if (conf & (RTE_ETH_TX_OFFLOAD_VXLAN_TNL_TSO |
102 : : RTE_ETH_TX_OFFLOAD_GENEVE_TNL_TSO | RTE_ETH_TX_OFFLOAD_GRE_TNL_TSO))
103 : 0 : flags |= (NIX_TX_OFFLOAD_TSO_F | NIX_TX_OFFLOAD_OL3_OL4_CSUM_F |
104 : : NIX_TX_OFFLOAD_L3_L4_CSUM_F);
105 : :
106 [ # # ]: 0 : if ((dev->rx_offloads & RTE_ETH_RX_OFFLOAD_TIMESTAMP))
107 : 0 : flags |= NIX_TX_OFFLOAD_TSTAMP_F;
108 : :
109 [ # # ]: 0 : if (conf & RTE_ETH_TX_OFFLOAD_SECURITY)
110 : 0 : flags |= NIX_TX_OFFLOAD_SECURITY_F;
111 : :
112 [ # # ]: 0 : if (dev->tx_mark)
113 : 0 : flags |= NIX_TX_OFFLOAD_VLAN_QINQ_F;
114 : :
115 [ # # ]: 0 : if (nix->tx_compl_ena)
116 : 0 : flags |= NIX_TX_OFFLOAD_MBUF_NOFF_F;
117 : :
118 : 0 : return flags;
119 : : }
120 : :
121 : : static int
122 [ # # ]: 0 : cn10k_nix_ptypes_set(struct rte_eth_dev *eth_dev, uint32_t ptype_mask)
123 : : {
124 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
125 : :
126 [ # # ]: 0 : if (ptype_mask) {
127 : 0 : dev->rx_offload_flags |= NIX_RX_OFFLOAD_PTYPE_F;
128 : 0 : dev->ptype_disable = 0;
129 : : } else {
130 : 0 : dev->rx_offload_flags &= ~NIX_RX_OFFLOAD_PTYPE_F;
131 : 0 : dev->ptype_disable = 1;
132 : : }
133 : :
134 : 0 : cn10k_eth_set_rx_function(eth_dev);
135 : 0 : return 0;
136 : : }
137 : :
138 : : static void
139 : : nix_form_default_desc(struct cnxk_eth_dev *dev, struct cn10k_eth_txq *txq,
140 : : uint16_t qid)
141 : : {
142 : : union nix_send_hdr_w0_u send_hdr_w0;
143 : :
144 : : /* Initialize the fields based on basic single segment packet */
145 : 0 : send_hdr_w0.u = 0;
146 : 0 : if (dev->tx_offload_flags & NIX_TX_NEED_EXT_HDR) {
147 : : /* 2(HDR) + 2(EXT_HDR) + 1(SG) + 1(IOVA) = 6/2 - 1 = 2 */
148 : 0 : send_hdr_w0.sizem1 = 2;
149 [ # # # # : 0 : if (dev->tx_offload_flags & NIX_TX_OFFLOAD_TSTAMP_F) {
# # ]
150 : : /* Default: one seg packet would have:
151 : : * 2(HDR) + 2(EXT) + 1(SG) + 1(IOVA) + 2(MEM)
152 : : * => 8/2 - 1 = 3
153 : : */
154 : 0 : send_hdr_w0.sizem1 = 3;
155 : :
156 : : /* To calculate the offset for send_mem,
157 : : * send_hdr->w0.sizem1 * 2
158 : : */
159 : 0 : txq->ts_mem = dev->tstamp.tx_tstamp_iova;
160 : : }
161 : : } else {
162 : : /* 2(HDR) + 1(SG) + 1(IOVA) = 4/2 - 1 = 1 */
163 : 0 : send_hdr_w0.sizem1 = 1;
164 : : }
165 : 0 : send_hdr_w0.sq = qid;
166 : 0 : txq->send_hdr_w0 = send_hdr_w0.u;
167 : : rte_wmb();
168 : : }
169 : :
170 : : static int
171 : 0 : cn10k_nix_tx_compl_setup(struct cnxk_eth_dev *dev,
172 : : struct cn10k_eth_txq *txq,
173 : : struct roc_nix_sq *sq, uint16_t nb_desc)
174 : : {
175 : : struct roc_nix_cq *cq;
176 : :
177 : 0 : cq = &dev->cqs[sq->cqid];
178 : 0 : txq->tx_compl.desc_base = (uintptr_t)cq->desc_base;
179 : 0 : txq->tx_compl.cq_door = cq->door;
180 : 0 : txq->tx_compl.cq_status = cq->status;
181 : 0 : txq->tx_compl.wdata = cq->wdata;
182 : 0 : txq->tx_compl.head = cq->head;
183 : 0 : txq->tx_compl.qmask = cq->qmask;
184 : : /* Total array size holding buffers is equal to
185 : : * number of entries in cq and sq
186 : : * max buffer in array = desc in cq + desc in sq
187 : : */
188 : 0 : txq->tx_compl.nb_desc_mask = (2 * rte_align32pow2(nb_desc)) - 1;
189 : 0 : txq->tx_compl.ena = true;
190 : :
191 : 0 : txq->tx_compl.ptr = (struct rte_mbuf **)plt_zmalloc(txq->tx_compl.nb_desc_mask *
192 : : sizeof(struct rte_mbuf *), 0);
193 [ # # ]: 0 : if (!txq->tx_compl.ptr)
194 : 0 : return -1;
195 : :
196 : : return 0;
197 : : }
198 : :
199 : : static void
200 : 0 : cn10k_nix_tx_queue_release(struct rte_eth_dev *eth_dev, uint16_t qid)
201 : : {
202 [ # # ]: 0 : struct cn10k_eth_txq *txq = eth_dev->data->tx_queues[qid];
203 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
204 : : struct roc_nix *nix = &dev->nix;
205 : :
206 [ # # ]: 0 : if (nix->tx_compl_ena) {
207 : : /* First process all CQ entries */
208 : 0 : handle_tx_completion_pkts(txq, 0);
209 : 0 : plt_free(txq->tx_compl.ptr);
210 : : }
211 : 0 : cnxk_nix_tx_queue_release(eth_dev, qid);
212 : 0 : }
213 : :
214 : : static int
215 : 0 : cn10k_nix_tx_queue_setup(struct rte_eth_dev *eth_dev, uint16_t qid, uint16_t nb_desc,
216 : : unsigned int socket, const struct rte_eth_txconf *tx_conf)
217 : : {
218 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
219 : 0 : struct roc_nix *nix = &dev->nix;
220 : : uint64_t mark_fmt, mark_flag;
221 : : struct roc_cpt_lf *inl_lf;
222 : : struct cn10k_eth_txq *txq;
223 : : struct roc_nix_sq *sq;
224 : : uint16_t crypto_qid;
225 : : int rc;
226 : :
227 : : RTE_SET_USED(socket);
228 : :
229 : : /* Common Tx queue setup */
230 : 0 : rc = cnxk_nix_tx_queue_setup(eth_dev, qid, nb_desc,
231 : : sizeof(struct cn10k_eth_txq), tx_conf);
232 [ # # ]: 0 : if (rc)
233 : : return rc;
234 : :
235 : 0 : sq = &dev->sqs[qid];
236 : : /* Update fast path queue */
237 : 0 : txq = eth_dev->data->tx_queues[qid];
238 : 0 : txq->fc_mem = sq->fc;
239 [ # # ]: 0 : if (nix->tx_compl_ena) {
240 : 0 : rc = cn10k_nix_tx_compl_setup(dev, txq, sq, nb_desc);
241 [ # # ]: 0 : if (rc)
242 : : return rc;
243 : : }
244 : :
245 : : /* Set Txq flag for MT_LOCKFREE */
246 : 0 : txq->flag = !!(dev->tx_offloads & RTE_ETH_TX_OFFLOAD_MT_LOCKFREE);
247 : :
248 : : /* Store lmt base in tx queue for easy access */
249 : 0 : txq->lmt_base = nix->lmt_base;
250 : 0 : txq->io_addr = sq->io_addr;
251 : 0 : txq->nb_sqb_bufs_adj = sq->nb_sqb_bufs_adj;
252 : 0 : txq->sqes_per_sqb_log2 = sq->sqes_per_sqb_log2;
253 : :
254 : : /* Fetch CPT LF info for outbound if present */
255 [ # # ]: 0 : if (dev->outb.lf_base) {
256 : 0 : crypto_qid = qid % dev->outb.nb_crypto_qs;
257 : 0 : inl_lf = dev->outb.lf_base + crypto_qid;
258 : :
259 : 0 : txq->cpt_io_addr = inl_lf->io_addr;
260 : 0 : txq->cpt_fc = (uint64_t __rte_atomic *)inl_lf->fc_addr;
261 : 0 : txq->cpt_fc_sw = (int32_t __rte_atomic *)((uintptr_t)dev->outb.fc_sw_mem +
262 : 0 : crypto_qid * RTE_CACHE_LINE_SIZE);
263 : :
264 : 0 : txq->cpt_desc = inl_lf->nb_desc * 0.7;
265 : 0 : txq->sa_base = (uint64_t)dev->outb.sa_base;
266 : 0 : txq->sa_base |= (uint64_t)eth_dev->data->port_id;
267 : : PLT_STATIC_ASSERT(ROC_NIX_INL_SA_BASE_ALIGN == BIT_ULL(16));
268 : : }
269 : :
270 : : /* Restore marking flag from roc */
271 : 0 : mark_fmt = roc_nix_tm_mark_format_get(nix, &mark_flag);
272 : 0 : txq->mark_flag = mark_flag & CNXK_TM_MARK_MASK;
273 [ # # ]: 0 : txq->mark_fmt = mark_fmt & CNXK_TX_MARK_FMT_MASK;
274 : :
275 : : nix_form_default_desc(dev, txq, qid);
276 : 0 : txq->lso_tun_fmt = dev->lso_tun_fmt;
277 : 0 : return 0;
278 : : }
279 : :
280 : : static int
281 [ # # ]: 0 : cn10k_nix_rx_queue_setup(struct rte_eth_dev *eth_dev, uint16_t qid,
282 : : uint16_t nb_desc, unsigned int socket,
283 : : const struct rte_eth_rxconf *rx_conf,
284 : : struct rte_mempool *mp)
285 : : {
286 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
287 : : struct cn10k_eth_rxq *rxq;
288 : : struct roc_nix_rq *rq;
289 : : struct roc_nix_cq *cq;
290 : : int rc;
291 : :
292 : : RTE_SET_USED(socket);
293 : :
294 : : /* CQ Errata needs min 4K ring */
295 [ # # ]: 0 : if (dev->cq_min_4k && nb_desc < 4096)
296 : : nb_desc = 4096;
297 : :
298 : : /* Common Rx queue setup */
299 : 0 : rc = cnxk_nix_rx_queue_setup(eth_dev, qid, nb_desc,
300 : : sizeof(struct cn10k_eth_rxq), rx_conf, mp);
301 [ # # ]: 0 : if (rc)
302 : : return rc;
303 : :
304 : : /* Do initial mtu setup for RQ0 before device start */
305 [ # # ]: 0 : if (!qid) {
306 : 0 : rc = nix_recalc_mtu(eth_dev);
307 [ # # ]: 0 : if (rc)
308 : : return rc;
309 : :
310 : : /* Update offload flags */
311 : 0 : dev->rx_offload_flags = nix_rx_offload_flags(eth_dev);
312 : 0 : dev->tx_offload_flags = nix_tx_offload_flags(eth_dev);
313 : : }
314 : :
315 : 0 : rq = &dev->rqs[qid];
316 : 0 : cq = &dev->cqs[qid];
317 : :
318 : : /* Update fast path queue */
319 : 0 : rxq = eth_dev->data->rx_queues[qid];
320 : 0 : rxq->rq = qid;
321 : 0 : rxq->desc = (uintptr_t)cq->desc_base;
322 : 0 : rxq->cq_door = cq->door;
323 : 0 : rxq->cq_status = cq->status;
324 : 0 : rxq->wdata = cq->wdata;
325 : 0 : rxq->head = cq->head;
326 : 0 : rxq->qmask = cq->qmask;
327 : 0 : rxq->tstamp = &dev->tstamp;
328 : :
329 : : /* Data offset from data to start of mbuf is first_skip */
330 : 0 : rxq->data_off = rq->first_skip;
331 : 0 : rxq->mbuf_initializer = cnxk_nix_rxq_mbuf_setup(dev);
332 : :
333 : : /* Setup security related info */
334 [ # # ]: 0 : if (dev->rx_offload_flags & NIX_RX_OFFLOAD_SECURITY_F) {
335 : 0 : rxq->lmt_base = dev->nix.lmt_base;
336 : 0 : rxq->sa_base = roc_nix_inl_inb_sa_base_get(&dev->nix,
337 : 0 : dev->inb.inl_dev);
338 : : }
339 : :
340 : : /* Lookup mem */
341 : 0 : rxq->lookup_mem = cnxk_nix_fastpath_lookup_mem_get();
342 : 0 : return 0;
343 : : }
344 : :
345 : : static void
346 : 0 : cn10k_nix_rx_queue_meta_aura_update(struct rte_eth_dev *eth_dev)
347 : : {
348 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
349 : : struct cnxk_eth_rxq_sp *rxq_sp;
350 : : struct cn10k_eth_rxq *rxq;
351 : : struct roc_nix_rq *rq;
352 : : int i;
353 : :
354 : : /* Update Aura handle for fastpath rx queues */
355 [ # # ]: 0 : for (i = 0; i < eth_dev->data->nb_rx_queues; i++) {
356 : 0 : rq = &dev->rqs[i];
357 : 0 : rxq = eth_dev->data->rx_queues[i];
358 : 0 : rxq->meta_aura = rq->meta_aura_handle;
359 : 0 : rxq->meta_pool = dev->nix.meta_mempool;
360 : : /* Assume meta packet from normal aura if meta aura is not setup
361 : : */
362 [ # # ]: 0 : if (!rxq->meta_aura) {
363 : : rxq_sp = cnxk_eth_rxq_to_sp(rxq);
364 : 0 : rxq->meta_aura = rxq_sp->qconf.mp->pool_id;
365 : 0 : rxq->meta_pool = (uintptr_t)rxq_sp->qconf.mp;
366 : : }
367 : : }
368 : : /* Store mempool in lookup mem */
369 : 0 : cnxk_nix_lookup_mem_metapool_set(dev);
370 : 0 : }
371 : :
372 : : static int
373 : 0 : cn10k_nix_tx_queue_stop(struct rte_eth_dev *eth_dev, uint16_t qidx)
374 : : {
375 : 0 : struct cn10k_eth_txq *txq = eth_dev->data->tx_queues[qidx];
376 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
377 : 0 : uint16_t flags = dev->tx_offload_flags;
378 : 0 : struct roc_nix *nix = &dev->nix;
379 : 0 : uint32_t head = 0, tail = 0;
380 : : int rc;
381 : :
382 : 0 : rc = cnxk_nix_tx_queue_stop(eth_dev, qidx);
383 [ # # ]: 0 : if (rc)
384 : : return rc;
385 : :
386 : : /* Clear fc cache pkts to trigger worker stop */
387 : 0 : txq->fc_cache_pkts = 0;
388 : :
389 [ # # # # ]: 0 : if ((flags & NIX_TX_OFFLOAD_MBUF_NOFF_F) && txq->tx_compl.ena) {
390 : 0 : struct roc_nix_sq *sq = &dev->sqs[qidx];
391 : : do {
392 : 0 : handle_tx_completion_pkts(txq, flags & NIX_TX_VWQE_F);
393 : : /* Check if SQ is empty */
394 : 0 : roc_nix_sq_head_tail_get(nix, sq->qid, &head, &tail);
395 [ # # ]: 0 : if (head != tail)
396 : 0 : continue;
397 : :
398 : : /* Check if completion CQ is empty */
399 : 0 : roc_nix_cq_head_tail_get(nix, sq->cqid, &head, &tail);
400 [ # # ]: 0 : } while (head != tail);
401 : : }
402 : :
403 : : return 0;
404 : : }
405 : :
406 : : static int
407 : 0 : cn10k_nix_configure(struct rte_eth_dev *eth_dev)
408 : : {
409 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
410 : : int rc;
411 : :
412 : : /* Common nix configure */
413 : 0 : rc = cnxk_nix_configure(eth_dev);
414 [ # # ]: 0 : if (rc)
415 : : return rc;
416 : :
417 [ # # ]: 0 : if (dev->tx_offloads & RTE_ETH_TX_OFFLOAD_SECURITY ||
418 [ # # ]: 0 : dev->rx_offloads & RTE_ETH_RX_OFFLOAD_SECURITY) {
419 : : /* Register callback to handle security error work */
420 : 0 : roc_nix_inl_cb_register(cn10k_eth_sec_sso_work_cb, NULL);
421 : : }
422 : :
423 : : /* Update offload flags */
424 : 0 : dev->rx_offload_flags = nix_rx_offload_flags(eth_dev);
425 : 0 : dev->tx_offload_flags = nix_tx_offload_flags(eth_dev);
426 : :
427 : : /* reset reassembly dynfield/flag offset */
428 : 0 : dev->reass_dynfield_off = -1;
429 : 0 : dev->reass_dynflag_bit = -1;
430 : :
431 : 0 : plt_nix_dbg("Configured port%d platform specific rx_offload_flags=%x"
432 : : " tx_offload_flags=0x%x",
433 : : eth_dev->data->port_id, dev->rx_offload_flags,
434 : : dev->tx_offload_flags);
435 : 0 : return 0;
436 : : }
437 : :
438 : : /* Function to enable ptp config for VFs */
439 : : static void
440 : 0 : nix_ptp_enable_vf(struct rte_eth_dev *eth_dev)
441 : : {
442 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
443 : :
444 [ # # ]: 0 : if (nix_recalc_mtu(eth_dev))
445 : 0 : plt_err("Failed to set MTU size for ptp");
446 : :
447 : 0 : dev->rx_offload_flags |= NIX_RX_OFFLOAD_TSTAMP_F;
448 : :
449 : : /* Setting up the function pointers as per new offload flags */
450 : 0 : cn10k_eth_set_rx_function(eth_dev);
451 : 0 : cn10k_eth_set_tx_function(eth_dev);
452 : 0 : }
453 : :
454 : : static uint16_t
455 : 0 : nix_ptp_vf_burst(void *queue, struct rte_mbuf **mbufs, uint16_t pkts)
456 : : {
457 : : struct cn10k_eth_rxq *rxq = queue;
458 : : struct cnxk_eth_rxq_sp *rxq_sp;
459 : : struct rte_eth_dev *eth_dev;
460 : :
461 : : RTE_SET_USED(mbufs);
462 : : RTE_SET_USED(pkts);
463 : :
464 : : rxq_sp = cnxk_eth_rxq_to_sp(rxq);
465 : 0 : eth_dev = rxq_sp->dev->eth_dev;
466 : 0 : nix_ptp_enable_vf(eth_dev);
467 : :
468 : 0 : return 0;
469 : : }
470 : :
471 : : static int
472 : 0 : cn10k_nix_ptp_info_update_cb(struct roc_nix *nix, bool ptp_en)
473 : : {
474 : : struct cnxk_eth_dev *dev = (struct cnxk_eth_dev *)nix;
475 : : struct rte_eth_dev *eth_dev;
476 : : struct cn10k_eth_rxq *rxq;
477 : : int i, rc;
478 : :
479 [ # # ]: 0 : if (!dev)
480 : : return -EINVAL;
481 : :
482 : 0 : eth_dev = dev->eth_dev;
483 [ # # ]: 0 : if (!eth_dev)
484 : : return -EINVAL;
485 : :
486 : 0 : dev->ptp_en = ptp_en;
487 : :
488 [ # # ]: 0 : for (i = 0; i < eth_dev->data->nb_rx_queues; i++) {
489 : 0 : rxq = eth_dev->data->rx_queues[i];
490 : 0 : rxq->mbuf_initializer = cnxk_nix_rxq_mbuf_setup(dev);
491 : : }
492 : :
493 [ # # # # : 0 : if (roc_nix_is_vf_or_sdp(nix) && !(roc_nix_is_sdp(nix)) &&
# # ]
494 : 0 : !(roc_nix_is_lbk(nix))) {
495 : : /* In case of VF, setting of MTU cannot be done directly in this
496 : : * function as this is running as part of MBOX request(PF->VF)
497 : : * and MTU setting also requires MBOX message to be
498 : : * sent(VF->PF)
499 : : */
500 [ # # ]: 0 : if (dev->ptp_en) {
501 : 0 : rc = rte_mbuf_dyn_rx_timestamp_register
502 : : (&dev->tstamp.tstamp_dynfield_offset,
503 : : &dev->tstamp.rx_tstamp_dynflag);
504 [ # # ]: 0 : if (rc != 0) {
505 : 0 : plt_err("Failed to register Rx timestamp field/flag");
506 : 0 : return -EINVAL;
507 : : }
508 : : }
509 : 0 : eth_dev->rx_pkt_burst = nix_ptp_vf_burst;
510 : 0 : rte_eth_fp_ops[eth_dev->data->port_id].rx_pkt_burst = eth_dev->rx_pkt_burst;
511 : : rte_mb();
512 [ # # ]: 0 : if (dev->cnxk_sso_ptp_tstamp_cb)
513 : 0 : dev->cnxk_sso_ptp_tstamp_cb(eth_dev->data->port_id,
514 : 0 : NIX_RX_OFFLOAD_TSTAMP_F, dev->ptp_en);
515 : :
516 : : }
517 : :
518 : : return 0;
519 : : }
520 : :
521 : : static int
522 : 0 : cn10k_nix_timesync_enable(struct rte_eth_dev *eth_dev)
523 : : {
524 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
525 : : int i, rc;
526 : :
527 : 0 : rc = cnxk_nix_timesync_enable(eth_dev);
528 [ # # ]: 0 : if (rc)
529 : : return rc;
530 : :
531 : 0 : dev->rx_offload_flags |= NIX_RX_OFFLOAD_TSTAMP_F;
532 : 0 : dev->tx_offload_flags |= NIX_TX_OFFLOAD_TSTAMP_F;
533 : :
534 [ # # ]: 0 : for (i = 0; i < eth_dev->data->nb_tx_queues; i++)
535 [ # # ]: 0 : nix_form_default_desc(dev, eth_dev->data->tx_queues[i], i);
536 : :
537 : : /* Setting up the rx[tx]_offload_flags due to change
538 : : * in rx[tx]_offloads.
539 : : */
540 : 0 : cn10k_eth_set_rx_function(eth_dev);
541 : 0 : cn10k_eth_set_tx_function(eth_dev);
542 : 0 : return 0;
543 : : }
544 : :
545 : : static int
546 : 0 : cn10k_nix_timesync_disable(struct rte_eth_dev *eth_dev)
547 : : {
548 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
549 : : int i, rc;
550 : :
551 : 0 : rc = cnxk_nix_timesync_disable(eth_dev);
552 [ # # ]: 0 : if (rc)
553 : : return rc;
554 : :
555 : 0 : dev->rx_offload_flags &= ~NIX_RX_OFFLOAD_TSTAMP_F;
556 : 0 : dev->tx_offload_flags &= ~NIX_TX_OFFLOAD_TSTAMP_F;
557 : :
558 [ # # ]: 0 : for (i = 0; i < eth_dev->data->nb_tx_queues; i++)
559 [ # # ]: 0 : nix_form_default_desc(dev, eth_dev->data->tx_queues[i], i);
560 : :
561 : : /* Setting up the rx[tx]_offload_flags due to change
562 : : * in rx[tx]_offloads.
563 : : */
564 : 0 : cn10k_eth_set_rx_function(eth_dev);
565 : 0 : cn10k_eth_set_tx_function(eth_dev);
566 : 0 : return 0;
567 : : }
568 : :
569 : : static int
570 [ # # ]: 0 : cn10k_nix_timesync_read_tx_timestamp(struct rte_eth_dev *eth_dev,
571 : : struct timespec *timestamp)
572 : : {
573 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
574 : : struct cnxk_timesync_info *tstamp = &dev->tstamp;
575 : : uint64_t ns;
576 : :
577 [ # # ]: 0 : if (*tstamp->tx_tstamp == 0)
578 : : return -EINVAL;
579 : :
580 : 0 : *tstamp->tx_tstamp = ((*tstamp->tx_tstamp >> 32) * NSEC_PER_SEC) +
581 [ # # ]: 0 : (*tstamp->tx_tstamp & 0xFFFFFFFFUL);
582 : : ns = rte_timecounter_update(&dev->tx_tstamp_tc, *tstamp->tx_tstamp);
583 : 0 : *timestamp = rte_ns_to_timespec(ns);
584 : 0 : *tstamp->tx_tstamp = 0;
585 : : rte_wmb();
586 : :
587 : 0 : return 0;
588 : : }
589 : :
590 : : static int
591 : 0 : cn10k_nix_dev_start(struct rte_eth_dev *eth_dev)
592 : : {
593 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
594 : 0 : struct roc_nix *nix = &dev->nix;
595 : : int rc;
596 : :
597 : : /* Common eth dev start */
598 : 0 : rc = cnxk_nix_dev_start(eth_dev);
599 [ # # ]: 0 : if (rc)
600 : : return rc;
601 : :
602 : : /* Update VF about data off shifted by 8 bytes if PTP already
603 : : * enabled in PF owning this VF
604 : : */
605 [ # # # # : 0 : if (dev->ptp_en && (!roc_nix_is_pf(nix) && (!roc_nix_is_sdp(nix))))
# # ]
606 : 0 : nix_ptp_enable_vf(eth_dev);
607 : :
608 : : /* Setting up the rx[tx]_offload_flags due to change
609 : : * in rx[tx]_offloads.
610 : : */
611 : 0 : dev->rx_offload_flags |= nix_rx_offload_flags(eth_dev);
612 : 0 : dev->tx_offload_flags |= nix_tx_offload_flags(eth_dev);
613 : :
614 [ # # ]: 0 : if (dev->rx_offload_flags & NIX_RX_OFFLOAD_SECURITY_F)
615 : 0 : cn10k_nix_rx_queue_meta_aura_update(eth_dev);
616 : :
617 : : /* Set flags for Rx Inject feature */
618 [ # # ]: 0 : if (roc_idev_nix_rx_inject_get(nix->port_id))
619 : 0 : dev->rx_offload_flags |= NIX_RX_SEC_REASSEMBLY_F;
620 : :
621 : 0 : cn10k_eth_set_tx_function(eth_dev);
622 : 0 : cn10k_eth_set_rx_function(eth_dev);
623 : 0 : return 0;
624 : : }
625 : :
626 : : static int
627 [ # # ]: 0 : cn10k_nix_reassembly_capability_get(struct rte_eth_dev *eth_dev,
628 : : struct rte_eth_ip_reassembly_params *reassembly_capa)
629 : : {
630 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
631 : : int rc = -ENOTSUP;
632 : : RTE_SET_USED(eth_dev);
633 : :
634 [ # # ]: 0 : if (!roc_feature_nix_has_reass())
635 : : return -ENOTSUP;
636 : :
637 [ # # ]: 0 : if (dev->rx_offloads & RTE_ETH_RX_OFFLOAD_SECURITY) {
638 : 0 : reassembly_capa->timeout_ms = 60 * 1000;
639 : 0 : reassembly_capa->max_frags = 4;
640 : 0 : reassembly_capa->flags = RTE_ETH_DEV_REASSEMBLY_F_IPV4 |
641 : : RTE_ETH_DEV_REASSEMBLY_F_IPV6;
642 : : rc = 0;
643 : : }
644 : :
645 : : return rc;
646 : : }
647 : :
648 : : static int
649 : 0 : cn10k_nix_reassembly_conf_get(struct rte_eth_dev *eth_dev,
650 : : struct rte_eth_ip_reassembly_params *conf)
651 : : {
652 : : RTE_SET_USED(eth_dev);
653 : : RTE_SET_USED(conf);
654 : 0 : return -ENOTSUP;
655 : : }
656 : :
657 : : static int
658 [ # # ]: 0 : cn10k_nix_reassembly_conf_set(struct rte_eth_dev *eth_dev,
659 : : const struct rte_eth_ip_reassembly_params *conf)
660 : : {
661 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
662 [ # # ]: 0 : struct roc_cpt_rxc_time_cfg rxc_time_cfg = {0};
663 : : int rc = 0;
664 : :
665 [ # # ]: 0 : if (!roc_feature_nix_has_reass())
666 : : return -ENOTSUP;
667 : :
668 [ # # ]: 0 : if (!conf->flags) {
669 : : /* Clear offload flags on disable */
670 [ # # ]: 0 : if (!dev->inb.nb_oop)
671 : 0 : dev->rx_offload_flags &= ~NIX_RX_REAS_F;
672 : 0 : dev->inb.reass_en = false;
673 : 0 : return 0;
674 : : }
675 : :
676 : 0 : rc = roc_nix_reassembly_configure(&rxc_time_cfg, conf->timeout_ms);
677 [ # # # # ]: 0 : if (!rc && dev->rx_offloads & RTE_ETH_RX_OFFLOAD_SECURITY) {
678 : 0 : dev->rx_offload_flags |= NIX_RX_REAS_F;
679 : 0 : dev->inb.reass_en = true;
680 : : }
681 : :
682 : : return rc;
683 : : }
684 : :
685 : : static int
686 : : cn10k_nix_rx_avail_get(struct cn10k_eth_rxq *rxq)
687 : : {
688 : : uint32_t qmask = rxq->qmask;
689 : : uint64_t reg, head, tail;
690 : : int available;
691 : :
692 : : /* Use LDADDA version to avoid reorder */
693 : : reg = roc_atomic64_add_sync(rxq->wdata, rxq->cq_status);
694 : : /* CQ_OP_STATUS operation error */
695 : : if (reg & BIT_ULL(NIX_CQ_OP_STAT_OP_ERR) ||
696 : : reg & BIT_ULL(NIX_CQ_OP_STAT_CQ_ERR))
697 : : return 0;
698 : : tail = reg & 0xFFFFF;
699 : : head = (reg >> 20) & 0xFFFFF;
700 : : if (tail < head)
701 : : available = tail - head + qmask + 1;
702 : : else
703 : : available = tail - head;
704 : :
705 : : return available;
706 : : }
707 : :
708 : : static int
709 : 0 : cn10k_rx_descriptor_dump(const struct rte_eth_dev *eth_dev, uint16_t qid,
710 : : uint16_t offset, uint16_t num, FILE *file)
711 : : {
712 : : struct cn10k_eth_rxq *rxq = eth_dev->data->rx_queues[qid];
713 : : const uint64_t data_off = rxq->data_off;
714 : : const uint32_t qmask = rxq->qmask;
715 : : const uintptr_t desc = rxq->desc;
716 : : union cpt_parse_hdr_u *cpth;
717 : : uint32_t head = rxq->head;
718 : : struct nix_cqe_hdr_s *cq;
719 : : uint16_t count = 0;
720 : : int available_pkts;
721 : : uint64_t cq_w1;
722 : :
723 : : available_pkts = cn10k_nix_rx_avail_get(rxq);
724 : :
725 [ # # ]: 0 : if ((offset + num - 1) >= available_pkts) {
726 : 0 : plt_err("Invalid BD num=%u", num);
727 : 0 : return -EINVAL;
728 : : }
729 : :
730 : : while (count < num) {
731 : : cq = (struct nix_cqe_hdr_s *)(desc + CQE_SZ(head) +
732 : : count + offset);
733 : : cq_w1 = *((const uint64_t *)cq + 1);
734 : : if (cq_w1 & BIT(11)) {
735 : : rte_iova_t buff = *((rte_iova_t *)((uint64_t *)cq + 9));
736 : : struct rte_mbuf *mbuf =
737 : : (struct rte_mbuf *)(buff - data_off);
738 : : cpth = (union cpt_parse_hdr_u *)((uintptr_t)mbuf + (uint16_t)data_off);
739 : : roc_cpt_parse_hdr_dump(file, cpth);
740 : : } else {
741 : : roc_nix_cqe_dump(file, cq);
742 : : }
743 : :
744 : : count++;
745 : : head &= qmask;
746 : : }
747 : : return 0;
748 : : }
749 : :
750 : : static int
751 : 0 : cn10k_nix_tm_mark_vlan_dei(struct rte_eth_dev *eth_dev, int mark_green,
752 : : int mark_yellow, int mark_red,
753 : : struct rte_tm_error *error)
754 : : {
755 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
756 : 0 : struct roc_nix *roc_nix = &dev->nix;
757 : : uint64_t mark_fmt, mark_flag;
758 : : int rc, i;
759 : :
760 : 0 : rc = cnxk_nix_tm_mark_vlan_dei(eth_dev, mark_green, mark_yellow,
761 : : mark_red, error);
762 : :
763 [ # # ]: 0 : if (rc)
764 : 0 : goto exit;
765 : :
766 : 0 : mark_fmt = roc_nix_tm_mark_format_get(roc_nix, &mark_flag);
767 [ # # ]: 0 : if (mark_flag) {
768 : 0 : dev->tx_offload_flags |= NIX_TX_OFFLOAD_VLAN_QINQ_F;
769 : 0 : dev->tx_mark = true;
770 : : } else {
771 : 0 : dev->tx_mark = false;
772 [ # # ]: 0 : if (!(dev->tx_offloads & RTE_ETH_TX_OFFLOAD_VLAN_INSERT ||
773 : : dev->tx_offloads & RTE_ETH_TX_OFFLOAD_QINQ_INSERT))
774 : 0 : dev->tx_offload_flags &= ~NIX_TX_OFFLOAD_VLAN_QINQ_F;
775 : : }
776 : :
777 [ # # ]: 0 : for (i = 0; i < eth_dev->data->nb_tx_queues; i++) {
778 : 0 : struct cn10k_eth_txq *txq = eth_dev->data->tx_queues[i];
779 : :
780 : 0 : txq->mark_flag = mark_flag & CNXK_TM_MARK_MASK;
781 : 0 : txq->mark_fmt = mark_fmt & CNXK_TX_MARK_FMT_MASK;
782 : : }
783 : 0 : cn10k_eth_set_tx_function(eth_dev);
784 : 0 : exit:
785 : 0 : return rc;
786 : : }
787 : :
788 : : static int
789 : 0 : cn10k_nix_tm_mark_ip_ecn(struct rte_eth_dev *eth_dev, int mark_green,
790 : : int mark_yellow, int mark_red,
791 : : struct rte_tm_error *error)
792 : : {
793 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
794 : 0 : struct roc_nix *roc_nix = &dev->nix;
795 : : uint64_t mark_fmt, mark_flag;
796 : : int rc, i;
797 : :
798 : 0 : rc = cnxk_nix_tm_mark_ip_ecn(eth_dev, mark_green, mark_yellow, mark_red,
799 : : error);
800 [ # # ]: 0 : if (rc)
801 : 0 : goto exit;
802 : :
803 : 0 : mark_fmt = roc_nix_tm_mark_format_get(roc_nix, &mark_flag);
804 [ # # ]: 0 : if (mark_flag) {
805 : 0 : dev->tx_offload_flags |= NIX_TX_OFFLOAD_VLAN_QINQ_F;
806 : 0 : dev->tx_mark = true;
807 : : } else {
808 : 0 : dev->tx_mark = false;
809 [ # # ]: 0 : if (!(dev->tx_offloads & RTE_ETH_TX_OFFLOAD_VLAN_INSERT ||
810 : : dev->tx_offloads & RTE_ETH_TX_OFFLOAD_QINQ_INSERT))
811 : 0 : dev->tx_offload_flags &= ~NIX_TX_OFFLOAD_VLAN_QINQ_F;
812 : : }
813 : :
814 [ # # ]: 0 : for (i = 0; i < eth_dev->data->nb_tx_queues; i++) {
815 : 0 : struct cn10k_eth_txq *txq = eth_dev->data->tx_queues[i];
816 : :
817 : 0 : txq->mark_flag = mark_flag & CNXK_TM_MARK_MASK;
818 : 0 : txq->mark_fmt = mark_fmt & CNXK_TX_MARK_FMT_MASK;
819 : : }
820 : 0 : cn10k_eth_set_tx_function(eth_dev);
821 : 0 : exit:
822 : 0 : return rc;
823 : : }
824 : :
825 : : static int
826 : 0 : cn10k_nix_tm_mark_ip_dscp(struct rte_eth_dev *eth_dev, int mark_green,
827 : : int mark_yellow, int mark_red,
828 : : struct rte_tm_error *error)
829 : : {
830 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
831 : 0 : struct roc_nix *roc_nix = &dev->nix;
832 : : uint64_t mark_fmt, mark_flag;
833 : : int rc, i;
834 : :
835 : 0 : rc = cnxk_nix_tm_mark_ip_dscp(eth_dev, mark_green, mark_yellow,
836 : : mark_red, error);
837 [ # # ]: 0 : if (rc)
838 : 0 : goto exit;
839 : :
840 : 0 : mark_fmt = roc_nix_tm_mark_format_get(roc_nix, &mark_flag);
841 [ # # ]: 0 : if (mark_flag) {
842 : 0 : dev->tx_offload_flags |= NIX_TX_OFFLOAD_VLAN_QINQ_F;
843 : 0 : dev->tx_mark = true;
844 : : } else {
845 : 0 : dev->tx_mark = false;
846 [ # # ]: 0 : if (!(dev->tx_offloads & RTE_ETH_TX_OFFLOAD_VLAN_INSERT ||
847 : : dev->tx_offloads & RTE_ETH_TX_OFFLOAD_QINQ_INSERT))
848 : 0 : dev->tx_offload_flags &= ~NIX_TX_OFFLOAD_VLAN_QINQ_F;
849 : : }
850 : :
851 [ # # ]: 0 : for (i = 0; i < eth_dev->data->nb_tx_queues; i++) {
852 : 0 : struct cn10k_eth_txq *txq = eth_dev->data->tx_queues[i];
853 : :
854 : 0 : txq->mark_flag = mark_flag & CNXK_TM_MARK_MASK;
855 : 0 : txq->mark_fmt = mark_fmt & CNXK_TX_MARK_FMT_MASK;
856 : : }
857 : 0 : cn10k_eth_set_tx_function(eth_dev);
858 : 0 : exit:
859 : 0 : return rc;
860 : : }
861 : :
862 : : /* Update platform specific eth dev ops */
863 : : static void
864 : 0 : nix_eth_dev_ops_override(void)
865 : : {
866 : : static int init_once;
867 : :
868 [ # # ]: 0 : if (init_once)
869 : : return;
870 : 0 : init_once = 1;
871 : :
872 : : /* Update platform specific ops */
873 : 0 : cnxk_eth_dev_ops.dev_configure = cn10k_nix_configure;
874 : 0 : cnxk_eth_dev_ops.tx_queue_setup = cn10k_nix_tx_queue_setup;
875 : 0 : cnxk_eth_dev_ops.rx_queue_setup = cn10k_nix_rx_queue_setup;
876 : 0 : cnxk_eth_dev_ops.tx_queue_release = cn10k_nix_tx_queue_release;
877 : 0 : cnxk_eth_dev_ops.tx_queue_stop = cn10k_nix_tx_queue_stop;
878 : 0 : cnxk_eth_dev_ops.dev_start = cn10k_nix_dev_start;
879 : 0 : cnxk_eth_dev_ops.dev_ptypes_set = cn10k_nix_ptypes_set;
880 : 0 : cnxk_eth_dev_ops.timesync_enable = cn10k_nix_timesync_enable;
881 : 0 : cnxk_eth_dev_ops.timesync_disable = cn10k_nix_timesync_disable;
882 : 0 : cnxk_eth_dev_ops.timesync_read_tx_timestamp =
883 : : cn10k_nix_timesync_read_tx_timestamp;
884 : 0 : cnxk_eth_dev_ops.ip_reassembly_capability_get =
885 : : cn10k_nix_reassembly_capability_get;
886 : 0 : cnxk_eth_dev_ops.ip_reassembly_conf_get = cn10k_nix_reassembly_conf_get;
887 : 0 : cnxk_eth_dev_ops.ip_reassembly_conf_set = cn10k_nix_reassembly_conf_set;
888 : 0 : cnxk_eth_dev_ops.eth_rx_descriptor_dump = cn10k_rx_descriptor_dump;
889 : : }
890 : :
891 : : /* Update platform specific tm ops */
892 : : static void
893 : : nix_tm_ops_override(void)
894 : : {
895 : : static int init_once;
896 : :
897 [ # # ]: 0 : if (init_once)
898 : : return;
899 : 0 : init_once = 1;
900 : :
901 : : /* Update platform specific ops */
902 : 0 : cnxk_tm_ops.mark_vlan_dei = cn10k_nix_tm_mark_vlan_dei;
903 : 0 : cnxk_tm_ops.mark_ip_ecn = cn10k_nix_tm_mark_ip_ecn;
904 : 0 : cnxk_tm_ops.mark_ip_dscp = cn10k_nix_tm_mark_ip_dscp;
905 : : }
906 : :
907 : : static void
908 : : npc_flow_ops_override(void)
909 : : {
910 : : static int init_once;
911 : :
912 [ # # ]: 0 : if (init_once)
913 : : return;
914 : 0 : init_once = 1;
915 : :
916 : : /* Update platform specific ops */
917 : 0 : cnxk_flow_ops.create = cn10k_flow_create;
918 : 0 : cnxk_flow_ops.destroy = cn10k_flow_destroy;
919 : 0 : cnxk_flow_ops.info_get = cn10k_flow_info_get;
920 : :
921 : 0 : cnxk_flow_ops.configure = cnxk_flow_configure;
922 : 0 : cnxk_flow_ops.pattern_template_create = cnxk_flow_pattern_template_create;
923 : 0 : cnxk_flow_ops.pattern_template_destroy = cnxk_flow_pattern_template_destroy;
924 : 0 : cnxk_flow_ops.actions_template_create = cnxk_flow_actions_template_create;
925 : 0 : cnxk_flow_ops.actions_template_destroy = cnxk_flow_actions_template_destroy;
926 : 0 : cnxk_flow_ops.template_table_create = cnxk_flow_template_table_create;
927 : 0 : cnxk_flow_ops.template_table_destroy = cnxk_flow_template_table_destroy;
928 : : }
929 : :
930 : : /* Fast-path (async) flow ops. Installed per-port in cn10k_nix_probe(). */
931 : : static const struct rte_flow_fp_ops cn10k_flow_fp_ops = {
932 : : .async_create = cnxk_flow_async_create,
933 : : .async_create_by_index = cnxk_flow_async_create_by_index,
934 : : .async_create_by_index_with_pattern = cnxk_flow_async_create_by_index_with_pattern,
935 : : .async_actions_update = cnxk_flow_async_actions_update,
936 : : .async_destroy = cnxk_flow_async_destroy,
937 : : .push = cn10k_flow_push,
938 : : .pull = cnxk_flow_pull,
939 : : };
940 : :
941 : : static int
942 : 0 : cn10k_nix_remove(struct rte_pci_device *pci_dev)
943 : : {
944 : 0 : return cnxk_nix_remove(pci_dev);
945 : : }
946 : :
947 : : static int
948 : 0 : cn10k_nix_probe(struct rte_pci_driver *pci_drv, struct rte_pci_device *pci_dev)
949 : : {
950 : : struct rte_eth_dev *eth_dev;
951 : : struct cnxk_eth_dev *dev;
952 : : int rc;
953 : :
954 : 0 : rc = roc_plt_init();
955 [ # # ]: 0 : if (rc) {
956 : 0 : plt_err("Failed to initialize platform model, rc=%d", rc);
957 : 0 : return rc;
958 : : }
959 : :
960 : 0 : nix_eth_dev_ops_override();
961 : : nix_tm_ops_override();
962 : : npc_flow_ops_override();
963 : :
964 : 0 : cn10k_eth_sec_ops_override();
965 : :
966 : : /* Common probe */
967 : 0 : rc = cnxk_nix_probe(pci_drv, pci_dev);
968 [ # # ]: 0 : if (rc)
969 : : return rc;
970 : :
971 : : /* Find eth dev allocated */
972 : 0 : eth_dev = rte_eth_dev_allocated(pci_dev->device.name);
973 [ # # ]: 0 : if (!eth_dev) {
974 : : /* Ignore if ethdev is in mid of detach state in secondary */
975 [ # # ]: 0 : if (rte_eal_process_type() != RTE_PROC_PRIMARY)
976 : : return 0;
977 : 0 : return -ENOENT;
978 : : }
979 : :
980 [ # # ]: 0 : if (rte_eal_process_type() != RTE_PROC_PRIMARY) {
981 : : /* Setup callbacks for secondary process */
982 : 0 : cn10k_eth_set_tx_function(eth_dev);
983 : 0 : cn10k_eth_set_rx_function(eth_dev);
984 : 0 : return 0;
985 : : }
986 : :
987 : : dev = cnxk_eth_pmd_priv(eth_dev);
988 : :
989 : : /* Install fast-path (async) flow ops for this port. */
990 [ # # ]: 0 : eth_dev->flow_fp_ops = &cn10k_flow_fp_ops;
991 : :
992 : : /* DROP_RE is not supported with inline IPSec for CN10K A0 and
993 : : * when vector mode is enabled.
994 : : */
995 [ # # # # ]: 0 : if (roc_errata_nix_has_no_drop_re() && !roc_env_is_asim()) {
996 : 0 : dev->ipsecd_drop_re_dis = 1;
997 : 0 : dev->vec_drop_re_dis = 1;
998 : : }
999 : :
1000 : : /* Register up msg callbacks for PTP information */
1001 : 0 : roc_nix_ptp_info_cb_register(&dev->nix, cn10k_nix_ptp_info_update_cb);
1002 : :
1003 : 0 : return 0;
1004 : : }
1005 : :
1006 : : static const struct rte_pci_id cn10k_pci_nix_map[] = {
1007 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CN10KA, PCI_DEVID_CNXK_RVU_PF),
1008 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CN10KAS, PCI_DEVID_CNXK_RVU_PF),
1009 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CNF10KA, PCI_DEVID_CNXK_RVU_PF),
1010 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CN10KB, PCI_DEVID_CNXK_RVU_PF),
1011 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CNF10KB, PCI_DEVID_CNXK_RVU_PF),
1012 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CN10KA, PCI_DEVID_CNXK_RVU_VF),
1013 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CN10KA, PCI_DEVID_CNXK_RVU_ESWITCH_VF),
1014 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CN10KB, PCI_DEVID_CNXK_RVU_ESWITCH_VF),
1015 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CNF10KA, PCI_DEVID_CNXK_RVU_ESWITCH_VF),
1016 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CN10KAS, PCI_DEVID_CNXK_RVU_VF),
1017 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CNF10KA, PCI_DEVID_CNXK_RVU_VF),
1018 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CN10KB, PCI_DEVID_CNXK_RVU_VF),
1019 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CNF10KB, PCI_DEVID_CNXK_RVU_VF),
1020 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CN10KA, PCI_DEVID_CNXK_RVU_AF_VF),
1021 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CN10KAS, PCI_DEVID_CNXK_RVU_AF_VF),
1022 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CNF10KA, PCI_DEVID_CNXK_RVU_AF_VF),
1023 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CN10KB, PCI_DEVID_CNXK_RVU_AF_VF),
1024 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CNF10KB, PCI_DEVID_CNXK_RVU_AF_VF),
1025 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CN10KA, PCI_DEVID_CNXK_RVU_SDP_VF),
1026 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CN10KAS, PCI_DEVID_CNXK_RVU_SDP_VF),
1027 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CNF10KA, PCI_DEVID_CNXK_RVU_SDP_VF),
1028 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CN10KB, PCI_DEVID_CNXK_RVU_SDP_VF),
1029 : : CNXK_PCI_ID(PCI_SUBSYSTEM_DEVID_CNF10KB, PCI_DEVID_CNXK_RVU_SDP_VF),
1030 : : {
1031 : : .vendor_id = 0,
1032 : : },
1033 : : };
1034 : :
1035 : : static struct rte_pci_driver cn10k_pci_nix = {
1036 : : .id_table = cn10k_pci_nix_map,
1037 : : .drv_flags = RTE_PCI_DRV_NEED_MAPPING | RTE_PCI_DRV_NEED_IOVA_AS_VA |
1038 : : RTE_PCI_DRV_INTR_LSC,
1039 : : .probe = cn10k_nix_probe,
1040 : : .remove = cn10k_nix_remove,
1041 : : };
1042 : :
1043 : 302 : RTE_PMD_REGISTER_PCI(net_cn10k, cn10k_pci_nix);
1044 : : RTE_PMD_REGISTER_PCI_TABLE(net_cn10k, cn10k_pci_nix_map);
1045 : : RTE_PMD_REGISTER_KMOD_DEP(net_cn10k, "vfio-pci");
|